Understanding the sample application
The sample application consists of two parts – a frontend web application and a backend REST API.
The frontend web application is a single-page application written in JavaScript. As we want to focus on what Keycloak can offer, the application is very simple. Furthermore, to make it as simple as possible to run the application, it uses Node.js. The application provides the following features:
- Login with Keycloak.
- It displays the user’s name.
- It displays the user’s profile picture, if available.
- It shows the ID token.
- It shows the Access token.
- It refreshes the tokens.
- It invokes the secured endpoint provided by the backend.
The backend REST API is also very simple and is implemented with Node.js. It provides a REST API with two endpoints:
/public
: A publicly available endpoint with no security/secured
: A secured endpoint requiring an access token with themyrealm
global role
Node.js is used for example applications as we want to make the code as easy to understand and as simple to run as possible, regardless of what programming language you are familiar with.
The following diagram shows the relationship between the frontend, the backend, and Keycloak. The frontend authenticates the users using Keycloak and then invokes the backend, which uses Keycloak to verify that the request should be permitted:
Figure 2.1: Application overview
Now that you have a basic understanding of the sample application, let’s look at some more details on how it all comes together.
When the user clicks on the login button in the frontend application, the browser is redirected to the Keycloak login page. The user then authenticates with Keycloak, before the browser is redirected back to the application with a special code called an authorization code. The application then invokes Keycloak to exchange the authorization code for the following tokens:
- An ID token: This provides the application information pertaining to the authenticated user.
- An access token: The application includes this token when making a request to a service, which allows the service to verify whether the request should be permitted.
- A refresh token: Both the ID and the access token have short expirations – by default, 5 minutes. The refresh token is used by the application to obtain new tokens from Keycloak.
The flow described is what is known as the authorization code flow in OpenID Connect. If you are not already familiar with OAuth 2.0 or OpenID Connect, they can be a bit daunting at first, but once you become familiar with them, they are actually quite simple and easy to understand.
To help visualize the login process, a simplified sequence diagram is provided as follows:
Figure 2.2: Authorization code flow in OpenID Connect simplified
The steps in this diagram are as follows:
- The User clicks on the login button.
- The application redirects to the Keycloak Login page.
- The Keycloak login page is displayed to the User.
- The User fills in the username and password and submits the results to Keycloak.
- After verifying the username and password, Keycloak sends the Authorization code to the application.
- The application exchanges the Authorization code for an ID token and an access token. The application can now verify the identity of the user by inspecting the ID token.
By delegating the authentication of the user to Keycloak, the application does not have to know how to authenticate the user. This is especially relevant when the authentication mechanisms change. For example, two-factor authentication can be enabled without having to make changes to the application. This also means the application does not have access to the user’s credentials.
The next step related to Keycloak is when the frontend invokes the backend. The backend REST API has a protected endpoint that can only be invoked by a user with the global role, myrole
.
To be completely accurate, the frontend is granted permissions to invoke the backend on behalf of the user. This is part of the beauty of OAuth 2.0. An application does not have access to do everything that the user is able to do, only what it should be able to do.
When the frontend makes a request to the backend, it includes the access token within the request. By default, Keycloak uses JSON Web Signature (JWS) as the token format. These types of tokens are often referred to as non-opaque tokens, meaning the contents of the token are directly visible to the application.
The token also includes a digital signature, making it possible to verify that the token was indeed issued by Keycloak. In essence, this means that the backend can both verify the token and read the contents without a request to Keycloak, resulting in less demand on the Keycloak server and lower latency when processing requests to the backend.
To help visualize what happens when the frontend sends a request to the backend, take a look at the following diagram:
Figure 2.3: Secured request from the frontend to the backend simplified
The steps in the diagram are as follows:
- The Backend retrieves Keycloak’s public keys. The Backend does not need to do this for all requests to the Backend, but can instead cache the keys in memory.
- The Frontend sends a request to the Backend, including the access token.
- The Backend uses the public keys it retrieved earlier to verify that the access token was issued by a trusted Keycloak instance, and then verifies that the token is valid and that the token contains the role
myrole
. - The Backend returns the results to the Frontend.
You now have a basic understanding of how the sample applications are secured with Keycloak. In the next section, you will learn how to run the sample application.