一、拼多多反爬虫机制与 JS 逆向的必要性
拼多多的前端页面数据加载并非传统的服务端渲染,而是大量采用异步请求(AJAX)加载数据。这些异步请求的参数(如sign、token等)往往经过 JavaScript 加密处理,直接通过 Python 的requests库发送请求,会因参数无效被服务器拒绝。
例如,当我们在拼多多搜索 “手机” 时,浏览器的网络请求中会出现一个获取商品列表的接口,其请求参数包含一串加密的sign值。这个sign值是由前端 JS 根据请求参数、时间戳、固定密钥等信息计算得出的。如果无法还原这个加密过程(即 JS 逆向),就无法构造有效的请求参数,自然无法获取数据。
JS 逆向的本质,是通过分析前端 JavaScript 代码,还原其数据加密、参数生成的逻辑,再将该逻辑用 Python 或其他语言复现,从而构造出符合服务器要求的请求。对于拼多多这类平台,入门级的 JS 逆向主要聚焦于参数加密逻辑的还原,这也是本文的核心内容。
二、JS 逆向的基础步骤(以拼多多商品接口为例)
步骤 1:抓包分析请求参数
首先需要使用浏览器的开发者工具(Chrome/Firefox 的 F12)抓取目标接口的请求信息。以拼多多网页版商品列表接口为例:
1. 打开拼多多网页版,搜索 “手机”;
2. 打开开发者工具的「Network」标签,筛选「XHR/Fetch」类型的请求;
3. 找到商品列表对应的接口(如/api/search/get),查看其请求参数和响应数据。
此时会发现,请求参数中包含page(页码)、keyword(关键词)、timestamp(时间戳)、sign(签名)等参数,其中sign是加密后的字符串,也是我们需要逆向的核心。
步骤 2:定位加密 JS 代码
找到sign参数的生成逻辑,是 JS 逆向的关键。常用方法有两种:
1. 全局搜索:在开发者工具的「Sources」标签中,使用快捷键Ctrl+Shift+F搜索sign或sign=,定位到包含该参数生成的 JS 代码段;
2. 断点调试:在请求发起的代码处设置断点,逐步执行代码,观察sign参数的生成过程。
拼多多的前端代码经过了压缩混淆,但入门级的加密逻辑往往不会过于复杂。我们可以通过观察代码中的加密函数(如 MD5、SHA256 等哈希函数,或自定义的拼接加密),确定sign的生成规则。
步骤 3:还原加密逻辑
找到加密代码后,需要理解其逻辑并记录关键信息:
● 加密所使用的算法(如 MD5);
● 参与加密的参数顺序(如timestamp+keyword+page+密钥);
● 固定密钥(可能是硬编码在 JS 中的字符串,如pdd_123456)。
例如,假设拼多多某接口的sign生成逻辑为:将timestamp、keyword、page和固定密钥pdd_secret按顺序拼接,再进行 MD5 加密得到小写字符串。我们需要将这一逻辑准确还原。
步骤 4:Python 复现加密逻辑
将还原的 JS 加密逻辑用 Python 代码实现,生成对应的sign参数,再构造 HTTP 请求获取数据。
三、代码实现:拼多多商品数据抓取的 JS 逆向案例
前置说明
本文案例中的接口和加密逻辑为拼多多入门级模拟场景(因拼多多真实加密逻辑会持续更新,且涉及平台合规性,此处采用简化的模拟逻辑),核心是演示 JS 逆向的流程。实际场景中,需结合具体抓包结果调整逻辑。
步骤 1:抓包与 JS 加密逻辑分析(模拟)
假设抓包得到的请求参数为:
json
{
"keyword": "手机",
"page": 1,
"timestamp": 1718000000000,
"sign": "a1b2c3d4e5f67890abcdef1234567890"
}
通过全局搜索和断点调试,找到 JS 加密代码如下(压缩后的简化版):
javascript
运行
function generateSign(params, secret) {
// 1. 按参数名升序排序
let sortedKeys = Object.keys(params).sort();
let str = '';
// 2. 拼接参数名和值
for (let key of sortedKeys) {
str += key + params[key];
}
// 3. 拼接固定密钥
str += secret;
// 4. MD5加密并转小写
return md5(str).toLowerCase();
}
// 调用示例:
let params = {
keyword: "手机",
page: 1,
timestamp: 1718000000000
};
let secret = "pdd_2024_secret"; // 固定密钥
let sign = generateSign(params, secret);
这段代码的逻辑是:将请求参数按名升序排序,拼接参数名和值,再拼接固定密钥,最后 MD5 加密得到sign。
步骤 2:Python 复现加密逻辑
首先安装所需依赖:
然后编写 Python 代码,实现参数拼接、MD5 加密,并构造请求:
python
import requests
import hashlib
import time
def generate_sign(params, secret):
"""
复现JS的sign生成逻辑
:param params: 请求参数字典
:param secret: 固定密钥
:return: 加密后的sign
"""
# 1. 按参数名升序排序
sorted_keys = sorted(params.keys())
str_temp = ''
# 2. 拼接参数名和值
for key in sorted_keys:
str_temp += key + str(params[key])
# 3. 拼接固定密钥
str_temp += secret
# 4. MD5加密并转小写
md5_obj = hashlib.md5()
md5_obj.update(str_temp.encode('utf-8'))
sign = md5_obj.hexdigest().lower()
return sign
def get_pdd_goods(keyword, page):
"""
获取拼多多商品数据
:param keyword: 搜索关键词
:param page: 页码
:return: 商品数据
"""
# 固定配置
url = "https://api.pinduoduo.com/api/search/get" # 模拟接口,实际需替换为真实接口
secret = "pdd_2024_secret" # 从JS中提取的固定密钥
# 构造基础参数
timestamp = int(time.time() * 1000) # 生成当前时间戳(毫秒)
params = {
"keyword": keyword,
"page": page,
"timestamp": timestamp
}
# 生成sign参数
sign = generate_sign(params, secret)
params["sign"] = sign # 将sign加入参数
# 发送请求
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36",
"Referer": "https://www.pinduoduo.com/",
"Cookie": "" # 实际场景中需添加抓包得到的Cookie
}
# 配置代理信息
proxyHost = "www.16yun.cn"
proxyPort = "5445"
proxyUser = "16QMSOML"
proxyPass = "280651"
# 构建代理URL(支持HTTP和HTTPS)
proxy_url = f"http://{proxyUser}:{proxyPass}@{proxyHost}:{proxyPort}"
proxies = {
"http": proxy_url,
"https": proxy_url
}
try:
# 发送请求时添加proxies参数
response = requests.get(url, params=params, headers=headers, proxies=proxies)
if response.status_code == 200:
return response.json()
else:
print(f"请求失败,状态码:{response.status_code}")
return None
except Exception as e:
print(f"请求异常:{e}")
return None
# 主函数调用
if __name__ == "__main__":
goods_data = get_pdd_goods("手机", 1)
if goods_data:
print("获取的商品数据:")
print(goods_data)
else:
print("未获取到商品数据")
代码说明
1. generate_sign 函数:完全复现了 JS 中的加密逻辑,包括参数排序、拼接、MD5 加密;
2. get_pdd_goods 函数:构造请求参数,生成sign,发送 HTTP 请求并返回数据;
3. 注意事项:实际场景中,url需要替换为抓包得到的真实接口,Cookie需要添加浏览器中的有效 Cookie,secret需要从真实 JS 代码中提取。
四、JS 逆向的进阶与合规性说明
1. 进阶挑战
拼多多的真实 JS 代码会采用代码混淆(如变量名混淆、控制流平坦化)、动态密钥(密钥从服务器获取,而非硬编码)、浏览器指纹验证(如验证 User-Agent、Canvas 指纹)等手段,增加逆向难度。此时需要掌握:
● 使用ast模块解析混淆后的 JS 代码;
● 使用execjs库直接执行 JS 代码(避免手动复现);
● 模拟浏览器环境(如使用 Selenium、Playwright)绕过指纹验证。
2. 合规性重要提醒
本文的案例仅用于技术学习,抓取拼多多数据需遵守平台的《用户协议》和《robots.txt》规则,不得用于商业用途或恶意攻击。根据《中华人民共和国网络安全法》和《反不正当竞争法》,未经授权的大规模数据抓取可能涉嫌违法违规。
五、总结
本文以拼多多数据抓取为例,讲解了 Python 爬虫中 JS 逆向的基础流程:抓包分析参数→定位加密 JS 代码→还原加密逻辑→Python 代码复现。对于入门者而言,核心是理解 JS 逆向的本质是逻辑还原,而非单纯的代码编写。
在实际应用中,JS 逆向的难度会随着平台反爬虫技术的升级而增加,但基础思路始终不变。同时,必须牢记合规性原则,将技术用于合法的场景中。通过本文的案例,希望能帮助入门者迈出 JS 逆向的第一步,为后续的爬虫开发和数据分析工作打下基础。
红包分享
钱包管理

