PublicShow sourceoauth2.pl -- Oauth2 based login

This module provides oauth2 based login. Oauth2 is a federated identity protocol. It allows a user to login to a service by redirecting to an identity provider. After validating the user, the identity provider redirects back to our service. In the process we obtain an anonymous identifier for the user and optionally user attributes such as the user's name, email, etc.

As oauth2 does not use HTTP authentication the fact that a user has logged in must be handled using an HTTP session.

Using this module requires the user to define two hooks:

Source server_attribute(?ServerID, ?Attribute, ?Value) is nondet[multifile]
Multifile hook that defines available oauth2 servers. ServerID is our internal nickname for the oauth2 identity provider. Attribute and Value provide the various attributes we need to know to contact the server. Defined attributes are:
url
Base URL for the identity provider. Normally points at the root of the server. Other locations are relative to this URL.
redirect_uri
URI to which the identity provider will redirect back. This is the public URL for oauth2(ServerID/reply). It may be left undefined if the server can find its own location. This URI is normally registered with the identity provider.
discovery_endpoint
Endpoint for automatic configuration. The default is url, followed by /.well-known/openid-configuration. The discovery URL is used if one of the other required attributes is not defined by the hook.
authorization_endpoint
Path on the identity provider that initiates a login. The default is obtained from the `discovery_endpoint.
token_endpoint
Location to validate the access code and obtain an access token. The default is obtained from the `discovery_endpoint.
userinfo_endpoint
Path to get info on the user from the access token. The default is obtained from the `discovery_endpoint.
tokeninfo_endpoint
Needed for implicit and hybrid login flows (typically not used by servers)
client_id
Identity by which we are known at the identity provider.
client_secret
Secret we need to identify ourselves with the identity provider
scope
Set of attributes we wish to have from the identity provider.
cert_verify_hook
Set the certificate verification hook. Default is to verify the certificate. If set to cert_accept_any, any certificate is accepted. This can be used to deal with self-signed certificates in expertimental setups.
Source oauth2_login(+Request, +Options)
HTTP handler to login using oauth2. It causes a redirect to the oauth2 identity server, which will redirect back to oauth2(reply).
Source oauth2_reply(+Request, +Options)
HTTP handler for the redirect we get back from the oauth2 server.
To be done
- Deal with expires_in and id_token fields.
Source login(+Request, +ServerID, +TokenInfo) is semidet[multifile]
Multifile hook to realise the actual login. Normally this hook shall create a session and associate the session with the identity of the user. This hook may keep track of a user profile.

If this hook fails, oauth2_reply/2 returns a text/plain document with the obtained information. This can be used for debugging and development purposes.

Arguments:
Request- is the HTTP request dealing with the redirect back from the identity provider.
ServerID- identifies the identity provider.
TokenInfo- is a dict containing information about the access token.
UserInfo- is a dict containing information about the user.
Source oauth2_validate_access_token(+ServerID, +AccessToken, -Info:dict)
Validates the AccessToken with Unity (implicit or hybrid flow).
Source oauth2_user_info(+ServerID, +TokenInfo, -UserInfo) is det
Given the token details obtained in oauth2_reply/2, get extended information about the user from the identity provider. TokenInfo is a dict that must contain access_token.
Source oauth2_claim(+TokenInfo, -Claim) is semidet
True when Claim is the claim made in TokenInfo.