The kernel that decides whether an AI agent's action is allowed — with 1,747 tests, cryptographic receipts, and 60-second verification.
When an AI agent can spend money, change infrastructure, or write to production, someone has to decide what's allowed. That decision can't live in the agent — the agent is the thing you're worried about. The decision has to live in a kernel that's outside the agent's process and outside the agent's own code path. Rules don't work. A smart enough model routes around rules. Prompts don't work. Prompts are soft. A model that reasons itself into approving its own refund will approve its own refund.
Custodian is that kernel. The model proposes. The kernel decides. The verifier proves. The kill switch stops. The receipt cryptographically records everything.
custodianis the provider-neutral governance kernel.paladinis the provider-neutral credential vault and egress broker.talariais the Hermes Agent + NemoClaw integration layer — its own repo and PyPI package (custodian-talaria), depending on this kernel through a normal version pin (custodian-kernel[paladin]>=0.4.0,<0.5) rather than shipping in the same distribution. A future Claude/Codex integration would be its own equivalent package, resting on the same neutral core.- A consuming website or business application owns its routes, branding, credentials, prompts, and deployment configuration. Custodian does not know about or call back to getcustodian.xyz unless that deployment explicitly supplies its own endpoint.
custodian and paladin ship together in the 0.4.0 distribution so
installation and Windows testing remain one step. Their import dependency
direction is still enforced: integrations (like talaria) may depend on the
kernel or broker; the kernel and broker never depend on a particular website
or agent framework — see tests/test_architecture_boundaries.py.
Install:
pip install custodian-codex-guard
custodian setup # detects a local Hermes Agent, tells you what to add
custodian setup --profile hermes # installs + configures Talaria and its dashboard
custodian doctor --profile hermes # verifies the complete installationcustodian setup is the one command most people use after installation. The
Hermes profile installs the compatible Talaria release with its local
dashboard, installs the guard plugin and starter policy, creates the Paladin
vault if needed, and enables the plugin when Hermes is available. Prefer to
wire it up yourself instead? Plain extras work exactly as before:
pip install custodian-codex-guard[paladin] and pip install custodian-talaria.
Custodian is a kernel. The kernel existed before Build Week. The kernel is agent-agnostic — it works with any tool-calling agent.
Watch the product demo: Custodian Codex Guard: A Safety Layer for AI Coding Agents.
What we shipped during OpenAI Build Week is the Codex Guard adapter — the piece that knows how to talk to OpenAI's Codex CLI. The adapter sits between Codex and the kernel. Every action Codex proposes gets classified by the kernel before it runs. Safe workspace reads, tests, and edits may proceed; secrets, off-scope paths, destructive commands, network access, production changes, money movement, and governance changes deny or require a human. Decisions produce value-free HMAC hash-chained receipts.
Enforcement is a Codex PreToolUse hook, not the opt-in MCP tool: once active it
runs before every tool call and blocks anything the kernel denies — even under
approval_policy = "never" or a trusted project, regardless of whether the model
consults the guard. Two install postures:
custodian-codex setupinstalls a user-level hook. Codex requires a one-time TUI trust approval for it (an untrusted hook is skipped in non-interactiveexec), so approve the prompt once.sudo custodian-codex setup --managed-lockinstalls it as an always-on managed hook (auto-trusted, runs inexec) and locks Codex to managed hooks only, so neither the model nor a project config can strip it. This is the "100% required" posture; the managed dir is platform-aware (/etc/codex,%PROGRAMDATA%\Codex, orCUSTODIAN_CODEX_MANAGED_DIR).
Operator escape hatch, if the guard misbehaves: sudo custodian-codex hook-uninstall --managed (or custodian-codex hook-uninstall for the user-level
hook). Only someone with write access to the managed dir can disable it — never
the model. The MCP server remains for receipt/approval visibility, and
custodian-codex doctor reports whether enforcement is managed, user-level, or
missing.
This is the contribution to the OpenAI Build Week track: the policy bridge, the receipts CLI, the MCP server integration, and 104 tests covering the full Codex threat model. The kernel that does the work predates Build Week; the adapter is what we built this week.
Codex (with GPT-5.6) implemented the typed action bridge and MCP server,
adversarially tested false risk labels and path handling, and produced
the deterministic judge demo. The dated branch history and session
submitted through /feedback distinguish the new work from the
pre-existing 0.4.0 kernel.
python scripts/codex-guard-demo.py
pytest -q tests/test_codex_guard.pyFor the judge-ready Codex plugin install:
python -m pip install -e .
custodian-codex setup
custodian-codex doctorStart a new Codex thread, then ask it to evaluate a risky action. Codex may
create a pending request, but only the separate operator command
custodian-codex approve ID --digest DIGEST can grant one exact, expiring,
single-use action.
See the Codex Guard judge guide and the plugin README.
Verify in 60 seconds, no credentials, no cloning:
pip install custodian-codex-guard
custodian-verifycustodian-verify runs deterministic package and regression checks with 0
credentials, 0 cloning, and 0 setup. To verify a deployment too, its owner can
explicitly supply the compatible audit endpoint:
custodian-verify --dashboard-url https://your-service.example/api/audit-summaryCustodian never assumes that an installation belongs to getcustodian.xyz.
Or, for the deeper proof:
git clone https://github.com/KeyArgo/custodian-codex-guard
cd custodian-codex-guard
pip install -e ".[dev]"
python3 verify_kit.pyverify_kit.py runs 5 phases end-to-end with no credentials: re-introduces the self-approval bug to prove the test catches it, runs the 1,747-test suite, runs a planted-lie case, pulls the real Stripe PaymentIntent pi_3TkZWEPfSF4TGXT90AWlrnle, and tests the kill switch end-to-end.
@governdecorator — wrap any function with implicit kernel enforcement. Band, cap, kill switch — all automatic. Zero kernel imports in user code.- CustodianMiddleware — drop-in ASGI middleware for FastAPI/Flask/Starlette. Governed routes return 402 on escalation, 403 on denial.
- GovernedReceipt — SHA-256 fingerprint of every governed action: tamper-evident (change any field and
verify()fails). For full authenticity, receipts can be Ed25519-signed by the kernel's private key (custodian.signing) so they cannot be forged by anyone without that key. - EventBus — pub/sub hooks for kernel lifecycle events. Wire Twilio SMS, Slack alerts, or any consumer.
- CustodianSession — sub-session band inheritance. A child session cannot exceed the parent.
- Authority bands L0-L4 — per-action caps, daily envelopes, margin gates, no-self-dealing, all opt-in.
- Operator-only kill switch — denies every request regardless of amount, band, or policy. Cannot be bypassed by the agent.
A 2.0% slice fraud team at a payments company uses 14 humans to manually approve agent-initiated refunds. They do 1,200/day. Each takes 2 minutes. $36k/yr in human time. Custodian replaces all 14 humans with a deterministic kernel — same throughput, no human in the loop for 95% of cases, full audit trail, single human via Twilio for the 5% edge cases. The agent cannot approve its own refund because the kernel is outside the agent's process. The model can propose. The kernel decides.
Any company running an AI agent with a Stripe account, a Modal spend, a NIM inference budget, a refund flow, or any other action that costs money or breaks something has this exact problem. Custodian is the kernel for it.
- 1,747 passing tests, 0 failed, 4 deselected (network only)
- Real Stripe test-mode PaymentIntent on record:
pi_3TkZWEPfSF4TGXT90AWlrnle - Real Twilio SMS escalation path
- Real OpenRouter API key wired in
- Real Modal + NVIDIA NIM in the demo commands
- 4 kernel bug fixes from adversarial review (kill switch fail-closed, fn_name in receipt, sub_session inheritance, receipt fingerprint coverage)
- Live dashboard: getcustodian.xyz
- Live operator panel: getcustodian.xyz/operator
- Repo (GitHub): https://github.com/KeyArgo/custodian-codex-guard
- PyPI: https://pypi.org/project/custodian-kernel/
- Live dashboard: https://getcustodian.xyz
- Operator panel: https://getcustodian.xyz/operator
- Hackathon entry: OpenAI Build Week 2026 (Codex + GPT-5.6, Developer Tools track)
- 1,747 tests, 0 failures (network tests excluded)
- Deterministic claim verifier (CONTRADICTED / VERIFIED / UNVERIFIABLE)
- Operator-only kill switch with resume logic
- Authority bands L0-L4 with per-request caps
- Real Stripe PaymentIntent on record (
pi_3TkZWEPfSF4TGXT90AWlrnle) - Real Twilio SMS escalation
- Self-approval regression test (proves the kernel fix)
- 106 governed tools in
custodian/bundled_skills/
custodian request— spend decision with policy evaluationcustodian audit— full audit ledgercustodian demo verify— 4 claim-verification scenarios (no creds)custodian demo cycle— closes the economic cycle on camera (no creds)custodian status-banner— one-screen kernel state (totals + last 5)custodian demo attacks— 5 planted-bad-claim tests (no creds)custodian beancount— export ledger to Beancount v2custodian confirm <id>— post-action confirm (60s deadline)
daily_envelope: $50— rolling 24-hour cap per bandmargins: { minimum_margin: $0.10, minimum_margin_pct: 20 }— refuse if margin too lowband_after_task: L0— auto-downgrade after a skill completespolicies: { no_self_dealing: true }— block self-paying agents
python3 verify_kit.py— 5-phase self-verifying proof- Regresses the self-approval bug live
- Pulls fresh dashboard + Stripe data
- Runs the full test suite
- Tests the kill switch end-to-end
custodian demo verify— 4 claim-verifier scenarioscustodian demo attacks— 5 attack patterns the kernel catchescustodian demo cycle— full economic cycle (earn → gate → spend → verify)
Custodian is a kernel-enforced authority and spend platform for AI agents.
An agent cannot exceed its band or approve its own escalation because the boundary is enforced outside the agent's own process and outside its own code path — not by the agent's good behavior.
The agent submits a spend request. The policy engine decides: autonomous (within your configured band, no human needed) or escalation (over the cap, human approval required via Twilio Verify). The agent never holds the keys to both sides of that decision, so self-approval is structurally impossible, not just discouraged.
New here? Read docs/WHAT_THIS_IS.md first — a plain-language
walkthrough of what this actually does, why it needs AI in exactly one place and nowhere
else, and a worked real example end to end.
Wondering what this is actually for beyond one demo? See
docs/BUSINESSES_THIS_UNLOCKS.md — the same enforcement
pattern applied to five concrete, named business shapes, not just the one shown here.
pip install custodian-codex-guardFor development (clone first):
pip install -e ".[dev]"# Scaffold a workspace
custodian init --dir myagent
# Edit the generated policy.yaml to configure authority bands
# (see docs/POLICY_LANGUAGE.md)
# Autonomous request (under the $2.00 default cap)
custodian request --amount 1.00 --description "API credits"
# Escalation request (over the cap — will warn about missing Twilio config)
custodian request --amount 50.00 --description "Server upgrade"
# Check authority state
custodian status
# View audit log
custodian auditYour data is never trapped on one computer, and losing it takes real effort:
# Workspace (policy + spend history + audit trail) → one .zip
custodian backup # → ~/custodian-backups/custodian-backup-<time>.zip
custodian restore <backup.zip> # bring it back, here or on a new machine
# Credential vault (paladin) → one ENCRYPTED file, vault + audit chain
paladin backup # → ~/paladin-backups/paladin-backup-<time>.zip
paladin restore <backup.zip> # needs the same passphrase (or keyfile)Safety properties, on purpose:
paladin backupproves your passphrase opens the vault before writing the backup — you'll never discover an unopenable backup during a disaster.- The paladin backup stays encrypted end to end (AES-256-GCM); the passphrase and keyfile are never inside it.
custodian backupsnapshots the database with SQLite's online-backup API, so it's consistent even mid-write.restore(both tools) verifies the backup before touching anything, refuses to overwrite without--force, and even then saves your current data first (*.pre-restore/pre-restore-<time>.zip). A restore can't lose data.
New to the repo? Read docs/WHAT_THIS_IS.md first
(one paragraph, no jargon), then Getting Started
(10-minute walkthrough). Everything below is reference material you'll want
once you're actually building or auditing something specific — this list is
the single index; nothing here duplicates another entry.
- Getting Started — 10-minute walkthrough
- Architecture — design, flow diagram, privilege separation model
- Public API Reference — every live HTTP route, verified against production
- Policy Language — complete YAML format reference
- Security — threat model, self-approval fix, verification model
- Security Hardening — credential/adapter/bridge scan and findings
- Paladin — the credential broker (the agent never sees the value), with bulk import from .env/Bitwarden/1Password (
paladin import) - Guard Adapters — money/security/privacy/guardrail hooks around every action
- NemoClaw — the inference-routing adapter (drop-in NVIDIA NIM client replacement)
- Talaria — the Hermes Agent + NemoClaw integration suite (governed invoke surface, context-loss re-anchoring); own repo/package, see docs/TALARIA.md for the pointer
- Verification — how to check every claim yourself
- What This Unlocks — use cases beyond the reference demo
The rest of docs/ (design drafts, hackathon video scripts, dated session
handovers) is development history, not onboarding material — grep the
directory if you're chasing the reasoning behind a specific past decision,
but the list above is everything a new reader or integrator actually needs.
Custodian ships a governed tool library. Every tool is a Hermes-compatible
skill (SKILL.md frontmatter) that declares a custodian-band from L0–L4.
The ToolRegistry auto-discovers them — no registration code needed.
custodian tools list # show all 106 tools grouped by band
custodian tools run http-get --url https://example.com
custodian tools summary # JSON band breakdown
Tool categories:
| Category | Count | Band | Example |
|---|---|---|---|
| Utilities | 8 | L0 | base64, hash-sha256, url-parse, json-transform, timezone, currency-convert |
| Web | 5 | L0–L1 | http-get, http-post, web-scrape, web-search, news-search |
| Files | 3 | L0–L1 | file-read, file-list, shell-exec (read-only allowlist) |
| Memory | 5 | L0 | kv-get/set/delete/list, sqlite-query |
| Scheduling | 5 | L1 | task-queue-add/list, cron-create/list/delete |
| Communication | 6 | L1–L2 | email-send, sms-send, slack-message, discord-webhook, webhook-post, push-notification |
| Docker | 4 | L1–L2 | docker-list, docker-logs, docker-start, docker-stop |
| GitHub | 3 | L0–L1 | github-file-read, github-issue-create, github-pr-list |
| NVIDIA NIM | 4 | L2 | nim-model-list, nim-job-submit, nim-job-status, nim-cost-estimate |
| Stripe (extended) | 8 | L2–L3 | stripe-balance, stripe-customer-lookup, stripe-invoice, stripe-refund |
| Financial AI | 5 | L2–L3 | modal-run, huggingface-infer, openai-complete, anthropic-complete |
| Calendar | 5 | L1–L2 | calendar-list, calendar-create, calendar-update |
Tools with missing credentials return {"ok": false, "stub": true} — the
framework works without any env vars configured; stub tools show in the registry
with their band and description so the capability surface is visible during review.
| Band | Policy | Use case |
|---|---|---|
| L0 | Always autonomous, no spend | Read-only data fetching |
| L1 | Autonomous, trivial side effects | Creating records, sending low-stakes messages |
| L2 | Autonomous up to per-action cap | AI inference, Stripe calls under threshold |
| L3 | Always escalates to operator | Refunds, subscription changes, payouts |
| L4 | Always escalates, unlimited scope | Reserved for future high-stakes tools |
- A real Stripe (test-mode) PaymentIntent is on record:
pi_3TkZWEPfSF4TGXT90AWlrnle— confirm it at Stripe's own API or dashboard. - A real Twilio Verify integration sends SMS approval codes to an operator's phone. The code is never written to any file the agent can read.
- A real, operator-only kill switch (
custodian kill --by <name>/custodian resume --by <name>) is wired into the live, authoritativespend.py— not a separate demo path. Verified live: a real autonomous spend succeeded, the kill switch was engaged, the exact same request was denied by the real script running inside the live sandbox, then released, then the real spend succeeded again. The full sequence is in the real audit log. - 1,747 passing tests (4 network-dependent tests deselected by default), tested with Python 3.11+.
- The test suite includes
test_self_approval_regression.py— a regression test for the exact security bug this design prevents. The fix was proven by deliberately reintroducing the bug, confirming the test failed, then restoring the fix. That test exists so the bug can never silently return. - Public commit history at
github.com/inovinlabs/custodian-dev.
Don't take any of this on faith. Everything verifiable from pip:
pip install custodian-codex-guard # install the kernel
custodian demo verify # live claim check against the running system
pip install custodian-codex-guard[dev] && pytest tests/ # 1,747 tests, 0 failures
git clone https://github.com/KeyArgo/custodian-codex-guard # read every lineSee docs/VERIFICATION.md for the full manual breakdown.
- Custodian Codex Guard is an application-layer enforcement boundary for actions routed through its installed hook and MCP integration. It complements the host sandbox and cannot govern a separate, unintegrated tool runner.
- Paladin's strongest credential-isolation mode requires a ready Linux Bubblewrap sandbox and fails closed when that sandbox is unavailable. The legacy non-sandbox environment-injection path remains for compatibility and is not appropriate for untrusted agent code.
- Only one approval backend is shipped:
twilio_verify. Backends named other thantwilio_verifyornoneare rejected at policy validation time. - Only one storage backend is shipped: SQLite (via
SqliteStorage). - No multi-tenant support. No plugin marketplace. No general-purpose expression language in the policy DSL — the match vocabulary is a fixed, small set (skill name, context flags, spend-amount threshold).
- No third-party security audit has been performed.