| name | local-dev |
| description | Start the local development environment (embedded Postgres + Meilisearch + API) and run e2e tests. |
| disable-model-invocation | true |
| argument-hint | ["start|test|test:sandbox|reset|stop|status"] |
| allowed-tools | Bash(npm *, npx *, curl *, pkill *, sleep *, kill *, lsof *, ls *, cat *, mkdir *, rm *), Read, TaskOutput |
Local Development Environment
Manage the local dev stack via the arkeon CLI. Everything runs as a single Node process — embedded Postgres, spawned Meilisearch, and the API server — no Docker.
Stack Management
start (default)
Use arkeon up to start the stack as a background daemon:
npx tsx packages/arkeon/src/index.ts up
This:
- Starts embedded Postgres + Meilisearch + API server
- Registers the instance at
~/.arkeon/instances/<port>.json
- Registers the "admin" profile in the instance actor registry
- Stores the admin key in the CLI credential store
- Polls
/health until ready (up to 120s — first run downloads ~100MB Meilisearch binary)
For named instances (parallel stacks):
npx tsx packages/arkeon/src/index.ts up --name my-feature
Each named instance gets its own ARKEON_HOME at ~/.arkeon/<name>/, its own port, and its own data.
Check it's running:
npx tsx packages/arkeon/src/index.ts status
stop
npx tsx packages/arkeon/src/index.ts down [name]
Gracefully drains the API, stops Meilisearch, stops Postgres. No orphan processes.
reset
npx tsx packages/arkeon/src/index.ts reset --force
Wipes ~/.arkeon/data/ but preserves secrets and Meilisearch binary. Use --hard to wipe everything.
status
npx tsx packages/arkeon/src/index.ts status
Shows: process state, health, seed state, LLM config, state directory, running instances, and repo binding info (if in an initialized repo).
Worktree Isolation
Each worktree MUST run its own named instance and only use its own CLI build. The CLI and server are the same package — there's no version negotiation. Running worktree B's CLI against worktree A's server will break if the branches have schema or API differences.
WORKTREE_NAME=$(basename "$PWD")
npx tsx packages/arkeon/src/index.ts up --name "$WORKTREE_NAME"
This gives each worktree:
- Its own
ARKEON_HOME at ~/.arkeon/<name>/ (Postgres data, Meilisearch, secrets)
- Its own port (auto-selected, avoids collisions)
- Its own entry in
~/.arkeon/instances/ and its own actor registry
- Running its own branch's built code
Always run arkeon init, arkeon auth, and all other commands from the same worktree that started the instance. Don't cross worktree/instance boundaries.
Main tree (not a worktree) uses the default instance: ~/.arkeon/, port 8000.
Repo Binding and Auth
Initialize a repo
After the stack is running, bind a repo to it:
cd /path/to/my-repo
npx tsx packages/arkeon/src/index.ts init my-project
This creates:
- An ingestor actor on the graph
.arkeon/state.json with api_url, space_id, current_actor
- Actor key in
~/.config/arkeon-cli/credentials.json
- Entry in the instance actor registry
Auth profiles
All CLI commands auto-resolve identity from the repo's active profile. No ARKE_API_KEY needed.
npx tsx packages/arkeon/src/index.ts auth status
npx tsx packages/arkeon/src/index.ts auth profiles
npx tsx packages/arkeon/src/index.ts auth add reviewer --kind agent
npx tsx packages/arkeon/src/index.ts auth use reviewer
npx tsx packages/arkeon/src/index.ts auth remove reviewer
The resolution chain: ARKE_API_KEY env (override) -> repo state.actors (per-repo) -> instance actor registry (per-instance) -> global credential store.
Testing
test
- Ensure the stack is running (
arkeon up if not).
- Get admin key from
~/.arkeon/secrets.json.
- Run e2e tests:
ADMIN_KEY=$(cat ~/.arkeon/secrets.json | python3 -c "import sys,json; print(json.load(sys.stdin)['adminBootstrapKey'])")
E2E_BASE_URL=http://localhost:8000 \
ADMIN_BOOTSTRAP_KEY="$ADMIN_KEY" \
npm run test:e2e -w packages/arkeon
For named instances, adjust the port and secrets path:
ADMIN_KEY=$(cat ~/.arkeon/<name>/secrets.json | python3 -c "import sys,json; print(json.load(sys.stdin)['adminBootstrapKey'])")
E2E_BASE_URL=http://localhost:<port> \
ADMIN_BOOTSTRAP_KEY="$ADMIN_KEY" \
npm run test:e2e -w packages/arkeon
test:sandbox
Worker sandbox tests. Requires bubblewrap on Linux; macOS uses the fallback path.
./scripts/test-sandbox.sh
Knowledge Pipeline
The LLM-powered knowledge extraction pipeline is opt-in. It requires an OpenAI API key and an explicit env var:
ENABLE_KNOWLEDGE_PIPELINE=true OPENAI_API_KEY=sk-... npx tsx packages/arkeon/src/index.ts up
When enabled, ingesting documents (arkeon ingest) triggers entity/relationship extraction via LLM. Without it, ingestion stores raw chunks but skips extraction.
Unit tests (no LLM needed)
Merge, materialize, and ops-building logic can be tested without a running stack or API key:
npm test -w packages/arkeon -- --grep merge
E2E pipeline tests (LLM required)
Pipeline e2e tests (chunk-finalization.test.ts, ingest-idempotency.test.ts) are gated behind ENABLE_KNOWLEDGE_PIPELINE=true. They are skipped by default:
ENABLE_KNOWLEDGE_PIPELINE=true \
OPENAI_API_KEY=sk-... \
E2E_BASE_URL=http://localhost:8000 \
ADMIN_BOOTSTRAP_KEY="$ADMIN_KEY" \
npm run test:e2e -w packages/arkeon
Notes
- First run downloads the Meilisearch binary (~100MB) into
~/.arkeon/bin/. Cached after that.
- Secrets are generated on first run and stored in
$ARKEON_HOME/secrets.json. reset preserves them; reset --hard wipes them.
- After schema SQL changes,
reset and restart — migrations are idempotent but a fresh cluster is the reliable way to exercise the full chain.
- Worker sandbox tests require bubblewrap on Linux. On macOS the fallback path runs.
- The instance registry at
~/.arkeon/instances/ is cleaned up on arkeon down. Stale entries from crashed processes are pruned by arkeon status.