Repository navigation
Description
Hi,
Keycloak has some non-standard behavior that we need to support: The KEYCLOAK-15234 bug report is about Single-Sign-Off not working with non-Keycloak adapters (like scribejava). Keycloak allows clients to register an "Admin URL" that gets called when users log off. Unfortunately, it only works when a custom client_session_state=${sessionId} POST parameter is added when calling the token endpoint to exchange a code for a token.
The OAuth20Service service currently does not provide any means to add custom parameters to any of the getAccessToken() methods.
The question is whether we should provide a PR for this project or work around it in application code. We prefer preparing a PR and I would like to hear the project's opinion on how to proceed. We're happy to provide a PR, but would like the approach to be approved beforehand, so we don't waste effort and end up with a fork that never gets merged. There are at least a couple of ways this could be made possible:
Change protected -> public for 4 methods in OAuth2AccessToken
If the three sendAccessTokenRequest* methods and createAccessTokenRequest were changed from protected to public, then instead of:
OAuth2AccessToken accessToken = service.getAccessToken(code)
our application code could now:
OAuthRequest request = service.createAccessTokenRequest(AccessTokenRequestParams.create(code));
request.addParameter("client_session_state", sessionId)
OAuth2AccessToken accessToken = service.sendAccessTokenRequestSync(request)
In my opinion this the cleanest, most flexible and most elegant solution, but there is also:
A new KeycloakService implements public OAuth2AccessToken getAccessToken*(..., String clientSessionState) methods
Modify KeycloakApi to override method public OAuth20Service createService so it creates a KeycloakService (like e.g. FacecbookApi creates a FacebookService). KeycloakService then provides a (number of) public OAuth2AccessToken getAccessToken(String code, String clientSessionState) method(s) that add the extra parameter.
There are already 6 methods with various parameter and sync/async combinations. Should there now be 12? The existing 6 plus versions with the extra parameter? This is a maintainability nightmare... It also makes getAccessToken different from e.g. the revokeToken family in that respect that "only" has 6 variations.
Also, ServiceBuilderOAuth20's build() method returns a OAuth20Service so the application would have to cast the result of build() to KeycloakService to access these 6 new methods. :-(
OAuth2AccessToken gets new getAccessToken(..., Map<String, String> extraParameters) methods
Here instead of creating a custom KeycloakService we add more generic methods to the base class. Again, we'll end up with 12 methods instead of the current 6.
I don't like this for the same maintainability reasons.
Application Level Workaround - no scribejava changes
Essentially we derive from KeycloakApi to just provide strictly what we need:
We Implement our own OurKeycloakApi that returns an OurKeycloakService that implements the one extra method we need. That is for sure the easiest for us to do, but it doesn't help out the next Keycloak user that runs into this problem.
We'll do this unless there is consensus here on what a PR should look like. We just think it is a shame others have to do similar customizations to get logging out to work properly.
Activity
mmejiadeveloper commentedon Sep 8, 2020
Hi, some questions:
Is this still working? Have you reproducible steps? Can this be reproduced with postman in a quick way?
pmorch commentedon Nov 17, 2020
Hi @mmejiadeveloper, sorry I misted your post. It must have gotten lost in my inbox.
I'm not sure what you mean. Yes this is still a problem as described in Keycloak up until and including version 11.x. In version 12 (as yet unreleased), logout can also be done in a completely other way, see KEYCLOAK-15234. But still support for keycloak < 12 will require this.
Absolutely. I did that back when I was experimenting with this. I don't have those postman files handy any longer though. It wasn't difficult to do.
pmorch commentedon Nov 18, 2020
Since I didn't hear from anybody other than @mmejiadeveloper, and nothing about which approach would be preferred, I've made a workaround using the "Application Level Workaround - no scribejava changes" approach. If anybody ever needs it, it is to be found as:
Workaround for scribejava: Keycloak: Adding a custom field for the
tokenendpoint POST to get Single-Sign-Off to work #980My itch has been scratched. If maintainers decide not to do anything more, I'm fine with closing this issue.
kullfar commentedon Mar 10, 2021
Hi, @pmorch.
Sorry for the delay.
I have investigated the problem.
Actually I like the variant "Change protected -> public for 4 methods in OAuth2AccessToken".
But I have another option. We have class AccessTokenRequestParams (https://github.com/scribejava/scribejava/blob/master/scribejava-core/src/main/java/com/github/scribejava/core/oauth/AccessTokenRequestParams.java).
It is used as argument for a method getAccessToken (https://github.com/scribejava/scribejava/blob/master/scribejava-core/src/main/java/com/github/scribejava/core/oauth/OAuth20Service.java#L90).
It can be used to hold extra params (without adding new overloaded getAccessToken methods).
So, the usage will be like this
or even
(I think both methods should be added)
And it will keep the public OAuth20Service API cleaner but less customizable (there will be no way to play around with the OAuthRequest somehow else before sending it to the API provider).
implement possibility to add extra parameters to Access Token Request…
kullfar commentedon Mar 12, 2021
I have added AccessTokenRequestParams.[add|set]ExtraParamater[s] methods.
4e90348
kullfar commentedon Mar 12, 2021
I'm closing this issue, feel free to reopen or create another one, if this change didn't help you.