近期在负责小程序交接的时候,发现原来的小程序只是通过web-view套了一层壳子,实际还是H5的页面,在实际的项目中这样的方法确实可行,可以快捷有效的将之前复杂的业务线全程复用,但是如何让小程序与微信公众号(H5)关联起来,成了套壳实现的关键。
首先梳理一下逻辑:一个微信使用者在微信公众号里面有且只有一个openId,小程序同样,但是小程序的openId 和微信公众号的不同。因此,就需要通过另一个相关联的标识:unionid
unionid是用来区分用户的唯一性,在相同微信开放平台帐号下的移动应用、网站应用、小程序、公众号,用户的unionid是唯一的。也就是说,同一用户,对同一个微信开放平台下的不同应用,unionid是相同的。因此,通过unionid可以就可以将程序关联起来,以下代码均为小程序:
Html:获取用户信息的接口:wx.getUserInfo ,在用户未授权过的情况下调用此接口,将不再出现授权弹窗,会直接进入 fail 回调,此时需要展示授权按钮,让用户手动触发授权按钮,授权的用户,直接通过web-view 加载H5地址,请了解web-view组件。
<view >
<viewwx:if="{{showBtn}}">
<button wx:if="{{canIUse}}" open-type="getUserInfo" bindgetuserinfo="getUserInfo"></button>
</view>
<view wx:if="{{showH5}}">
<web-view src="{{url}}" bindmessage="分享-转发触发的回调" value="{{}}"></web-view>
</view>
<view controls="{{!officialCanIUse}}">
<!-- 公众号关注组件 -->
<official-account></official-account>
</view>
</view>
JS初始化加载:
data: {
url:"",
canIUse: wx.canIUse("button.open-type.getUserInfo"),
showBtn: false,//判断按钮显示与否的,true表示显示,反之隐藏
showH5: false//判断web-view显示与否的,true表示显示,反之隐藏
},
onLoad: function (options) {
var that = this;
// 查看是否授权
wx.getSetting({
success: function (res) {
if (res.authSetting["scope.userInfo"]) {//已经授权
wx.showLoading({
title: "加载中",
});
//直接调用getUserInfo获取用户微信信息
wx.getUserInfo({
success: function (res) {
//小程序获取信息
wxLogin(that,res.userInfo);//获取code
}
})
}else{
that.setData({showBtn:true})
}
}
})
},
function wxLogin(that,userInfo){
that.setData({隐藏关注提示,显示web-view})
// 存储用户头像电话等信息
wx.setStorage({
"key": "userInfo",
"data": userInfo
})
//接下来的流程设计小程序的登陆流程,请参考小程序登陆流程文档理解代码逻辑
wx.login({
success: res => {
//------获取凭证进而换取用户登录态信息,包括用户的唯一标识------
//openid(小程序的)以及本次登录的会话密钥session_key等
varappCode=res.code;
if (appCode ) {
console.log("获取用户登录凭证:" + appCode );
console.log(appCode +"-"+appid+"-");//appid :小程序id
getUnionId(appCode);//appCode查unionid
} else {
console.log("获取用户登录凭证失败:" + res.errMsg);
}
}
})
}
//请求后端
functiongetUnionId(appCode){
var params = { "appCode": appCode, "appid": appid };
varurl="https:aaa/bbb/ccc";//需要在微信开发者平台对小程序进行域名设置,否则调不通
console.log("code查unionid url: " + url + " params:" + JSON.stringify(params));
// ------ 发送凭证 ------
wx.request({
url: url,
data: params,
method: "POST",
header: {
"content-type": "application/json"
},
success:function(res){
if(res.statusCode==200){
if (res.data.openid != null){
//保存小程序的openid-存表存表存表
save(res.data.openid);
}
if (res.data.unionid != null) {
getOpneId(res.data);//unionid查公众号的openid
} else if (res.data.openid != null){
//登陆H5首页,url中的标识表明是通过小程序进入的首页
varurl="https:aaa/bbb/ccc.html?sOpenid="+res.data.openid;
that.setData({ url: url });
wx.hideLoading();
}
}
},
})
}
functiongetOpneId(data){
var unionId = data.unionid;
var sOpenId = data.openid;
var params = { "unionid": unionId};
varurl="https:nId";//后端接口地址,让后端去再去调用公众号的接口
// ------ 发送凭证 ------
wx.request({
url: url,
data: params,
method: "POST",
header: {
"content-type": "application/json"
},
success: function (res) {
console.log("获取到公众号返回的用户信息为:" + JSON.stringify(res.data));
if(res.statusCode==200&&res.data.code!="500"){
var url;
if (res.data.md5PhoneNumber != null) {
wx.setStorage({
"key": "phoneNumber",
"data": res.data.phoneNumber
});
wx.setStorage({
"key": "md5PhoneNumber",
"data": res.data.md5PhoneNumber
});
url="H5首页,url拼接手机号以及加密串和微信小程序登陆标识(sOpenid)";
}else{
url = "H5首页,url微信小程序登陆标识";
}
that.setData({ url: url });
wx.hideLoading();
} else{
varurl="H5首页,url微信小程序登陆标识";
that.setData({ url: url });
wx.hideLoading();
}
wx.hideLoading();
},fail:function(res){
console.log("获取到公众号返回的用户信息为:" + JSON.stringify(res.data));
wx.showToast({
title: "接口异常",
icon: "none",
mask: "true",
duration: 20000
})
wx.hideLoading();
}
})
}
这样的话, 就可以将公众号和小程序相互关联,对应的 H5 页面,也要判断当前客户端是什么类似:公众号还是小程序。