微信官方修改了授权接口:从2018年4月30日开始,小程序体验版、开发版调用
wx.getUserInfo
接口,将无法弹出授权询问框,默认调用失败。我们只能通过button
让用户主动触发授权。这样做能提高用户体验,对小程序来说,当用户拒绝授权,也可以展示它的功能和特色;对用户来说,一开始拒绝了授权也可以重新授权。
先说明,登录是登录,授权是授权。
1、登录:通过wx.login
拿到code
给后台,接口返回token
、openID
等参数。有了这些参数我们就可以直接请求那些不需要用户操作便可以读取的接口(比如:新闻列表、新闻详情、视频播放等等);
2、授权:当小程序需要用户操作(比如:关注、评论、下单购买、地理位置、个人中心等等),就需要用户先授权。
用户点击需要授权的操作时(如关注),会有以下几种情况:
1、已授权的用户可以直接操作;
2、未授权的用户弹出授权框:
(1)拒绝授权:关闭授权框,用户操作无效(如关注,无法触发关注的http请求,保持原状);
(2)接收授权:将用户信息通过token
发送给后台,并主动请求用户操作(如关注,接收授权后触发关注的http请求,提示关注成功)。
代码详解
(注意!注意!下方高能!以下提到的NetWork.xxx
是我这封装的方法,如果没有封装可以直接使用wx.reques()
方法,等同于wx.reques()
成功返回的回调函数。)
1、首先需要定义一个全局变量判断该用户是否授权,授权的状态需要后台在请求登录接口时返回给前台,在app.js
声明:
getToken: function(){
wx.login({
success: res => {
// 发送 res.code 到后台换取 openId, sessionKey, unionId
console.log("code:", res.code);
this.globalData.loginCode = res.code
let params = {
code: res.code
}
NetWork.login(params, (res, err) => {
//授权状态
this.globalData.is_auth = res.data.is_auth;
})
}
})
},
globalData: {
is_auth: 0 //登录后返回的授权状态:0未授权,1已授权
}
2、在界面上,若是未授权状态,将使用open-type="getUserInfo"
的button
遮罩在页面或相应点击事件的最上层,样式是全透明;若是已授权,则不展示这个button
(这里的is_auth
首先要在该页面的js
中声明是全局的那个is_auth
哦):
.auth-btn{
width: 100%;
height: 100%;
position: absolute;
top: 0;
left: 0;
z-index: 99;
background-color: rgba(255, 255, 255, 0)
}
3、当用户是未授权状态时,才会点击到上述的授权button
,并触发上述的onGotUserInfo
事件。若用户接受授权,该方法会将用户信息放在e.detail.userInfo
,然后将信息传给后台,同时改变当前页和全局的授权状态。该事件方法在当前界面的js
中代码如下:
//授权用户信息
onGotUserInfo: function (e) {
console.log(e.detail.userInfo)
if (e.detail.userInfo !== undefined){
let info = e.detail.userInfo;
let paramsObj = {
nickname: info.nickName,
province: info.province,
city: info.city,
country: info.country,
headimgurl: info.avatarUrl,
sex: info.gender
}
NetWork.postUserInfo(paramsObj, (res, err) => {
wx.showLoading({
title: '加载中...',
})
//将全局的授权状态改为:1已授权,其他页面授权的按钮也会通过该状态看是否展示
App.globalData.is_auth = 1;
//当前页面授权状态改为:1已授权
this.setData({
is_auth: 1,
});
})
}
},
4、最后存在一个问题。类似收藏、关注等功能,更合理的操作应该是:在未授权状态点击收藏按钮时,弹出授权框,用户点击 “允许” 授权之后,用户不用再次点击收藏,直接http请求收藏的接口,提示收藏成功or失败。所以上一步的操作可以这么写:
//授权用户信息
onGotUserInfo: function (e) {
console.log(e.detail.userInfo)
if (e.detail.userInfo !== undefined){
let info = e.detail.userInfo;
let paramsObj = {
nickname: info.nickName,
province: info.province,
city: info.city,
country: info.country,
headimgurl: info.avatarUrl,
sex: info.gender
}
NetWork.postUserInfo(paramsObj, (res, err) => {
wx.showLoading({
title: '加载中...',
})
//将全局的授权状态改为:1已授权,其他页面授权的按钮也会通过该状态看是否展示
App.globalData.is_auth = 1;
//当前页面授权状态改为:1已授权
this.setData({
is_auth: 1,
});
//请求收藏
this.collectOrder();
})
}
},
//收藏
collectOrder: function () {
// type 状态:0未收藏,1已收藏
let paramsObj = {
goods_id: this.data.goodsId,
type: 0
}
NetWork.getCollect(paramsObj, (res, err) => {
wx.showToast({
title: '收藏成功!',
icon: 'none',
duration: 1500
})
//collect状态:0未收藏,1已收藏。页面展示已收藏的样式
this.setData({
collect: 1
})
})
},