transmission
This module provides functionality for real-time location tracking and port entry/exit detection for the Smart1 SDK.
Overview
The transmission module allows you to:
Track user location in real-time and send data to the server
Automatically detect when users enter or exit ports during active orders
Configure tracking intervals and GPS behavior
Handle offline data caching and retry logic
Monitor battery level, GPS status, and device information
Main Components
Smart1Tracker
Main singleton object that handles location tracking and port detection processes using Android Handlers for reliable background execution.
Methods:
fun start(config, provider, coroutineScope, autoRestartOnError, onGettingInPort, onGettingOutPort, onLog, onFatalError)- Starts the tracker with configuration and callbacksfun stop()- Stops all tracker processesfun notifyNewOrderInProgress()- Notifies the tracker that a new order has been set to "in progress" status to trigger immediate entry/exit port validation
Start Parameters:
config: Smart1TrackerConfig- Tracker configurationprovider: Smart1TrackerDataProvider- Location data providercoroutineScope: CoroutineScope- Coroutine scope for managing async operations (required)autoRestartOnError: Boolean = true- Auto-restart on errors (default: true)onGettingInPort: ((Int) -> Unit)? = null- Callback when entering a port (receives port ID)onGettingOutPort: ((Int) -> Unit)? = null- Callback when exiting a port (receives port ID)onLog: ((level: Smart1TrackerLogLevel, processType: Smart1TrackerProcessType?, message: String) -> Unit)? = null- Logging callbackonFatalError: (() -> Unit)? = null- Fatal error callback (only called when autoRestartOnError is false)
Smart1TrackerDataProvider
Interface that must be implemented to provide location data to the tracker.
Required Methods:
fun getLastLocation(): CoordinatesData?- Returns current device locationfun getCompanyId(): Long?- Returns the company ID (optional, can return null to use session data)
Models
Smart1TrackerConfig
Configuration for the tracker behavior.
Properties:
reportTrackingTimeIntervalInMillis: Long- Interval for sending location data (default: 20,000ms / 20 seconds, minimum: 10,000ms)inOutPortOnActiveOrderValidationTimeIntervalInMillis: Long- Interval for checking port entry/exit (default: 20,000ms / 20 seconds, minimum: 10,000ms)skipReportTrackingIfGPSIsDisabled: Boolean- Skip tracking when GPS is off (default: false)
CoordinatesData
Location data model (from core module).
Properties:
latitude: Double- Latitude coordinate (-90 to 90)longitude: Double- Longitude coordinate (-180 to 180)
Types
Smart1TrackerLogLevel
Enum representing log levels for tracker events.
Values:
INFO- Informational messages (e.g., "Sending tracker data frame")WARNING- Warning messages (e.g., GPS disabled, location null)ERROR- Error messages (e.g., tracking process errors)
Smart1TrackerProcessType
Enum representing the type of tracker process.
Values:
TRACKING- Location tracking processPORT_VALIDATION- Port entry/exit detection processUNKNOWN- Unknown or general process type
Usage Examples
Basic Tracker Setup
import com.servinformacion.smart1sdk.android.transmission.Smart1Tracker
import com.servinformacion.smart1sdk.android.transmission.Smart1TrackerDataProvider
import com.servinformacion.smart1sdk.android.transmission.model.Smart1TrackerConfig
import com.servinformacion.smart1sdk.android.transmission.types.Smart1TrackerLogLevel
import com.servinformacion.smart1sdk.android.transmission.types.Smart1TrackerProcessType
import com.servinformacion.smart1sdk.android.core.model.CoordinatesData
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.SupervisorJob
import android.util.Log
class LocationService {
private val scope = CoroutineScope(Dispatchers.Main + SupervisorJob())
fun startTracking() {
val config = Smart1TrackerConfig(
reportTrackingTimeIntervalInMillis = 30_000, // 30 seconds
inOutPortOnActiveOrderValidationTimeIntervalInMillis = 20_000, // 20 seconds
skipReportTrackingIfGPSIsDisabled = false
)
val provider = object : Smart1TrackerDataProvider {
override fun getLastLocation(): CoordinatesData? {
// Return current location from your location provider
return getCurrentLocation()
}
override fun getCompanyId(): Long? {
// Return null to use session data
return null
}
}
Smart1Tracker.start(
config = config,
provider = provider,
coroutineScope = scope,
autoRestartOnError = true,
onGettingInPort = { portId ->
// Called when entering a port
Log.d("Tracker", "Entering port: $portId")
handlePortEntry(portId)
},
onGettingOutPort = { portId ->
// Called when exiting a port
Log.d("Tracker", "Exiting port: $portId")
handlePortExit(portId)
},
onLog = { level, processType, message ->
// Optional: Log tracker events
val tag = when (processType) {
Smart1TrackerProcessType.TRACKING -> "Tracking"
Smart1TrackerProcessType.PORT_VALIDATION -> "PortValidation"
Smart1TrackerProcessType.UNKNOWN -> "Tracker"
null -> "Tracker"
}
when (level) {
Smart1TrackerLogLevel.INFO -> Log.i(tag, message)
Smart1TrackerLogLevel.WARNING -> Log.w(tag, message)
Smart1TrackerLogLevel.ERROR -> Log.e(tag, message)
}
},
onFatalError = {
// Optional: Handle fatal errors (only called if autoRestartOnError = false)
Log.e("Tracker", "Fatal error occurred")
}
)
}
fun stopTracking() {
Smart1Tracker.stop()
}
}Manual Error Handling
If you want to handle errors manually instead of auto-restart:
Smart1Tracker.start(
config = config,
provider = provider,
coroutineScope = scope,
autoRestartOnError = false, // Disable auto-restart
onGettingInPort = { portId -> handlePortEntry(portId) },
onGettingOutPort = { portId -> handlePortExit(portId) },
onLog = { level, processType, message ->
Log.d("Tracker", "[$processType] $message")
},
onFatalError = {
// Handle fatal error - must call stop() before restarting
Log.e("Tracker", "Fatal error - restarting tracker")
Smart1Tracker.stop()
// Wait a bit before restarting
scope.launch {
delay(2000)
startTracking() // Restart manually
}
}
)Notifying Order Status Changes
When you set an order to "in progress" status, you should notify the tracker to immediately validate port entry/exit instead of waiting for the next scheduled validation cycle:
class OrderManager {
fun setOrderInProgress(orderId: Int) {
// Update order status in your system
updateOrderStatus(orderId, OrderStatus.IN_PROGRESS)
// Notify the tracker to immediately check port validation
Smart1Tracker.notifyNewOrderInProgress()
// The tracker will now validate port entry/exit on the next validation cycle
// instead of waiting up to 15 minutes for the automatic refresh
}
}When to use notifyNewOrderInProgress():
When an order is set to "in progress" status
When you need immediate port validation instead of waiting for the automatic refresh cycle
After any order status change that requires immediate port detection
Benefits:
Ensures port entry/exit detection starts immediately for new active orders
Reduces validation delay to the next validation interval (typically 20 seconds)
No need to understand internal implementation details - just notify when an order starts
Important Notes
Singleton Pattern:
Smart1Trackeris a singleton object - call methods directly without instantiation.Minimum Intervals: Both tracking intervals must be at least 10,000ms (10 seconds).
GPS Validation: The tracker validates coordinates:
Latitude: -90 to 90
Longitude: -180 to 180
Automatic Retry: Failed transmissions are cached and retried when connection is restored.
Port Detection: Automatically detects entry/exit from ports during active orders.
Session Required: Must have a valid session before starting the tracker.
Port Entry/Exit Callbacks: The
onGettingInPortandonGettingOutPortcallbacks receive the port ID when detection occurs.Coroutine Scope: Must provide a coroutine scope for proper lifecycle management (required parameter).
GPS Disabled Behavior: Configure
skipReportTrackingIfGPSIsDisabledbased on your needs:true: Pauses tracking when GPS is off (saves battery)false: Continues tracking even without GPS (may use network location)Auto-Restart: When
autoRestartOnError = true(default), the tracker automatically recovers from errors. Set tofalsefor manual error handling viaonFatalError.Logging: Use the
onLogcallback to monitor tracker behavior and debug issues in production.Handler-Based: Uses Android Handlers instead of coroutine loops for more reliable background execution.
⚠️ Data Synchronization Notice
When port entry/exit events are detected (onGettingInPort or onGettingOutPort), the server may automatically update the schedules (agendas) of the active order. It is strongly recommended to refresh your app's local data (orders, schedules, ports, etc.) when these callbacks are triggered to maintain synchronization with the API and ensure data consistency across your application.
Tracker Behavior
Location Tracking Process
Checks if location provider returns valid data
Validates GPS status (if configured)
Validates coordinate ranges
Sends data frame to server
Port Detection Process
Gets current location from provider
Validates location data
Checks if user is near any port from active orders
Triggers notifications on entry/exit
Error Handling
The tracker handles errors gracefully with automatic recovery:
Temporary Errors (Auto-Recovery):
Invalid location: Skips transmission, reschedules for next interval
GPS disabled: Behavior depends on configuration, reschedules automatically
Network error: Caches data for later retry
Invalid coordinates: Logs warning, reschedules for next interval
Fatal Errors (Auto-Restart or Manual):
Handler creation failures: Triggers auto-restart (if enabled) or
onFatalErrorcallbackUnexpected exceptions: Triggers auto-restart (if enabled) or
onFatalErrorcallback
Error Recovery Modes:
Auto-Restart (default):
autoRestartOnError = trueAutomatically stops and restarts the tracker after 2 seconds
No manual intervention needed
Recommended for production
Manual Handling:
autoRestartOnError = falseCalls
onFatalErrorcallbackYou must call
Smart1Tracker.stop()before restartingUseful for custom error handling logic
Performance Considerations
Battery Impact: Lower intervals = higher battery usage
Network Usage: More frequent updates = more data transmission
Offline Support: Data is cached when offline and sent when connection returns
Background Processing: Use foreground service for reliable tracking
Best Practices
Use Foreground Service: For continuous tracking in the background
Optimize Intervals: Balance between accuracy and battery life
Handle Permissions: Ensure location permissions are granted
Lifecycle Management: Stop tracker when not needed
Error Handling: Implement robust error handling in data provider
GPS Configuration: Set
skipReportTrackingIfGPSIsDisabledappropriatelyScope Management: Provide appropriate coroutine scope for lifecycle (required)
Implement Logging: Use
onLogcallback to monitor tracker behavior in productionAuto-Restart: Use default
autoRestartOnError = truefor production reliabilitySingleton Usage: Call
Smart1Tracker.start()directly - no need to instantiateSingle Source of Truth: Maintain a centralized data store (e.g., local database) for all app data (orders, schedules, ports, etc.). When port entry/exit events trigger data updates, update this single source and let reactive observers (e.g., database listeners, Flow collectors) propagate changes automatically to all UI components. This architecture ensures:
Consistent data across the entire application
Automatic UI updates when data changes
Reduced code duplication and manual synchronization
Easier debugging and maintenance
Use Cases
Delivery Tracking: Real-time location updates for delivery drivers
Fleet Management: Monitor vehicle locations and movements
Port Operations: Automatic detection of port entry/exit
Route Compliance: Verify drivers follow assigned routes
Time Tracking: Accurate timestamps for location events
Offline Support: Continue tracking without internet connection