Hi,
In a plain oauth2Login() application (keycloak as IDP for example), after https://github.com/spring-projects/spring-security/pull/16589 has been implemented, consider the following example :
@PostMapping("/fast")
public Map<String, Object> getOidcUserPrincipal @AuthenticationPrincipal OidcUser principal1) {
var principal2 = SecurityContextHolder.getContext().getAuthentication().getPrincipal();
return principal1.getClaims();
}
Once the OidcUserRefreshedEventListener#onApplicationEventhas been triggered, it's already too late for the AuthenticationPrincipalArgumentResolverto get the updated value, as it's not aware of the OidcUserRefreshedEvent.
So in the example above, with a very short Access Token Lifespan (let's say 2 minutes), principal1 might get the "before" refresh ID Token, whereas principal2 has the up-to-date value.
Shoot the endpoint before the refresh happens, values are in sync, wait a little, they are out-of-sync and so on.
Hope this is clear.
Thanks
Comment From: jgrandja
@mpalourdio Sorry but I don't fully understand the issue you are having.
Can you please put together a minimal sample or test that reproduces the issue and then I can look into it further.
Comment From: mpalourdio
Yup, not very clear, I admit.
AuthenticationPrincipalArgumentResolver is the "helper" that let us inject @AuthenticationPrincipal OidcUser xxxx as argument of a method in a controller (or whatever @Bean) like in my example.
The problem is: If a user tries to access the endpoint in which we inject @AuthenticationPrincipal OidcUser xxxx, and the OidcUserRefreshedEventListener must be triggered because of the IDP token refresh policy (one or 2 minutes lifespan), the OidcUser xxxxxx that is resolved as the method argument by AuthenticationPrincipalArgumentResolver, ie. @AuthenticationPrincipal OidcUser xxxx, will be resolved before OidcUserRefreshedEventListener#onApplicationEvent happens.
The consequence is that @AuthenticationPrincipal OidcUser xxxxx is outdated once we enter the method, because the listeners have been triggered after AuthenticationPrincipalArgumentResolver resolves @AuthenticationPrincipal OidcUser xxxx`
Why ? I suppose that before triggering all the OIDC refresh workflow, @AuthenticationPrincipal OidcUser xxxx is resolved very soon in order to be injected as method parameter.
Hope this is clearer.
Comment From: jgrandja
@mpalourdio I now understand the issue but it's still not clear how your specific flow is working. This is why I asked in the previous comment:
Can you please put together a minimal sample or test that reproduces the issue and then I can look into it further.
If this is indeed a bug, then a test would need to be provided regardless as part of the fix. I'll wait on the sample or test and will then look into this further.
Just to clarify:
and the
OidcUserRefreshedEventListenermust be triggered because of the IDP token refresh policy
OidcUserRefreshedEventListener is ONLY triggered when a refresh_token grant flow is performed by the client. The refresh_token grant flow is triggered via RefreshTokenOAuth2AuthorizedClientProvider through an OAuth2AuthorizedClientManager.