docs(prd-0017): nest auth.scheme + auth.token_ref under optional auth
test / unit (pull_request) Successful in 18s
test / integration (pull_request) Successful in 1m38s

Earlier draft had `auth_scheme: "none"` as the unauthenticated
signal — awkward sentinel. Nest the two credential-injection
fields under an optional `auth` key instead. Presence of the key
= authenticated; absence = unauthenticated. Empty `auth: {}` is
an error (omission is what means "no auth").

Touches: scope bullet, manifest example, mitmproxy addon
description's auth-handling step. Two trailing `auth_scheme:
"none"` references kept as historical context for what the new
shape replaces.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
2026-05-25 13:35:47 -04:00
parent b0d9802469
commit a79b2b7be0
+33 -18
View File
@@ -21,7 +21,8 @@ are split between cred-proxy and pipelock:
the cred-proxy URL.
3. **Credential injection.** Continues cred-proxy's existing role:
match by hostname (or hostname + path), strip inbound
Authorization, inject one based on `auth_scheme` + `token_ref`.
Authorization, inject one based on the route's optional `auth:
{ scheme, token_ref }` block.
Pipelock's role narrows to hostname allowlist + DLP body scanning
on the egress-proxy → upstream leg. Pipelock no longer holds the
@@ -90,8 +91,10 @@ delivery.
(was pipelock's CA).
- Manifest rename: `bottle.cred_proxy.routes[]`
`bottle.egress_proxy.routes[]`. The route shape gains optional
`path_allowlist: [<prefix>, ...]` and supports `auth_scheme:
"none"`.
`path_allowlist: [<prefix>, ...]` and a nested optional `auth:
{ scheme, token_ref }` block (presence/absence of `auth` is the
authenticated vs unauthenticated signal — replaces the old
`auth_scheme: "none"` pattern).
- Agent's `HTTP_PROXY` / `HTTPS_PROXY` env vars repointed at the
egress-proxy (was pipelock).
- Pipelock retains its sidecar slot and its own DLP + hostname
@@ -151,30 +154,41 @@ default proxy path.
```yaml
egress_proxy:
routes:
# Authenticated route (today's cred-proxy shape, slightly
# renamed). path_allowlist optional.
# Authenticated route — `auth` block carries the injection
# config. path_allowlist optional.
- host: "api.github.com"
auth_scheme: "Bearer"
token_ref: "GH_PAT"
auth:
scheme: "Bearer"
token_ref: "GH_PAT"
path_allowlist:
- "/repos/didericis/"
- "/users/didericis"
# Unauthenticated path-filtered route.
# Unauthenticated path-filtered route — `auth` omitted
# entirely (presence/absence of the key is the auth signal).
- host: "github.com"
auth_scheme: "none"
path_allowlist:
- "/didericis/"
# Bare-pass route: no auth injection, no path enforcement.
# Useful when you want a host to skip path filtering but
# still be DLP-scanned by pipelock.
# Bare-pass route: no auth, no path constraint. Useful when
# you want a host to skip path filtering but still be
# DLP-scanned by pipelock on the outbound leg.
- host: "api.anthropic.com"
auth_scheme: "none"
# no path_allowlist → all paths pass
```
Route matching is on `host` (was `path` prefix). The hostname
gates whether a route applies; `path_allowlist` (if present)
constrains the URL path under that host.
constrains the URL path under that host. The optional `auth`
block carries credential-injection config:
- Omit `auth` → no Authorization header injected (replaces the
earlier draft's `auth_scheme: "none"`).
- `auth.scheme` → one of `Bearer`, `token` (the values
cred-proxy supports today; sidesteps the gitea-token quirk).
- `auth.token_ref` → host env var holding the secret. Same
semantics as cred-proxy's `TokenRef` field today.
Validation: `auth` (if present) must contain both `scheme` and
`token_ref`. An empty `auth: {}` is an error rather than a
synonym for "no auth" — that's what omission is for.
### mitmproxy addon shape
@@ -187,9 +201,10 @@ The egress-proxy ships a small Python addon that:
matches → forward unchanged (pipelock will hostname-gate it). If
route matches and has `path_allowlist`, check `flow.request.path`
against the prefix list; 403 with a clear reason if no match.
- On approved requests: strip inbound Authorization, inject
`Authorization: <auth_scheme> <token-from-env>` if `auth_scheme
!= "none"`.
- On approved requests: strip inbound Authorization. If the route
carries an `auth` block, inject `Authorization: <auth.scheme>
<token-from-env-named-by-auth.token_ref>`. If the route omits
`auth`, leave Authorization unset.
- SIGHUP / file-mtime watch on `routes.yaml` for hot-reload (same
cadence as today's cred-proxy SIGHUP path).