OpenID Connect 授权码模式更新时间: 2024-10-17 16:12:00
一、场景介绍
这个场景适用于安卓系统的移动端和电视应用,计划通过OpenID Connect协议接入小米帐号。通过ID Token,应用可以获取用户的身份认证信息(ID Token)及其基本开放信息,确保用户安全登录。首次登录时,用户需要同意授权,当身份令牌过期后,可以通过令牌轮换的方式,获取新的身份令牌。
二、接入准备
- 接入小米账号OAuth功能
- 开通scope: openid
三、概要流程
+------------+ +------------+ +------------+
| | | | | |
| User | | Client | | Xiaomi |
| | | | | |
+-----+------+ +-----+------+ +-----+------+
| | |
| | |
| 1.Login | |
+----------------------->| |
| | |
| 2.Authorize | |
+------------------------+------------------------->|
| | |
| | 3.Auth code |
| |<-------------------------+
| | |
| | 4.request id-token |
| +------------------------->|
| | |
| | 5.id-token |
| |<-------------------------+
| | |
| +----+ |
| | | |
| | |6.validate id-token |
| | | |
| |<---+ |
| | |
| | |
| 7.Login success | |
|<-----------------------+ |
| | |
| | |
| | |
四、授权码模式接入
Step 1 : 用户授权
获取用户授权 https://account.xiaomi.com/oauth2/authorize
- 请求code码,用户点击同意
参数名 | 是否必填 | 参数解释 |
client_id | 必填 | 申请应用时分配的应用 ID,可以在应用详情页获取 |
redirect_url | 必填 | 小米账号OAuth应用配置的回调地址, 必须和申请应用是填写的一致(参数部分可不一致) |
scope | 必填 | 一个字符串数组,以空格分开,必须包含字符串openid,其他权限请参见业务的scope描述,根据需要拼接权限项scope。 |
response_type | 必填 | 描述获取授权的方式, 这里 response_type=code |
oidc_nonce | 选填 | OpenId Connect 规范,用于验证请求 |
Step 2 :下发ID Token
http://account.xiaomi.com/oauth2/auth/token
- 业务通过Auth Code ,secret 等基础信息,从小米账号获取ID Token
参数名 | 是否必填 | 参数解释 |
client_id | 必填 | 申请应用时分配的应用 ID,可以在应用详情页获取 |
code | 必填 | 用来换取 access_token 和id_token的授权码,有效期为 10 分钟且只能使用一次 |
redirect_uri | 必填 | 小米账号OAuth应用配置的回调地址, 必须和申请应用是填写的一致(参数部分可不一致) |
client_secret | 必填 | 申请应用时分配的 AppSecret |
grant_type | 必填 | 这里 grant_type=authorization_code |
Response:
{
"access_token": "V3_lzGCv7LqvYFP6mBoanWLuRjh8MMhPHx4gRq8SQHZIci6MC3eQ6IJa5YQpqhOII39h18dKFDiE8wKdz7u8vUAe654FnmEwFBu54rJcOg9qcOKrG1mbBYjuczASwjYTypJlUT4HGJPbeulOqIzFTmBQo6d1_4rmfQLtM4pVHPFzCM",
"token_type": "mac",
"scope": "1 3 5 ",
"expires_in": 259200,
"refresh_token": "R3_QqlAYhdl1Olb7PuH3cRO1FptL7dHyNEfv2aC4TxFuUaZTFeBO0EPg4ye6AeaNwGaNqK15vMGudqWXPnPWtlydOhrtYSbQN7aA_sTUUR4FzdWPHpQ23F7T9Crpu0Y3C9seQKfOENvKptUZQtR4ZarUm71GKoPiuwkTYBfcwVLVf2r-aZ5Rbh0e0t_ZclTdvru",
"mac_algorithm": "HmacSHA1",
"mac_key": "Hu7bX4kTjnC1o4Pi1QvYdcEN4ek",
"openId": "2.0:pbbikQHaDlvoASCssZs3/jVAX1w=",
"union_id": "QcRJkVC_10gI9yQwwn3swNz8_4R0mJ8m8OZNyJFA",
"id_token": "eyJraWQiOiJLb1prRE1GOHZwU0xqekNjMnprUFJwWHVKeGRqUTlkSkc5bFExd2I0IiwiYWxnIjoiUlMyNTYifQ.eyJhdF9oYXNoIjoiT3JrY0c4SHo3c3F2MTRBRFBLVlY5QSIsInN1YiI6IlFjUkprVkNfMTBnSTl5UXd3bjNzd056OF80UjBtSjhtOE9aTnlKRkEiLCJhdWQiOiIxMTczNzAyMDAwIiwiYXpwIjoyODgyMzAzNzYxNTE5MjEyNjk4LCJvcGVuaWQiOiIyLjA6cGJiaWtRSGFEbHZvQVNDc3NaczMvalZBWDF3PSIsImlzcyI6Imh0dHBzOi8vYWNjb3VudC54aWFvbWkuY29tL29hdXRoMiIsIm5pY2tuYW1lIjoiQ3JvdXBpZXIiLCJleHAiOjE2OTY5Mzc2MjUsImlhdCI6MTY5NjkzNDAyNSwianRpIjoiNTQ3OWEyZTYtYWJhMi00YTA5LWJhYTUtMTJkMDUxNjMwYzljIiwicGljdHVyZSI6Imh0dHBzOi8vY2RuLmNuYmoxLmZkcy5hcGkubWktaW1nLmNvbS91c2VyLWF2YXRhci80N2NjMTUzMy1hM2Q4LTQ3YmMtOGM2Ni04NDhmZGNiMThkMzMuanBnIn0.GFVlQJudzj_Sy77COUkoLkar833Q7goq6Nel1GKEfycy5rIlNnbYoA-48PKkva9oFe9qzbnmERda94H2AIzvJEp2w_WaZIofl4FxZCMi06zAqmcJDb-r0Hv1J6oAKGHc1buP6J4jm084jJaWg2d4PZ_G-3B_XKJSSvSuHKnxOBP9oVmp54beRS4IjKaQ_Tf4j6ZZiIhnzRk-ObRa58Nvajkxt8Dypuc1ywUbFNcp0GLHgchN4gPcoUcafsYFhCJV3fuCV11p2fgQueg9E5WSW8arDKOT-kW_xFbd-7WlcmsyQgNfxeCIqO00M0CT6kw1I3KYzEFI98pwPzPxes-IUQ",
"traceId": "97acd63de502df099bd334902e23ebaf"
}
ID Token解析后结果:
{
"at_hash": "l8LyD8BUDd0LkENqfQezgA",
"sub": "QcRJkVC_10gI9yQwwn3swNz8_4R0mJ8m8OZNyJFA",
"time_stamp": "1700623277",
"openid": "2.0:pbbikQHaDlvoASCssZs3/jVAX1w=",
"data2": "456",
"iss": "https://account.xiaomi.com/oauth2",
"data1": "123",
"picture": "https://cdn.cnbj1.fds.api.mi-img.com/user-avatar/47cc1533-a3d8-47bc-848fdcb18d33.jpg",
"aud": "1173702000",
"oidc_extend": "extend",
"azp": 2882303761519212500,
"nickname": "userName",
"exp": 1700638453,
"iat": 1700634853,
"jti": "b7057153-2ed7-4a8a-a4b7-723f68241830"
}
五、令牌轮换
https://account.xiaomi.com/oauth2/auth/token
- 令牌过期后,使用使用下发令牌接口获取的refreshToken访问小米账号OAuth令牌轮换端点,直接生成ID Token和新的Refresh Token,后续获取新的令牌,只需要进行刷新操作
参数名 | 是否必填 | 参数解释 |
client_id | 必填 | 申请应用时分配的应用 ID,可以在应用详情页获取 |
refresh_token | 必填 | 授权码模式下发访问令牌时下发的刷新令牌,只可使用一次 |
redirect_uri | 必填 | 回调地址, 必须和申请应用是填写的一致(参数部分可不一致) |
client_secret | 必填 | 申请应用时分配的 AppSecret,需要 URLEncode |
grant_type | 必填 | 这里 grant_type=refresh_token |
六、验证ID Token有效性
方式一:标准验证(推荐)
适合场景:无特殊校验逻辑,希望开箱即用的场景
- 接收客户端发送过来的ID Token。
- 调用标准库进行ID Token校验并获取用户信息。
方式二:手动验证
适合场景:定制化参数校验场景
- 从https://account.xiaomi.com/oauth2/.well-known/openid-configuration的响应消息体中获取jwks_uri的属性值,该属性值为公钥URI,调用该URI,在响应消息体中获取keys的属性值,并根据keys的属性值生成公钥。
- 验证签名。ID Token是JWT格式的,验证ID Token的签名可以采用通用的JWT库,例如jwt.io。
- 验证ID Token中iss字段的值是否等于“https://account.xiaomi.com/oauth2”。
- 验证ID Token中aud字段的值等于应用的client_id。
- 验证ID Token中的过期时间(exp字段)是否已过期。
- 如果以上验证均通过,则表示用户ID Token验证通过,应用可使用登录结果中的用户信息。
七、附录
验证Token
各语言类库: https://jwt.io/libraries
在线验证: https://jwt.io/#debugger-io
协议标准:https://openid.net/specs/openid-connect-core-1_0.html#IDTokenValidation
上一篇:OAuth2.0 授权码模式
下一篇:OAuth SDK合规使用说明
文档内容是否有帮助?
有帮助
无帮助