国产av日韩一区二区三区精品,成人性爱视频在线观看,国产,欧美,日韩,一区,www.成色av久久成人,2222eeee成人天堂

首頁(yè) 微信小程序 微信開(kāi)發(fā) 詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟

詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟

Mar 15, 2017 pm 05:49 PM

這篇文章主要為大家詳細(xì)介紹了java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟方法,感興趣的小伙伴們可以參考一下

首先說(shuō)微信企業(yè)號(hào)的開(kāi)發(fā)模式分為:編輯模式(普通模式)開(kāi)發(fā)模式(回調(diào)模式) ,在編輯模式下,只能做簡(jiǎn)單的自定義菜單和自動(dòng)回復(fù)消息,要想實(shí)現(xiàn)其他功能還得開(kāi)啟開(kāi)發(fā)者模式。

一、編輯模式和開(kāi)發(fā)模式對(duì)消息的處理流程

?1.編輯模式下,所有的業(yè)務(wù)流程都配置在微信服務(wù)器上,由它處理

? 詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟

2.開(kāi)發(fā)模式,消息通過(guò)第三方服務(wù)器處理,最后經(jīng)過(guò)微信服務(wù)器把消息發(fā)送給用戶

? 詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟

開(kāi)發(fā)模式能處理的消息比編輯模式多,所以要先開(kāi)啟開(kāi)發(fā)模式才能開(kāi)發(fā)更多功能。

二、開(kāi)發(fā)模式的開(kāi)啟

???? 在回調(diào)模式下,企業(yè)不僅可以主動(dòng)調(diào)用企業(yè)號(hào)接口,還可以接收用戶的消息或事件接收的信息使用XML數(shù)據(jù)格式、UTF8編碼,并以AES方式加密。

1.開(kāi)啟回調(diào)模式后要配置參數(shù)如下:

? 詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟

其中url是要訪問(wèn)的servlet,token和EncodingAESKey是隨機(jī)獲取的,但要和項(xiàng)目中保持一致。

2.驗(yàn)證URL的有效性

當(dāng)你提交以上信息時(shí),企業(yè)號(hào)將發(fā)送GET請(qǐng)求到填寫(xiě)的URL上,GET請(qǐng)求攜帶四個(gè)參數(shù),企業(yè)在獲取時(shí)需要做urldecode處理,否則會(huì)驗(yàn)證不成功。

詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟

3.代碼

CoreServlet1類?

public class CoreServlet1 extends HttpServlet {
 private static final long serialVersionUID = 4440739483644821986L;
 String sToken = "weixinCourse";
 String sCorpID = "wxe510946434680dab";
 String sEncodingAESKey = "DjlyZxgKiWRESIW2VnV9dSr7HsS7usWDfnwA8Q1ove1";
 
 public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
 
  WXBizMsgCrypt wxcpt;
 
   try {
 wxcpt = new WXBizMsgCrypt(sToken, sEncodingAESKey, sCorpID); 
 
 String sVerifyMsgSig = request.getParameter("msg_signature");
 
 String sVerifyTimeStamp = request.getParameter("timestamp"); 
 
 String sVerifyNonce = request.getParameter("nonce"); 
 
 String sVerifyEchoStr = request.getParameter("echostr");  
 String sEchoStr;
 
 sEchoStr = wxcpt.VerifyURL(sVerifyMsgSig, sVerifyTimeStamp,
   sVerifyNonce, sVerifyEchoStr);
 System.out.println("verifyurl echostr: " + sEchoStr);
 PrintWriter out = response.getWriter();
 out.print(sEchoStr); 
 out.close();
 out = null;
 
 } catch (AesException e1) {
 
 e1.printStackTrace();
 }
 
  }
}

工具類:

 /**
 * 對(duì)公眾平臺(tái)發(fā)送給公眾賬號(hào)的消息加解密示例代碼.
 * 
 * @copyright Copyright (c) 1998-2014 Tencent Inc.
 */

// ------------------------------------------------------------------------

/**
 * 針對(duì)org.apache.commons.codec.binary.Base64,
 * 需要導(dǎo)入架包c(diǎn)ommons-codec-1.9(或commons-codec-1.8等其他版本)
 * 官方下載地址:http://m.miracleart.cn/
 */
package com.qq.weixin.mp.aes;

import java.nio.charset.Charset;
import java.util.Arrays;
import java.util.Random;

import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;

import org.apache.commons.codec.binary.Base64;

/**
 * 提供接收和推送給公眾平臺(tái)消息的加解密接口(UTF8編碼的字符串).
 * <ol>
 * <li>第三方回復(fù)加密消息給公眾平臺(tái)</li>
 * <li>第三方收到公眾平臺(tái)發(fā)送的消息,驗(yàn)證消息的安全性,并對(duì)消息進(jìn)行解密。</li>
 * </ol>
 * 說(shuō)明:異常java.security.InvalidKeyException:illegal Key Size的解決方案
 * <ol>
 * <li>在官方網(wǎng)站下載JCE無(wú)限制權(quán)限策略文件(JDK7的下載地址:
 *   http://m.miracleart.cn/;/li>
 * <li>下載后解壓,可以看到local_policy.jar和US_export_policy.jar以及readme.txt</li>
 * <li>如果安裝了JRE,將兩個(gè)jar文件放到%JRE_HOME%\lib\security目錄下覆蓋原來(lái)的文件</li>
 * <li>如果安裝了JDK,將兩個(gè)jar文件放到%JDK_HOME%\jre\lib\security目錄下覆蓋原來(lái)文件</li>
 * </ol>
 */
public class WXBizMsgCrypt {
 static Charset CHARSET = Charset.forName("utf-8");
 Base64 base64 = new Base64();
 byte[] aesKey;
 String token;
 String corpId;

 /**
 * 構(gòu)造函數(shù)
 * @param token 公眾平臺(tái)上,開(kāi)發(fā)者設(shè)置的token
 * @param encodingAesKey 公眾平臺(tái)上,開(kāi)發(fā)者設(shè)置的EncodingAESKey
 * @param corpId 企業(yè)的corpid
 * 
 * @throws AesException 執(zhí)行失敗,請(qǐng)查看該異常的錯(cuò)誤碼和具體的錯(cuò)誤信息
 */
 public WXBizMsgCrypt(String token, String encodingAesKey, String corpId) throws AesException {
 if (encodingAesKey.length() != 43) {
  throw new AesException(AesException.IllegalAesKey);
 }

 this.token = token;
 this.corpId = corpId;
 aesKey = Base64.decodeBase64(encodingAesKey + "=");
 }

 
 

 /**
 * 對(duì)密文進(jìn)行解密.
 * 
 * @param text 需要解密的密文
 * @return 解密得到的明文
 * @throws AesException aes解密失敗
 */
 String decrypt(String text) throws AesException {
 byte[] original;
 try {
  // 設(shè)置解密模式為AES的CBC模式
  Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");
  SecretKeySpec key_spec = new SecretKeySpec(aesKey, "AES");
  IvParameterSpec iv = new IvParameterSpec(Arrays.copyOfRange(aesKey, 0, 16));
  cipher.init(Cipher.DECRYPT_MODE, key_spec, iv);

  // 使用BASE64對(duì)密文進(jìn)行解碼
  byte[] encrypted = Base64.decodeBase64(text);

  // 解密
  original = cipher.doFinal(encrypted);
 } catch (Exception e) {
  e.printStackTrace();
  throw new AesException(AesException.DecryptAESError);
 }

 String xmlContent, from_corpid;
 try {
  // 去除補(bǔ)位字符
  byte[] bytes = PKCS7Encoder.decode(original);

  // 分離16位隨機(jī)字符串,網(wǎng)絡(luò)字節(jié)序和corpId
  byte[] networkOrder = Arrays.copyOfRange(bytes, 16, 20);

  int xmlLength = recoverNetworkBytesOrder(networkOrder);

  xmlContent = new String(Arrays.copyOfRange(bytes, 20, 20 + xmlLength), CHARSET);
  from_corpid = new String(Arrays.copyOfRange(bytes, 20 + xmlLength, bytes.length),
   CHARSET);
 } catch (Exception e) {
  e.printStackTrace();
  throw new AesException(AesException.IllegalBuffer);
 }

 // corpid不相同的情況
 if (!from_corpid.equals(corpId)) {
  throw new AesException(AesException.ValidateCorpidError);
 }
 return xmlContent;

 }


 /**
 * 驗(yàn)證URL
 * @param msgSignature 簽名串,對(duì)應(yīng)URL參數(shù)的msg_signature
 * @param timeStamp 時(shí)間戳,對(duì)應(yīng)URL參數(shù)的timestamp
 * @param nonce 隨機(jī)串,對(duì)應(yīng)URL參數(shù)的nonce
 * @param echoStr 隨機(jī)串,對(duì)應(yīng)URL參數(shù)的echostr
 * 
 * @return 解密之后的echostr
 * @throws AesException 執(zhí)行失敗,請(qǐng)查看該異常的錯(cuò)誤碼和具體的錯(cuò)誤信息
 */
 public String VerifyURL(String msgSignature, String timeStamp, String nonce, String echoStr)
  throws AesException {
 String signature = SHA1.getSHA1(token, timeStamp, nonce, echoStr);

 if (!signature.equals(msgSignature)) {
  throw new AesException(AesException.ValidateSignatureError);
 }

 String result = decrypt(echoStr);
 return result;
 }

}
 /**
 * 對(duì)公眾平臺(tái)發(fā)送給公眾賬號(hào)的消息加解密示例代碼.
 * 
 * @copyright Copyright (c) 1998-2014 Tencent Inc.
 */

// ------------------------------------------------------------------------

package com.qq.weixin.mp.aes;

import java.security.MessageDigest;
import java.util.Arrays;

/**
 * SHA1 class
 *
 * 計(jì)算公眾平臺(tái)的消息簽名接口.
 */
class SHA1 {

 /**
 * 用SHA1算法生成安全簽名
 * @param token 票據(jù)
 * @param timestamp 時(shí)間戳
 * @param nonce 隨機(jī)字符串
 * @param encrypt 密文
 * @return 安全簽名
 * @throws AesException 
 */
 public static String getSHA1(String token, String timestamp, String nonce, String encrypt) throws AesException
   {
 try {
  String[] array = new String[] { token, timestamp, nonce, encrypt };
  StringBuffer sb = new StringBuffer();
  // 字符串排序
  Arrays.sort(array);
  for (int i = 0; i < 4; i++) {
  sb.append(array[i]);
  }
  String str = sb.toString();
  // SHA1簽名生成
  MessageDigest md = MessageDigest.getInstance("SHA-1");
  md.update(str.getBytes());
  byte[] digest = md.digest();

  StringBuffer hexstr = new StringBuffer();
  String shaHex = "";
  for (int i = 0; i < digest.length; i++) {
  shaHex = Integer.toHexString(digest[i] & 0xFF);
  if (shaHex.length() < 2) {
   hexstr.append(0);
  }
  hexstr.append(shaHex);
  }
  return hexstr.toString();
 } catch (Exception e) {
  e.printStackTrace();
  throw new AesException(AesException.ComputeSignatureError);
 }
 }
}

 class PKCS7Encoder {
 static Charset CHARSET = Charset.forName("utf-8");
 static int BLOCK_SIZE = 32;
/**
 * 刪除解密后明文的補(bǔ)位字符
 * 
 * @param decrypted 解密后的明文
 * @return 刪除補(bǔ)位字符后的明文
 */
 static byte[] decode(byte[] decrypted) {
 int pad = (int) decrypted[decrypted.length - 1];
 if (pad < 1 || pad > 32) {
  pad = 0;
 }
 return Arrays.copyOfRange(decrypted, 0, decrypted.length - pad);
 }
}

三、總結(jié)
企業(yè)通過(guò)參數(shù)msg_signature對(duì)請(qǐng)求進(jìn)行校驗(yàn),如果確認(rèn)此次GET請(qǐng)求來(lái)自企業(yè)號(hào),那么企業(yè)應(yīng)用對(duì)echostr參數(shù)解密并原樣返回echostr明文(不能加引號(hào)),則接入驗(yàn)證生效,回調(diào)模式才能開(kāi)啟。開(kāi)啟后一些功能會(huì)陸續(xù)實(shí)現(xiàn),敬請(qǐng)期待!


以上是詳解java微信企業(yè)號(hào)開(kāi)發(fā)之開(kāi)發(fā)模式的開(kāi)啟步驟的詳細(xì)內(nèi)容。更多信息請(qǐng)關(guān)注PHP中文網(wǎng)其他相關(guān)文章!

本站聲明
本文內(nèi)容由網(wǎng)友自發(fā)貢獻(xiàn),版權(quán)歸原作者所有,本站不承擔(dān)相應(yīng)法律責(zé)任。如您發(fā)現(xiàn)有涉嫌抄襲侵權(quán)的內(nèi)容,請(qǐng)聯(lián)系admin@php.cn

熱AI工具

Undress AI Tool

Undress AI Tool

免費(fèi)脫衣服圖片

Undresser.AI Undress

Undresser.AI Undress

人工智能驅(qū)動(dòng)的應(yīng)用程序,用于創(chuàng)建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用于從照片中去除衣服的在線人工智能工具。

Clothoff.io

Clothoff.io

AI脫衣機(jī)

Video Face Swap

Video Face Swap

使用我們完全免費(fèi)的人工智能換臉工具輕松在任何視頻中換臉!

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費(fèi)的代碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

功能強(qiáng)大的PHP集成開(kāi)發(fā)環(huán)境

Dreamweaver CS6

Dreamweaver CS6

視覺(jué)化網(wǎng)頁(yè)開(kāi)發(fā)工具

SublimeText3 Mac版

SublimeText3 Mac版

神級(jí)代碼編輯軟件(SublimeText3)

熱門(mén)話題

Laravel 教程
1601
29
PHP教程
1502
276