subtitle-studio: 字幕生成系统

- 选择文件夹/单文件 → SenseVoice 转录 → LLM 修正 → 多路线翻译 → 双语 SRT
- 路线:直译中文 / 英转中 / 仅转录
- 并发流水线:转录(可调) + LLM 并发(可调),降噪拆锁并发
- 断点续跑:.subtitle-work/ 中间产物,三阶段独立续跑 + 翻译段级续跑
- 去重:history 跟随视频文件夹,防重复任务保护
- 实时进度:SSE 推送 + 耗时显示 + 子任务状态 + 重新生成按钮
- 时间戳调优:VAD silence_schedule + noisereduce 降噪 + 完整性校验
This commit is contained in:
hmo
2026-08-16 20:17:14 +08:00
commit 7de5ab3902
20 changed files with 2410 additions and 0 deletions
+55
View File
@@ -0,0 +1,55 @@
# -*- coding: utf-8 -*-
"""
subtitle-studio 后台启动器(无阻塞)
用 subprocess.Popen 启动 uvicornshell 调用立即返回
日志写到 logs/server.log
用法: python start_server.py [port]
"""
import sys, os, subprocess, time, threading
PYTHON = sys.executable
PROJECT_ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
APP_DIR = os.path.join(PROJECT_ROOT, "src")
LOG_DIR = os.path.join(PROJECT_ROOT, "logs")
PORT = sys.argv[1] if len(sys.argv) > 1 else "8788"
os.makedirs(LOG_DIR, exist_ok=True)
log_path = os.path.join(LOG_DIR, "server.log")
def is_running(port):
"""端口是否已被监听"""
try:
import socket
with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
s.settimeout(1)
return s.connect_ex(("127.0.0.1", int(port))) == 0
except Exception:
return False
def main():
if is_running(PORT):
print(f"subtitle-studio 已在运行: http://127.0.0.1:{PORT}")
return
# 打开日志文件(追加模式)
logf = open(log_path, 'a', encoding='utf-8', buffering=1)
# 真正的异步启动:不等待,不继承句柄
proc = subprocess.Popen(
[PYTHON, "-m", "uvicorn", "substudio.main:app",
"--host", "127.0.0.1", "--port", PORT, "--app-dir", APP_DIR],
cwd=PROJECT_ROOT,
stdout=logf,
stderr=subprocess.STDOUT,
creationflags=subprocess.CREATE_NO_WINDOW,
)
print(f"已启动 subtitle-studio (PID {proc.pid})")
print(f"服务地址: http://127.0.0.1:{PORT}")
print(f"日志: {log_path}")
# 不等待进程,直接返回
if __name__ == "__main__":
main()