版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/hans201507/article/details/50429052
概述
接入微信公众平台开发,开发者需要按照如下步骤完成:
1、填写服务器配置 2、验证服务器地址的有效性 3、依据接口文档实现业务逻辑
下面详细介绍这3个步骤。
第一步:填写服务器配置
登录微信公众平台官网后,在公众平台后台管理页面 - 开发者中心页,点击“修改配置”按钮,填写服务器地址(URL)、Token和EncodingAESKey,其中URL是开发者用来接收微信消息和事件的接口URL。Token可由开发者可以任意填写,用作生成签名(该Token会和接口URL中包含的Token进行比对,从而验证安全性)。EncodingAESKey由开发者手动填写或随机生成,将用作消息体加解密密钥。
同时,开发者可选择消息加解密方式:明文模式、兼容模式和安全模式。模式的选择与服务器配置在提交后都会立即生效,请开发者谨慎填写及选择。加解密方式的默认状态为明文模式,选择兼容模式和安全模式需要提前配置好相关加解密代码,详情请参考消息体签名及加解密部分的文档。
URL部分为你的域名,Token随便填,符合要求救可以了。
第二步:验证服务器地址的有效性
开发者提交信息后,微信服务器将发送GET请求到填写的服务器地址URL上,GET请求携带四个参数:
参数 | 描述 |
---|---|
signature | 微信加密签名,signature结合了开发者填写的token参数和请求中的timestamp参数、nonce参数。 |
timestamp | 时间戳 |
nonce | 随机数 |
echostr | 随机字符串 |
开发者通过检验signature对请求进行校验(下面有校验方式)。若确认此次GET请求来自微信服务器,请原样返回echostr参数内容,则接入生效,成为开发者成功,否则接入失败。
加密/校验流程如下: 1. 将token、timestamp、nonce三个参数进行字典序排序 2. 将三个参数字符串拼接成一个字符串进行sha1加密 3. 开发者获得加密后的字符串可与signature对比,标识该请求来源于微信
import java.security.MessageDigest;
import java.util.Arrays;
/**
* 验证服务器地址的有效性
* @author 13501
*
*/
public class SignUtil {
//与接口配置信息中的Token要一致
private static String token ="pengsonghua";
public static boolean checkSignature(String signature,String timestamp,String nonce){
String[] arr=new String[]{token,timestamp,nonce};
// 将token、timestamp、nonce三个参数进行字典序排序
Arrays.sort(arr);
StringBuilder content=new StringBuilder();
for (int i=0;i<arr.length;i++) {
content.append(arr[i]);
}
MessageDigest md=null;
String tmpStr=null;
try {
md = MessageDigest.getInstance("SHA-1");
// 将三个参数字符串拼接成一个字符串进行sha1加密
byte[] digest = md.digest(content.toString().getBytes());
tmpStr = byteToStr(digest);
} catch (Exception e){
e.printStackTrace();
}
content=null;
// 将sha1加密后的字符串可与signature对比,标识该请求来源于微信
return tmpStr!=null?tmpStr.equals(signature.toUpperCase()):false;
}
/**
* 将字节数组转换为十六进制字符串
*
* @param byteArray
* @return
*/
private static String byteToStr(byte[] byteArray) {
String strDigest="";
for(int i=0;i<byteArray.length;i++) {
strDigest+=byteToHexStr(byteArray[i]);
}
return strDigest;
}
/**
* 将字节转换为十六进制字符串
*
* @param mByte
* @return
*/
private static String byteToHexStr(byte mByte) {
char[] Digit={'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
char[] tempArr=new char[2];
tempArr[0]=Digit[(mByte>>>4)&0X0F];
tempArr[1]=Digit[mByte&0X0F];
String s=new String(tempArr);
return s;
}
}
第三步:依据接口文档实现业务逻辑
验证URL有效性成功后即接入生效,成为开发者。如果公众号类型为服务号(订阅号只能使用普通消息接口),可以在公众平台网站中申请认证,认证成功的服务号将获得众多接口权限,以满足开发者需求。
此后用户每次向公众号发送消息、或者产生自定义菜单点击事件时,开发者填写的服务器配置URL将得到微信服务器推送过来的消息和事件,然后开发者可以依据自身业务逻辑进行响应,例如回复消息等。
另外附action部分代码@Namespace("/weixin")
@Controller
@Scope("prototype")
public class WeiXinAction{
@Action(value="service")})
public String test() throws IOException{
HttpServletRequest request=ServletActionContext.getRequest();
// 微信加密签名
<span style="white-space:pre"> </span>String signature=request.getParameter("signature");
<span style="white-space:pre"> </span>// 时间戳
<span style="white-space:pre"> </span>String timestamp=request.getParameter("timestamp");
<span style="white-space:pre"> </span>// 随机数
<span style="white-space:pre"> </span>String nonce=request.getParameter("nonce");
<span style="white-space:pre"> </span>// 随机字符串
<span style="white-space:pre"> </span>String echostr=request.getParameter("echostr");
<span style="white-space:pre"> </span>PrintWriter out=ServletActionContext.getResponse().getWriter();
<span style="white-space:pre"> </span>if(SignUtil.checkSignature(signature,timestamp,nonce)){
<span style="white-space:pre"> </span>out.print(echostr);
<span style="white-space:pre"> </span>out.flush();
<span style="white-space:pre"> </span>out.close();
<span style="white-space:pre"> </span> }
<span style="white-space:pre"> </span>return null;
}
}