广西嘉华李家鸣 發表於 2020-1-6 15:37:00

微信公众号开发总结(一) --程序入口

<p>  最近准备利用业务时间写一个公众号练练手,查看了微信官方文档后,发现文档内容写的非常详细,前期粗略的看了下开发指南,比以前接入的第三方接口简单多了,于是磨刀霍霍按照开发指南一步步配置服务器、申请测试账号并在线调试,轻轻松松的就接入成功。</p>
<p>  下面就是我接入微信、接收微信通知的代码,写的比较粗糙,望不吝赐教.</p>
<p>  引入pom依赖</p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 128, 0, 1)">&lt;!--</span><span style="color: rgba(0, 128, 0, 1)"> https://mvnrepository.com/artifact/com.github.binarywang/weixin-java-mp </span><span style="color: rgba(0, 128, 0, 1)">--&gt;</span>
      <span style="color: rgba(0, 0, 255, 1)">&lt;</span><span style="color: rgba(128, 0, 0, 1)">dependency</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>
            <span style="color: rgba(0, 0, 255, 1)">&lt;</span><span style="color: rgba(128, 0, 0, 1)">groupId</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>com.github.binarywang<span style="color: rgba(0, 0, 255, 1)">&lt;/</span><span style="color: rgba(128, 0, 0, 1)">groupId</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>
            <span style="color: rgba(0, 0, 255, 1)">&lt;</span><span style="color: rgba(128, 0, 0, 1)">artifactId</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>weixin-java-mp<span style="color: rgba(0, 0, 255, 1)">&lt;/</span><span style="color: rgba(128, 0, 0, 1)">artifactId</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>
            <span style="color: rgba(0, 0, 255, 1)">&lt;</span><span style="color: rgba(128, 0, 0, 1)">version</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>3.6.0<span style="color: rgba(0, 0, 255, 1)">&lt;/</span><span style="color: rgba(128, 0, 0, 1)">version</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span>
      <span style="color: rgba(0, 0, 255, 1)">&lt;/</span><span style="color: rgba(128, 0, 0, 1)">dependency</span><span style="color: rgba(0, 0, 255, 1)">&gt;</span></pre>
</div>
<p>  定义&nbsp;wxMpService Bean</p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 0, 0, 1)">   @Bean
    </span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> WxMpService wxMpService() {

      WxMpService service </span>= <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> WxMpServiceImpl();

      WxMpDefaultConfigImpl configStorage </span>= <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> WxMpDefaultConfigImpl();
      </span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">下面的四个参数替换成你自己的就可以了</span>
<span style="color: rgba(0, 0, 0, 1)">      configStorage.setAppId(appid);
      configStorage.setSecret(secret);
      configStorage.setToken(token);
      configStorage.setAesKey(aesKey);

      Map</span>&lt;String, WxMpConfigStorage&gt; config = <span style="color: rgba(0, 0, 255, 1)">new</span> HashMap&lt;&gt;<span style="color: rgba(0, 0, 0, 1)"> ();<br>
      config.put(appid,configStorage);
      service.setMultiConfigges(config);
      </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> service;
    }    </span></pre>
</div>
<p>  </p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 0, 0, 1)">@Slf4j
@AllArgsConstructor
@RestController
@RequestMapping(</span>"/wx/portal/{appid}"<span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)"> WxPortalController {
    @Autowired
    </span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> WxMpService wxService;
    @Autowired
    </span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> WxMpMessageRouter messageRouter;

    </span><span style="color: rgba(0, 128, 0, 1)">/**</span><span style="color: rgba(0, 128, 0, 1)">验证消息 </span><span style="color: rgba(0, 128, 0, 1); text-decoration: underline">https://developers.weixin.qq.com/doc/offiaccount/Basic_Information/Access_Overview.html</span><span style="color: rgba(0, 128, 0, 1)"> *</span><span style="color: rgba(0, 128, 0, 1)">*/</span><span style="color: rgba(0, 0, 0, 1)">
    @GetMapping(produces </span>= "text/plain;charset=utf-8"<span style="color: rgba(0, 0, 0, 1)">)
    </span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> String authGet(@PathVariable String appid,
                        @RequestParam(name </span>= "signature", required = <span style="color: rgba(0, 0, 255, 1)">false</span><span style="color: rgba(0, 0, 0, 1)">) String signature,
                        @RequestParam(name </span>= "timestamp", required = <span style="color: rgba(0, 0, 255, 1)">false</span><span style="color: rgba(0, 0, 0, 1)">) String timestamp,
                        @RequestParam(name </span>= "nonce", required = <span style="color: rgba(0, 0, 255, 1)">false</span><span style="color: rgba(0, 0, 0, 1)">) String nonce,
                        @RequestParam(name </span>= "echostr", required = <span style="color: rgba(0, 0, 255, 1)">false</span><span style="color: rgba(0, 0, 0, 1)">) String echostr) {
      log.info(</span>"\n接收到来自微信服务器的认证消息:[{}, {}, {}, {}]"<span style="color: rgba(0, 0, 0, 1)">, signature,
            timestamp, nonce, echostr);
      </span><span style="color: rgba(0, 0, 255, 1)">if</span><span style="color: rgba(0, 0, 0, 1)"> (StringUtils.isAnyBlank(signature, timestamp, nonce, echostr)) {
            </span><span style="color: rgba(0, 0, 255, 1)">throw</span> <span style="color: rgba(0, 0, 255, 1)">new</span> IllegalArgumentException("请求参数非法,请核实!"<span style="color: rgba(0, 0, 0, 1)">);
      }

      </span><span style="color: rgba(0, 0, 255, 1)">if</span> (!<span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.wxService.switchover(appid)) {
            </span><span style="color: rgba(0, 0, 255, 1)">throw</span> <span style="color: rgba(0, 0, 255, 1)">new</span> IllegalArgumentException(String.format("未找到对应appid=[%s]的配置,请核实!"<span style="color: rgba(0, 0, 0, 1)">, appid));
      }

      </span><span style="color: rgba(0, 0, 255, 1)">if</span><span style="color: rgba(0, 0, 0, 1)"> (wxService.checkSignature(timestamp, nonce, signature)) {
            </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> echostr;
      }
      </span><span style="color: rgba(0, 0, 255, 1)">return</span> "非法请求"<span style="color: rgba(0, 0, 0, 1)">;
    }

    </span><span style="color: rgba(0, 128, 0, 1)">/**</span><span style="color: rgba(0, 128, 0, 1)"> 事件推送 </span><span style="color: rgba(0, 128, 0, 1); text-decoration: underline">https://developers.weixin.qq.com/doc/offiaccount/Message_Management/Receiving_event_pushes.html</span><span style="color: rgba(0, 128, 0, 1)"> *</span><span style="color: rgba(0, 128, 0, 1)">*/</span><span style="color: rgba(0, 0, 0, 1)">
    @PostMapping(produces </span>= "application/xml; charset=UTF-8"<span style="color: rgba(0, 0, 0, 1)">)
    </span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> String post(@PathVariable String appid,
                     @RequestBody String requestBody,
                     @RequestParam(</span>"signature"<span style="color: rgba(0, 0, 0, 1)">) String signature,
                     @RequestParam(</span>"timestamp"<span style="color: rgba(0, 0, 0, 1)">) String timestamp,
                     @RequestParam(</span>"nonce"<span style="color: rgba(0, 0, 0, 1)">) String nonce,
                     @RequestParam(</span>"openid"<span style="color: rgba(0, 0, 0, 1)">) String openid,
                     @RequestParam(name </span>= "encrypt_type", required = <span style="color: rgba(0, 0, 255, 1)">false</span><span style="color: rgba(0, 0, 0, 1)">) String encType,
                     @RequestParam(name </span>= "msg_signature", required = <span style="color: rgba(0, 0, 255, 1)">false</span><span style="color: rgba(0, 0, 0, 1)">) String msgSignature) {
      log.info(</span>"\n接收微信请求:, , encType=[{}], msgSignature=[{}],"
                + " timestamp=[{}], nonce=[{}], requestBody=[\n{}\n] "<span style="color: rgba(0, 0, 0, 1)">,
            openid, signature, encType, msgSignature, timestamp, nonce, requestBody);

      </span><span style="color: rgba(0, 0, 255, 1)">if</span> (!<span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.wxService.switchover(appid)) {
            </span><span style="color: rgba(0, 0, 255, 1)">throw</span> <span style="color: rgba(0, 0, 255, 1)">new</span> IllegalArgumentException(String.format("未找到对应appid=[%s]的配置,请核实!"<span style="color: rgba(0, 0, 0, 1)">, appid));
      }

      </span><span style="color: rgba(0, 0, 255, 1)">if</span> (!<span style="color: rgba(0, 0, 0, 1)">wxService.checkSignature(timestamp, nonce, signature)) {
            </span><span style="color: rgba(0, 0, 255, 1)">throw</span> <span style="color: rgba(0, 0, 255, 1)">new</span> IllegalArgumentException("非法请求,可能属于伪造的请求!"<span style="color: rgba(0, 0, 0, 1)">);
      }

      String out </span>= <span style="color: rgba(0, 0, 255, 1)">null</span><span style="color: rgba(0, 0, 0, 1)">;
      </span><span style="color: rgba(0, 0, 255, 1)">if</span> (encType == <span style="color: rgba(0, 0, 255, 1)">null</span><span style="color: rgba(0, 0, 0, 1)">) {
            </span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)"> 明文传输的消息</span>
            WxMpXmlMessage inMessage =<span style="color: rgba(0, 0, 0, 1)"> WxMpXmlMessage.fromXml(requestBody);
            WxMpXmlOutMessage outMessage </span>= <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.route(inMessage);
            </span><span style="color: rgba(0, 0, 255, 1)">if</span> (outMessage == <span style="color: rgba(0, 0, 255, 1)">null</span><span style="color: rgba(0, 0, 0, 1)">) {
                </span><span style="color: rgba(0, 0, 255, 1)">return</span> ""<span style="color: rgba(0, 0, 0, 1)">;
            }

            out </span>=<span style="color: rgba(0, 0, 0, 1)"> outMessage.toXml();
      } </span><span style="color: rgba(0, 0, 255, 1)">else</span> <span style="color: rgba(0, 0, 255, 1)">if</span> ("aes"<span style="color: rgba(0, 0, 0, 1)">.equalsIgnoreCase(encType)) {
            </span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)"> aes加密的消息</span>
            WxMpXmlMessage inMessage =<span style="color: rgba(0, 0, 0, 1)"> WxMpXmlMessage.fromEncryptedXml(requestBody, wxService.getWxMpConfigStorage(),
                timestamp, nonce, msgSignature);
            log.info(</span>"\n消息解密后内容为:\n{} "<span style="color: rgba(0, 0, 0, 1)">, inMessage.toString());
            WxMpXmlOutMessage outMessage </span>= <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.route(inMessage);
            </span><span style="color: rgba(0, 0, 255, 1)">if</span> (outMessage == <span style="color: rgba(0, 0, 255, 1)">null</span><span style="color: rgba(0, 0, 0, 1)">) {
                </span><span style="color: rgba(0, 0, 255, 1)">return</span> ""<span style="color: rgba(0, 0, 0, 1)">;
            }

            out </span>=<span style="color: rgba(0, 0, 0, 1)"> outMessage.toEncryptedXml(wxService.getWxMpConfigStorage());
      }

      log.info(</span>"\n组装回复信息:{}"<span style="color: rgba(0, 0, 0, 1)">, out);
      </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> out;
    }

    </span><span style="color: rgba(0, 0, 255, 1)">private</span><span style="color: rgba(0, 0, 0, 1)"> WxMpXmlOutMessage route(WxMpXmlMessage message) {
      </span><span style="color: rgba(0, 0, 255, 1)">try</span><span style="color: rgba(0, 0, 0, 1)"> {
            </span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">this</span><span style="color: rgba(0, 0, 0, 1)">.messageRouter.route(message);
      } </span><span style="color: rgba(0, 0, 255, 1)">catch</span><span style="color: rgba(0, 0, 0, 1)"> (Exception e) {
            log.error(</span>"路由消息时出现异常!"<span style="color: rgba(0, 0, 0, 1)">, e);
      }
      </span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">null</span><span style="color: rgba(0, 0, 0, 1)">;
    }

}</span></pre>
</div>
<p>   消息验证成功后,我们就可以获取AccessToken,公众号中接口几乎都会用到这个token,但是这个token并非保持不变的,有效期2H。</p>
<p><img src="https://img2018.cnblogs.com/i-beta/1477997/202001/1477997-20200106153354947-1747954086.png" alt="" width="640" height="184"></p>
<p>&nbsp;</p>
<p>&nbsp;  以上就是接入公众号的前期准备,服务器配置这些官方文档已经说的很清楚了,所以本文就没有介绍。</p><br><br>
来源:https://www.cnblogs.com/JackpotHan/p/12156628.html
頁: [1]
查看完整版本: 微信公众号开发总结(一) --程序入口