anchor.diff:  }
   ----
   
  +.Kotlin
  +[source,kotlin,role="secondary"]
  +----
  +class JwtOpaqueTokenIntrospector : OpaqueTokenIntrospector {
  +    private val delegate: OpaqueTokenIntrospector = NimbusOpaqueTokenIntrospector("https://idp.example.org/introspect", "client", "secret")
  +    private val jwtDecoder: JwtDecoder = NimbusJwtDecoder(ParseOnlyJWTProcessor())
  +    override fun introspect(token: String): OAuth2AuthenticatedPrincipal {
  +        val principal = delegate.introspect(token)
  +        return try {
  +            val jwt: Jwt = jwtDecoder.decode(token)
  +            DefaultOAuth2AuthenticatedPrincipal(jwt.claims, NO_AUTHORITIES)
  +        } catch (ex: JwtException) {
  +            throw OAuth2IntrospectionException(ex.message)
  +        }
  +    }
  +
  +    private class ParseOnlyJWTProcessor : DefaultJWTProcessor<SecurityContext>() {
  +        override fun process(jwt: SignedJWT, context: SecurityContext): JWTClaimsSet {
  +            return jwt.jwtClaimsSet
  +        }
  +    }
  +}
  +----
  +====
  +
   Thereafter, this custom introspector can be configured simply by exposing it as a `@Bean`:
   
  -[source,java]
  +====
  +.Java
  +[source,java,role="primary"]
   ----
   @Bean
   public OpaqueTokenIntrospector introspector() {
  -    return new JwtOpaqueTokenIntropsector();
  -}
  -----
  +    return new JwtOpaqueTokenIntrospector();
  +}
  +----
  +
  +.Kotlin
  +[source,kotlin,role="secondary"]
  +----
  +@Bean
  +fun introspector(): OpaqueTokenIntrospector {
  +    return JwtOpaqueTokenIntrospector()
  +}
  +----
  +====
   
   [[oauth2resourceserver-opaque-userinfo]]
   === Calling a `/userinfo` Endpoint
  
positive.code: Now that you're resource server has validated the token, it might be handy to pass it to downstream services.
  This is quite simple with `{security-api-url}org/springframework/security/oauth2/server/resource/web/reactive/function/client/ServletBearerExchangeFilterFunction.html[ServletBearerExchangeFilterFunction]`, which you can see in the following example:
  
  [source,java]
  ----
  @Bean
  public WebClient rest() {
  
negative.code: }
  ----
  
  .Kotlin
  [source,kotlin,role="secondary"]
  ----
  class CustomAuthoritiesOpaqueTokenIntrospector : OpaqueTokenIntrospector {
      private val delegate: OpaqueTokenIntrospector = NimbusOpaqueTokenIntrospector("https://idp.example.org/introspect", "client", "secret")
      override fun introspect(token: String): OAuth2AuthenticatedPrincipal {
          val principal: OAuth2AuthenticatedPrincipal = delegate.introspect(token)
          return DefaultOAuth2AuthenticatedPrincipal(
                  principal.name, principal.attributes, extractAuthorities(principal))
      }
  
      private fun extractAuthorities(principal: OAuth2AuthenticatedPrincipal): Collection<GrantedAuthority> {
          val scopes: List<String> = principal.getAttribute(OAuth2IntrospectionClaimNames.SCOPE)
          return scopes
                  .map { SimpleGrantedAuthority(it) }
      }
  }
  ----
  ====
  
  Thereafter, this custom introspector can be configured simply by exposing it as a `@Bean`:
  
  ====
  .Java
  [source,java,role="primary"]
  ----
  @Bean
  public OpaqueTokenIntrospector introspector() {
  