Gateway-lifecycle SANDBOX CAPABILITY: ONE shared loopback egress proxy and ONE ephemeral MITM CA for the WHOLE daemon, keyed PER SESSION.
Why shared, not per-session (turn 32): the gateway is multi-tenant — many clients/sessions hit one daemon. A per-session proxy+CA thrashes listeners and mints a fresh CA per session; worse, every child would carry a different trust root. Instead there is ONE listener and ONE CA (the "same certs" property — every child trusts the same root), plus a REGISTRY mapping a per-session TOKEN → that session's live policy fn.
How a connection is attributed to a session: the jailed child's proxy env carries
its unguessable token in the proxy URL userinfo (http://<token>@127.0.0.1:<port>);
curl/git/requests/… send it back as Proxy-Authorization: Basic base64(<token>:);
the proxy hands the token to resolve-policy, which looks up the registry.
FAIL-CLOSED: a request whose token is missing or not registered to a LIVE session
is DENIED (a :deny-all? sentinel policy) — the shared door never serves a policy
it cannot attribute. The token is a random UUID, so one session cannot reach
another's (broader) policy by guessing.
Lazy: the proxy listener and the CA keygen happen only on first ensure-proxy! /
ensure-ca! — a gateway that never jails a shell child opens neither.
Gateway-lifecycle SANDBOX CAPABILITY: ONE shared loopback egress proxy and ONE ephemeral MITM CA for the WHOLE daemon, keyed PER SESSION. Why shared, not per-session (turn 32): the gateway is multi-tenant — many clients/sessions hit one daemon. A per-session proxy+CA thrashes listeners and mints a fresh CA per session; worse, every child would carry a different trust root. Instead there is ONE listener and ONE CA (the "same certs" property — every child trusts the same root), plus a REGISTRY mapping a per-session TOKEN → that session's live policy fn. How a connection is attributed to a session: the jailed child's proxy env carries its unguessable token in the proxy URL userinfo (`http://<token>@127.0.0.1:<port>`); curl/git/requests/… send it back as `Proxy-Authorization: Basic base64(<token>:)`; the proxy hands the token to `resolve-policy`, which looks up the registry. FAIL-CLOSED: a request whose token is missing or not registered to a LIVE session is DENIED (a `:deny-all?` sentinel policy) — the shared door never serves a policy it cannot attribute. The token is a random UUID, so one session cannot reach another's (broader) policy by guessing. Lazy: the proxy listener and the CA keygen happen only on first `ensure-proxy!` / `ensure-ca!` — a gateway that never jails a shell child opens neither.
(ensure-ca!)Lazily create the ONE shared ephemeral MITM CA. Returns its PEM path.
Lazily create the ONE shared ephemeral MITM CA. Returns its PEM path.
(ensure-java-trust!)Return the shared CA's ephemeral PKCS12 truststore credentials for managed JVM children. The store is deleted with the gateway capability.
Return the shared CA's ephemeral PKCS12 truststore credentials for managed JVM children. The store is deleted with the gateway capability.
(ensure-proxy!)Lazily start the ONE shared loopback egress proxy bound to the token-keyed resolver + the shared CA. Returns its port. Idempotent + thread-safe.
Lazily start the ONE shared loopback egress proxy bound to the token-keyed resolver + the shared CA. Returns its port. Idempotent + thread-safe.
(ensure-session-proxy! token)Lazily start a session-attributed compatibility front door for managed language
processes whose HTTP stacks do not reliably send Proxy-Authorization from URL
userinfo (notably urllib and JVM dependency resolvers). The listener is bound to
loopback, resolves exactly token's live policy, and shares the gateway CA and
proxy implementation. Unknown/disposed sessions fail closed. Returns its port.
Lazily start a session-attributed compatibility front door for managed language processes whose HTTP stacks do not reliably send Proxy-Authorization from URL userinfo (notably urllib and JVM dependency resolvers). The listener is bound to loopback, resolves exactly `token`'s live policy, and shares the gateway CA and proxy implementation. Unknown/disposed sessions fail closed. Returns its port.
(proxy-port)The running shared proxy's port, or nil if it was never started.
The running shared proxy's port, or nil if it was never started.
(register-session! token policy-fn)Register policy-fn (0-arg → the session's compiled policy value or nil) under
token. The shared proxy resolves this session's policy from here per request.
Register `policy-fn` (0-arg → the session's compiled policy value or nil) under `token`. The shared proxy resolves this session's policy from here per request.
(registered? token)True when token maps to a live session policy fn.
True when `token` maps to a live session policy fn.
(resolve-policy token)Token-keyed resolver handed to the shared proxy's :policy-fn. Returns the
session's compiled policy, or a :deny-all? sentinel when the token is absent or
unregistered (FAIL-CLOSED — an unattributable request reaches nothing).
Token-keyed resolver handed to the shared proxy's `:policy-fn`. Returns the session's compiled policy, or a `:deny-all?` sentinel when the token is absent or unregistered (FAIL-CLOSED — an unattributable request reaches nothing).
(set-reserved-ports! ports)Register loopback ports a jailed child must never reach (the gateway's own control plane) even though loopback is allowed by default. The shared proxy's own port is reserved automatically. Idempotent.
Register loopback ports a jailed child must never reach (the gateway's own control plane) even though loopback is allowed by default. The shared proxy's own port is reserved automatically. Idempotent.
(shutdown!)Stop every gateway proxy listener, delete the shared ephemeral trust files, and clear all session policy state. Idempotent.
Stop every gateway proxy listener, delete the shared ephemeral trust files, and clear all session policy state. Idempotent.
(unregister-session! token)Drop a session's policy and stop its optional language-process front door. Idempotent; the shared proxy + CA remain gateway-owned.
Drop a session's policy and stop its optional language-process front door. Idempotent; the shared proxy + CA remain gateway-owned.
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |