最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

node.js中PC端微信小程序包解密的處理思路

 更新時間:2021年12月11日 09:26:34   作者:基爾醬  
我們使用node.js去寫一個解碼的程序。根據(jù)上邊加密的流程,我們首先讀取加密文件,把前6個字節(jié)的固定字符串去除,這篇文章主要介紹了node.js中PC端微信小程序包解密,需要的朋友可以參考下

原來發(fā)布在掘金,搬過來好了。

微信小程序在PC端是加密存儲的,如果直接打開是看不到什么有用的信息的,需要經(jīng)過解密才可以看到包內(nèi)具體的內(nèi)容。本文使用nodejs實現(xiàn)解密算法,主要涉及到crypto, commander, chalk三個包的使用。

小程序的源碼在哪里

PC端打開過的小程序會被緩存到本地微信文件的默認保存位置,可以通過微信PC端=>更多=>設(shè)置查看:

進入默認保存位置下的/WeChat Files/WeChat Files/Applet文件夾,可以看到該目錄下有一系列前綴為wx的文件(文件名其實是小程序的appid),這些就是我們打開過的小程序啦:

進入其中某個小程序的文件夾,我們可以看到一個名字為一串?dāng)?shù)字的文件夾。點進這個文件夾, 就可以看到一個__APP__.wxapkg文件,也就是小程序?qū)?yīng)的代碼啦:

然而,當(dāng)我們打開這個文件之后卻發(fā)現(xiàn)是這樣的:

WTF 這能看出來個??。很明顯,這個文件是經(jīng)過加密的,需要解密才能看到我們想看到的東西。

PC端小程序是怎么被加密的

這里參考了一位大佬用Go語言寫的PC端wxapkg解密代碼。整理一下的話,加密流程是這樣的:

首先將明文代碼在第1024字節(jié)處一分為二,前半部分使用CBC模式的AES加密,后半部分則直接進行異或。最后,將加密后的兩節(jié)拼接起來,并在最前邊寫入固定的字符串:"V1MMWX"。

所以,我們打開__APP__.wxapkg文件看到的就是加密后的代碼,如果想還原回去的話,需要從后往前逐步推回去。

解密思路

預(yù)處理

我們使用node.js去寫一個解碼的程序。根據(jù)上邊加密的流程,我們首先讀取加密文件,把前6個字節(jié)的固定字符串去除。由于AES加密和異或前后數(shù)據(jù)的位數(shù)是相同的,我們可以據(jù)此獲取到加密后的頭部1024字節(jié)和加密后的尾部部分:

const fs = require('fs').promises;
...
 
const buf = await fs.readFile(pkgsrc); // 讀取原始Buffer
const bufHead = buf.slice(6, 1024 + 6);
const bufTail = buf.slice(1024 + 6);

加密后的頭部部分

為了得到這1024個字節(jié)的明文,我們需要知道AES加密的初始向量iv,以及一個32位的密鑰。已知16字節(jié)的初始向量iv是字符串:“the iv: 16 bytes”,我們接下來需要計算出這個由pbkdf2算法導(dǎo)出的32位的密鑰。

pbkdf2(Password-Based Key Derivation Function)是一個用來生成密鑰的函數(shù),它使用一個偽隨機函數(shù),將原文密碼和salt作為輸入,通過不斷的迭代得到密鑰。在crypto庫中,pbkdf2函數(shù)是這樣的:

const crypto = require('crypto');
...
 
crypto.pbkdf2(password, salt, iterations, keylen, digest, callback)

其中參數(shù)分別是:原文密碼、鹽值、迭代次數(shù)、密鑰長度、散列算法、回調(diào)函數(shù)。已知salt是"saltiest",原文密碼為微信小程序的id(也就是wx開頭的那個文件夾名),迭代次數(shù)為1000,散列算法為sha1。因此,我們可以寫出計算密鑰的代碼:

crypto.pbkdf2(wxid, salt, 1000, 32, 'sha1', (err, dk) => {
    if (err) {
        // 錯誤
    }
    // dk即為計算得到的密鑰
})

密鑰和初始向量iv都有了之后,我們可以開始對密文進行解密了。AES加密算法是一種非對稱加密算法,它的密鑰分成公開的公鑰和只有自己知道的私鑰,任何人都可以使用公鑰進行加密,但是只有持有私鑰的人解密得到明文。

小程序使用的加密算法是CBC(Cipher Block Chaining, 密碼分組鏈接)模式的AES,也就是它在加密的時候,首先把明文進行分塊,然后將每一塊與前一塊加密后的密文進行異或,再使用公鑰進行加密,得到每一塊的密文。對于第一塊明文,由于它不存在前一塊明文,因此它會與初始向量iv進行異或,再進行公鑰加密。在實現(xiàn)的時候,我們只需要調(diào)用crypto提供的解密函數(shù)就可以啦。

我們知道,AES算法根據(jù)密鑰長度的不同有AES128, AES192和AES256。回顧上邊,我們的密鑰是32字節(jié),也就是256位的,因此顯然我們應(yīng)該使用的是AES256。綜上,我們可以寫出來解密的代碼:

const decipher = crypto.createDecipheriv('aes-256-cbc', dk, iv);
const originalHead = Buffer.alloc(1024, decipher.update(bufHead));

其中originalHead就是我們要的前1024字節(jié)的明文啦。我們可以打印出來看看:

嗯…… 有那么點意思了。

加密后的尾部部分

這一部分就很簡單啦。由于異或運算是具有自反性的,因此只需要簡單的判斷一下小程序id的位數(shù)獲得異或的xorKey,再把它與密文進行異或,就可以得到原文了:

const xorKey = wxid.length < 2 ? 0x66 : wxid.charCodeAt(wxid.length - 2);
const tail = [];
for(let i = 0; i < bufTail.length; ++i){
    tail.push(xorKey ^ bufTail[i]);
}
const originalTail = Buffer.from(tail);

將頭部部分的明文與尾部部分的明文進行拼接,再以二進制形式寫入文件,就可以得到最終的明文啦。

再漂亮點

根據(jù)上邊的描述,我們可以把我們整個的解密過程封裝成一個黑盒子:

commander

我們可以使用commander庫讓程序直接從命令行讀取小程序的id和密文包。commander是一個nodejs命令行界面的解決方案,可以很方便的定義自己的cli命令。比如說對于下面這一串代碼:

const program = require('commander');
...
program
    .command('decry <wxid> <src> [dst]')
    .description('解碼PC端微信小程序包')
    .action((wxid, src, dst) => {
        wxmd(wxid, src, dst);
    })
 
program.version('1.0.0')
    .usage("decry <wxid> <src> [dst]")
    .parse(process.argv);

我定義了一個"decry <wxid> <src> [dst]"的命令,其中尖括號代表必選參數(shù),方括號代表可選參數(shù)。description內(nèi)是關(guān)于這個命令的描述文本,action則是執(zhí)行這段命令。在控制臺使用node執(zhí)行代碼之后,可以看到如下界面:

于是我們就可以根據(jù)提示,輸入?yún)?shù)進行解密啦。commander.js的中文文檔在這里。

chalk

為了讓我們的控制臺多一抹顏色,我們可以使用chalk.js來美化輸出。chalk的基本用法也比較簡單:

const chalk = require('chalk');
...
 
console.log(chalk.green('綠了'))

這樣我們就可以在黑白的控制臺上填上一抹綠色,替大熊貓實現(xiàn)夢想:

除此之外,我們還可以使用es6的字符串標簽?zāi)0甯奖愕氖褂胏halk。具體的參考chalk官方文檔吧。

源代碼

代碼發(fā)布到github和gitee啦,可以給大家參考一下下~

github點這里,?gitee點這里

到此這篇關(guān)于node.js中PC端微信小程序包解密的文章就介紹到這了,更多相關(guān)nodejs微信小程序解密內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • express + jwt + postMan驗證實現(xiàn)持久化登錄

    express + jwt + postMan驗證實現(xiàn)持久化登錄

    這篇文章主要介紹了express + jwt + postMan驗證實現(xiàn)持久化登錄,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-06-06
  • node.js中axios使用心得總結(jié)

    node.js中axios使用心得總結(jié)

    這篇文章主要介紹了node.js中axios使用心得總結(jié),以及分析了中間遇到的錯誤,大家參考一下。
    2017-11-11
  • nodejs實現(xiàn)bigpipe異步加載頁面方案

    nodejs實現(xiàn)bigpipe異步加載頁面方案

    本文給大家分享的是使用nodejs結(jié)合bigpipe實現(xiàn)異步加載頁面的方案,非常的實用,也是以后前端性能優(yōu)化的一個方向,希望大家能夠喜歡。
    2016-01-01
  • 詳解node單線程實現(xiàn)高并發(fā)原理與node異步I/O

    詳解node單線程實現(xiàn)高并發(fā)原理與node異步I/O

    本篇文章主要介紹了node單線程實現(xiàn)高并發(fā)原理與node異步I/O ,具有一定的參考價值,有興趣的可以了解一下
    2017-09-09
  • Node.js開發(fā)之套接字(socket)編程入門示例

    Node.js開發(fā)之套接字(socket)編程入門示例

    這篇文章主要介紹了Node.js開發(fā)之套接字(socket)編程,結(jié)合簡單實例形式分析了node.js套接字socket客戶端與服務(wù)器端相關(guān)實現(xiàn)與使用技巧,需要的朋友可以參考下
    2019-11-11
  • Ubuntu中搭建Nodejs開發(fā)環(huán)境過程分享

    Ubuntu中搭建Nodejs開發(fā)環(huán)境過程分享

    這篇文章主要介紹了Ubuntu中搭建Nodejs開發(fā)環(huán)境過程,比較郁悶的是apt-get安裝失敗了,如果有遇到一樣問題的朋友,可以參考一下本文
    2014-06-06
  • Node.js(安裝,啟動,測試)

    Node.js(安裝,啟動,測試)

    這里主要介紹基于windows平臺上最簡單方便的安裝方式,啟動以及簡單測試
    2014-06-06
  • Node.js的包詳細介紹

    Node.js的包詳細介紹

    這篇文章主要介紹了Node.js的包詳細介紹,Node.js的包是一個目錄,其中包含JSON格式的包說明文件package.json,Node.js的包基本遵循CommonJS規(guī)范,需要的朋友可以參考下
    2015-01-01
  • Nodejs 獲取時間加手機標識的32位標識實現(xiàn)代碼

    Nodejs 獲取時間加手機標識的32位標識實現(xiàn)代碼

    本文給大家分享nodejs獲取時間加手機標識的32位標識實現(xiàn)代碼,非常不錯,具有參考借鑒價值,需要的朋友參考下
    2017-03-03
  • 在Node.js中實現(xiàn)視頻收藏功能

    在Node.js中實現(xiàn)視頻收藏功能

    在構(gòu)建視頻分享平臺時,視頻的收藏功能是用戶互動的重要組成部分,本文將介紹如何在Node.js應(yīng)用中實現(xiàn)視頻收藏功能,包括數(shù)據(jù)模型的創(chuàng)建、業(yè)務(wù)邏輯的實現(xiàn)以及接口的驗證測試,需要的朋友可以參考下
    2024-04-04

最新評論

横峰县| 泉州市| 贵州省| 新乡县| 安福县| 色达县| 六安市| 巫溪县| 绿春县| 吴桥县| 东海县| 嵊泗县| 京山县| 晋州市| 汉沽区| 阿拉善左旗| 西宁市| 沧源| 阆中市| 西畴县| 青冈县| 嘉荫县| 黑山县| 吴桥县| 沧源| 东乡族自治县| 玉林市| 元阳县| 紫金县| 周至县| 衡东县| 南平市| 太和县| 丰原市| 石棉县| 崇信县| 佛冈县| 邳州市| 合作市| 武陟县| 西藏|