本文就 OAuth 协议如何从最初的 OAuth 1.0 版本一步步优化、迭代、重组后到现今的 OAuth 2.1 版本进行剖析。方便开发者在使用 OAuth时能更好地理解、适配更多场景,丰富业务功能。
OAuth,对于应用程序开发人员或相关软件开发行业人员可能非常熟悉,它与我们日常冲浪生活息息相关。如在美团中使用微信登录、在网易云中使用QQ登录等,这些平台彼此之间的交互及数据打通,就是 OAuth 实现的。在万物互联互通的时代,OAuth 已是应用对外交互和共享信息不可或缺的方式。
OAuth 不是一个 API 或者服务,而是一种开放的授权协议,用于允许 web、移动和桌面应用程序以简单和标准的方法进行安全授权。"An open protocol to allow secure authorization in a simple and standard method from web, mobile and desktop applications."——OAuth 官网介绍
注意,OAuth 关注的是 Authorization(授权)的层面(即“What”),而不是 Authentication(认证)的层面(即“Who”),关于Authentication(认证)相关的标准协议我们后面会有专门的文章描述。
在传统的授权领域中,第三方应用请求用户的受保护的资源时,服务端会通过使用用户的账密凭证在服务器上进行身份验证(HTTP Basic Authentication),以便为第三方应用程序提供访问权限,这也就进一步要求用户与第三方应用之间共享授权凭证。
譬如,应用 A 想访问用户 B 的支付宝账号信息,按照传统的解决方案,那就是应用 A 要求用户 B 在应用 A 中输入支付宝账号密码,然后应用 A 再使用用户 B 的账号密码去支付宝获取该用户的账号信息。这种方式无疑会造成下面几种问题:
OAuth 的出现,彻底改变了双方系统之间只能通过暴露账密去授权获取用户数据的方式。OAuth 通过在第三方应用与服务提供方之间引入了一个授权层来解决这些问题。首先就要求第三方应用不能直接登录服务提供方,只能先登录授权层,获取到授权层颁发的访问令牌,然后通过这个令牌才能获取到相应权限的资源(并非全部资源),以此将第三方应用与服务提供方区分开。
接下来我们将从OAuth1.0、OAuth1.0A、OAuth2.0、OAuth2.1详细展开,为大家剖析OAuth协议。
如何理解这三个角色?我们以使用支付宝登录淘宝为例,举个简单的例子:
图一:淘宝的登录页面
如上图,User 对应的是当前需要登录到淘宝的真实用户,Service Provider 对应的就是支付宝平台,Consumer 就是淘宝本身。
OAuth 1.0 标准的授权流程
如上图。还是以使用支付宝登录淘宝为例简单的使用文字描述以上流程:
A. 淘宝(Consumer)向支付宝(Service Provider)申请 Request Token(换取 Access Token 的临时令牌);
请求参数
B. 支付宝(Service Provider)签发未授权的 Request Token 后返回淘宝(Consumer),引导用户跳转到支付宝(Service Provider)对 Request Token 进行授权;
响应参数
C. 支付宝(Service Provider)获取用户的授权;
请求参数
D. 支付宝(Service Provider)向淘宝(Consumer)颁发 Request Token;
响应参数
E. 淘宝(Consumer)使用 Request Token 换取 Access Token(访问令牌);
请求参数
F. 支付宝(Service Provider)授权并向淘宝(Consumer)颁发 Access Token;
响应参数
请求参数
以上流程基本就是 Consumer 使用 Request Token 换取 Access Token 的过程。Request Token 和 Access Token 的使用范围和生命周期是不一致的。Request Token 只是获取 Access Token 的前置属性,无法通过该 token 直接获取用户的受保护资源,并且生命周期较短;而 Access Token 是访问用户受保护资源的唯一令牌,生命周期较长,OAuth 1.0 中一般可以以年为单位去设置该值的有效期。
2009年6月24日,OAuth 1.0 A 发布,修订了 1.0 的严重的安全漏洞(Session Fixation Attack):OAuth Security Advisory: 2009.1
按照官方的解释:攻击者首先初始化一个合法的会话(oauth_callbak 配置成攻击者的地址),然后诱使正常用户授权该会话,用户授权成功后回调到攻击者的服务器,从而拿到正常用户的 Access Token,进而获取到正常用户的任何受保护的资源。
图三:OAuth 1.0 a 授权流程
如图中高亮标注的部分,OAuth 1.0 A做出的优化主要在于:
OAuth 1.0 A既然都已经修复了 1.0 遗留的问题,那么为什么还要重新制定一个 2.0 版本呢?其实这个问题,细看一下 OAuth 1.0 的授权流程就可以猜到一二,1.0 虽然经过修复后没有什么太过致命的安全问题,但是从整个使用流程来看 1.0 还是太过于复杂、繁琐,对于开发者来说极其不友好。另外,1.0 对于桌面端、移动端应用来说,无法很好地集成,因为 1.0 十分关键的一点就是 oauth_callback 的存在,而像桌面端、移动端此类应用通常没有服务端,所以在使用 1.0 的时候就要为了兼容这种设计上的错误而冒很大的风险(泄露 consumer_key 和 consumer_secret)。因此,为了弥补 1.0 的“先天不足”,2010年5月开始,OAuth 正式进入 2.0 这一“伟大的”时代。
2012年10月,OAuth 2.0 正式发布为 RFC 标准协议 RFC6749
OAuth 2.0是一种开放的、标准的访问授权(Authorization)协议,是 OAuth 协议的下一代版本。OAuth 2.0 关注客户端开发者的简易性,同时为 Web 应用、桌面应用、手机和智能设备提供专门的授权流程,在业内得到广泛应用,它也率先被 Google、Microsoft、Facebook、Okta 等各大厂商应用于实际的用户授权访问的业务场景中或者基于此协议对外提供服务。它的制定就是为了解决资源的访问安全性(access_token)以及授权灵活性(scope)的问题,OAuth 2.0 能够使得应用对资源的访问更加安全,对开发者来说更加友好。OAuth 2.0与1.0有以下区别:
图四:OAuth 2.0 授权码模式授权流程
这种方式是最常用的流程,也是功能最完整、流程最严密的授权模式。它的特点就是通过客户端的后台服务器,与"服务提供商"的认证服务器进行互动。它适用于那些有后端的 Web 应用。授权码通过前端传送,令牌则是储存在后端,而且所有与资源服务器的通信都在后端完成。这样可以避免令牌泄漏。
图五:OAuth 2.0 隐式模式授权流程
这种方式不通过第三方应用程序的服务器,RFC 6749就规定了这种方式允许直接向前端颁发令牌。这种方式没有授权码这个中间步骤,所以称为(授权码)"隐藏式"(implicit),一般移动 APP 端多选用这种方式。
图六:OAuth 2.0 密码模式授权流程
用户向客户端提供自己的用户名和密码。客户端使用这些信息,向“服务商提供商”索要授权。在这种模式中,用户必须把自己的密码给到客户端,但是客户端不得储存密码(建议)。这通常用在用户对客户端高度信任的情况下,比如客户端是操作系统的一部分,或者由一个著名公司出品。而认证服务器只有在其他授权模式无法执行的情况下,才能考虑使用这种模式。
图七:OAuth 2.0 客户端模式授权流程
指客户端以自己的名义,而不是以用户的名义,向"服务提供商"进行认证。这种方式给出的令牌,是针对第三方应用的,而不是针对用户的,即有可能多个应用共享同一个令牌。
OAuth 2.1 规范草案的作者之一 Aaron Parecki 在一篇博客文章中描述” My main goal with OAuth 2.1 is to capture the current best practices in OAuth 2.0 as well as its well-established extensions under a single name. That also means specifically that this effort will not define any new behavior itself, it is just to capture behavior defined in other specs. It also won’t include anything considered experimental or still in progress. “
简而言之,OAuth 2.1 的出现不是为了推翻 OAuth 2.0 或者完全替代 OAuth 2.0,相反的,OAuth 2.1 的出现,在基于 OAuth 2.0 的基础上,极大地增加了 OAuth 协议的健壮性和扩展性,正如 Aaron Parecki 所说,OAuth 2.1 并不会包含任何被认为是实验性或者尚未落地的东西。
未完待续~
接下来技术咖还会就 OAuth 协议的流程细节、应用场景、各种混合解决方案等进行一一剖析。另外,各位读者朋友,如果有相关问题,欢迎评论区留言,我们会对优质的留言专门汇总后整理成详细的问答类文章分享给大家。
| 留言与评论(共有 0 条评论) “” |