A MITM proxy that provides path-based access control over HTTP and HTTPS traffic and transparent secret injection for agentic workloads. For HTTPS, Warden intercepts TLS connections, decrypts requests for policy evaluation, and re-encrypts them before forwarding upstream. HTTP requests are inspected directly. Agents never see or handle secrets directly.
AI agents running in sandboxed environments need to access authenticated web services (APIs, registries, internal tools). Giving agents direct access to secrets is a security risk — they can leak, be exfiltrated, or persist beyond the session. Unrestricted network access is equally dangerous.
A traditional HTTPS proxy can only see the destination host via CONNECT — it cannot inspect request paths, methods, or headers. This limits policy granularity to host-level allow/deny.
Warden solves this by performing TLS interception:
- Deep request inspection — Warden terminates the agent's TLS connection, decrypts the request, and evaluates it against path-level policies before re-encrypting and forwarding upstream.
- Policy-driven secret injection — Policies can inject headers, query parameters, or other credentials into matching requests. The agent never sees the secret.
- Default-deny access control — All requests are denied unless an explicit allow rule matches. Administrators allowlist specific host + path + method combinations. No catch-all, no fallthrough.
Warden runs alongside agents. In single-tenant mode, one instance serves one agent. In multi-tenant mode, a single instance serves multiple agents, each identified by mTLS client certificate with isolated policies and secrets. Agents connect over TCP or vsock. NetworkPolicy or Security Groups ensure agents can only reach the internet through Warden. See Deployment for full setup guides.
Kubernetes / OpenShift (separate pods, NetworkPolicy enforced):
┌─────────────────────┐ ┌─────────────────────┐
│ Agent Pod │ │ Warden Pod │
│ │ │ │
│ HTTP_PROXY=warden │────▶│ :8080 proxy │────▶ upstream
│ SSL_CERT_FILE=... │ │ :9090 health │
│ │ │ │
│ NetworkPolicy: │ │ NetworkPolicy: │
│ egress → warden │ │ egress → anywhere │
│ only │ │ ingress ← agent │
└─────────────────────┘ └─────────────────────┘
MicroVM (Firecracker, Cloud Hypervisor, QEMU):
┌─────────────────────┐ vsock ┌────────────────────────┐ ┌──────────────┐
│ Guest VM │────────▶│ Warden │ TLS │ │
│ │ │ │───────▶│ Upstream │
│ ┌─────────────┐ │ │ Policy ─▶ Inject │ │ Service │
│ │ Agent │ │◀────────│ ─▶ Forward │◀───────│ │
│ │ (sandbox) │ │ └────────────────────────┘ └──────────────┘
│ └─────────────┘ │ Host / Sidecar
│ │ │
│ Trusts Warden CA │
│ HTTP_PROXY=bridge │
└─────────────────────┘
- Agent sends
CONNECTto Warden; Warden presents a dynamically generated certificate for the target host, signed by its CA - Warden decrypts the request and evaluates it against policy rules (host, path, method)
- If no rule matches →
403 Forbidden(default deny). If deny rule matches →403 Forbidden. - If allowed → Warden injects secrets (if configured), opens a real TLS connection upstream, and relays the response
| Protocol | Support | Notes |
|---|---|---|
| HTTP/1.1 | yes | Direct inspection, policy + injection |
| HTTPS | yes | MITM — TLS termination, inspection, re-encryption |
| HTTP/2 | yes | Transparent via Go stdlib. Works with gRPC (/package.Service/Method) |
| WebSocket | upgrade only | Policy evaluated on upgrade request. Frames pass through post-upgrade |
Multi-Tenant (mTLS, multiple agents per Warden):
Agent EC2 A ──mTLS──▶ ┌─────────────────────┐
(CN=alpha) │ Warden │
Agent EC2 B ──mTLS──▶ │ tenant resolution │──▶ upstream
(CN=beta) │ per-tenant policies │
Agent EC2 C ──mTLS──▶ │ per-tenant secrets │
(CN=gamma) └─────────────────────┘
# Build
make build
# Run with example config
make run CONFIG=config.example.yaml
# Configure agent to use Warden
export HTTP_PROXY=http://localhost:8080
export HTTPS_PROXY=http://localhost:8080
export SSL_CERT_FILE=/tmp/warden-ca.crt| Document | Description |
|---|---|
| Configuration | Full config reference, defaults, validation rules |
| Policies | Policy rules, glob patterns, evaluation order, injection |
| Secrets | All secret backends: env, file, vault, kubernetes, github-app |
| Telemetry | Logs, traces, metrics, OTLP setup |
| DNS | DNS resolution, DNS-over-TLS, caching, IP denylist |
| Deployment | Container sidecar, microVM, agent trust setup, health checks |
| Development | Building, testing, fuzzing, project structure, extending |
server:
listen: "0.0.0.0:8080"
health_listen: "0.0.0.0:9090"
ca:
auto: true
cert_output: /shared/warden-ca.crt
dns:
servers: ["8.8.8.8:53"]
cache:
enabled: true
deny_resolved_ips:
- "10.0.0.0/8"
- "169.254.0.0/16"
- "127.0.0.0/8"
secrets:
- type: env
- type: file
path: /run/secrets
policies:
- name: block-metadata
host: "169.254.169.254"
action: deny
- name: github-api
host: "api.github.com"
path: "/repos/myorg/**"
methods: ["GET", "POST"]
action: allow
inject:
headers:
Authorization: "Bearer ${GITHUB_TOKEN}"
- name: pypi-read-only
host: "pypi.org"
methods: ["GET"]
action: allowSee Configuration for the full reference.
Apache License 2.0 — see LICENSE for details.