Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.ixo.world/llms.txt

Use this file to discover all available pages before exploring further.

Two contexts, two lifetimes

ContextLifetimeHas user?Where you receive it
PluginContextBoot (cached)NogetTools, getSubAgents, getMiddlewares, getNestModules
RuntimeContextFresh per requestYes (authenticated)Tool handlers, sub-agent handlers, middleware hooks, getRequestTools, getRequestSubAgents
The distinction matters because the wrong context can’t see what your code needs. A boot-time hook can’t ask “who is the user” — there is none yet. A per-request hook can’t be used to register a Nest module — it’s already too late.

What each context carries

PluginContext — boot-time, no user

  • config — the merged, Zod-validated env (base + every plugin’s configSchema).
  • identity — your oracle’s identity (name, org, description, entityDid, prompt).
  • availablePlugins — set of names of all loaded plugins; useful for soft-dependency branching.
  • logger — a plugin-scoped logger.

RuntimeContext — per request, authenticated user

Everything in PluginContext, plus:
FieldPurpose
userDID, Matrix user ID, UCAN delegation, timezone
sessionThread ID (= session.id), client (portal / matrix / slack), request ID, room ID
historymessages, recent(n), userContext, typed state view
secretsgetIndex(), getValues(keys) for per-user secrets
matrixScoped methods: postToRoom, getRoomState, getEventById
ucanrequireCapability, hasCapability, mintInvocation, resolveServiceDid
llmget(role, params) for the configured provider
emitTyped event emitter (toolCall, actionCall, renderComponent, reasoning, …)
sharedTyped reads from other plugins’ getSharedState
loadedPluginsSet of plugin names loaded for this thread
abortSignalRequest-scoped abort
Full field list and types: RuntimeContext reference.

Registration vs execution

A tool registered via boot-time getTools(ctx) still receives a fresh RuntimeContext when its handler fires. “Boot-time” applies to when the tool is registered, not to when it runs. Both contexts coexist over the lifetime of any tool.

Choosing the right hook

If a hook exists in both forms, pick by what your code reads:
If your code needs…Use
Only config + identityBoot-time hook (getTools(ctx))
Live state (loadedPlugins, userContext, browser tools)Per-request hook (getRequestTools(rtCtx))
The authenticated user’s DID / timezone at registration timePer-request hook
Stable tool listBoot-time hook
When both hooks fire on the same plugin, their outputs are merged — no need to choose one or the other.

Write a plugin

See both contexts in real code.

RuntimeContext reference

The full field list.
Source: packages/oracle-runtime/src/runtime-context/ and PluginContext / RuntimeContext.