The threat model is blunt
Our security design starts from an uncomfortable premise: the LLM agent is the most untrusted component in the request path. Anything it can name in plaintext, it can echo into a chat completion, a tool-call argument, a git commit body, or a Markdown image URL. So we design for the leak rather than hoping it doesn’t happen.
How a secret is used without exposing it
Instead of fetching a plaintext value and pasting it into a curl command, an agent uses secure-curl with placeholders:
| |
The {{stripe_api_key}} placeholder is resolved at the Forge egress proxy — a boundary the agent doesn’t control — not in the agent’s process. The real credential is substituted onto the outbound request and forwarded. The agent never sees the value, so the value can never end up in its context, its transcript, or a synced session snapshot
.
For discovery, agents call secret_list, which returns aliases and metadata only — never values.
Scoped to the minimum
Secrets are encrypted at rest per organization and restricted along four axes simultaneously — per agent, per workflow, per runtime, and per team. A character only ever sees the aliases its charter allows, enforced in the runtime tool dispatcher, not by convention.
Audit without exposure
Every interaction with a secret produces an append-only audit row: who, when, which alias, what destination — plus a salted SHA of the value, never the value itself. The chain is tamper-evident, and because the hash is salted with a per-org pepper held separately, a compromise of the audit log alone can’t reverse-lookup a credential.
This is the same posture that lets Simple Container keep encrypted-in-git secrets safe from agents reading your repo — the foundation an agent-driven pipeline needs before it can be trusted to ship.