理解OAuth2协议原理

  • OAuth2简介
    • 角色
    • 流程
    • 客服端注册
    • Client Type
  • 四种授权模式
    • 授权码模式
    • 隐藏式
    • 密码式
    • 凭证式
    • RefreshToken
    • Github Demo加深理解
  • Reference

OAuth2简介

OAuth 是一个开放授权协议标准,允许用户授权第三方应用访问他们存储在另外的服务提供者上的信息,而不需要将用户名和密码提供给第三方应用或分享他们数据的全部内容。

OAuth2 是 OAuth 协议2.0版本,不兼容1.0版本。RFC6749 文档描述了 OAuth2 协议的全部内容。本文将会基本 RFC协议文档去带大家理解OAuth2协议,如果读完以后感觉晦涩弄懂,可以结合 阮一峰大神这个博客去理解。

角色

例子:Ruby China这个网站支持使用github账号登录,当用户选择使用github登录的时候,需要用户先输入github账号密码登录github,然后询问用户是否授权rubyChina这个网站获取用户的信息。RubyChina


这就是一个第三方登录的一个例子, 下面列出的是OAuth2协议中所涉及到的几个角色以及描述。

角色 描述
Resource Owner 资源所有者,一般指登录用户 (如:github用户)
Http Service HTTP服务提供商,例如github
Client (Third Party application) 客户端,也叫第三方应用,如Ruby China
Authorization Server (授权服务器)在对用户认证并且获得用户授权以后,给client发放access Token的服务器
Resource Server 资源服务器,即服务提供商存放用户受保护资源的服务器。它与认证服务器,可以是同一台服务器,也可以是不同的服务器
User Agent 用户代理,一般指浏览器

流程

  • A)用户打开客户端以后,客户端要求用户给予授权。
  • B)用户同意给予客户端授权。
  • C)客户端使用上一步获得的授权,向认证服务器申请令牌。
  • D)认证服务器对客户端进行认证以后,确认无误,同意发放令牌。
  • E)客户端使用令牌,向资源服务器申请获取资源。
  • F)资源服务器确认令牌无误,同意向客户端开放资源。

客服端注册

  • 如果一个第三方应用想使用第三方登录,该第三方应用的开发者需要先到 Authentication Server去申请一个 client,一般需要:
    A. 应用名称,
    B. Home Page url
    D. Redirect URI
    D. 指定client type
  • 注册完以后可以拿到 clientId 和 client secret
  • 参考第三方网站开发文档,选择适合的授权模式去实现 OAuth2 第三方授权登录

例如如果你想要你自己的网站支持github登录的话,首先你要去github上面注册一个client:

Client Type

官方协议解释:OAuth defines two client types, based on their ability to authenticate securely with the authorization server (i.e., ability to maintain the confidentiality of their client credentials,根据client申请方时候有能力去维护client的credentials信息分为 confidential和public两种。

  • confidential: Clients capable of maintaining the confidentiality of their credentials (e.g., client implemented on a secure server with restricted access to the client credentials), or capable of secure client authentication using other means
  • public: Clients incapable of maintaining the confidentiality of their credentials (e.g., clients executing on the device used by the resource owner, such as an installed native application or a web browser-based application), and incapable of secure client authentication via any other means

四种授权模式

OAuth2的核心是认证服务器向第三方颁发令牌,其根据不同的互联网应用场景,定义了
一下四种允许第三方应用获取令牌的模式。分别是:

类型 描述
授权码模式 基于授权码code,是最严谨,最安全,流程最完整的授权模式
隐藏式 (简化模式) 授权码模式的简化版本,缺少了授权码环节
密码模式 第三方应用直接使用资源拥有者的用户密码去获取令牌
客户端凭证模式 第三方应用使用客户端凭证请求令牌

假设用户A通过浏览器访问网站:https://client.example.com,而该网站需要用户A授权,去访问用户A在网站 http://server.example.com 上面存储的个人信息。

我们以这个例子来解释下面介绍的各种模式。下面所说的客户端指的是 https://client.example.com,授权服务器以及资源服务器指的是 http://server.example.com,假设它们在同一个服务器上。

一下四种模式涉及到一些代码名称,先给大家列出来:

名词 描述
reponseType 表示请求返回的类型,有code和token两种,code表示请求返回授权码,token表示请求返回accessToken
clientId 客户端注册的时候认证服务器发放的id,用于认证客户端的身份
Client_secret 客户端注册的时候认证服务器发放的客户端秘钥,用于认证客户端的身份
state 不是必须的,客户端请求认证服务器时候带上一个state,认证服务器返回的时候原封不动地返回这个state,告诉客户端是认证服务器的response,而不是别人,用于防止跨站请求攻击好像。
redirectUri 用户授权或者否定授权以后认证服务器重定向回客户端的url
Scope 表示请求的权限范围
Code 授权码,用于客户端向认证服务器请求token,一般10分钟过期,而且只能使用一次
grantType 表示授权方式, authorization_code 表示授权码方式, password表示密码方式, client_credentials表示凭证方式

授权码模式

授权码(authorization code)方式,指的是第三方应用先申请一个授权码,然后再用该码获取令牌
这种方式是最常用的流程,安全性也最高,它适用于那些有后端的 Web 应用。授权码通过前端传送,令牌则是储存在后端,而且所有与资源服务器的通信都在后端完成。这样的前后端分离,可以避免令牌泄漏。

  • A)用户访问客户端(第三方应用),客户端引导(重定向)用户的代理(浏览器)去到授权服务器的授权页面,这个时候客户端会在URI上附上 clientId, redirectUri, requestScope以及 local state,例如:
GET HTTP/1.1
http://server.example.com/authorize?response_type=code&client_id=s6BhdRkqt3&state=xyz&redirect_uri=https%3A%2F%2Fclient%2Eexample%2Ecom%2Fcb&scope=read
  • B)授权服务器要求用户A输入用户密码认证身份,并询问用户A是否同意授权
  • C)假设用户同意授权,授权服务器使用 redirectUri (在authorization request中redirectUri或者客户端注册是的redirectUri)将用户导向客户端,并附上一个授权码code
https://client.example.com/cb?code=SplxlOBeZQQYbYS6WxSbIA&state=xyz
  • D)客户端拿到授权码code以后,在后台使用授权码向授权服务器发送post请求换取accessToken令牌,并附上在(A)这个步骤请求授权码的时候的redirectUri
POST HTTP/1.1
http://server.example.com/token
grant_type=authorization_code&code=SplxlOBeZQQYbYS6WxSbIA&redirect_uri=https%3A%2F%2Fclient%2Eexample%2Ecom%2Fcb&clientId=xxx&clientSecret=xyzz
  • E)认证服务器认证客户端,检验授权码以及redirectUri,检验成功后发放 accesToken 以及 refreshToken
    最后客户端就可以使用令牌向resourceServer请求资源了。

隐藏式

有些 Web 应用是纯前端应用,没有后端。这时就不能用上面的方式了,必须将令牌储存在前端。
OAuth2 允许直接向前端颁发令牌。这种方式没有授权码这个中间步骤,所以称为(授权码)“隐藏式”(implicit)

令牌直接存储到前端浏览器,是不太安全的。

  • A)用户访问客户端(第三方应用),客户端引导(重定向)用户的代理(浏览器)去到授权服务器的授权页面,这个时候客户端会在URI上附上 clientId, redirectUri, requestScope以及 local state,例如:
GET HTTP/1.1
http://server.example.com/authorize?response_type=code&client_id=s6BhdRkqt3&state=xyz&redirect_uri=https%3A%2F%2Fclient%2Eexample%2Ecom%2Fcb&scope=read
  • B)授权服务器要求用户A输入用户密码认证身份,并询问用户A是否同意授权
  • C)假设用户同意授权,授权服务器使用 redirectUri (在authorization request中redirectUri或者客户端注册是的redirectUri)将用户导向客户端,并附上令牌 accessToken
https://client.example.com/cb?#access_token=2YotnFZFEjr1zCsicMWpAA&state=xyz&token_type=example&expires_in=3600

令牌的位置URL 锚点(fragment),而不是查询字符串,好像是为了避免中间人攻击啥的 (http)

  • D、E、G)看网上说是使用一段脚本能够将token从(C)重定向的URI抽取出来,具体怎么时候就不是很清楚了

最后客户端就可以使用令牌向resourceServer请求资源了。

密码式

OAuth2 允许用户把用户名和密码直接告诉该应用,该应用就使用你的密码申请令牌,这种方式称为"密码式"(password)
直接提供账号密码,风险很大,所以应当是用户高度新人客户端才会使用这种方式。

客户端直接使用用户的账户密码去换取accessToken,发送的post请求:

POST
http://server.example.com/token
body: grant_type=password&username=johndoe&password=A3ddj3w&clientId=xxx

凭证式

客户端直接使用客户端凭证(client credentials)向认证服务器请求令牌,适用于没有前端的命令行应用。


同样使用post请求:

POST
http://server.example.com/token
body: grant_type=client_credentials&clientId=xxx&client_secret=SECRET

RefreshToken

  • client请求token的时候,服务器一般会返回一个refreshToken,一般来说accessToken的过期时间很短,当accessToken过期了之后,授权服务器允许client通过refreshToken去再次请求一个新的accessToken。所以refreshToken的过期时间肯定是要比accessToken长。

refreshToken是可选的,如果对于安全要求比较高的话,可以不用。

Github Demo加深理解

这个Demo的话参考阮一峰大神这个就行了:很简单,我一开始也是跟着大神学的,啊哈哈哈哈!
github OAuth2 Demo

Reference

http://www.ruanyifeng.com/blog/2019/04/oauth_design.html
https://tools.ietf.org/html/rfc6749
https://docs.github.com/en/free-pro-team@latest/developers/apps/authorizing-oauth-apps#web-application-flow

理解OAuth2协议原理相关推荐

  1. 深入理解http协议原理

    简述 对于Android开发来说,HTTP是网络开发中最为重要的.使用频率最高的手段,也是面试常问到的面试题.因此,深入了解HTTP是必备技能,只有了解它的基本原理才能够更好的运用. HTTP网络请求 ...

  2. OAuth2.0 原理流程及其单点登录和权限控制

    作者:王克锋 kefeng.wang/2018/04/06/oauth2-sso 单点登录是多域名企业站点流行的登录方式.本文以现实生活场景辅助理解,力争彻底理清 OAuth2.0 实现单点登录的原理 ...

  3. 深入理解oauth2框架,以及实际运用

    1.什么是单点登录 1.1.多点登录 传统的多点登录系统中,每个站点都实现了本站专用的帐号数据库和登录模块.各站点的登录状态相互不认可,各站点需要逐一手工登录.如下图,有两个术语含义如下: 认证(au ...

  4. 深入理解OAuth2.0协议

    1. 引言 如果你开车去酒店赴宴,你经常会苦于找不到停车位而耽误很多时间.是否有好办法可以避免这个问题呢?有的,听说有一些豪车的车主就不担心这个问题.豪车一般配备两种钥匙:主钥匙和泊车钥匙.当你到酒店 ...

  5. Spring Security并没有那么难嗷 简单理解OAuth2.0

    文章目录 1. 基本概念 1.1 什么是认证 1.2 什么是会话 1.3 什么是授权 1.4 授权的数据模型 1.5 RBAC 1.5.1 基于角色的访问控制 1.5.2 基于资源的访问控制 2. 基 ...

  6. Zookeeper ZAB协议原理浅析

    文章目录 前言 1. 基本角色和概念 2. Leader Election 3. Discovery 4. Synchronization 5. BroadCast 后记 前言 DTCC 要在下周一到 ...

  7. Http协议原理解析

    一:http的由来: OSI模型把网络通信分成七层:物理层.数据链路层.网络层.传输层.会话层.表示层和应用层,对于开发网络应用人员来说,一般把网络分成五层,这样比较容易理解.这五层为:物理层.数据链 ...

  8. 在实践中深入理解IP协议

    本文为我个人计划撰写的博客专题<在实践中深入理解常见网络协议>中关于IP协议的一篇,有兴趣的朋友可以继续关注我的博客,我将会陆续撰写各种协议的实践分析文章. TCP/IP协议栈其实当然不止 ...

  9. HTTPS协议原理分析

    HTTPS协议原理分析 HTTPS协议需要解决的问题 HTTPS作为安全协议而诞生,那么就不得不面对以下两大安全问题: 身份验证 确保通信双方身份的真实性.直白一些,A希望与B通信,A如何确认B的身份 ...

最新文章

  1. extern “C”的作用详解
  2. Ruby_day[1]控制流2
  3. 【小米笔试题】朋友圈问题-并查集解法
  4. String, StringBuilder 与StringBuffer的区别与联系
  5. P1993 小K的农场 (差分约束)
  6. 简单话题:LED呼吸灯和串口LED指示灯
  7. [.NET领域驱动设计实战系列]专题二:结合领域驱动设计的面向服务架构来搭建网上书店...
  8. MySql 获取当前节点及递归所有上级节点
  9. Day_05 显示字符串
  10. c语言字符型计算器,C语言字符计算器
  11. C++实现走迷宫算法
  12. mysql execute stmt_execute_prepared_stmt()
  13. angular4使用原生JS属性报错error TS2339: Property 'checked' does not exist on type 'HTMLElement'.
  14. php如何让img显示为圆形,css如何将图片设置为圆形图片
  15. 冷山的博客思听有声书摘下载索引页
  16. 数据库的数据文件和日志文件
  17. Linux系统故障-MBR(主引导记录)被破坏的解决方法
  18. u3d android 优化
  19. 【T+】畅捷通T+自定义报表将所有月份发生数在同一张表上体现
  20. 车联网目前在我国主要的应用市场

热门文章

  1. 去掉li标签前面的样式
  2. 2022-2027年中国丙肝药物行业市场调研及未来发展趋势预测报告
  3. 中M22春C、Java入门练习-7.5
  4. 微软发布最新补丁,修改VS2005可能被他人完全控制的漏洞
  5. 用python写全自动赛马娘脚本 全自动赛马娘脚本 Auto_Pretty Derby
  6. QTreeWidget 与复选框相同的节点选择
  7. 一个不错的看电影的地方
  8. 腹外斜肌(04):负重体侧屈
  9. 架构师的软实力之管理
  10. BSC全节点搭建实录,附详细攻略