当前位置:   article > 正文

python爬虫之biilibili弹幕爬取+qq音乐热评爬取_哔哩哔哩直播弹幕怎么爬取

哔哩哔哩直播弹幕怎么爬取

目录

前言

Bilibili弹幕爬取

分析与弹幕相关的内容

BilibiliSpider源码

run.py

结果截图

QQ音乐热评爬取

QQ音乐热评爬取源码

run.py

settting.py

结果截图:

结语:


前言

爬虫的方法很多比如用requests,beautifulsoup,scrapy这些库可以很方便的抓取网页内容。如果他的web端提供api接口那就更方便了,如果提供返回json数据也可以


Bilibili弹幕爬取

要爬取弹幕首先我们要分析它是如何进行http请求的,我们这里使用360极速浏览器的内置开发者工具,查看网络请求过程

分析与弹幕相关的内容

发现这是bilibili的一个api接口,那这就简单了,直接调用它的接口获取数据,这里有一个oid我们不知道是什么,我们直接搜索这个数值发现

这个请求出现了这个数值叫cid

cid是通过url里面的内容得到的

很明显是区分video的

于是我们可以得到如下代码(使用scrapy库)

BilibiliSpider源码

  1. import scrapy
  2. import re
  3. import json
  4. from matplotlib import pyplot as plt
  5. # 视频排序方式
  6. sort_model = {1:"totalrank",2:"click",3:"pubdate",4:"dm",5:"stow"}
  7. # bilibili 弹幕分析
  8. class BilibiliDanmuSpider(scrapy.Spider):
  9. name="BilibiliDanmuSpider"
  10. #,"https://api.bilibili.com/x/v1/dm/list.so?oid=43147218"
  11. def __init__(self,key=None,*args,**kwargs):
  12. super(eval(self.__class__.__name__),self).__init__(*args,**kwargs)
  13. print(key)
  14. self.start_urls=["https://search.bilibili.com/all?keyword=%s"%(key)]
  15. self.danmu_header = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/64.0.3282.167 Safari/537.36','Accept': '*/*','Accept-Encoding': 'gzip, deflate, br','Accept-Language': 'zh-CN,zh;q=0.9'}
  16. def isHttpUrl(self,url):
  17. return len(re.findall("^(http)s?://*",url))==1
  18. def parse(self,response):
  19. try:
  20. data=response.body.decode()
  21. selector=scrapy.Selector(text=data)
  22. print(response.url)
  23. for url in selector.xpath("//ul[@type='video']/li/a/@href").extract():
  24. url="https:%s"%(url)
  25. if self.isHttpUrl(url):
  26. yield scrapy.Request(url=url,callback=self.parseSubPage)
  27. except Exception as err:
  28. print(err)
  29. def parseSubPage(self,response):
  30. try:
  31. #print("subPage=%s"%(response.url))
  32. url=response.url
  33. #av_id=self.getAVID(url)
  34. #print(response.url,av_id)
  35. b_vid=re.findall(r"(?<=video/)[a-zA-Z0-9]+\.?[a-zA-Z0-9]*",url)
  36. if len(b_vid)==1:
  37. b_vid=b_vid[0]
  38. print("b_vid="+b_vid)
  39. url = "https://api.bilibili.com/x/player/pagelist?bvid="+b_vid+"&jsonp=jsonp"
  40. #url = "https://api.bilibili.com/x/player/pagelist?aid="+av_id+"&jsonp=jsonp"
  41. yield scrapy.Request(url=url,callback=self.getBarrage)
  42. except Exception as err:
  43. print(err)
  44. def getAVID(self,url):
  45. av_id = re.findall(r"(?<=av)\d+\.?\d*",url)
  46. if len(av_id)>0:
  47. return av_id[0]
  48. else:
  49. return ""
  50. def getBarrage(self,response):
  51. try:
  52. res=json.loads(response.text)
  53. cid=res['data'][0]['cid']
  54. print(cid)
  55. url="https://api.bilibili.com/x/v1/dm/list.so?oid=%d"%(cid)
  56. yield scrapy.Request(url=url,callback=self.getDanMu)
  57. except Exception as err:
  58. print(err)
  59. def getDanMu(self,response):
  60. import wordcloud
  61. try:
  62. texts={}
  63. data=response.body.decode()
  64. selector=scrapy.Selector(text=data)
  65. for text in selector.xpath("//d/text()").extract():
  66. if texts.get(text) == None:
  67. texts[text]=1
  68. else:
  69. texts[text]+=1
  70. texts=sorted(texts.items(), key=lambda kv: (kv[1]), reverse=True)
  71. res=""
  72. for text in texts:
  73. res+=text[0]+","
  74. print(res[:-1])
  75. # 构建词云对象w,设置词云图片宽、高、字体、背景颜色等参数
  76. w = wordcloud.WordCloud(width=1000,height=700,max_words=200,background_color='white', max_font_size=100,font_path="C:/Users/tangy/Desktop/py/lesson.cdu/res/simhei.ttf")
  77. # 调用词云对象的generate方法,将文本传入
  78. w.generate(res[:-1])
  79. plt.figure("response=%s"%(response.url))
  80. plt.imshow(w)
  81. plt.axis('off')
  82. plt.show()
  83. except Exception as err:
  84. print(err)

run.py

  1. from scrapy import cmdline
  2. key = input("输入关键字:")
  3. cmdline.execute(("scrapy crawl BilibiliDanmuSpider -s LOG_ENABLED=False -a key=%s"%(key)).split())

结果截图


QQ音乐热评爬取

想要爬取杰伦哥的歌的热评,直接上它的网页,也可以用app但是要用其他的抓包软件。这里只介绍网页端

找到具体位置,清除网络请求并点击加载更多的热评

发现第一个请求便是我们需要的数据

但是呢,我们发现加载更多的数据仍然是相同的数据,怀疑是api的问题于是我们找到它具体的javascript代码

根据代码进行编写,多次实验发现是同一数据,于是尝试修改pagesize,终于200是比较合适的,可以正常返回数据


新加:

https://c.y.qq.com/base/fcgi-bin/fcg_global_comment_h5.fcg?format=json&cid=205360772&reqtype=2&biztype=1&topid=104883226&cmd=6&needmusiccrit=1&pagenum=4&pagesize=20

这个连接是从桌面的应用抓的包得到的,根据这个就可以获取更多的热评


于是开始分析请求url

分析前面很多都是固定的,还有就是qq音乐的版本,所以我们这里不准备获取版本,直接使用当前版本,多首歌对比下来,值得我们注意的参数就只有topid和lasthotcommentid

于是乎开始分析这两个参数是如何得到的

在第一个请求我们找到了这个songid,但是后面在写搜索的时候发现在搜索列表也有数据,于是就用的搜索数据

在第3个url请求我们找到了

接下来对request url进行分析,值得我们注意的是多了一个serachId,这个seachid我觉得是随机生成的于是我就固定一个值,loginUin也可以可有可无,w是搜索的内容

start_urls初始化代码如下

self.start_urls=["https://c.y.qq.com/soso/fcgi-bin/client_search_cp?ct=24&qqmusic_ver=1298&new_json=1&remoteplace=txt.yqq.song&searchid=55594271468033902&t=0&aggr=1&cr=1&catZhida=1&lossless=0&flag_qc=0&p=1&n=10&w=%s&g_tk_new_20200303=652127051&g_tk=652127051&loginUin=&hostUin=0&format=json&inCharset=utf8&outCharset=utf-8&notice=0&platform=yqq.json&needNewCode=0"%(key)]

QQ音乐热评爬取源码

  1. import scrapy
  2. import re
  3. import json
  4. class ReviewsSpider(scrapy.Spider):
  5. name="ReviewsSpider"
  6. key=""
  7. pagesize=200
  8. topId=0
  9. def __init__(self,key=None,*args,**kwargs):
  10. self.key=key
  11. super(eval(self.__class__.__name__),self).__init__(*args,**kwargs)
  12. self.start_urls=["https://c.y.qq.com/soso/fcgi-bin/client_search_cp?ct=24&qqmusic_ver=1298&new_json=1&remoteplace=txt.yqq.song&searchid=55594271468033902&t=0&aggr=1&cr=1&catZhida=1&lossless=0&flag_qc=0&p=1&n=10&w=%s&g_tk_new_20200303=652127051&g_tk=652127051&loginUin=&hostUin=0&format=json&inCharset=utf8&outCharset=utf-8&notice=0&platform=yqq.json&needNewCode=0"%(key)]
  13. print(self.start_urls)
  14. self.music_header = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/64.0.3282.167 Safari/537.36','Accept': '*/*','Accept-Encoding': 'gzip, deflate, br','Accept-Language': 'zh-CN,zh;q=0.9'}
  15. def parse(self,response):
  16. try:
  17. data=response.body.decode()
  18. data=json.loads(data)
  19. songs=data['data']['song']['list']
  20. if len(songs)==0:
  21. print("not found by key=%s"%(self.key))
  22. return
  23. song=songs[0]
  24. self.topId=song['id']
  25. #mId=song['mid']
  26. url="https://c.y.qq.com/base/fcgi-bin/fcg_global_comment_h5.fcg?g_tk_new_20200303=652127051&g_tk=652127051&loginUin=&hostUin=0&format=json&inCharset=utf8&outCharset=GB2312&notice=0&platform=yqq.json&needNewCode=0&cid=205360772&reqtype=2&biztype=1&topid=%s&cmd=8&needmusiccrit=0&pagenum=0&pagesize=25&lasthotcommentid=&domain=qq.com&ct=24&cv=10101010"%(self.topId)
  27. yield scrapy.Request(url=url,callback=self.getComments)
  28. except Exception as err:
  29. print(err)
  30. def getComments(self,response):
  31. try:
  32. data=response.body.decode()
  33. data=json.loads(data)
  34. comments=data['hot_comment']['commentlist']
  35. if len(comments)==0:
  36. print("found comment error")
  37. return
  38. lastcommentid=comments[len(comments)-1]['rootcommentid']
  39. url="https://c.y.qq.com/base/fcgi-bin/fcg_global_comment_h5.fcg?g_tk_new_20200303=652127051&g_tk=652127051&loginUin=676435008&hostUin=0&format=json&inCharset=utf8&outCharset=GB2312&notice=0&platform=yqq.json&needNewCode=0&cid=205360772&reqtype=2&biztype=1&topid=%s&cmd=6&needmusiccrit=0&pagenum=1&pagesize=%d&lasthotcommentid=%s&domain=qq.com&ct=24&cv=10101010"%(self.topId,self.pagesize,lastcommentid)
  40. yield scrapy.Request(url=url,callback=self.getHotComment)
  41. except Exception as err:
  42. print(err)
  43. def getHotComment(self,response):
  44. try:
  45. data=response.body.decode()
  46. data=json.loads(data)
  47. comments=data['comment']['commentlist']
  48. if len(comments)==0:
  49. print("found comment error")
  50. return
  51. for comment in comments:
  52. print(comment['rootcommentcontent'])
  53. except Exception as err:
  54. print(err)

run.py

  1. from scrapy import cmdline
  2. key = input("输入关键字:")
  3. cmdline.execute(("scrapy crawl ReviewsSpider -s LOG_ENABLED=False -a key=%s"%(key)).split())

settting.py

  1. DEFAULT_REQUEST_HEADERS = {
  2. 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/64.0.3282.167 Safari/537.36',
  3. 'Accept': '*/*',
  4. 'Accept-Encoding': 'gzip, deflate, br',
  5. 'Accept-Language': 'zh-CN,zh;q=0.9'
  6. }
'
运行

结果截图:


结语:

不难发现爬取一些简单的数据并不困难,在爬取资源文件的时候多注意资源id的获取

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/正经夜光杯/article/detail/900042
推荐阅读
相关标签
  

闽ICP备14008679号