Skip to content

Connect Claude Code

Four Claude Code hooks send a record to Planisphere for each prompt you submit, each tool call Claude makes and each reply it finishes. Prompts, tool inputs and replies are hashed with SHA-256 on your machine; Planisphere receives the hashes, not the text. The hooks record activity. They don't gate it: every hook exits successfully, so a failed delivery never stops Claude Code.

The console writes the hooks for you. On the Connections page, under Connect a system, choose Claude Code, paste a key, and copy the block labelled Claude Code hooks (settings.json). Read the commands before you paste them anywhere.

What the hooks record

Every record uses the AI Provenance pack and the system name claude-code-primary.

Record (hook) Hashed on your machine Sent as plain metadata
prompt_submitted (UserPromptSubmit) The prompt text Model, session ID, working directory, agent type, a prompt counter
tool_used (PreToolUse, every tool) The tool's input, as compact JSON Tool name, tool class, session ID, agent type
agent_response (Stop) Claude's latest reply text, and the whole transcript file Model, session ID, stop reason, working directory, turn count, a reply counter

The fourth hook, SessionStart, sends nothing. It saves the session's model name in /tmp/planisphere/ so the prompt records can carry it.

The tool class groups tool names: fs_read (Read, Glob, Grep), fs_write (Write, Edit, NotebookEdit), shell (Bash, BashOutput, KillShell), network (WebFetch, WebSearch), agent_dispatch (Task, Agent), skill (Skill) and other.

A few limits follow from where the hooks run:

  • Tool calls are recorded before they run. PreToolUse fires as Claude asks for the tool, so a tool_used record says the call was requested. Its success is pending and its duration_ms is 0: placeholders, not measurements. Tool output is not recorded.
  • The working directory is sent as written. Prompt and reply records carry the full path of the folder Claude Code runs in. If a path names a client or a project you keep private, use a neutral folder name.
  • The Stop hook reads your transcript locally. It finds Claude's latest reply in the session transcript and hashes it, and it hashes the transcript file as a whole. Neither leaves your machine as text.
  • The counters are per machine. system_seq comes from ~/.claude/planisphere-seq-prompt and ~/.claude/planisphere-seq-response, which the hooks increment. Two machines keep separate counts.

Before you start

  • jq. The hooks use it to read each event Claude Code passes them. Check with command -v jq; on a Mac, brew install jq; on Debian or Ubuntu, sudo apt-get install jq.
  • curl and a SHA-256 tool. macOS has curl and shasum; most Linux systems have curl and sha256sum. The hooks use whichever is present.
  • A key from your workspace. Create one on the console's Keys page. Use a key just for this machine, for example claude-code-laptop, so you can revoke it without touching anything else.
  • macOS or Linux. Claude Code runs each hook command with sh -c: bash 3.2 in POSIX mode on macOS, dash on Debian and Ubuntu. The hooks are written for that plain POSIX shell, not for a newer bash.

The key ends up in your settings file as plain text, inside each hook command. Keep that file private, and never put these hooks in a settings file you commit to a repository.

Add the hooks

  1. In the console, open Connections and choose Claude Code under Connect a system.
  2. Paste your key into Key to fill in. It stays in that browser tab and fills into the hooks; nothing is sent.
  3. Copy the Claude Code hooks (settings.json) block.
  4. Open ~/.claude/settings.json, your user settings, which apply to every project on this machine. If the file doesn't exist, create it with the block as its whole content.
  5. If the file already has a "hooks" object, merge rather than replace: for each of SessionStart, PreToolUse, UserPromptSubmit and Stop, add the Planisphere entry to the event's list next to the entries you already have. Check the result is valid JSON with jq . ~/.claude/settings.json.
  6. Start a new Claude Code session. Claude Code's /hooks menu lists the hooks it loaded.

To connect a single project instead, put the hooks in that project's .claude/settings.local.json, your own settings for that project, which are not meant to be committed. Avoid .claude/settings.json in a project: it is shared through the repository, and the hooks contain your key.

Check that records arrive

Send a prompt in the new session, then open the console:

  • Connections → Systems sending records lists claude-code-primary with its record count for the last 24 hours, when the last record arrived and its last event. The last event opens that record.
  • Activity lists the records your workspace sealed, newest first. Each opens with its receipt.

The hooks don't print action keys, so start from the Systems table rather than Check a received record. One received record shows that the hooks ran and reached your workspace once; it doesn't show that every prompt or tool call was captured.

Troubleshooting

Nothing arrives. The hooks send in the background and discard errors, so a failure is silent. Check, in order:

  1. command -v jq prints a path.
  2. jq . ~/.claude/settings.json prints your settings, not an error.
  3. You started a new session after adding the hooks, and /hooks lists them.
  4. The key is current. This prints 200 for a working key and 401 for a revoked or mistyped one:

    curl -sS -o /dev/null -w '%{http_code}\n' https://api.planisphere.ooo/tenant/me \
      -H "X-Planisphere-Key: YOUR_KEY"
    

Prompts and replies arrive, but no tool calls, or Claude Code reports a hook error on every tool. Your hooks are an older copy. Claude Code runs hook commands with sh -c, and on macOS that is bash 3.2 in POSIX mode, which can't parse a case pattern's closing ) inside $(...). The old PreToolUse command then stops with syntax error near unexpected token and exit status 2, which Claude Code treats as a block on that tool call. Copy the hooks again from Connections, or edit the PreToolUse command so each pattern opens with ( as well:

CLASS=$(case "$TN" in (Read|Glob|Grep) echo fs_read;; (Write|Edit|NotebookEdit) echo fs_write;; (Bash|BashOutput|KillShell) echo shell;; (WebFetch|WebSearch) echo network;; (Task|Agent) echo agent_dispatch;; (Skill) echo skill;; (*) echo other;; esac);

Some prompts or tool calls never arrive, often the ones with line breaks or backslashes. Your hooks are an older copy that passes each event to jq with echo "$INPUT". In sh (bash 3.2 in POSIX mode on macOS, dash on Debian and Ubuntu), echo turns the \n and other backslash escapes inside the event's JSON into real characters, so jq can't read it and the record is silently dropped. Copy the hooks again from Connections: the current hooks pass each value with printf '%s\n', which prints it unchanged. To fix a copy by hand, replace every echo "$INPUT" and echo "$LAST" with the same printf form, for example:

SID=$(printf '%s\n' "$INPUT" | jq -r .session_id);

Older Stop hooks fail differently: instead of dropping the record, they send a reply record whose response hash is the hash of empty text (sha256:e3b0c442…) and whose model is blank. Records like that, sealed before you updated the hooks, show an empty reply, not the real one.

Records stopped after a while. A sandbox workspace keeps up to 100 records, and the hooks send one for every prompt, tool call and reply, so a working session reaches that quickly. After that the API answers 402 and the hooks drop the record. Upgrade on the console's Billing page.

The model shows as unknown. The prompt record reads the model name that SessionStart saved in /tmp/planisphere/. If that file is missing (the session began before you added the hooks, or /tmp was cleared), the record says unknown. A new session fixes it.

Remove the hooks

Delete the four Planisphere entries from ~/.claude/settings.json (or from the project file you used), then start a new session. Remove /tmp/planisphere/ and ~/.claude/planisphere-seq-* if you no longer want them, and revoke the key on the console's Keys page.

Hook events and settings files follow the official Claude Code hooks documentation.