Daemion docs

How do I extend Daemion?

Extensions are how you configure Daemion. Every agent, job, app, command, theme, and integration is an extension — a JSON record in SQLite that the engine loads at runtime. There is no separate table per type, no code deployment required. Add an extension and it’s live immediately.


What is an extension?

An extension is a single database record with a type, a name, a definition object, and a handful of metadata fields. The shape of definition varies by type — a command’s definition holds a prompt and a prefix, while a theme’s definition holds a color palette. Everything else (storage, lifecycle, enabling/disabling) is handled uniformly by the extension system regardless of type.

This means you learn one API and one data model to control every moving part of Daemion.


What are the 12 extension types?

TypeWhat it isExample
commandSlash (or @, !, #) commands in the chat UI/summarize — summarize the current thread
agentClaude agent identities with system prompts and model routingopus — thorough reasoning agent
jobAutonomous work units that run on a schedule or triggerdaily-digest — 8am briefing every weekday
appVite projects served by the gatewaybudget-tracker — interactive finance tool
themeVisual themes for the Daemion appmidnight — dark blue color scheme
rendererCustom content renderers for chat turnsmermaid — render diagrams inline
integrationConnections to external servicesgithub — GitHub webhook receiver
actionDiscrete callable actions exposed to agentssend-email — agent-callable email action
widgetEmbeddable UI componentsweather — weather card widget
artifactStructured outputs produced by agentsreport — formatted report artifact
capabilityAgent capability declarationsweb-search — agent can search the web
controlSystem configuration records — budget limits, rate caps, feature flagsdeploy-button — one-tap deploy trigger

What does the extension schema look like?

Every extension shares this universal shape, defined in src/schema/extension.ts:

typescript

interface Extension { id: string; // assigned by gateway on creation, e.g. “ext_01abc123” type: ExtensionType; // one of the 12 types above name: string; // unique per type, kebab-case, 1-100 chars description: string; // human-readable, max 500 chars definition: Record<string, unknown>; // type-specific config trigger_def?: Record<string, unknown> | null; // optional cron/event/webhook trigger source: “built-in” | “user” | “agent” | “community”; enabled: boolean; created_at: string; // ISO 8601 updated_at: string; // ISO 8601 }

The definition field is validated against a type-specific Zod schema when you create or update an extension. For example, a command extension’s definition must include a prefix (/, @, !, or #) and a handler string.


How do I create an extension?

The primary way to create extensions is through chat. Tell Daemion what you want — “create a command called /hello that greets me by name” — and the agent writes the extension record for you. The API below is the programmatic alternative for scripts, CI pipelines, and agent-initiated creation at runtime.

Create via API

bash
Verified

curl -X POST http://localhost:3001/extensions
-H “Authorization: Bearer $DAEMION_TOKEN”
-H “Content-Type: application/json”
-d ’{ “type”: “command”, “name”: “hello”, “description”: “Greet the user by name.”, “definition”: { “prefix”: ”/”, “handler”: “Reply with a warm greeting using the user'''s name from context.” }, “source”: “user”, “enabled”: true }’

The gateway validates definition against the schema for the given type and returns the created extension with its assigned id.


Frequently asked questions

Q Can agents create extensions at runtime?
Yes — this is a first-class pattern. An agent can POST to /extensions during a conversation to create a new job, command, or integration on the fly. Set source: "agent" and owner_agent_id to the agent's ID so you can filter and audit agent-created extensions later.
Q Where are extensions stored?
Extension records live in SQLite at ~/.daemion/daemion.db. File-backed extension types (jobs, agents) also have a directory on disk under jobs/ or agents/. The database record is the authoritative source — disk files are referenced by the definition.
Q What is the difference between the source values?
built-in — shipped with Daemion, read-only. user — created by you through chat or the API. agent — created autonomously by an agent during a conversation (paired with owner_agent_id). community — installed from the extension registry. Source affects display grouping in the app and determines whether an extension can be deleted.
Q What is Claude's role in all this?
Agents are Claude operating in a role — the system prompt in the gateway literally says "You are Claude, operating as a Daemion agent." Daemion agents are not separate AIs, they are Claude with a specific identity, system prompt, and model assignment. When an agent creates an extension at runtime, it is Claude using the gateway API to configure your system.

What can go wrong

Validation errors

400 &#123;"error": "validation failed", "details": [...]&#125; — The request body failed Zod schema validation. The details array lists each failing field. Check that type is one of the 12 valid values and that definition matches the required shape for that type.

403 &#123;"error": "cannot disable essential extensions"&#125; — Essential built-in extensions cannot be disabled. They can be inspected but not toggled off.

403 &#123;"error": "cannot delete essential extensions"&#125; — Essential extensions cannot be deleted. To customize behavior, create a new extension of the same type with source: "user".


What’s next?