python爬虫实战(十) 热门视频信息爬取(简易版)| 接口爬取

上篇爬虫博客,我们组合了scrapy和selenium对生活区的视频信息进行爬取。新手来说还是比较难理解的,有没有更简单的爬取方式呢?今天,就来继续分享一下某视频热门视频爬取另一种方式:API接口爬取。

目录

        • 一、API接口寻找
        • 二、爬取分析
        • 三、更多信息爬取

一、API接口寻找

以某视频网站的动画区的AMD为例,打开热门视频所在页面。使用谷歌浏览器的检查功能,对页面刷新,找到视频信息所在的接口,如下图所示:
在这里插入图片描述
result中共20条视频相关信息,需要爬取的字段

字段名含义
author作者名
id视频aid编号(后续爬取需要)
duration视频时长
favorite收藏数
play播放量
pubdate发布时间
review评论数
title视频名称

二、爬取分析

主要的爬取思路:找到该接口的URL,利用requests获取html文档信息。利用json模块将其转化为字典,接着利用字典各个键获取信息即可。

需要注意一点的是,该接口的URL很长,从search?后面其实都是传入下面这个字典的参数,其中page是代表当前页,time_from和time_to是限制所视频的投稿日期范围,cate_id是各个区编码代号(动画区其他部分代码号为25,47,210)
注意:构造的时候可以不用将callback传入!)
在这里插入图片描述

全部代码

import requests
import json
import time
import pandas as pd
import os
import random
os.chdir('C:/users/dell/Desktop/')
url = '为通过审核,这部分请读者自行获取URL'
head=["Mozilla/5.0 (Windows NT 6.0; rv:2.0) Gecko/20100101 Firefox/4.0 Opera 12.14","Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.0) Opera 12.14","Opera/12.80 (Windows NT 5.1; U; en) Presto/2.10.289 Version/12.02","Opera/9.80 (Windows NT 6.1; U; es-ES) Presto/2.9.181 Version/12.00","Opera/9.80 (Windows NT 5.1; U; zh-sg) Presto/2.9.181 Version/12.00",
]
headers={'user-agent':random.choice(head),'refer':'为通过审核,请读者自行获取'
}
def get_inf(url,headers,num):df = []for page in range(num):params = {'main_ver': 'v3','search_type': 'video','view_type': 'hot_rank','order': 'click','copy_right': -1,'cate_id': 24,'page': page,'pagesize': 20,'jsonp': 'jsonp','time_from': 20201201,'time_to': 20201219}try:r = requests.get(url,headers=headers,params=params)data = json.loads(r.text)inf_list = data['result']for i in range(len(inf_list)):author = data['result'][i]['author']duration = data['result'][i]['duration']collection = data['result'][i]['favorites']aid = data['result'][i]['id']title = data['result'][i]['title']pubdate = data['result'][i]['pubdate']review = data['result'][i]['review']play = data['result'][i]['play']df.append([author,title,pubdate,aid,duration,play,review,collection])print('第{}页爬取完毕'.format(page+1))time.sleep(random.randint(1,2))except:print('未爬到数据')df = pd.DataFrame(df,columns=['UP主','视频标题','发布时间','aid','视频时长','播放量','评论数','收藏数'])df.to_csv('bilibili.csv',encoding='gb18030',index=False)print('共{}条热门视频信息'.format(len(df)))
if __name__=='__main__':start = time.time()num = 100get_inf(url,headers,num)end = time.time()print('共花费{}分钟'.format(round((end-start)/60,2)))

由于是接口爬取,速度还是非常快的,2.76分钟爬完2000条数据
在这里插入图片描述

三、更多信息爬取

当然,从上面爬取的结果可知,原视频的点赞量、投币数以及弹幕数是没有的。因此,我们可以打开任意一个热门视频,运用同样的方法进行抓包,为加快爬取速度,在此使用协程异步爬取。

import numpy as np
import aiohttp
import asyncio
import pandas as pd
import os
import random
import time
import json
os.chdir('C:/users/dell/Desktop/')with open('aid.txt','r') as f: #将爬取得到aid保存为aid.txtaid = f.readlines()
df1 = []
aid_list = np.char.strip(aid,'\n')
semaphore = asyncio.Semaphore(10) #限制并发量
head=["Mozilla/5.0 (Windows NT 6.0; rv:2.0) Gecko/20100101 Firefox/4.0 Opera 12.14","Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.0) Opera 12.14","Opera/12.80 (Windows NT 5.1; U; en) Presto/2.10.289 Version/12.02","Opera/9.80 (Windows NT 6.1; U; es-ES) Presto/2.9.181 Version/12.00","Opera/9.80 (Windows NT 5.1; U; zh-sg) Presto/2.9.181 Version/12.00",
]
header={'user-agent':random.choice(head),'refer':'读者自行获取'
}
async def get_page(url):await asyncio.sleep(2)async with aiohttp.ClientSession() as session:async with await session.get(url, headers=header) as r:r_text = await r.text()return r_textasync def parse_page(text):try:data = json.loads(text)name = data['data']['owner']['name']video_name = data['data']['title']release_time = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime(data['data']['pubdate'])) #时间戳转化like = data['data']['stat']['like']coin = data['data']['stat']['coin']collection = data['data']['stat']['favorite']share = data['data']['stat']['share']view = data['data']['stat']['view']dm = data['data']['stat']['danmaku']df1.append([name,video_name,release_time,like,coin,collection,share,view,dm])except:print('未爬到数据')async def get_data(url):async with semaphore:text = await get_page(url)await parse_page(text)print('下载完成:', url)def main():url_list = ['为通过审核,读者自行获取该部分'+aid for aid in aid_list]tasks = [asyncio.ensure_future(get_data(url)) for url in url_list]loop = asyncio.get_event_loop()loop.run_until_complete(asyncio.wait(tasks))loop.close()if __name__=='__main__':start = time.time()main()df1 = pd.DataFrame(df1,columns=['UP主','视频名称','发布时间','点赞数','硬币数','收藏数','分享数','播放量','弹幕数'])df1.to_csv('b站.csv',encoding='gb18030',index=False)end = time.time()print('共花费{}分钟'.format(round((end-start)/60,2)))

同样爬取速度也是非常快的(早知道有接口就不用scrapy爬了,哈哈哈~),如下图所示
在这里插入图片描述

上篇博客,scrapy+selenium大概2个半小时爬完13000条数据。而这次,粗略计算一下,在网速正常的情况下,若要爬相同条数的视频信息,大约需要65分钟,又一次加快了速度!(所以,这里还是推荐大家在爬取网站前先去找找看有没有这种接口。不过像这种没有加密参数,也没有限制爬取条数限制的接口也是可遇不可求的。)

后续有时间将补上该部分的数据分析,以上就是本次分享的全部内容~


本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!

相关文章

立即
投稿

微信公众账号

微信扫一扫加关注

返回
顶部