Summary
Add an offline command queue to the OpenClaw mobile node app (iOS/Android) that captures user intents while disconnected and automatically syncs them to the gateway for execution when connectivity is restored.
Problem to solve
Many OpenClaw users operate in environments with intermittent or no cellular connectivity — rural areas, mountain passes, canyons, tunnels, basements, aircraft, etc. Currently, the mobile node app requires an active connection to the gateway to submit any command. This means users in dead zones cannot interact with their AI assistant at all, even for simple tasks like setting reminders, scheduling meetings, or queuing emails.
Real-world scenario: A user drives through a canyon with no cell service for 20-30 minutes on their daily commute. During that time, they think of several things they need their assistant to handle:
- "Remind me to buy eggs"
- "Schedule a meeting with John for Tuesday at 2pm"
- "Email me the monthly sales report"
- "Don't let me forget to call Mom when I get home"
Today, these thoughts are lost unless the user manually remembers them later. With an offline queue, the user speaks or types these commands while offline, and they execute automatically when the phone reconnects — either via cellular recovery or arriving at a WiFi-connected location (e.g., home).
Proposed solution
Core Behavior
- Capture: When the node app detects it has no gateway connectivity, switch to "offline queue" mode. The user can still interact via voice or text. Commands are stored locally on-device.
- Store: Persist queued commands in a local database (see Storage section below) with metadata: timestamp, raw input text/audio, priority hints, and queue position.
- Sync: When connectivity to the gateway is re-established, automatically flush the queue in FIFO order to the gateway as standard node messages/commands.
- Confirm: Provide user feedback on sync status — how many commands queued, how many synced, any that failed.
User Experience
- Seamless transition: The app should not require the user to do anything special to enter/exit offline mode. It should feel the same as normal usage — speak or type, and trust that it will be handled.
- Visual indicator: A subtle badge or status indicator showing "X commands queued" and current connectivity state (connected / offline / syncing).
- Voice input: Critical for hands-free use cases (driving). The app should accept voice input offline, store the audio and/or a local transcription, and forward to the gateway on sync.
- Queue management: Allow the user to review, edit, reorder, or delete queued commands before they sync.
- Notification on sync: When the queue flushes successfully, notify the user (e.g., "5 queued commands sent to your assistant").
Alternatives considered
Fall back to using Siri for “Apple Reminders” but then I have to ask openclaw to do those later on.
Impact
- Use case frequency: Anyone with a commute through dead zones (rural users, mountain/canyon roads, subway commuters)
- Competitive advantage: Most AI assistants (Siri, Google Assistant, Alexa) have limited or no offline queuing capability — this would be a differentiator
- Implementation complexity: Medium — the on-device storage and sync logic are straightforward; the main work is UI/UX for queue management and robust sync with retry
- Dependencies: Requires the iOS/Android node app to have local storage permissions and background sync capability
Evidence/examples
Real-world scenario: A user drives through a canyon with no cell service for 20-30 minutes on their daily commute. During that time, they think of several things they need their assistant to handle:
- "Remind me to buy eggs"
- "Schedule a meeting with John for Tuesday at 2pm"
- "Email me the monthly sales report"
- "Don't let me forget to call Mom when I get home"
Today, these thoughts are lost unless the user manually remembers them later. With an offline queue, the user speaks or types these commands while offline, and they execute automatically when the phone reconnects — either via cellular recovery or arriving at a WiFi-connected location (e.g., home).
Additional information
Storage Recommendation
SQLite is the natural choice for on-device queue storage:
- Already the standard embedded database on both iOS (via sqlite3 C library, bundled with the OS) and Android.
- Zero-configuration, serverless, single-file — perfect for a local queue.
- ACID-compliant — won't corrupt the queue on app crash or sudden power loss.
- Handles the expected volume trivially (dozens to low hundreds of commands between syncs).
- Both Swift (via GRDB, SQLite.swift, or raw C API) and Kotlin (via Room/SQLite) have mature SQLite libraries.
Suggested schema:
CREATE TABLE command_queue (
id INTEGER PRIMARY KEY AUTOINCREMENT,
created_at TEXT NOT NULL DEFAULT (strftime('%Y-%m-%dT%H:%M:%fZ', 'now')),
input_type TEXT NOT NULL CHECK (input_type IN ('text', 'voice')),
raw_text TEXT, -- user's text input or local transcription
audio_blob BLOB, -- raw audio if voice input (for gateway-side STT)
priority INTEGER DEFAULT 0, -- future use: urgent vs normal
status TEXT NOT NULL DEFAULT 'queued'
CHECK (status IN ('queued', 'syncing', 'sent', 'failed', 'cancelled')),
synced_at TEXT, -- timestamp when successfully sent to gateway
error TEXT, -- error message if sync failed
retry_count INTEGER DEFAULT 0
);
CREATE INDEX idx_queue_status ON command_queue(status);
Alternatives considered:
- Flat file / JSON array: Simpler but no crash safety, no concurrent access guarantees, harder to manage partial sync state.
- Core Data (iOS) / Room (Android): Adds abstraction but both are SQLite under the hood anyway. May be appropriate if the app already uses these frameworks.
- Realm: Overkill for a simple FIFO queue.
Sync Protocol
When the node detects gateway reachability:
- Query all rows with
status = 'queued', ordered by created_at ASC.
- For each command:
a. Set status = 'syncing'
b. Submit to gateway via the existing node→gateway message channel (WebSocket or HTTP, depending on protocol state)
c. On success: set status = 'sent', record synced_at
d. On failure: increment retry_count, set status = 'failed' if retries exhausted, otherwise back to queued
- Purge
sent rows after configurable retention (e.g., 24 hours or on next app launch).
Conflict handling: Commands are inherently append-only and user-initiated, so there are no merge conflicts. The gateway processes them as if they arrived in real-time, in order.
Edge Cases to Consider
- Stale commands: A reminder queued 2 hours ago saying "in 10 minutes" — the gateway/agent should interpret timestamps relative to when the command was spoken, not when it was received. Include
created_at in the sync payload so the agent has context.
- Duplicate prevention: If the app crashes mid-sync and restarts, the
status field prevents re-sending already-sent commands. Consider adding an idempotency key (UUID per command) for gateway-side dedup.
- Large audio blobs: If voice input is stored as raw audio, queue size could grow. Consider a configurable max queue size or audio compression.
- Battery considerations: Don't aggressively poll for connectivity. Use OS-level network reachability callbacks (NWPathMonitor on iOS, ConnectivityManager on Android) to trigger sync only when connectivity actually changes.
- Partial connectivity: The phone might have weak signal that drops mid-sync. Handle partial flushes gracefully — each command is independent.
Additional Ideas (Future Enhancements)
- On-device triage: Use a small local model (e.g., quantized LLM) to categorize commands by urgency, so time-sensitive items sync first.
- Geofence triggers: "When I get home" commands could use geofencing to trigger sync + immediate execution when arriving at a known location.
- Offline acknowledgment: The app could provide basic confirmation like "Got it — I'll handle that when we're back online" using canned responses, without needing the gateway.
- Batch optimization: Group related commands into a single gateway message for efficiency (e.g., "Here are 5 commands queued while offline, in order").
- Widget/Complication: iOS widget or Apple Watch complication showing queue count and last sync time.
Summary
Add an offline command queue to the OpenClaw mobile node app (iOS/Android) that captures user intents while disconnected and automatically syncs them to the gateway for execution when connectivity is restored.
Problem to solve
Many OpenClaw users operate in environments with intermittent or no cellular connectivity — rural areas, mountain passes, canyons, tunnels, basements, aircraft, etc. Currently, the mobile node app requires an active connection to the gateway to submit any command. This means users in dead zones cannot interact with their AI assistant at all, even for simple tasks like setting reminders, scheduling meetings, or queuing emails.
Real-world scenario: A user drives through a canyon with no cell service for 20-30 minutes on their daily commute. During that time, they think of several things they need their assistant to handle:
Today, these thoughts are lost unless the user manually remembers them later. With an offline queue, the user speaks or types these commands while offline, and they execute automatically when the phone reconnects — either via cellular recovery or arriving at a WiFi-connected location (e.g., home).
Proposed solution
Core Behavior
User Experience
Alternatives considered
Fall back to using Siri for “Apple Reminders” but then I have to ask openclaw to do those later on.
Impact
Evidence/examples
Real-world scenario: A user drives through a canyon with no cell service for 20-30 minutes on their daily commute. During that time, they think of several things they need their assistant to handle:
Today, these thoughts are lost unless the user manually remembers them later. With an offline queue, the user speaks or types these commands while offline, and they execute automatically when the phone reconnects — either via cellular recovery or arriving at a WiFi-connected location (e.g., home).
Additional information
Storage Recommendation
SQLite is the natural choice for on-device queue storage:
Suggested schema:
Alternatives considered:
Sync Protocol
When the node detects gateway reachability:
status = 'queued', ordered bycreated_at ASC.a. Set
status = 'syncing'b. Submit to gateway via the existing node→gateway message channel (WebSocket or HTTP, depending on protocol state)
c. On success: set
status = 'sent', recordsynced_atd. On failure: increment
retry_count, setstatus = 'failed'if retries exhausted, otherwise back toqueuedsentrows after configurable retention (e.g., 24 hours or on next app launch).Conflict handling: Commands are inherently append-only and user-initiated, so there are no merge conflicts. The gateway processes them as if they arrived in real-time, in order.
Edge Cases to Consider
created_atin the sync payload so the agent has context.statusfield prevents re-sending already-sent commands. Consider adding an idempotency key (UUID per command) for gateway-side dedup.Additional Ideas (Future Enhancements)