当前位置: 首页 > news >正文

blivedm 上手手记:把 B 站直播间变成你的实时数据源

blivedm 上手手记:把 B 站直播间变成你的实时数据源

【免费下载链接】blivedm获取bilibili直播弹幕,使用WebSocket协议,支持web端和B站直播开放平台两种接口项目地址: https://gitcode.com/gh_mirrors/bl/blivedm

做直播运营的人大概都经历过这样的时刻:一场三个小时的直播结束后,想复盘观众到底在聊什么、礼物集中在哪个时间段、哪位观众是真正的铁粉,结果只能对着回放手动翻弹幕,翻到眼冒金星。主播自己也想摸清观众喜好,却只有"礼物列表"和"弹幕滚屏"两扇窗,看不到全貌。

如果你正好需要解决"实时拿到 B 站直播间的弹幕、礼物、进房、上舰等数据"这件事,那么blivedm这个基于 WebSocket 的 Python 库就是为你准备的。它不刷屏、不轮询,把 B 站直播间的消息一条条推送到你的程序里,本文带你从零把它跑起来,并逐步搭出一个可落地的直播数据监控脚本。

动手之前,先看清一条直播消息里藏着什么

很多人以为"弹幕数据"就是一行文本加一个用户名,其实远不止如此。以 blivedm 解析后的DanmakuMessage为例,一条弹幕对象里除了msg(内容)和uname(用户名),还带上了这些字段:

  • 发送者画像uiduser_level(用户等级)、wealth_level(荣耀等级)、vip/svip(是否老爷)
  • 勋章信息medal_namemedal_level,即观众在哪个主播的直播间挂了什么牌子的粉丝勋章
  • 弹幕属性color(颜色)、font_sizedm_type(0 文本 / 1 表情 / 2 语音)
  • 其他timestampprivilege_type(是否舰队成员)等

也就是说,你拿到的不是"一行字",而是一份结构化的用户行为数据。有了用户等级和勋章信息,做"谁是核心观众"的分析就顺手多了。

类似地,礼物消息GiftMessagegift_namenumcoin_type(金瓜子还是银瓜子)、total_coin(总瓜子数);上舰消息能给出guard_level(1 总督、2 提督、3 舰长);醒目留言SuperChatMessage直接给出人民币金额price。这些都是复盘直播收入的关键字段。

先把环境备好,让第一条弹幕跑起来

项目没有发布到 PyPI,所以正确的安装方式是先拉取源码再安装依赖。clone 之后进入目录,安装依赖包即可:

git clone https://gitcode.com/gh_mirrors/bl/blivedm cd blivedm pip install aiohttp Brotli pure-protobuf yarl

依赖只有四个:aiohttp(异步 HTTP 与 WebSocket 客户端)、Brotli(解压弹幕数据流)、pure-protobuf(解析进房等 protobuf 消息)、yarl(URL 解析)。Python 3.8 及以上都能跑。

连接一个直播间,核心代码其实只有四步:建客户端 → 挂处理器 → start → join。参考仓库根目录的sample.py,一个最小的监听脚本长这样:

import asyncio import blivedm async def main(): # 1. 用房间号创建客户端,房间号就是直播间 URL 里的那串数字 client = blivedm.BLiveClient(12235923) # 2. 挂上消息处理器 handler = MyHandler() client.set_handler(handler) # 3. 启动并保持运行 client.start() await client.join() # 继承 BaseHandler,重写 _on_xxx 回调即可接收对应消息 class MyHandler(blivedm.BaseHandler): def _on_danmaku(self, client, message): print(f'[{client.room_id}] {message.uname}:{message.msg}') if __name__ == '__main__': asyncio.run(main())

这段代码做了什么BLiveClient负责与 B 站弹幕服务器建立 WebSocket 长连接并维持心跳;MyHandler是你的"消息接收器"——只要直播间有人发弹幕,_on_danmaku就会被调用,message是已经解析好的DanmakuMessage对象,直接取字段打印即可。

注意client.join()是等待客户端停止的协程,它会一直挂住,让脚本持续运行。想跑 5 秒后自动退出?参照sample.py的做法:await asyncio.sleep(5)之后调用client.stop(),再await client.join()收尾。

把回调用全:除了弹幕,还能收到什么

BaseHandler已经把 B 站 WebSocket 推送的各种命令分发成了一个个_on_xxx回调,你只需要按需重写。常用的一组:

class MyHandler(blivedm.BaseHandler): # 弹幕 def _on_danmaku(self, client, message): print(f'[{client.room_id}] {message.uname}:{message.msg}') # 礼物 def _on_gift(self, client, message): print(f'[{client.room_id}] {message.uname} 赠送{message.gift_name}x{message.num}' f'({message.coin_type}瓜子x{message.total_coin})') # 上舰(guard_level:1 总督 / 2 提督 / 3 舰长) def _on_user_toast_v2(self, client, message): print(f'[{client.room_id}] {message.username} 上舰,等级={message.guard_level}') # 醒目留言(直接带人民币金额) def _on_super_chat(self, client, message): print(f'[{client.room_id}] 醒目留言 ¥{message.price} {message.uname}:{message.message}') # 观众进房 / 关注等互动消息(msg_type 为 1 表示进入房间) def _on_interact_word_v2(self, client, message): if message.msg_type == 1: print(f'[{client.room_id}] {message.username} 进入房间') # 心跳包,可拿到当前人气值 def _on_heartbeat(self, client, message): print(f'[{client.room_id}] 当前人气 {message.popularity}')

这段代码做了什么:它把五类最常见的直播事件各自接到了处理函数上。尤其值得注意两点:_on_user_toast_v2里判断source != 2可以过滤掉"赠送的舰"而只留"付费的舰",sample.py里就是这么做的;_on_heartbeatmessage.popularity是服务器心跳回复里附带的人气值,虽然官方标注已废弃,但作为粗略的热度参考依然够用。

除了这些,还有_on_buy_guard(另一种上舰消息)、_on_super_chat_delete(醒目留言被删除)等回调。所有回调方法在blivedm/handlers.py里都能看到完整的清单和注释,翻一遍就知道全部能力边界。

一次盯五场直播:多房间并行监控

做竞品分析或批量监测时,一个客户端只盯一个房间显然不够。好消息是,多开客户端几乎零成本——每个BLiveClient都是独立的协程任务,共享一个aiohttp.ClientSession和同一个 handler 即可:

import asyncio import aiohttp import blivedm ROOM_IDS = [12235923, 14327465, 21396545] async def main(): # 共享一个 session,复用连接池,也方便统一注入 cookie session = aiohttp.ClientSession() handler = MyHandler() clients = [blivedm.BLiveClient(room_id, session=session) for room_id in ROOM_IDS] for client in clients: client.set_handler(handler) client.start() try: # 同时等待所有客户端 await asyncio.gather(*(client.join() for client in clients)) finally: # 统一收尾 await asyncio.gather(*(client.stop_and_close() for client in clients)) await session.close()

这段代码做了什么:列表推导式批量创建客户端,asyncio.gather让它们并行运行,任何一个房间的弹幕都会进入同一个MyHandler,而client.room_id帮你区分消息来自哪个房间。回调里所有 message 都是线程隔离的 dataclass 对象,直接累加统计即可,不用担心互相污染。

一个性能提示:set_handler的文档里写得很明白——消息处理与网络协程同在一个协程里跑,如果回调里做耗时操作会阻塞收消息。所以弹幕量大的直播间,建议回调只负责"入队",把真正的统计、落库丢给线程池或消息队列,别在回调里写重逻辑。

聊一聊断线重连和优雅退出

直播 WebSocket 连接断断续续是常态,blivedm 在这块已经帮你兜了底:

  • 自动重连:网络异常、认证失败时,客户端会自动重连;重连次数多了还会自动重新走一遍init_room()拿新的 token,防止旧 token 失效连不上。
  • 可调的重连策略set_reconnect_policy接收一个"输入重试次数、返回间隔秒数"的函数,你可以按需实现指数退避。
  • 生命周期四件套start()启动、stop()停止、join()等待停止完成、stop_and_close()停止并释放资源。注意stop_and_close()之后这个客户端就不能再用了,需要重新创建。
  • 崩溃兜底HandlerInterface.on_client_stopped(client, exception)会在客户端停止时被调用,exception非空就说明是异常退出——你可以在那里实现自己的告警或重启逻辑。

web 端直连 vs 开放平台接入,怎么选

blivedm 支持两条完全不同的接入通道,适用场景差别很大:

对比项web 端直连(BLiveClient)开放平台(OpenLiveClient)
接入门槛只需房间号,零申请需在 B 站直播开放平台申请密钥、建项目、拿主播身份码
消息类型弹幕、礼物、上舰、醒目留言、进房等额外支持点赞、直播开始/结束等事件
数据可靠性依赖网页端接口,字段可能随前端改版变动官方接口,格式稳定、字段标准化
适合场景快速验证、个人项目、监控任意直播间生产环境、需要完整事件类型的正式应用

web 端是最快的路径,跑通原型用它;如果你的应用要长期稳定跑、还想要"开始直播 / 结束直播 / 点赞"这类事件,就走开放平台。后者的接入代码在仓库根目录的open_live_sample.py里,核心骨架如下:

import asyncio import blivedm async def main(): # 换成你在开放平台申请到的真实凭证 client = blivedm.OpenLiveClient( access_key_id='你的 ACCESS_KEY_ID', access_key_secret='你的 ACCESS_KEY_SECRET', app_id=你的_APP_ID, room_owner_auth_code='主播身份码', ) client.set_handler(MyHandler()) client.start() await client.join() class MyHandler(blivedm.BaseHandler): def _on_open_live_danmaku(self, client, message): print(f'[{message.room_id}] {message.uname}:{message.msg}') def _on_open_live_gift(self, client, message): coin_type = '金瓜子' if message.paid else '银瓜子' print(f'[{message.room_id}] {message.uname} 赠送{message.gift_name}x{message.gift_num}({coin_type})') def _on_open_live_like(self, client, message): print(f'[{message.room_id}] {message.uname} 点赞了') def _on_open_live_start_live(self, client, message): print(f'[{message.room_id}] 开播了')

这段代码做了什么OpenLiveClient在连接前会先向开放平台发起"开启项目"请求,拿到场次 ID 和 WebSocket 地址,然后像 web 端一样建立长连接;回调方法名以_on_open_live_开头,与 web 端的_on_区分开,两者可以同时使用。注意开放平台还有一层项目心跳(默认 20 秒发一次),如果长时间没收到,服务器会判定项目失活并停止推送,客户端内部会自动检测并重新开启项目——这也是它适合长期运行的原因之一。

让数据落库:把实时流存成可分析的记录

纯打印没有积累,下一步自然是落库。把上一节的回调稍加改动,弹幕就能持续写入 SQLite:

import sqlite3 from datetime import datetime # 初始化一张弹幕表 conn = sqlite3.connect('live_data.db') conn.execute('''CREATE TABLE IF NOT EXISTS danmaku ( room_id INTEGER, uname TEXT, msg TEXT, user_level INTEGER, medal_name TEXT, medal_level INTEGER, ts INTEGER )''') conn.commit() class MyHandler(blivedm.BaseHandler): def _on_danmaku(self, client, message): conn.execute( 'INSERT INTO danmaku VALUES (?, ?, ?, ?, ?, ?, ?)', (client.room_id, message.uname, message.msg, message.user_level, message.medal_name, message.medal_level, message.timestamp), ) conn.commit()

这段代码做了什么:每收到一条弹幕就插入一行,medal_namemedal_level记录了观众挂的粉丝勋章,user_level记录了用户等级。存上几天后你会发现,这些字段足够支撑不少有意思的分析:

  • 弹幕情感分析:用情感词典或现成模型给msg打分,画出"整场直播的情绪曲线",看哪个环节观众反应最热烈
  • 热门话题识别:对弹幕做分词 + 词频统计,一键找出当天的热梗
  • 核心观众圈层:按medal_leveluser_level、送礼频次排序,识别高价值粉丝
  • 礼物收入复盘:礼物表和上舰表按timestamp聚合,就能看到"哪十分钟收入最高"

社区里甚至有人基于本库直接做了一个叫blivechat的弹幕互动工具(README 里可找到它的说明),说明这套数据流的想象空间远比"看弹幕"大得多。

从第一行代码到你的专属直播监控

回顾一下我们走过的路:先看清一条直播消息里能挖出多少字段,然后用四行代码接住了第一条弹幕,再把礼物、上舰、醒目留言、进房全部接入回调,紧接着实现了多直播间并行监控和断线自愈,最后对比了 web 端与开放平台两条接入通道,并把数据沉淀进了 SQLite。

到这里,一个能实时采集、持久化、可分析的 B 站直播数据管道已经在你手里了。接下来想把它做成什么,完全取决于你:挂一个机器人播报大额礼物、写一个自动统计下播收益的小工具、还是攒一个季度数据做观众画像?仓库里的sample.pyopen_live_sample.py就是你的起跑线,clone 下来改一改,今晚就能在你自己关注的直播间看到第一条被代码捕获的弹幕。

【免费下载链接】blivedm获取bilibili直播弹幕,使用WebSocket协议,支持web端和B站直播开放平台两种接口项目地址: https://gitcode.com/gh_mirrors/bl/blivedm

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

http://www.jsqmd.com/news/1405635/

相关文章:

  • 支付宝红包回收这样玩,轻松盘活闲置福利 - 京顺回收
  • 深耕青浦家装市场,六除六装饰以数据工厂模式标准化每一处工地 - 资讯报道
  • 华硕笔记本发烫降频怎么办?G-Helper 六步调优指南:实测温度直降 14°C
  • 贵州正规旅行社甄选攻略,2026年贵州优质旅行团怎么选?贵州跟团游避坑出行指南 - 跟我去旅游
  • 3分钟免费激活IDM:开源脚本永久冻结30天试用期的完整教程
  • NOC片上网络
  • Ventoy 使用教程:一个U盘免格式化装下所有系统,启动盘制作就该这么省心
  • Keil C51保姆级安装教程(附安装包)
  • ncmdump免费教程:3分钟完成NCM文件解密,把网易云音乐真正变成你的
  • 北京包包回收市场2026年趋势:顶奢坚挺、一线稳健、轻奢承压的梯队分化 - 大牌科普时报
  • 文件系统开发从几个月变成几小时?WinFsp让新手也能在Windows上造“虚拟磁盘“
  • OpenKore开源RO客户端自动化工具实战指南:7步搭好你的智能挂机助手
  • 四川 6‑18 岁孩子读文武学校|四川文武学校哪家靠谱?2026 招生解读 - Luckyone王
  • 江苏除甲醛公司参考解析:多种服务模式与本地实体服务商实践观察 - 康一科技
  • 用遍所有AI论文工具[特殊字符]终于摸清稳过审的底层逻辑|OKBIYE真的不一样
  • 完整性测试仪国产替代哪个好?解析 - 小橘甄选
  • 2026郑州二手宝格丽弹簧项链回收就来毓典奢品汇18617962974全国连锁专业靠谱 - 丽坤奢品汇
  • 零基础用PyPSA搞定电力系统分析:从搭电网模型到容量优化的3步实战路线
  • tessdata货架标签识别实战:10分钟从零搭起一套OCR货物定位系统
  • 让Python直连蓝牙设备:Bleak异步BLE客户端完整实战指南
  • 新手必看:读懂OpenMower的ROS软件架构——launch文件、参数系统与Topic/Service全景图
  • 2026年江阴老房翻新装修公司怎么选:拆旧防水防潮避坑指南 - 品牌评测研究中心
  • SaaS 产品从 0 到 1:麦芽AI 一条龙加速 MVP 落地 vs workbuddy/Codex 单点编程
  • 终极免费AI视频放大指南:用Video2X 3步把模糊视频无损升级到4K
  • 2026沃尔玛购物卡回收干货攻略,行情浮动规律、渠道适配与防骗技巧 - 京顺回收
  • 峨眉武术传习院办学参考,夹江文礼武术学校 2026 招生,四川全日制封闭式文武学校一览 - Luckyone王
  • Spring AI Alibaba 入门开发-提示词功能、提示词模板、格式化输出(备份)
  • 平开窗系统门窗生产商
  • AMBA总线
  • 2026新疆玉器品牌解读:祥玉奇源的直营品质之路 - 互联网科技品牌测评