Skip to main content

CLI Firewall

Every command evaluated before it runs.

Coding agents, shell-using workflows, and CI-invoked NHIs have one risk vector in common: they run commands. rm -rf, sudo, curl <suspicious-url>, aws ec2 terminate — one line of shell is often the difference between routine automation and catastrophic outcome. The CLI Firewall sits between the agent and the shell. Commands are evaluated; only those that pass receive a short-lived execution token. Output is streamed through a redactor. Every command, every argument, every byte of stdout and stderr, every exit code, every policy verdict — anchored to the ledger.


Evaluate, Then Execute

Agentic Command Lifecycle — Evaluate Before Execute

AGENTproposes commandvia /v1/cli/evaluateEVALUATEFirewall rulesPolicy evaluationGuardian verdictPass · Correct · Block · Approveif pass →EXECUTE/v1/cli/executewith execution tokenAUDITGlass Box entrystdout · stderr · exitBLOCKcommand refused · 403APPROVEcorrect command - 200CORRECTrewrite args · 200alternatively ↓

An agent proposes a command via POST /v1/cli/evaluate. The firewall evaluates it against three layers:

  1. Firewall rules — the allow / deny / rate-limit / redact rules you've configured for this NHI, tier, or organization.
  2. Policy evaluation — the same policy graph that governs chat output now applied to the command's semantic intent.
  3. Guardian verdict — a Guardian trained on shell usage patterns evaluates the argument set for injection, escalation, or suspicious sequencing.

The agent receives one of four verdicts:

  • Pass — with an execution token valid for one use within a short TTL.
  • Correct — the firewall rewrites the arguments (for example, scoping a glob that was too wide) and returns a corrected version for the agent to retry.
  • Approve — the command is held pending human approval. A notification goes out; execution happens when approved.
  • Block403 Forbidden with a reason code and the rule / policy that triggered.

The agent then calls POST /v1/cli/execute with the issued token. Trinitite executes the command in your environment, streams stdout / stderr through a configurable redactor, and writes everything to the ledger — including the exit code.


The Four Rule Types

Firewall Rule Types — Four Actions

Allow
kubectl get · docker ps · ls /workspace/*
Explicit allowlist. Anything not matched falls through to subsequent rules or denied by default.
Deny
rm -rf / · sudo * · curl <external>
Hard deny with reason code. Highest precedence — always wins over allow rules at the same level.
Rate limit
aws ec2 terminate — max 1/hour per NHI
Command rate limits scoped per NHI, per tier, or per session. Token-bucket enforced at the gateway.
Redact
env · printenv · echo $SECRET
Command executes; output is scrubbed of configured patterns before returning to the agent.

Rules compose. A command might match an allow rule for its primary verb, a rate-limit rule for its frequency, and a redact rule for its output — all three apply. Rule precedence is explicit (deny > rate-limit > allow, with redact applying in addition to whatever verdict the command received).


NHI-Scoped and Tier-Aware

Every firewall rule is scoped. A T0 agent might be allowed only kubectl get and ls in a narrow directory. A T2 operational agent gets a wider allowlist including selected write operations but still can't run rm -rf /. A T3 break-glass admin gets a much larger surface with human approval required on destructive commands.

The tier claim on the NHI's JIT token drives the firewall scope automatically. You don't write per-tier rules manually — you write rules once, tagged with tiers, and the firewall resolves the applicable set per request.


Output Redaction

$ env | grep DATABASE_URL
DATABASE_URL=[REDACTED by trinitite · rule: env-secrets]

The redactor runs on stdout and stderr before they stream back to the agent. Configurable patterns catch obvious classes:

  • API keys (provider-specific regex for OpenAI, Anthropic, AWS, Stripe, etc.)
  • Connection strings with embedded credentials
  • Known internal hostnames
  • PII patterns (SSN, credit card, account number)

Custom patterns compose with the built-ins — typically your organization's identifier conventions (acct-*, emp-*, internal ticket IDs you don't want in agent context).


The Audit Record

Every command produces an audit row with:

{
"audit_id": "aud_…",
"nhi_id": "nhi_…",
"command": "aws ec2 describe-instances",
"args_hash": "sha256:…",
"verdict": "pass",
"rule_matched": "allow:aws:read-only",
"execution_token": "exec_…",
"exit_code": 0,
"stdout_hash": "sha256:…",
"stderr_hash": "sha256:…",
"stdout_redacted": true,
"duration_ms": 342,
"ledger_block": "blk_…",
"policy_hash": "sha256:…",
"guardian_digest": "sha256:…"
}

The hashes are content-addressed — a regulator can request the stdout content, verify against the hash, and know it matches the execution record byte-for-byte.


What You Get

CapabilityDirect shell accessCLI Firewall
Command evalNoneEvery command checked first
Destructive defenseTrust the agentDeny rules enforced pre-execution
Scope controlAmbient env permissionsTier-aware allow/deny per NHI
Output safetyRaw streamRedactor on every byte
Audit evidenceShell history (mutable)Ledger-anchored execution records
Forensic replayNot possibleContent-addressed stdout / stderr
Approval workflowsOut-of-bandFirst-class approve verdict

Next Steps

Skill Vault — the signed registry for the SKILL.md files agents load into context.

NHI Governance — the tier model that drives firewall scope.

Glass Box Ledger — where every command execution is anchored.