赞
踩
在交流群中看见有同学想利用python实现有道翻译的功能,特写一篇自己的研究心得分享给大家。(由于兴趣爱好,本文不采用抠 js 的形式进行解析,转换成纯 python 的形式进行解析!)
网站地址: 有道翻译
进入目标网站,打开控制台并随意输入一个单词对网页的翻译流程进行分析。
通过多次使用翻译功能发现,以 translate 开头的链接即是我们的目标链接。不难看出,发现只有四个参数是一直在变幻的,分别是 salt、sign、ts、bv,其中不难看出 salt 与 ts 是时间戳,关键点在于 bv 以及 sign。通过发现这2个参数并不是通过服务器返回,那就肯定是js生成的。
可以发现,此链接相关的 js 只有一个,那太好办了。bv,sign 参数肯定是在这个 js 里面生成的。点击进去进行进一步的分析。
通过对关键字sign的搜索发现有多个结果,在每个结果前下一个断点重新发起请求发现 sign, bv的生成位置!
通过断点可以看到,bv 参数 是某个值进行了一个名为 md5 (此处不排除这个md5方法为自定义方法并非原则上的md5)的方法转换而来, ts 是当前的时间戳, salt 则是当前的时间戳加上一个随机数, 而 sign 则是一个组合值进行名为 md5 的方法的处理。
此时只需要知道参数 navigator.appVersion 的生成方式 以及所谓的 md5 内部的处理方法。
在 navigator.appVersion 处设下断点,拿到其值发现是浏览器特征! 这个值是固定不变的。抱着侥幸的心理,猜测该程序员使用传统的 MD5 方式进行加密处理而非重写,我们拿这个值进行 MD5 加密处理。
非常幸运,此处的MD5方法正是MD5加密算。知道了加密逻辑,所有参数的值都可以计算出来了! ( 如果不是MD5 加密算法,则需要对方法进行跟进解析。想节约时间的同学可以直接用 execjs 的形式将关键代码抠出来执行即可,本文不使用抠 js 的形式,使用纯 python 写法)
- #!/usr/bin/python3
- # -*- coding:utf-8 -*-
- """
- @file: youdao_fanyi.py
- @time: 2020/6/1 10:00
- @desc: python 模拟有道翻译
- """
- import requests
- import time
- import random
- from hashlib import md5
-
-
- class YouDaoFanYi(object):
- def __init__(self):
- self.url = 'http://fanyi.youdao.com/translate_o?smartresult=dict&smartresult=rule'
- self.headers = {
- 'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) '
- 'Chrome/81.0.4044.138 Safari/537.36',
- }
-
- @staticmethod
- def create_data(e):
- n = "5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/81.0.4044.138 Safari/537.36"
- t = md5(n.encode()).hexdigest()
- r = int(time.time() * 1000)
- i = int(str(r) + str(random.randint(0, 10)))
- sign = md5(("fanyideskweb" + e + str(i) + "Nw(nmmbP%A-r6U3EUn]Aj").encode()).hexdigest()
- return {'ts': r, 'bv': t, 'salt': i, 'sign': sign}
-
- def fanyi_word(self, word):
- sys_data = self.create_data(word)
- data = {
- 'i': word,
- 'from': 'AUTO',
- 'to': 'AUTO',
- 'smartresult': 'dict',
- 'client': 'fanyideskweb',
- 'doctype': 'json',
- 'version': 2.1,
- 'keyfrom': 'fanyi.web',
- 'action': 'FY_BY_REALTlME'
- }
- result = requests.post(url=self.url, headers=self.headers, data={**data, **sys_data}).json()
- print(result)
- return result
-
- def main(self, word):
- self.fanyi_word(word)
-
-
- if __name__ == '__main__':
- fanyi = YouDaoFanYi()
- fanyi.main('爬虫')
执行代码发现结果并非自己想要的结果
原因可能出现在请求头中,随之分析一波请求头! (这里用到POSTMAN 工具分析比较方便,由于不好截图,部分使用文字说明)
打开POSTMAN
第五步: 点击Import按钮
通过对Header的分析发现必须携带的参数如下,Cookie中的值为固定值:
- 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
- 'Referer': 'http://fanyi.youdao.com/'
- 'Cookie': 'OUTFOX_SEARCH_USER_ID="-1571440969@10.108.160.19"'
最后附上完整代码:
- #!/usr/bin/python3
- # -*- coding:utf-8 -*-
- """
- @file: youdao_fanyi.py
- @time: 2020/5/19 10:00
- @desc: python 模拟有道翻译
- """
- import requests
- import time
- import random
- from hashlib import md5
-
-
- class YouDaoFanYi(object):
- def __init__(self):
- self.url = 'http://fanyi.youdao.com/translate_o?smartresult=dict&smartresult=rule'
- self.headers = {
- 'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) '
- 'Chrome/81.0.4044.138 Safari/537.36',
- 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
- 'Referer': 'http://fanyi.youdao.com/',
- 'Cookie': 'OUTFOX_SEARCH_USER_ID="-1571440969@10.108.160.19"'
- }
-
- @staticmethod
- def create_data(e):
- n = "5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/81.0.4044.138 Safari/537.36"
- t = md5(n.encode()).hexdigest()
- r = int(time.time() * 1000)
- i = int(str(r) + str(random.randint(0, 10)))
- sign = md5(("fanyideskweb" + e + str(i) + "Nw(nmmbP%A-r6U3EUn]Aj").encode()).hexdigest()
- return {'ts': r, 'bv': t, 'salt': i, 'sign': sign}
-
- def fanyi_word(self, word):
- sys_data = self.create_data(word)
- data = {
- 'i': word,
- 'from': 'AUTO',
- 'to': 'AUTO',
- 'smartresult': 'dict',
- 'client': 'fanyideskweb',
- 'doctype': 'json',
- 'version': 2.1,
- 'keyfrom': 'fanyi.web',
- 'action': 'FY_BY_REALTlME'
- }
- result = requests.post(url=self.url, headers=self.headers, data={**data, **sys_data}).json()
- print(result)
- return result
-
- def main(self, word):
- self.fanyi_word(word)
-
-
- if __name__ == '__main__':
- fanyi = YouDaoFanYi()
- fanyi.main('爬虫')
这样一来发现能够获得正确的响应结果了!
1、此网站还分多种语言指定转换,这边就不继续进行分析了。有兴趣的小伙伴可以对js进行解析拿到对应的值即可。
2、这次分析明白了有些请求不光光是把参数分析出来就完事了,往往有的时候请求失败的问题不是参数有没有解析正确,可能问题藏在请求头里面。所以需要多方面的完善,思维多变。
3、在代码中看见关键字例如MD5等优先考虑是否是常规的加密,可以省去很多麻烦。当然不排除闲得慌的程序员自己定义一个‘MD5‘来进行加密,这也是值得注意的点。例如本文中遇见的MD5关键字,很幸运就是常规的加密算法,省去了很多麻烦。
4、小伙伴们还有什么比较有意思的网站需要分析可以留言哟,博主看见了说不定下一篇文章就是解析它了。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。