NAME

OIDC::Client - OpenID Connect Client

SYNOPSIS

my $client = OIDC::Client->new(
  provider          => 'my_provider',
  id                => 'my_client_id',
  secret            => 'my_client_secret',
  provider_metadata => \%provider_metadata,
  log               => $app->log,
);

# or...

my $client = OIDC::Client->new(
  config => $config_provider,
  log    => $app->log,
);

my $token_response = $client->get_token(
  code         => $code,
  redirect_uri => q{http://yourapp/oidc/callback},
);

DESCRIPTION

Client module for OpenID Connect protocol.

Use this module directly from a batch or a simple script. For use from within an application, you should instead use the framework plugin included in the OIDC-Client distribution.

METHODS

BUILD

Called after the object is created. Makes some basic checks and forces the retrieval of provider metadata and kid keys.

auth_url( %args )

my $authorize_url = $client->auth_url(%args);

Returns a scalar or a Mojo::URL object containing the initial authorization URL. This is the URL to use to initiate an authorization code flow.

The optional parameters are:

response_mode

Defines how tokens are sent by the provider.

Can take one of these values:

query

Tokens are sent in query parameters.

form_post

Tokens are sent in a POST form.

redirect_uri

Redirection URI to which the response will be sent. Can also be specified in the signin_redirect_uri configuration entry.

state

String which is sent during the request to the identity provider and sent back from the IDP along with the Code.

nonce

String which is sent during the request to the identity provider and sent back from the IDP in the returned ID Token.

scope

Specifies the desired scope of the requested token. Must be a string with space separators. Can also be specified in the scope configuration entry.

audience

Specifies the audience/resource that the access token is intended for. Can also be specified in the audience configuration entry.

extra_params

Hashref which can be used to send extra query parameters. Can also be specified in the authorize_endpoint_extra_params configuration entry.

want_mojo_url

Defines whether you want this method to return a Mojo::URL object instead of a scalar. False by default.

get_token( %args )

my $token_response = $client->get_token(
  code         => $code,
  redirect_uri => q{http://yourapp/oidc/callback},
);

Fetch token(s) from an OAuth2/OIDC provider and returns a OIDC::Client::TokenResponse object.

This method doesn't execute any verification. Call the verify_token method to do so.

The optional parameters are:

grant_type

Specifies how the client wants to interact with the identity provider. Accepted here : authorization_code, client_credentials, password or refresh_token. Can also be specified in the token_endpoint_grant_type configuration entry. Default to authorization_code.

auth_method

Specifies how the client credentials are sent to the identity provider. Accepted here : post or basic. Can also be specified in the token_endpoint_auth_method configuration entry. Default to post.

code

Authorization-code that is issued beforehand by the identity provider. Used only for the authorization_code grant-type.

redirect_uri

Redirection URI to which the response will be sent. Can also be specified in the signin_redirect_uri configuration entry. Used only for the authorization_code grant-type.

username / password

User credentials for authorization Can also be specified in the username and password configuration entries. Used only the for password grant-type.

audience

Specifies the Relaying Party for which the token is intended. Can also be specified in the audience configuration entry. Not used for the refresh_token grant-type.

scope

Specifies the desired scope of the requested token. Must be a string with space separators. Can also be specified in the scope configuration entry. Not used for the authorization_code nor the refresh_token grant-type.

refresh_token

Token that can be used to renew the associated access token before it expires. Used only for the refresh_token grant-type.

verify_token( %args )

my $claims = $client->verify_token(
  token             => $token,
  expected_audience => $audience,
  expected_nonce    => $nonce,
);

Checks the structure, claims and signature of the JWT token. Throws an OIDC::Client::Error::TokenValidation exception if an error occurs. Otherwise, returns the claims.

This method automatically manages a JWK key rotation. If a JWK key error is detected during token verification, the JWK keys in memory are refreshed by retrieving them again from the JWKS URL. The token is checked again, and if an error occurs, an OIDC::Client::Error::TokenValidation exception is thrown.

The following claims are validated :

"exp" (Expiration Time) claim

By default, must be valid (not in the future) if present.

"iat" (Issued At) claim

By default, must be valid (not in the future) if present.

"nbf" (Not Before) claim

By default, must be valid (not in the future) if present.

"iss" (Issuer) claim

Must be the issuer recorded in the provider metadata.

"aud" (Audience) claim

Must be the expected audience (see parameters beelow).

"sub" (Subject) claim

Must be the expected subject defined in the parameters (see beelow).

The [Crypt::JWT::decode_jwt()](https://metacpan.org/pod/Crypt::JWT#decode_jwt) function is used to validate and decode a JWT token. Remember that you can change the options transmitted to this function (see OIDC::Client::Config).

The parameters are:

token

The JWT token to validate. Required.

expected_audience

If the token is not intended for the expected audience, an exception is thrown. Default to the audience configuration entry or otherwise the client id.

expected_subject

If the subject claim value is not the expected subject, an exception is thrown. Optional.

expected_nonce

If the nonce claim value is not the expected nonce, an exception is thrown. Optional.

has_expired( $expiration_time )

my $has_expired = $client->has_expired($token->{expires_at});

Returns true if the timestamp passed in parameter has expired. The configuration entry expiration_leeway is included in the calculation if present.

get_userinfo( %args )

my $userinfo = $client->get_userinfo(
  access_token => $stored_token->{token},
  token_type   => $stored_token->{token_type},
);

Get and returns the user information from an OAuth2/OIDC provider.

The parameters are:

access_token

Content of the valid access token obtained through OIDC authentication.

token_type

Optional, default to Bearer.

get_audience_for_alias( $audience_alias )

my $audience = $client->get_audience_for_alias($audience_alias);

Returns the audience for an alias that has been configured in the configuration entry audience_alias/$audience_alias/audience.

get_scope_for_audience( $audience )

my $scope = $client->get_scope_for_audience($audience);

Returns the scope for an audience that has been configured in the configuration entry audience_alias/$audience_alias/scope.

exchange_token( %args )

my $exchanged_token_response = $client->exchange_token(
  token    => $token,
  audience => $audience,
);

Exchanges an access token, obtained through OIDC authentication, for another access token that is accepted by a different OIDC application.

Returns a OIDC::Client::TokenResponse object.

The parameters are:

token

Content of the valid access token obtained through OIDC authentication.

audience

Audience of the target application.

scope

Specifies the desired scope of the requested token. Must be a string with space separators. Optional.

build_api_useragent( %args )

my $ua = $client->build_api_useragent(
  token      => $token,
  token_type => $token_type,
);

Builds a web client (Mojo::UserAgent object) that will have the given token in the authorization header for each request.

The optional parameters are:

token

Content of the access token to send to the other application.

If it is not passed as parameter, the method get_token is invoked without any parameter to retrieve the token from the provider. This can be useful if the client is configured for a password grant or a client credentials grant.

token_type

Token type. Default to "Bearer".

logout_url( %args )

my $logout_url = $client->logout_url(%args);

URL allowing the end-user to logout. Returns a scalar or a Mojo::URL object which contain the logout URL.

The optional parameters are:

id_token

Content of the end-user's ID token.

state

String to add to the logout request that will be included when redirecting to the post_logout_redirect_uri.

post_logout_redirect_uri

Redirect URL value that indicates where to redirect the user after logout. Can also be specified in the post_logout_redirect_uri configuration entry.

extra_params

Hashref which can be used to send extra query parameters.

want_mojo_url

Defines whether you want this method to return a Mojo::URL object instead of a scalar. False by default.

get_claim_value( %args )

my $claim_value = $client->get_claim_value(name => 'login', claims => $claims);

Returns the value of a claim by its configured name.

The hash parameters are:

name

Name of the claim configured in the claim_mapping section.

claims

Hashref of the claims.

optional

Defines whether the wanted claim must exist in the claims.

decode_jwt( %args )

Simple pass-through of the Crypt::JWT::decode_jwt() function that can be mocked in tests

CONFIGURATION

To use this module directly via a batch or script, here is the section to add to your configuration file:

oidc_client:
  provider:                  provider_name
  id:                        my-app-id
  secret:                    xxxxxxxxx
  audience:                  other_app_name
  well_known_url:            https://yourprovider.com/oauth2/.well-known/openid-configuration
  scope:                     roles
  token_endpoint_grant_type: password
  username:                  TECHXXXX
  password:                  xxxxxxxx

This is an example, see the detailed possibilities in OIDC::Client::Config.

SAMPLES

Here are some samples by category. Although you will have to adapt them to your needs, they should be a good starting point.

API call

To make an API call to another application :

my $oidc_client = OIDC::Client->new(
  log    => $self->log,
  config => $self->config->{oidc_client},
);

# Retrieving a web client (Mojo::UserAgent object)
my $ua = $oidc_client->build_api_useragent();

# Usual call to the API
my $res = $ua->get($url)->result;

Here, there is no token exchange because the audience has been configured to get the access token intended for the other application.

AUTHOR

Sébastien Mourlhou

COPYRIGHT AND LICENSE

Copyright (C) Sébastien Mourlhou

This program is free software, you can redistribute it and/or modify it under the terms of the Artistic License version 2.0.

SEE ALSO