[英]How to validate spring security antmatcher in a custom filter
[英]How to add a authorization filter to validate token and set security context in spring security?
我有一个使用 spring security 4 的 spring MVC 应用程序,我想根据请求中的 jwt 令牌添加授权。 我需要在过滤器中做的是
但是当我启动应用程序时,我收到一条错误消息,指出An AuthenticationManager is required 。 我不确定 UserDetails 服务如何适用于我的用例。 因此,我添加了一个虚拟返回值进行测试,因为没有 UserDetailsService 应用程序将无法工作。 对此有什么想法吗?
Spring 安全配置类
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(
prePostEnabled = true
)
public class SpringSecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
@Qualifier("applicationUserService")
UserDetailsService userDetailsService;
@Override
public void configure(AuthenticationManagerBuilder authenticationManagerBuilder) throws Exception {
SecurityContextHolder.setStrategyName(SecurityContextHolder.MODE_INHERITABLETHREADLOCAL);
authenticationManagerBuilder
.userDetailsService(userDetailsService)
.passwordEncoder(bCryptPasswordEncoder());
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable().authorizeRequests()
.antMatchers(HttpMethod.GET, "/home").hasAnyRole("ADMIN")
.antMatchers(HttpMethod.GET, "/login").hasAnyRole("ADMIN")
.anyRequest().authenticated()
.and()
.addFilter(new AuthorizationFilter(authenticationManager()))
.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
}
@Bean
public BCryptPasswordEncoder bCryptPasswordEncoder() {
return new BCryptPasswordEncoder();
}
授权过滤器类
public class AuthorizationFilter extends BasicAuthenticationFilter {
private static final Logger LOGGER = LoggerFactory.getLogger(AuthorizationFilter.class);
public AuthorizationFilter(AuthenticationManager authenticationManager) {
super(authenticationManager);
}
@Override
protected void doFilterInternal(HttpServletRequest req, HttpServletResponse response, FilterChain chain) throws IOException, ServletException {
LOGGER.info("Request Info : {}", req.getRequestURI());
// get token
// fetch details from external API
// set security context
List<GrantedAuthority> authorities = new ArrayList<>();
authorities.add((GrantedAuthority) () -> "ROLE_ADMIN");
SecurityContextHolder.getContext().setAuthentication(new UsernamePasswordAuthenticationToken("user1", null, authorities));
LOGGER.info("security context principle:{}", SecurityContextHolder.getContext().getAuthentication().getPrincipal().toString());
LOGGER.info("authorities context:{}", SecurityContextHolder.getContext().getAuthentication().getAuthorities().toString());
chain.doFilter(req, response);
}
UserDetailsService 实现
@Service
@Qualifier("applicationUserService")
public class ApplicationUserServiceImpl implements UserDetailsService {
@Override
public UserDetails loadUserByUsername(String s) throws UsernameNotFoundException {
return new User("sidath", "123", emptyList());
}
}
试试这个步骤
AbstractAuthenticationProcessingFilter
来评估请求和返回令牌。
public class AwesomeFilter extends AbstractAuthenticationProcessingFilter {
public AuthorizationFilter () {
super(new AntPathRequestMatcher("/your_post_url", "POST"));
}
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) {
// Evaluate request...
// Build your custom authentication token with the info
AwesomeToken token = new AwesomeToken();
// Authenticate token with authentication manager
return getAuthenticationManager().authenticate(token);
}
AuthenticationProvider
来支持你的AwesomeToken
。 Spring Security 将尝试“支持”这一点。public class AwesomeProvider implements AuthenticationProvider {
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
// Evaluate your custom token
// Call your API, etc
// Build your user authentication token details with authorities
Collection<? extends GrantedAuthority> auths = Collections.singletonList(new
SimpleGrantedAuthority("ROLE_ADMIN"));
AwesomeUserToken token = new AwesomeUserToken(auths);
// Return user token
return token;
}
@Override
public boolean supports(Class<?> authentication) {
return (AwesomeToken.class.isAssignableFrom(authentication));
}
@Override
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
auth
.authenticationProvider(new AwesomeProvider());
}
@Override
public void addFilters(HttpSecurity http, AuthenticationManager authenticationManager) throws Exception {
AwesomeFilter filter = new AwesomeFilter();
filter.setAuthenticationManager(authenticationManager);
http
.addFilterAfter(filter, UsernamePasswordAuthenticationFilter.class);
}
最后,当 Spring Security 检测到带有过滤器的请求时,它将尝试支持提供者,然后返回具有所需权限的令牌。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.