com.authlete.jakarta.spi.AuthorizationRequestHandlerSpi Maven / Gradle / Ivy
Show all versions of authlete-java-jakarta Show documentation
/*
* Copyright (C) 2015-2019 Authlete, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*/
package com.authlete.jakarta.spi;
import jakarta.ws.rs.core.Response;
import com.authlete.common.dto.AuthorizationResponse;
import com.authlete.common.dto.Property;
/**
* Service Provider Interface to work with {@link
* com.authlete.jakarta.AuthorizationRequestHandler AuthorizationRequestHandler}.
*
*
* An implementation of this interface must be given to the constructor
* of {@link com.authlete.jakarta.AuthorizationRequestHandler
* AuthorizationRequestHandler} class.
*
*
* @author Takahiko Kawasaki
*/
public interface AuthorizationRequestHandlerSpi
{
/**
* Check whether an end-user has already logged in or not.
*
*
* This method is called only when an authorization request comes
* with {@code prompt=none}. Therefore, if you have no mind to
* support {@code prompt=none}, always return {@code false}. See
* 3.1.2.1. Authentication Request in OpenID
* Connect Core 1.0 for details about {@code prompt=none}.
*
*
*
* Below is an example implementation using Apache Shiro.
*
*
*
*
* @Override
* public boolean isUserAuthenticated()
* {
* return SecurityUtils.getSubject().isAuthenticated();
* }
*
*
* @return
* {@code true} if an end-user has already logged in. Otherwise,
* {@code false}. When {@code false} is returned, the client
* application will receive {@code error=login_required}.
*/
boolean isUserAuthenticated();
/**
* Get the time when the current end-user was authenticated in
* milliseconds since Unix epoch (1970-01-01).
*
*
* The value is used to check whether the elapsed time since the last
* authentication has exceeded the maximum authentication age or not.
* See {@code max_age} in "3.1.2.1. Authentication Request" in OpenID
* Connect Core 1.0, and {@code default_max_age} in "2. Client Metadata" in OpenID Connect Dynamic Client Registration 1.0 for details.
*
*
*
* This method is called only when an authorization request comes
* with {@code prompt=none}. Therefore, if you have no mind to
* support {@code prompt=none}, always return 0. See
* 3.1.2.1. Authentication Request in OpenID
* Connect Core 1.0 for details about {@code prompt=none}.
*
*
*
* Below is an example implementation using Apache Shiro.
*
*
*
*
* @Override
* public long getUserAuthenticatedAt()
* {
* Session session = SecurityUtils.getSubject().getSession(false);
*
* if (session == null)
* {
* return 0;
* }
*
* return session.getStartTimestamp().getTime();
* }
*
*
* @return
* The time when the end-user was authenticated in seconds
* since Unix epoch (1970-01-01).
*/
long getUserAuthenticatedAt();
/**
* Get the subject (= unique identifier) of the current end-user.
* It must consist of only ASCII letters and its length must not
* exceed 100.
*
*
* This method is called only when an authorization request comes
* with {@code prompt=none}. Therefore, if you have no mind to
* support {@code prompt=none}, always return {@code null}. See
* 3.1.2.1. Authentication Request in OpenID
* Connect Core 1.0 for details about {@code prompt=none}.
*
*
*
* Below is an example implementation using Apache Shiro.
*
*
*
*
* @Override
* public long getUserAuthenticatedAt()
* {
* return (String)SecurityUtils.getSubject().getPrincipal();
* }
*
*
* @return
* The subject (= unique identifier) of the current end-user.
*/
String getUserSubject();
/**
* Get the authentication context class reference (ACR) that was
* satisfied when the current end-user was authenticated.
*
*
* The value returned by this method has an important meaning only
* when {@code acr} claim is requested as an essential claim. See "5.5.1.1. Requesting the "acr" Claim" in OpenID
* Connect Core 1.0 if you are interested in the details.
*
*
*
* This method is called only when an authorization request comes
* with {@code prompt=none}. Therefore, if you have no mind to
* support {@code prompt=none}, always return {@code null}. See
* 3.1.2.1. Authentication Request in OpenID
* Connect Core 1.0 for details about {@code prompt=none}.
*
*
*
* If you don't know what ACR is, return {@code null}.
*
*
* @return
* The authentication context class reference (ACR) that
* was satisfied when the current end-user was authenticated.
*/
String getAcr();
/**
* Generate an authorization page (HTML) to ask an end-user whether to
* accept or deny an authorization request by a client application.
*
*
* Key information that should be displayed in an authorization page is
* stored in the {@code info} object. For example, the name of the client
* application can be obtained by calling {@code info.}{@link
* AuthorizationResponse#getClient() getClient()}{@code .}{@link
* com.authlete.common.dto.Client#getClientName() getClientName()} method.
* Likewise, requested scopes can be obtained as an array of {@link
* com.authlete.common.dto.Scope Scope} objects by calling {@code
* info.}{@link AuthorizationResponse#getScopes() getScopes()} method.
*
*
*
* In an authorization page, an end-user will finally decide either to
* grant authorization to the client application or to reject the
* authorization request. The authorization server should receive the
* decision and call {@link
* com.authlete.jakarta.AuthorizationDecisionHandler#handle(String,
* String[], String[]) handle()} method.
*
*
* @param info
* A response from Authlete's {@code /api/auth/authorization} API.
* Key information that should be displayed in an authorization
* page is stored in the object.
*
* @return
* A response to show an authorization page.
*/
Response generateAuthorizationPage(AuthorizationResponse info);
/**
* Get extra properties to associate with an access token and/or an
* authorization code.
*
*
* This method is expected to return an array of extra properties.
* The following is an example that returns an array containing one
* extra property.
*
*
*
* @Override
* public {@link Property}[] getProperties()
* {
* return new {@link Property}[] {
* new {@link Property#Property(String, String)
* Property}("example_parameter", "example_value")
* };
* }
*
*
*
* Extra properties returned from this method will appear as top-level entries
* in a JSON response from an authorization server as shown in 5.1. Successful Response
* in RFC 6749.
*
*
*
* Keys listed below should not be used and they would be ignored on
* the server side even if they were used. It's because they are reserved
* in RFC 6749 and
* OpenID Connect Core 1.0.
*
*
*
* - {@code access_token}
*
- {@code token_type}
*
- {@code expires_in}
*
- {@code refresh_token}
*
- {@code scope}
*
- {@code error}
*
- {@code error_description}
*
- {@code error_uri}
*
- {@code id_token}
*
*
*
* Note that there is an upper limit on the total size of extra properties.
* On the server side, the properties will be (1) converted to a multidimensional
* string array, (2) converted to JSON, (3) encrypted by AES/CBC/PKCS5Padding, (4)
* encoded by base64url, and then stored into the database. The length of the
* resultant string must not exceed 65,535 in bytes. This is the upper limit, but
* we think it is big enough.
*
*
*
* This method is called only when an authorization request comes with {@code
* prompt=none}. Therefore, if you have no mind to support {@code prompt=none},
* always return {@code null}. See 3.1.2.1.
* Authentication Request in OpenID Connect Core
* 1.0 for details about {@code prompt=none}.
*
*
* @return
* Extra properties. If {@code null} is returned, any extra property will
* not be associated.
*
* @since 1.3
*/
Property[] getProperties();
/**
* Get scopes to associate with an access token and/or an authorization code.
*
*
* If {@code null} is returned, the scopes specified in the original
* authorization request from the client application are used. In other
* cases, including the case of an empty array, the specified scopes will
* replace the original scopes contained in the original authorization
* request.
*
*
*
* Even scopes that are not included in the original authorization request
* can be specified. However, as an exception, "openid"
scope
* is ignored on the server side if it is not included in the original
* request. It is because the existence of "openid"
scope
* considerably changes the validation steps and because adding
* "openid"
triggers generation of an ID token (although the
* client application has not requested it) and the behavior is a major
* violation against the specification.
*
*
*
* If you add "offline_access"
scope although it is not
* included in the original request, keep in mind that the specification
* requires explicit consent from the user for the scope (OpenID Connect Core 1.0, 11. Offline Access). When
* "offline_access"
is included in the original request, the
* current implementation of Authlete's /api/auth/authorization API checks
* whether the request has come along with prompt
request
* parameter and the value includes "consent"
. However, note
* that the implementation of Authlete's /api/auth/authorization/issue API
* does not perform such checking if "offline_access"
scope
* is added via this scopes
parameter.
*
*
* @return
* Scopes to associate with an authorization code and/or an access
* token. If a non-null value is set, the original scopes requested
* by the client application are replaced.
*
* @since 1.4
*/
String[] getScopes();
/**
* Get the value of the "sub" claim to be used in the id_token.
*
*
* If doing a pairwise subject derivation, this method should check the
* registration of the current Client to see if it has a PAIRWISE subject
* identifier type. If so, it returns the calculated string of that subject.
* If not, it returns {@code null} and the value of {@link #getUserSubject()}
* is used by the API instead.
*
*
* @return
* The value of the "sub" claim to be used in the id_token,
* or {@code null} if no such subject exists.
*
* @since 2.22
*/
String getSub();
}