Architecture Overview
Snippbot runs as a single self-hosted daemon on your own infrastructure. The daemon serves the REST API and bundled web UI from one process; everything below is internal to that process.
System diagram
Section titled “System diagram” ┌──────────────────────────────────┐ │ Client Interfaces │ │ CLI · Web UI · REST API · WS │ └────────────────┬─────────────────┘ │ ┌────────────────▼─────────────────┐ │ Snippbot Daemon │ │ port 18781 (API + UI) │ │ │ │ Middleware: Auth · CORS · CSRF │ │ Rate Limiting · Security Headers │ └────────────────┬─────────────────┘ │ ┌───────────────────────────┼──────────────────────────┐ │ │ │┌────────▼───────┐ ┌──────────▼────────┐ ┌──────────▼────────┐│ Core Engine │ │ Background │ │ Integrations ││ │ │ Workers │ │ ││ • Projects │ │ • Scheduler │ │ • Browser (CDP) ││ • Agents │ │ • Workflow engine │ │ • Sandbox ││ • Memory │ │ • Sub-agent mgr │ │ (Docker/Podman) ││ • Security │ │ • Insight queue │ │ • Channels (6) ││ • Hooks │ │ • Digest engine │ │ • Email (SMTP) ││ • Config │ │ • MCP servers │ │ • Devices (WS) ││ • Proactivity │ │ • Thinking engine │ │ • Audio (STT/TTS) ││ │ │ │ │ • Push (APNs/FCM) ││ │ │ │ │ • Files / Assets │└────────┬───────┘ └──────────┬─────────┘ └────────────────────┘ │ │ └───────────────────────────┤ │ ┌────────────────▼─────────────────┐ │ SQLite Databases │ │ ~/.snippbot/*.db │ └──────────────────────────────────┘Intent Routing Layer
Section titled “Intent Routing Layer”Cutting across the system diagram above is one routing layer that every signal passes through before reaching the subsystem that acts on it: the Unified Intent Dispatcher.
Producers Dispatcher Executors ───────── ────────── ───────── USER_MESSAGE ────► ┌──────────────────┐ ────► TurnOrchestrator CHANNEL ────► │ Tier 1: hints │ ────► channel_adapter HOOK ────► │ Tier 2: policy │ ────► DeviceToolRouter SCHEDULER ────► │ Tier 3: LLM │ ────► InsightQueue AUTONOMY ────► │ Tier 4: fallback │ ────► schedule_followup PROACTIVE ────► └──────────────────┘ ────► HookEngine DEVICE ────► decision log ────► push notifications API / INTERNAL ────► ────► Suppress (telemetry)The dispatcher applies user-policy (quiet hours, urgency thresholds,
daily caps via ProactivityManager), classifies ambiguous signals with
the user’s default internal model, and writes one structured JSONL entry
per decision to ~/.snippbot/dispatch/. Every executor in the system
diagram above is reachable via the dispatcher.
See Unified Intent Dispatcher for the full design — envelope schema, tier rules, producer table, executor table, decision-log format, and operator controls.
Components
Section titled “Components”A Snippbot install ships as three things a user interacts with directly:
| Component | What it is |
|---|---|
Daemon (snippbot) | The single ASGI server that hosts the REST API, the web UI, and all background workers. Runs on port 18781. |
CLI (snippbot) | Command-line interface for installing, starting, stopping, and configuring the daemon, plus utility commands (project, channel, device, dispatcher, secrets, etc.). |
Device agent (snippbot-device, optional) | Lightweight Python agent installed on remote machines that pair to the daemon over WebSocket to expose local tools (bash, files, system info). |
Two tunnels, two purposes
Section titled “Two tunnels, two purposes”Snippbot can run two independent tunnels, and they are easy to confuse because both make something on your machine reachable from the internet. They serve different features and are configured in different places:
| Tunnel | Port | Why it exists | Where it’s configured |
|---|---|---|---|
| Channel adapter | 18790 | So messaging platforms (Slack, Google Chat, …) can deliver inbound webhooks to your agents | Settings → Channels |
| Remote access | 18781 | So the mobile app can reach the daemon when off your local network | Settings → Remote Access |
They hold separate spawn locks and can run at once. Note that the ngrok free plan permits only one agent session, which is why remote access defaults to cloudflared.
Inside the daemon, the core engine groups the major subsystems shown in the diagram above: projects, agents, memory, scheduler, loops, workflows, sub-agents, hooks, MCP, channels, browser automation, sandboxing, security, and proactivity. The Intent Dispatcher (described below) sits in front of every subsystem.
See Packages for the per-package breakdown.
Request flow
Section titled “Request flow”REST API request:
Client │ HTTP request + Bearer token ▼Starlette middleware │ Auth check (token → user lookup) │ CORS validation │ CSRF protection │ Rate limiting │ Security headers ▼Route handler │ Input validation │ Permission check │ Business logic call ▼Core engine │ Database read/write │ Background task dispatch │ Event bus publish ▼JSON responseTask execution flow:
POST /api/projects/{id}/approve │ ▼project_store.py: status → approved │ ▼Background worker picks up project │ ▼Permission check: verify agent permissions │ ▼executor.py: load agent + tools + memory context │ ▼Team orchestration: Architect → Executor → Reviewer │ ▼LLM API call (streaming) │ ▼Tool calls executed (browser, files, search, sandbox, etc.) │ ▼Episode written to memory │ ▼Task status → completed / failed │ ▼Event bus → hooks, notifications, digest, insightsEvent bus
Section titled “Event bus”All components communicate via an in-process pub/sub event bus with 100+ event types:
# Publish an eventawait event_bus.publish("task.completed", {"task_id": "...", "status": "completed"})
# Subscribe to events@event_bus.subscribe("task.*")async def on_task_event(event_type: str, data: dict): ...Events are also written to a JSONL log at ~/.snippbot/events.jsonl for replay and debugging.
Databases
Section titled “Databases”Snippbot uses multiple SQLite databases, all in ~/.snippbot/:
| File | Purpose |
|---|---|
snippbot.db | Projects, phases, tasks, agents, conversations, messages |
auth.db | Users, sessions, API keys, refresh tokens |
memory.db | Episodic memory, embeddings, metadata |
vector.db | Vector embeddings (FTS5 + faiss) |
graph.db | Knowledge graph (entities, relations) |
scheduler.db | Jobs, run history, chains, NL parsing history |
workflows.db | Workflow definitions, versions, templates, runs, step runs |
sub_agents.db | Sub-agent state, messages, approvals |
| settings.db | UI settings (14 categories) |
| channels.db | Channel platform credentials, bindings, access |
| devices.db | Paired device registry, capabilities, health |
| insights.db | Proactive insights, engagement signals |
| credentials.db | Encrypted secrets and audit log |
| execution.db | Execution jobs, plans, messages, worker state |
Plus additional databases for metrics, sandbox audit, notifications, thinking cycles, and subsystem configuration.
Related
Section titled “Related”- Intent Dispatcher — routing layer between every producer and executor
- Packages — detailed package responsibilities
- Events — event bus and event types
- Database — full schema reference
- Execution Flow — task lifecycle internals