Related to #5629

Like it is for Resource Server JWT support, it should be simple to customize the authentication token that gets returned from the introspection support, e.g.:

http
    .oauth2ResourceServer()
        .opaqueToken()
            .introspectionAuthenticationConverter(this::convertToCustomAuthentication)

We should add support for this both on the servlet and on the reactive sides.

Comment From: rwinch

I realize this is probably not finalized, but I'm wondering if we need introspection in the method name?

Comment From: jzheaux

I think it depends on the contract.

For JWT, the code is:

http
    .oauth2ResourceServer()
        .jwt()
            .jwtAuthenticationConverter(...)

And that's because the contract is Converter<Jwt, ? extends AbstractAuthenticationToken>.

The contract here isn't quite as clear since it would require both the token and its attributes, which there isn't a class for like there is for Jwt.

Comment From: ch4mpy

@jzheaux, couldn't both method be claimsAuthenticationConverter(...) with a contract like Convervter<Map<String, Object>, AbstractAuthenticationToken>?

What is the value of having the opaque string of a token, headers, signature or other upstream validation data inside the Authentication implementation (OpenID impl. even embeds authentication request and response) ?

Once decoded, is a token more than a claim-set? RFC-7519 Terminology defines JSON Web Token (JWT) as "A string representing a set of claims" and RFC-7662 Introspection Response can be parsed either as a strongly-typed object or a Map<String, Object> (as it currently is by the framework)

Those are questions I had for two month or so, which gave me time to explore a bit around it.

You can find, in this repo (you already have cloned), what I've done around OAuth2ClaimSetAuthentication<T extends UnmodifiableClaimSet & Principal>, another AbstractAuthenticationToken implementation.

Its main interest being it's generic: takes the token claims type as parameter. Yes, I've also derived Map<String, Object> into ClaimSet and then JwtClaimSet & IntrospectionClaimSet. The latter two are also Principal (java.security one), name being retrieved from subject claim, so fit as OAuth2ClaimSetAuthentication parameters.

Comment From: jzheaux

The Opaque Token API has undergone a fair amount of change since this ticket was created.

While I still feel like there is value in continuing to consider this feature, it's fairly simple at this point to customize the authorities with a simple override of OpaqueTokenIntrospector:

@Bean 
public OpaqueTokenIntrospector introspector() {
    OpaqueTokenIntrospector delegate = new NimbusOpaqueTokenIntrospector(...);
    return token -> {
        OAuth2AuthenticatedPrincipal principal = delegate.introspect(token);
        Collection<GrantedAuthority> mapped = mapAuthorities(principal);
        return new DefaultOAuth2AuthenticatedPrincipal(
            principal.getName(), principal.getAttributes(), mapped);
    }
}

Comment From: jgrandja

@jzheaux Should we still consider this or should we close?

Comment From: koenbeckers

I would still like this, as our application needs to convert from an opaque token into a User object.

Comment From: dkfellows

Looks like there will be a OpaqueTokenAuthenticationConverter (https://github.com/spring-projects/spring-security/commit/1efb63387f14dc7858f445884f34b70af30b85b4) in 5.8 and 6, thanks to @ch4mpy.

Comment From: jgrandja

@jzheaux I believe this can be closed as a duplicate of gh-11661 ?

Comment From: spring-projects-issues

If you would like us to look at this issue, please provide the requested information. If the information is not provided within the next 7 days this issue will be closed.

Comment From: spring-projects-issues

Closing due to lack of requested feedback. If you would like us to look at this issue, please provide the requested information and we will re-open the issue.