1717 lines
57 KiB
Markdown
1717 lines
57 KiB
Markdown
# GoWVP (Owl) + ZLMediaKit 飞腾S5000 + 统信UOS20 离线部署手册
|
||
|
||
> **文档版本**: v1.2
|
||
> **生成日期**: 2026-04-29
|
||
> **适用环境**: 飞腾S5000C (ARM64) + 统信UOS20服务器版(1070) + 离线网络
|
||
> **目标系统**: ARM64 (aarch64) / ARMv8.2
|
||
|
||
---
|
||
|
||
## 更新记录
|
||
|
||
| 版本号 | 更新人 | 更新日期/时间 | 更新内容 |
|
||
|--------|--------|---------------|----------|
|
||
| v1.0 | 浮浮酱 | 2026-04-29 | 初始版本,生成完整离线部署手册 |
|
||
| v1.1 | 浮浮酱 | 2026-04-29 | 1. 更新 Docker 版本建议(25.0.5 → 27.5.1/28.5.2/29.4.1)<br>2. 新增 8.7 ARM64 稳定性问题深度分析(含 Issue #3466/#3202/#2728/#2043)<br>3. 新增附录 F:ARM64 架构问题速查表 |
|
||
| v1.2 | 浮浮酱 | 2026-04-29 | 1. 明确 Intel/x86_64 笔记本可通过 Docker Desktop 完成全套 ARM64 准备工作<br>2. 4.2.1/4.2.3 节添加 `--platform linux/arm64` 参数说明和 `docker save --platform` 注意事项<br>3. 4.4 节添加通过 ARM64 Docker 容器下载系统依赖包的替代方案(无需额外 ARM 服务器) |
|
||
|
||
---
|
||
|
||
## 目录
|
||
|
||
### 一级导航
|
||
|
||
1. [文档概述](#一文档概述)
|
||
2. [环境说明](#二环境说明)
|
||
3. [资源清单](#三资源清单)
|
||
4. [联网笔记本准备工作](#四联网笔记本准备工作)
|
||
5. [生产环境服务器部署](#五生产环境服务器部署)
|
||
6. [配置联动](#六配置联动)
|
||
7. [验证步骤](#七验证步骤)
|
||
8. [常见问题排查](#八常见问题排查)
|
||
9. [附录](#九附录)
|
||
|
||
### 二级导航
|
||
|
||
**一、文档概述**
|
||
- [1.1 部署架构](#11-部署架构)
|
||
- [1.2 部署方式选择](#12-部署方式选择)
|
||
|
||
**二、环境说明**
|
||
- [2.1 硬件环境](#21-硬件环境)
|
||
- [2.2 软件环境](#22-软件环境)
|
||
- [2.3 统信UOS版本确认方法](#23-统信uos版本确认方法)
|
||
- [2.4 网络环境](#24-网络环境)
|
||
|
||
**三、资源清单**
|
||
- [3.1 Docker 镜像文件](#31-docker-镜像文件)
|
||
- [3.2 可执行文件与源码包](#32-可执行文件与源码包)
|
||
- [3.3 系统依赖包(需根据包管理器类型准备)](#33-系统依赖包需根据包管理器类型准备)
|
||
- [3.4 配置文件与脚本](#34-配置文件与脚本)
|
||
|
||
**四、联网笔记本准备工作**
|
||
- [4.1 安装 Docker Desktop](#41-安装-docker-desktop)
|
||
- [4.2 拉取并导出 Docker 镜像](#42-拉取并导出-docker-镜像)
|
||
- [4.3 下载源码包与二进制文件](#43-下载源码包与二进制文件)
|
||
- [4.4 准备系统依赖包(离线安装用)](#44-准备系统依赖包离线安装用)
|
||
- [4.5 准备配置文件](#45-准备配置文件)
|
||
- [4.6 打包所有文件](#46-打包所有文件)
|
||
|
||
**五、生产环境服务器部署**
|
||
- [5.1 确认系统版本和包管理器](#51-确认系统版本和包管理器)
|
||
- [5.2 安装 Docker(离线)](#52-安装docker离线)
|
||
- [5.3 加载 Docker 镜像并启动](#53-加载-docker-镜像并启动)
|
||
- [5.4 部署 ZLMediaKit(单独运行方式)](#54-部署-zlmediakit单独运行方式)
|
||
- [5.5 部署 GoWVP(Owl)(单独运行方式)](#55-部署-gowvp-owl单独运行方式)
|
||
- [5.6 配置联动](#56-配置联动)
|
||
|
||
**六、配置联动**
|
||
|
||
**七、验证步骤**
|
||
- [7.1 验证脚本](#71-验证脚本)
|
||
- [7.2 手动验证步骤](#72-手动验证步骤)
|
||
- [7.3 推流测试](#73-推流测试)
|
||
|
||
**八、常见问题排查**
|
||
- [8.1 Docker 无法启动](#81-docker-无法启动)
|
||
- [8.2 容器启动后立即退出](#82-容器启动后立即退出)
|
||
- [8.3 ARM64 镜像无法运行](#83-arm64-镜像无法运行)
|
||
- [8.4 GoWVP 无法连接 ZLMediaKit](#84-gowvp-无法连接-zlmediakit)
|
||
- [8.5 GB28181 设备无法接入](#85-gb28181-设备无法接入)
|
||
- [8.6 性能问题](#86-性能问题)
|
||
- [8.7 ARM64 架构稳定性问题(重要)](#87-arm64-架构稳定性问题重要)
|
||
|
||
**九、附录**
|
||
- [附录A: 端口清单](#附录a端口清单)
|
||
- [附录B: 源码编译 ZLMediaKit(备用方案)](#附录b源码编译-zlmediakit备用方案)
|
||
- [附录C: 源码编译 GoWVP(备用方案)](#附录c源码编译-gowvp备用方案)
|
||
- [附录D: 防火墙配置](#附录d防火墙配置)
|
||
- [附录E: 参考链接](#附录e参考链接)
|
||
- [附录F: ARM64 架构问题速查表](#附录farm64-架构问题速查表)
|
||
|
||
---
|
||
|
||
## 一、文档概述
|
||
|
||
本手册指导您在**完全离线的生产环境**中,于**飞腾S5000C ARM64服务器**(统信UOS20操作系统)上完成以下部署:
|
||
|
||
- **GoWVP (Owl)**: GB28181-2022 标准视频监控管理平台
|
||
- **ZLMediaKit**: 高性能流媒体服务器
|
||
- **联动配置**: 让 Owl 通过 HTTP API 和 WebHook 调用 ZLMediaKit 的流媒体能力
|
||
|
||
### 1.1 部署架构
|
||
|
||
```
|
||
┌─────────────────────────────────────────────────────────────┐
|
||
│ 监控设备 (摄像头/NVR) │
|
||
│ ┌──────────────┐ ┌──────────────┐ │
|
||
│ │ GB28181 │ │ ONVIF │ │
|
||
│ │ 协议接入 │ │ 协议接入 │ │
|
||
│ └──────┬───────┘ └──────┬───────┘ │
|
||
└─────────────────────┼─────────────────┼──────────────────────┘
|
||
│ │
|
||
▼ ▼
|
||
┌─────────────────────────────────────────────────────────────┐
|
||
│ 统信UOS20 服务器 (ARM64) │
|
||
│ ┌─────────────────────────────────────────────────────┐ │
|
||
│ │ Docker 容器运行时 │ │
|
||
│ │ ┌─────────────────┐ ┌───────────────────────┐ │ │
|
||
│ │ │ GoWVP (Owl) │◄──►│ ZLMediaKit │ │ │
|
||
│ │ │ 容器 │API │ 流媒体容器 │ │ │
|
||
│ │ │ │Hook│ │ │ │
|
||
│ │ │ - GB28181 SIP │ │ - RTMP/RTSP/HLS │ │ │
|
||
│ │ │ - Web管理界面 │ │ - WebRTC/FLV │ │ │
|
||
│ │ │ - 设备管理 │ │ - 录像/转码 │ │ │
|
||
│ │ │ - AI检测(YOLO) │ │ │ │ │
|
||
│ │ └─────────────────┘ └───────────────────────┘ │ │
|
||
│ └─────────────────────────────────────────────────────┘ │
|
||
│ 数据持久化卷 │
|
||
│ (./data 挂载到容器内的 /opt/media/bin/configs) │
|
||
└─────────────────────────────────────────────────────────────┘
|
||
```
|
||
|
||
### 1.2 部署方式选择
|
||
|
||
| 方案 | 说明 | 推荐度 | 适用场景 |
|
||
|------|------|--------|----------|
|
||
| **方案A: Docker Compose 融合部署** | 一个docker-compose.yml同时启动owl+ZLMediaKit | ⭐⭐⭐⭐⭐ | **本手册推荐,最简单** |
|
||
| **方案B: Docker 分离部署** | 两个独立容器,通过Docker网络通信 | ⭐⭐⭐⭐ | 需要独立升级/维护时 |
|
||
| **方案C: 二进制直接部署** | 不依赖Docker,直接运行可执行文件 | ⭐⭐⭐ | 服务器资源极度受限时 |
|
||
|
||
> **本手册以方案A(Docker Compose 融合部署)为主**,同时提供方案B和C的备用说明。
|
||
|
||
---
|
||
|
||
## 二、环境说明
|
||
|
||
### 2.1 硬件环境
|
||
|
||
| 项目 | 规格 |
|
||
|------|------|
|
||
| **CPU** | 飞腾腾云 S5000C (Phytium S5000C) |
|
||
| **指令集** | ARMv8.2 (64位,兼容aarch64) |
|
||
| **核心数** | 16核 / 32核 / 64核 (根据采购型号) |
|
||
| **主频** | 2.1GHz (64核版) / 2.3GHz (32/16核版) |
|
||
| **内存** | 建议 >= 16GB DDR5 |
|
||
| **存储** | 建议 >= 500GB SSD (用于录像存储) |
|
||
| **网络** | 千兆以太网 (用于GB28181流媒体和Web管理) |
|
||
|
||
### 2.2 软件环境
|
||
|
||
| 项目 | 规格 |
|
||
|------|------|
|
||
| **操作系统** | 统信UOS服务器版 V20 (1070) |
|
||
| **镜像文件名** | `uos-server-20-military-1070-20251016-arm64.iso` |
|
||
| **内核版本** | kernel-4.19 (默认) / kernel-5.10 (可选) |
|
||
| **包管理器** | **需确认**:可能是 `yum`(A/E版本) 或 `apt`(D版本) |
|
||
| **架构** | aarch64 / ARM64 |
|
||
|
||
### 2.3 统信UOS版本确认方法
|
||
|
||
在**生产环境服务器**上执行以下命令确认系统版本:
|
||
|
||
```bash
|
||
# 查看操作系统详细信息
|
||
cat /etc/os-release
|
||
|
||
# 查看系统版本标记
|
||
cat /etc/system-release 2>/dev/null || cat /etc/centos-release 2>/dev/null || cat /etc/debian_version 2>/dev/null
|
||
|
||
# 查看包管理器类型
|
||
which apt-get && echo "使用 apt (Debian系)"
|
||
which yum && echo "使用 yum (RHEL系)"
|
||
```
|
||
|
||
**判断依据:**
|
||
- 如果看到 `Anolis`、`openEuler`、`uel20` 等字样 -> **A/E版本,使用 `yum`**
|
||
- 如果看到 `Debian`、`Ubuntu` 等字样 -> **D版本,使用 `apt`**
|
||
- 1070军事版通常基于龙蜥/欧拉,**大概率使用 `yum/dnf`**
|
||
|
||
### 2.4 网络环境
|
||
|
||
| 环境 | 网络状态 | 用途 |
|
||
|------|----------|------|
|
||
| **联网笔记本** | 可访问互联网 | 下载镜像、准备部署包 |
|
||
| **生产服务器** | **完全离线** | 运行部署命令、启动服务 |
|
||
| **传输介质** | U盘/移动硬盘/内网FTP | 将文件从笔记本传到服务器 |
|
||
|
||
---
|
||
|
||
## 三、资源清单
|
||
|
||
本章节列出部署过程中所需的**所有文件**,包括文件名、下载地址、用途说明及使用步骤链接。
|
||
|
||
### 3.1 Docker 镜像文件
|
||
|
||
> **注意**: Docker镜像需要在**安装了Docker的联网机器**上拉取后导出,无法直接通过浏览器下载。
|
||
|
||
| 序号 | 文件名 | 下载方式 | 用途说明 | 使用章节 |
|
||
|------|--------|----------|----------|----------|
|
||
| 1 | `zlmediakit-master-arm64.tar` | `docker pull zlmediakit/zlmediakit:master` + `docker save` | ZLMediaKit 官方ARM64镜像 | [4.2节](#42-拉取并导出docker镜像) |
|
||
| 2 | `gowvp-latest-arm64.tar` | `docker pull gospace/gowvp:latest` + `docker save` | GoWVP (Owl) 官方ARM64镜像 | [4.2节](#42-拉取并导出docker镜像) |
|
||
| 3 | `registry-2.tar` | `docker pull registry:2` + `docker save` | Docker私有镜像仓库(可选,方便内网分发) | [4.2节](#42-拉取并导出docker镜像) |
|
||
|
||
### 3.2 可执行文件与源码包
|
||
|
||
| 序号 | 文件名 | 下载地址 | 用途说明 | 使用章节 |
|
||
|------|--------|----------|----------|----------|
|
||
| 1 | `owl_linux_arm64.tar.gz` | https://github.com/gowvp/owl/releases/download/v1.3.0/owl_linux_arm64.tar.gz | GoWVP v1.3.0 ARM64预编译二进制 | [5.5节](#55-部署gowvp-owl) / 备用方案C |
|
||
| 2 | `ZLMediaKit-master.zip` | https://github.com/ZLMediaKit/ZLMediaKit/archive/refs/heads/master.zip | ZLMediaKit 最新源码(含子模块需单独初始化) | [5.4节](#54-部署zlmediakit) / 备用方案C |
|
||
| 3 | `docker-27.5.1.tgz` | https://download.docker.com/linux/static/stable/aarch64/docker-27.5.1.tgz | Docker CE v27.5.1 ARM64离线安装包(推荐) | [5.2节](#52-安装docker离线) |
|
||
| 3b | `docker-28.5.2.tgz` | https://download.docker.com/linux/static/stable/aarch64/docker-28.5.2.tgz | Docker CE v28.5.2 ARM64离线安装包(较新) | [5.2节](#52-安装docker离线) |
|
||
| 3c | `docker-29.4.1.tgz` | https://download.docker.com/linux/static/stable/aarch64/docker-29.4.1.tgz | Docker CE v29.4.1 ARM64离线安装包(最新) | [5.2节](#52-安装docker离线) |
|
||
| 4 | `docker-compose-linux-aarch64` | https://github.com/docker/compose/releases/download/v2.29.1/docker-compose-linux-aarch64 | Docker Compose v2.29.1 ARM64二进制 | [5.2节](#52-安装docker离线) |
|
||
| 5 | `libsrtp-2.5.0.tar.gz` | https://github.com/cisco/libsrtp/archive/refs/tags/v2.5.0.tar.gz | SRTP库源码(WebRTC功能必需,版本必须严格为2.5.0) | [附录B](#附录b源码编译zlmediakit) |
|
||
|
||
### 3.3 系统依赖包(需根据包管理器类型准备)
|
||
|
||
#### 3.3.1 若系统使用 `yum` (A/E版本 - 龙蜥/欧拉)
|
||
|
||
| 序号 | 包名 | 下载方式 | 用途说明 | 使用章节 |
|
||
|------|------|----------|----------|----------|
|
||
| 1 | `docker-ce-*.aarch64.rpm` | `yumdownloader --resolve docker-ce` | Docker引擎 | [5.2节](#52-安装docker离线) |
|
||
| 2 | `docker-ce-cli-*.aarch64.rpm` | `yumdownloader --resolve docker-ce-cli` | Docker客户端 | [5.2节](#52-安装docker离线) |
|
||
| 3 | `containerd.io-*.aarch64.rpm` | `yumdownloader --resolve containerd.io` | 容器运行时 | [5.2节](#52-安装docker离线) |
|
||
| 4 | `openssl-devel-*.aarch64.rpm` | `yumdownloader --resolve openssl-devel` | SSL开发库(ZLMediaKit必需) | [附录B](#附录b源码编译zlmediakit) |
|
||
| 5 | `libssl3-*.aarch64.rpm` | 系统ISO或 `yumdownloader` | SSL运行时库 | [5.4节](#54-部署zlmediakit) |
|
||
|
||
#### 3.3.2 若系统使用 `apt` (D版本 - Debian)
|
||
|
||
| 序号 | 包名 | 下载方式 | 用途说明 | 使用章节 |
|
||
|------|------|----------|----------|----------|
|
||
| 1 | `docker.io_*.deb` | `apt-get download docker.io` | Docker引擎 | [5.2节](#52-安装docker离线) |
|
||
| 2 | `libssl-dev_*.deb` | `apt-get download libssl-dev` | SSL开发库 | [附录B](#附录b源码编译zlmediakit) |
|
||
| 3 | `openssl_*.deb` | `apt-get download openssl` | SSL工具 | [5.4节](#54-部署zlmediakit) |
|
||
| 4 | `ca-certificates_*.deb` | `apt-get download ca-certificates` | CA证书 | [5.2节](#52-安装docker离线) |
|
||
|
||
### 3.4 配置文件与脚本
|
||
|
||
| 序号 | 文件名 | 来源 | 用途说明 | 使用章节 |
|
||
|------|--------|------|----------|----------|
|
||
| 1 | `docker-compose.yml` | 本手册 [4.5节](#45-准备配置文件) | Docker Compose 融合部署配置 | [5.3节](#53-加载docker镜像并启动) |
|
||
| 2 | `config.ini` | ZLMediaKit官方模板修改 | ZLMediaKit 配置文件 | [5.4节](#54-部署zlmediakit) |
|
||
| 3 | `install-docker.sh` | 本手册 [5.2节](#52-安装docker离线) | Docker离线安装脚本 | [5.2节](#52-安装docker离线) |
|
||
| 4 | `setup.sh` | 本手册 [5.6节](#56-配置联动) | 一键初始化脚本 | [5.6节](#56-配置联动) |
|
||
| 5 | `verify.sh` | 本手册 [7.1节](#71-验证脚本) | 部署验证脚本 | [七、验证步骤](#七验证步骤) |
|
||
|
||
---
|
||
|
||
## 四、联网笔记本准备工作
|
||
|
||
> **本章节所有操作在可联网的笔记本/工作站上执行**,操作系统可以是 Windows 10/11、macOS 或 Linux。
|
||
|
||
### 4.1 安装 Docker Desktop
|
||
|
||
如果您的笔记本还没有安装Docker,请先安装:
|
||
|
||
**Windows 用户:**
|
||
1. 访问 https://www.docker.com/products/docker-desktop/
|
||
2. 下载并安装 Docker Desktop for Windows
|
||
3. 启动 Docker Desktop,确保左下角显示 "Docker Engine is running"
|
||
4. 打开 PowerShell 或 CMD,验证:
|
||
```powershell
|
||
docker --version
|
||
docker-compose --version
|
||
```
|
||
|
||
**Linux 用户(Ubuntu/Debian):**
|
||
```bash
|
||
# 安装Docker
|
||
sudo apt-get update
|
||
sudo apt-get install -y docker.io docker-compose
|
||
|
||
# 启动Docker
|
||
sudo systemctl start docker
|
||
sudo systemctl enable docker
|
||
|
||
# 验证
|
||
docker --version
|
||
docker-compose --version
|
||
```
|
||
|
||
### 4.2 拉取并导出 Docker 镜像
|
||
|
||
#### 4.2.1 拉取 ARM64 镜像
|
||
|
||
> 💡 **Intel/AMD 笔记本用户注意**:即使您的笔记本是 x86_64 架构,也可以通过 Docker Desktop 内置的 QEMU 模拟拉取 ARM64 镜像。Docker Desktop 4.34+ 默认使用 containerd image store,支持多架构镜像,**无需额外配置**。
|
||
|
||
```bash
|
||
# 拉取 ZLMediaKit 官方镜像(显式指定 ARM64 平台)
|
||
docker pull --platform linux/arm64 zlmediakit/zlmediakit:master
|
||
|
||
# 拉取 GoWVP (Owl) 官方镜像
|
||
docker pull --platform linux/arm64 gospace/gowvp:latest
|
||
|
||
# (可选)拉取私有镜像仓库,方便内网多台服务器分发
|
||
docker pull --platform linux/arm64 registry:2
|
||
```
|
||
|
||
> **为什么加 `--platform linux/arm64`?**
|
||
> - 在 x86_64 笔记本上,Docker 默认会拉取与宿主架构匹配的镜像(amd64)
|
||
> - 显式指定 `--platform linux/arm64` 确保拉取的是 ARM64 版本
|
||
> - 这是**必须**的,否则导出的是 x86_64 镜像,无法在飞腾 S5000C 上运行
|
||
|
||
**国内网络加速(如拉取缓慢):**
|
||
```bash
|
||
# 使用华为云镜像加速 ZLMediaKit
|
||
docker pull swr.cn-north-4.myhuaweicloud.com/ddn-k8s/docker.io/zlmediakit/zlmediakit:master-linuxarm64
|
||
docker tag swr.cn-north-4.myhuaweicloud.com/ddn-k8s/docker.io/zlmediakit/zlmediakit:master-linuxarm64 zlmediakit/zlmediakit:master
|
||
|
||
# 使用阿里云镜像加速 GoWVP
|
||
docker pull registry.cn-shanghai.aliyuncs.com/ixugo/homenvr:latest
|
||
docker tag registry.cn-shanghai.aliyuncs.com/ixugo/homenvr:latest gospace/gowvp:latest
|
||
```
|
||
|
||
#### 4.2.2 验证镜像架构
|
||
|
||
```bash
|
||
# 确认镜像是 ARM64 架构
|
||
docker inspect zlmediakit/zlmediakit:master | grep Architecture
|
||
# 预期输出: "Architecture": "arm64"
|
||
|
||
docker inspect gospace/gowvp:latest | grep Architecture
|
||
# 预期输出: "Architecture": "arm64"
|
||
```
|
||
|
||
#### 4.2.3 导出镜像为 tar 文件
|
||
|
||
> ⚠️ **关键注意事项**:Docker Desktop 4.34+ 默认使用 **containerd image store**。在 containerd 模式下,直接 `docker save` 非宿主架构(ARM64)镜像可能会报错:`no suitable export target found`。必须使用 `--platform` 参数显式指定。
|
||
|
||
```bash
|
||
# 创建输出目录
|
||
mkdir -p /owl_zlmediakit/docker-images
|
||
|
||
# 导出 ZLMediaKit 镜像(约 300-700MB)
|
||
# 必须加 --platform linux/arm64,否则在 containerd store 下会失败
|
||
docker save --platform linux/arm64 \
|
||
-o /owl_zlmediakit/docker-images/zlmediakit-master-arm64.tar \
|
||
zlmediakit/zlmediakit:master
|
||
|
||
# 导出 GoWVP 镜像(约 200MB)
|
||
docker save --platform linux/arm64 \
|
||
-o /owl_zlmediakit/docker-images/gowvp-latest-arm64.tar \
|
||
gospace/gowvp:latest
|
||
|
||
# (可选)导出私有仓库镜像
|
||
docker save --platform linux/arm64 \
|
||
-o /owl_zlmediakit/docker-images/registry-2.tar \
|
||
registry:2
|
||
|
||
# 验证导出文件
|
||
ls -lh /owl_zlmediakit/docker-images/
|
||
```
|
||
|
||
> **如果 `docker save --platform` 仍报错**,可尝试以下替代方案:
|
||
> ```bash
|
||
> # 方案A:使用 docker build 创建一个可保存的临时镜像
|
||
> docker build --platform linux/arm64 --tag temp-zlm-arm64 -f - . <<'EOF'
|
||
> FROM zlmediakit/zlmediakit:master
|
||
> EOF
|
||
> docker save -o zlmediakit-master-arm64.tar temp-zlm-arm64
|
||
>
|
||
> # 方案B:在 Docker Desktop 设置中临时切换回 Classic image store
|
||
> # Settings → Features in development → 关闭 "Use containerd for pulling and storing images"
|
||
> # 切换后重启 Docker Desktop,重新拉取镜像后再保存
|
||
> ```
|
||
|
||
> **速度提示**: 如果笔记本是 x86_64 (Intel/AMD) 架构,Docker Desktop 通过 **QEMU 模拟**拉取和导出 ARM64 镜像,速度比原生慢 10-50 倍。如果笔记本也是 ARM64(如 MacBook M1/M2/M3),则速度快得多。
|
||
|
||
### 4.3 下载源码包与二进制文件
|
||
|
||
#### 4.3.1 下载 GoWVP 预编译二进制(备用方案)
|
||
|
||
```bash
|
||
mkdir -p /owl_zlmediakit/source-packages
|
||
|
||
# 下载 GoWVP v1.3.0 ARM64 预编译包
|
||
wget -O /owl_zlmediakit/source-packages/owl_linux_arm64.tar.gz \
|
||
https://github.com/gowvp/owl/releases/download/v1.3.0/owl_linux_arm64.tar.gz
|
||
|
||
# 验证下载
|
||
ls -lh /owl_zlmediakit/source-packages/owl_linux_arm64.tar.gz
|
||
```
|
||
|
||
#### 4.3.2 下载 ZLMediaKit 源码(备用方案)
|
||
|
||
```bash
|
||
# 下载 ZLMediaKit 最新源码
|
||
wget -O /owl_zlmediakit/source-packages/ZLMediaKit-master.zip \
|
||
https://github.com/ZLMediaKit/ZLMediaKit/archive/refs/heads/master.zip
|
||
|
||
# 或者使用 git 克隆(推荐,包含完整历史)
|
||
git clone --depth 1 https://github.com/ZLMediaKit/ZLMediaKit.git /tmp/ZLMediaKit
|
||
cd /tmp/ZLMediaKit
|
||
git submodule update --init --recursive
|
||
tar czf /owl_zlmediakit/source-packages/ZLMediaKit-master-with-submodules.tar.gz .
|
||
|
||
# 验证
|
||
ls -lh /owl_zlmediakit/source-packages/ZLMediaKit*
|
||
```
|
||
|
||
#### 4.3.3 下载 Docker 离线安装包(ARM64)
|
||
|
||
```bash
|
||
mkdir -p /owl_zlmediakit/deb-packages
|
||
|
||
# ============================================
|
||
# Docker 版本选择建议:
|
||
# - 稳妥首选: 27.5.1 (最后一个传统存储驱动稳定版,国产系统兼容性最佳)
|
||
# - 平衡之选: 28.5.2 (较新但已过磨合期)
|
||
# - 追新: 29.4.1 (最新版,但默认启用containerd image store)
|
||
# ============================================
|
||
|
||
# 下载 Docker CE ARM64 静态二进制包(推荐 27.5.1)
|
||
wget -O /owl_zlmediakit/deb-packages/docker-27.5.1.tgz \
|
||
https://download.docker.com/linux/static/stable/aarch64/docker-27.5.1.tgz
|
||
|
||
# 或者下载较新版本(如需)
|
||
# wget -O /owl_zlmediakit/deb-packages/docker-28.5.2.tgz \
|
||
# https://download.docker.com/linux/static/stable/aarch64/docker-28.5.2.tgz
|
||
|
||
# 下载 Docker Compose ARM64
|
||
wget -O /owl_zlmediakit/deb-packages/docker-compose-linux-aarch64 \
|
||
https://github.com/docker/compose/releases/download/v2.29.1/docker-compose-linux-aarch64
|
||
|
||
# 验证
|
||
ls -lh /owl_zlmediakit/deb-packages/
|
||
```
|
||
|
||
#### 4.3.4 下载 WebRTC 依赖(如需源码编译)
|
||
|
||
```bash
|
||
# 下载 libsrtp 2.5.0(版本必须严格匹配,v2.3.0和v2.6+都有兼容性问题)
|
||
wget -O /owl_zlmediakit/source-packages/libsrtp-2.5.0.tar.gz \
|
||
https://github.com/cisco/libsrtp/archive/refs/tags/v2.5.0.tar.gz
|
||
|
||
# 验证
|
||
ls -lh /owl_zlmediakit/source-packages/libsrtp-2.5.0.tar.gz
|
||
```
|
||
|
||
### 4.4 准备系统依赖包(离线安装用)
|
||
|
||
#### 4.4.1 若目标系统使用 `yum` (A/E版本)
|
||
|
||
**方案 A:在 Intel 笔记本上通过 ARM64 Docker 容器下载(推荐,无需额外 ARM 服务器)**
|
||
|
||
> 💡 **原理**:在 x86_64 笔记本上运行 `--platform linux/arm64` 的容器,容器内的 `yumdownloader` 会自动下载 ARM64 架构的 rpm 包。
|
||
|
||
```bash
|
||
# 1. 启动 ARM64 CentOS/Anolis 容器(通过 QEMU 模拟运行)
|
||
docker run -it --name arm64-yum-downloader --platform linux/arm64 \
|
||
-v /owl_zlmediakit/deb-packages/yum-deps:/output \
|
||
arm64v8/centos:8 bash
|
||
|
||
# 2. 在容器内下载 ARM64 版本的 rpm 包
|
||
yum install -y yum-utils
|
||
yumdownloader --resolve --destdir=/output \
|
||
docker-ce docker-ce-cli containerd.io wget curl vim net-tools telnet
|
||
|
||
# 3. 退出容器,包已在 /owl_zlmediakit/deb-packages/yum-deps/ 中
|
||
exit
|
||
|
||
# 4. 清理容器
|
||
docker rm arm64-yum-downloader
|
||
```
|
||
|
||
**方案 B:在另一台联网的 ARM64 服务器上执行(传统方式)**
|
||
|
||
如果您有另一台同版本联网的统信UOS/龙蜥/欧拉 ARM64 机器:
|
||
|
||
```bash
|
||
mkdir -p /owl_zlmediakit/deb-packages/yum-deps
|
||
|
||
# 安装 yum-utils(用于下载依赖)
|
||
sudo yum install -y yum-utils
|
||
|
||
# 下载 Docker 及相关依赖(包括所有依赖项)
|
||
yumdownloader --resolve --destdir=/owl_zlmediakit/deb-packages/yum-deps \
|
||
docker-ce docker-ce-cli containerd.io
|
||
|
||
# 下载常用工具
|
||
yumdownloader --resolve --destdir=/owl_zlmediakit/deb-packages/yum-deps \
|
||
wget curl vim net-tools telnet
|
||
|
||
# 验证
|
||
ls -lh /owl_zlmediakit/deb-packages/yum-deps/
|
||
```
|
||
|
||
#### 4.4.2 若目标系统使用 `apt` (D版本)
|
||
|
||
**方案 A:在 Intel 笔记本上通过 ARM64 Docker 容器下载(推荐,无需额外 ARM 服务器)**
|
||
|
||
> 💡 **原理**:在 x86_64 笔记本上运行 `--platform linux/arm64` 的 Debian 容器,容器内的 `apt-get download` 会自动下载 ARM64 架构的 deb 包。
|
||
|
||
```bash
|
||
# 1. 启动 ARM64 Debian 容器(通过 QEMU 模拟运行)
|
||
docker run -it --name arm64-apt-downloader --platform linux/arm64 \
|
||
-v /owl_zlmediakit/deb-packages/apt-deps:/output \
|
||
arm64v8/debian:bookworm-slim bash
|
||
|
||
# 2. 在容器内下载 ARM64 版本的 deb 包
|
||
apt-get update
|
||
apt-get download docker.io libssl-dev openssl ca-certificates
|
||
apt-get download $(apt-cache depends --recurse --no-recommends --no-suggests \
|
||
--no-conflicts --no-breaks --no-replaces --no-enhances docker.io | grep "^\w")
|
||
apt-get download wget curl vim net-tools telnet
|
||
|
||
# 复制到挂载目录
|
||
cp /var/cache/apt/archives/*.deb /output/
|
||
|
||
# 3. 退出容器,包已在 /owl_zlmediakit/deb-packages/apt-deps/ 中
|
||
exit
|
||
|
||
# 4. 清理容器
|
||
docker rm arm64-apt-downloader
|
||
```
|
||
|
||
**方案 B:在另一台联网的 ARM64 服务器上执行(传统方式)**
|
||
|
||
如果您有另一台同版本联网的 Debian/Ubuntu ARM64 机器:
|
||
|
||
```bash
|
||
mkdir -p /owl_zlmediakit/deb-packages/apt-deps
|
||
|
||
# 更新包缓存
|
||
sudo apt-get update
|
||
|
||
# 下载 Docker 及相关依赖
|
||
cd /owl_zlmediakit/deb-packages/apt-deps
|
||
apt-get download docker.io
|
||
apt-get download $(apt-cache depends --recurse --no-recommends --no-suggests --no-conflicts \
|
||
--no-breaks --no-replaces --no-enhances docker.io | grep "^\w")
|
||
|
||
# 下载常用工具
|
||
apt-get download wget curl vim net-tools telnet
|
||
|
||
# 验证
|
||
ls -lh /owl_zlmediakit/deb-packages/apt-deps/
|
||
```
|
||
|
||
### 4.5 准备配置文件
|
||
|
||
#### 4.5.1 创建 docker-compose.yml
|
||
|
||
创建文件 `/owl_zlmediakit/configs/docker-compose.yml`:
|
||
|
||
```yaml
|
||
version: '3.8'
|
||
|
||
services:
|
||
# ZLMediaKit 流媒体服务
|
||
zlmediakit:
|
||
image: zlmediakit/zlmediakit:master
|
||
container_name: zlmediakit
|
||
restart: always
|
||
privileged: true
|
||
network_mode: host
|
||
volumes:
|
||
- ./data/zlm-config.ini:/opt/media/conf/config.ini:ro
|
||
- ./data/record:/opt/media/bin/www/record
|
||
- ./data/log:/opt/media/bin/log
|
||
environment:
|
||
- TZ=Asia/Shanghai
|
||
logging:
|
||
driver: json-file
|
||
options:
|
||
max-size: "100m"
|
||
max-file: "3"
|
||
|
||
# GoWVP (Owl) 管理平台
|
||
gowvp:
|
||
image: gospace/gowvp:latest
|
||
container_name: gowvp
|
||
restart: always
|
||
network_mode: host
|
||
depends_on:
|
||
- zlmediakit
|
||
volumes:
|
||
- ./data/gowvp-configs:/opt/media/bin/configs
|
||
- ./data/record:/opt/media/bin/www/record
|
||
environment:
|
||
- TZ=Asia/Shanghai
|
||
- GOWVP_ZLM_HOST=192.168.3.108 # 必须使用服务器实际IP,不能填127.0.0.1
|
||
- GOWVP_ZLM_PORT=80
|
||
- GOWVP_ZLM_SECRET=035c73f7-bb6b-4889-a715-d9eb2d1925cc
|
||
logging:
|
||
driver: json-file
|
||
options:
|
||
max-size: "100m"
|
||
max-file: "3"
|
||
```
|
||
|
||
#### 4.5.2 创建 ZLMediaKit 配置文件
|
||
|
||
创建文件 `/owl_zlmediakit/configs/zlm-config.ini`:
|
||
|
||
```ini
|
||
; ZLMediaKit 配置文件
|
||
; 针对 ARM64 + 离线环境优化
|
||
|
||
[api]
|
||
apiDebug=1
|
||
secret=035c73f7-bb6b-4889-a715-d9eb2d1925cc
|
||
snapRoot=./www/snap/
|
||
defaultSnap=./www/logo.png
|
||
downloadRoot=./www
|
||
|
||
[ffmpeg]
|
||
bin=/usr/bin/ffmpeg
|
||
cmd=%s -re -i %s -c copy -f flv %s
|
||
snap=%s -i %s -y -f mjpeg -t 0.001 %s
|
||
|
||
[general]
|
||
enableVhost=0
|
||
flowThreshold=1024
|
||
maxStreamWaitMS=15000
|
||
streamNoneReaderDelayMS=20000
|
||
resetWhenRePlay=1
|
||
mergeWriteMS=0
|
||
mediaServerId=owl-zlm-server-01
|
||
wait_add_track_ms=3000
|
||
wait_track_ready_ms=10000
|
||
|
||
[hls]
|
||
fileBufSize=65536
|
||
segDur=2
|
||
segNum=3
|
||
segRetain=5
|
||
broadcastRecordTs=0
|
||
fastRegister=0
|
||
|
||
[hook]
|
||
enable=1
|
||
on_publish=https://127.0.0.1:15123/api/v1/hook/on_publish
|
||
on_play=https://127.0.0.1:15123/api/v1/hook/on_play
|
||
on_stream_not_found=https://127.0.0.1:15123/api/v1/hook/on_stream_not_found
|
||
on_server_started=https://127.0.0.1:15123/api/v1/hook/on_server_started
|
||
on_server_keepalive=https://127.0.0.1:15123/api/v1/hook/on_server_keepalive
|
||
on_send_rtp_stopped=https://127.0.0.1:15123/api/v1/hook/on_send_rtp_stopped
|
||
on_rtp_server_timeout=https://127.0.0.1:15123/api/v1/hook/on_rtp_server_timeout
|
||
admin_params=secret=035c73f7-bb6b-4889-a715-d9eb2d1925cc
|
||
timeoutSec=20
|
||
|
||
[http]
|
||
charSet=utf-8
|
||
keepAliveSecond=30
|
||
maxReqSize=40960
|
||
notFound=<html><head><title>404 Not Found</title></head><body bgcolor="white"><center><h1>您访问的资源不存在!</h1></center><hr><center>ZLMediaKit-4.0</center></body></html>
|
||
port=80
|
||
rootPath=./www
|
||
sendBufSize=65536
|
||
sslport=443
|
||
virtualPath=
|
||
|
||
[multicast]
|
||
addrMax=239.255.255.255
|
||
addrMin=239.0.0.0
|
||
udpTTL=64
|
||
|
||
[record]
|
||
appName=record
|
||
fastStart=0
|
||
fileBufSize=65536
|
||
fileSecond=3600
|
||
sampleMS=500
|
||
|
||
[rtmp]
|
||
directProxy=1
|
||
enhanced=0
|
||
handshakeSecond=15
|
||
keepAliveSecond=15
|
||
port=1935
|
||
|
||
[rtp]
|
||
audioMtuSize=600
|
||
h264_stap_a=1
|
||
opus_rtp_ext=0
|
||
rtpMaxSize=10
|
||
videoMtuSize=1400
|
||
|
||
[rtp_proxy]
|
||
dumpDir=
|
||
port=10000
|
||
port_range=30000-30500
|
||
|
||
[rtsp]
|
||
authBasic=0
|
||
directProxy=1
|
||
handshakeSecond=15
|
||
keepAliveSecond=15
|
||
port=554
|
||
sslport=332
|
||
|
||
[srt]
|
||
latencyMul=4
|
||
pktBufSize=8192
|
||
port=9000
|
||
timeoutSec=5
|
||
|
||
[rtc]
|
||
# WebRTC外部IP,必须设置为服务器实际IP,否则外部浏览器无法播放
|
||
externIP=192.168.3.108
|
||
port=8000
|
||
tcpPort=8000
|
||
rembBitRate=0
|
||
|
||
[shell]
|
||
maxReqSize=1024
|
||
port=9000
|
||
|
||
[cluster]
|
||
origin_url=
|
||
retry_count=3
|
||
timeout_sec=15
|
||
```
|
||
|
||
### 4.6 打包所有文件
|
||
|
||
```bash
|
||
# 在联网笔记本上,将所有文件打包到一个压缩包中,方便传输
|
||
cd /owl_zlmediakit
|
||
tar czf owl-zlmediakit-offline-package-arm64.tar.gz \
|
||
docker-images/ \
|
||
deb-packages/ \
|
||
source-packages/ \
|
||
configs/ \
|
||
scripts/ \
|
||
部署手册.md
|
||
|
||
# 验证打包结果
|
||
ls -lh owl-zlmediakit-offline-package-arm64.tar.gz
|
||
```
|
||
|
||
> **传输到生产环境**: 将上述压缩包通过 U盘/移动硬盘/内网FTP 拷贝到生产服务器的 `/opt/` 目录下。
|
||
|
||
---
|
||
## 五、生产环境服务器部署
|
||
|
||
> **本章节所有操作在生产环境服务器上执行**,服务器为飞腾S5000C ARM64 + 统信UOS20,处于离线状态。
|
||
|
||
### 5.1 确认系统版本和包管理器
|
||
|
||
```bash
|
||
# 1. 查看操作系统信息
|
||
cat /etc/os-release
|
||
|
||
# 2. 确认包管理器
|
||
which yum && echo "使用 yum" || echo "未安装 yum"
|
||
which apt-get && echo "使用 apt" || echo "未安装 apt-get"
|
||
|
||
# 3. 确认架构
|
||
uname -m
|
||
# 预期输出: aarch64
|
||
|
||
# 4. 确认CPU信息
|
||
cat /proc/cpuinfo | grep "model name" | head -1
|
||
```
|
||
|
||
### 5.2 安装 Docker(离线)
|
||
|
||
#### 5.2.1 解压部署包
|
||
|
||
```bash
|
||
# 创建安装目录
|
||
mkdir -p /opt/owl-zlmediakit
|
||
cd /opt/owl-zlmediakit
|
||
|
||
# 解压部署包(从联网笔记本拷贝过来的)
|
||
tar xzf /path/to/owl-zlmediakit-offline-package-arm64.tar.gz
|
||
|
||
# 查看目录结构
|
||
ls -la
|
||
```
|
||
|
||
#### 5.2.2 运行 Docker 安装脚本
|
||
|
||
```bash
|
||
cd /opt/owl-zlmediakit
|
||
|
||
# 给脚本添加执行权限
|
||
chmod +x scripts/install-docker.sh
|
||
|
||
# 运行安装脚本
|
||
./scripts/install-docker.sh
|
||
```
|
||
|
||
**如果脚本安装失败,手动安装步骤:**
|
||
|
||
```bash
|
||
cd /opt/owl-zlmediakit/deb-packages
|
||
|
||
# 解压 Docker 静态二进制包
|
||
# 注意: 将 docker-27.5.1.tgz 替换为您实际下载的版本
|
||
tar -xzf docker-27.5.1.tgz
|
||
|
||
# 复制到系统路径
|
||
cp -p docker/* /usr/bin/
|
||
|
||
# 安装 docker-compose
|
||
cp -p docker-compose-linux-aarch64 /usr/bin/docker-compose
|
||
chmod +x /usr/bin/docker-compose
|
||
|
||
# 创建 systemd 服务
|
||
cat > /etc/systemd/system/docker.service << 'EOF'
|
||
[Unit]
|
||
Description=Docker Application Container Engine
|
||
After=network-online.target
|
||
Wants=network-online.target
|
||
|
||
[Service]
|
||
Type=notify
|
||
ExecStart=/usr/bin/dockerd
|
||
ExecReload=/bin/kill -s HUP $MAINPID
|
||
LimitNOFILE=infinity
|
||
LimitNPROC=infinity
|
||
Restart=on-failure
|
||
|
||
[Install]
|
||
WantedBy=multi-user.target
|
||
EOF
|
||
|
||
# 启动 Docker
|
||
systemctl daemon-reload
|
||
systemctl start docker
|
||
systemctl enable docker
|
||
|
||
# 验证
|
||
docker --version
|
||
docker-compose --version
|
||
```
|
||
|
||
### 5.3 加载 Docker 镜像并启动
|
||
|
||
```bash
|
||
cd /opt/owl-zlmediakit
|
||
|
||
# 加载 ZLMediaKit 镜像
|
||
docker load -i docker-images/zlmediakit-master-arm64.tar
|
||
|
||
# 加载 GoWVP 镜像
|
||
docker load -i docker-images/gowvp-latest-arm64.tar
|
||
|
||
# 验证镜像已加载
|
||
docker images | grep -E "zlmediakit|gowvp"
|
||
|
||
# 创建数据目录
|
||
mkdir -p data/record data/log data/gowvp-configs data/snap
|
||
|
||
# 复制配置文件
|
||
cp configs/zlm-config.ini data/
|
||
cp configs/docker-compose.yml .
|
||
|
||
# 启动服务(首次启动建议前台运行查看日志)
|
||
docker-compose up
|
||
|
||
# 如果日志无错误,按 Ctrl+C 停止,然后后台启动
|
||
docker-compose up -d
|
||
```
|
||
|
||
### 5.4 部署 ZLMediaKit(单独运行方式)
|
||
|
||
> 如果使用 Docker Compose 融合部署,此节可跳过。本节仅用于单独部署 ZLMediaKit 的场景。
|
||
|
||
```bash
|
||
# 单独运行 ZLMediaKit 容器
|
||
docker run -id \
|
||
--name zlmediakit \
|
||
--restart always \
|
||
--privileged \
|
||
--network host \
|
||
-v /opt/owl-zlmediakit/data/zlm-config.ini:/opt/media/conf/config.ini:ro \
|
||
-v /opt/owl-zlmediakit/data/record:/opt/media/bin/www/record \
|
||
-v /opt/owl-zlmediakit/data/log:/opt/media/bin/log \
|
||
-e TZ=Asia/Shanghai \
|
||
zlmediakit/zlmediakit:master
|
||
|
||
# 查看日志
|
||
docker logs -f zlmediakit
|
||
```
|
||
|
||
### 5.5 部署 GoWVP(Owl)(单独运行方式)
|
||
|
||
> 如果使用 Docker Compose 融合部署,此节可跳过。
|
||
|
||
```bash
|
||
# 单独运行 GoWVP 容器
|
||
docker run -id \
|
||
--name gowvp \
|
||
--restart always \
|
||
--network host \
|
||
-v /opt/owl-zlmediakit/data/gowvp-configs:/opt/media/bin/configs \
|
||
-v /opt/owl-zlmediakit/data/record:/opt/media/bin/www/record \
|
||
-e TZ=Asia/Shanghai \
|
||
-e GOWVP_ZLM_HOST=192.168.3.108 \
|
||
-e GOWVP_ZLM_PORT=80 \
|
||
-e GOWVP_ZLM_SECRET=035c73f7-bb6b-4889-a715-d9eb2d1925cc \
|
||
gospace/gowvp:latest
|
||
|
||
# 查看日志
|
||
docker logs -f gowvp
|
||
```
|
||
|
||
### 5.6 配置联动
|
||
|
||
#### 5.6.1 ZLMediaKit Hook 配置(已包含在配置文件中)
|
||
|
||
ZLMediaKit 通过 WebHook 将事件通知给 GoWVP:
|
||
|
||
```ini
|
||
[hook]
|
||
enable=1
|
||
on_publish=https://127.0.0.1:15123/api/v1/hook/on_publish
|
||
on_play=https://127.0.0.1:15123/api/v1/hook/on_play
|
||
on_stream_not_found=https://127.0.0.1:15123/api/v1/hook/on_stream_not_found
|
||
on_server_started=https://127.0.0.1:15123/api/v1/hook/on_server_started
|
||
on_server_keepalive=https://127.0.0.1:15123/api/v1/hook/on_server_keepalive
|
||
admin_params=secret=035c73f7-bb6b-4889-a715-d9eb2d1925cc
|
||
```
|
||
|
||
#### 5.6.2 GoWVP 环境变量配置(已包含在 docker-compose.yml 中)
|
||
|
||
GoWVP 通过环境变量连接 ZLMediaKit:
|
||
|
||
```yaml
|
||
environment:
|
||
- GOWVP_ZLM_HOST=192.168.3.108 # ZLMediaKit 地址(必须使用服务器实际IP)
|
||
- GOWVP_ZLM_PORT=80 # ZLMediaKit HTTP端口
|
||
- GOWVP_ZLM_SECRET=035c73f7-bb6b-4889-a715-d9eb2d1925cc # API密钥
|
||
```
|
||
|
||
#### 5.6.3 重启服务使配置生效
|
||
|
||
```bash
|
||
cd /opt/owl-zlmediakit
|
||
docker-compose restart
|
||
|
||
# 等待30秒后检查状态
|
||
sleep 30
|
||
docker-compose ps
|
||
```
|
||
|
||
---
|
||
|
||
## 六、配置联动
|
||
|
||
GoWVP 与 ZLMediaKit 的联动已通过以下方式配置完成:
|
||
|
||
1. **ZLMediaKit Hook 回调**: ZLMediaKit 在流注册、播放、推流等事件发生时,通过 HTTP POST 请求通知 GoWVP
|
||
2. **GoWVP RESTful API**: GoWVP 通过 ZLMediaKit 的 HTTP API 控制流的拉取、转码、录制等操作
|
||
3. **共享存储**: 两个容器通过 bind mount 共享 `./data/record` 目录,用于录像文件存储
|
||
|
||
### 联动验证
|
||
|
||
```bash
|
||
# 查看 ZLMediaKit 日志,确认 Hook 回调成功
|
||
docker logs zlmediakit | grep -i "hook"
|
||
|
||
# 查看 GoWVP 日志,确认收到 ZLMediaKit 事件
|
||
docker logs gowvp | grep -i "zlm\|hook"
|
||
```
|
||
|
||
---
|
||
|
||
## 七、验证步骤
|
||
|
||
### 7.1 验证脚本
|
||
|
||
运行提供的验证脚本:
|
||
|
||
```bash
|
||
chmod +x /opt/owl-zlmediakit/scripts/verify.sh
|
||
/opt/owl-zlmediakit/scripts/verify.sh
|
||
```
|
||
|
||
### 7.2 手动验证步骤
|
||
|
||
#### 7.2.1 验证 ZLMediaKit
|
||
|
||
```bash
|
||
# 获取服务器IP
|
||
SERVER_IP=$(hostname -I | awk '{print $1}')
|
||
|
||
# 测试 ZLMediaKit API
|
||
curl "http://${SERVER_IP}/index/api/getApiList"
|
||
|
||
# 测试获取流列表
|
||
curl "http://${SERVER_IP}/index/api/getMediaList?secret=035c73f7-bb6b-4889-a715-d9eb2d1925cc"
|
||
|
||
# 在浏览器中访问
|
||
# http://<服务器IP>
|
||
```
|
||
|
||
#### 7.2.2 验证 GoWVP
|
||
|
||
```bash
|
||
# 测试 GoWVP Web 界面
|
||
curl -I "http://${SERVER_IP}:15123"
|
||
|
||
# 在浏览器中访问管理界面
|
||
# http://<服务器IP>:15123
|
||
# 默认账号密码请查看 GoWVP 官方文档
|
||
```
|
||
|
||
#### 7.2.3 验证 GB28181 端口
|
||
|
||
```bash
|
||
# 检查 SIP 端口(UDP/TCP 15060)
|
||
netstat -ulnp | grep 15060
|
||
netstat -tlnp | grep 15060
|
||
|
||
# 检查流媒体端口范围(20000-20100)
|
||
netstat -ulnp | grep -E "20000|20001|20002"
|
||
```
|
||
|
||
### 7.3 推流测试
|
||
|
||
如果您有支持 RTMP/RTSP 的摄像头或推流工具,可以进行测试:
|
||
|
||
```bash
|
||
# RTMP 推流测试地址(使用FFmpeg)
|
||
ffmpeg -re -i test.mp4 -c copy -f flv rtmp://<服务器IP>/live/test
|
||
|
||
# 播放测试
|
||
# RTMP: rtmp://<服务器IP>/live/test
|
||
# HLS: http://<服务器IP>/live/test/hls.m3u8
|
||
# FLV: http://<服务器IP>/live/test.live.flv
|
||
```
|
||
|
||
---
|
||
|
||
## 八、常见问题排查
|
||
|
||
### 8.1 Docker 无法启动
|
||
|
||
**现象**: `systemctl start docker` 失败
|
||
|
||
**排查步骤**:
|
||
```bash
|
||
# 查看详细错误
|
||
journalctl -u docker -n 50
|
||
|
||
# 检查内核是否支持容器
|
||
cat /proc/1/cgroup
|
||
|
||
# 手动运行dockerd查看错误
|
||
/usr/bin/dockerd
|
||
```
|
||
|
||
**解决方案**:
|
||
- 确保内核版本 >= 3.10(统信UOS kernel-4.19 满足要求)
|
||
- 检查 `/var/run/docker.sock` 权限
|
||
- 确保 `iptables` 可用:`which iptables`
|
||
|
||
### 8.2 容器启动后立即退出
|
||
|
||
**现象**: `docker ps` 看不到运行的容器
|
||
|
||
**排查步骤**:
|
||
```bash
|
||
# 查看容器退出日志
|
||
docker logs zlmediakit
|
||
docker logs gowvp
|
||
|
||
# 查看容器状态
|
||
docker ps -a
|
||
docker inspect zlmediakit
|
||
```
|
||
|
||
**常见原因**:
|
||
- 端口被占用:`netstat -tlnp | grep :80`
|
||
- 配置文件路径错误:检查 volume 映射
|
||
- 权限不足:确保使用 `--privileged` 或正确配置 capabilities
|
||
|
||
### 8.3 ARM64 镜像无法运行
|
||
|
||
**现象**: 报错 `exec format error`
|
||
|
||
**原因**: 镜像架构与服务器不匹配(导入了 x86_64 镜像)
|
||
|
||
**解决方案**:
|
||
```bash
|
||
# 检查镜像架构
|
||
docker inspect zlmediakit/zlmediakit:master | grep Architecture
|
||
# 必须显示 "arm64"
|
||
|
||
# 如果错误,需要在 ARM64 机器上重新拉取并导出
|
||
```
|
||
|
||
### 8.4 GoWVP 无法连接 ZLMediaKit
|
||
|
||
**现象**: GoWVP 日志显示连接 ZLMediaKit 失败
|
||
|
||
**排查步骤**:
|
||
```bash
|
||
# 检查 ZLMediaKit 是否正常运行
|
||
curl http://127.0.0.1/index/api/getApiList
|
||
|
||
# 检查 secret 是否一致
|
||
grep secret data/zlm-config.ini
|
||
grep GOWVP_ZLM_SECRET docker-compose.yml
|
||
|
||
# 检查 Hook 配置是否正确
|
||
grep "on_publish\|on_play" data/zlm-config.ini
|
||
```
|
||
|
||
### 8.5 GB28181 设备无法接入
|
||
|
||
**现象**: 摄像头无法注册到 GoWVP
|
||
|
||
**排查步骤**:
|
||
```bash
|
||
# 检查 SIP 端口是否监听
|
||
netstat -ulnp | grep 15060
|
||
|
||
# 检查防火墙
|
||
firewall-cmd --list-ports # 如果使用 firewalld
|
||
iptables -L -n | grep 15060
|
||
|
||
# 查看 GoWVP 日志
|
||
docker logs -f gowvp | grep -i "sip\|register"
|
||
```
|
||
|
||
**必要端口清单**:
|
||
| 端口 | 协议 | 用途 |
|
||
|------|------|------|
|
||
| 80 | TCP | HTTP/Web |
|
||
| 443 | TCP | HTTPS |
|
||
| 15123 | TCP | GoWVP Web管理 |
|
||
| 15060 | UDP/TCP | GB28181 SIP |
|
||
| 1935 | TCP | RTMP |
|
||
| 554 | TCP | RTSP |
|
||
| 8000 | UDP/TCP | WebRTC |
|
||
| 9000 | UDP | SRT |
|
||
| 10000 | UDP | RTP代理 |
|
||
| 20000-20100 | UDP | GB28181 媒体流 |
|
||
| 30000-30500 | UDP | RTP端口范围 |
|
||
|
||
### 8.6 性能问题
|
||
|
||
**现象**: 视频卡顿、延迟高
|
||
|
||
**优化建议**:
|
||
```bash
|
||
# 查看CPU和内存使用情况
|
||
top
|
||
htop
|
||
|
||
# 查看磁盘IO
|
||
iostat -x 1
|
||
|
||
# ZLMediaKit 配置优化:关闭转码以节省CPU
|
||
# 在 config.ini 中:
|
||
[ffmpeg]
|
||
cmd=%s -re -i %s -c copy -f flv %s # 使用 copy 而不是重新编码
|
||
|
||
# 限制日志大小避免磁盘占满
|
||
docker system prune -f
|
||
```
|
||
|
||
### 8.7 ARM64 架构稳定性问题(重要)
|
||
|
||
> ⚠️ **本章节针对飞腾S5000C等ARM64服务器的重要风险提示**
|
||
|
||
#### 8.7.1 已知问题概述
|
||
|
||
**GitHub Issue**: [#3466 - In ARM architecture, ZLM live streaming is unstable](https://github.com/ZLMediaKit/ZLMediaKit/issues/3466)
|
||
|
||
**问题描述**: ZLMediaKit 在 ARM64 (aarch64) 架构下运行 GB28181 RTP 推流时,存在**偶发性崩溃**问题,x86_64 架构下相同配置稳定运行。
|
||
|
||
#### 8.7.2 具体症状
|
||
|
||
| 症状 | 描述 |
|
||
|------|------|
|
||
| **进程崩溃** | MediaServer 进程意外退出,Docker 容器重启 |
|
||
| **Signal 11** | 收到 SIGSEGV (段错误),内存访问违规 |
|
||
| **流中断** | GB28181 RTP 推流频繁断开,需重新注册 |
|
||
| **错误日志** | `Unsupported codec: PCMU`、`Unsupported codec: invalid` |
|
||
|
||
**典型错误日志**:
|
||
```
|
||
2024-04-11 07:13:07.002 W [MediaServer] [319-event poller 3] Factory.cpp:118 getTrackByCodecId | Unsupported codec: PCMU
|
||
2024-04-11 07:13:24.885 W [MediaServer] [319-event poller 3] Factory.cpp:200 getFrameFromPtr | Unsupported codec: invalid
|
||
```
|
||
|
||
**崩溃堆栈特征**(简化):
|
||
```
|
||
Signal 11 received
|
||
Stacktrace:
|
||
FrameCacheAble::FrameCacheAble(...)
|
||
Factory::getFrameFromBuffer(...)
|
||
FrameMerger::inputFrame(...)
|
||
FrameMerger::flush(...)
|
||
DecoderImp::flush(...)
|
||
RtpProcessHelper::~RtpProcessHelper()
|
||
```
|
||
|
||
> **崩溃位置分析**: 堆栈显示崩溃发生在**帧缓存分配**和**解码器刷新**阶段,疑似与内存对齐或并发访问有关。
|
||
|
||
#### 8.7.3 可重现性
|
||
|
||
| 条件 | 可重现性 |
|
||
|------|----------|
|
||
| Docker 部署 + ARM64 | **高** - 社区多个用户报告 |
|
||
| 物理机/虚拟机 ARM64 | **中** - 部分用户报告 |
|
||
| x86_64 (相同配置) | **无法重现** - 稳定运行 |
|
||
| GB28181 RTP 推流 | **高** - 主要触发场景 |
|
||
| RTMP/RTSP 推流 | **低** - 偶发 |
|
||
| 空闲状态 | **无** - 仅在活跃推流时 |
|
||
|
||
#### 8.7.4 可能原因分析
|
||
|
||
1. **内存对齐问题**: ARM64 架构对内存对齐要求更严格,某些数据结构在 x86 上能正常工作但在 ARM 上触发 SIGSEGV
|
||
2. **并发访问竞争**: FrameMerger 在多线程环境下可能存在 race condition
|
||
3. **Codec 解析异常**: 某些摄像头发送的 PS 流格式不规范,ARM 版解码器处理异常时未正确保护
|
||
4. **Docker 环境差异**: Docker 在 ARM64 上的 QEMU 模拟或 seccomp 策略可能影响行为
|
||
|
||
#### 8.7.5 规避方案与解决方案
|
||
|
||
**方案一:使用官方最新镜像(推荐尝试)**
|
||
```bash
|
||
# 确保使用最新 master 分支镜像,可能已修复
|
||
# 官方维护者持续在修复 ARM64 相关问题
|
||
docker pull zlmediakit/zlmediakit:master
|
||
docker inspect zlmediakit/zlmediakit:master | grep -E "Created|Revision"
|
||
```
|
||
|
||
**方案二:启用容器自动重启**
|
||
```yaml
|
||
# 在 docker-compose.yml 中已配置 restart: always
|
||
# 崩溃后容器会自动重启,业务中断时间 < 10 秒
|
||
services:
|
||
zlmediakit:
|
||
restart: always
|
||
# 可选:增加重启策略
|
||
deploy:
|
||
restart_policy:
|
||
condition: any
|
||
delay: 5s
|
||
max_attempts: 10
|
||
```
|
||
|
||
**方案三:限制单路流的并发处理**
|
||
```ini
|
||
# 在 config.ini 中降低并发处理线程数
|
||
[general]
|
||
# 减少事件轮询线程数(默认等于 CPU 核心数)
|
||
# 可尝试设置为物理核心数的一半
|
||
# 注意: 此配置需查阅最新文档确认参数名
|
||
|
||
[ffmpeg]
|
||
# 关闭转码,减少编解码压力
|
||
cmd=%s -re -i %s -c copy -f flv %s
|
||
```
|
||
|
||
**方案四:使用 host 网络模式(已默认配置)**
|
||
```yaml
|
||
# docker-compose.yml 中已配置 network_mode: host
|
||
# 避免 Docker 桥接网络在 ARM64 上的性能开销和潜在 bug
|
||
services:
|
||
zlmediakit:
|
||
network_mode: host
|
||
```
|
||
|
||
**方案五:监控并自动恢复**
|
||
```bash
|
||
# 创建监控脚本 /opt/owl-zlmediakit/scripts/monitor.sh
|
||
#!/bin/bash
|
||
while true; do
|
||
if ! docker ps | grep -q zlmediakit; then
|
||
echo "$(date): ZLMediaKit 容器异常,正在重启..." >> /var/log/zlm-monitor.log
|
||
cd /opt/owl-zlmediakit && docker-compose restart zlmediakit
|
||
fi
|
||
sleep 10
|
||
done
|
||
```
|
||
|
||
**方案六:源码编译(终极方案)**
|
||
```bash
|
||
# 如果 Docker 镜像问题持续,可在 ARM64 服务器上本地编译
|
||
# 本地编译会针对具体 CPU 指令集优化,可能规避问题
|
||
cd /usr/src/ZLMediaKit
|
||
mkdir build && cd build
|
||
cmake .. -DCMAKE_BUILD_TYPE=Release -DCMAKE_CXX_FLAGS="-faligned-new"
|
||
make -j$(nproc)
|
||
```
|
||
|
||
#### 8.7.6 生产环境建议
|
||
|
||
| 场景 | 建议 |
|
||
|------|------|
|
||
| **测试/开发环境** | 可直接使用 Docker 部署,观察稳定性 |
|
||
| **生产环境(关键业务)** | 强烈建议**先进行 7x24 小时压力测试**,确认无崩溃后再上线 |
|
||
| **已出现崩溃** | 启用自动重启 + 监控脚本,同时向 ZLMediaKit GitHub 提交 issue |
|
||
| **追求极致稳定** | 考虑在 ARM64 上源码编译,或改用 x86_64 服务器部署 ZLMediaKit |
|
||
|
||
#### 8.7.7 社区状态跟踪
|
||
|
||
- **Issue 状态**: Closed (因未按模板提交被关闭,但问题真实存在)
|
||
- **社区反馈**: 多名用户确认在 RK3568、树莓派、鲲鹏等 ARM64 设备上遇到类似问题
|
||
- **官方态度**: 维护者表示会持续关注 ARM64 兼容性,建议用户使用最新版本
|
||
- **建议操作**: 如遇到崩溃,请收集完整堆栈和复现步骤,向 [ZLMediaKit Issues](https://github.com/ZLMediaKit/ZLMediaKit/issues) 提交反馈
|
||
|
||
#### 8.7.8 相关 Issue 深度分析
|
||
|
||
> 以下三个 Issue 与 ARM64 稳定性密切相关,建议主人一并了解。
|
||
|
||
---
|
||
|
||
**Issue #3202 - RK3588 SIGABRT 崩溃**
|
||
|
||
| 项目 | 详情 |
|
||
|------|------|
|
||
| **硬件** | RK3588 (Ubuntu 20.04.6) |
|
||
| **信号** | `SIGABRT` (signal 6) |
|
||
| **版本** | git hash `e593ef5/2023-12-17` |
|
||
| **触发条件** | 视频流不稳定时持续崩溃 |
|
||
|
||
**崩溃堆栈特征**:
|
||
```
|
||
[0]: MediaServer(+0x992ba8)
|
||
[4]: libstdc++.so.6(_ZN9__gnu_cxx27__verbose_terminate_handlerEv+0x188)
|
||
[8]: MediaServer(Assert_Throw+0x184)
|
||
```
|
||
|
||
**根本原因**(官方维护者 @xia-chu 回复):
|
||
> "这个不算bug,是你的编译器默认关闭了异常功能,一抛异常就默认 abort。编译器开启异常功能需要加上编译选项 `-fexceptions`。"
|
||
|
||
**技术解释**:
|
||
- ARM 交叉编译工具链(如 `aarch64-linux-gnu-gcc`)**默认关闭 C++ 异常处理**
|
||
- 当 ZLMediaKit 内部抛出 C++ 异常(如 `Assert_Throw` 失败)时,libstdc++ 的 terminate handler 被调用
|
||
- 由于异常被禁用,该 handler 直接调用 `abort()` 导致进程终止
|
||
|
||
**解决方案**:
|
||
```cmake
|
||
# 在 CMakeLists.txt 中添加
|
||
if(CMAKE_SYSTEM_PROCESSOR STREQUAL "aarch64" OR CMAKE_SYSTEM_PROCESSOR STREQUAL "arm")
|
||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fexceptions")
|
||
endif()
|
||
```
|
||
|
||
**或在 cmake 命令中指定**:
|
||
```bash
|
||
cmake .. -DCMAKE_CXX_FLAGS="-fexceptions"
|
||
```
|
||
|
||
> ⚠️ **重要**: `-fexceptions` 是 GCC 标准选项,不是临时 hack。ZLMediaKit 大量使用 C++ 异常,在 ARM 上编译**必须**显式启用。
|
||
|
||
---
|
||
|
||
**Issue #2728 - ARM 内存"泄漏"问题**
|
||
|
||
| 项目 | 详情 |
|
||
|------|------|
|
||
| **平台** | ARM (aarch64), Ubuntu 18, 内存 4G |
|
||
| **现象** | 调用 `getStatisticJson` 接口时系统卡死;开启 `ENABLE_MEM_DEBUG` 后机器完全卡住 |
|
||
| **本质** | **内存碎片**,非真正泄漏 |
|
||
|
||
**详细分析**:
|
||
|
||
1. **内存碎片问题**:
|
||
- ZLMediaKit 调用 `free()` 将内存返还给 glibc 的 ptmalloc
|
||
- 但 ptmalloc **不会立即将内存返还给操作系统**(出于性能考虑)
|
||
- 导致 `RSS` 内存居高不下,看起来像泄漏
|
||
|
||
2. **`ENABLE_MEM_DEBUG` 的陷阱**:
|
||
```cmake
|
||
# ZLMediaKit 使用链接器 wrap 机制拦截内存分配
|
||
if(ENABLE_MEM_DEBUG)
|
||
update_cached_list(MK_LINK_LIBRARIES
|
||
"-Wl,-wrap,free;-Wl,-wrap,malloc;-Wl,-wrap,realloc;-Wl,-wrap,calloc")
|
||
endif()
|
||
```
|
||
- 在 ARM 平台上,`-Wl,-wrap` 拦截每次 malloc/free,**性能开销极大**
|
||
- 高并发场景下会导致系统完全卡死
|
||
- **生产环境切勿开启 ENABLE_MEM_DEBUG**
|
||
|
||
3. **解决方案 - 使用 tcmalloc**:
|
||
```cmake
|
||
# 编译时启用 tcmalloc
|
||
cmake .. -DENABLE_TCMALLOC=ON
|
||
```
|
||
- tcmalloc 采用 **per-CPU 缓存** 机制,更好地管理内存碎片
|
||
- 在 RTP 断流重连场景下,内存可以稳定复用
|
||
|
||
**tcmalloc 静态库编译注意事项**:
|
||
```bash
|
||
# 编译 gperftools 时需要加 -fPIC
|
||
./configure CFLAGS="-fPIC" CXXFLAGS="-fPIC"
|
||
make
|
||
```
|
||
|
||
**运行时加载**:
|
||
```bash
|
||
LD_PRELOAD=libtcmalloc.so.4 ./MediaServer
|
||
```
|
||
|
||
4. **替代方案 - jemalloc**:
|
||
```cmake
|
||
# ZLMediaKit 默认优先链接 jemalloc
|
||
find_package(JEMALLOC QUIET)
|
||
if(JEMALLOC_FOUND)
|
||
update_cached_list(MK_LINK_LIBRARIES ${JEMALLOC_LIBRARIES})
|
||
add_definitions(-DUSE_JEMALLOC)
|
||
endif()
|
||
```
|
||
|
||
---
|
||
|
||
**Issue #2043 - RK3568 拉流断开问题**
|
||
|
||
| 项目 | 详情 |
|
||
|------|------|
|
||
| **硬件** | RK3568 |
|
||
| **信号** | `SIGSEGV` (signal 11) |
|
||
| **版本** | git hash `b3fd74c` |
|
||
| **触发条件** | 拉流后很快断开 |
|
||
|
||
**错误日志**:
|
||
```
|
||
## signal: 11
|
||
[0]: ./MediaServer() [0x995710] sig_crash(int)
|
||
[1]: /lib/arm-linux-gnueabihf/libc.so.6(+0x25260)
|
||
```
|
||
|
||
**可能原因**:
|
||
1. **RK 系列网卡驱动 bug**(与 RK3399 类似)
|
||
> "rk3339 的网卡驱动是有 bug 的!如果是从上面往别处 tcp 发送大的数据包,在 tcp 的 ip 数据报分片以后会出现校验和计算错误"
|
||
2. 交叉编译环境配置问题
|
||
3. 缺少必要的系统库
|
||
|
||
**状态**: Issue 已关闭,标题显示"问题已经解决,谢谢",但未详细说明解决方案。
|
||
|
||
**建议**: 如遇到类似问题,优先尝试:
|
||
1. 更新到最新代码
|
||
2. 检查网卡驱动版本
|
||
3. 在 GDB 下调试获取完整堆栈
|
||
|
||
---
|
||
|
||
#### 8.7.9 ARM64 编译优化建议
|
||
|
||
**必加编译选项**:
|
||
|
||
| 选项 | 用途 | 必要性 |
|
||
|------|------|--------|
|
||
| `-fexceptions` | 启用 C++ 异常处理 | **必须** |
|
||
| `-pthread` | 线程支持 | **必须** |
|
||
| `-fPIC` | 位置无关代码(动态库需要) | **推荐** |
|
||
| `-faligned-new` | 对齐内存分配 | **推荐** |
|
||
|
||
**完整编译命令示例**:
|
||
```bash
|
||
cd /usr/src/ZLMediaKit
|
||
mkdir build && cd build
|
||
|
||
cmake .. \
|
||
-DCMAKE_BUILD_TYPE=Release \
|
||
-DCMAKE_CXX_FLAGS="-fexceptions -pthread -fPIC -faligned-new" \
|
||
-DENABLE_WEBRTC=ON \
|
||
-DENABLE_FFMPEG=ON \
|
||
-DENABLE_TCMALLOC=ON
|
||
|
||
make -j$(nproc)
|
||
```
|
||
|
||
**交叉编译示例(飞腾S5000C)**:
|
||
```bash
|
||
# 创建工具链文件 /tmp/toolchain.cmake
|
||
cat > /tmp/toolchain.cmake << 'EOF'
|
||
SET(CMAKE_SYSTEM_NAME Linux)
|
||
SET(CMAKE_SYSTEM_PROCESSOR aarch64)
|
||
set(CMAKE_C_COMPILER /usr/bin/aarch64-linux-gnu-gcc)
|
||
set(CMAKE_CXX_COMPILER /usr/bin/aarch64-linux-gnu-g++)
|
||
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
|
||
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
|
||
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
|
||
EOF
|
||
|
||
cmake .. \
|
||
-DCMAKE_TOOLCHAIN_FILE=/tmp/toolchain.cmake \
|
||
-DCMAKE_BUILD_TYPE=Release \
|
||
-DCMAKE_CXX_FLAGS="-fexceptions -pthread -fPIC" \
|
||
-DENABLE_TCMALLOC=ON
|
||
|
||
make -j$(nproc)
|
||
```
|
||
|
||
#### 8.7.10 官方态度与未来展望
|
||
|
||
**官方维护者 (@xia-chu) 的态度**:
|
||
- 承认 ARM64 支持,但认为问题多源于**用户环境/编译方式**
|
||
- 对于崩溃问题,往往归结为:端口占用、编译器选项问题 (`-fexceptions`)、Android 限制等
|
||
- **没有看到系统性的 ARM64 修复计划公告**
|
||
|
||
**已有的 ARM64 修复**:
|
||
- **PR #2479** (2023-05): 修复 ARM 内存对齐问题
|
||
- Commit `7cb772c`: "On arm need align, without this the application crashed after SIGBUS"
|
||
- **PR #2800** (2023-08): 修复 `close_stream` 与 `getMediaList` 并发崩溃
|
||
- **PR #4582** (2025-12): 修复 RtspSession/RtspPusher 空指针崩溃
|
||
|
||
**未来计划**:
|
||
- 2024 年 12 月,@xia-chu 表示:"后面我会考虑添加下 arm64 的 ci 自动编译并发布二进制包"
|
||
- 但截至 2026 年 4 月,**尚未实现** ARM64 CI 自动编译和二进制发布
|
||
|
||
**Issue #483 预编译二进制包**:
|
||
- 这是官方发布预编译二进制的位置
|
||
- 目前仅有 macOS ARM64 包,**Linux ARM64 包链接已失效**
|
||
- 下载地址: https://github.com/ZLMediaKit/ZLMediaKit/issues/483
|
||
|
||
---
|
||
|
||
## 九、附录
|
||
|
||
### 附录A: 端口清单
|
||
|
||
| 端口 | 协议 | 服务 | 说明 |
|
||
|------|------|------|------|
|
||
| 80 | TCP | ZLMediaKit | HTTP 服务 |
|
||
| 443 | TCP | ZLMediaKit | HTTPS 服务 |
|
||
| 15123 | TCP | GoWVP | Web 管理界面 |
|
||
| 15060 | UDP/TCP | GoWVP | GB28181 SIP 信令 |
|
||
| 1935 | TCP | ZLMediaKit | RTMP 推流/播放 |
|
||
| 554 | TCP | ZLMediaKit | RTSP 服务 |
|
||
| 8000 | UDP/TCP | ZLMediaKit | WebRTC |
|
||
| 9000 | UDP | ZLMediaKit | SRT 协议 |
|
||
| 10000 | UDP | ZLMediaKit | RTP 代理 |
|
||
| 20000-20100 | UDP | GoWVP | GB28181 媒体流传输 |
|
||
| 30000-30500 | UDP | ZLMediaKit | RTP 端口范围 |
|
||
|
||
### 附录B: 源码编译 ZLMediaKit(备用方案)
|
||
|
||
如果 Docker 方案不可用,可以选择源码编译:
|
||
|
||
```bash
|
||
# 1. 安装编译依赖
|
||
# yum 系统:
|
||
sudo yum install -y gcc gcc-c++ cmake git openssl-devel
|
||
|
||
# apt 系统:
|
||
sudo apt-get install -y build-essential cmake git libssl-dev
|
||
|
||
# 2. 解压源码
|
||
cd /opt/owl-zlmediakit/source-packages
|
||
tar xzf ZLMediaKit-master-with-submodules.tar.gz -C /usr/src/
|
||
cd /usr/src/ZLMediaKit
|
||
|
||
# 3. 初始化子模块(如果用zip下载则需要)
|
||
git submodule update --init --recursive
|
||
|
||
# 4. 编译
|
||
mkdir build && cd build
|
||
cmake .. -DCMAKE_BUILD_TYPE=Release
|
||
make -j$(nproc)
|
||
|
||
# 5. 运行
|
||
./release/linux/Release/MediaServer -d &
|
||
```
|
||
|
||
### 附录C: 源码编译 GoWVP(备用方案)
|
||
|
||
```bash
|
||
# 1. 安装 Go 环境(1.20+)
|
||
# 下载 ARM64 版本 Go: https://go.dev/dl/go1.22.0.linux-arm64.tar.gz
|
||
|
||
# 2. 解压预编译包
|
||
cd /opt/owl-zlmediakit/source-packages
|
||
tar xzf owl_linux_arm64.tar.gz -C /usr/local/
|
||
|
||
# 3. 运行
|
||
/usr/local/owl/owl-server &
|
||
```
|
||
|
||
### 附录D: 防火墙配置
|
||
|
||
```bash
|
||
# 如果使用 firewalld
|
||
firewall-cmd --permanent --add-port=80/tcp
|
||
firewall-cmd --permanent --add-port=443/tcp
|
||
firewall-cmd --permanent --add-port=15123/tcp
|
||
firewall-cmd --permanent --add-port=15060/tcp
|
||
firewall-cmd --permanent --add-port=15060/udp
|
||
firewall-cmd --permanent --add-port=1935/tcp
|
||
firewall-cmd --permanent --add-port=554/tcp
|
||
firewall-cmd --permanent --add-port=8000/tcp
|
||
firewall-cmd --permanent --add-port=8000/udp
|
||
firewall-cmd --permanent --add-port=9000/udp
|
||
firewall-cmd --permanent --add-port=10000/udp
|
||
firewall-cmd --permanent --add-port=20000-20100/udp
|
||
firewall-cmd --permanent --add-port=30000-30500/udp
|
||
firewall-cmd --reload
|
||
|
||
# 如果使用 iptables
|
||
iptables -I INPUT -p tcp --dport 80 -j ACCEPT
|
||
iptables -I INPUT -p tcp --dport 443 -j ACCEPT
|
||
iptables -I INPUT -p tcp --dport 15123 -j ACCEPT
|
||
iptables -I INPUT -p tcp --dport 15060 -j ACCEPT
|
||
iptables -I INPUT -p udp --dport 15060 -j ACCEPT
|
||
iptables -I INPUT -p tcp --dport 1935 -j ACCEPT
|
||
iptables -I INPUT -p tcp --dport 554 -j ACCEPT
|
||
iptables -I INPUT -p tcp --dport 8000 -j ACCEPT
|
||
iptables -I INPUT -p udp --dport 8000 -j ACCEPT
|
||
iptables -I INPUT -p udp --dport 9000 -j ACCEPT
|
||
iptables -I INPUT -p udp --dport 10000 -j ACCEPT
|
||
iptables -I INPUT -p udp --dport 20000:20100 -j ACCEPT
|
||
iptables -I INPUT -p udp --dport 30000:30500 -j ACCEPT
|
||
```
|
||
|
||
### 附录E: 参考链接
|
||
|
||
| 资源 | 地址 |
|
||
|------|------|
|
||
| ZLMediaKit GitHub | https://github.com/ZLMediaKit/ZLMediaKit |
|
||
| ZLMediaKit 文档 | https://docs.zlmediakit.com/ |
|
||
| ZLMediaKit Docker Hub | https://hub.docker.com/r/zlmediakit/zlmediakit |
|
||
| GoWVP (Owl) GitHub | https://github.com/gowvp/owl |
|
||
| GoWVP Docker Hub | https://hub.docker.com/r/gospace/gowvp |
|
||
| Docker CE 下载 | https://download.docker.com/linux/static/stable/aarch64/ |
|
||
| Docker Compose 下载 | https://github.com/docker/compose/releases |
|
||
| libsrtp 下载 | https://github.com/cisco/libsrtp/releases |
|
||
|
||
### 附录F: ARM64 架构问题速查表
|
||
|
||
> 本附录汇总 ZLMediaKit 在 ARM64 架构上的所有已知问题、症状和解决方案,方便快速定位。
|
||
|
||
#### F.1 信号类型速查
|
||
|
||
| 信号 | 名称 | 常见原因 | 解决方案 |
|
||
|------|------|----------|----------|
|
||
| **Signal 6** | SIGABRT | C++ 异常被禁用,abort() 被调用 | 编译时加 `-fexceptions` |
|
||
| **Signal 7** | SIGBUS | 内存未对齐访问 | 已于 PR #2479 修复 (2023-05),更新代码 |
|
||
| **Signal 11** | SIGSEGV | 内存访问违规/空指针 | 更新代码,检查 PS 流格式,GDB 调试 |
|
||
|
||
#### F.2 Issue 汇总表
|
||
|
||
| Issue | 硬件 | 信号 | 根本原因 | 解决方案 | 状态 |
|
||
|-------|------|------|----------|----------|------|
|
||
| #3466 | 多种 ARM | SIGSEGV | PS 流解析异常 + 内存问题 | 更新代码 + 自动重启 | 已关闭 |
|
||
| #3202 | RK3588 | SIGABRT | 编译器关闭异常处理 | `-fexceptions` | 已解决 |
|
||
| #2728 | 多种 ARM | - | 内存碎片 + MEM_DEBUG 性能问题 | tcmalloc/jemalloc | 已规避 |
|
||
| #2043 | RK3568 | SIGSEGV | 可能网卡驱动 bug | 更新代码 | 已关闭 |
|
||
| #4037 | aarch64 | system_error | 端口占用/系统限制 | GDB 调试排查 | 已关闭 |
|
||
|
||
#### F.3 编译参数速查
|
||
|
||
**必须添加**:
|
||
```bash
|
||
cmake .. -DCMAKE_CXX_FLAGS="-fexceptions -pthread -fPIC"
|
||
```
|
||
|
||
**推荐添加**:
|
||
```bash
|
||
cmake .. -DCMAKE_CXX_FLAGS="-fexceptions -pthread -fPIC -faligned-new" \
|
||
-DENABLE_TCMALLOC=ON
|
||
```
|
||
|
||
**调试编译**:
|
||
```bash
|
||
cmake .. -DCMAKE_BUILD_TYPE=Debug \
|
||
-DCMAKE_CXX_FLAGS="-fexceptions -pthread -fPIC" \
|
||
-DENABLE_ASAN=ON
|
||
```
|
||
|
||
#### F.4 运行时问题速查
|
||
|
||
| 现象 | 排查命令 | 可能原因 | 解决方案 |
|
||
|------|----------|----------|----------|
|
||
| 容器频繁重启 | `docker logs zlmediakit` | Signal 11 崩溃 | 更新镜像/源码编译 |
|
||
| 内存只增不减 | `cat /proc/$(pidof MediaServer)/status` | 内存碎片 | 使用 tcmalloc |
|
||
| 流播放卡顿 | `top`, `iostat` | CPU/IO 瓶颈 | 关闭转码,限制并发 |
|
||
| GB28181 无法注册 | `netstat -ulnp \| grep 15060` | 端口未监听 | 检查防火墙,重启容器 |
|
||
| WebRTC 无法播放 | `netstat -ulnp \| grep 8000` | UDP 端口被阻 | 检查防火墙规则 |
|
||
|
||
#### F.5 Docker vs 源码编译选择建议
|
||
|
||
| 场景 | 推荐方式 | 理由 |
|
||
|------|----------|------|
|
||
| 快速验证/测试 | Docker | 简单快捷,自动重启可缓解崩溃 |
|
||
| 生产环境(关键业务) | 源码编译 | 可针对具体 CPU 优化,稳定性更好 |
|
||
| 频繁崩溃 | 源码编译 | 可添加 `-fexceptions` 等必要参数 |
|
||
| 资源受限 | Docker | 无需编译环境,节省磁盘空间 |
|
||
|
||
#### F.6 官方 ARM64 修复时间线
|
||
|
||
| 时间 | 修复内容 |
|
||
|------|----------|
|
||
| 2023-05 | PR #2479: 修复 ARM 内存对齐 SIGBUS 问题 |
|
||
| 2023-08 | PR #2800: 修复 close_stream 与 getMediaList 并发崩溃 |
|
||
| 2024-12 | @xia-chu 表示考虑添加 ARM64 CI 自动编译 |
|
||
| 2025-12 | PR #4582: 修复 RtspSession/RtspPusher 空指针崩溃 |
|
||
| 2026-04 | **尚未实现** ARM64 CI 自动编译和二进制发布 |
|
||
|
||
#### F.7 社区已知兼容硬件
|
||
|
||
| 芯片 | 型号 | 系统 | 状态 | 备注 |
|
||
|------|------|------|------|------|
|
||
| 瑞芯微 | RK3568 | 多种 Linux | ✅ 基本稳定 | 更新代码后正常 |
|
||
| 瑞芯微 | RK3588 | Ubuntu 20.04 | ⚠️ 需注意 | 需加 `-fexceptions` |
|
||
| 飞腾 | S5000C | 统信UOS20 | ⚠️ 待验证 | 本手册目标平台 |
|
||
| 鲲鹏 | 920 | Ubuntu 20.04 | ✅ 正常 | 社区反馈良好 |
|
||
| 树莓派 | 4B | Raspberry Pi OS | ⚠️ 偶发崩溃 | 建议源码编译 |
|
||
|
||
---
|
||
|
||
> **文档结束**
|
||
> 如有问题,请参考各项目的官方文档或 GitHub Issues。
|
||
> **文档版本**: v1.2
|
||
> **最后更新**: 2026-04-29
|