ctx init
Creates the .contexo/ knowledge tree for a project and connects the AI coding agents on your
machine to it.
When you’d reach for it
Section titled “When you’d reach for it”Once per project, from the repository root, before anything else. It needs no login and never
contacts a Contexo server — every step is a local file write — so it is safe to run while you are
still deciding whether you want Contexo at all (ctx detach reverses it).
Two things trip people up. First, ctx init does not log you in or attach a remote repo;
straight after it you have a local knowledge base and nothing else, which is exactly what
ctx status reports below. Second, everything is written relative to the current directory (or
--root), so running it from a subdirectory quietly gives you a second, useless .contexo/. Run
it where your .git is.
Re-running is safe. It is idempotent by design: existing config, seed files, MCP entries and hooks
are left alone, so ctx init is a reasonable way to pick up an agent you installed after the fact
(though ctx mcp install and ctx hooks install are the targeted
tools for that).
Synopsis
Section titled “Synopsis”ctx initctx init --root path/to/projectctx init --no-gitignorectx init --no-mcp --no-hooksctx init --no-vscode| Flag | Type | Default | Description |
|---|---|---|---|
--no-cursor | bool | false | skip auto-wiring Cursor (.cursor/mcp.json) even when Cursor is detected |
--no-gitignore | bool | false | skip adding .contexo/ to .gitignore |
--no-hooks | bool | false | skip registering the Claude Code Stop hook for per-turn capture |
--no-mcp | bool | false | skip wiring the MCP server into agent configs (.mcp.json, .cursor/mcp.json, .vscode/mcp.json) |
--no-vscode | bool | false | skip auto-wiring VS Code (.vscode/mcp.json) even when VS Code is detected |
| Flag | Type | Default | Description |
|---|---|---|---|
--root | string | project root directory (default: current directory) |
A few of these do less — or more — than their one-liners suggest:
--no-cursoronly skips Cursor’s MCP entry. Cursor’s capture hooks are governed by--no-hooks, not by--no-cursor, soctx init --no-cursoron a machine with Cursor installed still writes.cursor/hooks.json. Use--no-hooksas well if you want no.cursor/directory at all.--no-hooksskips all three capture integrations, not just Claude Code’s: no Stop hook in.claude/settings.json, no.codex/hooks.json, no.cursor/hooks.json.--no-mcpimplies no Cursor or VS Code MCP entry, and also suppresses the “Codex detected” hint. It does not affect hooks.--no-vscodeonly skips VS Code’s.vscode/mcp.json. VS Code has no capture hooks, so there is nothing else to skip.--rootis a global flag and is resolved before anything is created; every path on this page is relative to it.
Examples
Section titled “Examples”Initialize a project
Section titled “Initialize a project”ctx init── SETUP
Wired Claude Code (.mcp.json) — restart your agent to load the contexo server
Cursor detected — wired .cursor/mcp.json
VS Code detected — wired .vscode/mcp.json
.vscode/ is usually committed: teammates need ctx on PATH
Created .gitignore with .contexo/
Installed Contexo capture Stop-hook in .claude/settings.json
Restart Claude Code (or open a new session) so the hook is picked up.
Installed Cursor capture hooks (.cursor/hooks.json: beforeSubmitPrompt + afterAgentResponse)
✔ Initialized .contexo in ~/projects/acme-api
── AGENT INTEGRATIONS
AGENT MCP SERVER CAPTURE (STOP HOOK)
● Claude Code wired (.mcp.json) installed
● Cursor wired (.cursor/mcp.json) installed
● VS Code wired (.vscode/mcp.json) -
○ Codex not installed not installed
── ADD CONTEXO TO ANOTHER AGENT OR HARNESS
Contexo's MCP server is a standard stdio server: command "ctx", args ["mcp"].
Add that to the agent's own MCP config — same server everywhere; only the
file and format differ:
AGENT CONFIG FORMAT / HOW
Claude Code ./.mcp.json JSON mcpServers — ctx mcp install --tool=claude
Cursor ./.cursor/mcp.json JSON mcpServers — ctx mcp install --tool=cursor
VS Code ./.vscode/mcp.json JSON servers — ctx mcp install --tool=vscode
Codex ~/.codex/config.toml TOML [mcp_servers.contexo] — ctx mcp install --tool=codex
Windsurf ~/.codeium/windsurf/mcp_config.json JSON mcpServers
OpenCode ./opencode.json JSON mcp: { contexo: { type: "local", command: ["ctx","mcp"] } }
Hermes config.yaml YAML mcp_servers: { contexo: { command: ctx, args: [mcp] } }
OpenClaw (CLI-managed) run the `openclaw mcp` command
JSON mcpServers entry: "contexo": { "command": "ctx", "args": ["mcp"] }
VS Code servers entry: "contexo": { "type": "stdio", "command": "ctx", "args": ["mcp", "--root", "${workspaceFolder}"] }
Any other MCP client: add the same server; see its docs for the exact path.
Capture (the Stop hook): Claude Code, Codex, and Cursor are supported.
try ctx hooks install --tool=claude|codex|cursor|all
Claude parses its transcript; Codex and Cursor pair their prompt + response
hooks inline. Other MCP-capable harnesses get the tools now; capture as they
expose a stop/turn-end hook.The per-file lines come first, then the summary: where .contexo/ landed, an integration table for
this project, and the guide for agents Contexo does not wire itself. This run was in a fresh git
repo with Cursor and VS Code installed and no Codex on PATH.
See what you actually have afterwards
Section titled “See what you actually have afterwards”ctx statuscontexo ○ not authenticated
── REMOTE
server https://api.contexo.live (from default)
repo (none — run 'ctx remote set-repo <id>')
auth no (run 'ctx auth login')
▲ server: status: not authenticated
try ctx auth login
── KNOWLEDGE
pages 0
last pull (never)
captures none pending
✔ no local changes (server not checked)No server, no repo, not authenticated. ctx init is local-only; wiring up the remote is
ctx login followed by ctx remote set-repo.
Re-check the wiring later
Section titled “Re-check the wiring later”ctx mcp status── AGENT INTEGRATIONS
AGENT MCP SERVER CAPTURE (STOP HOOK)
● Claude Code wired (.mcp.json) installed
● Cursor wired (.cursor/mcp.json) installed
● VS Code wired (.vscode/mcp.json) -
○ Codex not installed not installed
Add another agent (Windsurf, OpenCode, Hermes, ...)?
try ctx mcp guideThis is the same table ctx init prints at the end, on demand. Useful after you install a new
agent, or when an agent claims it cannot see the contexo server.
How it works
Section titled “How it works”Everything below is a local file write. ctx init contacts no Contexo server and makes no git
commit. The only network traffic it can produce is the update nudge every ctx command runs after
it succeeds — an at-most-once-per-24h GitHub releases lookup, skipped when stdout is not a TTY or
when CONTEXO_NO_UPDATE_CHECK or CI is set.
| Path | What ctx init does |
Skipped by |
|---|---|---|
.contexo/, .contexo/wiki/concepts/, .contexo/wiki/entities/, .contexo/wiki/analyses/, .contexo/raw/sessions/ |
created (mkdir -p, mode 0755) |
never |
.contexo/config.json |
written as {"version": 1} — only if absent |
never |
.contexo/index.md, .contexo/tags.md |
seeded with empty-section placeholders — only if absent | never |
.mcp.json |
merges mcpServers.contexo = {"command": "ctx", "args": ["mcp"]} |
--no-mcp |
.cursor/mcp.json |
same entry, only when Cursor is detected | --no-mcp, --no-cursor |
.vscode/mcp.json |
merges servers.contexo, VS Code’s own format (below), only when VS Code is detected |
--no-mcp, --no-vscode |
.gitignore |
created (or appended to) with a comment header plus .contexo/, only when <root>/.git exists |
--no-gitignore |
.claude/settings.json |
appends a Stop hook group running ctx capture turn, tagged _contexo: contexo-capture-turn |
--no-hooks |
.codex/hooks.json |
Stop + UserPromptSubmit hooks running ctx capture turn --agent codex, only when Codex is detected |
--no-hooks |
.cursor/hooks.json |
beforeSubmitPrompt + afterAgentResponse hooks running ctx capture turn --agent cursor (adds "version": 1), only when Cursor is detected |
--no-hooks |
Merging, not overwriting. The JSON writers load whatever is already there and add only the
contexo key, so other MCP servers and other hooks survive. If the contexo MCP entry is present
and identical, nothing is written at all and init says so. The .gitignore edit is skipped
entirely when a line already reads .contexo/ or .contexo.
Detection is deliberately asymmetric. Cursor counts as installed if ~/.cursor exists or
cursor is on PATH — wiring it only writes harmless project-local files. VS Code is detected the
same way: a ~/.vscode directory or code on PATH. Codex must have its binary on PATH; a
bare ~/.codex directory is not enough, because other tools create that directory and wiring Codex
means shelling out to codex mcp add.
VS Code gets its own format. VS Code (Copilot agent mode) reads workspace MCP servers from
.vscode/mcp.json, under a servers key rather than mcpServers, and each entry names its
transport. VS Code does not promise to start the server in the project directory, so the entry
passes the project root explicitly; VS Code substitutes ${workspaceFolder} itself:
{ "servers": { "contexo": { "type": "stdio", "command": "ctx", "args": ["mcp", "--root", "${workspaceFolder}"] } }}Init merges this entry into an existing file and keeps every other server and top-level key. VS
Code allows comments and trailing commas in this file, which a strict JSON rewrite would destroy, so
a file that is not strict JSON (or whose servers is not an object) is left untouched: init prints
the entry above for you to add by hand, and carries on. Any other problem writing the file is also
only a warning (run 'ctx mcp install --tool=vscode' later); it never stops init. After wiring it,
init reminds you that .vscode/ is usually committed, so teammates need ctx on their PATH.
Codex’s MCP server is never wired by init. It lives in Codex’s global ~/.codex/config.toml,
so init only prints a one-line hint and leaves the decision to you:
ctx mcp install --tool=codexHook failures are non-fatal. If the Stop hook cannot be installed, init prints
Warning: could not install Claude Stop hook: … (run 'ctx hooks install' later) and carries on;
the knowledge directory is the load-bearing part. The Codex and Cursor capture hooks warn the same
way (Warning: could not install Codex capture hooks: …).
Why the seed files matter. .contexo/index.md and .contexo/tags.md are what the ctx://index
and ctx://tags MCP resources read; the index is advertised to agents with priority 1.0. Seeding
them means the very first session gets a valid (if empty) index instead of a read error. They are
rebuilt from your pages whenever an agent writes a page (ctx_write_page) and on every
ctx pull.
Common errors
Section titled “Common errors”init: write .mcp.json: agentwire: parse …: invalid character … — an existing .mcp.json (or
.cursor/mcp.json) is not valid JSON. Init refuses to guess and aborts. The .contexo/ tree was
created first and survives; the .gitignore line and the hooks come after MCP wiring and never
ran. Fix the file, or run ctx init --no-mcp and wire the agent afterwards with ctx mcp install.
.vscode/mcp.json is not strict JSON (comments or trailing commas?); left it untouched. Add this entry by hand:
— followed by the entry. Unlike the two files above, this one never aborts init:
paste the printed contexo entry into the file’s servers object yourself.
init: create …: permission denied — the project root is not writable. Directory creation is
the very first step, so nothing else has been touched.
No .gitignore line and no message about one — the directory has no .git, so the step is
skipped silently. Run git init first, then ctx init again (it is idempotent), or add
.contexo/ yourself.
Agent shows contexo with zero tools — the agent is running ctx mcp outside a Contexo
project. Outside a .contexo/ directory the MCP server starts in dormant mode with no tools rather
than failing. Check that the agent’s working directory is the project root you ran ctx init in.
See also
Section titled “See also”ctx detach— reverse everything on this page, including the VS Code entryctx mcp— wire, unwire, and inspect agent MCP configs on their ownctx hooks— install or remove the capture hooks on their ownctx login— the next step: authenticate and attach a remote repo
