如何正確的在專案中接入微信JS-SDK

detectiveHLH發表於2018-08-04

微信JS-SDK的功能

如果你點進來,那麼我相信你應該知道微信的JS-SDK可以用來做什麼了。微信的官方文件描述如下。

微信JS-SDK是微信公眾平臺面向網頁開發者提供的基於微信內的網頁開發工具包。

通過使用微信JS-SDK,網頁開發者可藉助微信高效地使用拍照、選圖、語音、位置等手機系統的能力,同時可以直接使用微信分享、掃一掃等微信特有的能力,為微信使用者提供更優質的網頁體驗。

通過使用微信的JS-SDK,你可以讓你網頁在微信內呼叫拍照、語音、支付、位置、掃一掃這些只能在微信內使用的功能。進過下面的步驟,一步一步的配置,就可以讓你正確的在專案中引入微信的JS-SDK。

引入微信的JS檔案

微信的javascript檔案的連結是: res.wx.qq.com/open/js/jwe…

但是隻支援使用 AMD/CMD 標準模組載入方法載入。於是我就在npm的官網上找到了釋出後的js-sdk,支援CommonJS的引入方式。npm的地址在 這裡。可以在你的專案中使用如下命令安裝。

npm install weixin-js-sdk
複製程式碼

安裝好後可以使用一下兩種方式進行引入。

/* 使用CommonJs規範引入 */
const wx = require('weixin-js-sdk');

/* 使用ES6模組引入 */
import wx from 'weixin-js-sdk';
複製程式碼

為wx.config實現許可權簽名演算法

如果你按照大部分的教程來,他們會讓你使用wx.config注入,獲取許可權。但是使用wx.config的前提是你必須要先實現許可權簽名演算法。而許可權簽名演算法的關鍵就是jsapi_ticket。關於jsapi_ticketm,官方的描述如下。

生成簽名之前必須先了解一下jsapi_ticket,jsapi_ticket是企業號號用於呼叫微信JS介面的臨時票據。正常情況下,jsapi_ticket的有效期為7200秒,通過access_token來獲取。由於獲取jsapi_ticket的api呼叫次數非常有限,頻繁重新整理jsapi_ticket會導致api呼叫受限,影響自身業務,開發者必須在自己的服務全域性快取jsapi_ticket。

大概什麼意思呢,看官方文件可能有點懵。大概意思就是:你想用我的sdk?可以,我給你個2個小時有效期的呼叫憑證。這個憑證我每天發給你的次數有限,所以你要儲存好,不然到時候再想要憑證,沒門。

這是通(很)俗(皮)的解釋。下面來點正常的解釋。想要獲取jsapi_ticket,你就需要向下面這個url:qyapi.weixin.qq.com/cgi-bin/get… GET請求,需要帶上兩個引數。access_token和type,如果你是獲取jsapi_ticket,那麼type就是固定的,值為jsapi。就可以在返回裡面拿到ticket。並且你需要在伺服器端快取返回拿到的ticket。這個ticket就是上面通俗解釋裡的憑證,有效期兩個小時,此後前端所有需要用到ticket的地方,後端需要去判斷,如果ticket仍然沒有過期,就從快取中取出返回給前端,如果失效,就再發一個GET介面,獲取後再存入快取並且返回給前端。如果請求正常的話,會返回下列資料。

{
    'errcode': 0,
    'errmsg': 'ok',
    'ticket': 'bxLdikRXVbTPdHSM05e5u5sUoXNKd8-41ZO3MhKoyN5OfkWITDGgnr2fwJ0m9E8NYzWKVZvdVtaUgWvsdshFKA',
    'expires_in': 7200,
}
複製程式碼

拿到了jsapi_ticket之後,我們就可以開始進行許可權簽名演算法了。演算法的流程如下。

如何正確的在專案中接入微信JS-SDK
這個邏輯需要在後端實現。為什麼會在下文給出。將需要用到js-sdk頁面的url、以及jsapi_ticket、noncestr(隨機字串)、timestamp(當前的時間戳)進行字典序 排序,然後使用URL鍵值對的格式 (即 key1=value1&key2=value2…)拼接成字串string。然後將這個string使用sha1加密,得到的結果就是signature了。然後將signature、timestamp、nonceStr返回給前端,wx.config需要用到這些資料。然後將它們用這裡需要特別注意一下,官方的注意文件如下。

注意事項

  1. 簽名用的noncestr和timestamp必須與wx.config中的nonceStr和timestamp相同。

  2. 簽名用的url必須是呼叫JS介面頁面的完整URL。

  3. 出於安全考慮,開發者必須在伺服器端實現簽名的邏輯。

這裡的官方文件其實也沒有那麼官方,其實就是告訴我們,實現上述簽名邏輯必須在伺服器,以及noncestr和timestamp必須要和在伺服器端簽名所使用的一致,還有就是呼叫微信js-sdk的頁面的url必須要跟服務端簽名所使用的url一致。所有在服務端可以直接從請求的header裡面的referer獲取。

你把介面做好之後,只要能夠正確的返回signature、nonceStr、timestamp(有後端的更好,直接找他們要介面就好了),就可以愉快的進行下一步了。

通過config介面注入許可權驗證配置

官方的描述如下。

所有需要使用JS-SDK的頁面必須先注入配置資訊,否則將無法呼叫(同一個url僅需呼叫一次,對於變化url的SPA的web app可在每次url變化時進行呼叫,目前Android微信客戶端不支援pushState的H5新特性,所以使用pushState來實現web app的頁面會導致簽名失敗,此問題會在Android6.2中修復)。

在進行了正確的微信javascript檔案引入後(看上面)在頁面中呼叫如下程式碼就可以注入許可權驗證配置。下面是官方給的樣例程式碼。

wx.config({
    debug: true, // 開啟除錯模式,呼叫的所有api的返回值會在客戶端alert出來,若要檢視傳入的引數,可以在pc端開啟,引數資訊會通過log打出,僅在pc端時才會列印。
    appId: '', // 必填,企業號的唯一標識,此處填寫企業號corpid
    timestamp: , // 必填,生成簽名的時間戳
    nonceStr: '', // 必填,生成簽名的隨機串
    signature: '',// 必填,簽名,見附錄1
    jsApiList: [] // 必填,需要使用的JS介面列表,所有JS介面列表見附錄2
});
複製程式碼

下面我給一個樣例資料。

// data就是上一步說的後端返回的那些資料,包含signature、nonceStr、timestamp
const data = await getJsSDK();

wx.config({
    debug: true,
    appId: '你的appId',
    timestamp: data.timestamp,
    nonceStr: data.nonceStr,
    signature: data.signature,
    jsApiList: [
      'onMenuShareTimeline', // 分享到朋友圈
      'onMenuShareAppMessage', // 分享給朋友
      'onMenuShareQQ',// 分享到QQ
      'onMenuShareWeibo',// 分享到騰訊微博
      'onMenuShareQZone',// 分享到QQ空間
    ]
});
複製程式碼

注入後的生命週期函式

在呼叫config後會有兩個結果,成(這)功(是)和(廢)失(話)敗。可以通過微信提供的兩個介面來進行事件回撥。

wx.ready(function(){
    // config資訊驗證後會執行ready方法,所有介面呼叫都必須在config介面獲得結果之後,config是一個客戶端的非同步操作,所以如果需要在頁面載入時就呼叫相關介面,則須把相關介面放在ready函式中呼叫來確保正確執行。對於使用者觸發時才呼叫的介面,則可以直接呼叫,不需要放在ready函式中。
});

wx.error(function(res){
    // config資訊驗證失敗會執行error函式,如簽名過期導致驗證失敗,具體錯誤資訊可以開啟config的debug模式檢視,也可以在返回的res引數中檢視,對於SPA可以在這裡更新簽名。
});
複製程式碼

呼叫分享介面

在ready()中呼叫具體的分享介面。如分享到朋友圈、好友、QQ空間。程式碼如下。我把介面的所有的鉤子函式都給了出來。其實常用的就只有的success和cancel。根據你個人的需求而定。

wx.ready(function(){
  /* 分享到朋友圈 */
  wx.onMenuShareTimeline({
    title: '', // 分享標題
    link: '', // 分享連結,該連結域名必須與當前企業的可信域名一致
    imgUrl: '', // 分享圖示
    success: function () {
      // 使用者確認分享後執行的回撥函式
    },
    cancel: function () {
      // 使用者取消分享後執行的回撥函式
    },
    trigger: function () {
      // 監聽Menu中的按鈕點選時觸發的方法
    },
    complete: function () {
      // 介面呼叫完成時執行的回撥函式,無論成功或失敗都會執行
    },
    fail: function () {
      // 介面呼叫失敗時執行的回撥函式
    },
  });
});
複製程式碼

微信官方文件在這給了一個特別的提醒。

注意:不要嘗試在trigger中使用ajax非同步請求修改本次分享的內容,因為客戶端分享操作是一個同步操作,這時候使用ajax的回包會還沒有返回。

大概意思就是,不要嘗試在鉤子函式中動態的修改title啊link啊的值,因為分享是同步的操作,ajax的值返回回來的時候分享的操作已經結束了。比起這個,要注意的是link欄位,它的域名必須要跟微信後臺配置的JS安全域域名一致,否則分享會失敗。到這為止,微信js-sdk的接入就完成了。還有問題可以直接留言或者聯絡我。

寫在後面

最後還需要注意一點的是,如果頁面的url發生了變化,在新的url下呼叫js-sdk一定要再呼叫一次簽名介面,用新的url再進行一次簽名,否則會呼叫不成功。

微信官方文件地址在 這裡

歡迎光臨 個人部落格

相關文章