OAuth 协议 1.0 介绍

  如今网站与网站的通信,API应用等等,往往需要用户登入,但传统的登入模式常常涉及明文密码,非常的不安全,因此产生了OAuth协议,用户无需输入密码,通过密钥进行加密与通信,并可以及时回收权限,有效地解决了安全问题。OAuth的安全,容易使用,成为当下流行的一种认证模式,如google, Facebook, 国内有douban, 新浪微博等等都有API上的应用。

一、术语 (括号内为旧版的名称)

因RFC 5849 The OAuth 1.0 Protocol在名称上与OAuth未标准化前有出入,为了和标准接轨本文使用新的名称。

1. client (Consumer)

可以发出OAuth认证请求的HTTP客户端。

2. server (Service Provider)

可以接收OAuth认证请求的HTTP服务端。

3. protected resource

可以从服务器里通过OAuth请求所获得的受限资源。

4. resource owner (User)

可以通过证书访问和控制受限资源的实体。

5. credentials

证书是由唯一标识(id)和所对应的密钥(secret)组成。共分三种:
client (Consumer Key and Secrect),
temporary (Request Token and Secrect),
token ( Access Token and Secret)

6. token

由服务端提供的唯一标识,用于之后的加密与受信请求。

二、OAuth流程

1. OAuth请求的3个步骤:

  1. client 申请 temporary credentials
  2. resource owner 认证 temporary credentials
  3. client 用已认证的 temporary credentials 换取 token credentials

2. client 申请 temporary credentials

client发送:
oauth_consumer_key
oauth_signature_method
oauth_timestamp (signature_method为PLAINTEXT可忽略)
oauth_nonce (signature_method为PLAINTEXT可忽略)
oauth_version(可选)
oauth_signature
oauth_callback (如果不使用callback,该项必需为oob,意为out-of-band)

server返回:
oauth_token
oauth_token_secret
oauth_callback_confirmed

3. resource owner 认证 temporary credentials

用户登入server/path?oauth_token=xxx, 并同意temporary credentials行为或分配权限。
server权限分配完毕重定向至oauth_callbak?oauth_token=xxx&oauth_verifier=xxx

4. client 用已认证的 temporary credentials 换取 token credentials

client发送:
oauth_consumer_key
oauth_token
oauth_signature_method
oauth_timestamp (signature_method为PLAINTEXT可忽略)
oauth_nonce (signature_method为PLAINTEXT可忽略)
oauth_version(可选)
oauth_signature
oauth_verifier

server返回:
oauth_token – token credentials id
oauth_token_secrect – token credentials secrect

至此,通过oauth_token与oauth_token_secret便可调用相就的API访问server上的protected resource。

以下是对OAuth请求的具体描述,一般来说通过OAuth现有的API无需知道以下细节,通过了解其通信规范也可轻松定制出自已的OAuth API库

三、OAuth请求构成

1. OAuth头

Authorization: OAuth realm=”example”, [oauth参数列表]

2. 参数描述

a. 通用
oauth_consumer_key 等价于client id
oauth_token 用以请求的token
oauth_signature_method 签名生成手段
oauth_timestamp 时间戳
oauth_nonce 确保请求唯一性的随机字串
oauth_version oauth版本,可选,若要指定则必须是1.0
oauth_signature oauth签名
b. 申请 temporary credentials 相关
oauth_callback 回调地址,若不指定则为oob
c. 申请 token credentials 相关
oauth_verifier 认证码

3. signature 生成

a. 基本字串的构成
基本字串共分5个部分
i. HTTP请求方法
如GET, POST, HEAD等
ii. &
iii. 基本URI
不包含query_string的完整uri并经过encoded
如 http://www.example.com/request?a=c
则 URI为 http://www.example.com/request

基本URI必定包含scheme(http://, https://等), domain(www.example.com), path(/request),如果http请求端口不是80,https请求不是443,那么必定寻包含port。
必定不包含query_string(任何参数)
如 https://www.example.com:8080/request

iv. &
v. 规则化的参数
1. 所有的名称和值必需encoded。
2. 参数按ascii码序排列。
3. 所有参数都有=,即使值为空。
4. 有&连接所有变量为一个字串。

{dot}
node[fontsize=10]
edge[fontsize=8]
rankdir=LR

node[shape=record]
base_string[label=” HTTP请求方法|&| 规则化的URI|&| 规则化的参数”]
uri[label=”URI的组成|scheme|domain| port|path”]
params[label=”规则化步骤| 1. encode参数名与值\l|2. 按ascii正序排列\l|3. 使用’&’连接\l| 4. encode所生成的字串\l”]

node[shape=box]
method[label=”GET/POST/HEAD等”]

node[shape=note]
uri:port -> “当且仅当scheme为http,port为80或https 443时无需指定\n如 https://www.example.com:8080/request”[dir=none]
params:val -> “‘=’必须指定,即使值为空\n如 a=3&b=&c=4″[dir=none]
params:encode -> “encode方法: 除 字母 数字 – . _ ~ 外所有字符都转为%XX(大写形式)\n有别于web的encode,如php的rawurlencode”[dir=none]

base_string:method -> method
base_string:uri -> uri
base_string:params -> params
{/dot}

加密字串
共有3种方法:HMAC-SHA1, RSA-SHA1, PLAINTEXT
a. HMAC-SHA1
digest = HMAC-SHA1(key, text)
key的构成为由3部分
1. client shared-secret
2. &
3. token shared-secret
&必须有即使token shared-secret为空。
得到的digest进行base64编码。

oauth encode方法(有别与php的rawurlencode或urlencode)
除了字母,数字,- . _ ~ 外所有的字符都需转化成%XX(大写)形式。
注意,空格必须转为%20,~不需要转。

四、相关链接

OAuth官网
RFC5849 OAuth 1.0 协议

发表评论

电子邮件地址不会被公开。 必填项已用*标注