Repository navigation
Conversation
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.
Draft RFC:
docs/rfcs/2026-11-01-oauth-scope-ceilings.md, plus its registry row.What it proposes
An admitted OIDC access token may carry an attenuation-only ceiling, read from its standard
scopeclaim. A request succeeds only when applied policy permits the actor and the ceiling covers the action. The actor stays the person's principal, applied policy stays the only grant, a token without a ceiling behaves exactly as today, and native signed credentials are untouched.The vocabulary is fixed in the server, six names over the thirteen existing policy actions:
graph.readread,invoke_query,exportgraph.writechange,branch_create,branch_delete,branch_merge,commit_publish,commit_dropgraph.schemaschema_applygraph.adminadmincluster.listgraph_listcluster.configconfig_manageA trust document opts in by declaring
scope_prefix(frozen with the binding at boot). Without it,scopestays ignored as it is now. With it: prefixed entries must name a vocabulary scope (unknown → 401invalid_token), unprefixed entries are ignored, and an absentscopeis an empty ceiling.The check sits in the one shared
handlers::authorize, after the policy decision, soinsufficient_scope(new 403 code, with the RFC 6750WWW-Authenticate … error="insufficient_scope", scope="…"challenge) is only ever returned for an action the person could perform with a wider scope;forbiddenis unchanged and still carries no challenge. Protected-resource metadata gainsscopes_supported;/accessgainsscopesand reports the intersection.Scope
Scopes only. No provider roles, no
act/delegation, no Agent Auth, no signed-credential v3, no client recorded on commits (#1173). Delegated branch-scoped credentials remain #978. Provider-role membership is the separate #1223. Closed #1218 bundled an earlier version of this with those.Verified against
origin/main3e0e467:oidc_identity.rs(scope/scp/azpnever read;client_idkept beside the actor since #1196),data_tokens.rs(v2 strictly refuses grants/roles),handlers::authorizeas the single HTTP/MCP choke point,mcp.rs/challenge.rs(metadata and 401 challenge; noscopes_supported, noinsufficient_scope),AccessOutput,ErrorOutput, RFC 0003 and the identity RFC's ceiling paragraph. WorkOS "Access token claims": Connect user tokens carryscopeandclient_id; DCR/CIMD clients cannot have per-client scopes; Connect tokens have no permissions claim. The entry bounds (256 × 128 bytes, RFC 6749 alphabet) match the control plane's existing M2Mvalidate_scopes.