如何在 Spring Boot oauth2 资源服务器中使用自定义身份验证标头

Posted

技术标签:

【中文标题】如何在 Spring Boot oauth2 资源服务器中使用自定义身份验证标头【英文标题】:How to use custom auth header with spring boot oauth2 resource server 【发布时间】:2021-12-18 13:01:31 【问题描述】:

我正在配置 spring cloud api 网关以支持多个安全链。为此,我使用了几个在特定安全标头存在时触发的安全过滤器链:

    已经使用授权标头的旧版 以及与外部 idp 集成的新实施。该解决方案利用资源服务能力。对于我想使用的这个链,可以说“New-Auth”标头。

如果我调整当前设置以在授权标头存在时触发第二个 (idp) 链(并使用 IDP 令牌进行调用),那么一切正常。这样,安全链会根据 idp jwk 验证它在 Authorization 标头中期望的令牌。但是这个标头已经为传统的身份验证保留了。

我想我需要一种方法来为 spring 资源服务器链指向一个新的标头名称来查找。

我的安全依赖:

implementation 'org.springframework.boot:spring-boot-starter-security'
implementation 'org.springframework.boot:spring-boot-starter-oauth2-resource-server'

我的配置

@EnableWebFluxSecurity
public class WebSecurityConfiguration 

  // ...

  @Bean
  @Order(1)
  public SecurityWebFilterChain iamAuthFilterChain(ServerHttpSecurity http) 
    ServerWebExchangeMatcher matcher = exchange -> 
      HttpHeaders headers = exchange.getRequest().getHeaders();
      List<String> strings = headers.get(SurpriseHeaders.IDP_AUTH_TOKEN_HEADER_NAME);
      return strings != null && strings.size() > 0
          ? MatchResult.match() : MatchResult.notMatch();
    ;

    http
        .securityMatcher(matcher)
        .csrf().disable()
        .authorizeExchange()
          .pathMatchers(navigationService.getAuthFreeEndpoints()).permitAll()
          .anyExchange().authenticated()
        .and()
          .oauth2ResourceServer(OAuth2ResourceServerSpec::jwt)
          .oauth2ResourceServer().jwt().jwkSetUri(getJwkUri())
          .and()
        .and()
          .addFilterAt(new LoggingFilter("idpAuthFilterChain"), SecurityWebFiltersOrder.FIRST)
          .addFilterAfter(new IdpTokenExchangeFilter(authClientService), SecurityWebFiltersOrder.AUTHENTICATION)
    ;    
    return http.build();
  



肮脏的解决方案

我们可以添加一些过滤器来编辑请求并将传入的“New-Auth”标头复制为security filter chain开头的“授权”标头。

看起来可行,但我相信它应该是更好的方法。

【问题讨论】:

【参考方案1】:

您可以为您的oauth2ResourceServer 配置指定ServerAuthenticationConverter,如下所示:

http
    .oauth2ResourceServer((resourceServer) -> resourceServer
        .bearerTokenConverter(customBearerTokenAuthenticationConverter())
        .jwt()
    );

ServerAuthenticationConverter customBearerTokenAuthenticationConverter() 
    ServerBearerTokenAuthenticationConverter tokenAuthenticationConverter = new ServerBearerTokenAuthenticationConverter();
    tokenAuthenticationConverter.setBearerTokenHeaderName("New-Auth");
    return tokenAuthenticationConverter;

【讨论】:

嗨,@Marcus。 http.oauth2ResourceServer 允许我配置没有 BearerTokenResolver 配置方法的 OAuth2ResourceServerSpec。可能我们正在谈论不同的安全实现。我正在使用的http.oauth2ResourceServer 实现位于org.springframework.security:spring-security-config5.5.0 我已经更新了对响应式应用程序的回答 它有效,谢谢!

以上是关于如何在 Spring Boot oauth2 资源服务器中使用自定义身份验证标头的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Spring Boot oauth2 资源服务器中使用自定义身份验证标头

资源服务器上的 Spring Boot OAuth2 自定义角色

如何在 Spring Boot 中使用 IPwhitelisting 和 OAuth2? [复制]

spring-boot oauth2 拆分授权服务器和资源服务器

使用Spring boot的OAuth2认证服务器和资源服务器

如何在 Spring Boot OAuth2 的 SecurityContextHolder 中获取 JWT 令牌?