春季安全性-jwt请求过滤器可验证和认证会话,但主体为null

时间:2019-11-30 14:59:20

标签: spring spring-boot spring-security

将我的Spring Boot从2.0.3更新为2.2.1后,我的Spring Security配置以某种方式停止工作。 设置如下-我希望通过过滤JWT令牌并创建UserDetails的请求过滤器来处理所有请求。因此配置非常简单:

@Configuration
@EnableWebSecurity
public class NoAuthConfigurationAdapter extends WebSecurityConfigurerAdapter {
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
                .csrf().disable()
                .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS)
                .and()
                .authorizeRequests()
                .antMatchers("/**").permitAll()
                .anyRequest().authenticated();


    }
}

和过滤器类

@Component
@Order(Ordered.HIGHEST_PRECEDENCE)
public class JwtRequestFilter extends OncePerRequestFilter {
    private static final Logger log = LoggerFactory.getLogger(JwtRequestFilter.class);

    @Autowired
    private JwtUserDetailsService jwtUserDetailsService;
    @Autowired
    private JwtUtils jwtTokenUtil;
    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
            throws ServletException, IOException {
        String requestTokenHeader = "";
        try{
            requestTokenHeader = WebUtils.getCookie(request, "token").getValue();
        } catch (NullPointerException ex ){}
        if (requestTokenHeader != null && requestTokenHeader.contains(".")) {
            jwtToken = requestTokenHeader;
            try {
                username = jwtTokenUtil.getUsernameFromToken(jwtToken);
            } catch (IllegalArgumentException e) {
                log.error("Unable to get JWT Token");
            } catch (ExpiredJwtException e) {
                log.error("JWT Token has expired");
            }
        }  
        if (username != null ) {
            UserDetails userDetails = null;
            userDetails = this.jwtUserDetailsService.loadUserByUsername(username);
            if (jwtTokenUtil.validateToken(jwtToken, userDetails)) {
                    UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken = new UsernamePasswordAuthenticationToken(
                            userDetails, null, userDetails.getAuthorities());
                    usernamePasswordAuthenticationToken
                            .setDetails(new WebAuthenticationDetailsSource().buildDetails(request));
                    SecurityContextHolder.getContext().setAuthentication(usernamePasswordAuthenticationToken);
            }
        } else {
            response.setStatus(HttpServletResponse.SC_FORBIDDEN);
            return;
        }
        chain.doFilter(request, response);

    }
    @Override
    protected boolean shouldNotFilter(HttpServletRequest request) {
        String[] AUTH_WHITELIST = {
                "/v2/auth/",
                "/api/packetdiscovery"
        };
        String path = request.getServletPath();
        return (StringUtils.startsWithAny(path, AUTH_WHITELIST));
    }
}

通过调试,我可以看到一切正常,直到请求到达NullPointerException上抛出Principal的Controller为止

@PreAuthorize("hasAuthority('ROLE_USER')")
@GetMapping(value = "/userinfo")
public ResponseEntity<SessionOwner> getSesstionOwner(Principal user) {
    return dashboardService.getSessionOwner(user.getName());

}

有人可以给我一些处理建议吗?

0 个答案:

没有答案