我似乎不明白我的代码有什么问题。我正在尝试使用Springboot安全性登录,一切似乎都正确,并且可以在控制台上看到我的用户名和密码。谁能告诉我我怎么了?
这是我的SecSecurityConfig类
package com.scanapp.config;
import com.scanapp.repositories.RoleRepository;
import com.scanapp.services.UserDetailsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import
org.springframework.security.authentication.dao.DaoAuthenticationProvider;
import org.springframework.security.crypto.password.PasswordEncoder;
@Configuration
@EnableWebSecurity
public class SecSecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private RoleRepository roleRepository;
@Autowired
@Qualifier("myuserdet")
UserDetailsService userDetailsService;
protected void init(AuthenticationManagerBuilder auth) throws Exception {
System.out.println("I'm here");
auth.authenticationProvider(authProvider());
}
@Bean
public DaoAuthenticationProvider authProvider() {
System.out.println("got here");
DaoAuthenticationProvider authProvider = new
DaoAuthenticationProvider();
authProvider.setUserDetailsService(userDetailsService);
authProvider.setPasswordEncoder(passwordEncoder());
return authProvider;
}
@Bean
public PasswordEncoder passwordEncoder()
{
return new CustomPassword();
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/resources**").permitAll()
.anyRequest().permitAll()
.and().formLogin().loginPage("/login").successForwardUrl("/index").defaultSuccessUrl("/index",true).failureUrl("/login?error").permitAll()
.and()
.csrf().disable();
System.out.println("got here too");
}
}
UserServiceDetails.java
package com.scanapp.services;
import com.drew.metadata.StringValue;
import com.scanapp.config.MyUserPrincipal;
import com.scanapp.config.SecSecurityConfig;
import com.scanapp.models.User;
import com.scanapp.repositories.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;
import org.springframework.web.bind.annotation.RequestParam;
import java.util.Objects;
@Qualifier("myuserdet")
@Service
public class UserDetailsService implements org.springframework.security.core.userdetails.UserDetailsService {
@Autowired
private UserRepository userRepository;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
User user = userRepository.findByEmail(username);
if (Objects.nonNull(user)) {
MyUserPrincipal principal = new MyUserPrincipal(user);
System.out.println(String.valueOf(principal));
System.out.println("User Found");
System.out.println(principal.getPassword());
System.out.println(principal.getUsername());
return principal;
}else {
throw new BadCredentialsException("User Not found");
}
}
}
MyUserPrincipal.java
package com.scanapp.config;
import com.scanapp.models.User;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
import java.util.Collection;
public class MyUserPrincipal implements UserDetails {
private User user;
public MyUserPrincipal(User user) {
this.user = user;
}
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return null;
}
@Override
public String getPassword()
{
return user.getPassword();
}
@Override
public String getUsername()
{
return user.getEmail();
}
@Override
public boolean isAccountNonExpired() {
return false;
}
@Override
public boolean isAccountNonLocked() {
return false;
}
@Override
public boolean isCredentialsNonExpired() {
return false;
}
@Override
public boolean isEnabled() {
return false;
}
}
CustomPassword.java
package com.scanapp.config;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
public class CustomPassword extends BCryptPasswordEncoder {
Logger logger = LoggerFactory.getLogger(this.getClass());
@Override
public String encode(CharSequence rawPassword) {
return super.encode(rawPassword);
}
@Override
public boolean matches(CharSequence rawPassword, String encodedPassword) {
System.out.println("paasword etered {}" + rawPassword);
return super.matches(rawPassword, encodedPassword);
}
}
答案 0 :(得分:0)
尝试从配置中删除此块。从理论上讲,Spring在后台创建了所有这些bean(自动选择passwordEncoder和UserDetailsService)。
@Autowired
@Qualifier("myuserdet")
UserDetailsService userDetailsService;
protected void init(AuthenticationManagerBuilder auth) throws Exception {
System.out.println("I'm here");
auth.authenticationProvider(authProvider());
}
@Bean
public DaoAuthenticationProvider authProvider() {
System.out.println("got here");
DaoAuthenticationProvider authProvider = new
DaoAuthenticationProvider();
authProvider.setUserDetailsService(userDetailsService);
authProvider.setPasswordEncoder(passwordEncoder());
return authProvider;
}
如果它不起作用,请尝试重命名您的UserDetailsService(尽管这很困难)。
答案 1 :(得分:0)
您的代码中杂乱无章。
1。您定义了CustomPassword,它仅扩展了BCryptPasswordEncoder。我建议返回
@Bean
public PasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}
2。您定义了另一个不执行任何操作且具有已授予权限的空列表的用户模型。这很奇怪,因为如果授权机构列表为空,它将失败。请返回导入
org.springframework.security.core.userdetails.User;
//..
return new User(userName, encodedPassword, Collections.singletonList(new SimpleGrantedAuthority("USER")
3。最好为您的bean使用其他名称,而不是春季的名称。请将UserDetailsService重命名为CustomUserDetailsService,并且不要在配置中使用限定符。
4。请确保在将密码保存到数据库中时,密码会使用BCryptPasswordEncoder进行散列。
答案 2 :(得分:0)
好。另一个想法: 根据文档,此方法不应返回null:
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return null;
}
返回AuthorityUtils.NO_AUTHORITIES;
。
理论上,在UserDetailsService创建主体之后,它可以在身份验证期间引发NullpointerException
。如果某个地方有一个通用catch (Exception e)
,那么它将被简单地嵌入到AuthenticationException
中。
---编辑
哎呀!
您还应该在true
类的最后四个方法中将返回值更改为MyUserPrincipal
:
@Override
public boolean isAccountNonExpired() {
return true;
}
@Override
public boolean isAccountNonLocked() {
return true;
}
@Override
public boolean isCredentialsNonExpired() {
return true;
}
@Override
public boolean isEnabled() {
return true;
}
您的普林卡帕勒总是被禁用,过期以及全部失效。当然,不允许登录! :)