On-Behalf-Of (OBO) Authentication

On-Behalf-Of (OBO) authentication allows an external application or integration to access the APIs of imc Learning Suite (LMS) on behalf of a specific user.

This can be useful when an external system needs to perform actions in LMS in the context of the currently authenticated user rather than using a single technical or service account for all requests.

For example, an external application may already know the identity of the user interacting with it and needs to call LMS APIs as that same user. With OBO authentication, the application can request an access token representing the respective LMS user and use this token for subsequent API requests.

OBO authentication is particularly relevant when:

  • API requests should be executed in the context of individual users.

  • different users should be represented by their respective LMS identities.

  • using one shared technical account for all API requests is not suitable for the integration.

If an integration only requires system-to-system communication using a single technical identity, OBO authentication may not be required.

The following sections describe the required configuration, JWT generation, and token exchange for using OBO authentication.

Configuration

For On-Behalf-Of (OBO) authentication, you require a secure encryptionKey. You must configure the key in the imc-ms-config/application.yml directory to make it available to the system.
According to the JWT JWA Specification (RFC 7518, Section 3.2), keys used with HMAC-SHA algorithms must have a size of at least 256 bits. Therefore, the configured encryptionKey must provide at least 256 bits of key material.

auth:
  jwt:
    issuer: ${endpoint.extern.url}
    subject:
      encryptionKey: 

Note the configured issuer, as you will require the exact value when generating the JWT. If the issuer is configured using a placeholder, resolve the corresponding configuration in the same application.yml file.

endpoint:
  extern:
    host: customer.imc-learning.com
    port: 443
    https: true # required in ils/application.properties
    protocol: HTTPS # this is used in systemintegration.xml where only uppercase is allowed
    scheme: https # this is used for various purposes (issuer in idm, url mapping like cors-filters, ...)
    url: ${endpoint.extern.scheme}://${endpoint.extern.host}:${endpoint.extern.port}

With the example configuration above, the issuer resolves to: https://customer.imc-learning.com:443

Scheer IMC is happy to assist with setting up the encryptionKey or to perform the configuration on your behalf and provide you with the required details.

JWT Generation

Once you complete the configuration, you can generate a JWT for the user to be impersonated. The following Java example creates a JWT for the OBO token exchange:

Java
SecretKey key = Keys.hmacShaKeyFor(encryptionKey.getBytes(StandardCharsets.UTF_8));

Instant now = Instant.now();
Instant expiresAt = now.plusSeconds(1 * 60 * 60); // e.g. 1 hour

String jwt = Jwts.builder()
        .setHeaderParam("typ", "JWT")
        .setSubject("imc_learner@im-c.de") // Email address of the user to impersonate
        .setIssuer("https://customer.imc-learning.com:443") // Must match the configured system
        .setIssuedAt(Date.from(now))
        .setExpiration(Date.from(expiresAt))
        .signWith(key, SignatureAlgorithm.HS256)
        .compact();

Important: The system URL used to access the API and the configured JWT issuer may differ. The iss claim in the JWT must exactly match the issuer configured in application.yml file.

OBO Token Exchange

POST {systemURL}/idm/jwt/service/impersonate

curl --location --request POST 'https://{systemURL}/idm/jwt/service/impersonate?grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Atoken-exchange&client_id={client}&client_secret={clientSecret}&subject_token={jwtToken}&subject_token_type=urn%3Aietf%3Aparams%3Aoauth%3Atoken-type%3Ajwt' \

API Parameter

Value

Description

grant_type

urn:ietf:params:oauth:grant-type:token-exchange

Specifies the OAuth 2.0 Token Exchange grant type

client_id


The client ID as configured in application.yml file. You must enable impersonation for this client.

client_secret


The client secret corresponding to the configured client

subject_token


The JWT containing the identity of the user to be impersonated

subject_token_type

urn:ietf:params:oauth:token-type:jwt

Specifies that the provided subject_token is a JWT

The API will return a response like:

JSON
{
    "refresh_token": "XXX",
    "access_token": "XXX",
    "token_type": "Bearer",
    "expires_in": 86400
}

You can now use the returned access_token to perform API requests on behalf of the user specified in the sub claim of the JWT. You can use the refresh_token to obtain a new access token when required.