I'm using asynchronous methods in my service (Spring 3 @Async
annotation). And I've got a problem - spawned thread doesn't have security context. Cause of it is Spring Security by default uses SecurityContextHolder.MODE_THREADLOCAL
strategy for its context holder. But I need to use SecurityContextHolder.MODE_INHERITABLETHREADLOCAL
strategy. For the moment I set up strategy in my AuthenticationSuccessHandler. But in my point of view it's not a good practice.
So how can I set it up in context configuration file?
Version of spring security is 3.0.0.
To, let's manually trigger authentication and then set the resulting Authentication object into the current SecurityContext used by the framework to hold the currently logged-in user: UsernamePasswordAuthenticationToken authReq = new UsernamePasswordAuthenticationToken(user, pass); Authentication auth = authManager.
The SecurityContextHolder is a helper class, which provide access to the security context. By default, it uses a ThreadLocal object to store security context, which means that the security context is always available to methods in the same thread of execution, even if you don't pass the SecurityContext object around.
The HttpServletRequest.getUserPrincipal() will return the result of SecurityContextHolder.getContext().getAuthentication() . This means it is an Authentication which is typically an instance of UsernamePasswordAuthenticationToken when using username and password based authentication.
You can set the environment variable spring.security.strategy
to MODE_INHERITABLETHREADLOCAL
. You could also have a simple bean that during your web applications startup calls SecurityContextHolder.setStrategyName(SecurityContextHolder.MODE_INHERITABLETHREADLOCAL)
and initialize that value in your context configuration file.
SecurityContextHolder API
The java config for @viator 's answer if it helps you.
@Bean public MethodInvokingFactoryBean methodInvokingFactoryBean() { MethodInvokingFactoryBean methodInvokingFactoryBean = new MethodInvokingFactoryBean(); methodInvokingFactoryBean.setTargetClass(SecurityContextHolder.class); methodInvokingFactoryBean.setTargetMethod("setStrategyName"); methodInvokingFactoryBean.setArguments(new String[]{SecurityContextHolder.MODE_INHERITABLETHREADLOCAL}); return methodInvokingFactoryBean; }
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With