Update api/seedvr_server.py
Browse files- api/seedvr_server.py +30 -30
api/seedvr_server.py
CHANGED
|
@@ -28,60 +28,61 @@ except ImportError as e:
|
|
| 28 |
print(f"Verifique se o repositório em '{SEEDVR_REPO_PATH}' está correto e completo.")
|
| 29 |
raise e
|
| 30 |
|
| 31 |
-
INIT = False
|
| 32 |
|
| 33 |
class SeedVRServer:
|
| 34 |
def __init__(self, **kwargs):
|
| 35 |
"""
|
| 36 |
Inicializa o servidor, define os caminhos e prepara o ambiente.
|
| 37 |
"""
|
| 38 |
-
|
| 39 |
-
|
| 40 |
-
|
| 41 |
-
|
| 42 |
-
|
| 43 |
-
|
| 44 |
-
|
| 45 |
-
|
| 46 |
|
| 47 |
if INIT:
|
| 48 |
-
print("
|
| 49 |
-
|
|
|
|
|
|
|
| 50 |
p.mkdir(parents=True, exist_ok=True)
|
| 51 |
-
|
| 52 |
-
setup_dependencies()
|
| 53 |
print("📦 SeedVRServer (Modo de Chamada Direta) pronto.")
|
| 54 |
-
|
| 55 |
-
|
| 56 |
-
print("⚙️ SeedVRServer pronto.")
|
| 57 |
|
| 58 |
-
def setup_dependencies():
|
| 59 |
""" Garante que o repositório e os modelos estão presentes. """
|
| 60 |
self._ensure_repo()
|
| 61 |
self._ensure_model()
|
| 62 |
|
| 63 |
def _ensure_repo(self) -> None:
|
| 64 |
""" Clona o repositório do SeedVR se ele não existir. """
|
| 65 |
-
if not (SEEDVR_ROOT / ".git").exists():
|
| 66 |
-
print(f"[SeedVRServer] Clonando repositório para {SEEDVR_ROOT}...")
|
| 67 |
# Usamos subprocess.run aqui porque é uma tarefa de inicialização única.
|
| 68 |
-
subprocess.run(["git", "clone", "--depth", "1", REPO_URL, str(SEEDVR_ROOT)], check=True)
|
| 69 |
else:
|
| 70 |
print("[SeedVRServer] Repositório SeedVR já existe.")
|
| 71 |
|
| 72 |
def _ensure_model(self) -> None:
|
| 73 |
""" Baixa os checkpoints do Hugging Face se não existirem localmente. """
|
| 74 |
-
print(f"[SeedVRServer] Verificando checkpoints (FP16) em {CKPTS_ROOT}...")
|
| 75 |
model_files = {
|
| 76 |
"seedvr2_ema_3b_fp16.safetensors": "MonsterMMORPG/SeedVR2_SECourses",
|
| 77 |
"ema_vae_fp16.safetensors": "MonsterMMORPG/SeedVR2_SECourses",
|
| 78 |
}
|
| 79 |
for filename, repo_id in model_files.items():
|
| 80 |
-
if not (CKPTS_ROOT / filename).exists():
|
| 81 |
print(f"Baixando {filename} de {repo_id}...")
|
| 82 |
hf_hub_download(
|
| 83 |
-
repo_id=repo_id, filename=filename, local_dir=str(CKPTS_ROOT),
|
| 84 |
-
cache_dir=str(HF_HOME_CACHE), token=os.getenv("HF_TOKEN")
|
| 85 |
)
|
| 86 |
print("[SeedVRServer] Checkpoints (FP16) estão no local correto.")
|
| 87 |
|
|
@@ -95,7 +96,7 @@ class SeedVRServer:
|
|
| 95 |
Executa a inferência diretamente no mesmo processo e retorna o caminho do arquivo de saída.
|
| 96 |
"""
|
| 97 |
# Cria um diretório de saída único para salvar o resultado.
|
| 98 |
-
out_dir = OUTPUT_ROOT / f"run_{int(time.time())}_{Path(file_path).stem}"
|
| 99 |
out_dir.mkdir(parents=True, exist_ok=True)
|
| 100 |
output_filepath = out_dir / f"result_{Path(file_path).stem}.mp4"
|
| 101 |
|
|
@@ -104,14 +105,14 @@ class SeedVRServer:
|
|
| 104 |
args = SimpleNamespace(
|
| 105 |
video_path=file_path,
|
| 106 |
output=str(output_filepath),
|
| 107 |
-
model_dir=str(CKPTS_ROOT),
|
| 108 |
seed=seed,
|
| 109 |
resolution=res_h, # O script do SeedVR usa a altura (lado menor) como referência.
|
| 110 |
batch_size=sp_size,
|
| 111 |
-
model="
|
| 112 |
-
preserve_vram=
|
| 113 |
debug=True, # Mantém o debug ativo para logs detalhados.
|
| 114 |
-
cuda_device=",".join(map(str, range(NUM_GPUS_TOTAL))),
|
| 115 |
skip_first_frames=0,
|
| 116 |
load_cap=0,
|
| 117 |
output_format='video' # Garante que sempre gere vídeo
|
|
@@ -142,7 +143,6 @@ class SeedVRServer:
|
|
| 142 |
except Exception as e:
|
| 143 |
print(f"❌ Error during direct inference execution: {e}")
|
| 144 |
import traceback
|
| 145 |
-
init = False
|
| 146 |
traceback.print_exc()
|
| 147 |
# Propaga o erro para a UI do Gradio, que o exibirá de forma amigável.
|
| 148 |
raise
|
|
|
|
| 28 |
print(f"Verifique se o repositório em '{SEEDVR_REPO_PATH}' está correto e completo.")
|
| 29 |
raise e
|
| 30 |
|
| 31 |
+
INIT = False
|
| 32 |
|
| 33 |
class SeedVRServer:
|
| 34 |
def __init__(self, **kwargs):
|
| 35 |
"""
|
| 36 |
Inicializa o servidor, define os caminhos e prepara o ambiente.
|
| 37 |
"""
|
| 38 |
+
self.SEEDVR_ROOT = SEEDVR_REPO_PATH
|
| 39 |
+
self.CKPTS_ROOT = Path("/data/seedvr_models_fp16")
|
| 40 |
+
self.OUTPUT_ROOT = Path(os.getenv("OUTPUT_ROOT", "/app/outputs"))
|
| 41 |
+
self.INPUT_ROOT = Path(os.getenv("INPUT_ROOT", "/app/inputs"))
|
| 42 |
+
self.HF_HOME_CACHE = Path(os.getenv("HF_HOME", "/data/.cache/huggingface"))
|
| 43 |
+
self.REPO_URL = os.getenv("SEEDVR_GIT_URL", "https://github.com/numz/ComfyUI-SeedVR2_VideoUpscaler")
|
| 44 |
+
self.NUM_GPUS_TOTAL = int(os.getenv("NUM_GPUS", "4"))
|
| 45 |
+
|
| 46 |
|
| 47 |
if INIT:
|
| 48 |
+
print("🚀 SeedVRServer ja inicializando...")
|
| 49 |
+
else:
|
| 50 |
+
print("⚙️ SeedVRServer (Modo de Chamada Direta) inicializando...")
|
| 51 |
+
for p in [self.CKPTS_ROOT, self.OUTPUT_ROOT, self.INPUT_ROOT, self.HF_HOME_CACHE]:
|
| 52 |
p.mkdir(parents=True, exist_ok=True)
|
| 53 |
+
|
| 54 |
+
self.setup_dependencies()
|
| 55 |
print("📦 SeedVRServer (Modo de Chamada Direta) pronto.")
|
| 56 |
+
INIT = True
|
| 57 |
+
|
|
|
|
| 58 |
|
| 59 |
+
def setup_dependencies(self):
|
| 60 |
""" Garante que o repositório e os modelos estão presentes. """
|
| 61 |
self._ensure_repo()
|
| 62 |
self._ensure_model()
|
| 63 |
|
| 64 |
def _ensure_repo(self) -> None:
|
| 65 |
""" Clona o repositório do SeedVR se ele não existir. """
|
| 66 |
+
if not (self.SEEDVR_ROOT / ".git").exists():
|
| 67 |
+
print(f"[SeedVRServer] Clonando repositório para {self.SEEDVR_ROOT}...")
|
| 68 |
# Usamos subprocess.run aqui porque é uma tarefa de inicialização única.
|
| 69 |
+
subprocess.run(["git", "clone", "--depth", "1", self.REPO_URL, str(self.SEEDVR_ROOT)], check=True)
|
| 70 |
else:
|
| 71 |
print("[SeedVRServer] Repositório SeedVR já existe.")
|
| 72 |
|
| 73 |
def _ensure_model(self) -> None:
|
| 74 |
""" Baixa os checkpoints do Hugging Face se não existirem localmente. """
|
| 75 |
+
print(f"[SeedVRServer] Verificando checkpoints (FP16) em {self.CKPTS_ROOT}...")
|
| 76 |
model_files = {
|
| 77 |
"seedvr2_ema_3b_fp16.safetensors": "MonsterMMORPG/SeedVR2_SECourses",
|
| 78 |
"ema_vae_fp16.safetensors": "MonsterMMORPG/SeedVR2_SECourses",
|
| 79 |
}
|
| 80 |
for filename, repo_id in model_files.items():
|
| 81 |
+
if not (self.CKPTS_ROOT / filename).exists():
|
| 82 |
print(f"Baixando {filename} de {repo_id}...")
|
| 83 |
hf_hub_download(
|
| 84 |
+
repo_id=repo_id, filename=filename, local_dir=str(self.CKPTS_ROOT),
|
| 85 |
+
cache_dir=str(self.HF_HOME_CACHE), token=os.getenv("HF_TOKEN")
|
| 86 |
)
|
| 87 |
print("[SeedVRServer] Checkpoints (FP16) estão no local correto.")
|
| 88 |
|
|
|
|
| 96 |
Executa a inferência diretamente no mesmo processo e retorna o caminho do arquivo de saída.
|
| 97 |
"""
|
| 98 |
# Cria um diretório de saída único para salvar o resultado.
|
| 99 |
+
out_dir = self.OUTPUT_ROOT / f"run_{int(time.time())}_{Path(file_path).stem}"
|
| 100 |
out_dir.mkdir(parents=True, exist_ok=True)
|
| 101 |
output_filepath = out_dir / f"result_{Path(file_path).stem}.mp4"
|
| 102 |
|
|
|
|
| 105 |
args = SimpleNamespace(
|
| 106 |
video_path=file_path,
|
| 107 |
output=str(output_filepath),
|
| 108 |
+
model_dir=str(self.CKPTS_ROOT),
|
| 109 |
seed=seed,
|
| 110 |
resolution=res_h, # O script do SeedVR usa a altura (lado menor) como referência.
|
| 111 |
batch_size=sp_size,
|
| 112 |
+
model="seedvr2_ema_7b_fp16.safetensors",
|
| 113 |
+
preserve_vram=False,
|
| 114 |
debug=True, # Mantém o debug ativo para logs detalhados.
|
| 115 |
+
cuda_device=",".join(map(str, range(self.NUM_GPUS_TOTAL))),
|
| 116 |
skip_first_frames=0,
|
| 117 |
load_cap=0,
|
| 118 |
output_format='video' # Garante que sempre gere vídeo
|
|
|
|
| 143 |
except Exception as e:
|
| 144 |
print(f"❌ Error during direct inference execution: {e}")
|
| 145 |
import traceback
|
|
|
|
| 146 |
traceback.print_exc()
|
| 147 |
# Propaga o erro para a UI do Gradio, que o exibirá de forma amigável.
|
| 148 |
raise
|