spring-security 如果请求具有使用Spring Security的特定标头标记,如何允许调用终结点

nwlls2ji  于 2022-11-11  发布在  Spring
关注(0)|答案(1)|浏览(109)

我正在使用Sping Boot 来构建一个Web应用程序,有时我不想在权限和规则管理上花费太多时间,我只想能够创建一个随机字符串令牌,并允许其他服务使用我的服务,如果他们知道这个令牌...
都知道所有的危险和问题有关的这种方法,但对于原型集成,这是我需要的...
问题是我如何配置Spring Security来验证特定端点的特定令牌[注意,我希望不同的端点使用不同的令牌,如果整个应用程序只有一个令牌,则解决方案将是一个简单的过滤器]
示例:

protected void configure(HttpSecurity http) throws Exception {
    http.cors().and()
                  .csrf().disable()
                  .authorizeRequests()
                  .antMatchers(AUTH_WHITELIST).permitAll()
                  .antMatchers(HttpMethod.POST, "/boards/").access("SOMETHING LIKE: httpRequest->headers->get('tokenHeader') == 'mytoken'")
    .anyRequest().authenticated() 
//......
}

我想实现这样的目标......
我现在唯一能做我想做的事的方法就是:

@Value("${controller.plan.authorization}")
    private String AUTHORIZATION_TOKEN;

     @GetMapping
    public List<Plan> getPlans(@RequestHeader(HttpHeaders.AUTHORIZATION) authToken: String)  {
        if (AUTHORIZATION_TOKEN.equals(authToken))
            return planService.findAll()
        else
            throw ResponseStatusException(HttpStatus.UNAUTHORIZED, "invalid authorization_token")
    }

这是相当脱离Spring的模式,在我看来真的很烦人
有没有办法使用Spring Security来实现这一点?

ckocjqey

ckocjqey1#

因此,您有一些公共代码,需要在多个控制器和端点中以相同的方式执行。
这使得拦截器成为一个合适的解决方案。
请尝试以下操作

@Configuration
public class WebSecurityConfig implements WebMvcConfigurer
{
    @Autowired
    private MyInterceptor myInterceptor;

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(myInterceptor).addPathPatterns("*/boards/*");
    }

}

那么您所描述的功能应该与以下内容接近

@Component
public class MyInterceptor implements HandlerInterceptor {

    @Value("${controller.plan.authorization}")
    private String AUTHORIZATION_TOKEN;

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {

        final String requestTokenHeader = request.getHeader(HttpHeaders.AUTHORIZATION);

        if (AUTHORIZATION_TOKEN.equals(requestTokenHeader)) {
            //continue execution in spring flow to reach the relative controller
            return true;
        } else {
            //break flow and return response.
            response.getWriter().write("invalid authorization_token");
            response.setStatus(HttpStatus.UNAUTHORIZED.value());
            return false;
        }
    }

}

现在,您的控制器可以摆脱样板代码。

相关问题