考虑到用户使用 OpenID Connect 的隐式客户端流程登录到我的应用程序的场景,其中 OP 是 PingFederate,如果用户关闭了应用程序并在有效的时间内返回到它,我如何确定用户是否仍然登录时间段?
1 回答
重新提出一个老问题,因为 OpenID Connect 仍然被广泛使用。要检查用户是否已通过身份验证 - 无论是来自与您的应用程序的先前会话,还是来自与另一个联合应用程序的会话 -prompt=none在身份验证请求中提供。根据规范,有关prompt=none状态的文档:
授权服务器不得显示任何身份验证或同意用户界面页面。如果最终用户尚未经过身份验证,或者客户没有预先配置对请求的声明的同意或不满足处理请求的其他条件,则会返回错误。错误代码通常是 login_required、interaction_required 或第 3.1.2.6 节中定义的其他代码。这可以用作检查现有身份验证和/或同意的方法。
“静默身份验证”prompt=none在 iFrame 中使用此参数。Auth0 对此进行了一些讨论,here。简而言之,身份验证请求是在一个不可见的 iFrame 中发出的,这样用户代理的主框架就不会被重定向。根据您的身份提供商 (IdP),这可能是也可能不是有效选项。出于安全原因,授权端点通常会拒绝使用X-Frame-Options: DENY标头在帧中发出的请求。IdP 上的 Cookie 来源策略也可能会阻止静默身份验证。也就是说,同样可以在 SPA 的初始加载时通过弹出窗口或完整的用户代理重定向来完成。
值得指出的是,由于广泛的安全问题,隐式流已被弃用很长时间,其中许多安全问题没有足够的缓解策略。基于浏览器的应用程序的OAuth 2.0描述了当前的最佳实践。现在可以使用带有 PKCE 的代码流,但它仍然存在许多无法充分缓解的安全问题(再次在最佳实践文档中进行了描述)。
在边缘设备(SPA 和 API 服务器之间的服务器)中带有后端会话服务器的代码流是最好的安全选择。这种方法将令牌完全排除在用户代理之外,有助于通过 XSS 攻击缓解令牌泄漏,如果操作正确,CSRF 攻击将变得无能为力。关于这个问题,一个长期存在的刷新令牌可以存储在会话服务器中,并且可以用于在页面刷新或关闭浏览器之间保持身份验证。 这是关于这种方法的文章。
解决上述评论之一:“为什么在完成 authN 后关闭网站的用户会期望 AuthN 在关闭后仍然有效?” 因为它是更好的用户体验,也是当今预期的用户体验。想想谷歌、Atlassian,甚至这个站点(StackOverflow):用户登录一次,几乎不需要再次登录,只要用户经常与站点交互并且不会引发任何安全危险信号。
解决另一条评论:“如果你到了应用程序现在有一个'ID 令牌'的地步,那就是关键。只要令牌有效(检查到期时间)。” ID 令牌和访问令牌都应该很快过期,而刷新令牌应该是长期存在的。这样,如果 IdP 撤销用户的访问权限,撤销将迅速传播到所有客户端应用程序。