在现代网络应用中,流媒体传输变得越来越重要,特别是在实时视频应用、直播和监控等领域。通过 RTSP 或 RTMP 协议获取视频流,并将其转换为 WebSocket 格式,以便在前端浏览器中播放,是一个非常实用的需求。本文将介绍如何使用 Node.js 和 FFmpeg 来实现这个过程。
环境准备
首先,你需要安装 Node.js 和 FFmpeg。在 Ubuntu 系统中可以通过以下命令安装 FFmpeg:
sudo apt update
sudo apt install ffmpeg
接下来,确保你已经安装了 Node.js。你可以通过 Node.js 官方网站下载并安装,或者使用包管理器安装。
创建项目
创建一个新的 Node.js 项目:
mkdir stream-server
cd stream-server
npm init -y
npm install ws child_process
这里我们使用 ws
作为 WebSocket 的库,使用 child_process
模块来执行 FFmpeg 命令。
编写代码
我们将编写一个简单的 Node.js 脚本,通过 WebSocket 将 RTSP/RTMP 流发送到前端。
const WebSocket = require('ws');
const { spawn } = require('child_process');
const rtspUrl = 'rtsp://your_rtsp_source';
const rtmpUrl = 'rtmp://your_rtmp_source';
const wss = new WebSocket.Server({ port: 8080 });
wss.on('connection', (ws) => {
console.log('Client connected');
// 启动 FFmpeg 进程
const ffmpeg = spawn('ffmpeg', [
'-i', rtspUrl, // 输入rtsp流
'-f', 'mpegts', // 输出格式
'pipe:1' // 输出到标准输出
]);
// 当 FFmpeg 进程有数据传输时,将数据通过 WebSocket 发送给前端
ffmpeg.stdout.on('data', (data) => {
if (ws.readyState === WebSocket.OPEN) {
ws.send(data);
}
});
// 错误处理
ffmpeg.stderr.on('data', (data) => {
console.error(`FFmpeg error: ${data}`);
});
// 进程结束时关闭 WebSocket
ffmpeg.on('close', (code) => {
console.log(`FFmpeg process exited with code ${code}`);
ws.close();
});
// 客户端关闭时处理
ws.on('close', () => {
console.log('Client disconnected');
ffmpeg.kill('SIGINT'); // 关闭FFmpeg进程
});
});
console.log('WebSocket server is running on ws://localhost:8080/');
代码说明
- 导入依赖:我们导入了
ws
和child_process
模块。 - 创建 WebSocket 服务器:监听客户端的连接。
- 启动 FFmpeg 进程:通过
spawn
启动 FFmpeg,将 RTSP 视频流转换为 MPEG-TS 格式,并将输出流发送到 WebSocket。 - 数据传输:使用
ffmpeg.stdout.on('data')
监听 FFmpeg 的输出数据,并通过 WebSocket 将数据转发给连接的客户端。 - 错误处理:监听 FFmpeg 的错误输出。
- 关闭处理:当客户端断开连接时,关闭 FFmpeg 进程。
前端播放
在前端,你可以使用 HTML5 的 <video>
标签来播放流媒体。以下是一个简单的示例:
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>RTSP/RTMP Stream</title>
</head>
<body>
<video id="video" controls autoplay></video>
<script>
const video = document.getElementById('video');
const ws = new WebSocket('ws://localhost:8080/');
ws.binaryType = 'arraybuffer';
ws.onmessage = (event) => {
const blob = new Blob([event.data], { type: 'video/mp2t' });
const url = URL.createObjectURL(blob);
video.src = url;
};
</script>
</body>
</html>
总结
通过以上步骤,我们成功地将 RTSP 或 RTMP 流转换为 WebSocket 格式,并在前端实现了视频播放。这个示例提供了一个基本的实现,可以根据实际需求进行扩展,比如支持多个流、加入错误处理机制等。希望这篇文章能够为你在流媒体应用开发中提供帮助。