题目链接:https://match.yuanrenxue.cn/match/18
翻页请求,如下图:
发现两个请求,第一个getTime获取时间戳,13位的;第二个请求18data数据接口,请求参数page页码、t时间戳10位、v加密参数。

Initiator点击req进入js断点:


断点调试,进入getdata:


单步走一步,再进入XMLHttpRequest的open:



往后拖动看一下这行代码:

代码粘贴到工具中格式化一下518行:

开始进入:

执行下一步看u__值:

mouses数组:
[
"784m23",
"784m22",
"784d22",
"784m22",
"784u22"
]
第一次getTime请求返回值:

t值:


第二次u__数组下标1第一个对象有两个键值,分别是page|mouses和secretkey,标线是一个串重复了一下:

这里点快了,已经看到secret_key,往回点一步进去看看myenc:

点快了,重新调试下:

使用脚本hook下加密算法:


可以确定是AES加密,加密文本是page|鼠标坐标,key和iv是一样的,每个翻页,鼠标坐标是不一样的,每个都点一下得到每页的坐标。
完整代码如下:
import json import random import re import time import requests from Crypto.Cipher import AES from Crypto.Util.Padding import pad import base64 def get_time_18(): """获取时间戳""" url = "https://match.yuanrenxue.cn/api/getTime" headers = { "accept": "*/*", # "accept-encoding": "gzip, deflate, br, zstd", "accept-language": "zh-CN,zh;q=0.9", "cache-control": "no-cache", "cookie": "Hm_lvt_f80b2b389f44bbfb3bfe1704817d44e0=1776316664; HMACCOUNT=3ADBE34EA00D9961; m=6671485b46b93b3d5d3b2c71b2fae812; RM4hZBv0dDon443M=zXwPga1bWho3zuQdtlvfd+gbmJkHwS5sqa0qRH5Hu4kaqIaJZDgVmD591BxFsUgK3D+sth+tCXnacBrtNiMnuai9dzalg/PXyHcx55q6lD/909Os2hkVxaFXm1z4ZSdZ1ATPGc8L+Prng0uhjipUH+mfdAFzRuTrxpt4AYuTUtK4hGLFqL1BN062PVOLE4VIU4XG7gQJudP9wEU3h6NZ8EyLS2jOuLg1Hqn5NnGhyCM=; sessionid=qarkeoj53qh9hd1t0fj0vwgdvxkkki9b; Hm_lpvt_f80b2b389f44bbfb3bfe1704817d44e0=1776740916", "pragma": "no-cache", "priority": "u=0, i", "referer": "https://match.yuanrenxue.cn/match/18", "sec-ch-ua": "\"Chromium\";v=\"146\", \"Not-A.Brand\";v=\"24\", \"Google Chrome\";v=\"146\"", "sec-ch-ua-mobile": "?0", "sec-ch-ua-platform": "\"Windows\"", "sec-fetch-dest": "empty", "sec-fetch-mode": "cors", "sec-fetch-site": "same-origin", "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/146.0.0.0 Safari/537.36" } try: r = requests.get(url=url, verify=False, headers=headers) if r.status_code == 200: data = r.text return data else: print(f'error:{r.status_code}-----{r.text}') except Exception as e: raise ValueError(e) def encrypt_aes_cbc(plaintext, key, iv): # 将密钥和 IV 转换为字节 key_bytes = key.encode('utf-8') iv_bytes = iv.encode('utf-8') # 创建 AES 加密器(CBC 模式) cipher = AES.new(key_bytes, AES.MODE_CBC, iv_bytes) # 对明文进行 PKCS7 填充并加密 padded_plaintext = pad(plaintext.encode('utf-8'), AES.block_size) ciphertext_bytes = cipher.encrypt(padded_plaintext) # 将密文转换为 Base64 编码 ciphertext_base64 = base64.b64encode(ciphertext_bytes).decode('utf-8') return ciphertext_base64 def get_v(page, t): # 根据 page 值生成明文 if page == 1: text = f"{page}|684m138,684m137,684m136,684d136,684u136" elif page == 2: text = f"{page}|721m99,721m98,721d98,721m98,721u98" elif page == 3: text = f"{page}|778m79,779m79,780m79,780d79,780u79" elif page == 4: text = f"{page}|790m145,790u145,834d147,834m147,834u147" elif page == 5: text = f"{page}|883m149,883m148,883m147,883d147,883u147" else: text = f"{page}|830m145,830m144,830m143,830d143,830u143" # 将时间戳转换为十六进制并重复两次作为密钥和 IV hex_t = hex(int(t))[2:] # 去掉 0x 前缀 key = hex_t * 2 iv = key # 执行加密 ciphertext = encrypt_aes_cbc(text, key, iv) return ciphertext def get_question_18_result(): """jsvmp""" url = "https://match.yuanrenxue.cn/api/v/question/18data" headers = { "accept": "*/*", # "accept-encoding": "gzip, deflate, br, zstd", "accept-language": "zh-CN,zh;q=0.9", "cache-control": "no-cache", "cookie": "Hm_lvt_f80b2b389f44bbfb3bfe1704817d44e0=1776316664; HMACCOUNT=3ADBE34EA00D9961; m=6671485b46b93b3d5d3b2c71b2fae812; RM4hZBv0dDon443M=zXwPga1bWho3zuQdtlvfd+gbmJkHwS5sqa0qRH5Hu4kaqIaJZDgVmD591BxFsUgK3D+sth+tCXnacBrtNiMnuai9dzalg/PXyHcx55q6lD/909Os2hkVxaFXm1z4ZSdZ1ATPGc8L+Prng0uhjipUH+mfdAFzRuTrxpt4AYuTUtK4hGLFqL1BN062PVOLE4VIU4XG7gQJudP9wEU3h6NZ8EyLS2jOuLg1Hqn5NnGhyCM=; sessionid=qarkeoj53qh9hd1t0fj0vwgdvxkkki9b; Hm_lpvt_f80b2b389f44bbfb3bfe1704817d44e0=1776740916", "pragma": "no-cache", "priority": "u=1, i", "referer": "https://match.yuanrenxue.cn/match/18", "sec-ch-ua": "\"Chromium\";v=\"146\", \"Not-A.Brand\";v=\"24\", \"Google Chrome\";v=\"146\"", "sec-ch-ua-mobile": "?0", "sec-ch-ua-platform": "\"Windows\"", "sec-fetch-dest": "empty", "sec-fetch-mode": "cors", "sec-fetch-site": "same-origin", "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/146.0.0.0 Safari/537.36" } sum_data = 0 s = requests.Session() s.headers.clear() s.headers.update(headers) for page in range(1, 6): print(f'page:{page}') t = get_time_18() t = int(t) // 1000 print(f't:{t}') v = get_v(page, t) print(f'v:{v}') if page == 5: headers['user-agent'] = 'yuanrenxue' s.headers.update(headers) params = { "page": page, # "pageSize": "10", "t": t, "v": v, } if page == 1: params = { "page": page, # "pageSize": "10", # "t": t, # "v": v, } try: r = s.get(url=url, params=params, verify=False) if r.status_code == 200: data = r.json()['data'] print(data) sum_data += sum(data) print(f"翻第{str(page)}页,累计求和:{sum_data}") time.sleep(5) else: print(f'error:{r.status_code}-----{r.text}') except Exception as e: raise ValueError(e) if __name__ == '__main__': get_question_18_result()
实践出真知~
浙公网安备 33010602011771号