Feat/oauth resource server - #1
Open
martomorri wants to merge 5 commits into
Open
martomorri wants to merge 5 commits into
martomorri wants to merge 5 commits into
Conversation
Exact pins, in package.json, package.runtime.json and the Dockerfile builder stage. The builder does not install package.json — it installs a hand-curated list — so a new runtime dependency has to be declared in all three places or the image fails to compile while the local build passes. tests/unit/sdk-pin-consistency.test.ts is extended to fail when those three declarations disagree, or when the two packages drift onto different versions. tsconfig.json gains a paths entry for @authplane/sdk/core: the package exposes that subpath through exports only, which moduleResolution: node cannot resolve. Conceived by Romuald Członkowski - www.aiadvisors.pl/en
Adds the two @AuthPlane packages. The rest of the diff is not intentional: v2.73.0 committed package.json without regenerating the lock, so `npm ci` fails with "not in sync" on a clean clone and any `npm install` rewrites it, also bumping @aws-sdk/* patch versions within their existing ranges. Kept as its own commit so it can be dropped or regenerated independently. Conceived by Romuald Członkowski - www.aiadvisors.pl/en
HTTP mode can accept access tokens issued by an external authorization server instead of the shared AUTH_TOKEN. Tokens are verified locally — signature against the issuer's JWKS, issuer, audience pinned to the configured resource URI, expiry, algorithm allowlist — and the server publishes RFC 9728 Protected Resource Metadata, extending the existing WWW-Authenticate challenge (czlonkowski#767) with resource_metadata. A client that has never been configured with a token discovers the authorization server from a bare 401 and runs the consent flow itself. AUTH_MODE=token stays the default and is unchanged; any other value refuses to start rather than guessing. All AuthPlane-specific code is in src/auth/authplane.ts behind the TokenVerifier interface, loaded only in oauth mode, so token mode never imports the SDK. Per-tool scopes (n8n:docs, n8n:workflows:read, n8n:workflows:write, n8n:executions, n8n:credentials, with a read/write split on the multiplexed tools) are checked in the tool handler after DISABLED_TOOLS. A denial is a tool error carrying required_scope and granted_scopes, not an HTTP status: refusing at the HTTP layer leaves the client's request hanging. Also optional DPoP sender-constrained tokens with the proof URL anchored to the configured resource origin rather than the Host header, introspection-based revocation that fails closed, binding of each MCP session to the subject that opened it — enforced on every route that reaches an existing session, including the server-to-client stream and session termination — and an audit trail keyed by subject and token id that never records the token itself. The 401 body, the rate limiter, the multi-tenant headers and the SSRF gate are unchanged. The access token is never used as the n8n API key. Conceived by Romuald Członkowski - www.aiadvisors.pl/en
Hermetic suites (npm run test:auth, 125 tests) run against a fake TokenVerifier and prove the server's own logic: that token mode is untouched, config validation and the named errors it raises, the tool-to-scope map, session binding and its eviction behaviour, audit redaction, challenge construction, the gate on all five MCP routes, and that a scope denial is a tool error rather than an HTTP 403. A live suite drives the adapter against a real authorization server, minting genuine tokens and signing genuine DPoP proofs, so it catches a claim read by the wrong name or an SDK default assumed wrongly. An end-to-end suite spawns the built server with a pinned environment and drives it with the official MCP client over Streamable HTTP. Both skip themselves unless AUTHPLANE_TEST_ISSUER, AUTHPLANE_TEST_ADMIN_URL and AUTHPLANE_TEST_ADMIN_KEY are set, so CI and a fresh clone stay green without a server. Conceived by Romuald Członkowski - www.aiadvisors.pl/en
docs/OAUTH_AUTHENTICATION.md covers configuration, the request path, scopes,
DPoP, revocation, session binding, the audit trail, client setup, the known
limits and how to plug in a different authorization server.
THREAT_MODEL.md is updated because §8 lists a new deployment mode as a review
trigger: the new trust boundary, the mitigations for session hijack and token
replay, and what the audit trail attributes. Rows added to HTTP_DEPLOYMENT.md
and SECURITY_HARDENING.md; a pointer in the README; a CHANGELOG entry.
scripts/test-oauth-endpoint.{sh,js} check a deployed instance from outside:
the unauthenticated 401 and its challenge, the metadata document at both paths,
and a valid token opening a session.
Conceived by Romuald Członkowski - www.aiadvisors.pl/en
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.
No description provided.