Devices
Devices are the moving entities you track in SpatialFlow. When a device's location crosses a geofence boundary, SpatialFlow detects the transition and triggers automated workflows.
What is a Device?
A device represents any tracked entity that sends location updates to SpatialFlow. Each device has a unique identifier, maintains location history, and can trigger geofence events when it moves in and out of defined boundaries.
Real-world examples:
- Delivery vehicles sending GPS updates every 30 seconds
- Mobile phones tracking field service technicians
- IoT sensors on shipping containers
- GPS trackers on fleet assets or equipment
Device Properties
Every device in SpatialFlow has these core properties:
Device UUID (Server ID)
- Server-generated UUID returned as
id - Required for device API route params (e.g.,
/devices/{uuid}) - Store this value and reuse it for all device routes
Device ID (Required)
- Your unique, client-defined identifier for the device
- 1-255 characters
- Must be unique within your workspace
- Used for display, filtering, and payloads (not for route params)
- Example:
truck-005,driver-alice,sensor-warehouse-1
Name (Required)
- Human-readable label for the device
- 1-255 characters
- Example: "Delivery Truck 5", "Alice's Phone", "Warehouse Sensor"
Device Type
- Categorizes the kind of device being tracked
- Defaults to
mobile - Options:
mobile: Mobile phones or tabletsvehicle: Cars, trucks, delivery vehiclesiot: IoT sensors and beaconstracker: Dedicated GPS trackersother: Custom device types
Metadata (Optional)
- Custom JSON object for storing additional attributes
- Use for filtering, routing, or application-specific data
- Example:
{
"driver_name": "Alice Johnson",
"vehicle_type": "delivery_van",
"customer_id": "ACME123",
"shift": "morning"
}
Last Known Location
- Automatically updated with each location update
- Includes latitude, longitude, and timestamp
- Used to detect geofence entry/exit transitions
Active Status
- Boolean flag to enable/disable tracking
- Inactive devices don't process location updates
- Useful for temporarily pausing tracking without deletion
Registering Devices
Via API
Register a new device using the REST API:
curl -X POST https://api.spatialflow.io/api/v1/devices \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"device_id": "truck-005",
"name": "Delivery Truck 5",
"device_type": "vehicle",
"metadata": {
"driver": "Alice Johnson",
"route": "downtown",
"capacity_kg": 1000
}
}'
Response:
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"device_id": "truck-005",
"name": "Delivery Truck 5",
"device_type": "vehicle",
"is_active": true,
"last_location": null,
"last_location_time": null,
"created_at": "2025-11-10T10:00:00Z",
"updated_at": "2025-11-10T10:00:00Z"
}
Via Dashboard
The SpatialFlow Dashboard provides a visual interface for device management:
- Navigate to Devices in the sidebar
- Click Create New Device
- Fill in the device details:
- Device ID
- Name
- Device Type
- Metadata (optional)
- Click Save
Register devices via POST /devices before sending location updates. Locations for unknown device_id values are rejected.
Sending Location Updates
Single Location Update
Send a location update for a specific device. Use the device UUID (id) returned from registration:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/location \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"latitude": 37.7749,
"longitude": -122.4194,
"timestamp": "2025-11-10T14:30:00Z",
"accuracy": 10.5,
"speed": 15.2,
"heading": 180
}'
Response:
{
"success": true,
"device_id": "truck-005",
"events_triggered": 1,
"message": "Location updated, 1 geofence events triggered"
}
Batch Updates
Update multiple devices or multiple locations in one request:
curl -X POST https://api.spatialflow.io/api/v1/devices/batch-update \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '[
{
"device_id": "truck-005",
"locations": [
{
"latitude": 37.7749,
"longitude": -122.4194,
"timestamp": "2025-11-10T14:30:00Z",
"accuracy": 10.5
},
{
"latitude": 37.7750,
"longitude": -122.4195,
"timestamp": "2025-11-10T14:31:00Z",
"accuracy": 12.0
}
]
},
{
"device_id": "truck-006",
"locations": [
{
"latitude": 37.7751,
"longitude": -122.4196,
"timestamp": "2025-11-10T14:30:00Z"
}
]
}
]'
Required Fields
When sending location updates:
Required:
latitude: Decimal degrees (-90 to 90)longitude: Decimal degrees (-180 to 180)
Optional but Recommended:
timestamp: ISO 8601 format (defaults to current time)accuracy: GPS accuracy in meters (used for filtering)speed: Speed in meters per secondheading: Direction in degrees (0-359)altitude: Altitude in metersmetadata: Additional contextual data
Location Filtering and Hysteresis
SpatialFlow implements intelligent filtering to reduce GPS jitter and prevent false triggers:
Accuracy Gate
- Rejects location updates with accuracy > 100 meters
- Ensures only high-quality GPS fixes trigger events
Distance Hysteresis
- Ignores movements < 25 meters
- Reduces noise from stationary devices with GPS drift
Time Hysteresis
- Requires 30 seconds between state transitions
- Prevents rapid enter/exit events at geofence boundaries
Cooldown Period
- 5-minute cooldown per device × geofence × event type
- Prevents alert fatigue from repeated triggers
These filters are automatically applied to all location updates. You don't need to implement your own filtering logic - SpatialFlow handles it for you.
Device Metadata
Use Cases
Device metadata is a flexible JSON field for storing custom attributes:
Fleet Management:
{
"driver_name": "Alice Johnson",
"vehicle_type": "refrigerated_truck",
"license_plate": "ABC-1234",
"vin": "1HGBH41JXMN109186",
"capacity_kg": 5000
}
Field Service:
{
"technician_name": "Bob Smith",
"technician_id": "TECH-001",
"certification": "HVAC-Master",
"tools_equipped": ["multimeter", "leak_detector"],
"shift": "morning"
}
Asset Tracking:
{
"asset_type": "shipping_container",
"container_id": "CONT-98765",
"contents": "electronics",
"customer": "ACME Corp",
"value_usd": 50000
}
IoT Sensors:
{
"sensor_type": "temperature_humidity",
"firmware_version": "2.1.3",
"battery_level": 85,
"measurement_interval_seconds": 300
}
Best Practices
Keep it flat:
// Good - easy to query and filter
{
"driver_name": "Alice",
"route_id": "R-001",
"priority": "high"
}
// Avoid - nested structures are harder to work with
{
"driver": {
"name": "Alice",
"info": {
"route": "R-001"
}
}
}
Use consistent naming:
// Good - consistent snake_case
{
"driver_name": "Alice",
"vehicle_type": "van",
"customer_id": "C123"
}
// Avoid - mixed conventions
{
"driverName": "Alice",
"vehicle-type": "van",
"CustomerID": "C123"
}
Don't store sensitive data:
- Avoid storing passwords, API keys, or PII in metadata
- Use references (IDs) instead of full data
- Consider encryption for sensitive identifiers
Device Lifecycle
Active Devices
Active devices process location updates and trigger geofence events:
is_active = true- Location updates create events
- Tracked in your active device count
- Visible in the dashboard
Inactive Devices
Deactivate devices to temporarily stop tracking:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/deactivate \
-H "Authorization: Bearer YOUR_API_KEY"
Inactive devices:
- Don't process location updates
- Don't trigger geofence events
- Don't count toward active device limits
- Retain historical data
- Can be reactivated anytime
Reactivate when needed:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/activate \
-H "Authorization: Bearer YOUR_API_KEY"
Deleting Devices
Permanently remove a device and all its data:
curl -X DELETE https://api.spatialflow.io/api/v1/devices/{device_uuid} \
-H "Authorization: Bearer YOUR_API_KEY"
Deleting a device removes:
- The device record
- All location history
- All geofence events
- This action cannot be undone
Consider deactivating instead of deleting to preserve historical data.
Archiving Strategy
For devices no longer in use but with valuable historical data:
- Deactivate the device to stop processing
- Export event data for archival (CSV/JSON)
- Update metadata with an
archived: trueflag - Delete after your data retention period expires
Querying Devices
List All Devices
Get all devices in your workspace:
curl https://api.spatialflow.io/api/v1/devices \
-H "Authorization: Bearer YOUR_API_KEY"
Filter by status:
# Active devices only
curl https://api.spatialflow.io/api/v1/devices?is_active=true \
-H "Authorization: Bearer YOUR_API_KEY"
# Inactive devices only
curl https://api.spatialflow.io/api/v1/devices?is_active=false \
-H "Authorization: Bearer YOUR_API_KEY"
Get Device Details
Retrieve a specific device by its UUID (id):
curl https://api.spatialflow.io/api/v1/devices/{device_uuid} \
-H "Authorization: Bearer YOUR_API_KEY"
Response:
{
"id": "123e4567-e89b-12d3-a456-426614174000",
"device_id": "truck-005",
"name": "Delivery Truck 5",
"device_type": "vehicle",
"is_active": true,
"last_location": {
"latitude": 37.7749,
"longitude": -122.4194
},
"last_location_time": "2025-11-10T14:30:00Z",
"created_at": "2025-11-10T10:00:00Z",
"updated_at": "2025-11-10T14:30:00Z"
}
Device Events
Get geofence events triggered by a device:
curl https://api.spatialflow.io/api/v1/devices/{device_uuid}/events?limit=20&offset=0 \
-H "Authorization: Bearer YOUR_API_KEY"
Response: Returns a list of geofence events with nested device, geofence, and location objects.
[
{
"id": "550e8400-e29b-41d4-a716-446655440000",
"event_type": "entry",
"device": {
"id": "550e8400-e29b-41d4-a716-446655440001",
"device_id": "truck-005",
"name": "Delivery Truck 5",
"type": "vehicle"
},
"geofence": {
"id": "550e8400-e29b-41d4-a716-446655440002",
"name": "Downtown Delivery Zone",
"description": "Main downtown delivery area"
},
"location": {
"latitude": 37.7749,
"longitude": -122.4194,
"accuracy": 10.5,
"speed": 15.2
},
"timestamp": "2025-11-10T14:30:00Z",
"workflows_triggered": ["workflow-789"],
"created_at": "2025-11-10T14:30:01Z"
}
]
Recent Events
Get recent events across all devices (role-scoped):
curl https://api.spatialflow.io/api/v1/devices/events/recent?limit=50&offset=0 \
-H "Authorization: Bearer YOUR_API_KEY"
Returns the same response structure as device events, but filtered by role:
- Field workers: See only their own device events
- Managers/Owners: See events for all workspace devices
Bulk Location Import
For historical data or customer migrations, import locations from CSV files:
CSV Format
device_id,ts,lat,lon,accuracy_m,speed_mps,heading_deg,meta_driver
truck-005,2025-10-01T14:12:03Z,42.651,-73.756,9.2,12.4,180,alice
truck-006,2025-10-01T14:13:00Z,42.652,-73.757,8.5,15.0,175,bob
truck-005,2025-10-01T14:14:00Z,42.653,-73.758,10.1,13.2,178,alice
Required columns:
device_id: Device identifierts: ISO 8601 timestamplat: Latitude (-90 to 90)lon: Longitude (-180 to 180)
Optional columns:
accuracy_m: GPS accuracy in metersspeed_mps: Speed in meters per secondheading_deg: Heading in degrees (0-359)meta_*: Metadata columns (e.g.,meta_driver,meta_cargo)
Upload CSV
curl -X POST https://api.spatialflow.io/api/v1/devices/locations/import \
-H "Authorization: Bearer YOUR_JWT_TOKEN" \
-F "file=@locations.csv"
Response:
{
"job_id": "import-123",
"status": "pending",
"filename": "locations.csv",
"created_at": "2025-11-10T15:00:00Z"
}
Check Import Status
curl https://api.spatialflow.io/api/v1/devices/locations/import/import-123 \
-H "Authorization: Bearer YOUR_JWT_TOKEN"
Response:
{
"job_id": "import-123",
"status": "completed",
"filename": "locations.csv",
"total_rows": 1000,
"valid_rows": 998,
"invalid_rows": 2,
"processed_rows": 1000,
"error_rate": 0.2,
"errors": [
{"line": 42, "error": "Invalid timestamp format"},
{"line": 157, "error": "Latitude out of range"}
],
"created_at": "2025-11-10T15:00:00Z",
"started_at": "2025-11-10T15:00:05Z",
"completed_at": "2025-11-10T15:02:15Z"
}
- Maximum file size: 50 MB
- Maximum rows: 500,000
- Error threshold: 1% (jobs fail if >1% of rows are invalid)
- Timestamps > 5 minutes in future are rejected
- Timestamps > 30 days old generate warnings
Best Practices
Naming Conventions
Use clear, consistent device IDs:
Good examples:
truck-005,truck-006,truck-007alice-phone,bob-phone,charlie-phonewarehouse-sensor-1,warehouse-sensor-2container-CONT98765
Avoid:
device-1,device-2(not descriptive)my-test-device(use meaningful names)- Random UUIDs as device_ids (use UUIDs internally, but make device_id human-readable)
Update Frequency
Balance real-time accuracy with costs and battery life:
Delivery vehicles (active):
- 15-30 second intervals
- Provides smooth tracking
- Good for customer ETAs
Field service (working):
- 1-5 minute intervals
- Adequate for job site tracking
- Better battery life
Fleet monitoring (idle):
- 10-15 minute intervals
- Reduces data costs
- Sufficient for oversight
Asset tracking (slow-moving):
- 30-60 minute intervals
- Minimal battery drain
- Suitable for long-term tracking
Consider implementing dynamic update intervals based on device state:
- Faster when moving (30s)
- Slower when stationary (5m)
- Even slower when idle (15m)
Metadata Management
Do:
- Use metadata for filtering and routing logic
- Keep metadata updated as device state changes
- Use consistent keys across all devices
- Document your metadata schema
Don't:
- Store large objects (keep under 1 KB)
- Use metadata for time-series data
- Store duplicate information already in device properties
- Change metadata structure frequently (breaks integrations)
Testing Location Updates
Always test device tracking before production:
- Register a test device:
curl -X POST https://api.spatialflow.io/api/v1/devices \
-H "Authorization: Bearer YOUR_API_KEY" \
-d '{
"device_id": "test-device-1",
"name": "Test Device",
"device_type": "mobile"
}'
- Send test location inside a geofence (use the device UUID from the response):
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/location \
-H "Authorization: Bearer YOUR_API_KEY" \
-d '{
"latitude": 37.7749,
"longitude": -122.4194
}'
- Verify event was triggered:
curl https://api.spatialflow.io/api/v1/devices/{device_uuid}/events \
-H "Authorization: Bearer YOUR_API_KEY"
- Check workflow execution:
- View triggered workflows in the dashboard
- Verify webhook deliveries
- Confirm action outputs
Battery Optimization (Mobile Devices)
For mobile apps tracking user location:
iOS:
- Use
allowsBackgroundLocationUpdatessparingly - Implement
startMonitoringSignificantLocationChangesfor low-power tracking - Request location updates only when needed
Android:
- Use fused location provider for battery efficiency
- Implement geofencing API for power-efficient boundary detection
- Batch location updates when possible
Both platforms:
- Only track when app is in use or user has opted in
- Provide clear location permission explanations
- Allow users to disable tracking
- Show battery usage estimates
Common Use Cases
1. Fleet Tracking
Track delivery vehicles, service trucks, or company cars:
{
"device_id": "fleet-truck-42",
"name": "Delivery Truck 42",
"device_type": "vehicle",
"metadata": {
"driver_name": "Alice Johnson",
"driver_id": "DRV-001",
"vehicle_make": "Ford",
"vehicle_model": "Transit",
"license_plate": "ABC-1234",
"route": "downtown_deliveries",
"shift": "morning"
}
}
Geofence events:
- Truck enters customer delivery zone → Send ETA notification
- Truck exits warehouse → Start delivery timer
- Truck enters restricted zone → Alert dispatcher
2. Field Service Management
Monitor technicians and service personnel:
{
"device_id": "tech-alice-phone",
"name": "Alice's Work Phone",
"device_type": "mobile",
"metadata": {
"technician_name": "Alice Johnson",
"employee_id": "EMP-123",
"certification": "HVAC-Master",
"current_job": "JOB-5678",
"tools": ["multimeter", "manifold_gauge"],
"availability": "on_site"
}
}
Geofence events:
- Technician enters job site → Clock in automatically
- Technician exits job site → Clock out and request completion notes
- Technician enters parts depot → Log parts pickup
3. Asset Monitoring
Track shipping containers, equipment, or valuable assets:
{
"device_id": "container-CONT98765",
"name": "Shipping Container CONT98765",
"device_type": "tracker",
"metadata": {
"container_type": "40ft_refrigerated",
"contents": "pharmaceuticals",
"customer": "MedSupply Inc",
"shipment_id": "SHIP-2024-001",
"temperature_sensor": "enabled",
"value_usd": 250000
}
}
Geofence events:
- Container enters port → Notify customs broker
- Container exits approved route → Security alert
- Container enters warehouse → Update inventory system
4. IoT Sensor Tracking
Monitor environmental sensors or mobile IoT devices:
{
"device_id": "temp-sensor-warehouse-3",
"name": "Warehouse 3 Temperature Sensor",
"device_type": "iot",
"metadata": {
"sensor_type": "temperature_humidity",
"location": "warehouse_3",
"zone": "cold_storage",
"firmware_version": "2.1.3",
"battery_level": 85,
"last_calibration": "2025-10-15"
}
}
Geofence events:
- Sensor moves outside warehouse → Theft alert
- Sensor enters maintenance area → Pause monitoring
- Sensor exits facility → Deactivate automatically
Signals
As devices send location updates, SpatialFlow's anomaly detection layer analyzes their behavior and generates signals when it detects notable patterns:
- Dwell signals fire when a device stays inside a geofence longer than a configured threshold
- Policy violation signals fire when a device's location matches a policy rule (e.g., inside a restricted zone during off-hours)
- Geofence signals provide unified enter/exit events alongside the legacy GeofenceEvent system
Signals include full explainability — each signal carries metadata, reason codes, and a structured explanation showing what thresholds were evaluated and why the signal fired.
SpatialFlow's GPS jitter filters (minimum 25m distance, 30s time gap, 100m accuracy gate) apply before signal evaluation, so signals are not triggered by noisy GPS data.
See Signals to learn about signal types and lifecycle.
Integration Examples
Python SDK
import requests
API_KEY = "your_api_key"
BASE_URL = "https://api.spatialflow.io/api/v1"
# Register device
def register_device(device_id, name, device_type="mobile"):
response = requests.post(
f"{BASE_URL}/devices",
headers={"Authorization": f"Bearer {API_KEY}"},
json={
"device_id": device_id,
"name": name,
"device_type": device_type
}
)
return response.json()
# Send location update (use device UUID from register response)
def send_location(device_uuid, lat, lon, accuracy=None):
response = requests.post(
f"{BASE_URL}/devices/{device_uuid}/location",
headers={"Authorization": f"Bearer {API_KEY}"},
json={
"latitude": lat,
"longitude": lon,
"accuracy": accuracy
}
)
return response.json()
# Usage
device = register_device("truck-001", "Delivery Truck 1", "vehicle")
result = send_location(device["id"], 37.7749, -122.4194, accuracy=10.5)
print(f"Events triggered: {result['events_triggered']}")
JavaScript/Node.js
const axios = require('axios');
const API_KEY = 'your_api_key';
const BASE_URL = 'https://api.spatialflow.io/api/v1';
// Register device
async function registerDevice(deviceId, name, deviceType = 'mobile') {
const response = await axios.post(
`${BASE_URL}/devices`,
{
device_id: deviceId,
name: name,
device_type: deviceType
},
{
headers: { Authorization: `Bearer ${API_KEY}` }
}
);
return response.data;
}
// Send location update (use device UUID from register response)
async function sendLocation(deviceUuid, lat, lon, accuracy = null) {
const response = await axios.post(
`${BASE_URL}/devices/${deviceUuid}/location`,
{
latitude: lat,
longitude: lon,
accuracy: accuracy
},
{
headers: { Authorization: `Bearer ${API_KEY}` }
}
);
return response.data;
}
// Usage
(async () => {
const device = await registerDevice('truck-001', 'Delivery Truck 1', 'vehicle');
const result = await sendLocation(device.id, 37.7749, -122.4194, 10.5);
console.log(`Events triggered: ${result.events_triggered}`);
})();
Mobile App (React Native)
import * as Location from 'expo-location';
import axios from 'axios';
const API_KEY = 'your_api_key';
const BASE_URL = 'https://api.spatialflow.io/api/v1';
const DEVICE_UUID = 'device-uuid-from-api';
// Request location permissions
async function requestLocationPermission() {
const { status } = await Location.requestForegroundPermissionsAsync();
if (status !== 'granted') {
console.error('Location permission denied');
return false;
}
return true;
}
// Start location tracking
async function startTracking() {
const hasPermission = await requestLocationPermission();
if (!hasPermission) return;
// Watch position with options
await Location.watchPositionAsync(
{
accuracy: Location.Accuracy.High,
timeInterval: 30000, // 30 seconds
distanceInterval: 50 // 50 meters
},
async (location) => {
const { latitude, longitude, accuracy } = location.coords;
// Send to SpatialFlow
try {
const response = await axios.post(
`${BASE_URL}/devices/${DEVICE_UUID}/location`,
{
latitude,
longitude,
accuracy,
timestamp: new Date(location.timestamp).toISOString()
},
{
headers: { Authorization: `Bearer ${API_KEY}` }
}
);
console.log(`Location sent. Events: ${response.data.events_triggered}`);
} catch (error) {
console.error('Failed to send location:', error);
}
}
);
}
// Start tracking
startTracking();
Rate Limits
Be aware of API rate limits when sending location updates:
- Single updates: 600 requests per minute (10 per second)
- Batch updates: 1,000 requests per minute
- Device registration: 1,000 requests per hour
For high-frequency tracking:
- Use batch updates for multiple devices
- Implement exponential backoff on rate limit errors
- Consider queuing updates client-side during network issues
Shift Management
Shifts let you define working periods for devices, tracking when a field worker or vehicle is actively on duty. Shift data powers session analytics and time-on-site reporting.
Shift State Machine
OFF → ACTIVE (start-shift)
ACTIVE → PAUSED (pause-shift)
PAUSED → ACTIVE (resume-shift)
ACTIVE → OFF (end-shift)
PAUSED → OFF (end-shift)
Shift Endpoints
Start a shift:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/start-shift \
-H "Authorization: Bearer YOUR_API_KEY"
Pause a shift:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/pause-shift \
-H "Authorization: Bearer YOUR_API_KEY"
Resume a shift:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/resume-shift \
-H "Authorization: Bearer YOUR_API_KEY"
End a shift:
curl -X POST https://api.spatialflow.io/api/v1/devices/{device_uuid}/end-shift \
-H "Authorization: Bearer YOUR_API_KEY"
Sessions
Each shift creates a session record. List sessions for a device:
curl https://api.spatialflow.io/api/v1/devices/{device_uuid}/sessions \
-H "Authorization: Bearer YOUR_API_KEY"
Use cases:
- Field worker clock-in/clock-out tracking
- Job site time-on-site reporting
- Vehicle duty hours and break compliance
- Shift-based analytics and billing
Next Steps
Now that you understand devices, explore related features:
- Quick Start Guide - Track your first device in 5 minutes
- Geofences - Create boundaries that trigger events
- Workflows - Automate actions when devices enter/exit geofences
- Webhooks - Receive real-time device events
- Signals: Anomaly detection on device location patterns
- API Reference - Complete API documentation
Device routes use the server UUID (id). If you previously used device_id in route paths, update your client to pass the UUID.
API Endpoints
Key device endpoints:
POST /api/v1/devices- Register a new deviceGET /api/v1/devices- List all devicesGET /api/v1/devices/{uuid}- Get device detailsPOST /api/v1/devices/{uuid}/location- Update device locationPOST /api/v1/devices/{uuid}/start-shift- Start a tracking shiftPOST /api/v1/devices/{uuid}/pause-shift- Pause a tracking shiftPOST /api/v1/devices/{uuid}/resume-shift- Resume a paused shiftPOST /api/v1/devices/{uuid}/end-shift- End a tracking shiftGET /api/v1/devices/{uuid}/sessions- List device sessionsPOST /api/v1/devices/batch-update- Batch location updatesDELETE /api/v1/devices/{uuid}- Delete a devicePOST /api/v1/devices/{uuid}/activate- Activate a devicePOST /api/v1/devices/{uuid}/deactivate- Deactivate a deviceGET /api/v1/devices/{uuid}/events- Get device eventsGET /api/v1/devices/events/recent- Get recent events across all devicesPOST /api/v1/devices/locations/import- Import locations from CSVGET /api/v1/devices/locations/import/{job_id}- Get import job status
See the API Reference for complete details and examples.