[英]When send login request user be null for @AuthenticationPrincipal
當我嘗試從前端登錄時,出現錯誤。 我可以注冊,但我無法登錄。
錯誤:
java.lang.NullPointerException:無法調用“com.app.auction.user.User.getName()”,因為“user”在 com.app.auction.user.UserVM.(UserVM.java:17) 處為空 ~[類/:na] 在 com.app.auction.auth.AuthController.handleAuthentication(AuthController.java:21) ~[classes/:na]
我嘗試向這個 api 發送請求。
授權控制器
@RestController
public class AuthController {
@Autowired
UserRepository userRepository;
@PostMapping("/auth")
UserVM handleAuthentication(@CurrentUser User user) {
return new UserVM(user);
}
}
@當前用戶
@Target({ElementType.PARAMETER})/
@Retention(RetentionPolicy.RUNTIME)
@AuthenticationPrincipal
public @interface CurrentUser {
}
用戶虛擬機
package com.app.auction.user;
import lombok.Data;
@Data
public class UserVM {
private String name;
private String username;
private String email;
private String image;
public UserVM(User user) {
this.name = user.getName();
this.email = user.getEmail();
this.username=user.getUsername();
this.image=user.getImage();
}
}
無角色用戶
@Data
public class UserWithoutRole {
@NotNull(message="Name can not be null")
@Size(min = 2, max=50, message = "Name must be more than 2 letters ")
private String name;
@NotNull(message="Username can not be null")
@UniqueUsername
@Size(min=1,max=100 )
private String username;
@NotNull(message="Email can not be null")
private String email;
@NotNull(message="Password can not be null")
@Size(min = 4, max=16 , message = "Password must be a minimum of 4 characters and a maximum of 16 characters. ")
private String password;
private String image;
}
用戶
@Data
@Entity
public class User implements UserDetails{
/**
*
*/
private static final long serialVersionUID = -2725432351214985546L;
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
private String name;
private String username;
private String email;
private String password;
@ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
@JoinTable(name = "users_roles",
joinColumns = @JoinColumn(name = "user_id"),
inverseJoinColumns = @JoinColumn(name = "role_id"))
private Collection<Role> roles;
private String image;
public User() {
}
public User(UserWithoutRole user) {
this.name = user.getName();
this.email = user.getEmail();
this.username=user.getUsername();
this.image=user.getImage();
}
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
Collection<Role> roles = getRoles();
List<SimpleGrantedAuthority> authorities = new ArrayList<>();
for (Role role : roles) {
authorities.add(new SimpleGrantedAuthority(role.getName()));
}
return authorities;
}
@Override
public boolean isAccountNonExpired() {
return true;
}
@Override
public boolean isAccountNonLocked() {
return true;
}
@Override
public boolean isCredentialsNonExpired() {
return true;
}
@Override
public boolean isEnabled() {
return true;
}
}
安全配置
@EnableWebSecurity
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
@Autowired
UserAuthService userAuthService;
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable();
http.httpBasic();
http.httpBasic().authenticationEntryPoint(new AuthEntryPoint());
http.authorizeRequests()
.antMatchers("/").permitAll()
.antMatchers(HttpMethod.POST,"/auth").authenticated()
.and()
.authorizeRequests().anyRequest().permitAll();
http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userAuthService).passwordEncoder(passwordEncoder());
}
@Bean
PasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
}
用戶詳情服務
@Service
public class UserAuthService implements UserDetailsService{
@Autowired
UserRepository userRepository;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
User user = userRepository.findByUsername(username); //my user implements UserDetails it can return
if(user != null && user.isEnabled()){
return buildUserForAuthentication(user, mapRolesToAuthorities(user.getRoles()));
}else {
throw new UsernameNotFoundException("User not found");
}
}
private Collection<? extends GrantedAuthority> mapRolesToAuthorities(Collection<Role> roles) {
return roles.stream()
.map(role -> new SimpleGrantedAuthority(role.getName()))
.collect(Collectors.toList());
}
UserDetails buildUserForAuthentication(User user, Collection<? extends GrantedAuthority> collection) {
return new org.springframework.security.core.userdetails.User(user.getUsername(),
user.getPassword(), collection);
}
}
我解決了問題。 即使用戶實現了 UserDetails,我也無法獲得 @CurrentUser。 我將身份驗證作為參數獲取,然后轉換為我的 User 類。
@PostMapping("/auth")
UserVM handleAuthentication(Authentication authentication) {//@CurrentUser User user
User user=userService.getByUsername(authentication.getName());
return new UserVM(user);
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.