微信java 签名验证_JAVA版微信小程序用户数据的签名验证和加解密
签名验证和加解密
数据签名校验
为了确保 开放接口 返回用户数据的安全性,微信会对明文数据进行签名。开发者可以根据业务需要对数据包进行签名校验,确保数据的完整性。
签名校验算法涉及用户的session_key,通过 wx.login 登录流程获取用户session_key,并自行维护与应用自身登录态的对应关系。
通过调用接口(如 wx.getUserInfo)获取数据时,接口会同时返回 rawData、signature,其中 signature = sha1( rawData + session_key )
开发者将 signature、rawData 发送到开发者服务器进行校验。服务器利用用户对应的 session_key 使用相同的算法计算出签名 signature2 ,比对 signature 与 signature2 即可校验数据的完整性。
加密数据解密算法
接口如果涉及敏感数据(如wx.getUserInfo当中的 openId 和unionId ),接口的明文内容将不包含这些敏感数据。开发者如需要获取敏感数据,需要对接口返回的加密数据( encryptedData )进行对称解密。解密算法如下:
对称解密使用的算法为 AES-128-CBC,数据采用PKCS#7填充。
对称解密的目标密文为 Base64_Decode(encryptedData),
对称解密秘钥 aeskey = Base64_Decode(session_key), aeskey 是16字节
对称解密算法初始向量 iv 会在数据接口中返回。
微信官方提供了多种编程语言的示例代码( 点击下载 ),但就是没提供JAVA版本的,可能的确PHP是最好的语言,腾讯提供的demo好多都是PHP版本的。
JAVA代码案例
pom.xml引入以下依赖:
commons-codec
commons-codec
1.10
com.alibaba
fastjson
1.2.7
org.bouncycastle
bcprov-jdk15on
1.57
我们可以参考PHP给出的代码,使用JAVA实现: AESUtil:
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import java.security.AlgorithmParameters;
import java.security.InvalidAlgorithmParameterException;
import java.security.InvalidKeyException;
import java.security.Key;
import java.security.NoSuchAlgorithmException;
import java.security.NoSuchProviderException;
import java.security.Security;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
/**
* AES解密
* 创建者 柒
* 创建时间2018年3月12日
*/
public class AESUtil {
static {
Security.addProvider(new BouncyCastleProvider());
}
/**
* AES解密
* @param content 密文
* @return
* @throws InvalidAlgorithmParameterException
* @throws NoSuchProviderException
*/
public static byte[] decrypt(byte[] content, byte[] keyByte, byte[] ivByte)
throws InvalidAlgorithmParameterException {
try {
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding");
Key sKeySpec = new SecretKeySpec(keyByte, "AES");
//生成iv
AlgorithmParameters params = AlgorithmParameters.getInstance("AES");
params.init(new IvParameterSpec(ivByte));
cipher.init(Cipher.DECRYPT_MODE, sKeySpec, params);// 初始化
return cipher.doFinal(content);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (NoSuchPaddingException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
} catch (IllegalBlockSizeException e) {
e.printStackTrace();
} catch (BadPaddingException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
}
WXBizDataCrypt:
import java.io.UnsupportedEncodingException;
import java.security.InvalidAlgorithmParameterException;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.lang.StringUtils;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
/**
* 对微信小程序用户加密数据的解密
* 创建者 柒
* 创建时间 2018年3月12日
*/
public class WXBizDataCrypt {
public static String illegalAesKey = "-41001";//非法密钥
public static String illegalIv = "-41002";//非法初始向量
public static String illegalBuffer = "-41003";//非法密文
public static String decodeBase64Error = "-41004"; //解码错误
public static String noData = "-41005"; //数据不正确
private String appid;
private String sessionKey;
public WXBizDataCrypt(String appid, String sessionKey) {
this.appid = appid;
this.sessionKey = sessionKey;
}
/**
* 检验数据的真实性,并且获取解密后的明文.
* @param encryptedData string 加密的用户数据
* @param iv string 与用户数据一同返回的初始向量
* @return data string 解密后的原文
* @return String 返回用户信息
*/
public String decryptData(String encryptedData, String iv) {
if (StringUtils.length(sessionKey) != 24) {
return illegalAesKey;
}
// 对称解密秘钥 aeskey = Base64_Decode(session_key), aeskey 是16字节。
byte[] aesKey = Base64.decodeBase64(sessionKey);
if (StringUtils.length(iv) != 24) {
return illegalIv;
}
// 对称解密算法初始向量 为Base64_Decode(iv),其中iv由数据接口返回。
byte[] aesIV = Base64.decodeBase64(iv);
// 对称解密的目标密文为 Base64_Decode(encryptedData)
byte[] aesCipher = Base64.decodeBase64(encryptedData);
try {
byte[] resultByte = AESUtil.decrypt(aesCipher, aesKey, aesIV);
if (null != resultByte && resultByte.length > 0) {
String userInfo = new String(resultByte, "UTF-8");
JSONObject jsons = JSON.parseObject(userInfo);
String id = jsons.getJSONObject("watermark").getString("appid");
if (!StringUtils.equals(id, appid)) {
return illegalBuffer;
}
return userInfo;
} else {
return noData;
}
} catch (InvalidAlgorithmParameterException e) {
e.printStackTrace();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
return null;
}
/**
* encryptedData 和 iv 两个参数通过小程序wx.getUserInfo()方法获取
* @param args
* @see
*/
public static void main(String[] args) {
String appId = "wx4f4bc4dec97d474b";
String sessionKey = "tiihtNczf5v6AKRyjwEUhQ==";
String encryptedData = "CiyLU1Aw2KjvrjMdj8YKliAjtP4gsMZM"
+ "QmRzooG2xrDcvSnxIMXFufNstNGTyaGS"
+ "9uT5geRa0W4oTOb1WT7fJlAC+oNPdbB+"
+ "3hVbJSRgv+4lGOETKUQz6OYStslQ142d"
+ "NCuabNPGBzlooOmB231qMM85d2/fV6Ch"
+ "evvXvQP8Hkue1poOFtnEtpyxVLW1zAo6"
+ "/1Xx1COxFvrc2d7UL/lmHInNlxuacJXw"
+ "u0fjpXfz/YqYzBIBzD6WUfTIF9GRHpOn"
+ "/Hz7saL8xz+W//FRAUid1OksQaQx4CMs"
+ "8LOddcQhULW4ucetDf96JcR3g0gfRK4P"
+ "C7E/r7Z6xNrXd2UIeorGj5Ef7b1pJAYB"
+ "6Y5anaHqZ9J6nKEBvB4DnNLIVWSgARns"
+ "/8wR2SiRS7MNACwTyrGvt9ts8p12PKFd"
+ "lqYTopNHR1Vf7XjfhQlVsAJdNiKdYmYV"
+ "oKlaRv85IfVunYzO0IKXsyl7JCUjCpoG"
+ "20f0a04COwfneQAGGwd5oa+T8yO5hzuy"
+ "Db/XcxxmK01EpqOyuxINew==";
String iv = "r7BXXKkLb8qrSNn05n0qiA==";
WXBizDataCrypt biz = new WXBizDataCrypt(appId, sessionKey);
System.out.println(biz.decryptData(encryptedData, iv));
}
}
运行main方法,获取返回结果:
{"openId":"oGZUI0egBJY1zhBYw2KhdUfwVJJE","nickName":"Band","gender":1,"language":"zh_CN","city":"Guangzhou","province":"Guangdong","country":"CN","avatarUrl":"http://wx.qlogo.cn/mmopen/vi_32/aSKcBBPpibyKNicHNTMM0qJVh8Kjgiak2AHWr8MHM4WgMEm7GFhsf8OYrySdbvAMvTsw3mo8ibKicsnfN5pRjl1p8HQ/0","unionId":"ocMvos6NjeKLIBqg5Mr9QjxrP1FA","watermark":{"timestamp":1477314187,"appid":"wx4f4bc4dec97d474b"}}
微信java 签名验证_JAVA版微信小程序用户数据的签名验证和加解密相关推荐
- 微信小程序用户数据的签名校验和加解密 - 后端nodejs
在本文 微信小程序用户数据的签名校验和加解密 之前需要先看看 微信小程序-获取用户session_key,openid,unionid - 后端为nodejs 代码封装是在上文添加的. 小程序代码: ...
- 微信小程序数据拼接_微信小程序用户数据解密算法Java版
打开官方文档,开心~ 腾讯爸爸竟然给提供了解密算法 然而我下载解压后人傻了 可能鹅厂没养Java程序猿吧 那就看这C++改造吧 public class AnthCodeVerify { privat ...
- 微信小程序用户数据解密
概述 通过微信web开发者工具创建登录,获取用户信息,发送至后台,进行用户数据解密 详细 代码下载:http://www.demodashi.com/demo/10705.html 一.准备工作 1. ...
- 鼠标控制方向java代码_java鼠标操控小程序
最近在做一个软工的屏幕监控软件,已经实现了屏幕图片的传输,但是没有鼠标,才发现键盘上的PtrScSysRq键所截到图是没有鼠标信息的.== 暂时只需实现鼠标的移动事件,用robot.mouseMove ...
- java微信开发图文_java版微信公众号图文消息开发
1 本篇主要介绍微信公众帐号开发中图文消息的使用 以及图文消息的几种表现形式 图文消息的主要参数说明 通过微信官方的消息接口指南,可以看到对图文消息的参数介绍,如下图所示: 从图中可以了解到: 1)图 ...
- java 微信退款接口_java版微信和支付宝退款接口
本文实例为大家分享了java微信退款接口和支付宝退款接口的具体代码,供大家参考,具体内容如下 1.微信退款接口 相对来说我感觉微信的退款接口还是比较好调用的,直接发送httppost请求即可: /** ...
- java时钟_Java实现时钟小程序
哎,好久没上博客园发东西了,上一次还是两个月前的五一写的一篇计算器博客,不过意外的是那个程序成了这学期的Java大作业,所以后来稍微改了一下那个程序就交了上去,这还是美滋滋.然后五月中旬的时候写了一个 ...
- 微信扫描普通二维码调起体验版与已发布版的小程序
文章转自: 微信扫描普通二维码调起体验版与已发布版的小程序_baozaobenren的博客-CSDN博客 公司有这样一个需求,就是用微信扫描二维码直接调起我们的小程序,前期不知道,直接扫描二维码,调起 ...
- 微信php签名验证_微信小程序API 用户数据的签名验证和加解密
微信小程序API 用户数据的签名验证和加解密 用户数据的签名验证和加解密 数据签名校验 为了确保 开放接口 返回用户数据的安全性,微信会对明文数据进行签名.开发者可以根据业务需要对数据包进行签名校验, ...
最新文章
- frameset 后台管理_易达CMS下载-易达CMS(免费开源网站管理系统)v3.0.0.1103免费版
- java语言_JAVA语言
- oracle+数据到+mysql数据库乱码_oracle数据mysql数据库乱码
- 关于ASP.NET 中的主题
- terminated 线程_深入并发,线程相关知识全解析
- idea java web mysql_JavaWeb 开发环境配置 — 基于IDEA 2019.2
- ps去色的10种方法
- cmake安装及下载
- 数据库中间件sharding-jdbc实现数据脱敏
- Ubuntu下WPS中文字体显示问题
- ADS2015导入飞思卡尔元器件模型 安装DesignKit
- windows 2003 directx 3D加速 开启
- P3939 数颜色 主席树板子
- 性能优化之MySQL优化(转)
- Linux下压缩的压缩命令
- Aurora 8b/10b 协议和IP核设置
- 曼尼托巴大学计算机科学硕士,曼尼托巴大学电气和计算机工程硕士解析
- 电子调谐器的主要引脚及作用
- 如何做英文SEO、如何做英文外链
- 机器人受人类虐待后奋起反击?这段视频刷爆网络