先参考微信小程序官网文档整理逻辑思路
调用微信小程序登录接口----获取用户授权—调用getCode接口获取手机号码(这里我有遇到获取手机号码异常bug)----调用后端API登录
https://developers.weixin.qq.com/miniprogram/dev/framework/open-ability/getPhoneNumber.html
- 微信小程序代码
1.1 点击触发事件
<van-button type="primary" class="btn2" open-type="getPhoneNumber" @getphonenumber="_wxLogin">微信登录</van-button>
1.2 事件操作方法
// 微信登录获取手机号
_wxLogin(e){
let _that = this
if(e.detail.errMsg =="getPhoneNumber:ok"){
uni.showLoading({
title: '登录中...',
})
wx.login({
success:res=>{
if(res.code){
let params={
wxCode:res.code,
}
_that.$http.request({
url:'/api/applets/getWxCode', // 调用后端API-根据小程序code获取微信openId
method:'post',
data:params,
}).then(res=>{
if(res.code == 200){
let jsonData = JSON.parse(res.data)
wx.setStorage({
key: 'openId',
data: jsonData.openid
})
let params1={
signature:jsonData.session_key,
encrypteData:e.detail.encryptedData,
iv:e.detail.iv
}
_that.$http.request({
url:'/api/applets/login', // 调用后端API-登录方法
method:'post',
data:params1,
}).then(res=>{
if(res.code == 200){
wx.hideLoading()
wx.setStorage({
key: 'token',
data: res.data.token,
success:function (){
_that._getUserInfo()
}
})
}else{
wx.hideLoading()
}
}).catch(fail=>{
wx.hideLoading()
})
}else{
wx.hideLoading()
}
}).catch(fail=>{
wx.hideLoading()
})
}
},
fail: () => {
wx.hideLoading()
}
})
}
},
- 后端API接口
/**
* 根据小程序code获取微信openId
* @param code
* @return
*/
// https://developers.weixin.qq.com/miniprogram/dev/framework/open-ability/login.html
public static String getSessionKeyOrOpenId(String code, String appId, String appSecret) {
String requestUrl = "https://api.weixin.qq.com/sns/jscode2session";
Map<String, String> requestUrlParam = new HashMap<>();
requestUrlParam.put("appid", appId); //小程序appId
requestUrlParam.put("secret", appSecret); //小程序secret
requestUrlParam.put("js_code", code); //小程序端返回的code
requestUrlParam.put("grant_type", "authorization_code"); //默认参数
//发送post请求读取调用微信接口获取openid用户唯一标识
return UrlUtils.sendGet(requestUrl, requestUrlParam);
}
/**
* 解析加密数据-获取手机号码
* @param encryptedData
* @param sessionKey
* @param iv
* @return
*/
public static JSONObject getWxMiniInfo(String encryptedData, String sessionKey, String iv) {
byte[] dataByte = Base64.decode(encryptedData); // 被加密的数据
byte[] keyByte = Base64.decode(sessionKey); // 加密秘钥
byte[] ivByte = Base64.decode(iv); // 偏移量
try {
// 如果密钥不足16位,那么就补足. 这个if 中的内容很重要
int base = 16;
if (keyByte.length % base != 0) {
int groups = keyByte.length / base + (keyByte.length % base != 0 ? 1 : 0);
byte[] temp = new byte[groups * base];
Arrays.fill(temp, (byte) 0);
System.arraycopy(keyByte, 0, temp, 0, keyByte.length);
keyByte = temp;
}
// 初始化
Security.addProvider(new BouncyCastleProvider());
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding", "BC");
SecretKeySpec spec = new SecretKeySpec(keyByte, "AES");
AlgorithmParameters parameters = AlgorithmParameters.getInstance("AES");
parameters.init(new IvParameterSpec(ivByte));
cipher.init(Cipher.DECRYPT_MODE, spec, parameters); // 初始化
byte[] resultByte = cipher.doFinal(dataByte);
if (null != resultByte && resultByte.length > 0) {
String result = new String(resultByte, "UTF-8");
return JSONObject.parseObject(result);
}
} catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidParameterSpecException | IllegalBlockSizeException | BadPaddingException
| UnsupportedEncodingException | InvalidKeyException | InvalidAlgorithmParameterException | NoSuchProviderException e) {
log.error("-------getWxMiniInfo------err:" + e);
}
return null;
}
- 初次获取手机号码异常而再次登录就好了。。。
解决方案:界面初始时,添加 onLoad()
ux.login({
success:res=>{
if(res.code){
let params={
wxCode:res.code,
}
}
},
})