一、移动端使用微信登录流程
1.1 实际业务流程图:
1.2 微信授权登录流程图:
图中名词解释:
(1)什么是OAuth2.0?
OAuth 2.0(Open Authorization 2.0)是一种用于授权 的开放标准,旨在允许第三方应用程序 访问用户 在另一个服务提供者上的资源,而无需共享用户的凭证。该协议广泛用于身份验证和授权的领域,特别是在互联网服务和应用程序中。
(2)角色
-
资源所有者(Resource Owner): 拥有资源的用户,这是指 ------ 用户。
-
客户端(Client): 试图访问资源的应用程序或服务,这里指 ------ 第三方应用。
-
授权服务器(Authorization Server): 负责验证资源所有者的身份并授予客户端访问资源的权限,这里指------微信服务器。
-
资源服务器(Resource Server): 存储和管理受保护的用户资源,仅在得到授权后提供这些资源,这里指------微信服务器。
二、步骤
2.1 注册微信开放平台账号
注册后获取AppId
和secret
2.2 对接SDK(前端需要做)
(1)IOS对接SDK
java
-(void)sendAuthRequest
{
//构造SendAuthReq结构体
SendAuthReq* req =[[[SendAuthReq alloc]init]autorelease];
req.scope = @"snsapi_userinfo"; // 只能填 snsapi_userinfo
req.state = @"123";
//第三方向微信终端发送一个SendAuthReq消息结构
[WXApi sendReq:req];
}
(2) Android对接SDK
java
{
// send oauth request
Final SendAuth.Req req = new SendAuth.Req();
req.scope = "snsapi_userinfo"; // 只能填 snsapi_userinfo
req.state = "wechat_sdk_demo_test";
api.sendReq(req);
}
2.3 触发微信授权登录
我们以大众点评APP为例:
(1) 拉起微信客户端
有了步骤【2.2】后,用户在APP中点击微信登陆,微信客户端被拉起。
java
# 请求参数:
appid: 步骤【2.1】注册后可以获取
scope: 应用授权作用域,获取用户个人信息则填写 snsapi_userinfo
(2) 用户点击【同意】【拒绝】【取消】返回值
java
{
"ErrCode": {
"ERR_OK": 0,(用户同意)
"ERR_AUTH_DENIED": -4,(用户拒绝授权)
"ERR_USER_CANCEL": -2(用户取消)
},
"code": "用户换取 access_token 的 code,仅在 ErrCode 为 0 时有效",
"state": "第三方程序发送时用来标识其请求的唯一性的标志,由第三方程序调用 sendReq 时传入,由微信终端回传,state 字符串长度不能超过 1K",
"lang": "微信客户端当前语言",
"country": "微信用户当前国家信息"
}
在用户同意授权后,我们获得了一个很重要的参数:code
2.3 通过通过 code 获取 access_token(后端需要做)
接口:
js
GET:https://api.weixin.qq.com/sns/oauth2/access_token?appid=APPID&secret=SECRET&code=CODE&grant_type=authorization_code
参数:
参数 | 是否必须 | 说明 |
---|---|---|
appid | 是 | 应用唯一标识,在微信开放平台提交应用审核通过后获得 |
secret | 是 | 应用密钥 AppSecret,在微信开放平台提交应用审核通过后获得 |
code | 是 | 填写第一步获取的 code 参数 |
grant_type | 是 | 固定填 authorization_code |
返回:
java
{
"access_token": "ACCESS_TOKEN",
"expires_in": 7200,
"refresh_token": "REFRESH_TOKEN",
"openid": "OPENID",
"scope": "snsapi_userinfo",
"unionid": "o6_bmasdasdsad6_2sgVt7hMZOPfL"
}
返回参数说明:
参数 | 说明 | |
---|---|---|
access_token | 接口调用凭证 | |
expires_in | access_token 接口调用凭证超时时间,单位(秒) | |
refresh_token | 用户刷新 access_token | |
openid | 接口调用凭证 | 授权用户唯一标识 |
scope | 接口调用凭证 | 用户授权的作用域(snsapi_userinfo) |
unionid | 接口调用凭证 | 当且仅当该移动应用已获得该用户的 userinfo 授权时,才会出现该字段 |
2.4 获取用户信息(用户需要做)
接口:
js
GET:https://api.weixin.qq.com/sns/userinfo?access_token=ACCESS_TOKEN&openid=OPENID
入参:
参数 | 是否必须 | 说明 |
---|---|---|
access_token | 是 | 调用凭证 |
openid | 是 | 普通用户的标识,对当前开发者账号唯一 |
lang | 否 | 国家地区语言版本,zh_CN 简体,zh_TW 繁体,en 英语,默认为 en |
出参:
java
{
"openid": "OPENID", //普通用户的标识,对当前开发者账号唯一
"nickname": "NICKNAME", //普通用户昵称
"sex": 1, //普通用户性别,1 为男性,2 为女性
"province": "PROVINCE", //普通用户个人资料填写的省份
"city": "CITY", // 普通用户个人资料填写的城市
"country": "COUNTRY", // 国家,如中国为 CN
"headimgurl": "https://thirdwx.qlogo.cn/mmopen/g3MonUZtNHkdmzicIlibx6iaFqAc56vxLSUfpb6n5WKSYVY0ChQKkiaJSgQ1dZuTOgvLLrhJbERQQ4eMsv84eavHiaiceqxibJxCfHe/0",
"privilege": ["PRIVILEGE1", "PRIVILEGE2"],
"unionid": " o6_bmasdasdsad6_2sgVt7hMZOPfL"
}
出参说明:
参数 | 说明 |
---|---|
openid | 普通用户的标识,对当前开发者账号唯一 |
nickname | 普通用户昵称 |
sex | 普通用户性别,1 为男性,2 为女性 |
province | 普通用户个人资料填写的省份 |
city | 普通用户个人资料填写的城市 |
country | 国家,如中国为 CN |
headimgurl | 用户头像,最后一个数值代表正方形头像大小(有 0、46、64、96、132 数值可选,0 代表 640*640 正方形头像),用户没有头像时该项为空 |
privilege | 用户特权信息,json 数组,如微信沃卡用户为(chinaunicom) |
unionid | 用户统一标识。针对一个微信开放平台账号下的应用,同一用户的 unionid 是唯一的。 |
2.5 刷新access_token
(1) 刷新token
在步骤【2.4】中我们需要获取微信用户的信息 ,需要使用到access_token
。这个令牌有效期是2小时。refresh_token
拥有较长的有效期(30 天)且无法续期,当 refresh_token 失效的后,需要用户重新授权后才可以继续获取用户头像昵称。
接口:
js
GET:https://api.weixin.qq.com/sns/oauth2/refresh_token?appid=APPID&grant_type=refresh_token&refresh_token=REFRESH_TOKEN
入参:
参数 | 是否必须 | 说明 |
---|---|---|
appid | 是 | 应用唯一标识 |
grant_type | 是 | 填 refresh_token |
refresh_token | 是 | 填写通过 access_token 获取到的 refresh_token 参数 |
出参:
java
{
"access_token": "ACCESS_TOKEN",
"expires_in": 7200,
"refresh_token": "REFRESH_TOKEN",
"openid": "OPENID",
"scope": "SCOPE"
}
(2)验证token是否有效
接口:
js
GET:https://api.weixin.qq.com/sns/auth?access_token=ACCESS_TOKEN&openid=OPENID
入参:
参数 | 是否必须 | 说明 |
---|---|---|
access_token | 是 | 调用接口凭证 |
openid | 是 | 普通用户标识,对该公众账号唯一证 |
出参:
token有效返回:
java
{
"errcode": 0,
"errmsg": "ok"
}
如果access_token
失效了,那么需要重新让用户授权登录。
三、如何确定唯一用户
3.1 使用UnionId确定唯一用户
如果我们的产品拥有移动端(IOS/Andriod) 、网页端 、微信小程序 ,都是用微信登录,同一个用户使用在上述的客户端登陆,那么我们如果在自己的后端服务器 中确定是同一个用户呢? 答案是:通过UnionId
这里我举个微信小程序和移动端关联确定唯一用户的实例:
微信小程序登录接口 在微信开放平台 绑定了小程序后,会返回UnionId
:
3.2 绑定微信小程序:
测试返回值:
返回了UnionId
。