Java调用WeChat's API总结

简介:   微信公众号结合着内置浏览器,有着普通浏览器无法完成的服务,前者可以获取浏览页面的微信用户的信息,从而根据信息为用户提供基于微信的更多服务;而后者仅仅能够浏览页面,通过用户的输入信息与用户互动。   本人根据个人的经历总结从小白到入门的过程,是一种记录,也是对渴望入门者的一种指引。

  微信公众号结合着内置浏览器,有着普通浏览器无法完成的服务,前者可以获取浏览页面的微信用户的信息,从而根据信息为用户提供基于微信的更多服务;而后者仅仅能够浏览页面,通过用户的输入信息与用户互动。

  本人根据个人的经历总结从小白到入门的过程,是一种记录,也是对渴望入门者的一种指引。

  1.   注册微信公众平台并申请公众平台测试账号
  2.   填写接口配置信息
  3.   服务器与公众号验证Token
  4.   项目引入weixin-java-mp

 

一、注册微信公众号平台并申请公众平台测试账号

  这方面没什么多言的,至于为何申请测试账号。因为私人只能申请订阅号,对应的开发者账号只能调用基本功能,无法使用高级功能;而测试账号可以使用任何功能以此来学习。

 

二、填写接口配置信息

  

  在这里要特别注意,URL的一栏并不是要填一个公网服务器即可,要求的是必须为一个可以有Token验证行为的地址。

  至于公网的问题,可以使用NATAPP将内网ip转换为公网随机域名,免费,可直接在本机调试项目,很方便。

 

三、服务器与公众号验证Token

  至于Token验证问题,需要代码来验证,原理就是要保证你的Token一致,验证方法有很多种,在weixin-java-mp工具类中也有对应的验证方法,不过本人感觉这种方法更简单:


 1 package xxx;
 2 
 3 import xxx.CheckoutUtil;
 4 import org.springframework.stereotype.Controller;
 5 import org.springframework.ui.Model;
 6 import org.springframework.web.bind.annotation.RequestMapping;
 7 
 8 import javax.servlet.http.HttpServletRequest;
 9 import javax.servlet.http.HttpServletResponse;
10 import java.io.IOException;
11 import java.io.PrintWriter;
12 
13 /**
14  * @author zuoyu
15  * @program xx
16  * @description 微信服务器验证Token
17  * @create 2018-07-31 17:55
18  **/
19 @Controller
20 @RequestMapping("/hello/")
21 public class HelloWeChatController {
22     /**
23      * 微信消息接收和token验证
24      *
25      * @param model
26      * @param request
27      * @param response
28      * @throws IOException
29      */
30     @RequestMapping("hello")
31     public void hello(Model model, HttpServletRequest request, HttpServletResponse response) throws IOException {
32         boolean isGet = request.getMethod().toLowerCase().equals("get");
33         PrintWriter print;
34         if (isGet) {
35             // 微信加密签名
36             String signature = request.getParameter("signature");
37             // 时间戳
38             String timestamp = request.getParameter("timestamp");
39             // 随机数
40             String nonce = request.getParameter("nonce");
41             // 随机字符串
42             String echostr = request.getParameter("echostr");
43             // 通过检验signature对请求进行校验,若校验成功则原样返回echostr,表示接入成功,否则接入失败
44             if (signature != null && CheckoutUtil.checkSignature(signature, timestamp, nonce)) {
45                 try {
46                     print = response.getWriter();
47                     print.write(echostr);
48                     print.flush();
49                 } catch (IOException e) {
50                     e.printStackTrace();
51                 }
52             }
53         }
54     }
55 }


  下面是在Servlet验证时要用到的工具类:


 1 package xxx;
 2 
 3 import java.security.MessageDigest;
 4 import java.security.NoSuchAlgorithmException;
 5 
 6 /**
 7  * @author zuoyu
 8  * @program xx
 9  * @description 微信验证工具
10  * @create 2018-07-31 17:53
11  **/
12 public class CheckoutUtil {
13     // 与接口配置信息中的Token要一致
14     private static String token = "";
15 
16     /**
17      * 验证签名
18      *
19      * @param signature
20      * @param timestamp
21      * @param nonce
22      * @return
23      */
24     public static boolean checkSignature(String signature, String timestamp, String nonce) {
25         String[] arr = new String[] { token, timestamp, nonce };
26         // 将token、timestamp、nonce三个参数进行字典序排序
27         // Arrays.sort(arr);
28         sort(arr);
29         StringBuilder content = new StringBuilder();
30         for (int i = 0; i < arr.length; i++) {
31             content.append(arr[i]);
32         }
33         MessageDigest md = null;
34         String tmpStr = null;
35 
36         try {
37             md = MessageDigest.getInstance("SHA-1");
38             // 将三个参数字符串拼接成一个字符串进行sha1加密
39             byte[] digest = md.digest(content.toString().getBytes());
40             tmpStr = byteToStr(digest);
41         } catch (NoSuchAlgorithmException e) {
42             e.printStackTrace();
43         }
44         content = null;
45         // 将sha1加密后的字符串可与signature对比,标识该请求来源于微信
46         return tmpStr != null ? tmpStr.equals(signature.toUpperCase()) : false;
47     }
48 
49     /**
50      * 将字节数组转换为十六进制字符串
51      *
52      * @param byteArray
53      * @return
54      */
55     private static String byteToStr(byte[] byteArray) {
56         String strDigest = "";
57         for (int i = 0; i < byteArray.length; i++) {
58             strDigest += byteToHexStr(byteArray[i]);
59         }
60         return strDigest;
61     }
62 
63     /**
64      * 将字节转换为十六进制字符串
65      *
66      * @param mByte
67      * @return
68      */
69     private static String byteToHexStr(byte mByte) {
70         char[] Digit = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
71         char[] tempArr = new char[2];
72         tempArr[0] = Digit[(mByte >>> 4) & 0X0F];
73         tempArr[1] = Digit[mByte & 0X0F];
74         String s = new String(tempArr);
75         return s;
76     }
77     public static void sort(String a[]) {
78         for (int i = 0; i < a.length - 1; i++) {
79             for (int j = i + 1; j < a.length; j++) {
80                 if (a[j].compareTo(a[i]) < 0) {
81                     String temp = a[i];
82                     a[i] = a[j];
83                     a[j] = temp;
84                 }
85             }
86         }
87     }
88 }


  将代码中的Token填写与在微信测试号的接口配置Token填写一致,然后URL指向该方法即可完成验证。

 

四、引入wenxin-java-mp工具包

  每次调用微信的API都是访问给定的请求URL、附带的参数、以及访问方式,完成后返回一个json数据包;例如获取微信用户的openID:

  

 

  如果这样在我们开发过程中是很繁琐的,而weixin-java-mp工具包就是一个将这些包装解析的繁琐动作封装起来,对外只暴露接口的工具包。当然类似的工具包还有很多,但个人感觉wenxin-java-mp是最完整且最简洁的,其他类似工具包有很多是基于其他框架、或者依赖包的。我们看一下用这个工具包获取openID多么方便:

  

  几乎所有的对微信API的操作在wenxin-java-mp里都是一个方法。当然,在我们开发过程中依然要一边看着官方文档一边使用,要知其原理。

 

 

 

  

目录
相关文章
|
2月前
|
Java API Spring
打造未来电商新引擎:揭秘Java可扩展API设计,让支付与物流灵活如丝,引领电商时代潮流!
【8月更文挑战第30天】本文通过电商平台案例,探讨了如何设计可扩展的Java API。首先定义支付和物流服务的接口与抽象类,然后实现具体服务,接着引入工厂模式或依赖注入管理服务实例,最后通过配置实现灵活扩展。这种设计确保了应用架构的灵活性和长期稳定性。
45 3
|
2月前
|
安全 Java API
告别繁琐编码,拥抱Java 8新特性:Stream API与Optional类助你高效编程,成就卓越开发者!
【8月更文挑战第29天】Java 8为开发者引入了多项新特性,其中Stream API和Optional类尤其值得关注。Stream API对集合操作进行了高级抽象,支持声明式的数据处理,避免了显式循环代码的编写;而Optional类则作为非空值的容器,有效减少了空指针异常的风险。通过几个实战示例,我们展示了如何利用Stream API进行过滤与转换操作,以及如何借助Optional类安全地处理可能为null的数据,从而使代码更加简洁和健壮。
72 0
|
24天前
|
Java API C++
Java 8 Stream Api 中的 peek 操作
本文介绍了Java中`Stream`的`peek`操作,该操作通过`Consumer&lt;T&gt;`函数消费流中的每个元素,但不改变元素类型。文章详细解释了`Consumer&lt;T&gt;`接口及其使用场景,并通过示例代码展示了`peek`操作的应用。此外,还对比了`peek`与`map`的区别,帮助读者更好地理解这两种操作的不同用途。作者为码农小胖哥,原文发布于稀土掘金。
Java 8 Stream Api 中的 peek 操作
|
8天前
|
安全 Java API
时间日期API(Date,SimpleDateFormat,Calendar)+java8新增日期API (LocalTime,LocalDate,LocalDateTime)
这篇文章介绍了Java中处理日期和时间的API,包括旧的日期API(Date、SimpleDateFormat、Calendar)和Java 8引入的新日期API(LocalTime、LocalDate、LocalDateTime)。文章详细解释了这些类/接口的方法和用途,并通过代码示例展示了如何使用它们。此外,还讨论了新旧API的区别,新API的不可变性和线程安全性,以及它们提供的操作日期时间的灵活性和简洁性。
|
11天前
|
Java 程序员 API
Java 8新特性之Lambda表达式与Stream API的探索
【9月更文挑战第24天】本文将深入浅出地介绍Java 8中的重要新特性——Lambda表达式和Stream API,通过实例解析其语法、用法及背后的设计哲学。我们将一探究竟,看看这些新特性如何让Java代码变得更加简洁、易读且富有表现力,同时提升程序的性能和开发效率。
|
9天前
|
SQL Java Linux
Java 8 API添加了一个新的抽象称为流Stream
Java 8 API添加了一个新的抽象称为流Stream
|
12天前
|
Java
flyway报错Caused by: java.lang.NoSuchMethodError: org.flywaydb.core.api.configuration.FluentConfigurat
flyway报错Caused by: java.lang.NoSuchMethodError: org.flywaydb.core.api.configuration.FluentConfigurat
14 2
|
29天前
|
安全 Java API
【性能与安全的双重飞跃】JDK 22外部函数与内存API:JNI的继任者,引领Java新潮流!
【9月更文挑战第7天】JDK 22外部函数与内存API的发布,标志着Java在性能与安全性方面实现了双重飞跃。作为JNI的继任者,这一新特性不仅简化了Java与本地代码的交互过程,还提升了程序的性能和安全性。我们有理由相信,在外部函数与内存API的引领下,Java将开启一个全新的编程时代,为开发者们带来更加高效、更加安全的编程体验。让我们共同期待Java在未来的辉煌成就!
49 11
|
1月前
|
安全 Java API
【本地与Java无缝对接】JDK 22外部函数和内存API:JNI终结者,性能与安全双提升!
【9月更文挑战第6天】JDK 22的外部函数和内存API无疑是Java编程语言发展史上的一个重要里程碑。它不仅解决了JNI的诸多局限和挑战,还为Java与本地代码的互操作提供了更加高效、安全和简洁的解决方案。随着FFM API的逐渐成熟和完善,我们有理由相信,Java将在更多领域展现出其强大的生命力和竞争力。让我们共同期待Java编程新纪元的到来!
47 11
|
27天前
|
监控 Java 大数据
【Java内存管理新突破】JDK 22:细粒度内存管理API,精准控制每一块内存!
【9月更文挑战第9天】虽然目前JDK 22的确切内容尚未公布,但我们可以根据Java语言的发展趋势和社区的需求,预测细粒度内存管理API可能成为未来Java内存管理领域的新突破。这套API将为开发者提供前所未有的内存控制能力,助力Java应用在更多领域发挥更大作用。我们期待JDK 22的发布,期待Java语言在内存管理领域的持续创新和发展。
下一篇
无影云桌面