Skip to content
Playground

Quickstart

Last updated 9 days ago · 1db78aa

↑ Updated 9 days ago

"docs(guides): dual-syntax tabbed code examples across all guide pages" · 1db78aa · 2026-10-02

  • ## 5. Add Capabilities
  • Bun ≥1.0.0 (curl -fsSL https://bun.sh/install | bash)
  • An API key from Anthropic, Google Gemini, OpenAI, Groq, xAI, or LiteLLM — or run a local model with Ollama (no key needed)
  • TypeScript 5.5+ with "moduleResolution": "bundler" (rax init scaffolds this for you) — see Installation for the full tsconfig.json

The fastest path through this guide is the rax workflow (Rax = Reactive Agents Executable).

  1. Create a project — scaffold with rax init or bun init manually.

  2. Set up your environment — add at least one provider API key to .env.

  3. Build an agent — three lines gets you a working agent.

  4. Run it — bun run src/agent.ts.

  5. Add capabilities — attach tools, memory, and reasoning with HarnessProfile presets.

Using the CLI:

Terminal window
bunx reactive-agents init my-agent-app --template standard
cd my-agent-app
bun install

(Once reactive-agents is installed in a project, the shorter rax alias works: rax init my-agent-app --template standard.)

rax init --template standard scaffolds:

  • Directorymy-agent-app/
    • Directorysrc/
      • agent.ts Your first agent — runnable with bun run src/agent.ts
      • Directorytools/ Drop custom tools here; auto-discovered when wired into builder
        • …
    • .env Provider API keys (gitignored by default)
    • package.json reactive-agents dependency + bun run agent script
    • tsconfig.json strict mode + Bun-aware module resolution
    • README.md

Or manually:

Terminal window
mkdir my-agent-app && cd my-agent-app
bun init -y
bun add reactive-agents

Set at least one provider key. Pick whichever you have access to:

Terminal window
# Pick at least one
echo 'ANTHROPIC_API_KEY=sk-ant-...' > .env # Recommended for first agent
echo 'OPENAI_API_KEY=sk-...' >> .env
echo 'GOOGLE_API_KEY=...' >> .env
echo 'GROQ_API_KEY=gsk_...' >> .env
echo 'XAI_API_KEY=xai-...' >> .env
# Or run fully local — no key needed
ollama pull qwen3:4b

Optional keys for built-in tools (web search, etc.) — add them later when you call .withTools() (or set tools: {} in the config):

Terminal window
echo 'TAVILY_API_KEY=tvly-...' >> .env # Web search (Tavily backend)
echo 'SERPER_API_KEY=...' >> .env # Web search (Serper.dev backend)

Create src/agent.ts:

src/agent.ts
import { createAgent } from "reactive-agents";
const agent = await createAgent({
name: "my-first-agent", // `name` is required in the declarative config
provider: "anthropic",
});
const result = await agent.run("What are the three laws of thermodynamics?");
console.log(result.output);

That’s the minimum. .withProvider() (builder) or provider (config) picks the default model for the provider automatically (claude-sonnet-4-6 for Anthropic). Set ANTHROPIC_API_KEY in your environment before running — or use the local tab with Ollama and no key at all (see the Local Models guide).

To pin a specific model or add a name:

src/agent.ts
const agent = await createAgent({
name: "my-first-agent",
provider: "anthropic",
model: "claude-sonnet-4-6",
});
const result = await agent.run("What are the three laws of thermodynamics?");
console.log("Output:", result.output);
console.log("Duration:", result.metadata.duration, "ms");
console.log("Steps:", result.metadata.stepsCount);
Terminal window
bun run src/agent.ts

The canonical composition path is a HarnessProfile preset — lean(), balanced(), or intelligent(). On the builder, pass the preset to .withProfile(...); declaratively, the same presets are the profile config key ("lean" | "balanced" | "intelligent"). Presets compose the registry’s default-on capability set so you don’t pile up redundant .withX() calls.

src/agent.ts
import { createAgent } from "reactive-agents";
const agent = await createAgent({
name: "research-agent",
provider: "anthropic",
model: "claude-sonnet-4-6",
profile: "balanced", // memory + RI + verifier + strategy switching
});

Pick the preset that matches the workload:

  • HarnessProfile.lean() (profile: "lean") — model + nothing else. Latency- and cost-sensitive paths; benchmark ablations.
  • HarnessProfile.balanced() (profile: "balanced") — today’s production defaults (memory + reactive intelligence + verifier + strategy switching).
  • HarnessProfile.intelligent() (profile: "intelligent") — balanced + skill persistence for cross-session compounding learning.

Override one capability after the preset — order matters; later calls win (this example is builder-only — .compose() takes functions, which aren’t serializable into a config; the memory override itself is available declaratively as memory: { tier: "enhanced" }):

const agent = await ReactiveAgents.create()
.withName("research-agent")
.withProvider("anthropic")
.withModel("claude-sonnet-4-6")
.withProfile(HarnessProfile.balanced())
.withMemory({ tier: "enhanced" }) // upgrade memory to vector embeddings
.compose((h) =>
h.before("act", (ctx) => { // canonical chokepoint composition
console.log(`[act] iteration ${ctx.iteration}`);
}),
)
.build();

Individual .withX() methods are fully supported and compose cleanly with presets. Reach for a HarnessProfile preset when you want the whole default-on capability set in one line, or .compose(...) for a precise chokepoint.