拓展阅读
chat
Q: 介绍一下 oath2
OAuth 2.0(Open Authorization 2.0)是一种授权框架,允许第三方应用程序访问用户在另一个服务提供者上托管的资源,而无需共享用户的凭据(例如用户名和密码)。
它已成为许多网络服务的标准授权协议,包括社交媒体平台、云存储服务、支付系统等。
OAuth 2.0的设计重点是简化客户端开发并提高安全性。
以下是OAuth 2.0的核心组件和工作流程:
核心组件:
-
资源所有者(Resource Owner):拥有受保护资源的用户。该用户授予客户端对其资源的访问权限。
-
客户端(Client):第三方应用程序,希望访问资源所有者的受保护资源。它可以是网站、移动应用程序或其他类型的应用程序。
-
授权服务器(Authorization Server):负责认证资源所有者并颁发访问令牌给客户端。这是OAuth 2.0流程的核心组件之一。
-
资源服务器(Resource Server):托管受保护资源的服务器。客户端通过访问令牌与资源服务器通信以访问资源。
OAuth 2.0的工作流程:
-
客户端注册:客户端向授权服务器注册,并提供其身份验证信息,如客户端ID和客户端密钥。
-
授权请求:客户端请求授权服务器授权,以访问资源所有者的受保护资源。
-
用户身份验证:授权服务器验证资源所有者的身份,并要求资源所有者授予客户端请求的权限。
-
授权授予:如果资源所有者同意授予客户端请求的权限,则授权服务器生成授权码或访问令牌,并将其发送回客户端。
-
令牌颁发:客户端收到授权码或访问令牌后,使用其私有密钥向授权服务器请求令牌。
-
访问令牌使用:客户端使用访问令牌向资源服务器请求受保护资源。资源服务器验证令牌,并根据其有效性决定是否授予对资源的访问权限。
-
访问资源:如果访问令牌有效且授权给客户端访问特定资源,则资源服务器向客户端提供所请求的资源。
OAuth 2.0的授权类型:
-
授权码授权(Authorization Code Grant):用于Web应用程序,客户端通过重定向将用户导向授权服务器,在授权后获取授权码,然后使用该授权码交换访问令牌。
-
隐式授权(Implicit Grant):用于移动和Web应用程序,直接将访问令牌传递给客户端,而不是通过授权码交换。
-
密码授权(Resource Owner Password Credentials Grant):用户直接将其凭据(用户名和密码)提供给客户端,客户端使用这些凭据向授权服务器请求访问令牌。
-
客户端凭证授权(Client Credentials Grant):适用于客户端自身需要访问资源的情况,而不是代表用户。
-
刷新令牌(Refresh Token):用于获取新的访问令牌,以便客户端可以持续访问受保护资源,而无需用户重新登录。
OAuth 2.0是一个灵活且功能强大的授权框架,通过支持不同类型的客户端和授权流程,使得开发者可以在不牺牲安全性的情况下实现对用户资源的安全访问。
为什么 OAuth2.0?解决了什么问题?
OAuth 2.0解决了许多互联网服务中存在的安全和用户体验问题,主要包括以下方面:
-
用户安全性: OAuth 2.0允许用户授权第三方应用程序访问其受保护的资源,而无需共享其凭据(例如用户名和密码)。这样可以大大降低用户的安全风险,因为用户不必将其敏感凭据直接提供给第三方应用程序。
-
用户体验: OAuth 2.0通过简化用户授权过程,提供了更好的用户体验。相比传统的用户名和密码验证,OAuth 2.0使得用户无需在每个第三方应用程序中输入其凭据,而只需在授权服务器上一次性授权即可。这大大简化了用户的操作流程,提高了用户体验。
-
授权管理: OAuth 2.0提供了灵活的授权机制,使得用户能够控制哪些第三方应用程序可以访问其资源,以及可以访问资源的范围。用户可以随时撤销对某个应用程序的访问权限,从而更好地管理其数据的安全性和隐私性。
-
客户端安全性: OAuth 2.0通过使用访问令牌而不是用户凭据来保护第三方应用程序与授权服务器之间的通信。这降低了客户端存储用户凭据的风险,并使得客户端更容易实现安全性措施。
-
适应多种场景: OAuth 2.0提供了多种授权类型,适用于不同的应用场景,包括Web应用程序、移动应用程序、服务端到服务端通信等。这使得OAuth 2.0成为了一个通用的授权框架,能够满足各种不同的需求。
总的来说,OAuth 2.0通过提供安全的授权机制和优化的用户体验,解决了许多传统身份验证方案存在的安全性和便利性问题,成为了互联网服务中广泛使用的标准授权协议。
OAuth 2.0 的交互图
简单的文字描述:
+--------+ +---------------+
| |--(A)- Authorization Request ->| |
| | | |
| |<-(B)-- Authorization Grant ---| |
| | | Authorization |
| |--(C)----- Access Token ------>| Server |
| | | |
| |<-(D)----- Access Token -------| |
| | +---------------+
| |
| | +---------------+
| |--(E)----- Access Token ------>| |
| Client | | |
| |<-(F)--- Protected Resource ---| Resource |
| | | Server |
| |<-(G)----- Access Token -------| |
+--------+ +---------------+
这个图示了OAuth 2.0的基本交互过程:
-
客户端(Client)向授权服务器(Authorization Server)发送授权请求(A)。
-
授权服务器验证用户并向客户端发放授权许可(Authorization Grant)(B)。
-
客户端使用授权许可向授权服务器请求访问令牌(C)。
-
授权服务器验证并发放访问令牌(D)。
-
客户端使用访问令牌向资源服务器(Resource Server)请求受保护资源(E)。
-
资源服务器验证访问令牌并提供受保护资源(F)。
-
客户端可以通过刷新令牌或重新授权等方式获取新的访问令牌(G)。
这是OAuth 2.0交互的基本流程,其中授权码授权流程为例。
OAuth2.0 有哪些开源的优秀框架?给出介绍+网址
OAuth 2.0是一个广泛应用的授权框架,因此有许多开源的优秀框架可以帮助开发者实现OAuth 2.0的功能。
以下是一些流行的OAuth 2.0框架以及它们的介绍和网址:
-
Spring Security OAuth: Spring Security OAuth是Spring框架提供的一个模块,用于实现OAuth 2.0和OAuth 1.0a协议。它提供了可扩展的API,可以轻松地集成到Spring应用程序中。Spring Security OAuth支持各种授权流程和客户端类型。
-
OAuthlib: OAuthlib是一个功能强大的Python库,用于实现OAuth 1.0和OAuth 2.0的服务端和客户端。它提供了灵活的API,支持各种OAuth 2.0授权流程和客户端类型,包括授权码授权、隐式授权、密码授权等。
- 网址:OAuthlib
-
Node OAuth2 Server: Node OAuth2 Server是一个基于Node.js的OAuth 2.0服务器库,用于实现OAuth 2.0的授权服务器。它提供了简单易用的API和中间件,可以轻松地集成到Node.js应用程序中,并支持各种OAuth 2.0授权流程。
-
Apache Oltu: Apache Oltu是一个开源的Java库,用于实现OAuth 2.0和OAuth 1.0a的客户端和服务端。它提供了简单易用的API,支持各种OAuth 2.0授权流程和客户端类型,包括授权码授权、密码授权、客户端凭证授权等。
- 网址:Apache Oltu
-
DotNetOpenAuth: DotNetOpenAuth是一个用于.NET平台的开源库,用于实现OAuth 2.0和OAuth 1.0a的客户端和服务端。它提供了灵活的API和易于集成的ASP.NET控件,可以帮助开发者轻松地实现OAuth 2.0的功能。
这些开源框架提供了丰富的功能和灵活的API,可以帮助开发者快速实现OAuth 2.0的功能,并且可以根据具体需求进行定制和扩展。
OAuth2.0 学习网址
以下是OAuth 2.0的官方学习资料:
- OAuth 2.0 RFC 文档:OAuth 2.0的官方规范文档,定义了OAuth 2.0的工作流程、授权流程、令牌颁发等方面的规范。
- OAuth 2.0官方网站:OAuth 2.0的官方网站提供了规范文档、社区资源、实现库等相关信息。
- OAuth 2.0示例代码:OAuth 2.0网站提供了各种语言的示例代码,包括Java、Python、Node.js等。
- OAuth 2.0规范GitHub Repo:OAuth 2.0规范的GitHub仓库,包含规范文档、讨论、贡献指南等。
- IETF OAuth Working Group:OAuth 2.0的工作组,负责维护和发展OAuth 2.0协议。
- OAuth 2.0 Wiki:OAuth 2.0的维基页面,提供了更多关于OAuth 2.0的信息、用例和示例。
以上资源提供了OAuth 2.0的官方规范、示例代码、社区讨论等相关信息,可以帮助你深入学习和理解OAuth 2.0协议。
OAuth
OAuth是一种开放标准,用于授权,通常被用作互联网用户授权网站或应用程序访问他们在其他网站上的信息的方式,但不会向他们提供密码。
其中, RFC是一系列以编号排定的文件。文件收集了有关因特网相关资讯,以及UNIX和因特网社群的软件文件。
- 缘由
一直想整理写关于 OAuth 的文章, 一直太懒没动笔。今天整理一下,后续可以结合Spring Security。或者自己实现比较轻量级的 OAuth。
简单梳理
从某种角度来说,OAuth2.0定义的很简洁,但是想理解透彻至灵活运用绝非易事。
- 场景。
直接复制前辈的例子:
有一个”云冲印”的网站,可以将用户储存在Google的照片,冲印出来。用户为了使用该服务,必须让”云冲印”读取自己储存在Google上的照片。
传统方法
用户将自己的Google用户名和密码,告诉”云冲印”,后者就可以读取用户的照片了。这样的做法有以下几个严重的缺点。
1) 纯粹的密码登录不安全,且交由”云冲印”保存密码也不安全。
2) 用户无法限制”云冲印”获得授权的范围和有效期, 为了重新取回所有权,用户只有修改密码。如此会导致所有其他三方认证失效。
3) 一个三方被破解,处处被破解。
OAuth 为此而生
基础概念:
1) Third-party application:第三方应用程序,本文中又称”客户端”(client),即上一节例子中的”云冲印”。
2) HTTP service:HTTP服务提供商,本文中简称”服务提供商”,即上一节例子中的Google。
3) Resource Owner:资源所有者,本文中又称”用户”(user)。
4) User Agent:用户代理,本文中就是指浏览器。
5) Authorization server:认证服务器,即服务提供商专门用来处理认证的服务器。
6) Resource server:资源服务器,即服务提供商存放用户生成的资源的服务器。它与认证服务器,可以是同一台服务器,也可以是不同的服务器。
- OAuth 思路
OAuth 在”客户端”与”服务提供商”之间,设置了一个授权层(authorization layer)
。
“客户端”不能直接登录”服务提供商”,只能登录授权层,以此将用户与客户端区分开来。”客户端”登录授权层所用的令牌(token),与用户的密码不同。 用户可以在登录的时候,指定授权层令牌的权限范围和有效期。”客户端”登录授权层以后,”服务提供商”根据令牌的权限范围和有效期,向”客户端”开放用户储存的资料。
- 流程
PS: 图片使用 OmniGraffle 绘制。
所有的操作中,第二步用户的许可是最重要的。
客户端必须得到用户的授权(authorization grant),才能获得令牌(access token)。OAuth 2.0定义了四种授权方式。
1) 授权码模式(authorization code)
2) 简化模式(implicit)
3) 密码模式(resource owner password credentials)
4) 客户端模式(client credentials)
本文主要整理第一种模式,其他自行参考原文。
授权码模式
授权码模式(authorization code)是功能最完整、流程最严密的授权模式。它的特点就是通过客户端的后台服务器,与”服务提供商”的认证服务器进行互动。
它的步骤如下:
(A)用户访问客户端,后者将前者导向认证服务器。
(B)用户选择是否给予客户端授权。
(C)假设用户给予授权,认证服务器将用户导向客户端事先指定的”重定向URI”(redirection URI),同时附上一个授权码。
(D)客户端收到授权码,附上早先的”重定向URI”,向认证服务器申请令牌。这一步是在客户端的后台的服务器上完成的,对用户不可见。
(E)认证服务器核对了授权码和重定向URI,确认无误后,向客户端发送访问令牌(access token)和更新令牌(refresh token)。
A步骤
客户端申请认证的URI,包含以下参数:
-
response_type:表示授权类型,必选项,此处的值固定为”code”
-
client_id:表示客户端的ID,必选项
-
redirect_uri:表示重定向URI,可选项
-
scope:表示申请的权限范围,可选项
-
state:表示客户端的当前状态,可以指定任意值,认证服务器会原封不动地返回这个值。
eg:
GET /authorize?response_type=code&client_id=s6BhdRkqt3&state=xyz
&redirect_uri=https%3A%2F%2Fclient%2Eexample%2Ecom%2Fcb HTTP/1.1
Host: server.example.com
C步骤
服务器回应客户端的URI,包含以下参数:
-
code:表示授权码,必选项。该码的有效期应该很短,通常设为10分钟,客户端只能使用该码一次,否则会被授权服务器拒绝。该码与客户端ID和重定向URI,是一一对应关系。
-
state:如果客户端的请求中包含这个参数,认证服务器的回应也必须一模一样包含这个参数。
eg:
HTTP/1.1 302 Found
Location: https://client.example.com/cb?code=SplxlOBeZQQYbYS6WxSbIA
&state=xyz
D步骤
客户端向认证服务器申请令牌的HTTP请求,包含以下参数:
-
grant_type:表示使用的授权模式,必选项,此处的值固定为”authorization_code”。
-
code:表示上一步获得的授权码,必选项。
-
redirect_uri:表示重定向URI,必选项,且必须与A步骤中的该参数值保持一致。
-
client_id:表示客户端ID,必选项。
eg:
POST /token HTTP/1.1
Host: server.example.com
Authorization: Basic czZCaGRSa3F0MzpnWDFmQmF0M2JW
Content-Type: application/x-www-form-urlencoded
grant_type=authorization_code&code=SplxlOBeZQQYbYS6WxSbIA
&redirect_uri=https%3A%2F%2Fclient%2Eexample%2Ecom%2Fcb
E步骤
认证服务器发送的HTTP回复,包含以下参数:
-
access_token:表示访问令牌,必选项。
-
token_type:表示令牌类型,该值大小写不敏感,必选项,可以是bearer类型或mac类型。
-
expires_in:表示过期时间,单位为秒。如果省略该参数,必须其他方式设置过期时间。
-
refresh_token:表示更新令牌,用来获取下一次的访问令牌,可选项。
-
scope:表示权限范围,如果与客户端申请的范围一致,此项可省略。
eg:
HTTP/1.1 200 OK
Content-Type: application/json;charset=UTF-8
Cache-Control: no-store
Pragma: no-cache
{
"access_token":"2YotnFZFEjr1zCsicMWpAA",
"token_type":"example",
"expires_in":3600,
"refresh_token":"tGzv3JOkF0XG5Qx2TlKWIA",
"example_parameter":"example_value"
}
相关参数使用JSON格式发送(Content-Type: application/json),HTTP头信息中明确指定不得缓存。