The goal of this SPI (Service Provider Interface) for Keycloak is to create a browser session by setting all relevant cookies out of a valid JWT (Json Web Token).
Useful to provide SSO (Single Sign On) capabilities for legacy web application to a new web application being authenticated by Keycloak.
Important to note is that this SPI expects the legacy web application to be able to access a valid JWT. This might occur if you need to introduce new features in legacy web applications.
Prerequisite is a valid JWT (access token) obtained from your Keycloak IDM.
With that valid JWT you may invoke within a browser the API provided by this SPI. E.g. with the following example JS code:
// config
var providerUrl = "http://localhost:5080";
var realm = "master";
var targetClientForNewSession = "application";
var jwt = "eyJhbGciOiJSUzI1NiIs.....";
// invocation
var xmlHttp = new XMLHttpRequest();
xmlHttp.open("GET", `${providerUrl}/auth/realms/${realm}/browser-session/init?publicClient=${targetClientForNewSession}`, false);
xmlHttp.withCredentials = true;
xmlHttp.setRequestHeader("Authorization", "Bearer " + jwt);
xmlHttp.send(null);
return xmlHttp.responseText;
This will create a new user session for the provided client and set the Keycloak cookies so that after loading / redirecting to the URL of the application secured by Keycloak no prompt to login will appear.
It contains of one single API request:
HTTP Method | Path | Request Header | Description |
---|---|---|---|
GET | baseUrl /auth/realms/realm /browser-session/init?publicClient=targetClientName |
Ensure Authorization: Bearer with the JWT |
baseUrl : URL to Keycloak e.g. https://your.keycloak.example.org realm : realm to be used e.g. master targetClientName : public client (defined in Keycloak) for which to start the browser session |
mvn clean package
keycloak-spi-browser-session-api-1.0.jar
to the deployments
folder of KeycloakThere is no real configuration for the SPI itself. It relies on parameters of the SPI API call and Keycloak settings.
user
the one identified by the JWT will be usedrealm
needs to be passed as path element in the browser-session API URL, see examplepublicClient
specifies the public client to be used for new session, see examplepublicClient
in Keycloak are used. Please note that *
should be avoided in production environments.Start Keycloak with PostgreSQL as the IDM Provider, a start-app
and dest-app
.
docker-compose up
The start-app
is the starting point e.g. an application where a user is already logged in and has a valid JWT. Please open http://localhost:5082. For sake of simplicity no authentication takes place here.
The dest-app
is just a demo website secured with keycloak.js.
The goal is to initiate a browser session from start-app
only having a valid JWT to dest-app
.
Please configure Keycloak as follows:
user
/ bitnami
)dest-app
with access type public
and Web Origin http://localhost:5082
and/or *
private
with access type confidential
testuser
with password Test123!
Build and deploy it
mvn clean package && docker cp target/keycloak-spi-browser-session-api-1.0.jar keycloak-spi-browser-session-api-keycloak-1:/opt/bitnami/keycloak/standalone/deployments/keycloak-spi-browser-session-api-1.0.jar
Run the test by generating a new access token and placing it into the demo/start-app/index.html
. This is only for demo purposes.
CLIENT_ID=private
# ... please change CLIENT_SECRET accordingly as it gets generated by Keycloak
CLIENT_SECRET=8b3576db-6492-4238-aa60-d7c71a9663f7
API_USER=testuser
API_PASSWORD='Test123!'
ACCESS_TOKEN=$(curl -s -d "client_id=$CLIENT_ID" -d "client_secret=$CLIENT_SECRET" --data-urlencode "username=$API_USER" --data-urlencode "password=$API_PASSWORD" -d 'grant_type=password' 'http://localhost:5080/auth/realms/master/protocol/openid-connect/token' | jq -r '.access_token')
sed -i -E 's#var jwt = ".*$#var jwt = "'"$ACCESS_TOKEN"'";#' demo/start-app/index.html
And please don't forget to reload http://localhost:5082
APACHE LICENSE, VERSION 2.0