我正在尝试配置Spring Boot应用程序以使用OIDC。服务器位于 SSL 终止代理后面。
以下是我使用的属性:
spring:
security:
oauth2:
client:
provider:
oidc:
authorization-uri: https://example.org/oidc/oauth2/authorize
token-uri: https://example.org/oidc/oauth2/access_token
user-info-uri: https://example.org/oidc/oauth2/userinfo
jwk-set-uri: https://example.org/oidc/oauth2/connect/jwk_uri
custom-params: param_name1,param_value1,param_name2,param_value2,nonce,123456789
registration:
oidc:
client-id: myclientid
client-secret: myclientsecret
authorization-grant-type: authorization_code
scope:
- openid
- email
- profile
redirect-uri: https://mydomain/myapp/login/oauth2/code/oidc
这是它出错的地方:
1. OIDC 服务器要求在请求 URL 中添加随机数参数
我已经通过使用自定义 OAuth2AuthorizationRequest 解决了这个问题,该请求读取自定义参数属性并将这些值附加到请求 URL
2. OidcAuthorizationCodeAuthenticationProvider 抛出由 invalid_redirect_uri_parameter 导致的异常
我已经尝试了许多方法来解决此问题。
我尝试创建一个过滤器,将 X-Forwarded-Proto 添加到请求中(因为代理不处理它(。
添加了标头,我还添加了以下属性:
server:
forward-headers-strategy: native
tomcat.protocol-header: x-forwarded-proto
但它似乎不起作用。
OidcAuthorizationCodeAuthenticationProvider 仍然会引发异常,因为此条件为 false:
!authorizationResponse.getRedirectUri().equals(authorizationRequest.getRedirectUri())
我已经调试了代码,唯一的区别是一个是http,另一个是https。
我发现了一个我根本不喜欢的非常黑客的解决方案,这是另一个过滤器,它只针对该特定 URL 修改 URL。
我更喜欢一个更优雅的解决方案。
3. 使用自定义 nonce 参数时,OidcAuthorizationCodeAuthenticationProvider 会抛出异常原因,invalid_nonce
现在我被困住了。我考虑过编写自己的身份验证提供程序,但我不能保证我的身份验证提供程序会在 Spring 提供的 OIDC 提供程序之前被选中。
有了随机数,这是一个第 22 条:
如果我不使用自定义参数,我找不到让 Spring 将随机数添加到请求的方法
如果我使用那个,Spring 在它是 JWT 的一部分时无法识别它并吓坏
了
任何帮助将不胜感激,因为这已经让我发疯了几天甚至几周。
谢谢。
编辑
在案例 2 中比较的 2 个 URL 来自:
- OAuth2授权请求
- OAuth2授权响应
OAuth2AuthorizationRequest内置于 OAuth2AuthorizationRequestRedirectFilter 在以下行:
OAuth2AuthorizationRequest authorizationRequest = this.authorizationRequestResolver.resolve(request);
重定向 uri 构建在 DefaultOAuth2AuthorizationRequestResolver.expandRedirectUri(( 中,它调用
UriComponentsBuilder.fromHttpUrl(UrlUtils.buildFullRequestUrl(request))
OAuth2AuthorizationResponse内置在 OAuth2LoginAuthenticationFilter.tryAuthentication(( 中,它也调用
UriComponentsBuilder.fromHttpUrl(UrlUtils.buildFullRequestUrl(request))
然后
OAuth2AuthorizationResponseUtils.convert(params, redirectUri)
我会仔细检查,但我不记得在构建这些 URL 时调用了 UriComponentsBuilder.adaptFromForwardedHeaders(HttpHeaders headers(。
即使这有效,这仍然会使随机数问题:(
我们偶然发现了同样的问题,问题主要是因为我们的服务器在反向代理后面,似乎代理以某种方式更改了 url 导致此检查失败
!authorizationResponse.getRedirectUri().equals(authorizationRequest.getRedirectUri())
此行在更高版本的 Spring 安全性中删除,在提交
24500fa3ca23aa23ede86dfcfe02113671d5b8bc
在 GitHub 提交
于 2019 年 12 月 6 日引入,在春季安全版本 5.1.13 中
因此,解决方案是将Spring boot升级到至少2.1.17,以获取Spring Boot 2.1.X系列版本。
虽然OP说他无法升级他的图书馆,但我希望这可以帮助那些可以升级的人。
我们还做了上面提到的解决方案,由Kavithakaran Kanapathippilla,并配置了我们的反向代理来添加X-forwarded-proto http标头,我也相信我们配置了spring启动应用程序属性来检查它们
用于在代理后面工作的 Spring 启动文档