春季启动:我一直在获得org.springframework.security.authentication.BadCredentialsException:错误的凭证,我不知道为什么

时间:2018-09-07 10:33:57

标签: spring spring-boot spring-security

我试图用JWT配置SpringBoot应用程序,并且每次尝试使用JWTAuthenticationFilter.class进行身份验证时,都会收到错误的凭据异常。我觉得整个问题都是由Bycrpt造成的,因为用户link,抱怨同样的问题。但是当我实现他的代码时,它对我不起作用。

下面是我的spring安全配置器类:

@EnableGlobalMethodSecurity(prePostEnabled = true)

// @配置 @EnableWebSecurity 公共类JwtSecurityConfiguration扩展了WebSecurityConfigurerAdapter {

private final CustomerDetailsService customerDetailsService;

@Autowired
private JwtAuthenticationEntryPoint unauthorizedHandler;

@Autowired
public JwtSecurityConfiguration(CustomerDetailsService customerDetailsService) {
    this.customerDetailsService = customerDetailsService;
}

@Autowired
public PasswordEncoder passwordEncoder(){
    return new BCryptPasswordEncoder();
}

@Override
public void configure(WebSecurity web) throws Exception {
    web.ignoring().antMatchers("/resources/**");
}

@Override
protected void configure(HttpSecurity http) throws Exception {
    http.csrf().disable()
            .authorizeRequests()
            .antMatchers("/welcome/login").permitAll()
            .antMatchers("**/rest/**").authenticated()
            .and()
            .exceptionHandling().authenticationEntryPoint(unauthorizedHandler)
            .and()
            .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);

    http.addFilterBefore(new JWTAuthenticationFilter(authenticationManager(), 
            (BCryptPasswordEncoder) passwordEncoder()), UsernamePasswordAuthenticationFilter.class);
    http.addFilter(new JWTAuthorizationFilter(authenticationManager(),customerDetailsService));
    http
            .headers()
            .frameOptions().sameOrigin()
            .cacheControl();
}

}

这是JWTAuthenticationFiler类:

public class JWTAuthenticationFilter extends UsernamePasswordAuthenticationFilter {

private AuthenticationManager authenticationManager;

@Autowired
private BCryptPasswordEncoder bCryptPasswordEncoder;

public JWTAuthenticationFilter(AuthenticationManager authenticationManager, BCryptPasswordEncoder bCryptPasswordEncoder) {
    this.authenticationManager = authenticationManager;
    this.bCryptPasswordEncoder = bCryptPasswordEncoder;
}

@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
    try {
        User user = new ObjectMapper().readValue(request.getInputStream(), User.class);
        user.setPassword(bCryptPasswordEncoder.encode(user.getPassword()));
        return authenticationManager.authenticate(new UsernamePasswordAuthenticationToken(user.getUserName(), user.getPassword()));
    } catch (IOException e) {
        throw new RuntimeException(e);
    }
}

@Override
protected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response, FilterChain chain, Authentication authResult) throws IOException, ServletException {
    ZonedDateTime expirationTimeUTC = ZonedDateTime.now(ZoneOffset.UTC).plus(EXPIRATION_TIME, ChronoUnit.MILLIS);
    String token = Jwts.builder().setSubject(((User)authResult.getPrincipal()).getUserName())
            .setExpiration(Date.from(expirationTimeUTC.toInstant()))
            .signWith(SignatureAlgorithm.ES256, SECRET)
            .compact();
    response.getWriter().write(token);
    response.addHeader(HEADER, TOKEN_PREFIX + token);
}

@Override
protected void unsuccessfulAuthentication(HttpServletRequest request, HttpServletResponse response, AuthenticationException failed) throws IOException, ServletException {
    super.unsuccessfulAuthentication(request, response, failed);
    response.getWriter().write(failed.getMessage());
}

}

最后这是我的customerdetailservice类:

@Component
public class CustomerDetailsService implements UserDetailsService {

@Autowired
DefaultUserDAOService defaultUserDAOService;

@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
    User user = defaultUserDAOService.getByUsername(username);
    if (user == null) {
        throw new UsernameNotFoundException(String.format("No user found with username '%s'.", username));
    } else {
        return new org.springframework.security.core.userdetails.User(user.getUserName(), user.getPassword(),
                AuthorityUtils.createAuthorityList("ROLE_USER"));
    }
}

}

1 个答案:

答案 0 :(得分:0)

添加新用户时,您做了吗?

user.setPassword(bCryptPasswordEncoder.encode(user.getPassword()));

在将其保存到数据库之前? Spring不会为您做到这一点,您必须自己做。并确保使用相同的算法和盐(如果有的话)

检查您的数据库以查看真正保存的密码是什么。

希望这对您有所帮助。