Java “春季安全投掷”;原因:不合格的证书”;UI中出错,但在登录期间正确查找用户

Java “春季安全投掷”;原因:不合格的证书”;UI中出错,但在登录期间正确查找用户,java,spring,spring-boot,spring-security,Java,Spring,Spring Boot,Spring Security,我用尽了我能找到的每一篇文章和博客,试图找出我做错了什么。所以,现在我请求你的帮助。我正在构建一个SpringBoot应用程序,并利用SpringSecurity进行用户管理/身份验证。我想我已经正确设置了所有内容,但是在登录期间,Spring安全性每次都会重定向到登录失败URL(/login?error),抛出错误: 您的登录尝试未成功,请重试。 原因:凭据不正确 服务器日志中没有任何说明或有用的内容。作为调试的一部分,我添加了一系列日志记录,以确认: 正在数据库中找到该用户(通过电子邮件,在

我用尽了我能找到的每一篇文章和博客,试图找出我做错了什么。所以,现在我请求你的帮助。我正在构建一个SpringBoot应用程序,并利用SpringSecurity进行用户管理/身份验证。我想我已经正确设置了所有内容,但是在登录期间,Spring安全性每次都会重定向到登录失败URL(/login?error),抛出错误:

您的登录尝试未成功,请重试。 原因:凭据不正确

服务器日志中没有任何说明或有用的内容。作为调试的一部分,我添加了一系列日志记录,以确认:

  • 正在数据库中找到该用户(通过电子邮件,在配置中将
    usernameParameter
    设置为电子邮件
  • Spring Security的
    userDetails.User
    从其
    new
    构造函数创建正确的用户(我已经记录了用户的详细信息)
  • 我是框架的新手,所以我可能忽略了一些东西,这是我非常感谢您的帮助的地方。我已经在下面包括了我的安全配置和用户服务(我已经清除了日志,以便您阅读)——请告诉我是否还有其他内容会有所帮助。提前谢谢

    SecurityConfiguration.java

    public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
    
    @Resource(name = "userService")
    private UserDetailsService userDetailsService;
    
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                .antMatchers("/test").hasRole("USER")
                .antMatchers("/**").permitAll()
                .and().formLogin().usernameParameter("email").defaultSuccessUrl("/register_success");
        http.authorizeRequests()
                .antMatchers("/resources/**").permitAll();
        super.configure(http);
    }
    
    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder authenticationManagerBuilder)
                                throws Exception {
        authenticationManagerBuilder.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
    }
    
    // Define this bean so autowired can find and use it (fixes complaining error)
    @Bean
    PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }
    
    @Bean
    BCryptPasswordEncoder bCryptPasswordEncoder() {
        return new BCryptPasswordEncoder();
    }
    }
    
    @Service("userService")
    public class UserService implements UserDetailsService {
    
    private static final String LOG_TAG = UserService.class.getSimpleName();
    private Logger logger = LoggerFactory.getLogger(LOG_TAG);
    
    private UserRepository userRepository;
    
    @Autowired
    SessionFactory sessionFactory;
    
    @Autowired
    public UserService(UserRepository userRepository) {
        this.userRepository = userRepository;
    }
    
    // Must provide email address as username argument
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        User user = userRepository.findByEmail(username);
        if (user == null) {
            throw new UsernameNotFoundException("There is no user with this email address.");
        }
        org.springframework.security.core.userdetails.User springUser = new org.springframework.security.core.userdetails.User(
                user.getEmail(), user.getPassword(), getAuthority());
        return springUser;
    }
    
    public User findByEmail(String email) {
        return userRepository.findByEmail(email);
    }
    
    public User findByConfirmationToken(String confirmationToken) {
        return userRepository.findByConfirmationToken(confirmationToken);
    }
    
    @Transactional
    public List<User> findAll() {
        Criteria criteria = sessionFactory.openSession().createCriteria(User.class);
        return (List<User>) criteria.list();
    }
    
    public void saveUser(User user) {
        userRepository.save(user);
    }
    
    //TODO: Figure out how to use this properly
    public List getAuthority() {
        return Arrays.asList(new SimpleGrantedAuthority("ROLE_USER"));
    }
    }
    
    UserService.java

    public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
    
    @Resource(name = "userService")
    private UserDetailsService userDetailsService;
    
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                .antMatchers("/test").hasRole("USER")
                .antMatchers("/**").permitAll()
                .and().formLogin().usernameParameter("email").defaultSuccessUrl("/register_success");
        http.authorizeRequests()
                .antMatchers("/resources/**").permitAll();
        super.configure(http);
    }
    
    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder authenticationManagerBuilder)
                                throws Exception {
        authenticationManagerBuilder.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
    }
    
    // Define this bean so autowired can find and use it (fixes complaining error)
    @Bean
    PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }
    
    @Bean
    BCryptPasswordEncoder bCryptPasswordEncoder() {
        return new BCryptPasswordEncoder();
    }
    }
    
    @Service("userService")
    public class UserService implements UserDetailsService {
    
    private static final String LOG_TAG = UserService.class.getSimpleName();
    private Logger logger = LoggerFactory.getLogger(LOG_TAG);
    
    private UserRepository userRepository;
    
    @Autowired
    SessionFactory sessionFactory;
    
    @Autowired
    public UserService(UserRepository userRepository) {
        this.userRepository = userRepository;
    }
    
    // Must provide email address as username argument
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        User user = userRepository.findByEmail(username);
        if (user == null) {
            throw new UsernameNotFoundException("There is no user with this email address.");
        }
        org.springframework.security.core.userdetails.User springUser = new org.springframework.security.core.userdetails.User(
                user.getEmail(), user.getPassword(), getAuthority());
        return springUser;
    }
    
    public User findByEmail(String email) {
        return userRepository.findByEmail(email);
    }
    
    public User findByConfirmationToken(String confirmationToken) {
        return userRepository.findByConfirmationToken(confirmationToken);
    }
    
    @Transactional
    public List<User> findAll() {
        Criteria criteria = sessionFactory.openSession().createCriteria(User.class);
        return (List<User>) criteria.list();
    }
    
    public void saveUser(User user) {
        userRepository.save(user);
    }
    
    //TODO: Figure out how to use this properly
    public List getAuthority() {
        return Arrays.asList(new SimpleGrantedAuthority("ROLE_USER"));
    }
    }
    
    @Service(“用户服务”)
    公共类UserService实现UserDetailsService{
    私有静态最终字符串LOG_TAG=UserService.class.getSimpleName();
    专用记录器Logger=LoggerFactory.getLogger(日志标签);
    私有用户存储库用户存储库;
    @自动连线
    会话工厂会话工厂;
    @自动连线
    公共用户服务(用户存储库用户存储库){
    this.userRepository=userRepository;
    }
    //必须提供电子邮件地址作为用户名参数
    public UserDetails loadUserByUsername(字符串用户名)引发UsernameNotFoundException{
    User=userRepository.findByEmail(用户名);
    if(user==null){
    抛出新的UsernameNotFoundException(“没有具有此电子邮件地址的用户”);
    }
    org.springframework.security.core.userdetails.User springUser=new org.springframework.security.core.userdetails.User(
    user.getEmail()、user.getPassword()、getAuthority());
    返回用户;
    }
    公共用户findByEmail(字符串电子邮件){
    返回userRepository.findByEmail(电子邮件);
    }
    公共用户FindByConfigurationToken(字符串确认Token){
    返回userRepository.findbyconfimationtoken(confirmationToken);
    }
    @交易的
    公共列表findAll(){
    Criteria=sessionFactory.openSession().createCriteria(User.class);
    返回(列表)条件。列表();
    }
    公共void saveUser(用户){
    userRepository.save(用户);
    }
    //TODO:找出如何正确使用此选项
    公共列表管理局(){
    返回array.asList(新的SimpleGrantedAuthority(“角色用户”);
    }
    }
    
    添加新用户时,需要使用PasswordEncoder加密密码

    像这样:

    @Autowired
    private BCryptPasswordEncoder passwordEncoder;
    public void saveUser(User user) {
        user.setPassword(passwordEncoder.encode(user.getPassword()));
        userRepository.save(user);
    }
    

    是否确定存储在数据库中的密码?密码必须以
    BcryptPassword
    格式存储在数据库中。密码不应作为普通字符串存储。@Cataclysm是的,我已记录了密码并直接在数据库中查看了它。密码确实已编码。@Cataclysm我现在还验证了原始密码是否正确刀剑输入与数据库中解密的密码匹配。当用户准备保存时,我在注册控制器中加密密码。
    //设置新密码user.setPassword(bCryptPasswordEncoder.encode(requestParams.get(“password”).toString());