我是spring-boot和spring-security的新手,无法独自理解以下错误。我的spring-boot应用程序只包含两个URL,一个是任何人都可以访问的,即只能通过其名称密码保存在数据库中,另一个是只有ADMIN才能访问的(用于添加用户并在MySql数据库中滚动(。但当我传递用户名和密码时,它会说:-
org.springframework.security.authentication.InternalAuthenticationServiceException: UserDetailsService returned null, which is an interface contract violation
我在下面发布所有必要的类:-
CustomUserDetailService:-
@Service
public class CustomUserDetailService implements UserDetailsService {
@Autowired
private UserRepository repository;
@Override
public UserDetails loadUserByUsername(String name) throws UsernameNotFoundException {
User user= repository.findByname(name);
CustomUserDetail userDetail=null;
if(user!=null){
CustomUserDetail userDetails=new CustomUserDetail();
userDetails.setUser(user);
}else{
throw new UsernameNotFoundException("User not exist with name :" +name);
}
return null;
}
}
自定义用户详细信息
public class CustomUserDetail implements UserDetails {
private User user;
/*Getter and Setter*/
public User getUser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
/*Overriden methods from userDetail*/
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return user.getRoles().stream().map(role -> new SimpleGrantedAuthority("Role_"+role))
.collect(Collectors.toList());
}
@Override
public String getPassword() {
return user.getPassword();
}
@Override
public String getUsername() {
return user.getName();
}
@Override
public boolean isAccountNonExpired() {
return true;
}
@Override
public boolean isAccountNonLocked() {
return true;
}
@Override
public boolean isCredentialsNonExpired() {
return true;
}
@Override
public boolean isEnabled() {
return true;
}
}
基本配置:-
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class BasicConfig extends WebSecurityConfigurerAdapter{
@Autowired
private UserDetailsService userDetailsService;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception
{
auth.userDetailsService(userDetailsService).passwordEncoder(encodePWD());
}
@Override
protected void configure(HttpSecurity http) throws Exception
{
http.csrf().disable();
http
.authorizeRequests()
.antMatchers("/user/").permitAll()
.and()
.authorizeRequests()
.antMatchers("/MiniApi/**").hasAnyRole("ADMIN")
.anyRequest().authenticated()
.and()
.formLogin()
.permitAll();
}
@Bean
public BCryptPasswordEncoder encodePWD()
{
return new BCryptPasswordEncoder();
}
}
控制器类:-我没有创建两个@Restcontroller类,只有一个@RequestMapping((作为基本URL
管理员控制器:-
@RestController
@RequestMapping("/MiniApi")
public class Admincontroller
{
@Autowired
private UserRepository userRepository;
@Autowired
private BCryptPasswordEncoder passwordEncoder;
@PreAuthorize("hasAnyRole('ADMIN')")
@PostMapping("/admin/add")
public String addUser(@RequestBody User user)
{
String pwd = user.getPassword();
String encryptPwd = passwordEncoder.encode(pwd);
user.setPassword(encryptPwd);
userRepository.save(user);
return "User added successfully...";
}
}
AnyOne:-
public class AnyOne {
@GetMapping("/anyone")
public String Anyone()
{
return "processing......";
}
}
更改我所做的:-如果我从CustomUserDetailService中删除return语句,我会得到return语句丢失错误,然后我添加返回userDetails它给了我:-
首先它要求我提供用户名和密码,然后这个
HTTP状态403–禁止
- 您返回的是null而不是
userDetails
@Service
public class CustomUserDetailService implements UserDetailsService {
@Autowired
private UserRepository repository;
@Override
public UserDetails loadUserByUsername(String name) throws
UsernameNotFoundException {
User user= repository.findByname(name);
CustomUserDetail userDetail=null;
if(user != null){
CustomUserDetail userDetails=new CustomUserDetail();
userDetails.setUser(user);
return userDetails;
}
throw new
UsernameNotFoundException("User not exist with name :" +name);
}
}