Awesome
Authlete Library for JAX-RS (Java)
Overview
This library provides utility classes to make it easy for developers to implement an authorization server which supports OAuth 2.0 and OpenID Connect and a resource server.
This library is written using JAX-RS 2.0 API and authlete-java-common library. JAX-RS is The Java API for RESTful Web Services. JAX-RS 2.0 API has been standardized by JSR 339 and it is included in Java EE 7. On the other hand, authlete-java-common is another Authlete's open source library which provides classes to communicate with Authlete Web APIs.
Authlete is a cloud service that provides an implementation of OAuth 2.0 & OpenID Connect (overview). You can build a DB-less authorization server by using Authlete because authorization data (e.g. access tokens), settings of authorization servers and settings of client applications are stored in the Authlete server on cloud.
java-oauth-server is an authorization server implementation which uses this library. It implements not only an authorization endpoint and a token endpoint but also a JWK Set endpoint, a configuration endpoint and a revocation endpoint. java-resource-server is a resource server implementation which also uses this library. It supports a userinfo endpoint defined in OpenID Connect Core 1.0 and includes an example of a protected resource endpoint, too. Use these reference implementations as a starting point of your own implementations of an authorization server and a resource server.
License
Apache License, Version 2.0
Maven
<dependency>
<groupId>com.authlete</groupId>
<artifactId>authlete-java-jaxrs</artifactId>
<version>${authlete-java-jaxrs.version}</version>
</dependency>
Please refer to the CHANGES.md file to know the latest version
to write in place of ${authlete-java-jaxrs.version}
.
Source Code
<code>https://github.com/authlete/authlete-java-jaxrs</code>
JavaDoc
<code>https://authlete.github.io/authlete-java-jaxrs</code>
Description
An authorization server is expected to expose the following endpoints.
- Authorization endpoint (RFC 6749, 3.1)
- Token endpoint (RFC 6749, 3.2)
This library provides utility classes to implement these endpoints. In addition, utility classes for endpoints listed below are included, too.
- JWK Set endpoint (OpenID Connect Core 1.0)
- Configuration endpoint (OpenID Connect Discovery 1.0)
- Revocation endpoint (RFC 7009)
- UserInfo endpoint (OpenID Connect Core 1.0)
- Introspection endpoint (RFC 7662)
Authorization Endpoint
AuthorizationRequestHandler
is a class to process an authorization
request from a client application. The class has handle()
method
which takes an instance of MultivaluedMap<String, String>
class
that holds request parameters of an authorization request.
public Response handle(MultivaluedMap<String, String> parameters)
throws WebApplicationException
An implementation of authorization endpoint can delegate the task to
process an authorization request to the handle()
method.
If you are using JAX-RS, it is easy to obtain an instance of
MultivaluedMap<String, String>
instance containing request
parameters and call the handle()
method with the instance.
But, the point exists at another different place. You are required
to prepare an implementation of AuthorizationRequestHandlerSpi
interface and pass it to the constructor of AuthorizationRequestHandler
class.
AuthorizationRequestHandlerSpi
is Service Provider Interface that
you are required to implement in order to control the behavior of the
handle()
method of AuthorizationRequestHandler
.
In summary, a flow in an authorization endpoint implementation will look like the following.
// Request parameters of an authorization request.
MultivaluedMap<String, String> parameters = ...;
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Your implementation of AuthorizationRequestHandlerSpi interface.
AuthorizationRequestHandlerSpi spi = ...;
// Create an instance of AuthorizationRequestHandler class.
AuthorizationRequestHandler handler =
new AuthorizationRequestHandler(api, spi);
// Delegate the task to process the authorization request to the handler.
Response response = handler.handle(parameters);
// Return the response to the client application.
return response;
The most important method defined in AuthorizationRequestHandlerSpi
interface is generateAuthorizationPage()
. It is called to generate
an authorization page. The method receives an instance of
AuthorizationResponse
class which represents a response from Authlete's
/api/auth/authorization
Web API. The instance contains information
that will be needed in generating an authorization page.
Response generateAuthorizationPage(AuthorizationResponse info);
See the JavaDoc and the reference implementation (java-oauth-server) for details.
Authorization Decision Endpoint
An authorization page displays information about an authorization request such as the name of the client application and requested permissions. An end-user checks the information and decides either to authorize or to deny the request. An authorization server receives the decision and returns a response according to the decision. Therefore, an authorization server must have an endpoint that receives the decision by an end-user in addition to the authorization endpoint.
AuthorizationDecisionHandler
is a class to process the decision.
The class has handle()
method as does AuthorizationRequestHandler
.
Also, its constructor requires an implementation of
AuthorizationDecisionHandlerSpi
interface as does the constructor
of AuthorizationRequestHandler
.
Token Endpoint
TokenRequestHandler
is a class to process a token request from a client
application. The class has handle()
method which takes two arguments of
MultivaluedMap<String, String>
and String
. The MultivaluedMap
argument represents request parameters and the String
argument is the
value of Authorization
header in the token request.
public Response handle(
MultivaluedMap<String, String> parameters, String authorization)
throws WebApplicationException
An implementation of token endpoint can delegate the task to process a
token request to the handle()
method.
The constructor of TokenRequestHandler
takes an implementation of
TokenRequestHandlerSpi
interface as does the constructor of
AuthorizationRequestHandler
.
In summary, a flow in a token endpoint implementation will look like the following.
// Request parameters of a token request.
MultivaluedMap<String, String> parameters = ...;
// The value of Authorization header.
String authorization = ...;
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Your implementation of TokenRequestHandlerSpi interface.
TokenRequestHandlerSpi spi = ...;
// Create an instance of TokenRequestHandler class.
TokenRequestHandler handler = new TokenRequestHandler(api, spi);
// Delegate the task to process the token request to the handler.
Response response = handler.handle(parameters, authorization);
// Return the response to the client application.
return response;
JWK Set Endpoint
An OpenID Provider is required to expose its JSON Web Key Set document (JWK Set) so that client application can (1) verify signatures by the OpenID Provider and (2) encrypt their requests to the OpenID Provider.
JwksRequestHandler
is a class to process a request to such an
endpoint. The class does not require any SPI implementation, so its
usage is simple.
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Create an instance of JwksRequestHandler class.
JwksRequestHandler handler = new JwksRequestHandler(api);
// Delegate the task to process a request.
Response response = handler.handle();
// Return the response to the client application.
return response;
Furthermore, BaseJwksEndpoint
class makes the task incredibly easier.
The following is an example of a complete implementation of a JWK Set
endpoint. The handle()
method of BaseJwksEndpoint
internally uses
JwksRequestHandler
.
@Path("/api/jwks")
public class JwksEndpoint extends BaseJwksEndpoint
{
@GET
public Response get()
{
// Handle the JWK Set request.
return handle(AuthleteApiFactory.getDefaultApi());
}
}
Configuration Endpoint
An OpenID Provider that supports OpenID Connect Discovery 1.0 must provide an OpenID Provider configuration endpoint that returns its configuration information in a JSON format. Details about the format are described in 3. OpenID Provider Metadata in OpenID Connect Discovery 1.0.
ConfigurationRequestHandler
is a class to process a request to
such a configuration endpoint. The class does not require any SPI
implementation, so its usage is simple.
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Create an instance of ConfigurationRequestHandler class.
ConfigurationRequestHandler handler = new ConfigurationRequestHandler(api);
// Delegate the task to process a request.
Response response = handler.handle();
// Return the response to the client application.
return response;
Furthermore, BaseConfigurationEndpoint
class makes the task incredibly
easier. The following is an example of a complete implementation of an
OpenID Provider configuration endpoint. The handle()
method of
BaseConfigurationEndpoint
internally uses ConfigurationRequestHandler
.
@Path("/.well-known/openid-configuration")
public class ConfigurationEndpoint extends BaseConfigurationEndpoint
{
@GET
public Response get()
{
// Handle the configuration request.
return handle(AuthleteApiFactory.getDefaultApi());
}
}
Note that the URI of a configuration endpoint is defined in 4.1. OpenID Provider Configuration Request in OpenID Connect Discovery 1.0. In short, the URI must be:
Issuer Identifier + /.well-known/openid-configuration
Issuer Identifier is a URL to identify an OpenID Provider, For example,
https://example.com
. For details about Issuer Identifier, see issuer
in 3. OpenID Provider Meatadata (OpenID Connect Discovery 1.0)
and iss
in 2. ID Token (OpenID Connect Core 1.0).
Revocation Endpoint
An authorization server may expose an endpoint to revoke access tokens and/or refresh tokens. RFC 7009 is the specification about such a revocation endpoint.
RevocationRequestHandler
is a class to process a revocation request.
The class has handle()
method which takes two arguments of
MultivaluedMap<String, String>
and String
. The MultivaluedMap
argument represents request parameters and the String
argument is
the value of Authorization
header in the revocation request.
public Response handle(
MultivaluedMap<String, String> parameters, String authorization)
throws WebApplicationException
An implementation of revocation endpoint can delegate the task to
process a revocation request to the handle()
method. Below is an
example of the handle()
method.
// Request parameters of a revocation request.
MultivaluedMap<String, String> parameters = ...;
// The value of Authorization header.
String authorization = ...;
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Create an instance of RevocationRequestHandler class.
RevocationRequestHandler handler = new RevocationRequestHandler(api);
// Delegate the task to process the revocation request to the handler.
Response response = handler.handle(parameters, authorization);
// Return the response to the client application.
return response;
Furthermore, BaseRevocationEndpoint
class makes the task incredibly
easier. The following is an example of a complete implementation of a
revocation endpoint. The handle()
method of BaseRevocationEndpoint
internally uses RevocationRequestHandler
.
@Path("/api/revocation")
public class RevocationEndpoint extends BaseRevocationEndpoint
{
@POST
@Consumes(MediaType.APPLICATION_FORM_URLENCODED)
public Response post(
@HeaderParam(HttpHeaders.AUTHORIZATION) String authorization,
MultivaluedMap<String, String> parameters)
{
// Handle the revocation request.
return handle(AuthleteApiFactory.getDefaultApi(), parameters, authorization);
}
}
UserInfo Endpoint
A userinfo endpoint is a protected resource endpoint that returns user information in JSON or JWT format. The behavior of this endpoint is described in 5.3. UserInfo Endpoint in OpenID Connect Core 1.0.
UserInfoRequestHandler
is a class to process a userinfo request.
The class has handle(String)
method which takes an access token.
An implementation of userinfo endpoint can delegate the task to
process a userinfo request to the handle()
method.
The constructor of UserInfoRequestHandler
class requires an
implementation of UserInfoRequestHandlerSpi
to control the
implementation-specific behaviors. The main purpose of the SPI
class is to collect claim values that will be embedded in a
response from a userinfo endpoint.
The following code snippet shows the usage of UserInfoRequestHandler
.
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Implementation of UserInfoRequestHandlerSpi interface.
UserInfoRequestHandlerSpi spi = ...;
// Create an instance of UserInfoRequestHandler class.
UserInfoRequestHandler handler = new UserInfoRequestHandler(api, spi);
// Access token contained in a userinfo request.
String accessToken = ...;
// Delegate the task to process the userinfo request to the handler.
Response response = handler.handle(accessToken);
// Return the response to the client application.
return response;
Furthermore, BaseUserInfoEndpoint
class makes the task incredibly
easier. The following is an example of an implementation of a
userinfo endpoint. The handle()
method of BaseUserInfoEndpoint
internally uses UserInfoRequestHandler
. Note that a userinfo
endpoint must accept an access token as a Bearer Token (RFC 6750).
@Path("/api/userinfo")
public class UserInfoEndpoint extends BaseUserInfoEndpoint
{
@GET
public Response get(
@HeaderParam(HttpHeaders.AUTHORIZATION) String authorization,
@QueryParam("access_token") String accessToken)
{
return handle(extractAccessToken(authorization, accessToken));
}
@POST
@Consumes(MediaType.APPLICATION_FORM_URLENCODED)
public Response post(
@HeaderParam(HttpHeaders.AUTHORIZATION) String authorization,
@FormParam("access_token") String accessToken)
{
return handle(extractAccessToken(authorization, accessToken));
}
private Response handle(String accessToken)
{
return handle(AuthleteApiFactory.getDefaultApi(),
new UserInfoRequestHandlerSpiImpl(), accessToken);
}
}
Introspection Endpoint
An authorization server may expose an endpoint to introspect access tokens and/or refresh tokens. RFC 7662 is the specification about such an introspection endpoint.
IntrospectionRequestHandler
is a class to process an introspection
request. The class has handle()
method which takes one argument of
type MultivaluedMap<String, String>
. The argument represents
request parameters in the introspection request.
public Response handle(MultivaluedMap<String, String> parameters)
throws WebApplicationException
An implementation of introspection endpoint can delegate the task
to process an introspection request to the handle()
method.
// Request parameters of an introspection request.
MultivaluedMap<String, String> parameters = ...;
// Implementation of AuthleteApi interface.
// See https://github.com/authlete/authlete-java-common for details.
AuthleteApi api = ...;
// Create an instance of IntrospectionRequestHandler class.
IntrospectionRequestHandler handler = new IntrospectionRequestHandler(api);
// Delegate the task to process the introspection request to the handler.
Response response = handler.handle(parameters);
// Return the response to the client application.
return response;
Furthermore, BaseIntrospectionEndpoint
class makes the task incredibly
easier. The following is an example of an implementation of an
introspection endpoint. The handle()
method of BaseIntrospectionEndpoint
internally uses IntrospectionRequestHandler
.
@Path("/api/introspection")
public class IntrospectionEndpoint extends BaseIntrospectionEndpoint
{
@POST
@Consumes(MediaType.APPLICATION_FORM_URLENCODED)
public Response post(MultivaluedMap<String, String> parameters)
{
// Note that RFC 7662 requires you implement your own means
// to protect the introspection endpoint. Therefore, check
// whether the API caller has necessary privileges to access
// this endpoint before calling the handle() method.
// Handle the introspection request.
return handle(AuthleteApiFactory.getDefaultApi(), parameters);
}
}
Note that 2.1. Introspection Request in RFC 7662 says
"To prevent token scanning attacks, the endpoint MUST also require
some form of authorization to access this endpoint". Therefore,
the actual implementation of your introspection endpoint must check
whether the API caller has necessary privileges before calling the
handle()
method.
Note
You can set a connection timeout value by calling setConnectionTimeout(int)
method of Settings
class which has been available since the version 2.9
of authlete-java-common. However, because there is no standard way to
set a connection timeout value before JAX-RS API 2.1 (which is a part of
Java EE 8), depending on implementations of JAX-RS Client API,
setConnectionTimeout(int)
may not work.
The implementation of setConnectionTimeout(int)
in this library
supports a few JAX-RS Client implementations such as Jersey. Please
see the source code for the exact list of supported implementations.
setReadTimeout(int)
method which has been available since the verison
2.10 of authlete-java-common has the same issue as
setConnectionTimeout(int)
does.
Summary
This library makes it easy to implement an authorization server that supports OAuth 2.0 and OpenID Connect and a resource server. See the JavaDoc and the reference implementations (java-oauth-server and java-resource-server) for details.
See Also
- Authlete - Authlete Home Page
- java-oauth-server - Authorization Server Implementation
- java-resource-server - Resource Server Implementation
- authlete-java-common - Authlete Common Library for Java
Contact
Purpose | Email Address |
---|---|
General | info@authlete.com |
Sales | sales@authlete.com |
PR | pr@authlete.com |
Technical | support@authlete.com |