此分享只用于学习用途,不作商业用途,若有冒犯,请联系处理
反爬前置信息
站点:aHR0cHM6Ly96d2Z3LmNxLmdvdi5jbi9pY2l0eS9pY2l0eS9lbmdpbmVlcmluZy9uYXZpZ2F0aW9u
接口:/icity/api-v2/cq.app.icity.engineering.EngineeringCmd/getBusinessList
加密点:
逆向研究
老样子,看调用堆栈,直接进去红框的代码处
从这些代码我们可以拿到请求体原文,肯定是用它进行加密的,然后锁定cmd.setData(data);
,大胆猜测加密就是在这里处理的
打上断点然后跟进去:cmd.setData(data);->$.extend(this.paramsObj, obj);
发现其实只是对请求体原文做一个处理,都没进行加密,不用说那就是cmd.executeAsync("getBusinessList")
这个位置了
在cmd.executeAsync("getBusinessList")
打上断点跟进去,再进入红框代码
这里就能看到所有加解密操作了
addUrlAuth
方法没啥难点,可以直接算法破解,其中__signature
其实是在首页返回的,在整个破解过程中,我们需要从首页拿到XSRF-TOKEN
cookie和__signature
接下来看下加解密
使用文本解码就可以看到实际的文本代码了
其实就是原生的AES加密,这个也可以直接使用算法破解,注意加解密的key值是XSRF-TOKEN
cookie取十六位
算法破解
依赖包
import base64
import json
import random
import time
from binascii import hexlify
from binascii import unhexlify
from hashlib import md5import requests
from Crypto.Cipher import AES
from Crypto.Util.Padding import pad
from Crypto.Util.Padding import unpad
addUrlAuth
def get_auth_params():sig = '__signature'chars = "0123456789abcdef"key = ''key_index = -1for i in range(6):c = sig[key_index + 1]key += ckey_index = chars.index(c)if key_index < 0 or key_index >= len(sig):key_index = itimestamp = str(int(random.random() * (9999 - 1000 + 1) + 1000)) + "_" + key + "_" + str(int(time.time() * 1000))tkey = md5((timestamp + base64.b64decode('eWVVUkx5VFpvdW00SzI3ZA==').decode()).encode()).hexdigest()return {'s': sig,'t': timestamp,'o': tkey,}
encrypt_a
def encrypt_a(plaintext, xsrf_token_prefix):key = xsrf_token_prefix.encode('utf-8')[:16]cipher = AES.new(key, AES.MODE_ECB)padded_data = pad(plaintext.encode('utf-8'), AES.block_size)encrypted_data = cipher.encrypt(padded_data)hex_encrypted_data = hexlify(encrypted_data).decode('utf-8')return hex_encrypted_data
decrypt_a
def decrypt_a(hex_encrypted_data, xsrf_token_prefix):encrypted_data = unhexlify(hex_encrypted_data)key = xsrf_token_prefix.encode('utf-8')cipher = AES.new(key, AES.MODE_ECB)decrypted_padded = cipher.decrypt(encrypted_data)return unpad(decrypted_padded, AES.block_size).decode('utf-8')