Skip to main content

Prerequisites

Before you begin, make sure you have:
  • Node.js 18+ installed
  • npm package manager
  • An OpenRouter API key (optional - demo mode works without keys)
Don’t have an OpenRouter key? Try demo mode first - it runs with an in-memory backend and sample data, no API keys required.

Create Your Agent

1

Clone the repository

Clone the ClarkOS SDK:
git clone https://github.com/clarkOS/clark my-agent
cd my-agent/example/convex
This gives you a fully-configured project with:
  • Convex backend setup
  • TypeScript configuration
  • Terminal UI (React Ink)
  • 179 passing tests
2

Install dependencies

Install the required packages:
npm install
3

Run the doctor (optional)

Validate your environment:
npm run doctor
This checks Node version, environment variables, and dependencies.
4

Try demo mode (no keys needed)

Start the agent with an in-memory backend:
npm run demo
This runs the terminal UI with sample data. Great for exploring before configuring API keys.
5

Or configure for full mode

Set up your environment variables:
cp .env.example .env.local
Edit .env.local with your API keys:
CONVEX_URL=https://your-project.convex.cloud
OPENROUTER_KEY=your-openrouter-key
GEMINI_API_KEY=your-gemini-key
Then run:
npm run dev

Terminal UI

The SDK includes a terminal-based interface built with React Ink:
┌─────────────────────────────────────────────┐
│  CLARK - Autonomous Agent                    │
│  Mood: curious | Health: 78 | Routine: day  │
├─────────────────────────────────────────────┤
│      ╭──────────╮                           │
│      │  ◉    ◉  │                           │
│      │    ──    │                           │
│      ╰──────────╯                           │
└─────────────────────────────────────────────┘

Keyboard Controls

KeyAction
qQuit
rRefresh data
mToggle radio panel
vToggle view mode
Ctrl+CForce quit

Your First Tick

The tick is the heartbeat of your agent. Every tick, your agent:
  1. Loads its current state and memories
  2. Gathers context (knowledge, recent activity)
  3. Calculates routine from current time
  4. Executes plugin hooks
  5. Updates state (health drift, counters)
To trigger a tick programmatically:
import { Agent, ConvexBackend } from './src';

const agent = new Agent({
  backend: new ConvexBackend({ url: process.env.CONVEX_URL! }),
});

await agent.tick();

Explore the API

Your agent exposes HTTP endpoints via the Convex backend:
EndpointMethodDescription
/healthGETHealth check
/stateGETCurrent agent state
/memoriesGETQuery memories
/memoriesPOSTStore a memory
/memories/coreGETCore memories
/memories/statsGETMemory statistics
/knowledgeGETKnowledge items
/logsGETActivity logs

Add a Plugin

Extend your agent with a plugin:
// plugins/logger.ts
import type { Plugin } from "./src/plugins";

export const loggerPlugin: Plugin = {
  name: "logger",
  version: "1.0.0",
  description: "Logs tick activity",

  init(agent) {
    console.log("Logger plugin initialized");
  },

  onTick(context) {
    console.log(`Tick executed. Mood: ${context.state.mood}, Health: ${context.state.health}`);
    console.log(`Memories loaded: ${context.memories.length}`);
  }
};
Register it in your agent:
import { Agent } from "./src";
import { ConvexBackend } from "./src/backend";
import { loggerPlugin } from "./plugins/logger";

const agent = new Agent({
  backend: new ConvexBackend({ url: process.env.CONVEX_URL! }),
  plugins: [loggerPlugin]
});

await agent.tick();

Run the Tests

The SDK includes 179 tests:
npm test

Next Steps

Understand Agents

Learn the core agent architecture.

Master Memory

Deep dive into the memory system.

Build Plugins

Create custom agent capabilities.

Explore Examples

See complete agent implementations.
Need help? Open an issue on GitHub.