JS調起微信掃一掃接口

示例是在JS調起微信掃一掃,掃描二維碼並獲取掃描結果!

1.首先是微信公衆號綁定JS接口安全域名 , 直接放文檔鏈接。 (文檔步驟一)

https://developers.weixin.qq.com/doc/offiaccount/OA_Web_Apps/JS-SDK.html#2

2.H5獲取JSP 引入JS文件 (文檔步驟二)

在需要調用JS接口的頁面引入如下JS文件,(支持https):http://res.wx.qq.com/open/js/jweixin-1.6.0.js
如需進一步提升服務穩定性,當上述資源不可訪問時,可改訪問:http://res2.wx.qq.com/open/js/jweixin-1.6.0.js (支持https)。

3.通過config接口注入權限驗證配置 (文檔步驟三)

因爲文檔有詳細說明,只講一下遇到的問題。
我當時是在,頁面點擊按鈕的時候進行配置,然後再調起掃一掃接口。然後config返回invalid signature簽名錯誤。
當時這個問題找了很久,不管是配置信息還是簽名,是沒有問題的。最後解決辦法是將config接口在JS 頁面加載的時候
先進行配置,點擊按鈕的時候就直接調起掃一掃接口,就完美解決了。
wx.config接口就是微信的配置接口。
這裏通過頁面加載獲取 配置的簽名信息。後臺代碼放第4點。

$(function (){
	// 獲取當前url
	var url = location.href.split('#')[0];
	var p = {m:"GETWECHATSCANINFO",url:url};
	var res = ajaxAssistant("wechat.action",p);
	if(res.code == 1000){
		res = $.parseJSON(res.msg);
		wxCfg(res.appId,res.timestamp,res.nonceStr,res.signature);
	}
	return false;
});
//配置wx js
function wxCfg(_appid,_timestamp, _nonceStr, _signature) {
	wx.config({
		debug :false,// 調試模式,調用的所有api的返回值會在客戶端alert出來。true開啓
		appId : _appid,// 必填,公衆號的唯一標識,公衆號後臺唯一標識
		timestamp : _timestamp,// 必填,生成簽名的時間戳 要與後臺生成的簽名一致。所以是傳過來的
		nonceStr : _nonceStr,// 必填,生成簽名的隨機串 也跟後臺生成的簽名一致。
		signature : _signature,// 必填,簽名
		jsApiList : ['checkJsApi', 'scanQRCode']// 必填,需要使用的JS接口列表,checkJsApi必填
	});
}

4.獲取微信 api_ticket

api_ticket 是用於調用微信JS API的臨時票據,有效期爲7200 秒,通過access_token 來獲取。
access_token就不想講了,網上很多。
開發者注意事項:
1.此用於卡券接口簽名的api_ticket與步驟三中通過config接口注入權限驗證配置使用的jsapi_ticket不同。
2.由於獲取api_ticket 的api 調用次數非常有限,頻繁刷新api_ticket 會導致api調用受限,影響自身業務,開發者需在自己的服務存儲與更新api_ticket。
接口調用請求說明
http請求方式: GET https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=ACCESS_TOKEN&type=wx_card

	public static String getTicket(String access_token){
		String jsapi_ticket = "";
		try {
			// token有效期    CacheUtil是封裝起來的 Map集合
			Object time = CacheUtil.get(TICKET_TIME_KEY);
			boolean isReToken = false;
			if (null!=time) {
				// ticket 有效期 7200秒  120分鐘  這裏過了 100分鐘獲取一次 , 理論1小時可獲取400次 但還是緩存起來
				boolean isE = isExpired(time.toString(), 100);
				isReToken = isE;
			} else {
				isReToken =!isReToken;
			}
			// true 重新獲取
			if (isReToken) {
				String requestUrl = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token="+access_token+"&type=jsapi";
				String response = HttpUtil.instanse().quickGetUrl(requestUrl, 10);
				JSONObject res = DataUtil.string2JSONObject(response);
				log.debug("#get_jsapi_ticket result is -> "+response);
				if(res.containsKey("ticket")){
					jsapi_ticket = res.getString("ticket");
					// 緩存時間戳  或 token 
					CacheUtil.set(TICKET_TOKEN_KEY,jsapi_ticket);
					CacheUtil.set(TICKET_TIME_KEY, System.currentTimeMillis());
				}
			} else {
				jsapi_ticket = CacheUtil.getString(TICKET_TOKEN_KEY);
			}
		} catch (Exception e) {
			log.debug("#request get_jsapi_ticket has error,",e);
		}
		return jsapi_ticket;
	}
	/**
	 * 驗證時間戳
	 * @param tokenAging  時間戳
	 * @param m	驗證超過的時間(分鐘)
	 * @return true 超過 
	 */
	public static boolean isExpired (String tokenAging,int m) {
		boolean is = false;
		
		Date date = new Date(Long.parseLong(tokenAging));
		
        Long minute =(System.currentTimeMillis() - date.getTime()) / (1000 * 60); // 分鐘爲單位
        
        if (minute > m) {
        	is = true;
        }
        return is;
	}

5.根據api_ticket 進行簽名簽名 SHA-1 簽名

import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Formatter;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
public static Map<String, String> sign(String jsapi_ticket, String url) {
        Map<String, String> ret = new HashMap<String, String>();
        // 字符串隨機數
        String nonce_str = create_nonce_str();
        // 時間戳(秒)
        String timestamp = create_timestamp();
        String string1;
        String signature = "";

        //注意這裏參數名必須全部小寫,且必須有序
        string1 = "jsapi_ticket=" + jsapi_ticket +
                  "&noncestr=" + nonce_str +
                  "&timestamp=" + timestamp +
                  "&url=" + url;
        try
        {
            MessageDigest crypt = MessageDigest.getInstance("SHA-1");
            crypt.reset();
            crypt.update(string1.getBytes("UTF-8"));
            signature = byteToHex(crypt.digest());
        }
        catch (NoSuchAlgorithmException e)
        {
            e.printStackTrace();
        }
        catch (UnsupportedEncodingException e)
        {
            e.printStackTrace();
        }

        ret.put("url", url);
        ret.put("jsapi_ticket", jsapi_ticket);
        ret.put("nonceStr", nonce_str);
        ret.put("timestamp", timestamp);
        ret.put("signature", signature);

        return ret;
    }
    private static String byteToHex(final byte[] hash) {
        Formatter formatter = new Formatter();
        for (byte b : hash)
        {
            formatter.format("%02x", b);
        }
        String result = formatter.toString();
        formatter.close();
        return result;
    }

    private static String create_nonce_str() {
        return UUID.randomUUID().toString();
    }

    private static String create_timestamp() {
        return Long.toString(System.currentTimeMillis() / 1000);
    }

6.最後可以調用微信掃一掃接口了

// 調起掃一掃  這裏是點擊掃一掃按鈕的事件方法
function wxScan() {
	wx.ready(function() {//配置文件加載完成之後會自動調用ready中的模塊
			wx.checkJsApi({
				jsApiList : ['scanQRCode'],
				success : function(res) {
					wx.scanQRCode({
						// 默認爲0,掃描結果由微信處理,1則直接返回掃描結果,
						needResult: 1,
						// 可以指定掃二維碼還是一維碼,默認二者都有
						scanType: ["qrCode","barCode"],
						success: function (res) {
							// result  這裏直接返回二維碼中的內容,根據內容可以做自己的業務了
							// needResult爲1 時
		                    var val = res.resultStr;
		                    
						}
					});
				}
			});
		});
		wx.error(function(res) {
			alert("掃一掃調起失敗:" + res.errMsg+",請重試!");
		});
}

7.常見錯誤

這裏就直接放官方文檔了,因爲自己沒遇到過。
https://developers.weixin.qq.com/doc/offiaccount/OA_Web_Apps/JS-SDK.html#66

個人博客:unclepig.top

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