feat: enforce token scopes in the api (rbac)#428
Merged
Conversation
src/api/auth.zig resolves a bearer token to its scopes (legacy admin token = full admin, or a named token by sha256 lookup) and maps a request to its required scope from path-prefix + method. add a 403 forbidden status + helper, and an audit setActorName so a named token shows up as the audit actor.
operator routes now require a valid token (legacy admin or named) and the scope for the request; insufficient scope returns 403. cluster join routes still use the join token. the audit actor is set to the token's name. with no token configured the server stays open (unchanged).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
enforces the scoped tokens from #427: every operator API route now requires a
token whose scopes permit the request. finishes the rbac + token lifecycle item.
summary
src/api/auth.zig:requiredScope(method, path)maps a request to its scope (GET/HEAD →:read,writes →
:write;/cluster/*writes →cluster:admin;/apps/dry-run→apps:read; public routes → none; unknown routes fail closed →*).authorize(...)resolves the bearer: the existing singleapi_tokenistreated as full admin (backward compatible), otherwise a named token is
looked up by
sha256(secret)and its scopes/expiry/revocation apply.required scope. cluster join routes keep using the join token. with no token
configured the server stays open (unchanged dev behavior).
api-token(legacy),so
/v1/auditattributes actions to a real identity.tested
YOQ_SKIP_SLOW_TESTS=1 zig build test— 2183 passed, 2 skipped, 0 failed(existing dispatch auth tests still pass: legacy admin token = full access).
requiredScopefor representative paths,authorizewith thelegacy admin token and with a missing/wrong token, scope matching, and the
audit name override.
yoq serve: astatus:readtoken gets 200 on/v1/statusand 403 on secrets (read and write); the admin token gets 200; no token gets
401; denied requests write no audit entry;
/v1/auditshows the actor.zig fmt --checkclean.