爬虫实战3-js逆向入门:以黑猫投诉平台为例

目录

引言

逆向过程

步骤一:找到参数对应js代码位置

步骤二:分析参数值的生成逻辑

步骤三:确定函数u的具体内容

步骤四:使用python实现请求参数的生成

投诉信息爬取


引言

下面是一张主流网页加密方法的思维导图,本文将介绍的黑猫投诉平台网站使用的即是请求头加密。

从开发者工具中抓包的结果来看,该网页的json数据包的请求参数中rs和signature两个参数在下拉后得到的新数据包中是动态变化的,而ts参数过一段时间会发生变化(推测应该是和时间戳相关的参数)。接下来就通过js逆向获取这几个参数的生成方法,并实现爬取投诉信息。

逆向过程

步骤一:找到参数对应js代码位置

由于用rs搜索容易重复,这里搜索signature参数,其中只有一个js文件中包含该变量名。

在js代码中再次搜索该变量名,发现共找到14个,为了找到真正的signature参数位置,对可能是该参数的位置打上断点,挨个尝试后确定获得signature参数值的位置在下图所示位置,实际是变量g的值。同时也可以清楚的看到ts和rs的值分别等于l和p两个变量的值。

步骤二:分析参数值的生成逻辑

从代码中很清楚的看到g的值通过这段代码赋予:var g = u([l, p, b, h, c, d["type" + e]].sort().join("")),也就是将这几个变量l, p, b, h, c, d["type" + e]排序后组成一个新的字符串,并将该字符串传入函数u,得到返回值即为g的值。

再往上找寻找上面几个变量的值的生成方式,可以发现在下图所示代码中,这些变量被创建和赋值。首先l变量确实是当前时间戳得到的值(l的值也是ts参数的值,印证了一开始的猜想);b是一个常数,值为"$d6eb7ff91ee257475%";h的值是PAGE_CONFIG对象的keywords属性的值,实际上从右边作用域可以看到就是我们的搜索关键字,值为"外卖 食品安全";c的值为10,它其实就是请求参数中的page_size的值;e的值从右边作用域也可以看到值为1,刷新网页该值不变,因此d["type" + e]的值可以确定为1;

最后是p的值,也是请求参数rs的值,它是一个函数的返回值,不需要管这个函数是干什么的,用chatgpt把这段代码转为python代码即可,转换之前还需找到e和t的值是什么,也从右边发现两者值不变,分别是1和4,但e在代码中用于判断,因此转为python值其实是True,如下得到p值得生成方法,实质就是生成16位得随机字符串:

def generate_random_string(e=True, t=4, r=16):chars = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"length = t if not e else random.randint(t, r)return ''.join(random.choice(chars) for _ in range(length))

步骤三:确定函数u的具体内容

将断点打到u函数的位置,跳到函数定义的位置

通过反复地打断点跟进,最终确定其执行的实际上是如下两个函数,其实质是执行了一次SHA-256 哈希算法。

知道他执行的是SHA-256 哈希算法后直接使用python对应的hashlib库中的方法即可。

步骤四:使用python实现请求参数的生成

直接放出代码

def generate_random_string(e=True, t=4, r=16):chars = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"length = t if not e else random.randint(t, r)return ''.join(random.choice(chars) for _ in range(length))def get_sha256(value):"""sha256加密:param value: 加密字符串:return: 加密结果转换为16进制字符串,并大写"""hsobj = hashlib.sha256()hsobj.update(value.encode("utf-8"))return hsobj.hexdigest()
ts=str(int(time.time() * 1000))#ts,时间戳
l=ts
rs=generate_random_string(True, 4, 16)
p=rs#rs
b = '$d6eb7ff91ee257475%'
h='外卖 食品安全'#keywords
c='10'#page_size
d=str(i)#d["type" + e]=page
signature=''.join(sorted([l, p, b, h, c, d]))
signature=get_sha256(signature)
params = {'ts': ts,'rs': rs,'signature': signature,'keywords': h,'page_size': c,'page': d,}

到这里请求参数就构造完成了。

投诉信息爬取

下面是投诉信息的爬取,把cookies和headers复制下来,使用get方法获得每条投诉对应的具体信息页面的url,然后从该url中爬取需要的信息,我这里只需要投诉时间、结束时间和投诉编号,完整代码如下:

import requests
import random
import hashlib
import time
import json
from bs4 import BeautifulSoupcookies = {#自己复制
}headers = {#自己复制
}#[l, p, b, h, c, d["type" + e]].sort().join("")
def generate_random_string(e=True, t=4, r=16):chars = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"length = t if not e else random.randint(t, r)return ''.join(random.choice(chars) for _ in range(length))def get_sha256(value):"""sha256加密:param value: 加密字符串:return: 加密结果转换为16进制字符串,并大写"""hsobj = hashlib.sha256()hsobj.update(value.encode("utf-8"))return hsobj.hexdigest()requests.packages.urllib3.disable_warnings()
sessions=requests.session()
data=[]
number=0
for i in range(1,101):#1524print(i)url_list=[]if len(data)%50==0 and len(data)!=0:time.sleep(60)while True:ts=str(int(time.time() * 1000))#ts,时间戳l=tsrs=generate_random_string(True, 4, 16)p=rs#rsb = '$d6eb7ff91ee257475%'h='外卖 食品安全'#keywordsc='10'#page_sized=str(i)#d["type" + e]=pagesignature=''.join(sorted([l, p, b, h, c, d]))signature=get_sha256(signature)params = {'ts': ts,'rs': rs,'signature': signature,'keywords': h,'page_size': c,'page': d,}try:response = sessions.get('https://tousu.sina.com.cn/api/index/s',cookies=cookies,headers=headers,params=params,verify=False,allow_redirects=False)response=json.loads(response.text)['result']['data']['lists']#print(response)for n in range(len(response)):if response[n]['main']['evaluate_u']==None:number+=1continueelse:url=response[n]['main']['url']url_list.append(url)number+=1breakexcept Exception as e:print(e,response.text,i)time.sleep(300)continuefor url in url_list:while True:try:response = sessions.get('https:'+url,cookies=cookies,headers=headers,verify=False,allow_redirects=False)soup = BeautifulSoup(response.text, 'html.parser')u_date_elements = soup.find_all(class_='u-date')u_list=soup.find('ul', class_='ts-q-list')c_num=u_list.find_all('li')[0].textendtime=u_date_elements[2].textstarttime=u_date_elements[6].textdata.append([starttime,endtime,c_num])breakexcept Exception as e:print(e,response.text,i)time.sleep(60)continue
data=pd.DataFrame(data,columns=['starttime','endtime','c_num'])

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/599647.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

算法每日一题:统计重复个数 | 字符串

大家好,我是星恒 感觉好难呀呀呀!今天是一道困难题目,思路挺简单,但是有些细节点不是很容易想通,建议大家多画图试一试,这样就会好理解许多 题目:leetcode 466定义 str [s, n] 表示 str 由 n 个…

OpenHarmony之消息机制实现

OpenHarmony之消息机制实现 背景 在之前的介绍(OpenHarmony之HDF驱动框架)中,了解到OpenHarmony的消息机制主要有以下两种: 用户态应用发送消息到驱动。用户态应用接收驱动主动上报事件。 下面我们分别来看看两种机制用户态的…

23 导航栏

效果演示 实现了一个响应式的导航栏&#xff0c;当鼠标悬停在导航栏上的某个选项上时&#xff0c;对应的横条会从左到右地移动&#xff0c;从而实现了导航栏的动态效果。 Code <div class"flex"><ul><li>1</li><li>2</li><l…

Apache、MySQL、PHP编译安装LAMP环境

1. 请简要介绍一下LAMP环境。 LAMP环境是一个在Linux操作系统上搭建的服务器环境组合&#xff0c;由Apache、MySQL、PHP三种软件构成。这种环境是开源的&#xff0c;跨平台的&#xff0c;并且由于各组件经常一起使用&#xff0c;因此具有高度的兼容性。 其中&#xff0c;Apac…

第三部分使用脚手架:vue学习(61-65)

文章目录 61 创建vue脚手架![在这里插入图片描述](https://img-blog.csdnimg.cn/direct/f71d4324be0542209e690ab9e886d199.png)62 分析脚手架结构63 render函数64 修改默认配置65 ref 属性 61 创建vue脚手架 写完vue文件&#xff0c;没有脚手架做翻译&#xff0c;浏览器不认识…

基于引力搜索算法优化的Elman神经网络数据预测 - 附代码

基于引力搜索算法优化的Elman神经网络数据预测 - 附代码 文章目录 基于引力搜索算法优化的Elman神经网络数据预测 - 附代码1.Elman 神经网络结构2.Elman 神经用络学习过程3.电力负荷预测概述3.1 模型建立 4.基于引力搜索优化的Elman网络5.测试结果6.参考文献7.Matlab代码 摘要&…

计算机网络学习笔记(一)

文章目录 1.1 请介绍七层网络体系结构。2 .请介绍五层网络体系结构。3 .了解网络编程协议吗&#xff1f;客户端发送给服务器的请求&#xff0c;怎么确定具体的协议&#xff1f;4. TCP、HTTP、FTP分别属于哪一层&#xff1f;5. 讲一下TCP/IP协议。6 .说一说你对ARP协议的理解。7…

继承和多态中的常见笔试面试题(一)

1. 下面哪种面向对象的方法可以让你变得富有( B ) A: 继承 B: 封装 C: 多态 D: 抽象 &#xff08;真趣味题&#xff09;a&#xff0c;期望你爸是李刚&#xff0c;但李刚未必有钱&#xff1b;乐观者选c&#xff0c;多态是在面向对象语言中&#xff0c;接口的多种不同的实现方式…

【SpringBoot】分组校验和自定义校验

分组检验 参数校验时&#xff0c;我们希望不同的方法参数校验规则不同&#xff0c;这时就需要分组校验。 public class Category {NotNull(groups Update.class)private Integer id;//主键IDNotEmptyprivate String categoryName;//分类名称// NotEmpty(groups {Add.class,…

基于闪电搜索算法优化的Elman神经网络数据预测 - 附代码

基于闪电搜索算法优化的Elman神经网络数据预测 - 附代码 文章目录 基于闪电搜索算法优化的Elman神经网络数据预测 - 附代码1.Elman 神经网络结构2.Elman 神经用络学习过程3.电力负荷预测概述3.1 模型建立 4.基于闪电搜索优化的Elman网络5.测试结果6.参考文献7.Matlab代码 摘要&…

机器学习实践

1.波士顿房价预测 波士顿房屋的数据于1978年开始统计&#xff0c;共506个数据点&#xff0c;涵盖了波士顿不同郊区房屋的14种特征信息。 在这里&#xff0c;选取房屋价格&#xff08;MEDV&#xff09;、每个房屋的房间数量&#xff08;RM&#xff09;两个变量进行回归&#xff…

解决报错Exception encountered during context initialization

推荐阅读 智能化校园&#xff1a;深入探讨云端管理系统设计与实现&#xff08;一&#xff09; 智能化校园&#xff1a;深入探讨云端管理系统设计与实现&#xff08;二&#xff09; 文章目录 推荐阅读报错解决 报错 今天在测试一个类时&#xff0c;突然间报了以下错误。 juni…

LeetCode_2_中等_两数相加

文章目录 1. 题目2. 思路及代码实现&#xff08;Python&#xff09;2.1 模拟迭代2.2 递归 1. 题目 给你两个 非空 的链表&#xff0c;表示两个非负的整数。它们每位数字都是按照 逆序 的方式存储的&#xff0c;并且每个节点只能存储 一位 数字。 请你将两个数相加&#xff0c…

自定义异常相关问题及答案(2024)

1、为什么要使用自定义异常&#xff1f; 使用自定义异常&#xff08;Custom Exceptions&#xff09;在程序设计中是一个良好的实践&#xff0c;它有几个重要的好处&#xff1a; 提高代码可读性&#xff1a; 自定义异常的名称如果能清晰表达出异常的情况&#xff0c;那么阅读代…

4.将新对象的地址版给pveg变量:

string "pveg - now. Btrangt"Cabbage Heads Hone*): 1.为对象分配内存: 2. 请用类构造函数,它 为“Cabbnge Heads Hose 分配空间 - # "Cabbage Heads Hoe" 复制到分配的内存单元中 - #f "Cabbage Heads Howe" 的地址赋给str 将值19粒给1en 更…

vmware安装centos 7.6 操作系统

vmware安装centos 7.6 操作系统 1、下载centos 7.6 操作系统镜像文件2、安装centos 7.6操作系统3、配置centos 7.6 操作系统3.1、配置静态IP地址 和 dns3.2、查看磁盘分区3.3、查看系统版本 1、下载centos 7.6 操作系统镜像文件 这里选择 2018年10月发布的 7.6 版本 官方下载链…

vscode安装Prettier插件,对vue3项目进行格式化

之前vscode因为安装了Vue Language Features (Volar)插件&#xff0c;导致Prettier格式化失效&#xff0c;今天有空&#xff0c;又重新设置了一下 1. 插件要先安装上 2. 打开settings.json {"editor.defaultFormatter": "esbenp.prettier-vscode","…

【物联网】手把手完整实现STM32+ESP8266+MQTT+阿里云+APP应用——第3节-云产品流转配置

&#x1f31f;博主领域&#xff1a;嵌入式领域&人工智能&软件开发 本节目标&#xff1a;本节目标是进行云产品流转配置为后面实际的手机APP的接入做铺垫。云产品流转配置的目的是为了后面能够让后面实际做出来的手机APP可以控制STM32/MCU&#xff0c;STM32/MCU可以将数…

前缀和算法模板

一维前缀和 算法用途&#xff1a;快速求出数组中某一连续区间的和 一维前缀和算法模板 1、预处理出一个 dp 数组 要求原数组存储在 n 1 的空间大小中&#xff0c;其中后 n 个空间存数据。 dp数组&#xff0c;数组开 n 1个空间&#xff0c;dp[i] 表示 [ 1, i ] 区间内所有…

抖店如何高效率起店?从0到1的起店思路和心得,分享如下!

我是王路飞。 万事开头难&#xff0c;我为什么一直强调让新手商家先入门&#xff0c;把流程跑通呢&#xff1f; 就好像我们上学时候考试&#xff0c;都知道100分很难&#xff0c;那我们就先从60分开始好了&#xff0c;有了考60分的基础&#xff0c;你就知道你跟100分的差距在…