Files
cube/apps/video2slides/README.md
T

47 lines
2.5 KiB
Markdown
Raw Normal View History

# video2slides
把一段长视频(演讲 / 课程录屏)按固定间隔抽帧,逐帧比差异,拖动阈值就能把重复画面变灰、留下关键变化(≈ 幻灯片翻页点)。
线上:<https://video2slides.famzheng.me>
## 架构
跟 cube 其它 app 同款:Rust + axum + `cube-core`,前端纯静态单页(零构建)。唯一特殊处——依赖 `ffmpeg`/`ffprobe`,所以镜像不是 `FROM scratch` 而是 `debian-slim` 装 ffmpeg + 拷静态 musl binary。
- 后端 `src/``core.rs`(存储 / 后台任务 / ffmpeg 抽帧 / image crate 逐帧灰度 MAE 差异)、`handlers.rs`REST)、`main.rs`(路由)。
- 前端 `frontend/index.html`:上传(进度) → 分析(进度) → 结果网格;顶部常驻 toolbar(阈值滑块 + 仅显示保留帧 + 保留/总数 + 分页),悬停缩略图浮出彩色大图。
## 流程
1. **上传** —— 拖拽或选文件,multipart 流式落盘,进度条到 100% 后 ffprobe 校验。
2. **分析** —— 设「每隔 N 秒抽一帧」(默认 8),`ffmpeg fps=1/N` 抽帧(限宽 1280),逐帧生成缩略图并算相邻帧灰度逐像素 MAE(0–100)。后台线程跑,前端轮询进度。
3. **挑帧** —— `diff ≥ 阈值` = 关键变化高亮保留;`< 阈值` = 跟上一帧太像变灰。纯前端实时切换,不回后端。
## 隔离与存储
- 前端在 `localStorage` 存随机 `v2s_client`,所有请求带 `X-Client-Id`,后端按 client 分目录。换浏览器 = 换身份,互相看不到。
- 每个视频一个目录:`source.*` 原片、`frames/` 抽出的彩色帧(大图预览)、`thumbs/` 缩略图、`meta.json`(含每帧时间戳与 diff)。
- 线上数据落 hostPath `/var/lib/cube/video2slides`(单节点 k3s,pod 重启不丢)。
## 本地跑
```bash
# 后端(数据 / 前端目录用 env 指过去,端口 8080)
VIDEO2SLIDES_DATA_DIR=/tmp/v2sdata VIDEO2SLIDES_DIST_DIR=apps/video2slides/frontend \
cargo run -p video2slides
```
打开 <http://localhost:8080>。需要本机有 `ffmpeg` / `ffprobe`
## 部署
push 到 master 且改了 `apps/video2slides/**``.gitea/workflows/deploy-video2slides.yml` 自动 build musl → 打 debian+ffmpeg 镜像(`--no-cache`)→ push registry → `kubectl apply` + rollout。
namespace `cube-video2slides`,已手工建好 `registry-creds`(从别的 ns 拷的,不进 git)。换 ns 重建命令:
```bash
kubectl -n cube-webgl get secret registry-creds -o yaml \
| sed 's/namespace: cube-webgl/namespace: cube-video2slides/' \
| kubectl apply -f -
```