前言:针对如题的内容,微信官方文档也只是说了几个关键点,详细过程含糊不清。本篇博文就直接奉上整个登录流程。此外,如果想了解小游戏分享功能,欢迎查看微信小游戏分享给好友或朋友圈 一文。
提示:该文章写于2019年,很多接口已经被弃用(不再同步接口文档)。自2021年4月28日24时起,小程序登录、用户信息相关接口做了调整。比如getUserInfo方法改成了getUserProfile。点击此处查看小程序公告
一、步骤与思路
1、调用 wx.login(object) 接口获取登录凭证 code。
2、如果第1步成功,在“success”中调用 wx.getSetting(object),检查是否已经授权。
3、如果已经授权,则可以直接调用 wx.getUserInfo(object) 拿到用户信息。
4、如果未授权,调用wx.createUserInfoButton(object),调起授权按钮,授权成功后可以拿到用户信息。
5、以上4步可以让我们拿到用户的头像、昵称、性别等信息,还有code、encryptedData、iv等。如果不需要传到服务端的话,当前流程已经结束。
6、如果需要获取用户的unionId(绑定了公众号的小游戏才有unionId),需要将用户信息的code、encryptedData、iv等传到服务端。
7、服务端收到数据后,首先调用 “https://api.weixin.qq.com/sns/jscode2session”,这一步需要code,小游戏appId和appSecret。成功后可以得到 sessionKey 等,加上客户端传来的 code、encryptedData、iv,一起解密得到 unionId、openId、昵称、头像等。
8、提示:code 将被用来获取sessionKey,而sessionKey、encryptedData、iv三者一起解出用户的敏感数据(包括unionId等)。
二、代码实现
1、点击“微信登录”按钮的回调函数 onWechatLogin()
onWechatLogin ()
{
var self = this;
// 第1步:调用 wx.login(object) 接口获取登录凭证 code
wx.login({
success: function(result)
{
// result对象就包括我们所需的 code
// 第2步,调用 wx.getSetting(object),检查是否已经授权,在 onGetSetting() 内。
self.onGetSetting(result.code);
},
fail: function(result)
{
// 失败处理
}
});
}
2、onGetSetting(),处理wx.getSetting(object):
onGetSetting (code)
{
wx.getSetting({
success (res)
{
if(res.authSetting["scope.userInfo"])
{
// 第3步:如果已经授权,则可以直接调用 wx.getUserInfo(object) 拿到用户信息
wx.getUserInfo({
lang: "zh_CN", // 返回信息的展示方式,en:英文类型,zh_CN:简体中文,zh_TW:繁体中文
withCredentials: true,
success: function(result)
{
console.log(">>>> result -> ", result);
/**
* 成功之后,result包含我们所需的信息,就可以在此处进行下一步的操作。
* 这里的 result和 下面用到的createUserInfoButton 里的res 是相同的数据。
* 如若存储到后台,将code,result.encryptedData、result.iv等发送到服务器
*/
},
fail: function(result)
{
// 错误处理
}
});
} else {
// 第4步:未授权,调用 wx.createUserInfoButton(object)
let sysInfo = wx.getSystemInfoSync();
let button = wx.createUserInfoButton({
lang: "zh_CN", // 返回信息的展示方式,en:英文类型,zh_CN:简体中文,zh_TW:繁体中文
type: "text",
text: "微信登录",
style: {
left: sysInfo.windowWidth / 2 - 50,
top: sysInfo.windowHeight / 2 - 30,
width: 100,
height: 60,
backgroundColor: "#c7a976",
borderColor: "#5c5941",
textAlign: "center",
fontSize: 16,
borderWidth: 4,
borderRadius: 4,
lineHeight: 60,
}
});
button.onTap((res) => {
if(res.userInfo) {
// 授权成功,把button去掉
button.destroy();
// 输出一下信息
console.log(">>>> res -> ", res)
/**
* 成功之后,res包含我们所需的信息,就可以在此处进行下一步的操作。
* 这里的 res和 上面用到的getUserInfo 里的result 是相同的数据。
* 如若存储到后台,将code,res.encryptedData、res.iv等发送到服务器
*/
} else {
// 取消授权,弹出小提示
wx.showModal({
title: "温馨提示",
content: "需要您的用户信息登录游戏!",
showCancel: false
});
}
});
button.show();
}
}
});
}
3、小拓展:上述在调 wx.createUserInfoButton() 时,只是用了“text”类型,下面我们换成用图片类型。
let button = wx.createUserInfoButton({
lang: "zh_CN", // 返回信息的展示方式,en:英文类型,zh_CN:简体中文,zh_TW:繁体中文
type: "image",
// 下面的资源路径不是项目内的路径,而是构建好build,其内部相对根目录的路径。
// 也可以直接写远程资源路径,如:https://www.xxx.com/images/wechatLogin.png
image: "images/wechatLogin.png",
style: {
left: 0,
top: 0,
width: btnWidth,
height: btnHeight
}
});
4、拿到用户信息我们输出查看一下,如下图。avatarUrl 是头像远程地址,其他的就是昵称,省份等。
5、接下来我们需要加载远程头像资源,在此之前呢,要在“微信公众平台”配置一下“合法域名”,否则即便有远程地址,也无法访问。具体配置哪一个域名,可以根据报错信息进行添加。
6、一切就绪,我们只需要通过cc.loader.load,或新版本的cc.assetManager来加载远程头像资源,代码如下。
cc.loader.load({url: userInfo["avatarUrl"], type: "png"}, (err, tex) => {
if(err) {
// 错误处理
} else {
let spriteFrame:cc.SpriteFrame = new cc.SpriteFrame(tex);
// 有了 spriteFrame,我们就可以设置到头像上了,例如头像是headSprite。
headSprite.getComponent(cc.Sprite).spriteFrame = spriteFrame;
}
});
至此获取微信最基本的昵称、性别、头像等已经可以了。下面看第三部分,了解一下如何获取用户的unionId。
三、模拟服务端
小提示:这部分只是简单地描述一下服务端的操作过程,代码仅供关键点参考。如果不需要服务端处理,前两部分内容已经可以满足需求。
import https from "https";
import iconv from "iconv-lite";
import WXBizDataCrypt from "WXBizDataCrypt"; // 微信提供的模块,用来执行解密
// APP_ID 是小游戏的appId,APP_SECRET是小游戏的appSecret,code是客户端传来的
let url = "https://api.weixin.qq.com/sns/jscode2session"
+ "?appid=" + APP_ID
+ "&secret=" + APP_SECRET
+ "&code=" + CODE;
let req = https.get(url, function (res) {
let datas = [];
let size = 0;
res.on("data", function (data) {
datas.push(data);
size += data.length;
});
res.on("end", function (){
let buff = Buffer.concat(datas, size);
let result = iconv.decode(buff, "utf8");
try {
let d = JSON.parse(result);
if( d.session_key ) {
try {
let wxCrypt = new WXBizDataCrypt(APP_ID, d.session_key);
// encryptedData, iv是客户端传递来的。
// 得到的res包含了openId、unionId、nickName等信息.
let res = wxCrypt.decryptData(encryptedData, iv);
/**
* 此时登录操作数据已经完成,可以正常进去游戏。
*/
}
catch (e) {
// 错误处理
}
} else {
// 错误处理
}
}
catch (e) {
// 错误处理
}
});
});
四、免费获取源码
我自己申请注册了一个微信公众平台账号,专门用来调研其规则与限制。下面这个二维码是自己写的一个小游戏demo,有登录、分享功能。对于初学者也可以私信我获取源码,免费发放,只求能够扫码体验一下(消息回复可能不及时,但肯定会回复的),这样我就可以进行之后的探索,并分享出来给大家。