小程序获取手机号前端解析篇(2)
在上一篇文章“小程序获取手机号”中讲述了如何获取code、小程序Id、小程序密钥以及已经后端的解析方案,在本文中将详解在前端如何解析code获取手机号
小程序获取手机号前端解析方案
前言:
书接上文,在上一篇文章中拆解了如何获得Code、AppID、AppSecret、在本篇文章中将说明如何不经后端在前端进行解析获取用户手机号。
? 前文链接
注意:
总的来说在前端解析code的弊端大于后端,主要体现在以下几点。
1)无法共享ACCESS_TOKEN,由于前端缓存是存储在本地的无法像后端一样存储到服务器上,这就导致每个用户在登录时都会重新获取一次ACCESS_TOKEN,如果用户量体大就会触发超频限制,导致当日无法在获取或解析。
2)不安全,在前端进行解析,就会用到小程序密钥等,会明文存放在业务代码中。
实现过程:
1. 获取code并保存code
此方法在上一篇文中有具体讲解此处不在详解,代码演示:
<template>
<view>
<button open-type="getPhoneNumber" @getphonenumber="decryptPhoneNumber">登录</button>
</view>
</template>
<script>
export default {
data() {
return {
code: null,
}
},
methods: {
// 获取code
decryptPhoneNumber(e) {
// 根据业务需求调整
let errMsg = null;
if (e.detail.errMsg.includes('fail user deny')) errMsg = "登录失败,您已拒绝获取信息!";
else if (!e.detail.code) errMsg = "登录失败,获取信息异常!";
if (errMsg) {
uni.showToast({
title: errMsg,
icon: "none"
});
return;
}
// 获取Code
this.code = e.detail.code;
console.log("code -------->" + this.code);
}
}
}
</script>此时点击登录会弹出如下提示:

2. 获取ACCESS_TOKEN
本文为了示列在mounted处调用函数进行获取TOKEN,你可以为进一步优化,比如在获取code后在调用防止用户进来后没登录,造成次数占用。
? TOKEN会在两小时后失效。
? 这里为了演示并没有吧token缓存到本地,您可以根据业务需要进行缓存,在缓存时记得存下当前时间,便于超时后重新获取
代码示列:
// 获取TOKEN
queryAccessToekn() {
if (this.token) return;
uni.request({
url: "https://api.weixin.qq.com/cgi-bin/token",
method: "GET",
data: {
grant_type: "client_credential",
appid: "填入之前获取的AppID",
secret: "填入之前获取的AppSecret"
},
success: (res) => {
if (!res) return;
this.token = res.data.access_token;
}
})
},
3. 解析Code获取手机号
? Code时效为五分钟
? 官网文档说明
代码示列解析Code:
// 解析Code,为了方便处理不管成功失败都走resolve返回,返回为string类型代表成功
analysisCode () {
return new Promise((resolve, reject) => {
uni.request({
url: `https://api.weixin.qq.com/wxa/business/getuserphonenumber?access_token=${this.token}`,
method: "POST",
data: {
code: this.code
},
success: (res) => {
if (!res) {
resolve(false);
return;
}
if (res.data.phone_info && res.data.phone_info.phoneNumber) {
resolve(res.data.phone_info.phoneNumber); // 返回手机号
return;
}
resolve(false);
}
})
})
},
在获取Code处调用:
// 获取Code
this.code = e.detail.code;
console.log("code -------->" + this.code);
// 解析code获取手机号
const res = await this.analysisCode();
console.log("phone ------->" + res);
if (typeof res === "boolean") {
// 获取失败处理
return
}
// 获取到手机号之后的逻辑
完整代码:
<template>
<view>
<button open-type="getPhoneNumber" @getphonenumber="decryptPhoneNumber">登录</button>
</view>
</template>
<script>
export default {
data() {
return {
code: null,
token: "",
}
},
mounted() {
this.queryAccessToekn();
},
methods: {
// 获取TOKEN
queryAccessToekn() {
if (this.token) return;
uni.request({
url: "https://api.weixin.qq.com/cgi-bin/token",
method: "GET",
data: {
grant_type: "client_credential",
appid: "",
secret: ""
},
success: (res) => {
if (!res) return;
this.token = res.data.access_token;
}
})
},
// 解析Code
analysisCode () {
return new Promise((resolve, reject) => {
uni.request({
url: `https://api.weixin.qq.com/wxa/business/getuserphonenumber?access_token=${this.token}`,
method: "POST",
data: {
code: this.code
},
success: (res) => {
if (!res) {
resolve(false);
return;
}
if (res.data.phone_info && res.data.phone_info.phoneNumber) {
// 返回手机号
resolve(res.data.phone_info.phoneNumber);
return;
}
resolve(false);
}
})
})
},
// 获取code
async decryptPhoneNumber(e) {
// 根据业务需求调整逻辑
let errMsg = null;
if (e.detail.errMsg.includes('fail user deny')) errMsg = "登录失败,您已拒绝获取信息!";
else if (!e.detail.code) errMsg = "登录失败,获取信息异常!";
if (errMsg) {
uni.showToast({
title: errMsg,
icon: "none"
});
return;
}
// 获取Code
this.code = e.detail.code;
console.log("code -------->" + this.code);
// 解析code获取手机号
const res = await this.analysisCode();
console.log("phone ------->" + res);
if (typeof res === "boolean") {
// 获取失败处理
return
}
// 获取到手机号之后的逻辑
}
}
}
</script>到这就结束了,感觉对您有所帮助的话点个?在走吧。
