Radia coordinates agents through immutable JSON records in a shared space. Workers declare which records they handle and claim matching work under renewable leases. The runtime provides durable delivery, content-scoped authorization and lineage without hard-coded agent-to-agent routing.
Direct calls make each participant depend on the identity and interface of the next one. Adding a capability can require changes to every caller that might use it. This becomes difficult when agents are deployed independently or owned by different teams.
Radia stores work as records. A worker registers a pattern such as
{ kind: "document", match: { type: "scan" } } and claims records that match it.
Publishers do not hold references to workers or choose a destination.
Starting a worker makes its pattern available to the space. If no eligible worker is running, matching records remain available until one can claim them.
A completed worker does not update its input. It writes a result record that names the input as a parent. The original document remains unchanged.
A result is another routable record. Downstream workers match it in the same way they match an initial request, and parent links preserve how each result was produced.
One command starts a space with storage, a web console and a credential already provisioned. From there you can drive it from the shell.
$ deno task dev # space + console, in one process
$ deno task compile # -> ./radia; put it on your PATH
$ radia put document '{"type":"pdf","classification":"public"}'
$ radia take document --lease 30 --json > claim.json
$ radia ack - --result-kind summary --result '{"text":"..."}' < claim.json
Run it from the checkout: compile it as above, or
deno run -A src/main.ts <verb> directly. The npm and pip packaging is
built but unpublished, so nothing installs radia for you yet and
npx radia does not work today.
The CLI, TypeScript and Python SDKs, web console and MCP adapter all use the public
/v0 API. None has a private runtime interface.
A worker declares its patterns and supplies a handler:
import { RadiaClient } from "radia";
import { agentLoop } from "radia/loop";
await agentLoop(new RadiaClient(url, { token }), {
name: "summarizer",
patterns: [{ kind: "document", match: { type: "pdf" } }],
handle: async (rec) => ({
kind: "summary",
body: { text: await summarize(rec.body) },
}),
});
The loop claims matching work, renews the lease while the handler runs and settles the claim with the returned record. If the process exits before settlement, the lease expires and the record becomes claimable again.
Radia currently runs on SQLite and PGlite for embedded use and PostgreSQL for multiple runtime instances. The same storage contract suite covers all three adapters.
Posting, querying, claiming and settling records, with fenced leases, retries, idempotency and dead-letter handling.
Kind- and pattern-scoped grants, short-lived run credentials, OIDC sign-in, delegation and labels that propagate with derived data. Authorization →
Content-addressed artifacts for images and files, with optional encryption, retention and payload erasure.
An event log, lineage and graph queries, diagnostics, mined flows, a web console, a tamper-evident event chain and OTLP export. Inspection →
Versioned multi-file trees that agents can write, execute in a jail, serve to a browser and export as Git repositories. Workspaces are an extension over the public API. Workspaces →