使用ffmpeg+flv.js + websokect播放rtsp格式视频流

对于rtsp的视频流网上有很多种的解决方案,但是大的趋势还是利用ffmpeg的工具进行rtsp的视频解析进行一个推流,我最终选择bilibili开源的flv.js,代码十分的简单全部都在底层封装好了。实现的方式也比较容易理解,ffmpeg进行rtsp的视频流解析转为flv视频流通过websocket通信把flv的流推给前端。其中两个地方比较坑需要注意linux搭建ffmpeg比较麻烦 ,一定要安装编译后的版本,不能取源码。

一、搭建服务端

1、安装node

服务端主要是用node运行解析rtsp转为flv的服务。安装过程并不多说了。

2、安装ffmpeg

  • Linux:这里由于不是我安装的,后续补充...................
  • windows:网盘连接:提取码8888 直接解压这个文件,配置环境变量 Path,加入D:\flvWbsockectPlayRESP\ffmpeg\bin,在cmd中输入ffmpeg出现版本信息等说明配置成功了

3、搭建后端服务

找一个文件夹创建一个package.json文件,将下面代码粘入

复制代码
{
  "name": "ffmpeg-server",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "ISC",
  "devDependencies": {
    "express": "^4.17.1",
    "express-ws": "^4.0.0",
    "ffmpeg": "0.0.4",
    "fluent-ffmpeg": "^2.1.2",
    "http": "0.0.0",
    "websocket-stream": "^5.5.0"
  }
}

然后再此文件夹运行upm install,服务器的环境搭建好了,在此文件夹创建一个index.js文件把下面代码粘入

复制代码
 var express = require("express");
    var expressWebSocket = require("express-ws");
    var ffmpeg = require("fluent-ffmpeg");
    ffmpeg.setFfmpegPath("D:/Gsafety/project-demo/flvWbsockectPlayRESP/ffmpeg/bin/ffmpeg");// 这里的目录指向先前安装好的ffmpeg
    var webSocketStream = require("websocket-stream/stream");
    var WebSocket = require("websocket-stream");
    var http = require("http");
    function localServer() {
        let app = express();
        app.use(express.static(__dirname));
        expressWebSocket(app, null, {
            perMessageDeflate: true
        });
        app.ws("/rtsp/:id/", rtspRequestHandle)
        app.listen(8888);//进行websocket通信的服务端端口
        console.log("express listened")
    }
    function rtspRequestHandle(ws, req) {
        console.log("rtsp request handle");
        const stream = webSocketStream(ws, {
            binary: true,
            browserBufferTimeout: 1000000
        }, {
            browserBufferTimeout: 1000000
        });
        let url = req.query.url;
        console.log("rtsp url:", url);
        console.log("rtsp params:", req.params);
        try {
            ffmpeg(url)
                .addInputOption("-rtsp_transport", "tcp", "-buffer_size", "102400") // 这里可以添加一些 RTSP 优化的参数
                .on("start", function () {
                    console.log(url, "Stream started.");
                })
                .on("codecData", function () {
                    console.log(url, "Stream codecData.")// 摄像机在线处理
                })
                .on("error", function (err) {
                    console.log(url, "An error occured: ", err.message);
                })
                .on("end", function () {
                    console.log(url, "Stream end!");// 摄像机断线的处理
                })
                .outputFormat("flv").videoCodec("copy").noAudio().pipe(stream);
        } catch (error) {
            console.log(error);
        }
    }
    localServer();

在此文件cmd的窗口运行node.js,如果打印日志出现express listened,这样服务端就搭建成功了

【免费分享】音视频学习资料包、大厂面试题、技术视频和学习路线图,资料包括(C/C++,Linux,FFmpeg webRTC rtmp hls rtsp ffplay srs 等等)有需要的可以点击788280672加群免费领取~

二、前端搭建

安装flv.js依赖

定义一个video来播放flv视频流的容器。

  • html代码:

ts代码:

复制代码
    private id='1';//websokect的通信id(自己定义一个,一个地址对应一个id)
    private rtsp= 'rtsp://wowzaec2demo.streamlock.net/vod/mp4:BigBuckBunny_115k.mov';//播放rtsp的地址
    private player:any= null;//播放的对象

    这里我在mounted的钩子函数中进行的播放操作

    if (flvjs.isSupported()) {
    let video = this.$refs.player;
    let videoUrl=publishObjectPath.value.videoUrl;
    if (video) {
        this.player = flvjs.createPlayer({
            type: "flv",
            isLive: true,
            url: videoUrl+`/rtsp/${this.id}/?url=${this.rtsp}`//这里的videoUrl我在json配置文件中进行配置连接的地址
        });
        this.player.attachMediaElement(video);
        try {
            this.player.load();
            this.player.play();  // 他还有很多的函数可以看一下flv.js的官方文档
        } catch (error) {
            console.log(error);
        };
    }
}

"videoUrl": "ws://172.20.0.188:8998/streamWs"  //streamWs是通过nginx进行代理  

三、搭建到互联网环境上,不在同一个服务器和不同网段需要使用nginx代理

复制代码
worker_processes  1;

events {
    worker_connections  1024;
}

http {
    include       mime.types;
    default_type  application/octet-stream;

    sendfile        on;
    keepalive_timeout  65;

    map $http_upgrade $connection_upgrade {
   default upgrade;
     ''  close;
    }

    server {
        listen       8998;
        server_name  localhost;
        location /streamWs/ {
            proxy_pass http://172.20.0.34:8888/;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_http_version 1.1;
            proxy_set_header Upgrade $http_upgrade;
            proxy_set_header Connection $connection_upgrade;
        }

    }

}

在配置proxy_pass的时候后面不加/,会将代理的字段再拼接上去这样你的接口是通的,但是不能进行通信,加上/才会把代理字段替换代理成你要代理的地址。这样线上就可以看到效果啦!

原文链接 使用ffmpeg+flv.js + websokect播放rtsp格式视频流

相关推荐
朝朝辞暮i12 分钟前
C++ 第 32 课:main()、rclcpp::init()、spin()、shutdown()
开发语言·c++·算法
旋生万物31 分钟前
螺旋角分布的功率谱分析:多窗谱 + FDR 校正
开发语言·python
沫璃染墨43 分钟前
《从零入门Linux系统篇(五十七):线程篇·十——生产者消费者模型进阶:从环形缓冲区到POSIX信号量》
linux·运维·服务器·开发语言·c++·系统架构·信号处理
时间的拾荒人1 小时前
Qt 窗口系统详解:从菜单栏到对话框的完整指南
开发语言·qt·面试
樱花落木兰1 小时前
分布式登录实战:Session 会话共享改造,Redis 存储用户登录状态
java·javascript·数据库·redis·分布式·缓存
wuyk5551 小时前
Python 网络爬虫入门到实战 第 04 章:请求头、UA 伪装、超时、异常处理、基础反爬绕过
开发语言·爬虫·python
流形填表1 小时前
题库去重实战:基于题干指纹的重复题清理
开发语言·c#
\光辉岁月/1 小时前
3.java运算符
java·开发语言
知识分享小能手1 小时前
C++ 学习教程,从入门到精通,string类和标准模板库 — 完整知识点详解(16)
开发语言·c++·学习
qq_401700411 小时前
Qt 炫酷曲线,图表,2D/3D开源库
开发语言·qt