概述
需求
通过接口调用,获取网络摄像头的 RTSP 推流 URL,需要播放此 RTSP 协议传输的视频流
解决方案
- 后端使用 ZLMediaKit 流媒体服务框架对 RTSP 视频流进行代理,输出 http-flv 直播地址
- 前端通过 flv.js 播放上述视频
相关资源
可以播放的 rtsp 地址
-
可以播放 rtsp 软件:VLC
flv.js
An HTML5 Flash Video (FLV) Player written in pure JavaScript without Flash.
FLV 支持格式
Installation
yarn add -D flv.js
Get Started
<script src="flv.min.js"></script>
<video id="videoElement"></video>
<script>
if (flvjs.isSupported()) {
var videoElement = document.getElementById('videoElement');
var flvPlayer = flvjs.createPlayer({
type: 'flv',
url: 'http://example.com/flv/video.flv'
});
flvPlayer.attachMediaElement(videoElement);
flvPlayer.load();
flvPlayer.play();
}
</script>
ZLMediaKit 流媒体服务
RESTful 接口
addStreamProxy
动态添加 rtsp | rtmp | hls 拉流代理。只支持 H264 | H265 | AAC | G711 负载
- 参数注意点:
- secret => 使用默认 secret(035c73f7-bb6b-4889-a715-d9eb2d1925cc),也可以通过 getServerConfig 接口获取
- stream => 因有多个视频流,故使用了 randomString
function randomString() { const number = 32; let t = 'ABCDEFGHJKMNPQRSTWXYZabcdefhijkmnprstwxyz2345678', a = t.length, n = ''; for (let i = 0; i < number; i++) n += t.charAt(Math.floor(Math.random() * a)); return n; }
- rtp_type => 根据具体的拉流方式设置
- Response
返回的key
是流的唯一标识,用于 delStreamProxy 接口
delStreamProxy
播放 URL 组成部分
以 rtsp://somedomain.com:554/live/0?token=abcdefg&field=value
-
scheam
=> 协议 => rtsp 协议,默认端口 554 -
vhost
=> 虚拟主机 => somedomain.com,该字段既可以值域名也可以是ip,如果是 ip 则对应的虚拟主机为__defaultVhost__
-
port
=> 服务端口号 => 554,如果不指定端口号,则使用协议默认端口号 -
app
=> 应用名 => live -
streamid
=> 流 ID => 0 -
args
=> 参数 => token=abcdefg&field=value
通过 流媒体源对应的播放 URL可知一个 http-flv 的地址 => http://<vhost>/<app>/<streamid>.flv
addStreamProxy response key => <vhost>/<app>/<streamid>
=> 根据 addStreamProxy response key 得到 http-flv 播放地址 => http://${key}.flv
docker ZLMediaKit
通过 docker 启动 ZLMediaKit 服务
docker pull panjjo/zlmediakit
在 ZLMediaKit 配置文件中详细描述了相关服务器监听端口,flv.js 使用 http 服务器,原视频流是 RTSP 服务器,故端口映射为
// http 服务器监听端口 => 80 => 本地 8080 映射 ZLMediaKit 80 端口
// RTSP 服务器监听端口 => 554 => 本地 8554 映射 ZLMediaKit 554 端口
docker run -id -p 8080:80 -p 8554:554 panjjo/zlmediakit
Postman 测试 docker ZLMediaKit 服务
通过Postman 配置文件导入即可以测试服务
注意点
- 通过 docker ZLMediaKit 流媒体服务拿到 HTTP 链接后,直接放入 flv.js 中进行播放,有一定的概率失败,此时可以先通过 接口调用 GET 一下此 HTTP 链接
// flvjs fetch(<httpFlvUrl>) flvPlayer = flvjs.createPlayer({ type: 'flv', url: <httpFlvUrl> });
-
flvPlayer.play();
的返回值类型是Promise<void> | void
。可以利用 Promise 清除 Loading 效果,毕竟flvPlayer.load();
和flvPlayer.play();
需要一定的时间addLoading(); // do something flvPlayer.play().then(() => { clearLoading(); });
- ERROR: Unsupported audio codec idx: "12"
此处和上面 flvjs 的 audio 支持格式遥相呼应。此时使用try catch
捕获错误即可let flvPlayer = null; try { if (flvJs.isSupported()) { // do something } } catch (e) { console.error(e); flvPlayer = null; }
- 播放 RTSP 视频时静音
flvPlayer = flvJs.createPlayer({ hasAudio: false, // other Attribute });
- flv.js 支持的 Video 格式 => RTSP 视频流解码格式需要为 H.264