我正在尝试向Principal中的Spring Security对象添加其他属性。因此我实现了


实现UserDetails的CustomUser对象
实现UserDetailsService的CustomUserService。


CustomUser:

@Entity
public class CustomUser implements UserDetails { ... }


CustomUserService:

@Service
public class CustomUserService implements UserDetailsService {

    @Autowired
    private CustomUserRepository customUserRepository;

    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {

        CustomUser customUser = this.customUserRepository.findByUsername(username);

        return new User(customUser.getUsername(), customUser.getPassword(), true, true, true, true,
            customUser.getAuthorities());
    }
}


最后,我将其添加到了security.xml中:

<beans:bean id="customUserDetailsService" class="project.service.CustomUserService"></beans:bean>

<authentication-manager>
    <authentication-provider user-service-ref="customUserDetailsService" />
</authentication-manager>


现在,我想通过以下方式获取一些CustomUser特定属性(例如fullName)

Authentication auth = SecurityContextHolder.getContext().getAuthentication();
CustomUser user = (CustomUser) auth.getPrincipal();


但我总是得到一个ClassCastException

java.lang.ClassCastException: org.springframework.security.core.userdetails.User cannot be cast to project.entity.CustomUser


有人知道如何处理吗?我的目标是在用户成功登录后在控制器中获取特定的用户数据。到现在为止,除了检索CustomUser属性之外,其他所有东西都可以正常工作。
谢谢!

最佳答案

作为CustomUser implements UserDetails

但是,您将返回新的User(...)并强制转换为类型不匹配的CustomUser,因此您收到了ClassCastException。
您必须直接返回CustomUser类型,如下所示。

   @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {

        return this.customUserRepository.findByUsername(username);


编辑:
代替CustomUser实现UserDetails,您必须扩展User对象并填充详细信息并按如下所示将其返回。您还可以将UserEntity对象和CustomUser对象分开

public class CustomUser extends org.springframework.security.userdetails.User {.....}

@Entity
public class UserEntity {...}

public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {

 UserEntity userEntity = this.customUserRepository.findByUsername(username);

 CustomUser customUser = new CustomUser( userEntity.getUsername(), userEntity.getPassword()........);

 return customUser;
}


之后,您访问

 CustomUser customUser = (CustoomUser) authentication.getPrincipal();

09-11 20:38