AGENTS.md@server · git:20261019.7622d3a · 2026-10-19 · sha256 cb91b67c8f19bbc8

AGENTS.md@server git:20261019.7622d3aA

Immutable. This exact content never changes and is served at /api/v1/blob/cb91b67c8f19bbc8.

Bun server on port 13337 by default. Serves the client at `/`, upgrades `/ws` to WebSocket. Read [README.md](README.md) for the directory map, storage ownership, and test commands.

- `web.ts` owns the Bun fullstack surface only: the SPA HTML shell (dev bundler + HMR / prebuilt `dist/`), the two WebSocket channels (`/ws` chat, `/api/workspaces/ws` live events), and graceful shutdown. Every HTTP API request is delegated to the Hono app via `fetch`.
- `api/index.ts` assembles the Hono REST API (all `/api/*` routes). Harness authentication routes live in `api/harnesses.ts`. `withWorkspace` middleware resolves `:id` → workspace (404 if missing) and stashes it on the context, so handlers read `c.get('ws')`. Its catch-all serves the prebuilt client from `dist/` in prod via Hono's `serveStatic` (cached, traversal-safe).
- API tests live in `api/` without an `api-` filename prefix. Unit tests stay beside their modules; existing integration and fixture-based tests live in `test/`.
- `cli.ts` is the executable entry point and loads color setup before the command tree. `cli/index.ts` owns command registration, root help, and demo/managed-user gates; `cli/commands/` holds one module per top-level command, with its subcommands and private helpers. Shared CLI support lives directly in `cli/`. Server launches use `PACKAGE_ROOT` to find the entry point and package files, independent of the command module's location.
- `scratchpad/` owns document persistence and reads (`document.ts`), asset files and cleanup (`assets.ts`), headless writes (`executor.ts` and `shape-defaults.ts`), and browser operation forwarding (`relay.ts`). Its unit tests live beside those modules.
- `static.ts` exposes the `dist/` location (`DIST_DIR`), the `prebuilt` flag, and the prod SPA `distShell`. `events.ts` holds `publishEvent` (server→client live-event broadcast over `/api/workspaces/ws`) decoupled from `web.ts` to avoid an import cycle; `web.ts` wires it via `setEventServer`.
- `state.ts` holds the connected chat clients and `broadcast()` (which also feeds the harness debug tap).
- `workspaces/` owns discovery, registration, provisioning, layout, environment settings, and workspace presentation. `workspaces/layout.ts` is the sole reader/writer of `.moi/.workspace.json`; `workspaces/registry.ts` stores the local workspace list in `DATA_DIR`.
- `sessions/` owns Moi's session metadata, selections and pins, renames, archiving, attachment preparation, and pending-view handoffs. Provider history and live provider sessions stay in `harness/`.
- `skills/` manages bundled workspace skill installation, versions, and updates. Keep its template paths relative to the installed package.
- `applets/` owns view/widget machinery: dependency analysis, compilation, typechecking, CSS scoping, bundle serving, source edits, server-function workers, thumbnails, UI component installation, and error journals. `applets/views.ts` and `applets/widgets.ts` own each kind's manifests and events. Worker paths must remain valid in source and published installs.
- `harness/` holds every agent backend (Claude Code, OpenClaw, Codex, Hermes): per-harness adapter + session + transport + protocol notes, colocated; Hermes uses the shared `acp/` implementation. Read `harness/README.md` for the message-type layers, the adapter contract, and the folder conventions before touching agent-backend code.
- WebSocket protocol: server sends `ServerMessage`, client sends `ClientMessage` — both defined in `lib/types.ts`.
- Never import `react`, `react-dom`, or the `tldraw` package into server-evaluated code in `server/` or `lib/`. `applets/runtime/` contains applet runtime sources: `moi.ts`, `rpc.ts`, and `collab.ts` run in browser bundles; tests run in Bun. The shared API base constant lives in `applets/api-base.ts`. The server must not evaluate React (a global install can pair mismatched `react`/`react-dom` copies, and `react-dom` then throws at load). The scratchpad writer uses `@tldraw/store` + `@tldraw/tlschema` instead; `server/test/server-react-free.test.ts` enforces this. See `docs/moi-scratchpad.md`.
- Agents run in the workspace directory; Claude Code and Codex approve every permission request by default (a `PreToolUse` allow hook and a transport-level accept, respectively) until UI approvals land. Each backend persists its own session history (see `harness/README.md`).