首页 文章

通过REST endpoints 进行Spring Security身份验证/授权

提问于
浏览
7

在我使用RESTful webservices的Spring Boot应用程序中,我已将Spring Security与Spring Social和 SpringSocialConfigurer 一起配置 .

现在我有两种身份验证/授权方式 - 通过用户名/密码和社交网络,例如Twitter .

为了在我的Spring MVC REST控制器中通过我自己的RESTful endpoints 实现身份验证/授权,我添加了以下方法:

@RequestMapping(value = "/login", method = RequestMethod.POST)
public Authentication login(@RequestBody LoginUserRequest userRequest) {
    Authentication authentication = authenticationManager.authenticate(new UsernamePasswordAuthenticationToken(userRequest.getUsername(), userRequest.getPassword()));
    boolean isAuthenticated = isAuthenticated(authentication);
    if (isAuthenticated) {
        SecurityContextHolder.getContext().setAuthentication(authentication);
    }
    return authentication;
}

private boolean isAuthenticated(Authentication authentication) {
    return authentication != null && !(authentication instanceof AnonymousAuthenticationToken) && authentication.isAuthenticated();
}

但是我不确定在成功 /login endpoints 调用之后必须返回到客户端的确切内容 . 我认为返回完整的身份验证对象是多余的 .

在成功验证的情况下应该返回给客户什么?

你能告诉我如何正确实现这个登录方法吗?

此外,在RESTfull登录的情况下,我将 UsernamePasswordAuthenticationToken 并且如果通过Twitter登录我将 SocialAuthenticationToken 在同一个应用程序中是否可以使用不同的令牌?

2 回答

  • 3

    您可以通过覆盖 SimpleUrlAuthenticationSuccessHandler 中的方法来配置成功验证时要返回的内容


    public class CustomAuthenticationSuccessHandler extends SimpleUrlAuthenticationSuccessHandler {
    
        public CustomAuthenticationSuccessHandler() {
            super();
            setRedirectStrategy(new NoRedirectStrategy());
        }
    
        @Override
        public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response,
                Authentication authentication) throws IOException, ServletException {
    
            super.onAuthenticationSuccess(request, response, authentication);
            ObjectMapper mapper = new ObjectMapper();
    
            response.setContentType("application/json;charset=UTF-8");
            response.getWriter().print(mapper.writeValueAsString(objectToBereturned);
            response.getWriter().flush();
        }
    
        protected class NoRedirectStrategy implements RedirectStrategy {
    
            @Override
            public void sendRedirect(HttpServletRequest request, HttpServletResponse response, String url)
                    throws IOException {
                // any redirect if required. leave the implementation black if not needed
            }
    
        }
    }
    

    此外,您还可以处理故障响应:


    public class CustomAuthenticationFailureHandler extends SimpleUrlAuthenticationFailureHandler {
        @Override
        public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response,
                AuthenticationException exception) throws IOException, ServletException {
            response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
        }
    }
    
  • 1

    Restful调用应始终返回响应代码 . 在你的情况下它应该只有200 OK . 失败401未经授权 . 拥有不同的令牌绝对没问题,无论如何都不能使用相同的令牌 .

    我个人更喜欢通过Spring Security过滤器而不是控制器来处理登录 endpoints ,因为您可以更好地控制流量 .

相关问题