.

作者 : 万境绝尘

转载请注明出处 : http://blog.csdn.net/shulianghan/article/details/20494177

.

GitHub源码位置 :

-- HTTP : https://github.com/han1202012/WeChatVerify.git

-- SSH : git@github.com:han1202012/WeChatVerify.git

CSDN下载认证程序的war包和源码 : http://download.csdn.net/detail/han1202012/6999207

微信验证war包下载 :

-- 访问地址 : ip地址:80/WeChatVerify/verifyServlet ;

-- Token : 注意Token是 "hanshuliang" ;

一. 开启开发模式解析

1. 开发者文档

首先进入编辑模式, 将编辑模式关闭, 进入开发模式 :

点击查看文档, 就可以打开微信的开发者文档 : 路线 功能 -> 高级功能 -> 开发模式 -> 查看文档 ;

开发者文档目录结构说明 :

-- 新手接入 : 包括 接入指南 典型案例介绍 开发者规范, 讲解如何接入开发者模;

-- 基础支持 : 包括 获取access_token 全局返回码说明 接口频率限制说明 上传下载多媒体文件;

-- 接收消息 : 包括 验证消息真实性 接收普通消息 接收事件推送 接收语音识别结果;

-- 发送消息 : 包括 发送被动响应消息 发送客服消息;

-- 用户管理 : 包括 分组管理接口 获取用户基本信息 获取关注者列表 获取用户地理位置 网页授权用户基本信息 网页获取用户网络状态;

-- 自定义菜单 : 包括 自定义菜单创建接口 自定义菜单查询接口 自定义菜单删除接口 自定义菜单事件推送;

-- 推广支持 : 包括 生成带参数的二维码 ;

-- 微信 JS接口 : 包括 隐藏微信中网页右上角的按钮 隐藏微信中网页底部的导航栏 网页获取用户网络状态;

-- 开发者交流互助 : 包括 开发者问答系统 接口调试工具 接口体验测试号申请;

2. 开发者校验流程解析

(1)申请消息接口

点击开发模式 "成为开发者" 按钮之后, 会弹出协议 :

之后会弹出填写 URL 和 Token :

-- URL : 用来接收微信服务器数据的接口URL;

-- Token : 任意填写, 用于生成签名;

(2) 验证URL有效性

校验流程 : 程序必须能够处理HTTP GET请求, 并对请求者身份进行校验, 确保请求来自微信服务器;

-- 获取参数 : HTTP GET 会携带四个参数 signature timestamp nonce echostr;

-- 拼装参数 : 将排序后的三个参数按照字典顺序排成字符串;

-- 加密参数 : 将排序后的字符串进行sha1加密;

-- 返回结果 : 将加密后的字符串 与 signature 参数对比, 如果相等则说明请求来自微信服务器, 原样返回参数 echostr;

二. 开发校验程序

1. 要点解析

(1) 在servlet中获取四个参数

获取方法 : 在doGet()方法中, 直接调用request的getParameter("signature")方法, 即可获取signature参数;

-- 示例 :

     //获取微信服务器发送给我们的四个参数String signature = req.getParameter("signature");String timestamp = req.getParameter("timestamp");String nonce = req.getParameter("nonce");String echostr = req.getParameter("echostr");

(2) 将参数按照字典顺序排序

排序方法 : 数组工具类 Arrays.sort()会自动将数组中的字符串按照字典循序排序;

-- 代码示例 :

     //将token timestamp nonce 按照字典顺序排序String[] params = new String[]{token, timestamp, nonce};Arrays.sort(params);//将上面三个参数排序之后拼接成字符串StringBuffer buffer = new StringBuffer();for(int i = 0; i < params.length; i ++){buffer.append(params[i]);}

(3) sha1 加密

获取MessageDigest加密类 : 通过调用 MessageDigest.getInstance("SHA-1"), 即可获取sha1加密类;

-- 代码示例 :

         //获取sha1加密对象MessageDigest digest = MessageDigest.getInstance("SHA-1");//将组合后的字符串使用sha1加密, 加密后获得一个byte数组byte[] byteDigest = digest.digest(buffer.toString().getBytes());

(4) byte数组转为字符串

byte转为char类型 :

-- 示例代码 :

 /** 将byte转为字符串*/public static String byte2HexStr(byte b) {char[] digit = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};char[] temp = new char[2];temp[0] = digit[(b >>> 4) & 0x0F];temp[1] = digit[b & 0x0F];String s = new String(temp);return s;}

byte数组转为字符串 : 需要调用上面的类;

-- 示例代码 :

 /** 将byte数组转为字符串*/public static String byte2str(byte[] byteArray) {String str = "";for(int i = 0; i < byteArray.length; i ++){str += byte2HexStr(byteArray[i]);}return str;}

(5) 向微信服务器发送信息

发送信息 : 先获取输出流, 然后校验, 如果通过校验就向微信服务器发送信息;

-- 示例代码 :

     //创建一个出处流, 用于向微信服务器发送数据PrintWriter out = resp.getWriter();//如果校验通过, 向微信服务器发送echostr参数if(VerifyUtils.checkSignature(signature, timestamp, nonce)){out.print(echostr);}//释放资源out.close();out = null;

.

2. 程序源码

GitHub源码位置 :

-- HTTP : https://github.com/han1202012/WeChatVerify.git

-- SSH : git@github.com:han1202012/WeChatVerify.git

CSDN下载认证程序的war包和源码 : http://download.csdn.net/detail/han1202012/6999207

微信验证war包下载 :

-- 访问地址 : ip地址:80/WeChatVerify/verifyServlet ;

-- Token : 注意Token是 "hanshuliang" ;

程序结构 :

Servlet源码 :

package shuliang.han.vertify.servlet;import java.io.IOException;
import java.io.PrintWriter;import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;import shuliang.han.vertify.VerifyUtils;public class VerifyServlet extends HttpServlet {private static final long serialVersionUID = 4440739483644L;@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {//获取微信服务器发送给我们的四个参数String signature = req.getParameter("signature");String timestamp = req.getParameter("timestamp");String nonce = req.getParameter("nonce");String echostr = req.getParameter("echostr");//创建一个出处流, 用于向微信服务器发送数据PrintWriter out = resp.getWriter();//如果校验通过, 向微信服务器发送echostr参数if(VerifyUtils.checkSignature(signature, timestamp, nonce)){out.print(echostr);}//释放资源out.close();out = null;}@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {//注意这里不能有任何操作, 否则不能完成验证}}

验证工具类源码 :

package shuliang.han.vertify;import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;public class VerifyUtils {private final static String token = "hanshuliang";public static boolean checkSignature(String signature, String timestamp, String nonce) {//将token timestamp nonce 按照字典顺序排序String[] params = new String[]{token, timestamp, nonce};Arrays.sort(params);//将上面三个参数排序之后拼接成字符串StringBuffer buffer = new StringBuffer();for(int i = 0; i < params.length; i ++){buffer.append(params[i]);}//str用于存储加密后的字符串String str = null;try {//获取sha1加密对象MessageDigest digest = MessageDigest.getInstance("SHA-1");//将组合后的字符串使用sha1加密, 加密后获得一个byte数组byte[] byteDigest = digest.digest(buffer.toString().getBytes());//获取加密后的字符串, 将byte数组转化为字符串str = byte2str(byteDigest);} catch (NoSuchAlgorithmException e) {e.printStackTrace();}/** 将加密后的字符串 与 signature 参数进行比较, * 如果加密后的字符串为null直接返回false* 如果加密后的字符串不为null, 直接返回*/boolean isVerified = (str != null) ? str.equals(signature.toUpperCase()) : false;return isVerified;}/** 将byte数组转为字符串*/public static String byte2str(byte[] byteArray) {String str = "";for(int i = 0; i < byteArray.length; i ++){str += byte2HexStr(byteArray[i]);}return str;}/** 将byte转为字符串*/public static String byte2HexStr(byte b) {char[] digit = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};char[] temp = new char[2];temp[0] = digit[(b >>> 4) & 0x0F];temp[1] = digit[b & 0x0F];String s = new String(temp);return s;}}

web.xml配置文件 :

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"><servlet><servlet-name>verifyServlet</servlet-name><servlet-class>shuliang.han.vertify.servlet.VerifyServlet</servlet-class></servlet><servlet-mapping><servlet-name>verifyServlet</servlet-name><url-pattern>/verifyServlet</url-pattern></servlet-mapping><welcome-file-list><welcome-file>index.jsp</welcome-file></welcome-file-list>
</web-app>

三. 进行校验

1.部署程序

(1) 导出war包

(2) 将war包上传到服务器

(3) 配置Tomcat的server.xml文件

微信服务器只能接受80端口数据 :

    <Connector port="80" protocol="HTTP/1.1" connectionTimeout="20000" redirectPort="8443" />

2. 使用阿里云服务器

将上面的程序导出的war包, 放到阿里云Tomcat服务器下 : 使用 http://hanshuliang.com:8080/WeChatVerify/verifyServlet 登陆;

-- 结果 : 这是正常情况, 因为在POST中没有添加参数;

HTTP Status 500 -


type Exception report

message

description The server encountered an internal error () that prevented it from fulfilling this request.

exception

java.lang.NullPointerExceptionjava.lang.String.compareTo(String.java:1168)java.lang.String.compareTo(String.java:92)java.util.Arrays.mergeSort(Arrays.java:1144)java.util.Arrays.sort(Arrays.java:1079)shuliang.han.vertify.VerifyUtils.checkSignature(VerifyUtils.java:13)shuliang.han.vertify.servlet.VerifyServlet.doGet(VerifyServlet.java:28)javax.servlet.http.HttpServlet.service(HttpServlet.java:617)javax.servlet.http.HttpServlet.service(HttpServlet.java:717)

note The full stack trace of the root cause is available in the Apache Tomcat/6.0.20 logs.


Apache Tomcat/6.0.20

不支持8080端口, 只支持80端口, 我的服务器上跑着ngix服务器, 独立域名博客在上面那 : 郁闷 ...

2. 开始校验

原来的Ngix服务器中80端口是独立域名博客, 现在讲独立域名博客指到 8086端口中 : 现在独立域名博客可以从 http://hanshuliang.com:8086/ 访问;

将Tomcat设置成80端口, 气死我了 ;

终于成功了 : 哭死了, 调试了好长时间啊, 终于通过了;

接口功能不全, 只有基础接口的权限 ...

GitHub源码位置 :

-- HTTP : https://github.com/han1202012/WeChatVerify.git

-- SSH : git@github.com:han1202012/WeChatVerify.git

CSDN下载认证程序的war包和源码 : http://download.csdn.net/detail/han1202012/6999207

微信验证war包下载 :

-- 访问地址 : ip地址:80/WeChatVerify/verifyServlet ;

-- Token : 注意Token是 "hanshuliang" ;

.

作者 : 万境绝尘

转载请注明出处 : http://blog.csdn.net/shulianghan/article/details/20494177

.

【微信开发】微信开发 之 开启开发模式相关推荐

  1. 如何在微信内置浏览器中开启开发者模式(f12)

    重要的事情放开头:此方法适用于3.2.1版本微信,如不想回退版本,就不用往下看了 相信大家都使用过浏览器的f12,可以看到浏览器所有的通讯数据以及网页源码 然而有些同学发现微信浏览器无法使用f12 真 ...

  2. Java开发微信公众号(二)---开启开发者模式,接入微信公众平台开发

    接入微信公众平台开发,开发者需要按照如下步骤完成: 1.填写服务器配置 2.验证服务器地址的有效性 3.依据接口文档实现业务逻辑 资料准备: 1.一个可以访问的外网,即80的访问端口,因为微信公众号接 ...

  3. java企业号回调模式,微信公众平台企业号开发—开启回调模式

    2014年9月17日,微信发布了期待已久的企业号.网上关于企业号的教程几乎还是0,所以这里分享一下的我的开发经验. 对比于订阅号和服务号的开发,企业号的开发显得更加复杂一点.这大概也是腾讯考虑到企业信 ...

  4. 【微信易信公众平台开发】开启开发者模式

    本系列文章均为A2BGeek原创,转载务必在明显处注明: 转载自A2BGeek的[微信易信公众平台开发]系列,原文链接:http://blog.csdn.net/a2bgeek/article/det ...

  5. python企业微信回调_Python+Flask 微信企业号开发二之开启回调模式

    一.  概述 上文主要是关于微信主动发送消息给用户, 这篇文章主要是用来描述如何开启微信企业号的回调模式 二 . 操作 1. 登陆微信企业号应用中心--我的应用--模式选择--回调模式 2. 代码 # ...

  6. 微信公众帐号开发教程第2篇-开发模式启用及接口配置

    编辑模式与开发模式 微信公众帐号申请成功后,要想接收处理用户的请求,就必须要在"高级功能"里进行配置,点击"高级功能",将看到如下界面: 从上图中可以看到,高级 ...

  7. [027] 微信公众帐号开发教程第3篇-开发模式启用及接口配置

    编辑模式与开发模式 微信公众帐号申请成功后,要想接收处理用户的请求,就必须要在"高级功能"里进行配置,点击"高级功能",将看到如下界面: 从上图中可以看到,高级 ...

  8. 微信公众平台开发1--微信公众账号开发者模式

    1 申请公众账号 地址mp.weixin.qq.com //注册微信公众平台 需要身份证信息 和 手机号码 下面是注册完成的微信界面 选择高级功能 关闭编辑模式  选择开发模式 开启 点击进入 2 申 ...

  9. 用c#开发微信(1)服务号的服务器配置和企业号的回调模式 - url接入

    2019独角兽企业重金招聘Python工程师标准>>> 阅读目录 一.用法 二.实现方法 最近研究了下服务号的服务器配置和企业号的回调模式.真正实现完后,觉得很简单,但一开始还是走了 ...

最新文章

  1. csr_matrix矩阵用法小结
  2. 《乐高EV3机器人搭建与编程》——2.2 颜色设计
  3. HTML5前端常见攻击方式案例讲解!
  4. apply和call用法
  5. 实验4 颜色、字符串资源的使用
  6. chrome调试、移动端调试
  7. 渗透测试学习 十一、 其他注入漏洞汇总
  8. 孩子成绩不好,学艺术还是上中职?
  9. java ajax传值到后台_java ajax发送数据到后台,中文乱码
  10. LAMMPS分子动力学模拟技术及应用
  11. MD5加密不可逆的原因
  12. DART语言学习整理
  13. 交通信号管理服务器,矿下交通信号控制系统
  14. mysql表出现crash 修复_MySQL表索引损坏致Crash及修复过程实例
  15. 计算机系高考激励的句子,高考激励人心的句子及图片
  16. 网站ICP备案与公安备案有什么区别---kalrry
  17. 用bat批量处理数据
  18. Pinterest简介
  19. 【mysql进阶-彩蛋篇】深入理解顺序io和随机io(全网最详细篇)
  20. 如何把 Node.js 嵌入自己的项目中

热门文章

  1. Python爬虫(三)_urllib2:get和post请求
  2. System.Timers.Timer与System.Windows.Forms.Timer 区别
  3. springboot 异步不生效
  4. 20165237 2017-2018-2 《Java程序设计》第5周学习总结
  5. And it's over,And it's a new start
  6. 地图篇-01.获取用户位置
  7. linux设置外接显示器的分辨率
  8. UESTC_摩天轮 2015 UESTC Training for Dynamic ProgrammingProblem K
  9. HTML 代码常用技巧
  10. InnoDB: Error: log file .\ib_logfile0 is of different size 0 10485760 bytes