Client authentication interceptor SPI

1. Intercepting client authentication events

The Connect2id server includes a Service Provider Interface (SPI) to let deployments implement custom client authentication logging, auditing or reporting.

Using the client_auth_id which the Connect2id server assigns to every authentication instance, deployments could for instance create a self-service point for client developers to quickly debug HTTP 401 Unauthorized errors or receive warnings when their client_id receives too many invalid_client errors.

The SPI is available since v12.12.

2. Client authentication interceptor SPI

To plug in a interceptor of client authentication events implement the ClientAuthenticationInterceptor SPI defined in the Connect2id server toolkit:

Git repohttps://bitbucket.org/connect2id/server-sdk

Features of the SPI:

  • Provides access to the client authentication parameters and additional context, such as the client_auth_id identifying the authentication instance and the registered client information.
  • Successful client authentications can be subjected to additional checks and rejected with an InvalidClientException to cause the Connect2id server to return an OAuth 2.0 invalid_client error to the client.

If the Connect2id server detects an SPI implementation it will log its loading and enabled status under OP6222.

INFO MAIN [main] [OP6222] Loaded client authentication interceptor: class=ClientAuthenticationEventListener enabled=true

The Connect2id server can load multiple enabled plugins, but note that the order of their invocation is not deterministic.

Important: The interceptors are called synchronously, so if you expect them to block or spend more than a few milliseconds to process an event, do that in a separate thread.

3. Example

Plugin that simply maintains counters of successful and failed client authentications:

import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.atomic.*;
import com.nimbusds.oauth2.sdk.auth.*;
import com.nimbusds.openid.connect.provider.spi.clientauth.*;

public class ClientAuthCounter implements ClientAuthenticationInterceptor {

        private final AtomicInteger successCounter = new AtomicInteger();

        private final AtomicInteger errorCounter = new AtomicInteger();

        @Override
        public void interceptSuccess(
            final ClientAuthentication clientAuth,
            final ClientAuthenticationContext ctx) {

            successCounter.incrementAndGet();
        }

        @Override
        public void interceptError(
            final ClientAuthentication clientAuth,
            final InvalidClientException exception,
            final ClientAuthenticationContext ctx) {

            errorCounter.incrementAndGet();
        }
}