Files
esh-pfi-infrastructure/stacks/index-tts/Dockerfile
T
vh ab696ecbd1 stacks/index-tts: revert git-lfs build attempt; document the LFS
budget hazard + media-CDN workaround

Tried adding git-lfs install + git lfs pull to the build to get
real example WAVs into the image — failed with:

    Error downloading object: examples/emo_hate.wav: Smudge error:
    batch response: This repository exceeded its LFS budget. The
    account responsible for the budget should increase it to
    restore access.

The index-tts org's LFS bandwidth quota is exhausted upstream and
out of our control. Reverting the Dockerfile change. The examples
aren't needed for the wrapper to work; emotion_text and
emotion_vector are sufficient for end-to-end testing without any
WAV file at all.

For users who want the bundled example clips as starter audio,
README now documents the media-CDN URL trick — same LFS objects
served via a different code path that doesn't count against the
LFS API budget. INDEX_TTS_TAG stays at v1.
2026-04-25 14:25:06 -07:00

70 lines
2.8 KiB
Docker

# syntax=docker/dockerfile:1.6
#
# IndexTTS-2 served behind our own thin FastAPI wrapper (~150 lines in
# app.py). Upstream ships only a Gradio webui; the existing csllpr
# FastAPI fork is for v1 and dormant. We own the wrapper end-to-end.
ARG CUDA_BASE=nvidia/cuda:12.8.0-cudnn-runtime-ubuntu22.04
FROM ${CUDA_BASE}
ENV DEBIAN_FRONTEND=noninteractive \
PIP_ROOT_USER_ACTION=ignore \
PYTHONUNBUFFERED=1 \
PATH="/opt/venv/bin:${PATH}"
RUN apt-get update \
&& apt-get install -y --no-install-recommends \
python3.10 python3.10-venv python3-pip \
git ffmpeg libsndfile1 \
ca-certificates wget \
&& rm -rf /var/lib/apt/lists/* \
&& python3.10 -m venv /opt/venv
# Pinned IndexTTS-2 SHA — bump in stack .env (INDEX_TTS_SHA build arg)
# when you want upstream updates.
#
# Note on LFS: examples/emo_*.wav and examples/voice_*.wav in the
# upstream repo are Git LFS objects, but the index-tts org has
# repeatedly exhausted GitHub's LFS bandwidth budget — `git lfs pull`
# in the build aborts with "This repository exceeded its LFS budget".
# We don't need the examples for the wrapper to work; they're just
# convenient starter audio. To stage real LFS-backed examples on the
# host, fetch them once via the media CDN (a different code path that
# doesn't count against the LFS API budget):
#
# curl -fsSL -o /worktank/index-tts/emotions/hate.wav \
# https://media.githubusercontent.com/media/index-tts/index-tts/main/examples/emo_hate.wav
ARG INDEX_TTS_SHA=830f6f8f94a51fea23ab1d639027a86200075a4e
RUN git clone https://github.com/index-tts/index-tts.git /opt/index-tts \
&& cd /opt/index-tts && git checkout ${INDEX_TTS_SHA}
# CUDA 12.8 torch wheels (per IndexTTS pyproject.toml's tool.uv.index
# pin — same versions, same source).
RUN pip install --no-cache-dir \
torch==2.8.0 torchaudio==2.8.0 \
--index-url https://download.pytorch.org/whl/cu128
# IndexTTS package + its long pinned-deps tail (numpy 1.26.2, transformers
# 4.52.1, sentencepiece, librosa, descript-audiotools, jieba/g2p-en/cn2an,
# WeTextProcessing, modelscope, accelerate, safetensors, etc.).
# BigVGAN is vendored under indextts/ so it resolves without a pip dep.
RUN cd /opt/index-tts && pip install --no-cache-dir -e .
# Wrapper deps (FastAPI stack + soundfile for in-memory WAV encoding).
RUN pip install --no-cache-dir \
fastapi 'uvicorn[standard]' python-multipart soundfile
WORKDIR /app
COPY app.py /app/app.py
COPY entrypoint.sh /usr/local/bin/entrypoint.sh
RUN chmod +x /usr/local/bin/entrypoint.sh
EXPOSE 8000
# wget is in the base image (added above); curl is not.
HEALTHCHECK --interval=30s --timeout=10s --start-period=600s --retries=3 \
CMD wget -q -O /dev/null http://127.0.0.1:8000/healthz || exit 1
ENTRYPOINT ["/usr/local/bin/entrypoint.sh"]
CMD ["uvicorn", "app:app", "--host", "0.0.0.0", "--port", "8000"]