授权流程主要分为两步:
步骤一:请求授权码
RP 通过将浏览器重定向到 OP 的 OAuth 2.0 授权端点来启动用户身份验证。具体示例:
HTTP/1.1 302 Found
Location: https://accounts.cloudtrust.com.cn/auth
?scope=openid
&response_type=code
&client_id=s6BhdRkqt3
&state=af0ifjsldkj
&redirect_uri=https%3A%2F%2Fclient.example.org%2Flogin
请求参数及其解释:
response_type: 指授权模式类型。
scope: 指定请求授权的范围。 范围值 “openid” 表示请求 OpenID 身份认证和身份令牌。
client_id: OP 上 RP 的客户端 ID 。 当 RP 向 OP 注册时,可获得该标识符。
state: 由 RP 设置的不透明值,以保持请求和回调之间的状态。
redirect_uri: 验证响应后的 RP 回调 URI。
在 OP 中,通常会检查用户会话的有效性(由浏览器cookie建立)来进行身份验证,如果无效,则提示用户登录,并询问用户是否同意登录 RP 。然后,OP 将使用授权码(成功)或错误代码(如果访问被拒绝或发生了其他错误,例如请求格式错误)调用 redirect_uri 。示例如下:
HTTP/1.1 302 Found
Location: https://client.example.org/cb?
code=SplxlOBeZQQYbYS6WxSbIA
&state=af0ifjsldkj
RP必须验证状态参数,并使用授权码获取身份令牌(ID Token)。
步骤二: 获取令牌
授权码是一个中间凭证,仅用于对上一步中获得的授权进行编码。因此,它对于RP是不透明的,只对OP服务器有意义。 要获取身份令牌,RP 必须将授权码提交给 OP,这需要发出直接的后端请求。 这样做原因有两个:
在发送令牌之前,OP验证RP身份。
将令牌直接传递给RP,从而避免将它们暴露给浏览器。
在OP的令牌端点用授权码获取令牌:
POST /token HTTP/1.1
Host: accounts.cloudtrust.com.cn
Content-Type: application/x-www-form-urlencoded
Authorization: Basic czZCaGRSa3F0MzpnWDFmQmF0M2JW
grant_type=authorization_code
&code=SplxlOBeZQQYbYS6WxSbIA
&redirect_uri=https%3A%2F%2Fclient.example.org%2Fcb
Client ID和 Client Secret 通过请求头参数 Authorization 传递。 除了HTTP基本认证模式(basic authentication)之外,OpenID Connect 还允许使用JWT签名断言进行身份验证,这避免了RP 用 Client Secret 来请求令牌,从而提供更好的安全性。
请求成功后,OP 回复中的 JSON 将带有身份令牌,访问令牌以及刷新令牌(可选):
HTTP/1.1 200 OK
Content-Type: application/json
Cache-Control: no-store
Pragma: no-cache
{
"id_token": "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJhbGljZSIsImlzcyI6Imh0dHB
zOi8vYWNjb3VudHMuY2xvdWR0cnVzdC5jb20uY24iLCJhdWQiOiJjbGllbnQtMTIzNDUiLCJ
ub25jZSI6Im4tMFM2X1d6QTJNaiIsImF1dGhfdGltZSI6MTMxMTI4MDk2OSwiYWNyIjoiY2x
vdWR0cnVzdC5sb2EuaGlzZWMiLCJpYXQiOjEzMTEyODA5NzAsImV4cCI6MTMxMTI4MTk3MH0
.O8lB_ij70i0f1m-tbM--KD6WNUAM2DiWIYl3yuJ1jLOjiAzs3qB6-IfFDpC7f2gxcsJymPY
h8S7t96gO7m-ngl2MAufWbqcEkiYSp6nkwOlpvUy3XdEg7qLq1im7ZNoikk7bPNpcYJZfqSI
IuSS7sVi4LI3bD5KYHs3EHUGakbk"
"access_token": "SlAV32hkKG",
"token_type": "Bearer",
"expires_in": 3600,
}
身份令牌是 JWT 形式,必须被 RP 验证后才能接受。
请注意,请求响应中还包括 bearer 类型的访问令牌。 这是为了确保令牌响应符合 OAuth 2.0 规范。 对于仅请求身份令牌的基本 OpenID 身份验证请求,此访问令牌是虚设的,可以安全地被忽略。 然而,当请求访问UserInfo端点上的用户信息数据时,访问令牌是必要的。