Edge Devices & Fleets
Manage IoT devices and fleet memory synchronization
Edge Devices & Fleets
Manage IoT devices and synchronize memory between edge devices and the Engram cloud. Fleet management allows grouping devices, configuring sync strategies, and monitoring device health.
Device Types
| Type | Description |
|---|---|
ROBOT | Autonomous or semi-autonomous robots |
SENSOR | Environmental or data-collection sensors |
IOT_GATEWAY | Gateway aggregating multiple devices |
SMART_CAMERA | Vision-enabled cameras with on-device inference |
VEHICLE | Connected vehicles |
DRONE | Unmanned aerial vehicles |
WEARABLE | Wearable computing devices |
INDUSTRIAL | Industrial automation equipment |
HOME_ASSISTANT | Smart home assistants |
CUSTOM | User-defined device type |
Sync Strategies
| Strategy | Description |
|---|---|
REAL_TIME | Sync immediately on every memory change |
PERIODIC | Sync on a fixed interval (configurable) |
ON_DEMAND | Sync only when explicitly triggered |
INTELLIGENT | Adaptive sync based on connectivity, battery, and data priority |
BANDWIDTH_AWARE | Sync based on available bandwidth, prioritizing critical memories |
Fleet Management
Create Fleet
Create a new fleet to group and manage devices.
POST /v1/fleets
Request Body
| Parameter | Type | Required | Description |
|---|---|---|---|
name | string | Yes | Fleet name |
description | string | No | Fleet description |
sync_strategy | string | No | Default sync strategy for devices (default: INTELLIGENT) |
sync_interval_seconds | integer | No | Interval for PERIODIC strategy (default: 300) |
metadata | object | No | Custom metadata |
Code Examples
cURL
curl -X POST https://api.engrammemory.ai/v1/fleets \
-H "Authorization: Bearer pr_live_xxxxx" \
-H "Content-Type: application/json" \
-d '{
"name": "Warehouse Robots",
"description": "Fleet of warehouse fulfillment robots",
"sync_strategy": "INTELLIGENT",
"metadata": {
"location": "warehouse-east",
"department": "logistics"
}
}'
Python
from engrammemory import Engram
client = Engram(api_key="pr_live_xxxxx")
fleet = client.fleets.create(
name="Warehouse Robots",
description="Fleet of warehouse fulfillment robots",
sync_strategy="INTELLIGENT",
metadata={"location": "warehouse-east", "department": "logistics"},
)
print(f"Fleet created: {fleet.id}")
JavaScript
import { Engram } from "engrammemory-ai";
const client = new Engram({ apiKey: "pr_live_xxxxx" });
const fleet = await client.fleets.create({
name: "Warehouse Robots",
description: "Fleet of warehouse fulfillment robots",
syncStrategy: "INTELLIGENT",
metadata: { location: "warehouse-east", department: "logistics" },
});
console.log(`Fleet created: ${fleet.id}`);
Response
{
"id": "fleet_abc123",
"name": "Warehouse Robots",
"description": "Fleet of warehouse fulfillment robots",
"sync_strategy": "INTELLIGENT",
"sync_interval_seconds": null,
"device_count": 0,
"metadata": {
"location": "warehouse-east",
"department": "logistics"
},
"created_at": "2026-04-10T12:00:00Z"
}
List Fleets
List all fleets for your account.
GET /v1/fleets
Code Examples
cURL
curl https://api.engrammemory.ai/v1/fleets \
-H "Authorization: Bearer pr_live_xxxxx"
Python
fleets = client.fleets.list()
for f in fleets.items:
print(f"{f.name}: {f.device_count} devices")
JavaScript
const fleets = await client.fleets.list();
fleets.items.forEach((f) => {
console.log(`${f.name}: ${f.deviceCount} devices`);
});
Response
{
"items": [
{
"id": "fleet_abc123",
"name": "Warehouse Robots",
"sync_strategy": "INTELLIGENT",
"device_count": 24,
"online_count": 22,
"offline_count": 2,
"created_at": "2026-04-10T12:00:00Z"
}
],
"total": 3
}
Update Fleet
PATCH /v1/fleets/{fleet_id}
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
fleet_id | string | Yes | Fleet ID |
Request Body
All fields optional. Only include fields to update.
| Parameter | Type | Description |
|---|---|---|
name | string | Fleet name |
description | string | Fleet description |
sync_strategy | string | Default sync strategy |
sync_interval_seconds | integer | Periodic sync interval |
metadata | object | Custom metadata |
Code Examples
cURL
curl -X PATCH https://api.engrammemory.ai/v1/fleets/fleet_abc123 \
-H "Authorization: Bearer pr_live_xxxxx" \
-H "Content-Type: application/json" \
-d '{ "sync_strategy": "PERIODIC", "sync_interval_seconds": 600 }'
Python
fleet = client.fleets.update("fleet_abc123", sync_strategy="PERIODIC", sync_interval_seconds=600)
JavaScript
const fleet = await client.fleets.update("fleet_abc123", {
syncStrategy: "PERIODIC",
syncIntervalSeconds: 600,
});
Response
Returns the updated fleet object.
Delete Fleet
Delete a fleet. Devices in the fleet are not deleted but become unassigned.
DELETE /v1/fleets/{fleet_id}
Code Examples
cURL
curl -X DELETE https://api.engrammemory.ai/v1/fleets/fleet_abc123 \
-H "Authorization: Bearer pr_live_xxxxx"
Python
client.fleets.delete("fleet_abc123")
JavaScript
await client.fleets.delete("fleet_abc123");
Response
204 No Content
Fleet Dashboard
Get a real-time overview of fleet status, device health, and sync metrics.
GET /v1/fleets/{fleet_id}/dashboard
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
fleet_id | string | Yes | Fleet ID |
Code Examples
cURL
curl https://api.engrammemory.ai/v1/fleets/fleet_abc123/dashboard \
-H "Authorization: Bearer pr_live_xxxxx"
Python
dashboard = client.fleets.dashboard("fleet_abc123")
print(f"Online: {dashboard.online_count}/{dashboard.device_count}")
print(f"Sync errors: {dashboard.sync_errors_24h}")
JavaScript
const dashboard = await client.fleets.dashboard("fleet_abc123");
console.log(`Online: ${dashboard.onlineCount}/${dashboard.deviceCount}`);
console.log(`Sync errors: ${dashboard.syncErrors24h}`);
Response
{
"fleet_id": "fleet_abc123",
"name": "Warehouse Robots",
"device_count": 24,
"online_count": 22,
"offline_count": 2,
"memories_synced_24h": 45200,
"sync_errors_24h": 12,
"avg_sync_latency_ms": 340,
"total_memory_usage_mb": 1240.5,
"devices_by_type": {
"ROBOT": 20,
"SENSOR": 3,
"IOT_GATEWAY": 1
},
"devices_by_status": {
"ONLINE": 22,
"OFFLINE": 1,
"MAINTENANCE": 1
},
"recent_alerts": [
{
"id": "alert_xyz",
"device_id": "dev_abc",
"type": "DEVICE_OFFLINE",
"message": "Device dev_abc has been offline for 15 minutes",
"created_at": "2026-04-10T14:00:00Z"
}
]
}
Device Management
Register Device
Register a new edge device, optionally assigning it to a fleet.
POST /v1/devices
Request Body
| Parameter | Type | Required | Description |
|---|---|---|---|
name | string | Yes | Device name |
type | string | Yes | Device type (see Device Types) |
fleet_id | string | No | Fleet to assign device to |
sync_strategy | string | No | Override fleet sync strategy |
sync_interval_seconds | integer | No | Override fleet sync interval |
capabilities | object | No | Device capabilities (memory, storage, GPU, etc.) |
metadata | object | No | Custom metadata |
Code Examples
cURL
curl -X POST https://api.engrammemory.ai/v1/devices \
-H "Authorization: Bearer pr_live_xxxxx" \
-H "Content-Type: application/json" \
-d '{
"name": "Robot-A7",
"type": "ROBOT",
"fleet_id": "fleet_abc123",
"sync_strategy": "INTELLIGENT",
"capabilities": {
"memory_mb": 4096,
"storage_gb": 64,
"has_gpu": true,
"max_vectors": 100000
},
"metadata": {
"firmware_version": "2.4.1",
"location": "aisle-7"
}
}'
Python
device = client.devices.create(
name="Robot-A7",
type="ROBOT",
fleet_id="fleet_abc123",
sync_strategy="INTELLIGENT",
capabilities={
"memory_mb": 4096,
"storage_gb": 64,
"has_gpu": True,
"max_vectors": 100000,
},
metadata={"firmware_version": "2.4.1", "location": "aisle-7"},
)
print(f"Device ID: {device.id}")
print(f"Device token: {device.device_token}") # Store securely
JavaScript
const device = await client.devices.create({
name: "Robot-A7",
type: "ROBOT",
fleetId: "fleet_abc123",
syncStrategy: "INTELLIGENT",
capabilities: {
memoryMb: 4096,
storageGb: 64,
hasGpu: true,
maxVectors: 100000,
},
metadata: { firmwareVersion: "2.4.1", location: "aisle-7" },
});
console.log(`Device ID: ${device.id}`);
console.log(`Device token: ${device.deviceToken}`); // Store securely
Response
{
"id": "dev_xyz789",
"name": "Robot-A7",
"type": "ROBOT",
"fleet_id": "fleet_abc123",
"status": "OFFLINE",
"sync_strategy": "INTELLIGENT",
"device_token": "devtok_abc123...",
"capabilities": {
"memory_mb": 4096,
"storage_gb": 64,
"has_gpu": true,
"max_vectors": 100000
},
"metadata": {
"firmware_version": "2.4.1",
"location": "aisle-7"
},
"created_at": "2026-04-10T12:00:00Z",
"last_heartbeat_at": null,
"last_sync_at": null
}
Note: The
device_tokenis only returned on creation. Store it securely -- it is used by the device to authenticate sync and heartbeat requests.
List Devices
List all devices with optional filtering.
GET /v1/devices
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
page | integer | No | Page number (default: 1) |
page_size | integer | No | Results per page (default: 20, max: 100) |
fleet_id | string | No | Filter by fleet |
type | string | No | Filter by device type |
status | string | No | Filter by ONLINE, OFFLINE, or MAINTENANCE |
Code Examples
cURL
curl "https://api.engrammemory.ai/v1/devices?fleet_id=fleet_abc123&status=ONLINE" \
-H "Authorization: Bearer pr_live_xxxxx"
Python
devices = client.devices.list(fleet_id="fleet_abc123", status="ONLINE")
for d in devices.items:
print(f"{d.name} ({d.type}): last sync {d.last_sync_at}")
JavaScript
const devices = await client.devices.list({
fleetId: "fleet_abc123",
status: "ONLINE",
});
devices.items.forEach((d) => {
console.log(`${d.name} (${d.type}): last sync ${d.lastSyncAt}`);
});
Response
{
"items": [
{
"id": "dev_xyz789",
"name": "Robot-A7",
"type": "ROBOT",
"fleet_id": "fleet_abc123",
"status": "ONLINE",
"last_heartbeat_at": "2026-04-10T14:29:55Z",
"last_sync_at": "2026-04-10T14:28:00Z",
"memories_count": 8420,
"sync_pending_count": 12
}
],
"total": 22,
"page": 1,
"page_size": 20,
"total_pages": 2
}
Get Device Details
Retrieve detailed information about a specific device.
GET /v1/devices/{device_id}
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
device_id | string | Yes | Device ID |
Code Examples
cURL
curl https://api.engrammemory.ai/v1/devices/dev_xyz789 \
-H "Authorization: Bearer pr_live_xxxxx"
Python
device = client.devices.get("dev_xyz789")
print(f"Status: {device.status}")
print(f"Memories: {device.memories_count}")
print(f"Pending sync: {device.sync_pending_count}")
JavaScript
const device = await client.devices.get("dev_xyz789");
console.log(`Status: ${device.status}`);
console.log(`Memories: ${device.memoriesCount}`);
console.log(`Pending sync: ${device.syncPendingCount}`);
Response
{
"id": "dev_xyz789",
"name": "Robot-A7",
"type": "ROBOT",
"fleet_id": "fleet_abc123",
"status": "ONLINE",
"sync_strategy": "INTELLIGENT",
"capabilities": {
"memory_mb": 4096,
"storage_gb": 64,
"has_gpu": true,
"max_vectors": 100000
},
"metadata": {
"firmware_version": "2.4.1",
"location": "aisle-7"
},
"memories_count": 8420,
"sync_pending_count": 12,
"last_heartbeat_at": "2026-04-10T14:29:55Z",
"last_sync_at": "2026-04-10T14:28:00Z",
"uptime_seconds": 432000,
"created_at": "2026-04-10T12:00:00Z"
}
Update Device
PATCH /v1/devices/{device_id}
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
device_id | string | Yes | Device ID |
Request Body
| Parameter | Type | Description |
|---|---|---|
name | string | Device name |
fleet_id | string | Fleet assignment (set null to unassign) |
sync_strategy | string | Sync strategy |
sync_interval_seconds | integer | Sync interval |
status | string | ONLINE, OFFLINE, or MAINTENANCE |
metadata | object | Custom metadata |
Code Examples
cURL
curl -X PATCH https://api.engrammemory.ai/v1/devices/dev_xyz789 \
-H "Authorization: Bearer pr_live_xxxxx" \
-H "Content-Type: application/json" \
-d '{ "status": "MAINTENANCE", "metadata": { "location": "repair-bay" } }'
Python
device = client.devices.update("dev_xyz789", status="MAINTENANCE", metadata={"location": "repair-bay"})
JavaScript
const device = await client.devices.update("dev_xyz789", {
status: "MAINTENANCE",
metadata: { location: "repair-bay" },
});
Response
Returns the updated device object.
Delete Device
Unregister a device. Device memories stored in Engram cloud are retained.
DELETE /v1/devices/{device_id}
Code Examples
cURL
curl -X DELETE https://api.engrammemory.ai/v1/devices/dev_xyz789 \
-H "Authorization: Bearer pr_live_xxxxx"
Python
client.devices.delete("dev_xyz789")
JavaScript
await client.devices.delete("dev_xyz789");
Response
204 No Content
Device Heartbeat
Send a keep-alive heartbeat with device metrics. Devices should send heartbeats at regular intervals (recommended: every 30 seconds).
POST /v1/devices/{device_id}/heartbeat
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
device_id | string | Yes | Device ID |
Request Headers
| Header | Required | Description |
|---|---|---|
Authorization | Yes | Bearer <device_token> (device token from registration) |
Request Body
| Parameter | Type | Required | Description |
|---|---|---|---|
cpu_usage_pct | float | No | CPU usage percentage |
memory_usage_pct | float | No | RAM usage percentage |
storage_usage_pct | float | No | Storage usage percentage |
battery_pct | float | No | Battery level percentage |
network_type | string | No | WIFI, CELLULAR, ETHERNET, SATELLITE |
signal_strength_dbm | integer | No | Network signal strength |
memories_count | integer | No | Local memories on device |
sync_pending_count | integer | No | Memories pending sync |
custom_metrics | object | No | Device-specific metrics |
Code Examples
cURL
curl -X POST https://api.engrammemory.ai/v1/devices/dev_xyz789/heartbeat \
-H "Authorization: Bearer DEVICE_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"cpu_usage_pct": 45.2,
"memory_usage_pct": 62.8,
"storage_usage_pct": 34.1,
"battery_pct": 78.0,
"network_type": "WIFI",
"signal_strength_dbm": -42,
"memories_count": 8420,
"sync_pending_count": 12
}'
Python
# Typically called from device-side code
from engram.edge import EngramEdgeClient
edge = EngramEdgeClient(device_token="DEVICE_TOKEN")
edge.heartbeat(
cpu_usage_pct=45.2,
memory_usage_pct=62.8,
storage_usage_pct=34.1,
battery_pct=78.0,
network_type="WIFI",
signal_strength_dbm=-42,
memories_count=8420,
sync_pending_count=12,
)
JavaScript
import { EngramEdgeClient } from "engrammemory-ai";
const edge = new EngramEdgeClient({ deviceToken: "DEVICE_TOKEN" });
await edge.heartbeat({
cpuUsagePct: 45.2,
memoryUsagePct: 62.8,
storageUsagePct: 34.1,
batteryPct: 78.0,
networkType: "WIFI",
signalStrengthDbm: -42,
memoriesCount: 8420,
syncPendingCount: 12,
});
Response
{
"status": "OK",
"server_time": "2026-04-10T14:30:00Z",
"sync_required": true,
"sync_priority": "NORMAL",
"pending_commands": []
}
Trigger Sync
Manually trigger a memory sync between device and cloud.
POST /v1/devices/{device_id}/sync
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
device_id | string | Yes | Device ID |
Request Body
| Parameter | Type | Required | Description |
|---|---|---|---|
direction | string | Yes | push (device to cloud), pull (cloud to device), or both |
force | boolean | No | Force full sync, ignoring incremental state (default: false) |
collections | array[string] | No | Limit sync to specific collections |
Code Examples
cURL
curl -X POST https://api.engrammemory.ai/v1/devices/dev_xyz789/sync \
-H "Authorization: Bearer pr_live_xxxxx" \
-H "Content-Type: application/json" \
-d '{
"direction": "both",
"force": false
}'
Python
sync = client.devices.sync("dev_xyz789", direction="both")
print(f"Sync job: {sync.job_id}")
print(f"Status: {sync.status}")
JavaScript
const sync = await client.devices.sync("dev_xyz789", { direction: "both" });
console.log(`Sync job: ${sync.jobId}`);
console.log(`Status: ${sync.status}`);
Response
{
"job_id": "sync_abc123",
"device_id": "dev_xyz789",
"direction": "both",
"status": "IN_PROGRESS",
"memories_to_push": 12,
"memories_to_pull": 45,
"started_at": "2026-04-10T14:30:00Z"
}
Alerts
List Alerts
List device and fleet alerts.
GET /v1/alerts
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
page | integer | No | Page number (default: 1) |
page_size | integer | No | Results per page (default: 20, max: 100) |
fleet_id | string | No | Filter by fleet |
device_id | string | No | Filter by device |
status | string | No | ACTIVE or RESOLVED |
type | string | No | Alert type: DEVICE_OFFLINE, SYNC_FAILED, STORAGE_FULL, LOW_BATTERY, HIGH_ERROR_RATE |
Code Examples
cURL
curl "https://api.engrammemory.ai/v1/alerts?status=ACTIVE&fleet_id=fleet_abc123" \
-H "Authorization: Bearer pr_live_xxxxx"
Python
alerts = client.alerts.list(status="ACTIVE", fleet_id="fleet_abc123")
for a in alerts.items:
print(f"[{a.type}] {a.device_id}: {a.message}")
JavaScript
const alerts = await client.alerts.list({
status: "ACTIVE",
fleetId: "fleet_abc123",
});
alerts.items.forEach((a) => {
console.log(`[${a.type}] ${a.deviceId}: ${a.message}`);
});
Response
{
"items": [
{
"id": "alert_abc123",
"type": "DEVICE_OFFLINE",
"status": "ACTIVE",
"device_id": "dev_xyz789",
"fleet_id": "fleet_abc123",
"message": "Device Robot-A7 has been offline for 15 minutes",
"created_at": "2026-04-10T14:00:00Z",
"resolved_at": null
},
{
"id": "alert_def456",
"type": "LOW_BATTERY",
"status": "ACTIVE",
"device_id": "dev_abc456",
"fleet_id": "fleet_abc123",
"message": "Device Robot-B3 battery at 8%",
"created_at": "2026-04-10T14:10:00Z",
"resolved_at": null
}
],
"total": 2,
"page": 1,
"page_size": 20,
"total_pages": 1
}
Resolve Alert
Mark an alert as resolved.
PATCH /v1/alerts/{alert_id}/resolve
Path Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
alert_id | string | Yes | Alert ID |
Request Body (Optional)
| Parameter | Type | Description |
|---|---|---|
resolution_note | string | Note about how the alert was resolved |
Code Examples
cURL
curl -X PATCH https://api.engrammemory.ai/v1/alerts/alert_abc123/resolve \
-H "Authorization: Bearer pr_live_xxxxx" \
-H "Content-Type: application/json" \
-d '{ "resolution_note": "Device restarted and back online" }'
Python
client.alerts.resolve("alert_abc123", resolution_note="Device restarted and back online")
JavaScript
await client.alerts.resolve("alert_abc123", {
resolutionNote: "Device restarted and back online",
});
Response
{
"id": "alert_abc123",
"type": "DEVICE_OFFLINE",
"status": "RESOLVED",
"device_id": "dev_xyz789",
"message": "Device Robot-A7 has been offline for 15 minutes",
"resolution_note": "Device restarted and back online",
"created_at": "2026-04-10T14:00:00Z",
"resolved_at": "2026-04-10T14:35:00Z"
}
Error Codes
| Code | HTTP Status | Description |
|---|---|---|
INVALID_DEVICE_TYPE | 400 | Unsupported device type |
INVALID_SYNC_STRATEGY | 400 | Unsupported sync strategy |
INVALID_SYNC_DIRECTION | 400 | Direction must be push, pull, or both |
FLEET_NOT_FOUND | 404 | Fleet ID does not exist |
DEVICE_NOT_FOUND | 404 | Device ID does not exist |
ALERT_NOT_FOUND | 404 | Alert ID does not exist |
DEVICE_LIMIT_EXCEEDED | 409 | Maximum devices per account reached |
FLEET_LIMIT_EXCEEDED | 409 | Maximum fleets per account reached |
SYNC_IN_PROGRESS | 409 | Device already has a sync job running |
DEVICE_OFFLINE | 422 | Cannot sync with offline device |
INVALID_DEVICE_TOKEN | 401 | Device token is invalid or expired |
RATE_LIMIT_EXCEEDED | 429 | Too many requests |