VeuReu commited on
Commit
448bb8e
·
verified ·
1 Parent(s): d350726

Upload 2 files

Browse files
Files changed (2) hide show
  1. api.py +17 -2
  2. character_detection.py +12 -4
api.py CHANGED
@@ -1,6 +1,6 @@
1
  from __future__ import annotations
2
  from fastapi import FastAPI, UploadFile, File, Form, BackgroundTasks, HTTPException
3
- from fastapi.responses import JSONResponse
4
  from fastapi.middleware.cors import CORSMiddleware
5
  from pathlib import Path
6
  import shutil
@@ -10,6 +10,7 @@ import uuid
10
  from datetime import datetime
11
  from typing import Dict
12
  from enum import Enum
 
13
 
14
  from video_processing import process_video_pipeline
15
  from casting_loader import ensure_chroma, build_faces_index, build_voices_index
@@ -125,6 +126,19 @@ def get_job_status(job_id: str):
125
 
126
  return response
127
 
 
 
 
 
 
 
 
 
 
 
 
 
 
128
  def process_video_job(job_id: str):
129
  """
130
  Procesa el vídeo de forma asíncrona.
@@ -155,7 +169,8 @@ def process_video_job(job_id: str):
155
  video_path=video_path,
156
  output_base=str(base),
157
  epsilon=epsilon,
158
- min_cluster_size=min_cluster_size
 
159
  )
160
 
161
  characters = result.get("characters", [])
 
1
  from __future__ import annotations
2
  from fastapi import FastAPI, UploadFile, File, Form, BackgroundTasks, HTTPException
3
+ from fastapi.responses import JSONResponse, FileResponse
4
  from fastapi.middleware.cors import CORSMiddleware
5
  from pathlib import Path
6
  import shutil
 
10
  from datetime import datetime
11
  from typing import Dict
12
  from enum import Enum
13
+ import os
14
 
15
  from video_processing import process_video_pipeline
16
  from casting_loader import ensure_chroma, build_faces_index, build_voices_index
 
126
 
127
  return response
128
 
129
+ @app.get("/files/{video_name}/{char_id}/{filename}")
130
+ def serve_character_file(video_name: str, char_id: str, filename: str):
131
+ """
132
+ Sirve archivos estáticos de personajes (imágenes).
133
+ Ejemplo: /files/dif_catala_1/char1/representative.jpg
134
+ """
135
+ file_path = TEMP_ROOT / video_name / char_id / filename
136
+
137
+ if not file_path.exists():
138
+ raise HTTPException(status_code=404, detail="File not found")
139
+
140
+ return FileResponse(file_path)
141
+
142
  def process_video_job(job_id: str):
143
  """
144
  Procesa el vídeo de forma asíncrona.
 
169
  video_path=video_path,
170
  output_base=str(base),
171
  epsilon=epsilon,
172
+ min_cluster_size=min_cluster_size,
173
+ video_name=video_name
174
  )
175
 
176
  characters = result.get("characters", [])
character_detection.py CHANGED
@@ -34,15 +34,17 @@ class CharacterDetector:
34
  Detector de personajes que integra el trabajo de Ana.
35
  """
36
 
37
- def __init__(self, video_path: str, output_base: Path):
38
  """
39
  Args:
40
  video_path: Ruta al archivo de vídeo
41
  output_base: Directorio base para guardar resultados (ej: /tmp/temp/video_name)
 
42
  """
43
  self.video_path = video_path
44
  self.output_base = Path(output_base)
45
  self.output_base.mkdir(parents=True, exist_ok=True)
 
46
 
47
  # Crear subdirectorios
48
  self.faces_dir = self.output_base / "faces"
@@ -227,10 +229,14 @@ class CharacterDetector:
227
  shutil.copy(representative_src, representative_dst)
228
 
229
  # Metadata del personaje
 
 
 
230
  characters.append({
231
  "id": char_id,
232
  "name": f"Personatge {cluster_id + 1}",
233
- "image_path": str(char_dir / "representative.jpg"),
 
234
  "num_faces": len(face_indices),
235
  "folder": str(char_dir)
236
  })
@@ -298,7 +304,8 @@ class CharacterDetector:
298
 
299
  # Función de conveniencia para usar en el API
300
  def detect_characters_from_video(video_path: str, output_base: str,
301
- epsilon: float = 0.5, min_cluster_size: int = 2) -> Dict[str, Any]:
 
302
  """
303
  Función de alto nivel para detectar personajes en un vídeo.
304
 
@@ -307,11 +314,12 @@ def detect_characters_from_video(video_path: str, output_base: str,
307
  output_base: Directorio base para guardar resultados
308
  epsilon: Parámetro epsilon para DBSCAN
309
  min_cluster_size: Tamaño mínimo de cluster
 
310
 
311
  Returns:
312
  Dict con resultados: {"characters": [...], "analysis_path": "..."}
313
  """
314
- detector = CharacterDetector(video_path, Path(output_base))
315
  characters, analysis_path = detector.detect_characters(epsilon, min_cluster_size)
316
 
317
  return {
 
34
  Detector de personajes que integra el trabajo de Ana.
35
  """
36
 
37
+ def __init__(self, video_path: str, output_base: Path, video_name: str = None):
38
  """
39
  Args:
40
  video_path: Ruta al archivo de vídeo
41
  output_base: Directorio base para guardar resultados (ej: /tmp/temp/video_name)
42
+ video_name: Nombre del vídeo (para construir URLs)
43
  """
44
  self.video_path = video_path
45
  self.output_base = Path(output_base)
46
  self.output_base.mkdir(parents=True, exist_ok=True)
47
+ self.video_name = video_name or self.output_base.name
48
 
49
  # Crear subdirectorios
50
  self.faces_dir = self.output_base / "faces"
 
229
  shutil.copy(representative_src, representative_dst)
230
 
231
  # Metadata del personaje
232
+ # Construir URL relativa para la imagen
233
+ image_url = f"/files/{self.video_name}/{char_id}/representative.jpg"
234
+
235
  characters.append({
236
  "id": char_id,
237
  "name": f"Personatge {cluster_id + 1}",
238
+ "image_path": str(char_dir / "representative.jpg"), # Ruta local
239
+ "image_url": image_url, # URL para el API
240
  "num_faces": len(face_indices),
241
  "folder": str(char_dir)
242
  })
 
304
 
305
  # Función de conveniencia para usar en el API
306
  def detect_characters_from_video(video_path: str, output_base: str,
307
+ epsilon: float = 0.5, min_cluster_size: int = 2,
308
+ video_name: str = None) -> Dict[str, Any]:
309
  """
310
  Función de alto nivel para detectar personajes en un vídeo.
311
 
 
314
  output_base: Directorio base para guardar resultados
315
  epsilon: Parámetro epsilon para DBSCAN
316
  min_cluster_size: Tamaño mínimo de cluster
317
+ video_name: Nombre del vídeo (para construir URLs)
318
 
319
  Returns:
320
  Dict con resultados: {"characters": [...], "analysis_path": "..."}
321
  """
322
+ detector = CharacterDetector(video_path, Path(output_base), video_name=video_name)
323
  characters, analysis_path = detector.detect_characters(epsilon, min_cluster_size)
324
 
325
  return {