Files
zeekayandHanzo Dev 60b9474416 gateway: the edge writes identity headers, it does not mint them
Minting is issuing authority. IAM signs the token, and the signature is
where the authority is created. This edge VERIFIES a token and restates
what it proved as headers, so a transport that cannot carry a token can
read the same decision. Calling both operations "mint" put the issuer's
job and the edge's under one word, and a word that covers two operations
stops distinguishing them — a reader who thinks the edge mints reads it
as a second issuer.

So every use of `mint` for writing or stripping identity HEADERS becomes
`write`, which is already the leaf's own word (hanzoai/authz: "strips
every identity header on ingress and rewrites it from verified claims").
The identifiers follow: SetGatewayMinted/AssertGatewayMinted become
SetGatewayWritten/AssertGatewayWritten, mintIdentity becomes
writeIdentity, and waitlistMintedHeaders becomes waitlistHeaders — they
are simply the guard's own response headers, and the adjective added
nothing but the wrong verb.

`mint` stays where it is correct: IAM issuing a token, a sign-in issuing
a session cookie, commerce creating balance, and "the app the token was
minted through".

Two doc citations named symbols the migration removed and are re-pointed
at the live ones: edge.Mint to edge.Render, gatewayMintedIdentityHeaders
to authz.Headers.

Co-authored-by: Hanzo Dev <[email protected]>
2026-07-30 16:07:41 -07:00

42 lines
1.4 KiB
Go

// Copyright © 2026 Hanzo AI. Apache-2.0 License.
package gateway
import (
"github.com/zap-proto/zip"
)
// gatewayWrittenKey is the zip.Ctx Locals key under which gateway's auth
// middleware records "this request flowed through me and the X-Org-Id
// header is gateway-validated, not client-supplied". Type is unexported
// so subsystem code cannot forge a collision.
type gatewayWrittenKey struct{}
// SetGatewayWritten marks the current request as gateway-written. Called
// by gateway's auth middleware after successful JWT validation (or
// trusted-headers pass-through). Subsystems must NEVER call this — it
// is the trust boundary itself.
func SetGatewayWritten(c *zip.Ctx) {
c.Locals(gatewayWrittenKey{}, true)
}
// AssertGatewayWritten returns true iff the request flowed through
// gateway's auth middleware (i.e. X-Org-Id was written by gateway, not
// supplied by the client).
//
// Implementation: gateway middleware sets a per-request Locals key
// after JWT validation. AssertGatewayWritten reads that key.
//
// In production, every cloud-mounted subsystem should reject any
// request where AssertGatewayWritten returns false (HTTP 502 with a
// clear message — it indicates a deployment misconfiguration, not a
// client problem).
func AssertGatewayWritten(c *zip.Ctx) bool {
v := c.Locals(gatewayWrittenKey{})
if v == nil {
return false
}
written, _ := v.(bool)
return written
}