## v0.9.20260325_144654 ### Features - API Key Authentication System - Job Worker System - V2 Backup Versioning ### Bug Fixes - get_processor_results_by_job column mapping Co-authored-by: OpenCode
541 lines
16 KiB
Markdown
541 lines
16 KiB
Markdown
# Momentry Core 開發日誌
|
||
|
||
| 項目 | 內容 |
|
||
|------|------|
|
||
| 建立者 | Warren |
|
||
| 建立時間 | 2026-03-18 |
|
||
| 文件版本 | V1.0 |
|
||
|
||
---
|
||
|
||
## 版本歷史
|
||
|
||
| 版本 | 日期 | 目的 | 操作人 | 工具/模型 |
|
||
|------|------|------|--------|-----------|
|
||
| V1.0 | 2026-03-18 | 創建文件 | Warren | OpenCode / MiniMax M2.5 |
|
||
|
||
---
|
||
|
||
> **文檔維護開始**:2026-03-18
|
||
> **⚠️ 補充說明**:事後補記(2026-03-18 以前),僅供參考。未來紀錄將即時記錄,參考價值較高。
|
||
|
||
---
|
||
|
||
## 開發工具
|
||
|
||
### Coding LLM 模型
|
||
|
||
| 階段 | 工具 | 模型 | ID | 說明 |
|
||
|------|------|------|-----|------|
|
||
| **初期** | Claude CLI | - | - | 初始專案架構建立 |
|
||
| **中期** | OpenCode | big-pickle | opencode/big-pickle | 主要開發協作者 |
|
||
|
||
**切換記錄**:
|
||
- 初期使用 Claude CLI 建立專案基本架構
|
||
- 中期切換至 OpenCode (big-pickle) 進行主要功能開發
|
||
|
||
---
|
||
|
||
## 2026-03-17
|
||
|
||
### ML 模型選用
|
||
|
||
| Processor | 模型 | 版本/大小 | 說明 |
|
||
|----------|------|-----------|------|
|
||
| **ASR** | WhisperX (faster-whisper) | base, int8 | 語音識別 + 對話分段 |
|
||
| **CUT** | PySceneDetect | 0.6.7.1 | ContentDetector 場景檢測 |
|
||
| **YOLO** | YOLOv8n | yolov8n.pt (6.2MB) | 物體檢測(nano 版本最快) |
|
||
| **OCR** | EasyOCR | 1.7.2 | 文字識別 |
|
||
| **Face** | OpenCV Haar Cascade | built-in | 人臉檢測(無需額外下載) |
|
||
| **Pose** | YOLOv8n-Pose | yolov8n-pose.pt (6.5MB) | 姿態估計(nano 版本) |
|
||
|
||
**模型下載**:
|
||
- YOLOv8n: `yolov8n.pt` (6.2MB)
|
||
- YOLOv8n-Pose: `yolov8n-pose.pt` (6.5MB)
|
||
|
||
**Python 依賴**:
|
||
```
|
||
torch==2.8.0
|
||
whisperx==3.8.2
|
||
ultralytics==8.4.23
|
||
scenedetect==0.6.7.1
|
||
easyocr==1.7.2
|
||
opencv-python==4.13.0.92
|
||
```
|
||
|
||
---
|
||
|
||
### ASR 實作完成
|
||
- 完成 Python ML processor scripts(使用本地模型)
|
||
- `asrx_processor.py` - whisperx for speaker diarization
|
||
- `cut_processor.py` - PySceneDetect for scene detection
|
||
- `yolo_processor.py` - YOLOv8 for object detection
|
||
- `ocr_processor.py` - EasyOCR for text recognition
|
||
- `face_processor.py` - OpenCV Haar Cascade for face detection
|
||
- `pose_processor.py` - YOLOv8 Pose for pose estimation
|
||
|
||
- 更新 `requirements.txt` with all dependencies
|
||
- 安裝完成:torch 2.8.0, whisperx 3.8.2, ultralytics 8.4.23, scenedetect 0.6.7.1, easyocr 1.7.2, opencv-python 4.13.0.92
|
||
- 下載模型:YOLOv8n.pt (6.2MB), YOLOv8n-Pose.pt (6.5MB)
|
||
|
||
### Async Streaming 實作
|
||
- 更新 Rust processor modules 使用 async streaming 進行 real-time progress
|
||
- `src/core/processor/asr.rs`
|
||
- `src/core/processor/cut.rs`
|
||
- `src/core/processor/yolo.rs`
|
||
- `src/core/processor/ocr.rs`
|
||
- `src/core/processor/face.rs`
|
||
- `src/core/processor/pose.rs`
|
||
|
||
### 測試結果
|
||
- 測試影片:BigBuckBunny_320x180.mp4
|
||
- ASR: 4 segments
|
||
- CUT: 134 scenes
|
||
- YOLO: 14315 frames(每幀處理耗時)
|
||
- OCR: 40 frames with text
|
||
- Face: 44 frames with faces
|
||
- Pose: Timeout
|
||
|
||
---
|
||
|
||
### Warning 清理
|
||
修復 clippy warnings:
|
||
- 移除未使用的 imports (HashMap in mongodb_db.rs, postgres_db.rs)
|
||
- 新增 `#[allow(dead_code)]` 標註未使用變數
|
||
- 新增 `Default` implementation for MongoDb, QdrantDb
|
||
- 將 `probe` module 重新命名為 `ffprobe`
|
||
- 新增 `player` feature in Cargo.toml
|
||
- 修復 `format_in_format_args` 警告
|
||
|
||
---
|
||
|
||
### TUI Progress Window 實作
|
||
建立新的 UI module:
|
||
- 建立 `src/ui/mod.rs`
|
||
- 建立 `src/ui/progress/mod.rs`
|
||
|
||
實作功能:
|
||
- ProcessorProgress 結構(追蹤每個 processor 狀態)
|
||
- ProgressState 結構(管理所有 processors)
|
||
- ProgressUi 結構(ratatui TUI 渲染)
|
||
- 整合到 `src/main.rs` 的 process 命令
|
||
|
||
TUI 顯示:
|
||
```
|
||
┌ Processing: BigBuckBunny_320x180.mp4 ────────────────────────────────────────┐
|
||
│ ASR [████████████] 100% (4 segs) │
|
||
│ CUT [████████████] 100% (134 scenes) │
|
||
│ ASRX [████████████] 100% (0 segs) │
|
||
│ YOLO [██░░░░░░░░░░░] 30% (4200/14315) ETA 2:30 │
|
||
│ OCR [---------] 0% │
|
||
│ Face [---------] 0% │
|
||
│ Pose [---------] 0% │
|
||
└──────────────────────────────────────────────────────────────────────────────┘
|
||
```
|
||
|
||
---
|
||
|
||
### 輸出位置討論
|
||
討論 stdout vs stderr vs TUI 的輸出配置:
|
||
- 最終結果 → stdout
|
||
- Python progress → 需改用 Redis Pub/Sub
|
||
- TUI Progress → stderr (ratatui)
|
||
|
||
---
|
||
|
||
## 2026-03-18
|
||
|
||
### Redis Message Bus 設計
|
||
討論使用 Redis 作為消息總線,分離 Python 輸出與 Rust TUI 顯示。
|
||
|
||
設計重點:
|
||
1. 頻道命名:`momentry:progress:{uuid}`
|
||
2. 本地 Redis:`localhost:6379`
|
||
3. 失敗策略:完全失效(因 stdout 問題未解決)
|
||
|
||
### UUID 使用時機分析
|
||
分析 Redis Key 上使用 UUID 的時機:
|
||
|
||
**全局 Keys(無 UUID)**:
|
||
- health, stats, jobs 管理
|
||
|
||
**Per-Video Keys(UUID 必要)**:
|
||
- job:{uuid}, progress:{uuid}, metrics:{uuid}
|
||
|
||
**Per-Processor Keys(UUID + Processor 必要)**:
|
||
- job:{uuid}:processor:{name}
|
||
|
||
### 備份系統整合
|
||
參考 `docs/SERVICE_ADDITION_GUIDE.md` 設計規範,規劃 OutputDir 模組:
|
||
|
||
1. **環境變數**:
|
||
- `MOMENTRY_OUTPUT_DIR` - JSON 輸出目錄
|
||
- `MOMENTRY_BACKUP_DIR` - 備份目錄(預設:`/Users/accusys/momentry/backup/momentry`)
|
||
- `MOMENTRY_BACKUP_ENABLED` - 啟用備份
|
||
|
||
2. **命名格式**:
|
||
- 備份格式:`momentry_data_{YYYYMMDD}_{HHMMSS}_{uuid}.{ext}`
|
||
- 校驗和:`{filename}.sha256`
|
||
|
||
3. **CLI 命令**:
|
||
- `cargo run -- backup list` - 列出備份
|
||
- `cargo run -- backup cleanup` - 清理舊備份
|
||
- `cargo run -- backup verify` - 驗證備份
|
||
|
||
---
|
||
|
||
### 監控系統整合
|
||
討論將 momentry_core 納入監控系統:
|
||
|
||
1. **Layer 2: Service 監控**
|
||
- 新增 momentry_core CLI 檢查
|
||
|
||
2. **Layer 7: Backup 監控**
|
||
- 新增 momentry 備份配置
|
||
|
||
3. **Redis 監控**
|
||
- 健康檢查
|
||
- Job 狀態監控
|
||
- 即時進度監控
|
||
|
||
---
|
||
|
||
## 實作完成項目
|
||
|
||
### 程式碼變更
|
||
|
||
| 日期 | 檔案 | 變更 |
|
||
|------|------|------|
|
||
| 2026-03-17 | `src/core/processor/*.rs` | Async streaming 更新 |
|
||
| 2026-03-17 | `src/ui/mod.rs` | 新增 UI module |
|
||
| 2026-03-17 | `src/ui/progress/mod.rs` | 新增 Progress TUI |
|
||
| 2026-03-17 | `src/main.rs` | 整合 Progress UI |
|
||
| 2026-03-18 | `src/core/storage/output_dir.rs` | 新增 OutputDir 模組 |
|
||
| 2026-03-18 | `src/core/storage/mod.rs` | 新增 output_dir export |
|
||
| 2026-03-18 | `src/core/db/redis_client.rs` | 新增 Redis 客戶端(Hash + Pub/Sub) |
|
||
| 2026-03-18 | `src/core/db/mod.rs` | 新增 redis_client export |
|
||
|
||
### 新增檔案
|
||
|
||
| 日期 | 檔案 | 說明 |
|
||
|------|------|------|
|
||
| 2026-03-18 | `docs/MOMENTRY_CORE_REDIS_KEYS.md` | Redis Key 設計規範 |
|
||
| 2026-03-18 | `docs/MOMENTRY_CORE_MONITORING.md` | 監控規範(暫定) |
|
||
| 2026-03-18 | `scripts/redis_publisher.py` | Redis 訊息發布模組 |
|
||
|
||
### 更新檔案
|
||
|
||
| 日期 | 檔案 | 說明 |
|
||
|------|------|------|
|
||
| 2026-03-17 | `Cargo.toml` | 新增 player feature |
|
||
| 2026-03-17 | `src/lib.rs` | 新增 ui module exports |
|
||
| 2026-03-18 | `docs/PENDING_ISSUES.md` | 新增問題 #2, #3 |
|
||
| 2026-03-18 | `src/core/storage/output_dir.rs` | 預設改為 `./output` |
|
||
| 2026-03-18 | `scripts/yolo_processor.py` | 新增 --uuid 參數 + Redis |
|
||
| 2026-03-18 | `scripts/cut_processor.py` | 新增 Redis |
|
||
| 2026-03-18 | `scripts/ocr_processor.py` | 新增 Redis |
|
||
| 2026-03-18 | `scripts/face_processor.py` | 新增 --uuid 參數 + Redis |
|
||
| 2026-03-18 | `scripts/pose_processor.py` | 新增 --uuid 參數 + Redis |
|
||
| 2026-03-18 | `scripts/asr_processor.py` | 新增 --uuid 參數 + Redis |
|
||
| 2026-03-18 | `scripts/asrx_processor.py` | 新增 --uuid 參數 + Redis |
|
||
| 2026-03-18 | `requirements.txt` | 新增 redis>=5.0.0 |
|
||
| 2026-03-18 | `src/core/processor/yolo.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/core/processor/cut.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/core/processor/ocr.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/core/processor/face.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/core/processor/pose.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/core/processor/asr.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/core/processor/asrx.rs` | 新增 uuid 參數 |
|
||
| 2026-03-18 | `src/main.rs` | 更新所有 processor 調用傳入 uuid |
|
||
| 2026-03-18 | `Cargo.toml` | 新增 futures-util 依賴 |
|
||
| 2026-03-18 | `src/core/db/redis_client.rs` | 新增 subscribe_and_callback 方法,密碼認證 |
|
||
| 2026-03-18 | `src/ui/progress/mod.rs` | 新增 update_from_redis 方法 |
|
||
| 2026-03-18 | `scripts/redis_publisher.py` | 新增密碼認證支援 |
|
||
| 2026-03-18 | 測試 | Redis Pub/Sub 成功運作 |
|
||
|
||
---
|
||
|
||
## 待解決問題
|
||
|
||
### 問題 #1: sqlx async INSERT 不會實際寫入數據庫
|
||
- 狀態:待解決
|
||
- 影響:`store_vector` 函數,PVector 存儲
|
||
|
||
### 問題 #2: TUI 與 stdout 輸出混合
|
||
- 狀態:已解決
|
||
- 解決方案:使用 Redis Message Bus
|
||
- 進度:
|
||
- ✅ Redis 客戶端 (`src/core/db/redis_client.rs`)
|
||
- ✅ Python redis_publisher.py
|
||
- ✅ 所有 Python processors 更新完成
|
||
- ✅ 所有 Rust processor 函數更新完成
|
||
- ✅ main.rs 調用更新完成
|
||
- ✅ Rust TUI Redis 訂閱已完成
|
||
|
||
### 問題 #3: Redis Message Bus 尚未實作
|
||
- 狀態:已解決
|
||
- 詳細設計:參考 `docs/MOMENTRY_CORE_REDIS_KEYS.md`
|
||
- 進度:Python 端 + Rust 端均已完成
|
||
|
||
---
|
||
|
||
## 環境變數
|
||
|
||
```bash
|
||
# 輸出目錄
|
||
MOMENTRY_OUTPUT_DIR=./output # 預設
|
||
|
||
# 備份
|
||
MOMENTRY_BACKUP_ENABLED=false # 預設
|
||
MOMENTRY_BACKUP_DIR=/Users/accusys/momentry/backup/momentry
|
||
|
||
# Redis(未來實作)
|
||
REDIS_URL=redis://localhost:6379
|
||
REDIS_PASSWORD=accusys
|
||
```
|
||
|
||
---
|
||
|
||
## 數據庫
|
||
|
||
- PostgreSQL: `postgres://accusys@localhost:5432/momentry`
|
||
- Redis: `localhost:6379`(待實作)
|
||
- Qdrant: `localhost:6333`
|
||
|
||
---
|
||
|
||
## 指令範例
|
||
|
||
```bash
|
||
# 註冊視頻
|
||
cargo run -- register /path/to/video.mp4
|
||
|
||
# 處理視頻
|
||
cargo run -- process <uuid>
|
||
|
||
# 列出備份
|
||
cargo run -- backup list
|
||
|
||
# 清理備份
|
||
cargo run -- backup cleanup
|
||
|
||
# 驗證備份
|
||
cargo run -- backup verify
|
||
|
||
# 查看狀態
|
||
cargo run -- status
|
||
|
||
# API Server
|
||
cargo run -- server --host 0.0.0.0 --port 3000
|
||
```
|
||
|
||
---
|
||
|
||
## 2026-03-18 (進行中)
|
||
|
||
### Redis Message Bus 實作
|
||
|
||
**問題**:TUI 與 Python stdout 輸出混合,導致 TUI 顯示混亂
|
||
|
||
**解決方案**:使用 Redis Pub/Sub 作為訊息匯流排
|
||
|
||
**實作內容**:
|
||
|
||
| 元件 | 檔案 | 狀態 |
|
||
|------|------|------|
|
||
| Redis 客戶端 | `src/core/db/redis_client.rs` | ✅ |
|
||
| Progress 訂閱 | `src/main.rs` | ✅ |
|
||
| UI 更新 | `src/ui/progress/mod.rs` | ✅ |
|
||
| Python Publisher | `scripts/redis_publisher.py` | ✅ |
|
||
| Python Processors | 7 個 `scripts/*_processor.py` | ✅ |
|
||
| Rust 函數 | `src/core/processor/*.rs` | ✅ |
|
||
|
||
**流程**:
|
||
```
|
||
Python Processor ──(Redis Pub)──> Redis ──(Subscribe)──> Rust TUI
|
||
```
|
||
|
||
**測試結果**:
|
||
- Redis 連線 ✅
|
||
- 密碼認證 ✅
|
||
- 即時進度發布 ✅
|
||
- TUI 即時更新 ✅
|
||
|
||
**新增依賴**:
|
||
- `futures-util = "0.3"` (Cargo.toml)
|
||
- `redis >= 5.0.0` (requirements.txt)
|
||
|
||
---
|
||
|
||
## 2026-03-18 (HTTP API)
|
||
|
||
### HTTP API 實作
|
||
|
||
**問題**:TUI 運作正常但使用者偏好 HTTP API 來查詢進度
|
||
|
||
**解決方案**:建立 HTTP 端點 + Redis Hash 儲存
|
||
|
||
**實作內容**:
|
||
|
||
| 元件 | 檔案 | 變更 |
|
||
|------|------|------|
|
||
| HTTP 端點 | `src/api/server.rs` | 新增 `/api/v1/progress/:uuid` |
|
||
| Redis Hash 查詢 | `src/core/db/redis_client.rs` | 新增 `get_processor_status` 方法 |
|
||
| Progress 儲存 | `src/main.rs` | 新增 Redis HSET 儲存進度 |
|
||
|
||
**API 端點**:
|
||
```
|
||
GET /api/v1/progress/:uuid
|
||
|
||
Response:
|
||
{
|
||
"uuid": "5dea6618a606e7c7",
|
||
"processors": [
|
||
{"name": "asr", "status": "complete", "current": 0, "total": 0, "message": "7 segments"},
|
||
{"name": "cut", "status": "complete", "current": 134, "total": 134, "message": "134 scenes"},
|
||
{"name": "yolo", "status": "complete", "current": 14300, "total": 14315, "message": "..."},
|
||
...
|
||
]
|
||
}
|
||
```
|
||
|
||
**流程**:
|
||
```
|
||
Python Processor ──(Redis Pub)──> Redis ──(Subscribe)──> Rust TUI
|
||
└──(HSET)──> Redis Hash
|
||
│
|
||
HTTP Client ──(GET /progress/:uuid)──> Rust API ─(HGETALL)──> Redis Hash
|
||
```
|
||
|
||
**測試結果**:
|
||
- ✅ 編譯成功
|
||
- ✅ API 伺服器啟動 (port 3002)
|
||
- ✅ 即時進度查詢
|
||
- ✅ 完整流程測試 (BigBuckBunny_320x180.mp4)
|
||
|
||
**除錯記錄**:
|
||
1. 語法錯誤:main.rs 有重複程式碼區塊 (lines 297-322),已移除
|
||
2. DB 連線池:從 5 增加到 10 個連線
|
||
3. PostgreSQL 狀態:處理 shutdown 狀態,殺掉 stale 連線
|
||
|
||
**新增變更**:
|
||
- `src/api/server.rs` - 新增進度端點
|
||
- `src/core/db/redis_client.rs` - 新增 `get_processor_status` 方法
|
||
- `src/core/db/postgres_db.rs` - 連線池 5→10
|
||
- `src/main.rs` - Redis Hash 儲存 + 語法修復
|
||
|
||
**使用方式**:
|
||
```bash
|
||
# 啟動 API 伺服器
|
||
cargo run --bin momentry -- server --host 127.0.0.1 --port 3002
|
||
|
||
# 註冊影片
|
||
cargo run --bin momentry -- register ~/test_video/BigBuckBunny_320x180.mp4
|
||
|
||
# 處理影片
|
||
cargo run --bin momentry -- process <uuid>
|
||
|
||
# 查詢進度
|
||
curl http://127.0.0.1:3002/api/v1/progress/<uuid>
|
||
```
|
||
|
||
---
|
||
|
||
## 2026-03-18 (Dashboard)
|
||
|
||
### Web Dashboard 實作
|
||
|
||
**目標**:建立 Web 介面監控 momentry_core 處理進度
|
||
|
||
**技術選擇**:Static HTML + JavaScript (非 WASM)
|
||
|
||
**實作內容**:
|
||
|
||
| 元件 | 檔案 | 說明 |
|
||
|------|------|------|
|
||
| Dashboard | `momentry_dashboard/dist/index.html` | 靜態 HTML 頁面 |
|
||
| API 代理 | Caddyfile port 3200 | 反向代理到 API server |
|
||
|
||
**功能**:
|
||
- 影片列表顯示
|
||
- 即時進度條 (每 5 秒自動刷新)
|
||
- 搜尋功能
|
||
- 處理器狀態 (ASR/CUT/YOLO/OCR/Face/Pose)
|
||
|
||
**訪問**:
|
||
- Dashboard: http://localhost:3200
|
||
- API: http://localhost:3200/api/v1/*
|
||
|
||
---
|
||
|
||
## 發生問題記錄
|
||
|
||
### HTTP API 問題
|
||
|
||
1. **語法錯誤** (main.rs)
|
||
- 位置:lines 297-322
|
||
- 原因:重複的程式碼區塊
|
||
- 解決:移除重複區塊
|
||
|
||
2. **DB 連線池耗盡**
|
||
- 原因:預設 5 個連線不足
|
||
- 解決:增加到 10 個連線
|
||
|
||
3. **PostgreSQL shutdown 狀態**
|
||
- 原因:共享記憶體未釋放
|
||
- 解決:殺掉 stale 連線
|
||
|
||
### WASM Dashboard 問題
|
||
|
||
1. **Yew 版本問題**
|
||
- 嘗試:yew 0.21 → 0.23
|
||
- 問題:feature 名稱變更 (`web-sys` → `web_sys` → `csr`)
|
||
- 解決:放棄 WASM,改用靜態 HTML
|
||
|
||
2. **編譯錯誤**
|
||
- `wasm32-unknown-unknown` target 未安裝
|
||
- 解決:`rustup target add wasm32-unknown-unknown`
|
||
|
||
3. **Yew 0.23 API 變更**
|
||
- Properties 需要 PartialEq derive
|
||
- 多處 API 語法變更
|
||
- 放棄 WASM 方案
|
||
|
||
### Gitea Push 問題
|
||
|
||
1. **Remote URL 錯誤**
|
||
- 原因:使用 localhost:3000 而非 gitea.momentry.ddns.net
|
||
- 解決:建立新 repo `momentry_core_0_1`
|
||
|
||
2. **認證問題**
|
||
- SSH key 未授權
|
||
- 密碼認證成功推送
|
||
|
||
### Caddy 設定問題
|
||
|
||
1. **API 代理順序**
|
||
- 問題:try_files 在 reverse_proxy 之前導致 API 回傳 HTML
|
||
- 解決:使用 `handle` 區塊明確定義順序
|
||
|
||
```caddyfile
|
||
:3200 {
|
||
handle /api/* {
|
||
reverse_proxy localhost:3002
|
||
}
|
||
handle {
|
||
root * /Users/accusys/momentry_dashboard/dist
|
||
try_files {path} /index.html
|
||
file_server
|
||
}
|
||
}
|
||
```
|
||
|
||
---
|
||
|
||
## 未來工作
|
||
|
||
- [ ] 修復 WASM Dashboard (Yew 0.23 相容性)
|
||
- [ ] 新增影片播放器整合
|
||
- [ ] WebSocket 實時推送
|
||
- [ ] 移動端響應式設計
|