您好,我们用的小程序一键授权的方案,需要获取手机号,这个接口偶尔报错,一天差不多3到4个,但是我们前端的基础库的版本是 2.16.1,前端代码是这样 :
<button
id="pageReserveBtnbtn-area"
open-type="getPhoneNumber"
bindgetphonenumber="handleGetPhoneNumber";
我的后端代码是:public Map<String, Object> getWeChatPhoneNumber(Map<String, Object> params) {
try {
WechatLoginReqDTO dto = new WechatLoginReqDTO();
dto.setCode(String.valueOf(params.get("code")));
OauthRespDTO oauthRespDTO = wechatOauthRestService.wechatAppletLogin(dto);
log.info("---- getWeChatPhoneNumber oauthRespDTO: {}", WkUtils.objectToJson(oauthRespDTO));
String str = WeChatUtil.decryptData(String.valueOf(params.get("encryptedData")), oauthRespDTO.getSessionKey(), String.valueOf(params.get("iv")));
return new Gson().fromJson(str, Map.class);
} catch (Exception e) {
log.error("---- getWeChatPhoneNumber error ----:{}", e.getMessage(), e);
throw new ApiClientException("wechat.auth.connection.failed");
}
}
private static byte[] decrypt(byte[] content, byte[] key, byte[] iv) throws Exception {
Cipher cipher = Cipher.getInstance(DEFAULT_CIPHER_ALGORITHM);
Key keySpec = new SecretKeySpec(key, KEY_ALGORITHM);
cipher.init(Cipher.DECRYPT_MODE, keySpec, generateIV(iv));
return cipher.doFinal(content);
}
public static String decryptData(String encryptedData, String session_key, String ivStr) throws Exception {
log.info("encryptedData: {}", encryptedData);
log.info("sessionKey: {}", session_key);
log.info("iv: {}", ivStr);
Base64.Decoder decoder = Base64.getDecoder();
byte[] content = decoder.decode(encryptedData);
byte[] key = decoder.decode(session_key);
if (key.length != 16) {
log.error("SessionKey解码后长度异常: {}", key.length);
throw new IllegalArgumentException("Invalid sessionKey");
}
byte[] iv = decoder.decode(ivStr);
if (iv.length != 16) {
throw new IllegalArgumentException("Invalid iv length: " + iv.length);
}
try {
byte[] plain = decrypt(content, key, iv);
return new String(plain, StandardCharsets.UTF_8);
} catch (IllegalArgumentException e) {
log.error("参数长度异常:{} ", e.getMessage(), e);
throw new RuntimeException("解密参数错误");
} catch (InvalidKeyException e) {
log.error("无效密钥: {}", e.getMessage(), e);
throw new RuntimeException("SessionKey无效");
} catch (BadPaddingException e) {
log.error("填充错误,请检查参数完整性:{} ", e.getMessage(), e);
throw new RuntimeException("数据损坏");
} catch (Exception e) {
log.error("解密未知错误: {}", e.getMessage(), e);
throw new RuntimeException("解密失败");
}
}
解密算法是:private static final String KEY_ALGORITHM = "AES";
private static final String DEFAULT_CIPHER_ALGORITHM = "AES/CBC/PKCS7Padding";
现在log日志报错是:log.error("填充错误,请检查参数完整性:{} ", e.getMessage(), e);
throw new RuntimeException("数据损坏");
