Spring Boot 安全性 - 在 Web 服务调用中显示自定义身份验证失败消息

当用户尝试使用暂停、锁定或无效的帐户调用我的网络服务时,我试图显示自定义错误。


问题是,无论我尝试什么,相同的消息不断返回:“访问此资源需要完全身份验证”


我的 CustomUserDetailsService 是这样的:


@Service

public class CustomUserDetailsService implements UserDetailsService {

    private static final Logger logger = LogManager.getLogger(CustomUserDetailsService.class);


    private @Autowired CredentialsServiceQuery credentials;

    private @Autowired MemberProfile memberProfile;


    @Override

    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {

        User.UserBuilder builder = null;

        try {

            boolean exists = credentials.checkUserExists(username);

            if (exists) {

                memberProfile = credentials.getUserInformation(username);


                builder = User.withUsername(username);

                builder.password(memberProfile.getPassword());

                builder.authorities(getGrantedAuthorities());

                logger.info("User exists: {}", username);

            } else {

                throw new UsernameNotFoundException(SpringSecurityMessageSource.getAccessor().getMessage("AbstractUserDetailsAuthenticationProvider.badCredentials", new Object[] {username}, "User credentials is wrong"));

            }

        } catch (Exception ex) {

            throw new UsernameNotFoundException(SpringSecurityMessageSource.getAccessor().getMessage("AbstractUserDetailsAuthenticationProvider.badCredentials", new Object[] {username}, "User credentials is wrong"));

            //throw new UsernameNotFoundException("An error occured while trying to find the username, " + username, ex);

        }

        return builder.build();

    }


    private List<GrantedAuthority> getGrantedAuthorities(){

        List<GrantedAuthority> authorities = new ArrayList<>();

        authorities.clear();        

        authorities.add(new SimpleGrantedAuthority("ROLE_USER"));


        return authorities;

    }


}


手掌心
浏览 112回答 1
1回答

素胚勾勒不出你

我不得不放弃尝试让 Spring Security 自动为入口点提供来自用户详细信息服务的异常消息的想法。因此,我改用自定义身份验证提供程序以获得更多控制,并引入了一个名为 ErrorMessage 的自定义服务:@Getter@Setter@ToString@Servicepublic class ErrorMessage {&nbsp; &nbsp; private String status;&nbsp; &nbsp; private String message;}@Getter、@Setter 和@ToString 注释来自 lombok。他们做到了,所以我不必编写 setter 和 getter 以及 toString 方法。在我的自定义身份验证提供程序中,我只是这样设置错误消息:private @Autowired ErrorMessage errorMessage;&nbsp; &nbsp;&nbsp;@Override&nbsp; &nbsp; &nbsp; &nbsp; public Authentication authenticate(Authentication authentication) throws AuthenticationException {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; try {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; String username = authentication.getName();&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; String password = authentication.getCredentials().toString();&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (!credentials.checkUserExists(username)) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //set something here&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; memberProfile = credentials.getUserInformation(username);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (passwordEncoder.matches(password, memberProfile.getPassword())) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; logger.info("It matches - encoder!");&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; return new UsernamePasswordAuthenticationToken(username, password, getGrantedAuthorities());&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } else {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; //error message bean utilised here&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; errorMessage.setStatus("100");&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; errorMessage.setMessage(username + "'s password is incorrect");&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; throw new BadCredentialsException("The credentials provided are incorrect");&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } catch (Exception ex) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; throw new BadCredentialsException("The credentials provided are incorrect", ex);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; }然后我以这种方式在入口点获得自定义错误消息:@Componentpublic class CustomAuthenticationEntryPoint implements AuthenticationEntryPoint {&nbsp; &nbsp; private @Autowired ErrorMessage errorMessage;&nbsp; &nbsp; @Override&nbsp; &nbsp; public void commence(HttpServletRequest request, HttpServletResponse response, AuthenticationException ex) throws IOException, ServletException {&nbsp; &nbsp; &nbsp; &nbsp; //String json = String.format("{\"errorcode\": \"%s\", \"message\": \"%s\"}", response.getStatus(), ex.getMessage());&nbsp; &nbsp; &nbsp; &nbsp; String json = String.format("{\"errorcode\": \"%s\", \"message\": \"%s\"}", errorMessage.getStatus(), errorMessage.getMessage());&nbsp; &nbsp; &nbsp; &nbsp; response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);&nbsp; &nbsp; &nbsp; &nbsp; response.setContentType("application/json");&nbsp; &nbsp; &nbsp; &nbsp; response.setCharacterEncoding("UTF-8");&nbsp; &nbsp; &nbsp; &nbsp; response.getWriter().write(json);&nbsp; &nbsp; }}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Java