Skip to content

feat: end-to-end signing mode support + spec-compliant error model#9

Merged
dasiths merged 12 commits into
mainfrom
feat/gap-remediation-plan-updates
May 22, 2026
Merged

feat: end-to-end signing mode support + spec-compliant error model#9
dasiths merged 12 commits into
mainfrom
feat/gap-remediation-plan-updates

Conversation

@dasiths
Copy link
Copy Markdown
Collaborator

@dasiths dasiths commented May 22, 2026

Summary

Implements full end-to-end support for all AAuth signing modes and constrains the demo to only valid permutations per the AAuth Protocol spec.

Changes

Signing Modes (SDK)

  • ISignatureKeyProvider strategy pattern for producing Signature-Key headers
  • Built-in providers: JwtSignatureKeyProvider, HwkSignatureKeyProvider, JwksUriSignatureKeyProvider, JktJwtSignatureKeyProvider
  • ISignatureKeyResolver + DefaultSignatureKeyResolver for multi-scheme verification dispatch
  • IKeyLookup interface for application-supplied key stores (hwk verification)

Signing Mode Constraints (per spec)

  • Identity-based (no PS): hwk or jwks_uri only — jwt requires a Person Server
  • Three-party (Autonomous/Deferred): jwt only — spec mandates agent token via scheme=jwt
  • Bootstrap: jkt-jwt — two-key delegation for key rotation

Error Model Compliance

  • Signature-Error header emitted on all 401 responses with correct error codes
  • supported_algorithms parameter on unsupported_algorithm (spec MUST)
  • required_input parameter on invalid_input
  • Non-Ed25519 keys classified as unsupported_algorithm (not invalid_key)

Demo (GuidedTour)

  • Signing mode selector shown only in Identity flow (hwk/jwks_uri)
  • Three-party flows display "Agent Token (scheme=jwt) — required for all PS flows"
  • Bootstrap description clarifies it's required for jwks_uri + PS flows, not hwk
  • Identity mode hides PS lane in sequence diagram and header
  • Signing mode change resets the flow

AgentConsole

  • Defaults to hwk without --ps, jwt with --ps
  • Rejects jwt without PS and non-jwt with PS

WhoAmI Resource

  • Handles hwk/jwks_uri for identity-based access (200 with scheme-appropriate claims)
  • jwt with ps claim triggers three-party challenge flow

Test Results

  • 320 tests pass (130 unit + 190 conformance)
  • New conformance tests for signing mode round-trips and supported_algorithms parameter

Spec References

dasiths added 12 commits May 22, 2026 09:52
- Add §9.1: act claim building gap (AuthTokenBuilder has no Act property)
- Add §9.2: scope narrowing enforcement
- Add §9.3: dual-dwk acceptance for auth tokens
- Add §8.5: JTI replay detection (distinct from revocation)
- Add §14.1: AAuth-Capabilities header
- Add §12 loopback port carve-out for server identifiers
- Expand conformance suite §1.5 with 9 explicit test file specs
- Document root cause of conformance blind spot in §13
- Update phase ordering, DoD sections, and research findings
- Add cross-cutting 'Extensibility seams' section to implementation plan
  with 10 interfaces, DI registration pattern, and design rules
- Add research §15 with full design rationale, interface inventory,
  IInteractionPresenter design, IKeyStore refinement, and alternatives
- Update 'Out of scope' table to map each item to its shipped interface
- New seam: IInteractionPresenter replaces raw Func<> callback for
  interaction presentation (console, browser, push, Blazor)
Phase 1 implements verification & error-reporting hardening per gaps.md:

§1.1 PoP binding enforcement:
- TokenVerifier.VerifyAuthToken() enforces cnf.jwk ↔ HTTP sig key binding
- Validates act claim is present with act.sub = agent identifier
- Enforces at least one of sub/scope in auth tokens
- Act-chain depth limit (MaxActDepth=10) prevents DoS via nesting

§1.2 Structured authentication errors:
- SignatureErrorCode enum with all 8 spec-defined codes
- AAuthVerificationMiddleware now emits Signature-Error header on 401
- TokenErrorCode enum for token endpoint error parsing
- PollingErrorCode enum + PollingErrorException for polling errors

§1.3 Identifier validation:
- AAuthServerId validates server identifiers (https, host-only, no port
  except loopback, no path/query/fragment, lowercase, IDN→ACE)
- AAuthAgentId validates agent identifiers (aauth:local@domain format,
  [a-z0-9-_+.]{1,255} local part, lowercase domain)
- Loopback port carve-out for development samples

§1.4 Token verifier completeness:
- Dual-dwk acceptance (aauth-person.json or aauth-access.json)
- Scope narrowing check (auth scope ⊆ resource scope)
- VerifyAuthTokenWithJwksAsync for JWKS-based verification
- DeferredPoller handles slow_down (+5s), invalid_code (abort),
  denied/expired (typed exception)

§1.5 Conformance suite: 89 new tests across 9 files:
- AuthTokens/: structure, verification, scope narrowing, dual-dwk
- Errors/: Signature-Error, token endpoint, polling errors
- Identifiers/: agent IDs, server IDs

All 265 tests pass (130 existing + 135 conformance).
Phase 2 (resource-side):
- IJtiStore + InMemoryJtiStore for replay detection
- Replay detection in AAuthVerificationMiddleware
- RevocationEndpoint (POST /revoke)
- Resource metadata: authorization_endpoint, revocation_endpoint fields
- Agent-side ServerMetadata/ResourceMetadata typed discovery models
- MetadataClientExtensions for typed PS/AS/resource fetch

Phase 3 (crypto + schemes):
- IAAuthKey interface extracted from AAuthKey
- EcdsaAAuthKey (P-256, RFC 6979 via BouncyCastle HMacDsaKCalculator)
- SignatureKeyHeader: FormatHwk, FormatJwksUri, FormatJktJwt
- SignatureKeyParser.ParseAny: jwt, hwk, jkt-jwt, jwks_uri schemes
- ParsedSignatureKeyInfo model for all scheme types

Phase 4 (bootstrap):
- IKeyStore + InMemoryKeyStore
- IPlatformAttestor + NoopAttestor
- AgentProviderClient (EnrolAsync, RefreshAsync)

Phase 5 (missions):
- AAuthMission model + AAuthMissionHeader

Phase 7 (agent/resource only):
- AAuth-Capabilities header + AAuthSigningHandler integration
- IOpaqueTokenStore + InMemoryOpaqueTokenStore (2-party flow)
- IInteractionPresenter + ConsoleInteractionPresenter

Conformance: 176 tests (was 144), all pass.
Unit: 130 tests, all pass. Total: 306.
…ples

- Add samples/MockAgentProvider/ with enrol, refresh, metadata, and JWKS
  endpoints demonstrating the Agent Provider role (§7)
- Update AgentConsole with --ap flag to enrol via AgentProviderClient
  instead of self-signing tokens locally
- Update GuidedTour with dedicated AP steps when AgentProviderUrl is set:
  Step 2 'Discover Agent Provider' (GET /.well-known/aauth-agent.json)
  Step 3 'Enrol with Agent Provider' (POST /enrol, shows full HTTP exchange)
  All subsequent step numbers shift +1; plan arrays and UI updated
- Add AgentProvider actor to sequence diagram
- Make all step numbering dynamic (Steps.Count + 1) for offset resilience
- Update post-implementation.md: AP now documented as sample-implemented
- Update implementation-plan.md Phase 4 DoD to reflect sample coverage
…ling and add entity highlighting

- Updated `appsettings.json` in GuidedTour to remove unnecessary endpoint from `AgentProviderUrl`.
- Modified CSS in `app.css` for improved layout and styling, including adjustments to the topbar and new entity highlighting styles.
- Enhanced `MockAgentProvider` to support optional person server URL in agent enrollment.
- Updated README to reflect changes in `AgentProviderUrl`.
- Improved `WhoAmI` service to handle authorization headers and updated token verification logic.
- Refactored `AgentProviderClient` to include optional person server in requests.
- Enhanced HTTP signature handling to cover authorization headers.
- Updated `AgentTokenBuilder` to support separate confirmation keys.
- Added integration tests for the WhoAmI flow, including a stub for the agent provider.
- Introduced `EntityHighlighter` component in GuidedTour for highlighting known entity URLs/IDs in HTML.
- Refactor AAuthVerificationMiddleware to support multiple Signature-Key schemes (jwt, hwk, jwks_uri, jkt-jwt) using ISignatureKeyResolver.
- Introduce ISignatureKeyProvider interface and implementations for each signing mode.
- Add DefaultSignatureKeyResolver to handle public key resolution based on the Signature-Key scheme.
- Update AAuthVerifier to accept IAAuthKey for verification.
- Create integration tests for signing and verifying requests across all signing modes.
- Implement in-memory key lookup for testing hwk scheme resolution.
- Ensure compliance with AAuth specifications for keying material and signature verification.
…ity uses hwk/jwks_uri

- Remove jwt from Identity flow signing selector (requires PS-issued token)
- Default Identity flow to hwk (Pseudonymous); three-party flows force jwt
- SigningMode setter now resets the timeline on change
- Hide PS lane and header URL in Identity mode (no PS involved)
- Add 'Agent Token (scheme=jwt)' callout to Autonomous/Deferred descriptions
- Update Bootstrap description: required for jwks_uri + PS flows, not hwk
- AgentConsole: reject jwt without --ps, default based on flow type
- Update implementation plan signing mode × flow matrix
- SignatureError.Format() now accepts supported_algorithms parameter
- Middleware emits supported_algorithms="EdDSA" for unsupported_algorithm errors
- Classify non-Ed25519 keys (wrong kty/crv) as unsupported_algorithm, not invalid_key
- Add conformance tests for supported_algorithms parameter and EC key rejection

Compliant with draft-hardt-httpbis-signature-key §5 Signature-Error:
'Response MUST include supported_algorithms listing the algorithms
the server accepts.'
Add 22 markdown docs covering the full AAuth .NET SDK:

- Foundation: README index, getting-started, protocol concepts
- Signing Modes: overview, hwk, jwks_uri, jwt, jkt-jwt
- Workflows: identity-based, resource-managed, ps-asserted,
  federated, bootstrap/enrollment, deferred consent
- Server: verification middleware, resource metadata, token
  issuance, replay detection, multi-scheme verification
- Advanced: missions, platform attestation, key management,
  error handling
- Reference: configuration options for all components

Also updates root README to correctly identify the four protocol
participants as Agent, Resource, Person Server, and Access Server
(with Agent Provider noted as a supporting role).
@dasiths dasiths merged commit 98646ce into main May 22, 2026
@dasiths dasiths deleted the feat/gap-remediation-plan-updates branch May 22, 2026 15:58
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.

1 participant