Embed it
Embed the runtime
@arcturn/core is the same event-driven agent the arcturn CLI is built on — one Agent per session, one AgentEvent stream out. No terminal required.
import { createAgent } from "@arcturn/core";
import { createClient, requireModel } from "@arcturn/ai";
import { createDefaultTools } from "@arcturn/tools";
const llm = createClient(); // resolves API keys from the environment
const { tools } = createDefaultTools({ cwd: process.cwd() });
const agent = createAgent({
llm,
model: requireModel("anthropic/claude-sonnet-4-5"),
systemPrompt: "You are a focused, careful coding agent.",
tools,
cwd: process.cwd(),
sessionDir: ".arcturn/sessions", // omit for an unpersisted, in-memory agent
permissions: { mode: "default" },
});
await agent.prompt("Add input validation to the signup handler");
console.log(agent.finalText());What you get
Everything the terminal agent has, as a library.
There is no separate embedding API. The TUI, the HTTP server and --output-format json are all just different consumers of the same Agent.
The agent loop and steering
One Agent per session, options in and events out. agent.prompt() resolves when the model stops calling tools; steer() injects text mid-run.
The same permission engine
PermissionEngine with rules, scopes and modes, wired from code — plus a PermissionRequester callback for your own UI, and the plan-mode exit gate.
Sessions that branch
JsonlSessionStore or MemorySessionStore behind one SessionStore interface: resume a branch, fork from an older entry, force compaction.
Custom tools
A JSON-Schema definition and an execute contract, with an abort signal, a permission callback and an incremental progress channel in context.
Sub-agents and MCP bridging
Delegate to child agents whose whole event stream re-publishes on the parent, and bridge MCP server tools into ordinary Tool objects.
VCR record/replay and cost
Record a cassette of stream events and tool results, replay it hermetically, and read per-turn usage and cost off the same stream.
The event stream
One subscription, every event.
Subscribe once and you have what the TUI renders, what the server forwards, and what the CLI prints as NDJSON — the same union, in the same order.
const off = agent.subscribe((event) => {
if (event.type === "toolEnd") {
console.log(event.result.isError ? "✗" : "✓", event.toolCallId);
}
});
// off() to unsubscribe
agent.on("runEnd", (event) => {
switch (event.reason) {
case "completed":
break; // normal
case "aborted":
break; // agent.abort() was called, or the external signal fired
case "error":
console.error(event.errorMessage); // model, provider, or a thrown hook
break;
}
});{"type":"turnStart","turn":1}
{"type":"toolCallStart","toolCallId":"tc_1","toolName":"grep","input":{"pattern":"TODO"}}
{"type":"toolCallEnd","toolCallId":"tc_1","result":{"content":[{"type":"text","text":"…"}]}}
{"type":"runEnd","reason":"completed"}Runs never reject. agent.prompt() resolves when the model stops calling tools, the run is aborted, or a runtime error occurs — the outcome always arrives as a terminal runEnd event instead, so failure handling lives in one place. Listener exceptions are swallowed by the agent: one bad subscriber can never break a run.
Package map
Eleven packages, split by concern.
The runtime is split by concern and each piece has its own dependency surface — @arcturn/types, core, index and protocol carry no external runtime dependencies at all.
@arcturn/types- Zero-dependency shared contracts (messages, events, tools, permissions, sessions, protocol)
@arcturn/ai- Unified multi-provider LLM streaming client with model catalog and retry
@arcturn/core- Agent runtime: event loop, steering, sessions, compaction, permissions, sub-agents
@arcturn/tools- Built-in tools: read, write, edit, bash (+background), grep, glob, ls, fetch
@arcturn/mcp- Model Context Protocol client bridge
@arcturn/tui- Terminal UI library with differential rendering
@arcturn/index- Token-optimized code index and BM25 semantic search
@arcturn/protocol- NDJSON wire protocol for server mode
@arcturn/server- WebSocket server exposing agent sessions to remote clients
@arcturn/evals- Task-level eval harness: real coding tasks with programmatic assertions
arcturn- The interactive coding agent, workflow engine, and agent-org runtime
| Package | What it is |
|---|---|
@arcturn/types | Zero-dependency shared contracts (messages, events, tools, permissions, sessions, protocol) |
@arcturn/ai | Unified multi-provider LLM streaming client with model catalog and retry |
@arcturn/core | Agent runtime: event loop, steering, sessions, compaction, permissions, sub-agents |
@arcturn/tools | Built-in tools: read, write, edit, bash (+background), grep, glob, ls, fetch |
@arcturn/mcp | Model Context Protocol client bridge |
@arcturn/tui | Terminal UI library with differential rendering |
@arcturn/index | Token-optimized code index and BM25 semantic search |
@arcturn/protocol | NDJSON wire protocol for server mode |
@arcturn/server | WebSocket server exposing agent sessions to remote clients |
@arcturn/evals | Task-level eval harness: real coding tasks with programmatic assertions |
arcturn | The interactive coding agent, workflow engine, and agent-org runtime |
Every turn counts.
The SDK docs start where this page stops: every option, every event, and a worked custom tool.