【JS 逆向百例】某公共資源交易網(wǎng),公告 URL 參數(shù)逆向分析

10年的鐘祥網(wǎng)站建設(shè)經(jīng)驗(yàn),針對設(shè)計(jì)、前端、開發(fā)、售后、文案、推廣等六對一服務(wù),響應(yīng)快,48小時及時工作處理。成都全網(wǎng)營銷推廣的優(yōu)勢是能夠根據(jù)用戶設(shè)備顯示端的尺寸不同,自動調(diào)整鐘祥建站的顯示方式,使網(wǎng)站能夠適用不同顯示終端,在瀏覽器中調(diào)整網(wǎng)站的寬度,無論在任何一種瀏覽器上瀏覽網(wǎng)站,都能展現(xiàn)優(yōu)雅布局與設(shè)計(jì),從而大程度地提升瀏覽體驗(yàn)。創(chuàng)新互聯(lián)建站從事“鐘祥網(wǎng)站設(shè)計(jì)”,“鐘祥網(wǎng)站推廣”以來,每個客戶項(xiàng)目都認(rèn)真落實(shí)執(zhí)行。

聲明

本文章中所有內(nèi)容僅供學(xué)習(xí)交流,抓包內(nèi)容、敏感網(wǎng)址、數(shù)據(jù)接口均已做脫敏處理,嚴(yán)禁用于商業(yè)用途和非法用途,否則由此產(chǎn)生的一切后果均與作者無關(guān),若有侵權(quán),請聯(lián)系我立即刪除!

逆向目標(biāo)

  • 目標(biāo):某地公共資源交易網(wǎng)
  • 主頁:aHR0cDovL2dnenkuamNzLmdvdi5jbi93ZWJzaXRlL3RyYW5zYWN0aW9uL2luZGV4
  • 接口:aHR0cDovL2dnenkuamNzLmdvdi5jbi9wcm8tYXBpLWNvbnN0cnVjdGlvbi9jb25zdHJ1Y3Rpb24vYmlkZGVyL2JpZFNlY3Rpb24vbGlzdA==
  • 逆向參數(shù):URL 鏈接中的 projectId、projectInfo 參數(shù)

逆向過程

抓包分析

通過鏈接進(jìn)入到網(wǎng)站,會發(fā)現(xiàn)先轉(zhuǎn)會圈才進(jìn)入到網(wǎng)頁,這里可能就有個渲染加載的過程,打開開發(fā)者人員工具,刷新網(wǎng)頁,往下滑會看到抓包到了數(shù)據(jù)返回的接口:aHR0cDovL2dnenkuamNzLmdvdi5jbi9wcm8tYXBpLWNvbnN0cnVjdGlvbi9jb25zdHJ1Y3Rpb24vYmlkZGVyL2JpZFNlY3Rpb24vbGlzdA==,GET 請求,從 preview 響應(yīng)預(yù)覽中可以看到當(dāng)前頁面所有公告的信息:

Query String Parameters 中有些參數(shù)信息,各類型什么含義后文會詳細(xì)講解:

  • pageNum: 當(dāng)前為第幾頁
  • pageSize: 頁面大小
  • informationType: 公告類型
  • projectType: 項(xiàng)目類型
  • informationName: 信息類型

接下來隨便點(diǎn)擊一條公告,跳轉(zhuǎn)到一個新頁面,會發(fā)現(xiàn)網(wǎng)頁鏈接變成了這種格式:XXX/index?projectId=XXX&projectInfo=XXX,生成了 projectId 和 projectInfo 兩個加密參數(shù),并且經(jīng)過測試,同一個公告頁面這兩個加密參數(shù)的值是固定的,接下來我們需要嘗試找到這兩個參數(shù)的加密位置。

調(diào)試分析定位

從主頁位置 CTRL + SHIFT + F 全局搜索 projectId 參數(shù),依次對比可以發(fā)現(xiàn),projectId 和 projectInfo 兩個加密參數(shù)在 chunk-.eb5f8d30.js 中定義,這里是個三目運(yùn)算,若項(xiàng)目類型相同則執(zhí)行其后的方法,若不同則往后執(zhí)行:

上文代碼行判斷中出現(xiàn)的 ZFCG、GTGC 是什么意思呢,CTRL + SHIFT + F 全局搜索 ZBGG 參數(shù),在 chunk-043c03b8.34f6abab.js 文件中我們可以找到相應(yīng)的定義,以下即各自的含義:

在第 267 行,return t.stop() 處打下斷點(diǎn)進(jìn)行調(diào)試分析,隨便點(diǎn)擊一條公告,會發(fā)現(xiàn)斷點(diǎn)斷住,即成功定位,鼠標(biāo)懸停在 projectId 和 projectInfo 對應(yīng)的值上,可以知道以下信息:

  • projectId :項(xiàng)目編號
  • projectInfo :信息類型

知道了兩個加密參數(shù)的具體含義,接下來我們就需要找到其加密位置了,projectId 和 projectInfo 參數(shù)由 a.parameterTool.encryptJumpPage 方法執(zhí)行,encryptJumpPage 跳轉(zhuǎn)頁面加密?這不簡直就是明示:

我們將鼠標(biāo)懸停在 a.parameterTool.encryptJumpPage 上,跟進(jìn)到方法生成的 js 文件 app.3275fd87.js 中去瞅瞅:

以上我們可以清晰地知道下面兩個參數(shù)的具體含義:

  • query:加密數(shù)據(jù)( projectId 和 projectInfo)
  • nextPath:路由跳轉(zhuǎn)位置

在第 2389 行打斷點(diǎn)進(jìn)行調(diào)試分析,從下圖可以知道,projectId 和 projectInfo 參數(shù)在 a 中被加密了:

進(jìn)一步跟蹤 a 的位置,往上滑可以看到第 2335 行到 2356 行是很明顯的 DES 加密:

但具體是哪個函數(shù)部分對 query 中的 projectId 和 projectInfo 參數(shù)進(jìn)行了加密還不得而知,我們繼續(xù)打斷點(diǎn)調(diào)試分析,在 2341 行打斷點(diǎn)時發(fā)現(xiàn),projectId 參數(shù)對應(yīng)的值 424,projectInfo 參數(shù)對應(yīng)的值 ZBGG,都在 function c(t) 中進(jìn)行了處理,證明此處就是關(guān)鍵的加密位置:

function c(t) {
    return i.a.DES.encrypt(t, o.keyHex, {
        iv: o.ivHex,
        mode: i.a.mode.CBC,
        padding: i.a.pad.Pkcs7
    }).ciphertext.toString()
}

分析這段關(guān)鍵的加密代碼:

  • iv:ivHex 十六進(jìn)制初始向量
  • mode:采用 CBC 加密模式,其是一種循環(huán)模式,前一個分組的密文和當(dāng)前分組的明文異或操作后再加密
  • padding:采用 Pkcs7 填充方式,在填充時首先獲取需要填充的字節(jié)長度 = 塊長度 - (數(shù)據(jù)長度 % 塊長度), 在填充字節(jié)序列中所有字節(jié)填充為需要填充的字節(jié)長度值
  • ciphertext.toString():將加密后的密文,以十六進(jìn)制字符串形式返回

模擬執(zhí)行

這里直接引用 JS,使用 nodejs 里面的加密模塊 crypto-js 來進(jìn)行 DES 加密,調(diào)試過程中提示哪個函數(shù)未定義,就將其定義部分添加進(jìn)來即可,改寫后的完整 JS 代碼如下:

var CryptoJS = require('crypto-js');

o = {
    keyHex: CryptoJS.enc.Utf8.parse(Object({
        NODE_ENV: "production",
        VUE_APP_BASE_API: "/pro-api",
        VUE_APP_CONSTRUCTION_API: "/pro-api-construction",
        VUE_APP_DEV_FILE_PREVIEW: "/lyjcdFileView/onlinePreview",
        VUE_APP_FILE_ALL_PATH: "http://www.lyjcd.cn:8089",
        VUE_APP_FILE_PREFIX: "/mygroup",
        VUE_APP_LAND_API: "/pro-api-land",
        VUE_APP_PREVIEW_PREFIX: "/lyjcdFileView",
        VUE_APP_PROCUREMENT_API: "/pro-api-procurement",
        VUE_APP_WINDOW_TITLE: "XXXXXX",
        BASE_URL: "/"
    }).VUE_APP_CUSTOM_KEY || ""),
    ivHex: CryptoJS.enc.Utf8.parse(Object({
        NODE_ENV: "production",
        VUE_APP_BASE_API: "/pro-api",
        VUE_APP_CONSTRUCTION_API: "/pro-api-construction",
        VUE_APP_DEV_FILE_PREVIEW: "/lyjcdFileView/onlinePreview",
        VUE_APP_FILE_ALL_PATH: "http://www.lyjcd.cn:8089",
        VUE_APP_FILE_PREFIX: "/mygroup",
        VUE_APP_LAND_API: "/pro-api-land",
        VUE_APP_PREVIEW_PREFIX: "/lyjcdFileView",
        VUE_APP_PROCUREMENT_API: "/pro-api-procurement",
        VUE_APP_WINDOW_TITLE: "XXXXXX",
        BASE_URL: "/"
    }).VUE_APP_CUSTOM_IV || "")
};

function c(t) {
    return CryptoJS.DES.encrypt(t, o.keyHex, {
        iv: o.ivHex,
        mode: CryptoJS.mode.CBC,
        padding: CryptoJS.pad.Pkcs7
    }).ciphertext.toString()
}

// 測試
// console.log(c('ZBGG'))
// ff15d186c4d5fa7a

VUE_APP_WINDOW_TITLE 對應(yīng)值內(nèi)容經(jīng)過脫敏處理,經(jīng)測試,不影響結(jié)果輸出

完整代碼

GitHub 關(guān)注 K 哥爬蟲,持續(xù)分享爬蟲相關(guān)代碼!歡迎 star !https://github.com/kgepachong/

以下只演示部分關(guān)鍵代碼,不能直接運(yùn)行!完整代碼倉庫地址:https://github.com/kgepachong/crawler/

本案例代碼:https://github.com/kgepachong/crawler/tree/main/ggzy_jcs_gov_cn

# =======================
# --*-- coding: utf-8 --*--
# @Author  : 微信公眾號:K哥爬蟲
# @FileName: ggzy.py
# @Software: PyCharm
# =======================


import urllib.parse
import execjs
import requests


url = '脫敏處理,完整代碼關(guān)注 https://github.com/kgepachong/crawler/'


def encrypted_project_id(id_enc):
    with open('ggzy_js.js', 'r', encoding='utf-8') as f:
        public_js = f.read()
        project_id = execjs.compile(public_js).call('Public', id_enc)
    return project_id


def encrypted_project_info(info_enc):
    with open('ggzy_js.js', 'r', encoding='utf-8') as f:
        public_js = f.read()
        project_info = execjs.compile(public_js).call('Public', info_enc)
    return project_info


def get_project_info(info_name, info_type):
    index_url = '脫敏處理,完整代碼關(guān)注 https://github.com/kgepachong/crawler/'
    urlparse = urllib.parse.urlparse(index_url)
    project_info = urllib.parse.parse_qs(urlparse.query)['informationName'][0]
    return project_info


def get_content(page, info_name, info_type):
    headers = {
        "Connection": "keep-alive",
        "Pragma": "no-cache",
        "Cache-Control": "no-cache",
        "Accept": "application/json, text/plain, */*",
        "User-Agent": "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36",
        "Referer": "脫敏處理,完整代碼關(guān)注 https://github.com/kgepachong/crawler/",
        "Accept-Language": "zh-CN,zh;q=0.9"
    }
    url_param = "脫敏處理,完整代碼關(guān)注 https://github.com/kgepachong/crawler/"
    params = {
        "pageNum": page,
        "pageSize": "20",
        "releaseTime": "",
        "search": "",
        "informationType": info_type,
        "departmentId": "",
        "projectType": "SZFJ",
        "informationName": info_name,
        "onlyCanBidSectionFlag": "NO"
    }
    response = requests.get(url=url_param, headers=headers, params=params)

    return response


def main():
    print("脫敏處理,完整代碼關(guān)注 https://github.com/kgepachong/crawler/")
    info_name = input("請輸入信息類型:")
    info_type = input("請輸入公告類型:")
    page = input("您想要獲取數(shù)據(jù)的頁數(shù):")
    get_content(page, info_name, info_type)
    response = get_content(page, info_name.upper(), info_type.upper())
    num = int(page) * 20
    print("總共獲取了 %d 個項(xiàng)目" % num)
    for i in range(20):
        title = response.json()['rows'][i]['content']
        query_id = response.json()['rows'][i]['projectId']
        query_info = get_project_info(info_name.upper(), info_type.upper())
        project_id_enc = encrypted_project_id(str(query_id))
        project_info_enc = encrypted_project_info(query_info)
        project_url = '%s?projectId=%s&projectInfo=%s' % (url, project_id_enc, project_info_enc)
        print("第 %d 個項(xiàng)目:" % (i+1) + "\n" + "項(xiàng)目名稱:%s  項(xiàng)目編號:%d " % (title, query_id) + "\n" + "項(xiàng)目鏈接:%s" % project_url)


if __name__ == '__main__':
    main()

代碼實(shí)現(xiàn)效果:


文章標(biāo)題:【JS 逆向百例】某公共資源交易網(wǎng),公告 URL 參數(shù)逆向分析
鏈接分享:http://m.kartarina.com/article26/dsoggcg.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供軟件開發(fā)標(biāo)簽優(yōu)化商城網(wǎng)站網(wǎng)站改版定制網(wǎng)站自適應(yīng)網(wǎng)站

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)

網(wǎng)站托管運(yùn)營
主站蜘蛛池模板: 无码乱码av天堂一区二区| 无遮掩无码h成人av动漫| 免费无码又爽又刺激聊天APP| 在线观看无码AV网站永久免费| 国产乱人伦中文无无码视频试看| 无码人妻久久一区二区三区蜜桃| 国产成人亚洲综合无码精品| 中文无码亚洲精品字幕| 中文字幕无码久久人妻| 无码色偷偷亚洲国内自拍| 无码成人一区二区| 无码人妻一区二区三区免费视频| 亚洲av无码专区在线| 无码人妻精品一区二区三| 无码 免费 国产在线观看91| 亚洲国产精品无码中文lv| 久久久久亚洲av无码专区蜜芽| aⅴ一区二区三区无卡无码| 69天堂人成无码麻豆免费视频| 亚洲V无码一区二区三区四区观看| 在线无码视频观看草草视频| 亚洲中文字幕无码亚洲成A人片| 无码人妻AⅤ一区二区三区| 久久无码精品一区二区三区| 久久亚洲中文字幕无码| 中日韩亚洲人成无码网站| 青青草无码免费一二三区| 亚洲成AV人片在线观看无码| 国产亚洲精久久久久久无码77777| 国产精品无码亚洲精品2021| 无码人妻久久一区二区三区免费丨 | 无套内射在线无码播放| 国产亚洲精品无码拍拍拍色欲| 国模无码视频一区二区三区| 高清无码v视频日本www| 孕妇特级毛片WW无码内射| 无码高潮爽到爆的喷水视频app| 一本色道无码道DVD在线观看| 中文字幕无码视频手机免费看| 亚洲午夜无码久久久久软件| 亚洲中文字幕久久精品无码VA|