我只想用access_token对Spring Security OAuth2进行身份验证

I want to authenticate Spring Security OAuth2 with access_token only

提问人:kokojustin 提问时间:10/11/2023 更新时间:10/12/2023 访问量:41

问:

在使用 Spring Security OAuth2 方法时,我对两件事感到好奇。

  1. 是否可以在不使用 JSESSION 或 jwtToken 的情况下通过每次检查access_token来执行身份验证? 例如,第一次,access_token和refresh_token通过 OAuth2 身份验证颁发并存储在 JDBC (mysql) 中。 在随后的请求中,我想检索存储在 mysql 中的access_token并确定其有效性。

  2. 如果 Spring Security OAuth2 方法中的access_token已过期,那么使用 refresh_token 发出新access_token并在 JDBC (mysql) 中更新它的代码在哪里?

Spring Security OAuth-2.0 访问令牌

评论


答:

0赞 ch4mp 10/12/2023 #1

你的问题与Spring关系不大。它主要是关于 OAuth2(无论实现它的框架是什么),您显然需要更多有关 OAuth2 的背景知识。

资源所有者在给定 OAuth2 客户端的 OAuth2 授权服务器上进行身份验证,以便此客户端可以获取获取令牌并授权其对 OAuth2 资源服务器的请求。你的问题究竟是关于这些演员中的哪一个?授权服务器、客户端和资源服务器通常是不同的应用程序,这 3 个应用程序都可以用 Spring 编写。

客户端(从中启动登录并存储令牌)和授权服务器(执行登录并颁发令牌)需要会话来运行流(不仅如此,而且此流是用于“登录”用户的),对此您几乎无能为力。资源服务器(使用令牌进行访问控制决策)可以在没有会话(无状态)的情况下进行配置,这通常是因为它使扩展和容错变得非常容易(任何实例都可以处理任何请求,并且可以随时用任何其他实例替换任何实例)。authorization_code

HttpSessionOAuth2AuthorizedClientRepository,默认的 Spring Security 实现,将令牌存储在会话中,只是因为它在许多方面都是一个非常好的选择(比数据库快得多,也更安全)。像往常一样,你可以使用数据库编写自己的实现,但性能会下降(可能还有安全问题)。如果担心的是跨客户端实例共享令牌,请考虑每个实例获取自己的令牌可能会更快,并且还有一个项目可以在实例之间共享会话数据。OAuth2AuthorizedClientRepositoryspring-session

OAuth2 资源服务器上验证令牌有两个选项:JWT 解码和自省。第二个问题涉及每个请求的授权服务器的往返行程,这似乎是您在第一个问题中要查找的内容,但这会对性能产生严重影响。此外,如果正确实现 OAuth2 客户端,它就不会带来任何安全性:“安全”客户端应该是机密的(在您信任的服务器上运行并使用密钥进行身份验证),并在用户注销时删除令牌(如果会话在授权服务器上关闭,则无需检查每个请求, 客户端上的会话应始终处于相同状态)。即使其中一个授权服务器客户端没有实现反向通道注销(在 Security 6.2.0 发布之前是 Spring 客户端的情况),要使客户端会话在授权服务器上的会话失效后有效,您必须处于 SSO 配置中(多个 OAuth2 客户端共享同一授权服务器), 让用户使用另一个客户端注销,并且介于此注销和访问令牌过期之间,这应该是一个很短的持续时间(可能少于 5 分钟)。

在 Spring 安全性中,具有令牌的 OAuth2 客户端的抽象是“授权客户端”。如果您想了解令牌获取和刷新的内部结构,则可以从探索源代码开始。OAuth2AuthorizedClientManager