Skip to content

fix(resource): keep MapAAuthResource discovery documents public - #56

Open
KellenCarl wants to merge 1 commit into
aauth-dev:mainfrom
KellenCarl:fix/48-map-aauth-resource-discovery
Open

KellenCarl wants to merge 1 commit into
aauth-dev:mainfrom
KellenCarl:fix/48-map-aauth-resource-discovery

Conversation

@KellenCarl

Copy link
Copy Markdown

Summary

Fixes #48. MapAAuthResource() mapped /.well-known/aauth-resource.json and /.well-known/jwks.json, then added global verification and challenge middleware. Mapped endpoints run at the end of the pipeline, so unsigned discovery GETs, which MetadataClient and any verifier send, got 401 and agents couldn't discover the resource.

Changes

  • Exempt only the SDK's discovery handlers. Verification and challenge are skipped only for GET requests whose selected endpoint carries a new internal PublicDiscoveryEndpoint marker. The marker is on the resource metadata and JWKS handlers.
  • Match the handler, not the path. A URL rewrite added after MapAAuthResource() can't carry the exemption to a protected endpoint (covered by a regression test). If routing hasn't selected an endpoint yet, the request is verified (fail closed).
  • Everything else stays protected: app routes under /.well-known, look-alike paths, non-GET methods, and jwks.json when the resource has no signing keys.
  • No public API changes.

Spec basis

Verifiers discover keys from {iss}/.well-known/{dwk} before they can check any signature (draft-11 #jwks-discovery, L2278). Metadata integrity rests on HTTPS plus the issuer match (#metadata-documents, L1981), not on request signatures. The Person Server and Access Server pipelines already exempt /.well-known.

Follow-ups (not in this PR)

  • The Person Server and Access Server exempt the whole /.well-known prefix; they could use the same handler marker.
  • If an app maps agent metadata (MapAAuthAgentWellKnown) alongside MapAAuthResource(), unsigned GETs to /.well-known/aauth-agent.json still get 401. Draft-11 has verifiers fetch that document (L473, L539, L1864), so it could take the same PublicDiscoveryEndpoint marker. I've left it out to keep this PR scoped to MapAAuthResource places signature verification in front of its own discovery endpoints #48. Happy to follow up if you'd like.

Validation

  • Dev container (mcr.microsoft.com/dotnet/sdk:10.0, .NET 10.0.403), Release build: 0 warnings, 0 errors.
  • dotnet test AAuth.slnx -c Release: 3,720 passed, 0 failed, plus the Events gate (89 passed).
  • New MapAAuthResourceDiscoveryTests (10 cases). The discovery tests fail on main and pass with this change.

MapAAuthResource() mapped /.well-known/aauth-resource.json and
/.well-known/jwks.json, then added global verification and challenge
middleware. Mapped endpoints run at the end of the pipeline, so unsigned
discovery GETs (as sent by MetadataClient and any verifier) got 401 and
agents could not discover the resource.

Verification and challenge now skip only GET requests whose selected
endpoint is one of the SDK's discovery handlers, tagged with an internal
PublicDiscoveryEndpoint marker. Matching the selected handler rather than
the path keeps the exemption tied to the code that actually runs, so a
later URL rewrite cannot carry it to a protected endpoint. If no endpoint
has been selected yet, the request is verified (fail closed).

Tests cover unsigned discovery, protected routes (including app routes
under /.well-known, look-alike paths and non-GET methods), the no-key
case, a validly signed agent request, and the URL-rewrite case.

Fixes aauth-dev#48
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

MapAAuthResource places signature verification in front of its own discovery endpoints

1 participant