声明
本文章内容仅供学习交流,抓包内容、敏感网址、数据接口均已做脱敏处理,严禁用于商业用途和非法用途,否则由此产生的一切后果均与作者无关,若有侵权,请联系我立即删除!
工具&环境
pycharm:开放工具 2019.2
chrome:浏览器
python:3.7.4
node:v12.14.1
逆向目标
#index 主页-获取session:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbG9naW4vaW5kZXg=
#login 登陆接口 :aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbmF0dXJhbE1hbi9sb2dpbk5v
#csrfSave 辅助接口-或其MD5码 :aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbmF0dXJhbE1hbi9jc3JmU2F2ZQ==
#uploadIdentifier 辅助接口-获取uuid :aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbmF0dXJhbE1hbi91cGxvYWRJZGVudGlmaWVy
# verCode 辅助接口-获取校验码(滑块):aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbG9naW4vdmVyQ29kZQ==
逆向参数:
Form data : loginNo、loginPwd、code、requestUUID
request headers: token
操作完整流程
1:chrome访问主页
#主页:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbG9naW4vaW5kZXg=
chrome打开无痕窗口,按F12,输入主页地址回车。观察网络请求
2:输入密码后,滑动滑块:
触发请求verCode
第6步:过滑块触发verCode接口
SESSION=ZDFjMDY4ZmMtZGYyNy00MDRmLWI5ZjEtNjE4NDcyZTRhYTMx
3:输入密码,并登陆
第7步:loginNo登陆 --header需要token
SESSION=ZDFjMDY4ZmMtZGYyNy00MDRmLWI5ZjEtNjE4NDcyZTRhYTMx
payload --form data
backUrl:
loginNo:
IIAesumzZ+GIKAYY5YJF32PBLMlLl+j2kUW5R7q/2WJGFUB8jziuwDFTeSpIdfIsrr/wbP9i2C2wNY9v386Ykkf2mNG9DGWBn9vA/TYl4lXrklgI+A7rvHzk9rh3bJ5ZKcBLC4RCE7eHfWxDUGdFgwdOCEcqFgbcErr02+RsIQaBdli9cV85JYTSpoR44nBTqOro5hX+bkQCpit20BbXeHwQeo4MAMzlpWarYPOGNuKusttWqNqzdhkM/Gl4AcKKzykGNsTR1P6wwL4Ba+ajmLUDsLrprtw9BA4k/22EEVQKHKsvA6+yRuCAbm8INjfp7yh5P8Lres4qv34Kj/bsFw==
loginPwd:
SKZuAq/nxYRAekdeUApamQCNdqKaeHh6KSje7zSGRjScoe2o8giKKqP7wNMcAEIF2y8xGxp7Jfq/jkK5xoOBkjyP+ov0r80guTAEGbe1JCughEBeHr/SJql2ZA8OZtNCyza66kv6SvyPkOu2HcfpAkpwzNMl8QQzoBo+68tnoPE4YriJaYaGt0RJe2Fdp+DJL3pK3K3Tg3q6O2Cpp6kM3tMfXGS3MJahoNa3JzGF2egVM8pytZDBjk7HFGoiXFbh72FZIhORW19Zu+9TWTHkm1d6ukvIY9rlHtHU6UFhjYjNOKn3i35XkIf8y0SSQlAdFcKl3yUEasAYDsXE9ZD9eg==
code:
11604ae4-21dc-4109-943f-adc25209c9e9
requestUUID:
19b9951f-786c-4d68-ab1c-7ba65b457589
guoBanAuthCode:
分析步骤
先描述分析大概步骤, 并再后面说明如何分析
1:进入页面--获取session,
2:自动调用uploadIdentifier,返回data.data是 requestUUID
3:并过滑块拦截到的https请求verCode,返回data.data是验证码
4:登陆触发loginNO,返回登陆是否成功的信息
搜索"requestUUID" 在登陆方法personLoginSubmit中可以看到如下代码
$.ajax({
url: uri + "/naturalMan/loginNo",
xhrFields: {withCredentials: true},
dataType: "json",
type: "post",
crossDomain: true == !(document.all),
data: {
"backUrl": localStorage.getItem("backUrl"),// 可为null
"loginNo": encrypt(personName), //手机号
"loginPwd": encrypt(apsswordTestCorrect),//密码
"code": loginCode, //verCode接口返回data.data
"requestUUID": UUID,//uploadIdentifier接口返回data.data
"guoBanAuthCode": guoBanAuthCode //可为null
},
success: function (data) {
var result = data.code;
var msg = data.msg;
if (result != successCode) {
$('#verCode').click();
$("#loginError").html(errorImgLabel + msg);
$("#loginbtn").attr("disabled", false);
$("#loginbtn").css("background", "#567fe6");
} else {
。。。
}
}
});
抠出encrypt.js代码
点击encrypt 函数在encrypt.js进入查看
//add by wangp at 2018-01-23 密码加密方法 start
function encrypt(pwd){
var key = "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsgDq4OqxuEisnk2F0EJFmw4xKa5IrcqEYHvqxPs2CHEg2kolhfWA2SjNuGAHxyDDE5MLtOvzuXjBx/5YJtc9zj2xR/0moesS+Vi/xtG1tkVaTCba+TV+Y5C61iyr3FGqr+KOD4/XECu0Xky1W9ZmmaFADmZi7+6gO9wjgVpU9aLcBcw/loHOeJrCqjp7pA98hRJRY+MML8MK15mnC4ebooOva+mJlstW6t/1lghR8WNV8cocxgcHHuXBxgns2MlACQbSdJ8c6Z3RQeRZBzyjfey6JCCfbEKouVrWIUuPphBL3OANfgp0B+QG31bapvePTfXU48TYK0M5kE+8LgbbWQIDAQAB";
var encrypt = new JSEncrypt();
encrypt.setPublicKey(key);
var encrypted = encrypt.encrypt(pwd);
return encrypted;
}
//add by wangp at 2018-01-23 密码加密方法 end
里面使用到JSEncrypt对象进行RSA加密,代码在jsencrypt.min.js中,点击进去,并格式化代码,copy出来保存为jsencrypt.min.js(也可以直接下载该文件)
格式前的代码,我们看不是很清楚
按“{}”格式化后,后其实JSEncrypt 就是 var ze = function(t)
新打开一个chrome无痕窗口,在chrome中新建snippet,并把jsencrypt.min.js+encrypt.js; (主页如果要在python+nodejs环境中运行,需要做些更改,后面会进一步描述。主页原因是浏览器环境会自动补全部分功能)
右键运行该代码片段
loginCode是如何生成的
var loginCode = $("#verCode").val();
搜索 loginCode
搜索 $("#verCode")
UUID是如何生成的
UUID定义再login.js中,是uploadIdentifier接口返回的data.data
var UUID = "";
搜索UUID赋值
最终代码
hnzwfw_encrypt.js
//add by czg at 2022-05-11 start for run in pythin
global.navigator={
userAgent: 'node.js',
};
var window = global;
var JSEncrypt ;
//add by czg at 2022-05-11 end for run in pythin
.....
jsencrypt.min.js部分代码
.....
//add by czg at 2022-05-11 start
function encrypt(pwd){
var key = "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsgDq4OqxuEisnk2F0EJFmw4xKa5IrcqEYHvqxPs2CHEg2kolhfWA2SjNuGAHxyDDE5MLtOvzuXjBx/5YJtc9zj2xR/0moesS+Vi/xtG1tkVaTCba+TV+Y5C61iyr3FGqr+KOD4/XECu0Xky1W9ZmmaFADmZi7+6gO9wjgVpU9aLcBcw/loHOeJrCqjp7pA98hRJRY+MML8MK15mnC4ebooOva+mJlstW6t/1lghR8WNV8cocxgcHHuXBxgns2MlACQbSdJ8c6Z3RQeRZBzyjfey6JCCfbEKouVrWIUuPphBL3OANfgp0B+QG31bapvePTfXU48TYK0M5kE+8LgbbWQIDAQAB";
var encrypt = new JSEncrypt();
encrypt.setPublicKey(key);
var encrypted = encrypt.encrypt(pwd);
return encrypted;
}
//add by czg at 2022-05-11 end
定义全局变量
需要copy进来的jsencrypt.min.js,部分添加对全局变量的赋值 JSEncrypt = ze
hnzwfw_login.py
import execjs #需要下载库 pip install pyExecJs
import requests #pip install requests
# 特别注意如果pc开始代理会报错误 ProxyError(e, request=request)
# UnicodeEncodeError: ‘gbk‘ codec can‘ https://www.10qianwan.com/articledetail/733782.html
# 原因 :场景为在 Windows 电脑下使用 Python execjs 运行指定的 JS 文件,但 JS 文件中包含中文 python 运行 execjs 出现错误
# 修改subprocess.py
# execjs._exceptions.ProgramError: ReferenceError: navigator is not defined https://blog.csdn.net/qq_36853469/article/details/105075131
# 这是因为execjs除了nodejs,还需要浏览器环境,浏览器上还需要document以及window对象,所以我们要还要安装环境
# execjs._exceptions.ProgramError: ReferenceError: window is not defined
cookies = {}
UA = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.110 Safari/537.36"
with open("hnzwfw_encrypt.js", encoding="utf-8") as f:
js = execjs.compile(f.read())
def csrf_save():
url = "加密后:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbmF0dXJhbE1hbi9jc3JmU2F2ZQ=="
headers = {"User-Agent": UA}
response = requests.post(url=url, headers=headers, cookies=cookies).json()
data = response["data"]
return data
# 获取session
def get_session():
url = "加密后:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbG9naW4vaW5kZXg="
headers = {"User-Agent": UA}
response = requests.get(url=url, headers=headers)
cookies.update(response.cookies.get_dict())
def get_uuid():
url = "加密后:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbmF0dXJhbE1hbi91cGxvYWRJZGVudGlmaWVy"
headers = {
"User-Agent": UA,
"token": js.call("encrypt", csrf_save()),
}
response = requests.post(url=url, headers=headers, cookies=cookies).json()
uuid = response["data"]
return uuid
def ver_code():
url = "加密后:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbG9naW4vdmVyQ29kZQ=="
headers = {
"User-Agent": UA,
"token": js.call("encrypt", csrf_save())
}
response = requests.post(url=url, headers=headers, cookies=cookies).json()
data = response["data"]
return data
def login(phone, pwd, code, uuid):
url = "加密后:aHR0cHM6Ly9sb2dpbi5obnp3ZncuZ292LmNuL3RhY3MtdWMvbmF0dXJhbE1hbi9sb2dpbk5v"
headers = {
"User-Agent": UA,
"token": js.call("encrypt", csrf_save())
}
data = {
"backUrl": "",
"loginNo": js.call("encrypt", phone),
"loginPwd": js.call("encrypt", pwd),
"code": code,
"requestUUID": uuid,
"guoBanAuthCode": ""
}
response = requests.post(url=url, headers=headers, cookies=cookies, data=data)
print(response.json())
def main():
phone = input("请输入账号:")
pwd = input("请输入密码:")
get_session()
uuid = get_uuid() #setHeader内部调用一次csrf_save
print("uploadIdentifier 接口获得uuid =" ,uuid)
code = ver_code() #setHeader内部调用一次csrf_save
print("ver_code 接口获得code =" ,code)
login(phone, pwd, code, uuid)
if __name__ == '__main__':
main()
PyCharm中运行测试
附-在pyCharm下执行碰到的问题、及解决办法
1:错误 ProxyError(e, request=request)
这是pc使用代理造成的,关闭代理即可。
2:execjs._exceptions.ProgramError: ReferenceError: navigator is not defined
及
execjs._exceptions.ProgramError: ReferenceError: window is not defined
//add by czg at 2022-05-11 start for run in pythin
global.navigator={
userAgent: 'node.js',
};
var window = global;
var JSEncrypt ;
//add by czg at 2022-05-11 end for run in pythin
3:UnicodeEncodeError: ‘gbk‘ codec can
Python 安装目录下 lib 文件夹里面的一个文件,名字叫做 subprocess.py,修改 encoding=None 为 encoding = "utf-8" 。
知识点
自执行函数
$.ajax()方法详解