Python爬虫入门教程 续上篇,python爬虫爬取AC中间站视频

一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第12天,点击查看活动详情

写在前面

上篇博客我们用比较大的篇幅分析了 B 站视频传输方式,这篇博客填一下之前留下的坑,我们把代码部分写出来。

文章来源:梦想橡皮擦,其实这个 ID 是一个组合

分析的步骤与逻辑这里不再重复给大家演示了,可以翻看上篇文章,里面有清晰的说明。

先记住

30280.m4s,对应音频文件 30064.m4s,对应视频文件

编码时间

B 站视频虽然已经分析完毕,但是实际编码还是有难度的,所以坚持住,我们一起搞定它。

全篇文章使用的链接为:www.bilibili.com/video/BV1Pv… ,BV 链接,B 站升级之后从 AV 连接提升到 BV,反爬技术成倍的叠加。

通过 Fiddler 抓取,分析之后,我们得到了这样的一些结论,重点如下图所示,页面返回状态码为 206,这个需要关注下

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

上面的图片,可能你看的比较晕,还是不要急,点击一个链接,我们需要看一下它是如何请求与返回数据的。分析之后,你会发现一个奇怪的现象,在链接相同的情况下,请求返回一个状态码是 200,另一个是 206。

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

这两个紧挨着的请求,请求地址一样,但是,返回的状态码不同,这还不是最重要的,看一下请求方式,会发现更奇怪的点出现了。

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

状态码是 200 的,请求方式竟然是 OPTIONS ... 另一个状态码是 206 的,请求方式是 GET ,有点意思,可能这就是我们最终的突破点了,先把请求方式了解透彻,下面就可以代码走起了。

这部分代码,我使用的链接是直接从 fiddler 中获取的,代码完毕之后,这个地方有个非常大的难度需要攻克,可以作为大家深入分析后续的一个亮点功能点。后面我们会基于这个链接做一些扩展讨论和探索。 从 fiddler 中复制的链接 https://9lglsr2.yfcalc.com:9940********=1 节省了一些篇幅,链接自己去找哦~

最终实现的代码如下,注意这个地方要通过 requests.session() 去发起请求,因为请求头中有 keep-alive 这个属性值,下述代码中删掉了部分链接,需要代码的可以关注我微信公号,回复 B 站,或者直接在文章头部下载文件也可以。

微信搜索“非本科程序员” 即可

import requests

"""
Host: 9lglsr2.yfcalc.com:9940
Connection: keep-alive
Origin: https://www.bilibili.com
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; UA删掉部分
range: bytes=998857-1198790
Accept: */*
Sec-Fetch-Site: cross-site
Sec-Fetch-Mode: cors
Referer: https://www.bilibili.com/video/BV1Pv41167FE
Accept-Encoding: identity
Accept-Language: en,zh-CN;q=0.9,zh;q=0.8

"""
# 你的地址和我的不同
url = "https://9lglsr2.yfcalc.com:9940/upos-dash-mirrorks3u.bilivideo.com/bilibilidash_篇幅关系,链接删掉部分"

header_options = {

    'Host': '9lglsr2.yfcalc.com:9940',
    'Connection': 'keep-alive',
    'Access-Control-Request-Method': 'GET',
    'Origin': 'https://www.bilibili.com',
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) UA删掉部分',
    'Access-Control-Request-Headers': 'range',
    'Accept': '*/*',
    'Sec-Fetch-Site': 'cross-site',
    'Sec-Fetch-Mode': 'cors',
    'Referer': 'https://www.bilibili.com/video/BV1Pv41167FE',
    'Accept-Encoding': 'gzip, deflate, br',
    'Accept-Language': 'en,zh-CN;q=0.9,zh;q=0.8'

}

# 拼凑一个请求头,你获取的跟我应该大不相同,写自己的即可
headers ={
    'Host': '9lglsr2.yfcalc.com:9940',
    'Connection': 'keep-alive',
    'Origin': 'https://www.bilibili.com',
    'User-Agent': 'Mozilla/5.0 UA删掉部分',
    'range': 'bytes=0-9999999999',
    'Accept': '*/*',
    'Sec-Fetch-Site': 'cross-site',
    'Sec-Fetch-Mode': 'cors',
    'Referer': 'https://www.bilibili.com/video/BV1Pv41167FE',
    'Accept-Encoding': 'identity',
    'Accept-Language': 'en,zh-CN;q=0.9,zh;q=0.8'
}
session=requests.session()
session.options(url=url,headers=header_options,verify=False)
res=session.get(url=url,headers=headers,verify=False)
with open('audio.mp3','wb') as fp:
    fp.write(res.content)
    fp.flush()
    fp.close()
print("下载成功")
复制代码

运行成功,下载的是音频文件。

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

用同样的办法,你可以把视频下载下来,只需要获取到视频的地址即可进行操作,我得到的地址如下

url = "9ns2tr2.yfcalc.com:13357/upos-dash-m…"

爬取的音频和视频是分离的,只需要用 ffmpeg 去合并一下即可。基本逻辑已经理清楚,剩下的是修改、完善,大部头的工作即将开始,当然我这块砖已经抛给你了,剩下的由你来完成。

编码未完成部分

上面的代码只是非常小的一部分逻辑,例如在下载视频的时候,没有进度条会导致视频不确定是否下载完毕,体验非常差,如果去完成一个项目,你需要补充下,学习阶段看自己的情况。

最大的问题是我们上述的请求地址是直接从 Fiddler 中获取的,这个地址到底是怎么来的,我尝试去解决,结果发现 B 站反爬果然还是比较厉害的,我展示一下大概的进展,并没有完成该问题。

写代码的时候,如果从网页源码去获取连接,发现获取难度很大,我们在网页源码中获取的链接和视频请求的链接明显不一致

源码获取的链接(网站右键,查看源码获取到的)

http://upos-sz-mirrorhw.bilivideo.com/upgcxcode/20/11/199591120/199591120-1-30280.m4s?e=ig8euxZM2rNcNbdlhoNvNC8BqJIzNbfqXBvEqxTEto8BTrNvN0GvT90W5JZMkX_YN0MvXg8gNEV4NC8xNEV4N03eN0B5tZlqNxTEto8BTrNvNeZVuJ10Kj_g2UB02J0mN0B5tZlqNCNEto8BTrNvNC7MTX502C8f2jmMQJ6mqF2fka1mqx6gqj0eN0B599M=&uipk=5&nbs=1&deadline=1591936610&gen=playurl&os=hwbv&oi=3056817678&trid=ba124908cc9b4c08b338898c507f1b2cu&platform=pc&upsig=69afcb746d8f70b3ef157b0d5d96105a&uparams=e,uipk,nbs,deadline,gen,os,oi,trid,platform&mid=39801623&orderid=0,2&logo=80000000

视频请求的真实链接

https://k31k9q1.yfcalc.com:15172/upos-dash-mirrorks3u.bilivideo.com/bilibilidash_98e9c0435499a2edc99cda183af9647c2c76fee9/199591120-1-30064.m4s?scuid=F6we2NvTZYGLpLeGVVZi&timeout=1592535041&check=1258368323&sttype=90&yfdspt=1591930241786&yfpri=100&yfopt=17&yfskip=1&yfreqid=CDkypiFjBDuLtgbAAQ&yftt=100&yfhost=5p8vjn1.yfcache.com&yfpm=1

这就需要我们破掉这个障碍了,难度最大的地方是需要找到视频请求的连接是如何拼接出来的。来吧,继续探案吧。

继续努力找到下图所示的链接,这应该就是突破点了,因为我从返回的数据中,找到了上述的 真实链接 地址。而且返回的是 JSON 串。

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

使用 url 解码工具,将参数用的 URL 进行解码,哇哦,似曾相识的感觉,距离真相越来越近了。

https://upos-dash-mirrorks3u.bilivideo.com/upgcxcode/20/11/199591120/199591120-1-30280.m4s?e=ig8euxZM2rNcNbdlhoNvNC8BqJIzNbfqXBvEqxTEto8BTrNvN0GvT90W5JZMkX_YN0MvXg8gNEV4NC8xNEV4N03eN0B5tZlqNxTEto8BTrNvNeZVuJ10Kj_g2UB02J0mN0B5tZlqNCNEto8BTrNvNC7MTX502C8f2jmMQJ6mqF2fka1mqx6gqj0eN0B599M=&uipk=5&nbs=1&deadline=1591938786&gen=playurl&os=hwbv&oi=3056817678&trid=8106da0eee9548cb8377565645dbc1f8u&platform=pc&upsig=adeb773cf597120141a94bd78a8775ab&uparams=e,uipk,nbs,deadline,gen,os,oi,trid,platform&mid=39801623&orderid=0,2&logo=80000000&[email protected]

现在的问题就是解开 B 站加密规则了,关于这部分,我尝试着去解开,发现混淆比较严重,分析起来非常耗时,以下是我这边的进展,核心部分代码已经找到,如果可以解开找到 JS 文件中对应的代码,然后用 Python 改造它,我找了 B 站两个视频,针对这两个视频分别找到了如下代码段,发现部分内容确实是加密的,但 混淆的字符串 是一致的,就是下面的 t 部分和 ak 部分

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

Python爬虫入门教程 71-100 续上篇,python爬虫爬取B站视频

然后在接下来,我陷入瓶颈了,这块的加密手段不是很容易逆向出来,也可以说需要大量的时间去尝试(又偷懒了,没继续思考~哈哈哈),如果你解决了,一定要给我发个简讯,告诉我一下哦!!!

彩蛋时间

对于 B 站视频下载,用 you-get 就非常香了,重新造轮子这个要看大家锻炼的是什么能力了,不过一般这种情况下,我就直接访问手机 Web 站了 ,访问地址换成 https://m.bilibili.com/video/BV1Pv41167FE 直接查看源码

在这里插入图片描述

emmm... 直接一个 MP4 文件,多香,多简单,写代码多方便,获取连接,提取地址,二进制下载,写入文件,存档,退出,一套组合拳,拿数据走人。

很多时候,我们无法解决技术问题,不是因为我们技术不行,而是因为我们不知道怎么才行

猜你喜欢

转载自juejin.im/post/7085545132644106276