工具接口抓包参数解密过程解密方法整理重构脚本实现总结
工具
Fiddler抓包工具手机Chrome浏览器Postman
接口抓包
打开fiddler软件,在Tools>Options按以下设置:设置连接信息,注意这里的端口是后面手机连接要用的:在cmd命令行查看PC的IP地址:手机连接到和PC相同的网络,并设置代理:然后接下来从Fiddler里就可以抓取到手机端的请求了,预约入口这里使用【深圳疾控】公众号,请求过程如下:下面就是查找的过程,找出对我们有用的请求并且分析,从下网上找:
社康信息接口这个接口可以查询社康列表,返回信息包括社康ID,社康名称,可打疫苗厂商,社康地址,当前状态等信息。获取深圳区列表这个接口返回的区代码后面会有用,用来查询这个区的号源:获取疫苗厂商列表这个接口是获取疫苗厂商列表信息,其中重要的数据是corpCode–厂商代码。获取token接口这个接口也可以不用分析,因为token很长时间不会过期,可以直接抓包拿到就可以,一般在请求头就可以找到。获取用户信息接口这个接口返回真实用户信息,也包含token。查看当前社康这天每个时间段的号源情况restSurplus大于0表示有号,下面箭头指的说明9:30-10:00有1个号:预约接口这里参数就包含了社康信息还有token一些参数,下节分析。查看预约结果信息预约成功后,查看详细预约信息。
参数解密过程
通过上一步分析,可以把有用的接口都捞出来了,接下来就是分析参数,然后用Postman来模拟请求,只有请求成功了才算真的分析清楚了。那么参数分析在那里分析方便呢?当然是浏览器啦,这里教大家一个小技巧,可以在Chrome上调试微信页面。
有小伙伴可能要问了,为什么是调试微信页面呢,其实公众号里面嵌入的是H5页面,因为我发现了有一个请求返回的是网页:用这个请求地址在Chrome浏览器访问页面试一下,结果是这样的:哦~原来预约界面就是H5页面,如此就简单多了,谁说预约只能在手机上的,这不PC也可以吗?
那么调试起来是不是很方便呢,Fiddler抓包现在就可以不用了,开始用Chrome整吧,这里提一下不要觉得加密的参数太多就怕了,一般网站加密方法是一样的,只要破了一个其他的就都破了,就以获取社康列表信息这个接口来看:
首先最简单的是能看到请求地址:https://xgsz.szcdnet/crmobile/outpatient/nearby请求方式:POST然后可以看到请求头里有一些加密的参数,还有Form-Data里也有一个params是加密的:经过使用Postman模拟请求,筛选出Header中的token、appid、otn、ybm是必须的,token是后台传过来的(后面分析),appid是固定的,所以重要的是otn、ybm这俩参数,因为加密了,下面就来看看加密方法,先搜索ybm:搜到这个js中这里正是设置header的地方,刚好ybm、otn是用的同一种加密方式,先看看加密方法的参数,这里c,p是上面生成的,后面是固定的字符串,在上面打个断点再刷新一下,可以查出上面的方法是啥:
这里的c=u()是返回的当前时间戳的相关字符串:p是d(e,得来的,e是token,c就是上面的时间戳相关参数,d方法是字符串拼接:接下来看看加密函数Object(_t.是啥,控制台先看下,是个函数:调试进去看看:额,这就不用多说了吧,一个是加密函数,一个是解密函数,参数都是传进来的,上面分析好了,接下来分析i方法是返回什么:这个就是加密函数了,但是最后返回一个newybzSM4(是什么鬼,感情这个方法只是处理参数而已,额,不急,我们进去看看:好家伙!直接进去了bundlmijs里面都是算法啊,调试里面的太复杂了,我放弃了,但是我发现一件事:其实这里会把这个函数输出到window对象上,这就好办了,不跟你玩了,直接把这个js文件下载下来,直接用,哈哈哈~
解密方法整理重构
经过了上面的分析,我自己写出了加密和解密的方法,如下:
因涉及个人隐私,中间的参数我没有贴真实的返回结果,请自行测试。
脚本实现
参数破解完后,最后一步就是实现自动化预约了,预约流程:
具体实现下面给个例子,因为现在号源也比较多,所以没有写脚本,需要的自己修改一下就行了:
# -*- coding: utf-8 -*-
import requests, time, copy
from urllib.parse import parse_qs, urlencode, urlparse
token = ''
appid = ''
otn = ''
ybm = ''
reservationtoken = ''
baseHeaders = {
# 'Cookie': findCookie,
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36 QBCore/4.0.1326.400 QQBrowser/9.0.2524.400 Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2875.116 Safari/537.36 NetType/WIFI MicroMessenger/7.0.20.1781(0x6700143B) WindowsWechat(0x63010200)'
}
# 获取疫苗余量
def getRest():
rest_url = 'https://xgsz.szcdc.net/crmobile/reservationStock/timeNumber'
params_1 = '4517CL5iSqYrVthaOYxxxxxxxxxx' # 先加密好
rest_headers = copy.deepcopy(baseHeaders)
rest_headers['token'] = token
rest_headers['appid'] = appid
rest_headers['otn'] = otn
rest_headers['ybm'] = ybm
rest_data = {
'params': params_1
}
rest_res = requests.post(rest_url, json=rest_data, headers=rest_headers).json()
return rest_res
# 预约
def save():
post_url = 'https://xgsz.szcdc.net/crmobile/reservation/saveAppointment'
data = {
'reusId': '6068111xxxxxxxxxxx', # 用户的reusId 固定
'depaId': '1698A7F4-CA7B-9FDA-FC3C-48DEE401491B', # 社康ID (第1个请求获取)
'corpCode': '80', # 厂商代码
'date': '2021-06-13', # 日期
'ouatId': '831', # 时间段ID (第2个请求获取)
'vaccCodes': '5601' # 新冠疫苗code
}
post_headers = copy.deepcopy(baseHeaders)
post_headers['token'] = token
post_headers['appid'] = appid
post_headers['reservationtoken'] = reservationtoken
post_headers['Content-Type'] = 'application/json'
rest_res = requests.post(post_url, json=data, headers=post_headers).json()
return rest_res
总结
这个抓取接口花了两次,第一次抓完后第二天官方就修改了参数,把原来的明文改为加密的了,后来又抓了一遍,通过参数的解密过程,大家会学会如何去分析、调试、并重构它,结果无所谓,主要是分析过程,希望能帮到大家。
文章为作者独立观点,不代表股票交易接口观点