npm.io
1.0.0 • Published yesterdayCLI

ankiclaw

Licence
MIT
Version
1.0.0
Deps
13
Size
335 kB
Vulns
0
Weekly
0
Install scriptsThis package runs scripts during installation (preinstall/install/postinstall)

AnkiClaw

A from-scratch personal agentic AI assistant — file access, terminal control, browser automation, and modular tools via MCP — with production-style guardrails: permissions, diff previews, logging, cost tracking, session persistence, and memory.

Built to demonstrate real agent engineering: the tool-calling loop, sandboxed permissions, context management under token budgets, and operational observability. Config lives in your user home (~/.ankiclaw), not inside each project.


Table of contents


How it works

At its core AnkiClaw is a loop:

  1. Build context (SOUL.md, memory, conversation, live plan).
  2. Call the model with a set of tool definitions.
  3. If the model requests a tool, run it under the permission policy.
  4. Feed the result back; repeat until the model responds with text only.
┌─────────────────────────────────────────────┐
│  CLI / TUI (ankiclaw start)                 │
└───────────────┬─────────────────────────────┘
                │
┌───────────────▼─────────────────────────────┐
│  Agent core                                 │
│  context → model → tool_use → execute → …   │
└───────────────┬─────────────────────────────┘
                │
    ┌───────────┼────────────┬─────────────┐
    ▼           ▼            ▼             ▼
  Files     Terminal      Browser        MCP
    │           │            │
  Permissions · Diff preview · Approval prompts

Cross-cutting: Plan · Cost · Logs · Interrupt · Sessions · Memory

Policy (what the agent may do) is separated from mechanism (how tools run). Edit SOUL.md and permissions.yaml without touching application code.


Requirements

  • Node.js 20+
  • An API key for at least one provider: Anthropic, OpenAI, or Google Gemini
  • Optional: Playwright Chromium (installed via postinstall; see Browser)

Install

Requires Node.js 20+.

npm install -g ankiclaw
ankiclaw init          # interactive setup → ~/.ankiclaw
ankiclaw start         # interactive TUI from any directory
Without a global install
npx ankiclaw init
npx ankiclaw start
Platform notes
Platform Notes
macOS / Linux Agent home is ~/.ankiclaw. After install, which ankiclaw should resolve on your PATH.
Windows npm installs an ankiclaw.cmd shim. Agent home is %USERPROFILE%\.ankiclaw.

If browser tools fail after install:

npx playwright install chromium

Quick start

  1. Run ankiclaw init and enter at least one API key; pick a default model.
  2. Run ankiclaw start.
  3. Ask it to do something concrete, e.g. “List files in the workspace and summarize README.”
  4. Approve terminal or file changes when prompted; press Esc to interrupt a running turn.
  5. Use /cost to see token usage; /quit to save and exit.

Shell tools use your current working directory, so you can cd into a repo and operate on it. File writes default to the sandboxed workspace/ under the agent home unless you approve paths outside it.


CLI usage

ankiclaw init [--force]     Interactive setup (~/.ankiclaw)
ankiclaw start              Start the interactive agent (alias: start_agent)
ankiclaw "one-shot prompt"  Run a single prompt and exit
ankiclaw help
Command Behavior
init Copies templates into the agent home, writes .env, patches config.yaml / permissions.yaml. Use --force to re-run over an existing home.
start Fullscreen TUI REPL with slash commands, live plan, cost meter, and Esc interrupt.
oneshot Non-interactive: one user prompt, agent loop runs to completion, then exits.

Override the agent home with ANKICLAW_HOME (absolute path or relative to cwd). Useful for development and isolated profiles.


Agent home

Default location: ~/.ankiclaw (Windows: %USERPROFILE%\.ankiclaw).

~/.ankiclaw/
├── .env                      # API keys (never commit)
├── SOUL.md                   # Persona + hard behavioral rules
├── config.yaml               # Provider, model catalog, memory settings
├── permissions.yaml          # Terminal / filesystem / browser policy
├── skills/
│   ├── git_workflow/SKILL.md
│   └── web_research/SKILL.md
├── tools/
│   └── mcp_registry.json     # External MCP servers
├── workspace/                # Default file sandbox
│   ├── scratch/              # Low-friction drafts (often always_allow)
│   └── secrets/              # Blocked from agent writes by default
├── sessions/                 # Saved chat snapshots
├── plans/session_<id>/       # Live todo checklists
├── memory/
│   ├── long_term/memory.jsonl
│   └── episodic/             # Archived full transcripts
├── logs/
│   ├── tool_calls_<date>.jsonl
│   ├── tool_calls_<date>.log
│   └── cost_<date>.jsonl
└── mcp-oauth/                # OAuth tokens for remote MCP servers

ankiclaw init seeds this tree from the package templates/ directory.


Features

1. Multi-provider models

AnkiClaw talks to Anthropic, OpenAI, and Google through a shared provider interface. The catalog in config.yaml lists available models; the TUI /model command switches at runtime.

Defaults (from the shipped template):

Model id Provider
claude-sonnet-5, claude-haiku-4-5 Anthropic
gpt-4.1, gpt-4.1-mini OpenAI
gemini-3.5-flash, gemini-3.5-flash-lite, gemini-3.5-pro Google

Environment overrides (win over config.yaml):

ANKICLAW_PROVIDER=google
ANKICLAW_MODEL=gemini-3.5-flash

API keys live in ~/.ankiclaw/.env (written by init):

ANTHROPIC_API_KEY=...
OPENAI_API_KEY=...
GEMINI_API_KEY=...

2. SOUL.md and skills

SOUL.md is the system prompt: identity, tone, and hard rules (“never delete outside the workspace,” “rely on diff/approval before mutating files”). Keeping this as markdown separates policy from code.

Skills are on-demand workflows under skills/<name>/SKILL.md. Each file may include YAML frontmatter (name, description). The agent sees a catalog of skill names/descriptions and calls load_skill to pull the full workflow into context when relevant.

Shipped skills:

Skill Purpose
git_workflow Safe local git inspection and commit-message drafting
web_research Search → browse → note-taking into the workspace

Add your own by dropping a new folder with a SKILL.md into skills/.


3. File tools and sandbox

Native tools:

Tool Role
read_file Read UTF-8 text, or extract text from PDF, DOCX, XLSX, CSV
create_file Create a new file (fails if it already exists)
edit_file Replace contents of an existing file
delete_file Delete a file

Sandboxing: every path is resolved to an absolute path against the agent home, checked for ../ traversal and symlink escapes, then matched against permissions.yaml.

filesystem:
  workspace_root: "./workspace"
  allow:
    - "workspace/**"
  deny:
    - "workspace/.env"
    - "workspace/secrets/**"
  outside_workspace: ask   # or "deny"

Diff preview: create / edit / delete compute a unified diff first. The CLI shows it; the same three-tier rules as terminal commands decide whether to auto-approve, ask, or block:

file_edits:
  always_allow:
    - "workspace/scratch/**"
  ask:
    - "workspace/**"
  always_block:
    - "workspace/.env"
    - "workspace/secrets/**"

Approved writes are logged (hashes, diff, timestamp) for audit.


4. Terminal permissions

Tool: run_terminal_command.

Three-tier policy in permissions.yaml:

terminal:
  always_allow:
    - "pwd"
    - "ls *"
    - "git status"
    - "git diff *"
  always_block:
    - "rm -rf /*"
    - "sudo *"
  default: ask

Commands are normalized and matched with globs. On ask, the TUI shows the exact command and waits for approval. Denied commands return a tool result the model can adapt to (it should not retry the same forbidden action).

Stdout/stderr are captured, truncated for the model context when huge, and fully preserved in the tool-call logs. The shell runs in your current working directory, so AnkiClaw can operate on whatever repo you launched it from.


5. Plan tracking

Tool: update_plan.

For multi-step work the agent maintains a live checklist (JSON internally, rendered as markdown for you):

~/.ankiclaw/plans/session_<id>/todo.md

Each item has status: pending | in_progress | done | paused. The plan is reinjected into context on later turns and shown in the TUI when updated. On interrupt, in-progress items become paused so a resumed session knows where it left off.


6. Interrupt / cancel

Press Esc during a busy turn to request an interrupt:

  • Between tool calls: the loop stops before the next dispatch.
  • Mid tool call: in-flight work (terminal, browser, search) is aborted via AbortSignal; partial results may return with interrupted: true.
  • The plan is marked paused rather than completed.

This is the control surface that makes long agent runs feel like a real tool instead of an unstoppable script.


7. Sessions and chats

Each interactive run is a session with an id like sess_a36f380c. After turns, AnkiClaw snapshots:

  • Working message history
  • Plan reference
  • Workspace root
  • Cost summary
  • Status (active / paused / completed)

Snapshots live under sessions/. In the TUI:

Command Action
/chat new Save current chat and start a fresh one
/chat load Pick or select a saved chat to resume
/chat delete Delete a saved chat
/clear Clear in-memory history for the current session
/quit Save and leave

The agent can also call load_chat with a session_id (e.g. from memory search) to pull a prior transcript into context.


8. Memory and compaction

Configured under memory: in config.yaml:

memory:
  compaction:
    token_threshold: 24000
    keep_recent_messages: 12
  long_term:
    max_inject: 8
  episodic:
    enabled: true
Layer What it is Tools / behavior
Working context Messages sent to the API each turn Built automatically
Compaction When estimated tokens cross the threshold, older turns are summarized; recent N kept verbatim Transparent; plan stays pinned
Long-term Distilled facts in memory/long_term/memory.jsonl remember, auto-distill on session end; injected on new sessions
Episodic Full archived transcripts under memory/episodic/ search_memory (keyword), then load_chat for the full thread

Retrieval is keyword/recency based — enough for durable preferences and “what did we do last time?” without a vector DB.


Headless Playwright Chromium plus a search helper.

Tool Behavior
web_search Discover URLs and snippets (Brave if BRAVE_API_KEY is set; otherwise DuckDuckGo HTML)
browser_navigate Open an http(s) URL; returns title + accessibility-tree snapshot (not raw HTML)
browser_click Click by CSS selector
browser_type Type into a field
browser_get_text Re-snapshot the current page
browser_screenshot Full-page PNG under workspace/scratch/screenshots/ (path returned; image not sent to the model)

Browser actions respect permissions.yaml:

browser:
  enabled: true
  navigate: ask
  interact: always_allow
  search: always_allow

If Chromium is missing: npx playwright install chromium.


10. MCP (modular tools)

AnkiClaw is an MCP client. Servers listed in tools/mcp_registry.json are connected at startup; their tools are merged into the model schema as mcp_<server>_<tool>. Adding a capability is a config change, not a code change.

Example registry entry shape:

{
  "name": "gmail",
  "enabled": false,
  "transport": "http",
  "url": "https://gmailmcp.googleapis.com/mcp/v1",
  "oauth": {
    "clientIdEnv": "GOOGLE_MCP_CLIENT_ID",
    "clientSecretEnv": "GOOGLE_MCP_CLIENT_SECRET",
    "redirectUri": "http://127.0.0.1:8765/oauth/callback"
  }
}
Google Workspace MCP (Developer Preview)

Overview: Configure Google Workspace MCP servers.

  1. In Google Cloud: enable product APIs + MCP APIs; configure OAuth consent.
  2. Create an OAuth Web application client.
  3. Authorized redirect URI (exact): http://127.0.0.1:8765/oauth/callback
  4. Put credentials in ~/.ankiclaw/.env (or re-run ankiclaw init):
GOOGLE_MCP_CLIENT_ID=...
GOOGLE_MCP_CLIENT_SECRET=...
  1. In tools/mcp_registry.json, set "enabled": true on the servers you want (gmail, drive, calendar, people, chat).
  2. Run ankiclaw start. On first connect, a browser opens for Google sign-in; tokens are stored under mcp-oauth/.

You can also register stdio or other HTTP MCP servers in the same registry format used by the hub.


11. Logging and cost

Tool-call logs (every file, terminal, browser, and MCP invocation):

File Format
logs/tool_calls_<date>.jsonl One JSON object per line (args, permission tier, approval, duration, truncation)
logs/tool_calls_<date>.log Human-readable mirror for skimming

Cost tracking: each API response’s token usage is appended to logs/cost_<date>.jsonl and priced with approximate public rates (including cache read/write when the provider reports them). Use /cost in the TUI for a session summary: call count, tokens by type, estimated USD, cache hit rate.

A live cost meter also appears in the TUI status area during a session.


Interactive slash commands

Type / in the TUI for a hierarchical palette:

Command Description
/chat Expand into chat management
/chat new Save current chat and start a new one
/chat load Load a saved chat
/chat delete Delete a saved chat
/model Expand into model commands
/model list Show current model and catalog
/model change <id> Switch model for this session
/cost Session token usage and estimated cost
/clear Clear conversation history for this session
/quit Save current chat and exit

Esc — interrupt the active turn.
↑ / ↓ · Enter — navigate pickers (sessions, models).


Configuration reference

config.yaml
Key Meaning
provider / model Default provider and model id
max_tokens Generation cap per model call
models Catalog entries (id, provider, label)
memory.compaction.token_threshold Trigger summarization when working context grows
memory.compaction.keep_recent_messages Verbatim window after compaction
memory.long_term.max_inject Max long-term facts injected into new context
memory.episodic.enabled Archive full transcripts on session end
permissions.yaml
Section Controls
terminal always_allow / always_block / default
filesystem workspace_root, path allow/deny, outside_workspace
file_edits Path-scoped allow / ask / block for mutations
browser enabled, navigate, interact, search
Environment variables
Variable Purpose
ANKICLAW_HOME Override agent home directory
ANKICLAW_PROVIDER / ANKICLAW_MODEL Override default model selection
ANTHROPIC_API_KEY / OPENAI_API_KEY / GEMINI_API_KEY Provider credentials
BRAVE_API_KEY Prefer Brave Search for web_search
GOOGLE_MCP_CLIENT_ID / GOOGLE_MCP_CLIENT_SECRET Google Workspace MCP OAuth

See .env.example / templates/env.example for a full commented template.


Local development

Clone this repo, then:

npm install
npm run start_agent    # ANKICLAW_HOME=<repo>/.agent via scripts/run-dev.mjs
npm test
npm run build
node bin/ankiclaw.js help
Script Role
npm run start_agent / npm run dev Run TypeScript via tsx against the repo’s .agent home
npm test Node test runner over test/**/*.test.ts
npm run build Compile src/dist/
npm run typecheck tsc --noEmit

Contributor agent home (.agent/) holds checked-in policy (SOUL.md, config.yaml, permissions.yaml, skills, MCP registry). Runtime dirs (logs/, sessions/, memory/, workspace/) are gitignored — put API keys in a local .env (also gitignored).

For a clean user-style install from a local checkout:

npm run build
npm link          # or: npm pack && npm install -g ./ankiclaw-*.tgz
ankiclaw init
ankiclaw start

Project layout

ankiclaw/
├── bin/ankiclaw.js           # CLI entry
├── src/
│   ├── agent.ts              # Tool loop + native tool definitions
│   ├── cli.ts / tui.ts / ui.ts
│   ├── permissions.ts        # Path + terminal + browser policy
│   ├── files.ts / terminal.ts / browser.ts / web-search.ts
│   ├── plan.ts / session.ts / interrupt.ts
│   ├── cost.ts / logger.ts
│   ├── soul.ts               # SOUL.md + skills loader
│   ├── init.ts / paths.ts
│   ├── model/                # Anthropic, OpenAI, Google providers
│   ├── memory/               # Compaction, long-term, episodic
│   └── mcp/                  # Hub, registry, OAuth
├── templates/                # Seeded into ~/.ankiclaw by init
├── test/
├── scripts/run-dev.mjs       # Local ANKICLAW_HOME=.agent runner
└── PROJECT_DESIGN.md         # Architecture notes and original phased plan

For deeper design rationale (permission philosophy, why dual logging, portfolio framing), see PROJECT_DESIGN.md.


License

MIT — see LICENSE.

Keywords