Phoenix-friendly protected-resource authentication.
This plug is a thin integration layer over Attesto.Plug.Authenticate. The
core plug owns the protocol work: parsing Bearer/DPoP credentials, verifying
the JWT access token, enforcing DPoP and mTLS sender-constraint bindings, and
rendering RFC 6750 / RFC 9449 failures. This wrapper derives the core options
from AttestoPhoenix.Config, resolves the verified subject through the
host's :load_principal callback, and assigns neutral values for downstream
Phoenix code.
Defaults:
:claims_key-:attesto_claims:principal_key-:attesto_principal:context_key-:attesto_context
The context assign is a map with :subject, :client_id, :scope, :claims,
:cnf, and :principal. It is deliberately protocol-shaped; application
policy such as accounts, roles, audit actors, and error envelopes belongs in
the host application.
RFC 9728 challenge discovery is selected through
AttestoPhoenix.Config.resource_metadata_url/3: an explicit per-plug
:resource_metadata value (including nil) takes precedence on every error
path and skips the resolver. A non-nil per-plug value is static Plug
configuration and is validated by init/1, which Phoenix runs at compile
time by default. Otherwise, the existing static
:resource_metadata URL remains the default, while an optional
:resource_metadata_resolver can choose a URL or omit it for each request.
Invalid runtime resolver results are omitted. A resolver exception is not
rescued and aborts the request, because resolvers are trusted host
configuration rather than untrusted request input.