bolt Valebyte VPS desde $4/mes — NVMe, despliegue en 60s.

Obtener VPS arrow_forward
eco Principiante Tutorial/Cómo hacer

WhisperX en VPS: transcripción con marcas de tiempo y separación de voces

calendar_month Sep 18, 2026 schedule 19 min de lectura visibility 60 vistas
WhisperX на VPS: транскрибация с таймкодами и разделением голосов
info

¿Necesitas un servidor para esta guía? Ofrecemos servidores dedicados y VPS en más de 50 países con configuración instantánea.

¿Necesitas un VPS para esta guía?

Explore otras opciones de servidores dedicados en

WhisperX en VPS: transcripción con códigos de tiempo y separación de voces

TL;DR

WhisperX permite desplegar en un VPS un servicio propio de transcripción de audio y vídeo: obtener texto, códigos de tiempo precisos de palabras y segmentos, así como separar las intervenciones de distintos hablantes. En esta guía se configurará un servicio Docker con aceleración por GPU, una API para iniciar tareas, HTTPS mediante Caddy, acceso seguro y copias de seguridad.

  • Para pruebas basta un VPS con CPU de 8 vCPU y 16 GB de RAM, pero para el procesamiento regular se necesita una GPU con 12–24 GB de VRAM.
  • WhisperX utiliza Whisper para el reconocimiento, alineación para los códigos de tiempo de las palabras y pyannote.audio para la diarización.
  • El resultado serán archivos JSON, SRT, VTT y TXT con marcas de tiempo e identificadores de hablantes.
  • El token secreto de Hugging Face para los modelos de diarización se guarda en el archivo .env, no en el código fuente.
  • Docker Compose simplifica las actualizaciones, el aislamiento de dependencias CUDA y el reinicio del servicio tras un fallo.
  • Las grabaciones originales y los resultados deben almacenarse fuera del contenedor y copiarse regularmente a S3 o a un servidor independiente.

Qué configuramos y por qué

WhisperX es una herramienta de transcripción local basada en los modelos Whisper y faster-whisper. A diferencia de la ejecución básica de Whisper, añade la alineación del texto con la señal de audio: como resultado, se pueden obtener no solo frases con una hora de inicio aproximada, sino también códigos de tiempo de palabras individuales. Esto resulta útil para subtítulos, transcripciones de entrevistas, edición de podcasts, búsqueda en archivos de vídeo y preparación de actas de reuniones.

La segunda función importante es la diarización, es decir, la separación de voces. Tras procesar una grabación, el servicio asigna a los segmentos etiquetas como SPEAKER_00, SPEAKER_01, etcétera. WhisperX no conoce automáticamente los nombres de las personas: determina qué fragmentos pertenecen a la misma voz. Los nombres pueden cambiarse más tarde en un editor de subtítulos o en el resultado JSON.

En esta guía se desplegará una API HTTP interna en Python. Recibe la ruta a un archivo multimedia ya cargado, inicia WhisperX dentro de un contenedor Docker, guarda los resultados en el directorio de tareas y devuelve JSON. Delante de la API se instalará Caddy, que obtiene automáticamente un certificado TLS de Let’s Encrypt y protege el servicio con HTTP Basic Auth. Este enfoque es adecuado para un propietario de VPS, un equipo pequeño o una herramienta SaaS interna.

Qué se obtendrá después de la configuración

  • Una dirección HTTPS como https://transcribe.example.com.
  • Una API protegida con los endpoints /health y /transcribe.
  • Procesamiento de MP3, WAV, M4A, MP4, MKV y otros formatos compatibles con FFmpeg.
  • Generación automática de result.json, result.srt, result.vtt y result.txt.
  • Códigos de tiempo de segmentos y palabras para los idiomas compatibles.
  • Separación de intervenciones hasta el número especificado de hablantes.
  • Reinicio automático del contenedor después de reiniciar el VPS.

Cómo es el flujo de procesamiento

  1. Carga el archivo original en el directorio /opt/whisperx/data/inbox mediante SFTP, SCP, rsync o un formulario de carga independiente.
  2. El cliente envía a la API el nombre del archivo, el idioma y los parámetros del modelo.
  3. FastAPI inicia un proceso independiente de WhisperX dentro del contenedor.
  4. WhisperX extrae la pista de audio mediante FFmpeg, reconoce el habla y obtiene los segmentos.
  5. El modelo alignment precisa los límites de las palabras si hay disponible un modelo de alineación para el idioma.
  6. pyannote.audio realiza la diarización y vincula los intervalos de tiempo con los hablantes.
  7. La API guarda los artefactos terminados en el directorio de la tarea y proporciona enlaces a ellos mediante una distribución interna de archivos.

Servicios en la nube y self-hosted: qué elegir

Criterio API de transcripción en la nube WhisperX en su propio VPS
Inicio Rápido: registro y clave de API Se requiere configurar Linux, Docker y un dominio
Precio con gran volumen Normalmente pago por minuto de audio Alquiler fijo de infraestructura
Confidencialidad Los archivos se transfieren a un proveedor externo Las grabaciones y los resultados permanecen bajo su control
Calidad Depende del producto elegido Se pueden cambiar los modelos Whisper y los parámetros de procesamiento
Diarización A menudo disponible como función de pago Funciona mediante pyannote.audio si se dispone de token
Limitaciones Límites de API, archivos y minutos Limitado por la GPU, el disco y la velocidad de su sistema

La opción self-hosted está especialmente justificada cuando las grabaciones contienen secretos comerciales, datos personales, información médica o jurídica. También resulta rentable para procesar regularmente decenas de horas de contenido al mes. Sin embargo, el servidor no debe dejarse sin mantenimiento: es necesario vigilar el espacio en disco, actualizar las imágenes y controlar el acceso a las grabaciones originales.

Importante: la diarización no es identificación de personas. La etiqueta SPEAKER_00 significa «la misma voz en esta grabación», no una persona concreta. Para el reconocimiento nominal se requieren modelos independientes y una base legal para el procesamiento de datos biométricos.

Qué configuración de VPS se necesita para esta tarea

El recurso principal para WhisperX no es la CPU, sino la memoria de vídeo de la GPU. El servicio funciona con CPU, pero el procesamiento de archivos largos será lento y la diarización carga adicionalmente la memoria. Para transcripciones cortas y esporádicas, un VPS con CPU será suficiente; para podcasts, videoclases y una cola de tareas, elija un VPS con GPU NVIDIA y acceso a CUDA.

Escenario CPU RAM GPU / VRAM Disco NVMe Resultado práctico
Pruebas y grabaciones ocasionales 8 vCPU 16 GB Sin GPU 150 GB Funciona, pero horas de audio pueden procesarse durante horas
Equipo pequeño 8–12 vCPU 32 GB NVIDIA 12–16 GB VRAM 300 GB Modelos medium/large-v3, procesamiento regular
Equipo de contenido o SaaS 16 vCPU 64 GB NVIDIA 24 GB VRAM 500 GB–1 TB Varias tareas en cola, large-v3 y diarización
Alta carga 24+ núcleos 128 GB Varias GPU de 24+ GB 1 TB+ Workers paralelos, cola de tareas independiente

Para la instalación básica descrita, resulta razonable un VPS con GPU, 8–12 vCPU, 32 GB de RAM, disco NVMe de al menos 300 GB y una GPU NVIDIA con 16 GB de VRAM. Al elegir, puede contratar un VPS con las características indicadas, si la configuración declara explícitamente el modelo de tarjeta gráfica, la cantidad de VRAM, la compatibilidad con CUDA y la posibilidad de usar la GPU desde Docker.

Elección del modelo e impacto en los recursos

Modelo Cuándo usarlo Referencia de VRAM Características
small Borradores, notas cortas, ahorro de recursos 4–6 GB Rápido, pero menos resistente al ruido y a los acentos
medium Equilibrio funcional entre calidad y coste 8–12 GB Buena elección para ruso y habla mixta
large-v3 Publicación, audio complejo, grabaciones multilingües 14–20 GB Mejor calidad, mayor latencia y requisitos

Los valores indicados son aproximados: la memoria real depende del tamaño del lote, el tipo de cálculo, la duración de la grabación, la diarización y las versiones de las bibliotecas. Para GPU normalmente se utiliza compute_type=float16. En CPU use int8; de lo contrario, el procesamiento será notablemente más lento y podría no caber en la RAM.

Cuándo un VPS no es suficiente

Se necesita un servidor dedicado cuando la GPU no se puede transferir a la máquina virtual, se requiere rendimiento garantizado sin influencia de vecinos, se planifican tareas continuas o el procesamiento de archivos confidenciales de varios terabytes. También se justifica con varias GPU y el procesamiento paralelo de decenas de archivos. Para una o dos tareas secuenciales, un VPS con GPU suele ser más sencillo, económico y fácil de escalar cambiando de plan.

Ubicación del servidor

La ubicación influye principalmente en la latencia de carga de los archivos originales, la jurisdicción de los datos personales y la velocidad de acceso del equipo a los resultados. Si los vídeos se graban en Europa y contienen datos de clientes de la UE, es razonable elegir un centro de datos europeo y definir de antemano el período de retención. Para archivos de 5–20 GB, la diferencia en el canal es más importante que la latencia: se necesita un canal real de entrada y salida de al menos 1 Gbit/s o un valor cercano sin límites de tráfico agresivos.

Preparación del servidor

A continuación se asume un Ubuntu Server 24.04 LTS recién instalado. En 2026, es una opción estable y cómoda para Docker, NVIDIA Container Toolkit y Caddy. Realice las acciones iniciales como el usuario que obtuvo acceso tras el aprovisionamiento. No publique la API antes de configurar las claves SSH y el firewall.

Actualice el sistema e instale las utilidades básicas

sudo apt update && sudo apt upgrade -y
sudo apt install -y ca-certificates curl gnupg git jq ufw fail2ban \
  unattended-upgrades rsync python3-venv

El primer comando instala los parches de seguridad actuales; el segundo añade utilidades para instalar Docker, realizar diagnósticos, configurar el firewall y copiar copias de seguridad.

Cree un administrador independiente

sudo adduser deploy
sudo usermod -aG sudo deploy
sudo mkdir -p /home/deploy/.ssh
sudo chmod 700 /home/deploy/.ssh

El usuario deploy realizará las tareas administrativas mediante sudo. Añada su clave pública SSH al archivo /home/deploy/.ssh/authorized_keys y establezca los permisos en 600.

sudo nano /home/deploy/.ssh/authorized_keys
sudo chmod 600 /home/deploy/.ssh/authorized_keys
sudo chown -R deploy:deploy /home/deploy/.ssh

Inserte una línea de clave pública, por ejemplo una que comience con ssh-ed25519. Antes de desactivar el acceso mediante contraseña, abra obligatoriamente una segunda sesión SSH y compruebe que el acceso del usuario deploy con clave funciona.

Desactive el acceso SSH por contraseña

sudo tee /etc/ssh/sshd_config.d/99-hardening.conf > /dev/null <<'EOF'
PermitRootLogin no
PasswordAuthentication no
KbdInteractiveAuthentication no
PubkeyAuthentication yes
X11Forwarding no
MaxAuthTries 3
EOF
sudo sshd -t && sudo systemctl reload ssh

El comando verifica la sintaxis de la configuración SSH antes de aplicarla. Si comete un error y reinicia SSH de inmediato, puede perder el acceso al servidor; por ello, no cierre la sesión actual hasta verificar correctamente el acceso en una nueva.

Configure UFW y Fail2ban

sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow OpenSSH
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw --force enable
sudo systemctl enable --now fail2ban

Solo están abiertos SSH, HTTP y HTTPS. El puerto de la API interna 8000 no se publica externamente: Caddy accederá a él mediante la red local de Docker. Puede comprobar las reglas con el comando sudo ufw status verbose.

Prepare DNS

Cree un registro A, por ejemplo transcribe.example.com, que apunte a la dirección IPv4 pública del VPS. Si utiliza IPv6, añada un registro AAAA solo si el firewall de IPv6 está correctamente configurado. Antes de iniciar Caddy, asegúrese de que el comando dig +short transcribe.example.com devuelve la IP de su servidor; de lo contrario, la obtención automática del certificado no funcionará.

Compruebe la GPU antes de instalar la aplicación

Si ha elegido un VPS con GPU, el controlador NVIDIA normalmente ya está instalado en la imagen del proveedor. Realice la comprobación:

nvidia-smi

La salida debe mostrar la versión del controlador, la versión de CUDA compatible y la tarjeta gráfica. Si el comando no se encuentra o muestra un error de comunicación con el controlador, corríjalo primero en el panel del VPS o instale el controlador NVIDIA adecuado para Ubuntu. No continúe con los contenedores hasta que nvidia-smi funcione en el host.

Instalación del software: paso a paso

Para aislar las dependencias se utilizarán Docker Engine 27+ o una versión compatible más reciente, Docker Compose v2 y NVIDIA Container Toolkit. WhisperX depende en gran medida de PyTorch, CUDA, FFmpeg, CTranslate2 y pyannote.audio; el contenedor evita conflictos entre paquetes del sistema.

Instale Docker Engine desde el repositorio oficial

sudo install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | \
  sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
sudo chmod a+r /etc/apt/keyrings/docker.gpg

Este bloque añade la clave de firma del repositorio oficial de Docker. No instale el paquete obsoleto docker.io al mismo tiempo que Docker Engine desde el repositorio oficial.

echo \
  "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.gpg] \
  https://download.docker.com/linux/ubuntu $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
  sudo tee /etc/apt/sources.list.d/docker.list > /dev/null

sudo apt update
sudo apt install -y docker-ce docker-ce-cli containerd.io \
  docker-buildx-plugin docker-compose-plugin

El comando conecta el repositorio e instala Docker Engine, Buildx y Compose. Verifique la instalación:

sudo docker run --rm hello-world
sudo usermod -aG docker deploy

La primera ejecución descargará una imagen de prueba y confirmará que el demonio funciona correctamente. Después de añadir el usuario al grupo docker, cierre la sesión SSH y vuelva a iniciarla. La pertenencia a este grupo otorga permisos cercanos a los de root, por lo que solo debe añadir administradores.

Instale NVIDIA Container Toolkit

curl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey | \
  sudo gpg --dearmor -o /usr/share/keyrings/nvidia-container-toolkit-keyring.gpg

curl -s -L https://nvidia.github.io/libnvidia-container/stable/deb/nvidia-container-toolkit.list | \
  sed 's#deb https://#deb [signed-by=/usr/share/keyrings/nvidia-container-toolkit-keyring.gpg] https://#' | \
  sudo tee /etc/apt/sources.list.d/nvidia-container-toolkit.list

Este bloque añade el repositorio oficial de NVIDIA Container Toolkit. Permite que el contenedor Docker utilice el controlador de GPU instalado en el sistema host.

sudo apt update
sudo apt install -y nvidia-container-toolkit
sudo nvidia-ctk runtime configure --runtime=docker
sudo systemctl restart docker

Después de configurar el runtime, pruebe el acceso de la GPU en un contenedor. La etiqueta CUDA siguiente es un ejemplo de imagen base compatible; si hay problemas, compare su versión con la versión del controlador mostrada por nvidia-smi.

docker run --rm --gpus all nvidia/cuda:12.6.3-base-ubuntu24.04 nvidia-smi

Si su tarjeta gráfica aparece en la salida del contenedor, la GPU está lista para WhisperX. En un VPS solo con CPU, omita este paso y establezca DEVICE=cpu y COMPUTE_TYPE=int8 en la configuración siguiente.

Cree la estructura del proyecto

sudo mkdir -p /opt/whisperx/{app,data/inbox,data/jobs,models,caddy}
sudo chown -R deploy:deploy /opt/whisperx
cd /opt/whisperx

El directorio data/inbox almacena los archivos de entrada, data/jobs los resultados y models los modelos descargados. Los modelos deben mantenerse en un volumen persistente; de lo contrario, se descargarán de nuevo al recrear el contenedor.

Cree el Dockerfile para la API y WhisperX

FROM nvidia/cuda:12.6.3-cudnn-runtime-ubuntu24.04

ENV DEBIAN_FRONTEND=noninteractive
ENV PYTHONUNBUFFERED=1
ENV PIP_NO_CACHE_DIR=1

RUN apt-get update && apt-get install -y --no-install-recommends \
    python3 python3-pip python3-venv ffmpeg git ca-certificates \
    && rm -rf /var/lib/apt/lists/

RUN python3 -m pip install --break-system-packages \
    "torch==2.6.0" "torchaudio==2.6.0" \
    --index-url https://download.pytorch.org/whl/cu126

RUN python3 -m pip install --break-system-packages \
    "whisperx==3.3.1" "fastapi==0.115.8" \
    "uvicorn[standard]==0.34.0" "python-multipart==0.0.20"

WORKDIR /app
COPY app/ /app/
CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]

El Dockerfile fija las versiones principales a nivel de imagen. WhisperX y las bibliotecas de ML relacionadas evolucionan rápidamente, por lo que antes de una actualización importante pruebe la nueva imagen en una copia de la grabación. No actualice PyTorch, CUDA y WhisperX simultáneamente en un servidor de producción.

Cree la aplicación API

mkdir -p /opt/whisperx/app
nano /opt/whisperx/app/main.py

Inserte el siguiente código. Solo permite archivos de /data/inbox, no acepta rutas arbitrarias y crea un directorio de resultados único para cada ejecución.

import json
import os
import subprocess
import uuid
from pathlib import Path

from fastapi import FastAPI, HTTPException
from pydantic import BaseModel, Field

app = FastAPI(title="WhisperX API", version="1.0")

INBOX = Path("/data/inbox").resolve()
JOBS = Path("/data/jobs").resolve()
DEVICE = os.getenv("DEVICE", "cuda")
COMPUTE_TYPE = os.getenv("COMPUTE_TYPE", "float16")
DEFAULT_MODEL = os.getenv("WHISPER_MODEL", "large-v3")
HF_TOKEN = os.getenv("HF_TOKEN", "")

class TranscribeRequest(BaseModel):
    filename: str = Field(pattern=r"^[A-Za-z0-9._ -]+$")
    language: str = Field(default="ru", min_length=2, max_length=5)
    model: str = Field(default=DEFAULT_MODEL)
    min_speakers: int | None = Field(default=None, ge=1, le=20)
    max_speakers: int | None = Field(default=None, ge=1, le=20)

@app.get("/health")
def health():
    return {"status": "ok", "device": DEVICE, "model": DEFAULT_MODEL}

@app.post("/transcribe")
def transcribe(payload: TranscribeRequest):
    source = (INBOX / payload.filename).resolve()
    if INBOX not in source.parents or not source.is_file():
        raise HTTPException(status_code=404, detail="Файл не найден в inbox")

    job_id = str(uuid.uuid4())
    output_dir = JOBS / job_id
    output_dir.mkdir(parents=True, exist_ok=False)

    command = [
        "whisperx", str(source),
        "--model", payload.model,
        "--language", payload.language,
        "--device", DEVICE,
        "--compute_type", COMPUTE_TYPE,
        "--output_dir", str(output_dir),
        "--output_format", "all",
    ]

    if HF_TOKEN:
        command.extend(["--diarize", "--hf_token", HF_TOKEN])

    if payload.min_speakers:
        command.extend(["--min_speakers", str(payload.min_speakers)])
    if payload.max_speakers:
        command.extend(["--max_speakers", str(payload.max_speakers)])

    completed = subprocess.run(
        command, text=True, stdout=subprocess.PIPE,
        stderr=subprocess.STDOUT, timeout=14400
    )

    (output_dir / "whisperx.log").write_text(
        completed.stdout, encoding="utf-8"
    )

    if completed.returncode != 0:
        raise HTTPException(
            status_code=500,
            detail={"job_id": job_id, "log": completed.stdout[-3000:]}
        )

    files = [item.name for item in output_dir.iterdir() if item.is_file()]
    return {"job_id": job_id, "status": "done", "files": files}

Para producción con varios usuarios, no ejecute procesamiento pesado de forma síncrona en una solicitud HTTP: añada una cola Redis y workers de Celery, RQ o Dramatiq. En la versión actual, una solicitud ocupa la conexión hasta que la tarea finaliza, lo cual es aceptable para un servicio interno personal y procesamiento secuencial.

Configuración

Obtenga un token para la diarización

WhisperX utiliza modelos restringidos de pyannote.audio para separar voces. Cree una cuenta de Hugging Face, acepte las condiciones de acceso a los modelos de diarización requeridos en la interfaz de Hugging Face y cree un token con permiso de lectura. No incluya este token en URL, repositorios Git, el historial de comandos shell ni código frontend.

Cree un archivo de entorno con permisos restringidos:

cd /opt/whisperx
nano .env
chmod 600 .env
HF_TOKEN=hf_замените_на_реальный_токен
DEVICE=cuda
COMPUTE_TYPE=float16
WHISPER_MODEL=large-v3
DOMAIN=transcribe.example.com
BASIC_AUTH_USER=operator
BASIC_AUTH_HASH=ЗАМЕНИТЕ_НА_BCRYPT_ХЕШ

Para un VPS con CPU, cambie los parámetros a DEVICE=cpu, COMPUTE_TYPE=int8 y normalmente comience con WHISPER_MODEL=small o medium. El modelo large-v3 puede usarse en CPU, pero no será práctico para grabaciones largas.

Genere una contraseña para Caddy

docker run --rm caddy:2.9.1 caddy hash-password \
  --plaintext 'СЛОЖНЫЙ_УНИКАЛЬНЫЙ_ПАРОЛЬ'

Copie en BASIC_AUTH_HASH el valor que comienza por $2a$ o uno similar. Si el shell interpreta el símbolo $, encierre el valor entre comillas simples en el archivo Compose o escape los signos de dólar como $$.

Cree Docker Compose

services:
  whisperx:
    build:
      context: .
      dockerfile: Dockerfile
    container_name: whisperx-api
    restart: unless-stopped
    env_file:
      - .env
    environment:
      - HF_HOME=/models/huggingface
      - TORCH_HOME=/models/torch
    volumes:
      - ./data:/data
      - ./models:/models
    expose:
      - "8000"
    gpus: all
    shm_size: "2gb"

  caddy:
    image: caddy:2.9.1
    container_name: whisperx-caddy
    restart: unless-stopped
    depends_on:
      - whisperx
    env_file:
      - .env
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - ./caddy/Caddyfile:/etc/caddy/Caddyfile:ro
      - caddy_data:/data
      - caddy_config:/config

volumes:
  caddy_data:
  caddy_config:

El parámetro gpus: all proporciona al contenedor acceso a todas las GPU disponibles. Si este es un servidor solo con CPU, elimine la línea gpus: all. El límite shm_size reduce la probabilidad de errores de memoria compartida en algunas bibliotecas PyTorch.

Configure HTTPS y el proxy inverso mediante Caddy

nano /opt/whisperx/caddy/Caddyfile
{$DOMAIN} {
    encode zstd gzip

    basic_auth {
        {$BASIC_AUTH_USER} {$BASIC_AUTH_HASH}
    }

    reverse_proxy whisperx:8000

    log {
        output stdout
        format json
    }
}

Caddy solicitará y renovará automáticamente el certificado TLS si el registro DNS ya apunta al servidor y los puertos 80 y 443 son accesibles desde el exterior. El contenedor interno de la API no tiene un puerto publicado, por lo que no se puede acceder a él directamente desde Internet.

Inicie el servicio y revise los registros

cd /opt/whisperx
docker compose build --pull
docker compose up -d
docker compose ps
docker compose logs -f --tail=100

La compilación de la primera imagen puede tardar varios minutos. En la primera solicitud, WhisperX también descarga el modelo de reconocimiento y los modelos de alineación; el tiempo depende de la velocidad de red y del tamaño del modelo seleccionado.

Verifique el healthcheck

curl -u 'operator:СЛОЖНЫЙ_УНИКАЛЬНЫЙ_ПАРОЛЬ' \
  https://transcribe.example.com/health

Respuesta esperada:

{"status":"ok","device":"cuda","model":"large-v3"}

Cargue un archivo de prueba e inicie la transcripción

scp interview.mp3 deploy@SERVER_IP:/opt/whisperx/data/inbox/
curl -u 'operator:СЛОЖНЫЙ_УНИКАЛЬНЫЙ_ПАРОЛЬ' \
  -X POST https://transcribe.example.com/transcribe \
  -H 'Content-Type: application/json' \
  -d '{"filename":"interview.mp3","language":"ru","model":"large-v3","min_speakers":2,"max_speakers":2}'

En la respuesta recibirá el identificador de la tarea y los nombres de los archivos creados. Verifique el contenido del directorio:

ls -lah /opt/whisperx/data/jobs/ИДЕНТИФИКАТОР_ЗАДАЧИ
cat /opt/whisperx/data/jobs/ИДЕНТИФИКАТОР_ЗАДАЧИ/interview.json | jq '.segments[0]'

En el JSON, los segmentos deben incluir los campos start, end, text y, si la diarización se realizó correctamente, speaker. Las palabras pueden contener campos temporales más precisos. Los archivos SRT y VTT se pueden importar cómodamente en DaVinci Resolve, Premiere Pro, YouTube Studio o editores de subtítulos.

Práctica de seguridad: Basic Auth es suficiente para una API interna personal, pero no sustituye la autorización completa de un producto multiusuario. Para un equipo, añada VPN, una lista de IP permitidas, un proxy OAuth o autenticación propia con registro de acciones y limitación de velocidad de solicitudes.

Copias de seguridad y mantenimiento

Un contenedor por sí solo no es una copia de seguridad. Al recrear el VPS, se perderán los registros de entrada, los resultados, la configuración, los tokens y los datos TLS si se encuentran únicamente en el disco local. Los modelos Whisper se pueden descargar de nuevo, pero también es útil almacenarlos en caché para recuperarse más rápido tras un fallo.

Qué se debe respaldar

  • /opt/whisperx/.env — token, parámetros del dispositivo y configuración de acceso. Guárdelo en una copia de seguridad cifrada.
  • /opt/whisperx/docker-compose.yml, Dockerfile, app/ y caddy/Caddyfile.
  • /opt/whisperx/data/jobs — transcripciones terminadas, registros y subtítulos.
  • /opt/whisperx/data/inbox — solo si los archivos de origen no se pueden restaurar desde otro almacenamiento.
  • Docker volumes de Caddy — certificados y configuración. Aceleran la recuperación, aunque el certificado se puede emitir de nuevo.

No es necesario conservar el vídeo de origen indefinidamente. Para grabaciones privadas, es más seguro establecer una regla: por ejemplo, eliminar los archivos de inbox 7 días después de una transcripción correcta y los resultados después de 90 días. La política de retención debe cumplir los acuerdos con los participantes de la grabación y la legislación aplicable.

Configure restic para un almacenamiento externo compatible con S3

sudo apt install -y restic
sudo mkdir -p /root/.config/restic
sudo chmod 700 /root/.config/restic
sudo nano /root/.config/restic/whisperx.env
sudo chmod 600 /root/.config/restic/whisperx.env

El archivo de entorno contiene las credenciales del almacenamiento remoto. Use un bucket independiente y una clave independiente con los permisos mínimos necesarios.

RESTIC_REPOSITORY=s3:https://s3.example.net/whisperx-backups
RESTIC_PASSWORD=contraseña_larga_aleatoria_del_repositorio
AWS_ACCESS_KEY_ID=su_clave
AWS_SECRET_ACCESS_KEY=su_secreto
AWS_DEFAULT_REGION=us-east-1

Inicialice el repositorio una vez:

sudo bash -c 'source /root/.config/restic/whisperx.env && restic init'

Cree un script de copia de seguridad diaria

sudo nano /usr/local/sbin/backup-whisperx.sh
sudo chmod 700 /usr/local/sbin/backup-whisperx.sh
#!/usr/bin/env bash
set -euo pipefail

source /root/.config/restic/whisperx.env

restic backup /opt/whisperx \
  --exclude='/opt/whisperx/models' \
  --exclude='/opt/whisperx/data/inbox/.tmp' \
  --tag whisperx

restic forget --keep-daily 7 --keep-weekly 4 --keep-monthly 6 --prune
restic check

El script excluye la caché de modelos: si es necesario, se descarga de nuevo y a menudo ocupa decenas de gigabytes. Si tiene una conexión a Internet lenta o una recuperación ante desastres rápida es crítica, elimine la exclusión models, pero estime de antemano el coste de almacenamiento y tráfico.

sudo crontab -e
20 3   * /usr/local/sbin/backup-whisperx.sh >> /var/log/backup-whisperx.log 2>&1

La tarea se ejecuta diariamente a las 03:20. Una vez al mes, pruebe obligatoriamente la restauración en un directorio independiente o en un VPS de prueba:

sudo bash -c 'source /root/.config/restic/whisperx.env && \
  restic restore latest --target /tmp/whisperx-restore-test'

Actualizaciones sin sorpresas

Para Caddy suele ser aceptable una actualización rolling: cambie la etiqueta fijada de la imagen, ejecute docker compose pull caddy y docker compose up -d. Realice la actualización de WhisperX, PyTorch, CUDA o pyannote.audio durante una ventana de mantenimiento. Estos componentes pueden cambiar los requisitos del modelo, el formato de los argumentos y el consumo de VRAM.

  1. Haga una copia de seguridad del proyecto y registre las versiones actuales: docker compose images.
  2. Cree una copia del directorio en un servidor de prueba o una rama independiente del proyecto.
  3. Compile la nueva imagen y procese una grabación de referencia en ruso y en los idiomas que necesite.
  4. Compare la calidad, la velocidad, la presencia de etiquetas de speaker y el formato JSON.
  5. Solo después de comprobarlo, actualice production y mantenga la posibilidad de volver a la etiqueta anterior de la imagen.

Control del disco, GPU y registros

df -h /opt/whisperx
docker system df
nvidia-smi
docker compose logs --since=24h whisperx | tail -n 200

Deje al menos un 20% de espacio libre en NVMe: los archivos de audio temporales, los modelos y los resultados pueden aumentar bruscamente el uso del disco. Una vez por semana, elimine los archivos de origen innecesarios y los resultados antiguos según el período de retención aprobado. No use indiscriminadamente docker system prune -a en production: el comando puede eliminar imágenes necesarias para una reversión rápida.

Solución de problemas + FAQ

¿Por qué el contenedor muestra «could not select device driver nvidia»?

El error significa que Docker no detecta el runtime de NVIDIA. Primero compruebe nvidia-smi en el propio VPS: sin un controlador funcional, el contenedor no corregirá nada. Luego ejecute dpkg -l | grep nvidia-container-toolkit y repita la configuración mediante sudo nvidia-ctk runtime configure --runtime=docker; después reinicie Docker. La comprobación docker run --rm --gpus all ... nvidia-smi debe funcionar antes de iniciar WhisperX.

¿Por qué se produce CUDA out of memory al iniciar large-v3?

No hay suficiente memoria de vídeo para el modelo, los lotes, la alineación o la diarización. Primero consulte la ocupación mediante nvidia-smi y detenga procesos GPU ajenos. Después reduzca el modelo a medium, use compute_type=float16 y no ejecute varias transcripciones en paralelo. Si la calidad de large-v3 es obligatoria, necesita una GPU con más VRAM, normalmente desde 16–24 GB según la carga.

La diarización no se inicia o aparece un error de acceso al modelo pyannote

Compruebe que HF_TOKEN esté definido en .env, no contenga comillas adicionales y que el contenedor se haya recreado después de modificar el archivo: docker compose up -d --force-recreate whisperx. El token debe tener permiso de lectura y en la cuenta deben aceptarse las condiciones de acceso a los modelos pyannote gated. Consulte el registro completo de la tarea en el archivo whisperx.log: normalmente indica la causa exacta del rechazo.

¿Por qué el resultado no tiene marcas de tiempo precisas de las palabras?

WhisperX añade word-level timestamps mediante un modelo de alineación independiente, pero no está disponible para todos los idiomas y depende de la calidad del audio. Compruebe que el parámetro language se haya proporcionado correctamente: para ruso use ru, no un nombre arbitrario del idioma. En grabaciones ruidosas con música, voces superpuestas o un micrófono deficiente, pueden faltar los límites de las palabras. Sin embargo, las marcas de tiempo de los segmentos normalmente se conservan.

La API responde 502 Bad Gateway a través de Caddy

El código 502 significa que Caddy no recibió una respuesta correcta del contenedor de la API. Compruebe el estado mediante docker compose ps y los registros docker compose logs whisperx. Una causa frecuente es que el contenedor se haya terminado debido a un error de Python, falta de RAM o VRAM al iniciarse. Compruebe también que en Caddyfile se especifique el host whisperx:8000, que coincide con el nombre del servicio Compose, y no una dirección IP externa.

¿Qué configuración de VPS es mínimamente adecuada?

El mínimo para experimentos es 8 vCPU, 16 GB de RAM y 150 GB de NVMe sin GPU. En una máquina así, use small, DEVICE=cpu y COMPUTE_TYPE=int8; una grabación larga puede procesarse durante más tiempo que su duración real. Para un trabajo regular cómodo con diarización, el mínimo práctico es 8 vCPU, 32 GB de RAM, 300 GB de NVMe y una GPU NVIDIA con 12–16 GB de VRAM.

¿Qué elegir para esta tarea: VPS o dedicated?

Un VPS con GPU es adecuado para un servicio personal, un equipo pequeño y carga variable: se despliega más rápido y normalmente es más fácil de escalar. Elija dedicated si necesita rendimiento garantizado, procesamiento constante, varias GPU, grandes archivos locales o requisitos estrictos de aislamiento. Más importante que el tipo de alquiler es contar con una GPU NVIDIA, VRAM suficiente, disco NVMe y la posibilidad de usar GPU dentro de contenedores Docker.

¿Por qué la transcripción es demasiado lenta?

Primero asegúrese de que la aplicación realmente use la GPU: la respuesta de /health debe contener device: cuda, y durante la tarea el comando nvidia-smi debe mostrar un proceso Python. Si se usa CPU, compruebe la configuración del runtime de GPU de Docker. En GPU, la aceleración también depende del modelo, la calidad del archivo de entrada y la diarización. Para una pasada preliminar, use medium y ejecute large-v3 solo para el texto final.

Conclusiones y próximos pasos

Ahora funciona en el VPS un servicio WhisperX propio: acepta grabaciones cargadas localmente, crea transcripciones, subtítulos, marcas de tiempo y etiquetas de speakers. El acceso está protegido con HTTPS y Basic Auth, y la configuración, los resultados y los secretos se pueden copiar a un almacenamiento externo mediante restic.

  1. Añada una cola de tareas en Redis y contenedores worker independientes si necesita procesar varios archivos sin solicitudes HTTP prolongadas.
  2. Cree un formulario web sencillo de carga con límite de tamaño de archivos, registro de tareas y limpieza automática de los archivos de origen.
  3. Pruebe los modelos medium y large-v3 con sus grabaciones, mida la velocidad y elija el equilibrio entre calidad, VRAM y coste de infraestructura.

¿Te fue útil esta guía?

Tus comentarios nos ayudan a mejorar nuestras guías.

Compartir esta publicación:

Envía esta guía a alguien a quien pueda resultarle útil.

Telegram VKVK WhatsApp Facebook LinkedIn XX

whisperx en VPS: transcripción con marcas de tiempo y separación de voces
support_agent
Valebyte Support
Usually replies within minutes
Hi there!
Send us a message and we'll reply as soon as possible.