Namespaces
A namespace groups deployments, and a token minted for a namespace reaches only the deployments in it — a key to one room, not a list of ids that goes stale.
On a deployment
One field. Absent means "default", so a fleet that never says the word
keeps behaving as one namespace and nothing changes on the wire or on disk:
{ "id": "web", "namespace": "team-a", "routes": [ … ], … }
Namespace names share the deployment-id alphabet (letters, digits, -
_ .) because they appear in URLs and filenames unescaped.
On a token
serverctl token mint team-a-operator --admin admin --namespace team-a
A namespace-confined token behaves differently from a plain deployment-scoped one, and the differences are the point:
- An empty
deploymentslist means the whole namespace — every deployment there, now and in the future. (Outside a namespace, an empty list means nothing; inside one, listing ids narrows within the namespace.) - The wall is absolute. Whatever the
deploymentslist says — even["*"]— the token never touches a deployment in another namespace, on the data plane or the admin API. - It never covers the fleet. Fleet-wide admin routes — minting tokens, the secret store, the all-jobs listing — are exactly the routes that see past a namespace wall, so a namespace token is refused them. A token cannot widen itself.
What a namespace admin token can do
A token minted with --admin admin --namespace team-a is a self-service
operator for that namespace:
GET /deployments— the listing, narrowed to the namespace.POST /deployments— register deployments, provided the spec says"namespace": "team-a". It cannot capture a deployment id that exists in another namespace, and an update cannot move a deployment out of the namespace.- Everything per-deployment — describe, scale, evict,
exec,shell, build/pull — for deployments in the namespace. - The directory,
/metricsand/security, narrowed to the namespace's deployments;GET /feeds/team-a, and no other namespace's feed.
Filtering
# everyone can filter listings by namespace
GET /deployments?namespace=team-a
serverctl get deployments # serverctl passes your token's view through
Data-plane gates compose with namespaces: a deployment's
auth gate with the app-token provider admits a namespace token
only if the deployment is inside that token's namespace. The same 401 covers "wrong
secret", "expired", and "wrong namespace" — probing the gate teaches nothing about which
it was.