微信JS-SDK——invalid signature 填坑

項目調用微信JS-SDK接口主要是爲了可以分享自定義的頁面。直接說在看文檔開發過程中的坑,文檔中有的就簡略了。

1. 獲得JsapiTicket直接攜帶token訪問接口即可。

2. 時間戳的獲取,在微信的sha1加密測試頁面,時間戳的長度爲10個數字,但是超過10個數字時,代碼也不報錯,爲了避免踩坑,的我的時間戳是這樣的

String timestamp = new SimpleDateFormat("MMddHHmmss").format(new Date());

3. sha1加密,加密前的參數按照官網文檔要求,需要按照自然順序排序,但是是因爲參數名是固定的,所以排序後的順序也不會變,我就直接按照自然順序拼接成了字符串:

String str= "jsapi_ticket="+ticke+"&noncestr="+nonce+"×tamp="+timestamp+"&url="+url;

在轉化爲16進制的字符串時,字母部分用小寫,加密代碼:

public static String checkSignature(String ticke, String timestamp, String nonce,String url) {
		String str= "jsapi_ticket="+ticke+"&noncestr="+nonce+"×tamp="+timestamp+"&url="+url;
		MessageDigest md = null;
		String tmpStr = null;
		try {
			md = MessageDigest.getInstance("SHA1");
			byte[] digest = md.digest(str.getBytes());
			tmpStr = byteToStr(digest);
		} catch (NoSuchAlgorithmException e) {
			e.printStackTrace();
		}
		return tmpStr;
	}
private static String byteToStr(byte[] byteArray) {
		String strDigest = "";
		for (int i = 0; i < byteArray.length; i++) {
			strDigest += byteToHexStr(byteArray[i]);
		}
		return strDigest;
	}
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;
	}

4. 準備好參數,開始寫js,需要分享功能頁面必須是公衆號功能設置的域名下的頁面:


   4.1  在需要分享功能的頁面引入js

 <script type="text/javascript" src="http://res.wx.qq.com/open/js/jweixin-1.2.0.js"></script>

  4.2 頁面加載的時候加載,js分享所需要的配置::

function weixin(){
		var targetUrl = encodeURIComponent(location.href.split("#")[0]);
        $.ajax({
            type:"post",
            async:false,
            data: {"targetUrl":targetUrl},
            dataType:"json",
            url: webPath+"/newToken_getJsapiTicket.action",
            success : function(data){
            	// alert(data.appid + "--" + data.times + "--" + data.nonce+ "--" + data.sign )
                wx.config({ // 開啓調試模式,調用的所有api的返回值會在客戶端alert出來,若要查看傳入的參數,可以在pc端打開,參數信息會通過log打出,僅在pc端時纔會打印。
                    appId: data.appid, // 必填,公衆號的唯一標識
                    timestamp:data.times , // 必填,生成簽名的時間戳
                    nonceStr: data.nonce, // 必填,生成簽名的隨機串
                    signature: data.sign,// 必填,簽名
                    jsApiList: ['onMenuShareAppMessage']
                });
            }
        });}
坑坑坑:動態獲得當前頁面的url:
encodeURIComponent(location.href.split("#")[0]);

一定要加上encode,同時,在請求的後臺通過URLDecode解密,不然後臺加密的url和wx.config加密的很可能不一樣,從而報invalid signature

後臺代碼:

public void getJsapiTicket(){
        String Url = request.getParameter("targetUrl");
        Map<String,Object> resultMap = new HashMap<String,Object>();
        try {
            String token = CommonUtils.getJsapiTicket();
            String timestamp = new SimpleDateFormat("MMddHHmmss").format(new Date());;
            String none = "weixin";
            String shaStr = SignUtil.checkSignature(token,timestamp,none,URLDecode(Url));
            resultMap.put("times",timestamp);
            resultMap.put("nonce",none);
            resultMap.put("sign",shaStr);
            resultMap.put("appid","wxb18664ff1d0f9e6b");
        } catch (Exception e) {
            e.printStackTrace();
        }
        writerPrint(JSONObject.fromObject(resultMap).toString());
    }

4.3 你用什麼分享接口,加載wx.config裏標明,我只測試了分享給朋友的接口

function baidu(){
        wx.onMenuShareAppMessage({
            title: 'https://www.baidu.com/', // 分享標題
            desc: 'wwwwwww', // 分享描述
            link: '域名/項目名/token_tiaozhuan.action?url=https://www.baidu.com/', // 分享鏈接,該鏈接域名或路徑必須與當前頁面對應的公衆號JS安全域名一致
            success: function (data) {
                location.href = data.url;
            }
        });
	}

這個方法就是複寫了微信分享時的分享內容,並不能直接調用好友列表,分享,真正的分享還需要手動點擊右上方的三個點,選擇分享給好友

然後點擊分享內容的時候,微信會想link參數的路徑發送請求,你直接在代碼裏跳轉就ok了

public void tiaozhuan(){
        try {
        	String Url = request.getParameter("url");
            response.sendRedirect(Url);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

完成!!!!!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章