Use Keycloak Gatekeeper in front of backend API by setting enable-refresh-tokens=true

We have a single page app (SPA) that runs on <DOMAIN>. Calls to <DOMAIN>/graphql are rerouted to the backend. Both the frontend and backend are secured via a Keycloak Gatekeeper instance.

The idea was that the frontend and backend share the kc-access token.

Now, the access token expires in the backend Gatekeeper. If we refresh the spa in the browser the frontend is rerouted to Keycloak and a fresh access token is required. But if we do not refresh all POST requests to <DOMAIN>/graphql fail with a 307 status code when the token has expired. The browser does not know how to handle this. We see an “{“error”:“RESTEASY003065: Cannot consume content type”}”. If the content-type header of the POST is removed the error is “no client_id provided”, while the client_id is included in the query string.

Redirecting a POST request to Keycloak would probably not be the best solution. Cleaner would be if the backend refreshes it’s access token itself.

This is what we tried by adding a session state store to the backend’s Gatekeeper. We are using the following configuration:

    - --discovery-url=DISCOVERY_URL
    - --client-id=CLIENT_ID
    - --client-secret=****
    - --enable-refresh-tokens=true
    - --encryption-key=0123456789012345
    - --store-url=boltdb:///boltdb
    - --listen=0.0.0.0:3001
    - --verbose=true
    - --redirection-url=REDIRECTION_URL
    - --upstream-url=http://127.0.0.1:3000

This does create a /boltdb file in the Gatekeeper, but it does not seem to be used since the file does not change.

The backend’s Gatekeeper gives the following logging:

1.5716729131430433e+09 debug keycloak-gatekeeper/session.go:51 found the user identity {“id”: “b5b659cd-148e-4f23-bf2f-28e6f207f6c7”, “name”: “piet”, “email”: “”, “roles”: “offline_access,dashboard_viewer,uma_authorization,account:manage-account,account:manage-account-links,account:view-profile”, “groups”: “”}
1.5716729131462774e+09 info keycloak-gatekeeper/middleware.go:154 accces token for user has expired, attemping to refresh the token {“client_ip”: “****”, “email”: “”}
1.5716729131463811e+09 error keycloak-gatekeeper/middleware.go:161 unable to find a refresh token for user {“client_ip”: “**”, “email”: “”, “error”: “no session state found”}

So we are “unable to find a refresh token for user” because there is “no session state found” according to the logging.

Anybody any idea how to enable token refresh?

Also posted on stackoverflow: https://stackoverflow.com/questions/58490152/use-keycloak-gatekeeper-in-front-of-backend-api