-
Notifications
You must be signed in to change notification settings - Fork 6k
Reactive equivalents for security expression handling and url-based access control #5867
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
@danielfernandez Thanks for reaching out. There is not SpEL expression support for request mappings within WebFlux applications. This largely has to do with the fact that we can now use method references and lambdas. For example: @Bean
SecurityWebFilterChain springSecurityFilterChain(ServerHttpSecurity http) {
http
// ...
.authorizeExchange()
.pathMatchers("/users").access(this::isRob)
.anyExchange().authenticated()
.and()
.httpBasic().and()
.formLogin()
.loginPage("/login");
return http.build();
}
private Mono<AuthorizationDecision> isRob(Mono<Authentication> authentication,
AuthorizationContext authorizationContext) {
return authentication
.map(Authentication::getName)
.map(username -> username.startsWith("rob@"))
.map(AuthorizationDecision::new);
} The reactive bits have changed the authorization model slightly as well. Now we use Eventually we should provide a way for APIs like Thymeleaf, but at the moment it does not exist (eventually we would just need to expose the |
Thanks a lot for the quick answer @rwinch. So it seems for that in WebFlux apps Thymeleaf should disable the part of its |
That makes sense to not support authorization at this point. I'm curious how you are able to interact with the authentication since it is available as a |
Short answer: with quite a lot of pain :) Long answer: The key restriction is that Thymeleaf cannot resolve any reactive variables on-the-fly during template execution (i.e. except for the data driver in data-driven mode, but that's not the case), so any possible solutions had to involve the resolution of The key was, controller advices weren't an option in this case because I wanted this to be transparent for the user, to work out-of-the-box just by adding the Spring Security dialect. At the same time I was very limited in how deep into Thymeleaf I could insert code for this because: 1. The So in the end what I did was to build on the already existing mechanism of Thymeleaf dialects providing execution attributes ( Extending this support a bit, these execution attribute objects can not only be objects, but also You can see the relevant code for this here: https://github.com/thymeleaf/thymeleaf-spring/blob/19276997cf349ed08c5b79cee227f36c5db751ab/thymeleaf-spring5/src/main/java/org/thymeleaf/spring5/view/reactive/ThymeleafReactiveView.java#L338-L365 So thanks to this mechanism, now the This execution attribute specified by final Function<ServerWebExchange, Mono<SecurityContext>> secCtxInitializer =
(exchange) -> ReactiveSecurityContextHolder.getContext(); So, again, limitation: that Unfortunately all of this took me multiple attempts, a couple of failed implementations and several months of Thymeleaf work (very intermittent, of course — we even had a new baby in the meantime and I sort of got distracted 😄), but finally it seems to be all starting to come together and I should be able to release this soon. This all made me delay a lot the release of Thymeleaf 3.0.10 in fact, because I needed support for this scenario from the core. In fact, 3.0.10 is not yet released because I first want to be really sure that what was made does work for the entire Spring Security 5 + WebFlux scenario… |
By the way, I finally went for only allowing a minimal set of authorization expressions in These expressions are too useful to lose them (esp. |
Thanks for the response! I'm looking forward to the automatic support of CSRF and authentication! |
@rwinch I'm happy to have a go but if you have any more pointers that would helpful? I'll look at basic SpEL but I like the |
@RobMaskell I think that is the problem. We don't know the expressions ahead of time and they would need to be evaluated eagerly. I think from the security side, the first thing we would need to do is support a SpEL implementation of This would at least empower Thymeleaf to be able to enhance things on their side to support authorization. Perhaps @danielfernandez has some ideas as to how that would be done. |
Summary
In the new
thymeleaf-extras-springsecurity5
I'm trying to make all the functionality already existing for Servlet-based applications available also for WebFlux ones.But I'm unable to find in the reactive side of Spring Security any equivalents for the functionality providen by
SecurityExpressionHandler<FilterInvocation>
orWebInvocationPrivilegeEvaluator
in Servlet-based web applications. These allow Thymeleaf to evaluate Spring Security expressions such ashasRole(x)
, and also perform url-based access control (privilege evaluator).Also, digging into Spring Security's code, I cannot find any infrastructure for quickly developing reactive equivalents to these. For example, not only there seems to be no reactive object to be used as an expression evaluation root, but actually there is no reactive invocation class --let's say a hypothetic
WebFilterInvocation
-- that would encapsulate the equivalentServerWebExchange
in order to support matching operations…Am I looking in the wrong place (the
spring-security-web
module)? Was this left out on purpose? If not, maybe with some detail on what would be needed I might be able to help, at least with the not-so-low-level infrastructure...Version
Spring Security
5.1.0.BUILD-SNAPSHOT
The text was updated successfully, but these errors were encountered: