# Radial Radial is a tool for getting work out of coding agents and reviewing it. You write a goal, then request a typed piece of work against it — a plan, an implementation, a review, an ADR. A daemon picks up the request, runs an agent in an isolated container, and posts the result as a versioned artifact you can review, approve, or send back for another round. It is built on [atproto](https://atproto.com/). Every participant, human or agent, is an atproto account, and every action is a signed record in that account's own repo. Code stays in git. There is no central Radial server: the web app and the daemon each read the same records and independently compute the same state. That design gives you a few things directly: - **Attribution.** Every action is a signed record, and a review pins the exact version it judged — a review of plan v2 is still a review of plan v2 after v3 exists. - **Clean membership.** A space's creator publishes who belongs to it. Removing a member revokes their grant, and every reader then ignores their records the same way, no matter when it synced. - **Artifact types are data.** An admin adds a `security-review` type by writing one record; every client picks it up and agents can start fulfilling it, with nothing deployed. - **No forced pipeline.** Reviews inform rather than gate. The UI surfaces soft signals (an implementation requested off an unapproved plan, a red check) as information, not as a block. - **Multiple operators.** Agents run by different operators can share a space with no shared infrastructure — the atproto network is the bus. ## The pieces | | | |---|---| | Web UI — [`packages/ui`](packages/ui/README.md) | A static SvelteKit SPA. Reads records straight from members' repos, caches in IndexedDB, writes to your own PDS under your own OAuth session. No server. | | Daemon — [`packages/daemon`](packages/daemon/README.md) | `radiald`: polls the spaces it serves, dispatches requests assigned to its agents into containers, runs project checks, observes merges. | | Agent container | One turn: an agent harness against a checkout, with a request-specific brief. Three harnesses ship — Claude Code, [pi](https://pi.dev) (15+ model providers), and the [Codex CLI](https://developers.openai.com/codex) — chosen per agent profile. Holds a forge token and a model key, never a protocol credential. | | Sidecar — [`packages/sidecar`](packages/sidecar/README.md) | `radial`: the human CLI, and the only path from an agent harness to the protocol. Validation, signing, and repo writes happen daemon-side, so a turn can only submit what its request asked for. | | [`core`](packages/core), [`ingest`](packages/ingest), [`lexicons`](packages/lexicons/README.md), [`atproto`](packages/atproto) | The record indexer and its store, repo polling, the `com.disnetdev.radial.*` schemas, and a zero-dependency XRPC client. | ## Quick start Requires Node 24 and pnpm 10. The workspace has no third-party runtime or test dependencies; TypeScript is the only development dependency. ```sh pnpm install --offline pnpm codegen pnpm test pnpm build ``` ### Look at the app first ```sh pnpm --filter @radial/ui dev # http://127.0.0.1:5173 ``` The space picker includes a built-in demo space (the "fixture"): a complete synthetic space of real `com.disnetdev.radial.*` records, no account or network needed. It's the fastest way to see what a goal timeline, a version chain, and a review verdict look like. Signing in with an atproto account reads and writes live spaces from the browser. Reading a space needs no account at all — paste its URI into the picker. [`packages/ui/README.md`](packages/ui/README.md) covers keyboard shortcuts and deployment. ### Put an agent behind it An operator registers existing agent atproto accounts, declares what each profile can produce, and runs a daemon that answers requests addressed to them: ```sh radiald config init # write ~/.config/radial/radial.json printf '%s\n' "$AGENT_APP_PASSWORD" | radiald init --password-stdin radiald run ``` This needs Docker, a forge login, and a model credential, and the config has real decisions in it. [`docs/running-an-agent.md`](docs/running-an-agent.md) is the end-to-end walkthrough, covering GitHub and [tangled](https://tangled.org) projects. [`docs/radial-json.md`](docs/radial-json.md) is the configuration reference. ## Documentation | | | |---|---| | [`docs/design.md`](docs/design.md) | The protocol design: trust, data model, the turn model, forges, security, and rejected alternatives. | | [`docs/plan.md`](docs/plan.md) | Phased implementation plan, exit criteria, and what is out of scope. | | [`docs/running-an-agent.md`](docs/running-an-agent.md) | Operator walkthrough: agent identities, spaces, `radiald run`, GitHub and tangled. | | [`docs/operators.md`](docs/operators.md) | Running a daemon alongside somebody else's: joining a space, routing, claims and leases, Jetstream. | | [`docs/radial-json.md`](docs/radial-json.md) | Every field of the operator's `radial.json`. | | [`docs/adr-tangled-forge.md`](docs/adr-tangled-forge.md) | Design record for the tangled forge integration. | | [`docs/phase6-ui-plan.md`](docs/phase6-ui-plan.md) | How the web app was built, step by step. | | [`PRODUCT.md`](PRODUCT.md), [`DESIGN.md`](DESIGN.md) | Who this is for and how it should feel; the design system as shipped. | ## Development ```sh pnpm lint # typecheck every package; check generated lexicon types are current pnpm test # unit, golden-scenario, and convergence tests pnpm build pnpm images # build the agent turn container image ``` Two invariants to keep in mind when contributing: - Any new record type or index rule lands in `core` with permutation-property coverage — every arrival order must produce the same view — before the daemon or the UI consumes it. - Lexicon changes are additive-only; records already live in people's repos.