使用CryptoJS解決微信小程序用戶信息解密

使用CryptoJS解決微信小程序用戶信息解密


問題描述:
wx.getUserInfo(OBJECT) 微信官方的這個獲取用戶信息的方法,須要對接口返回的加密數據( encryptedData )進行對稱解密。html

    微信官方有提供加密數據解密算法

  接口若是涉及敏感數據(如wx.getUserInfo當中的 openId 和unionId ),接口的明文內容將不包含這些敏感數據。開發者如須要獲取敏感數據,須要對接口返回的加密數據( encryptedData )進行對稱解密。 解密算法以下:git

  1. 對稱解密使用的算法爲 AES-128-CBC,數據採用PKCS#7填充。
  2. 對稱解密的目標密文爲 Base64_Decode(encryptedData)。
  3. 對稱解密祕鑰 aeskey = Base64_Decode(session_key), aeskey 是16字節。
  4. 對稱解密算法初始向量 爲Base64_Decode(iv),其中iv由數據接口返回。

  微信官方提供了多種編程語言的示例代碼(點擊下載)。每種語言類型的接口名字均一致。調用方式能夠參照示例。github

  另外,爲了應用能校驗數據的有效性,咱們會在敏感數據加上數據水印( watermark )算法

  注:此前提供的加密數據(encryptData)以及對應的加密算法將被棄用,請開發者不要再依賴舊邏輯。編程


  下載後發現,這裏邊竟然沒有純 js 的 demo,好歹你本身家的小程序是隻能用 js 哇。小程序


  

找了網上好多文章,基本都是 Java 版本的解密,因此決定本身弄個純js的。微信小程序

 

  乾貨:模仿 Node 的 demo,使用 CryptoJS實現純 js 下解密用戶信息

  1. 將 CryptoJS 的包放入 小程序的 utils 中(點擊下載

    

  2. 封裝 RdWXBizDataCrypt.jsapi

/**
 * Created by rd on 2017/5/4.
 */
// 引入CryptoJS
var Crypto = require('cryptojs/cryptojs.js').Crypto;
var app = getApp();

function RdWXBizDataCrypt(appId, sessionKey) {
  this.appId = appId
  this.sessionKey = sessionKey
}

RdWXBizDataCrypt.prototype.decryptData = function (encryptedData, iv) {
  // base64 decode :使用 CryptoJS 中 Crypto.util.base64ToBytes()進行 base64解碼
  var encryptedData = Crypto.util.base64ToBytes(encryptedData)
  var key = Crypto.util.base64ToBytes(this.sessionKey);
  var iv = Crypto.util.base64ToBytes(iv);

  // 對稱解密使用的算法爲 AES-128-CBC,數據採用PKCS#7填充
  var mode = new Crypto.mode.CBC(Crypto.pad.pkcs7);
  
  try {
    // 解密
    var bytes = Crypto.AES.decrypt(encryptedData, key, {
        asBpytes:true,
        iv: iv,
        mode: mode
    });
    
    var decryptResult = JSON.parse(bytes);
    
  } catch (err) {
    console.log(err)
  }

  if (decryptResult.watermark.appid !== this.appId) {
    console.log(err)
  }

  return decryptResult
}

module.exports = RdWXBizDataCrypt

 

  3. 在 app.js 中引入 RdWXBizDataCrypt微信

var WXBizDataCrypt = require('utils/RdWXBizDataCrypt.js');
var AppId = 'wx**************'
var AppSecret = '8f***************************'

App({
  onLaunch: function () {
  },
  getUserInfo:function(cb){
    var that = this
    if(this.globalData.userInfo){
      typeof cb == "function" && cb(this.globalData.userInfo)
    }else{
      //調用登陸接口,獲取 code
      wx.login({
        success: function (res) {
          //發起網絡請求
          wx.request({
              url: 'https://api.weixin.qq.com/sns/jscode2session',
              data:{
                  appid:AppId,
                  secret:AppSecret,
                  js_code:res.code,
                  grant_type:'authorization_code'
              },
              header: {  
                  "Content-Type": "application/x-www-form-urlencoded"
              }, 
              method: 'GET', 
              success: function(res){
                var pc = new WXBizDataCrypt(AppId, res.data.session_key)
                wx.getUserInfo({
                  success: function (res) {
                    var data = pc.decryptData(res.encryptedData , res.iv)
                    console.log('解密後 data: ', data)
                  }
                })
              },
              fail: function(res) {},
              complete: function(res) {}
          });
        }
      })
    }
  }
})

 

  4. 實現效果網絡

    

附圖:微信官方時序圖

 

相關文章
相關標籤/搜索