锦上添花的视频弹幕模块开发

本文涉及的产品
Redis 开源版,标准版 2GB
推荐场景:
搭建游戏排行榜
简介: 锦上添花的视频弹幕模块开发
  • 非实时弹幕
  • image.png
  • 多节点实时弹幕
  • image.png
add: async (req) => {
    let { content, episodeId, playTime, productId } = req.body
    if (!(content && episodeId && Number(playTime) >= 0 && productId)) {
        return BackCode.buildError({ msg: '缺少必要参数' })
    }
    let token = req.headers.authorization.split(' ').pop()
    let userInfo = SecretTool.jwtVerify(token)
    let barrageItem = {
        episode_id: episodeId,
        product_id: productId,
        play_time: playTime,
        content: content,
        account_id: userInfo.id,
        head_img: userInfo.head_img,
        username: userInfo.username,
        del: 0,
    }
    await DB.BulletScreen.create(barrageItem)
    return BackCode.buildSuccess()
},

具体解释如下:

  1. let { content, episodeId, playTime, productId } = req.body;: 这行代码从请求的 body 中解构出弹幕的内容 (content)、集数 ID (episodeId)、播放时间 (playTime) 和产品 ID (productId)。这些参数都是客户端传来的。
  2. if (!(content && episodeId && Number(playTime) >= 0 && productId)) { return BackCode.buildError({ msg: '缺少必要参数' }) }: 这行代码用于判断是否缺少必要参数。如果其中任何一个参数为空或播放时间小于零,就会返回一个错误响应,提示缺少必要参数。
  3. let token = req.headers.authorization.split(' ').pop();: 这行代码从请求头中获取授权令牌 (authorization),然后将其拆分为两部分,取第二部分作为 token。
  4. let userInfo = SecretTool.jwtVerify(token);: 这行代码使用 SecretTool 工具类的 jwtVerify 方法对 token 进行解析,并返回包含用户信息的对象。
  5. let barrageItem = { ... }: 这是一个对象字面量,用于存储要添加到数据库的弹幕数据。其中包含集数 ID、产品 ID、播放时间、内容、账户 ID、头像、用户名和删除标志等信息。
  6. await DB.BulletScreen.create(barrageItem);: 这行代码使用模型 BulletScreencreate 方法创建一个新的弹幕实例,并将前面构建的 barrageItem 对象作为参数传递给它。通过这个操作,弹幕数据被写入到数据库中。
  7. return BackCode.buildSuccess();: 最后,返回一个成功的响应。

弹幕查询

list_by_episode: async (req) => {
  let { beginTime, endTime, episodeId, productId } = req.body
  if (!(productId && episodeId && Number(beginTime) >= 0 && endTime)) {
    return BackCode.buildError({ msg: '缺少必要参数' })
  }
  let barrageList = await DB.BulletScreen.findAll({
    where: { play_time: { [Op.between]: [beginTime, endTime] }, episode_id: episodeId, product_id: productId    }
  })
  return BackCode.buildSuccessAndData({ data: barrageList })
},

现阶段浏览器网页主要的请求方式

用户如何在浏览器上不作任何操作的情况下接收到服务器的消息?

定时短轮询

定时1-3秒请求服务器接口查询状态

场景:扫码登录、扫码支付等等

缺点:

1.虽然是用户无感知得从服务器获取消息,但是控制台上会有一堆的网络请求; 2.而且定时频繁地请求服务器接口,会消耗带宽,增加服务器的负担; 3.用户扫码后需要等待几秒时间,页面才能跳转,会有明显的卡顿;

长轮询

将http接口请求的超时时间设置大些(满足用户扫码所需的时间),如果超时就发起下一次请求

场景:百度云网盘app扫码登录等

特点:

1.用户扫码之后,在电脑端网页就秒跳转,用户不需要等待

以上两种方式称为服务器推送技术本质上还是客户端主动请求数据,只不过在用户无感知的情况下,也叫comet技术

为什么使用websocket?

像轮询的机制还是以客户端发起的请求,对于简单的扫码登录状态查询可以适用,但是遇到数据传输量大的场景就不行了,同时不能保证及时接受到消息,类似视频会议、网页游戏等业务场景,需要两端互相传输大量的数据,因此就需要使用websocket

  • 由来

现在使用最广泛的应用层协议HTTP1.1基于TCP协议,同一时间内客户端和服务端只能有一方主动发送数据,称为半双工

而TCP协议是全双工的,同一时间内两端都可以同时像对方发送数据,称为全双工

为了满足两端相互发送大量的场景,兴起了基于TCP协议的应用层协议websocket

 

  • 什么websocket?
  • 定义

是一种在单个TCP连接上进行全双工通信的协议使得客户端和服务器之间的数据交换变得更加简单,允许服务端主动向客户端推送数据

在WebSocket API中,浏览器和服务器只需要完成一次握手,两者之间就直接可以创建持久性的连接,并进行双向数据传输

-   优点
    -   节省资源:对比客户端轮询请求后端接口,更加节省服务器资源和宽带
    -   更强实时性:由于协议是全双工的,所以服务器可以随时主动给客户端下发数据,延迟更小
    -   保持连接状态:HTTP请求建立一次链接就断开,而websocket是持久性链接
-   使用场景
    -   弹幕
    -   多玩家游戏
    -   视频会议
    -   股票基金报价实时更新
    -   体育实况更新
    -   音视频聊天
    -   在线教育
    -   社交订阅

弹幕获取-前端模块编码实战开发

自定义封装websocket

/**
 * 弹幕逻辑配置
 */
import { useRef, useState } from "react";
import { io } from "socket.io-client";
const useSocket = () => {
  // 弹幕实例变量名
  const socket = useRef<any>(null);
  // 发送的弹幕
  const videoDanmuList = useRef<any[]>([]);
  const initialize = () => {
    // 建立传输链接 http://127.0.0.1:8081
    socket.current = io("ws://127.0.0.1:8081");
    socket.current.on("connect", () => {
      console.log("socketio已连接");
    });
    onBulletChat();
  };
  // 发送弹幕事件
  const handleAddDanmu = (data: any) => {
    socket.current.emit("bulletChat", data);
  };
  // 监听bulletChat事件
  const onBulletChat = () => {
    socket.current.on("message", (data: any) => {
      videoDanmuList.current.push(data);
    });
  };
  return {
    videoDanmuList,
    initialize,
    handleAddDanmu,
    onBulletChat,
  };
};
export default useSocket;

后段启动websocket

app.js

const express = require('express');
const app = express();
const { createServer } = require('http');
const server = createServer(app)
server.listen(8081, () => {
  console.log('服务启动在:http://127.0.0.1:8081')
})

websocket.js

const { Server } = require('socket.io')
const Redis = require("ioredis");
// redis发布的api
const clientPublish = new Redis({ port: 6379, host: '8.130.120.189', password: 'xdclass.net' });
// redis订阅api
const clientSubscribe = new Redis({ port: 6379, host: '8.130.120.189', password: 'xdclass.net' });
clientSubscribe.subscribe('chat');
const websocket = (server) => {
    // 实例化socket
    const io = new Server(server, { cors: { origin: '*' } })
    // websocket建立链接
    io.on('connection', (socket) => {
        console.log('有客户端链接进来了')
        // 监听bulletChat事件
        socket.on('bulletChat', (info) => {
            clientPublish.publish('chat', JSON.stringify(info))
        })
    })
    // 订阅redis收到消息后,执行websocket的消息推送客户端
    clientSubscribe.on('message', (channel, message) => {
        io.emit('message', JSON.parse(message))
    })
}
module.exports = websocket

websocket使用模式

-   单播:点对点 私信私聊
-   多播:也叫组播(特定人群) 多人聊天,发布订阅
-   广播:游戏公告
如果你使用Node.js做服务端,那么该选择Socket.IO
目录
相关文章
|
前端开发 JavaScript 定位技术
threejs绘制风羽
threejs绘制风羽
787 0
|
Java 关系型数据库 MySQL
高校宿舍报修管理系统的设计与实现(论文+源码)_kaic
高校宿舍报修管理系统的设计与实现(论文+源码)_kaic
|
移动开发 前端开发 JavaScript
Twaver-HTML5基础学习(12)连线(Link)
本文介绍了Twaver HTML5中的连线(Link)元素,包括设置起始和结束节点的方法,以及如何管理和操作多个连线。通过示例代码展示了如何在React组件中创建和管理Link,包括设置连线颜色和标签偏移量。
291 2
Twaver-HTML5基础学习(12)连线(Link)
|
JSON Dart Android开发
Flutter 2024: Impeller引擎引领渲染新纪元
Flutter 2024以Impeller引擎引领渲染新时代,全面提升性能与流畅度。Impeller已在iOS及Android(支持Vulkan/OpenGL)全面部署,Material 3集成深化视觉体验,多视图支持增强复杂UI管理。Dart 3.2与3.4版本迭代优化语言特性与性能,引入宏编程简化JSON处理。桌面与Web端持续优化,深化平台适配。
653 14
|
存储 弹性计算 对象存储
阿里云对象存储OSS的预留空间是指什么?
阿里云OSS预留空间是预付费存储产品,提供成本优化,通过锁定存储容量来享受折扣。它仅抵扣标准存储(本地冗余)和ECS快照费用。例如,为节省600GB存储成本,可购买500GB通用预留空间和100GB标准-本地冗余存储包。
547 1
|
缓存 前端开发 JavaScript
一些有效的方法来加快网站的加载速度
【10月更文挑战第8天】一些有效的方法来加快网站的加载速度
484 62
|
Docker 容器
docker设置国内镜像源
docker设置国内镜像源
37675 5
|
编译器 C语言
C语言中的浮点数:深入探索与应用
C语言中的浮点数:深入探索与应用
2311 1
|
开发框架 前端开发 JavaScript
跨平台应用开发技术的深度探讨
【7月更文挑战第26天】 跨平台应用开发技术已成为当前软件开发领域的重要趋势。通过合理使用跨平台开发框架和工具,开发者可以更加高效地构建适用于多个平台的应用程序,提高开发效率和用户体验。然而,跨平台开发也面临着性能优化、兼容性问题等挑战,需要开发者不断学习和实践,以应对不断变化的市场需求和技术挑战。