HuggingFace Token Setup
Speaker diarization in OpenTranscribe requires access to gated PyAnnote models on HuggingFace. This page guides you through obtaining a free token and accepting the necessary model agreements.
Speaker diarization will NOT work without a valid HuggingFace token and acceptance of the pyannote/speaker-diarization-community-1 model agreement. Transcription will still work, but speakers will not be identified.
Why is HuggingFace Required?
OpenTranscribe uses PyAnnote.audio for speaker diarization (identifying "who spoke when"). PyAnnote's pre-trained models are hosted on HuggingFace as "gated" repositories, meaning you must:
- Create a free HuggingFace account
- Accept the model license agreements
- Use an access token to download the models
This is a one-time setup process. Once configured, models are cached locally and don't require internet access.
As of v0.5.0, local diarization defaults to a native diar-native sidecar
rather than the in-process PyAnnote pipeline described on this page (see
Speaker Diarization).
It reuses the identical HUGGINGFACE_TOKEN you configure here to export its own ONNX/PLDA
model set automatically on the backend's first startup — there is nothing extra to set up. If
that export fails for any reason (missing token, gate not accepted), diarization falls back to
the PyAnnote path this page walks through, so following the steps below keeps you covered
either way.
Step 1: Create HuggingFace Account
If you don't already have a HuggingFace account:
- Visit https://huggingface.co/join
- Sign up with email or GitHub/Google account
- Verify your email address
Time required: 2 minutes
Step 2: Generate Access Token
- Go to https://huggingface.co/settings/tokens
- Click "New token"
- Configure the token:
- Name:
OpenTranscribe(or any descriptive name) - Role: Select "Read" (default)
- Description: Optional
- Name:
- Click "Generate token"
- IMPORTANT: Copy the token and save it securely (you won't see it again)
Example token format: hf_ followed by random characters
Save your token in a password manager or secure note. You'll need it during OpenTranscribe setup. Tokens don't expire unless you delete them.
Time required: 2 minutes
Step 3: Accept the Model Agreement
Speaker diarization needs access to one gated model:
pyannote/speaker-diarization-community-1. It's CC-BY-4.0 and auto-approved — there's no
waiting list or human review, but you still have to click through the agreement once per
account.
pyannote/speaker-diarization-community-1
- Visit https://huggingface.co/pyannote/speaker-diarization-community-1
- Scroll to the model card
- Click "Agree and access repository"
- ✅ You should see "You have been granted access to this model"
The gate is checked per account, not just per repo. If HUGGINGFACE_TOKEN was generated
under a different account than the one that clicked "Agree and access repository" above, every
request fails with HTTP 403 — identically to a token that never accepted anything. This is the
single most common way this setup step goes wrong. If diarization still fails after you're sure
you accepted the agreement, check which account actually issued the token.
Older docs and forum posts reference pyannote/segmentation-3.0 and
pyannote/speaker-diarization-3.1 — that was the model pair OpenTranscribe used before moving
to speaker-diarization-community-1. community-1 bundles its own segmentation, embedding, and
PLDA weights in one self-contained repo, so accepting the old pair grants nothing for it, and
the native diar-native sidecar's export deliberately never touches them (their weights differ
from community-1's own). The in-process PyAnnote engine — the failover used when the sidecar is
unavailable — does keep speaker-diarization-3.1 as an internal last-resort fallback if loading
community-1 itself fails for a non-licensing reason. Accepting the old pair is optional, only
helps that inner fallback, and is never a substitute for accepting community-1.
Time required: 2 minutes
Step 4: Configure OpenTranscribe
Quick Install Method
If using the one-liner installer:
curl -fsSL https://raw.githubusercontent.com/attevon-llc/OpenTranscribe/master/setup-opentranscribe.sh | bash
The installer will prompt you:
Enter your HuggingFace token (or press Enter to skip): hf_your_token_here
Paste your token and press Enter. The installer will:
- Validate the token
- Check model access permissions
- Download and cache models (~500MB)
- Configure the
.envfile automatically
Manual Install Method
If installing from source:
-
Copy the environment template:
cp .env.example .env -
Edit
.envand add your token:# Required for speaker diarizationHUGGINGFACE_TOKEN=hf_your_token_here -
Start OpenTranscribe:
./opentr.sh start dev
Models will download automatically on first use (~10-30 minutes).
Verification
Method 1: Check Model Cache
After first transcription with speaker diarization:
# Check if the diarization pipeline was downloaded
ls -lh models/huggingface/hub/ | grep pyannote
# You should see (this is the only one required):
# models--pyannote--speaker-diarization-community-1
If the in-process PyAnnote engine's internal last-resort fallback ever ran, you'll also see
models--pyannote--speaker-diarization-3.1 and models--pyannote--segmentation-3.0 here —
that isn't an error, just evidence the fallback fired at some point.
Method 2: Test Transcription
- Upload a test file with multiple speakers
- Enable speaker diarization
- Process the file
- Check for speaker labels (Speaker 1, Speaker 2, etc.)
If diarization works, you'll see:
- ✅ Speaker segments identified
- ✅ Different speakers color-coded
- ✅ Speaker analytics in dashboard
Method 3: Check Container Logs
./opentr.sh logs celery-worker | grep -i pyannote
Success indicators (./opentr.sh logs backend for the native diarizer,
./opentr.sh logs celery-worker for the in-process PyAnnote fallback):
✅ "diar-native models already provisioned" / "diar-native models exported to ..."
✅ "Loading PyAnnote v4 pipeline: pyannote/speaker-diarization-community-1"
✅ "Loaded PyAnnote v4 model: pyannote/speaker-diarization-community-1"
Error indicators:
"diar-native provisioning failed (exit 5)" — TOKEN_DENIED, native engine
"Failed to load v4 model ... Trying fallback" — in-process engine falling back to 3.1
HTTP 403 / PermissionError mentioning speaker-diarization-community-1
Troubleshooting
Error: "Cannot access gated repository" / HTTP 403 / exit 5 (TOKEN_DENIED)
Cause: The speaker-diarization-community-1 agreement was not accepted by the account that
issued HUGGINGFACE_TOKEN, or the token itself is invalid.
What this looks like now: the native diarizer's model export runs at backend startup and
exits with code 5 (TOKEN_DENIED) on a rejected token. That failure is never fatal to the
stack — /readyz stays 503 for the native diarizer and every diarization job falls back to the
in-process PyAnnote engine, which loads the identical gated repo and hits the identical 403. The
practical result is a healthy-looking stack with no working diarizer, not a crash. Look for
diar-native provisioning failed (exit 5) in the backend's startup log.
Solution:
- Confirm the agreement was accepted (see Step 3) — by the same HuggingFace account that
generated
HUGGINGFACE_TOKEN. A token from one account and an "Agree and access repository" click from another fails identically to a token that never accepted anything. - Check
HUGGINGFACE_TOKENis correct in.env - Regenerate the token if needed
- Restart OpenTranscribe:
./opentr.sh restart-backend(re-runs provisioning) or./opentr.sh restart-all
Error: "Invalid HuggingFace token"
Cause: Token format incorrect or expired
Solution:
- Verify token starts with
hf_ - Check for extra spaces or quotes in
.env - Regenerate token from HuggingFace settings
- Update
.envand restart
Models Download on Every Restart
Cause: Model cache not persisting
Solution:
- Check
MODEL_CACHE_DIRin.env(default:./models) - Verify directory permissions:
ls -la models/# Should be owned by user running Docker
- Fix permissions:
./scripts/fix-model-permissions.sh
Slow Model Download
Cause: Large model files (~500MB total)
Solution:
- Be patient on first setup (10-30 minutes)
- Models are cached permanently after first download
- Use wired connection for faster downloads
- Check internet speed: https://fast.com
Speaker Diarization Not Working
Checklist:
- HuggingFace token configured in
.env -
speaker-diarization-community-1agreement accepted — by the token's own account - Models downloaded successfully (check logs)
- Speaker diarization enabled in UI settings
- Audio file has multiple speakers
- MIN_SPEAKERS and MAX_SPEAKERS configured correctly
Security Considerations
Token Security
Your HuggingFace token is sensitive information:
- ✅ DO: Store in
.envfile (git-ignored) - ✅ DO: Use read-only token permissions
- ✅ DO: Regenerate if compromised
- DON'T: Commit to version control
- DON'T: Share publicly
- DON'T: Use write permissions (unnecessary)
Revoking Access
If your token is compromised:
- Go to https://huggingface.co/settings/tokens
- Click "Revoke" next to the compromised token
- Generate a new token
- Update
.envwith new token - Restart OpenTranscribe
Model Caching
Storage Location
Models are cached at:
${MODEL_CACHE_DIR}/huggingface/hub/models--pyannote--speaker-diarization-community-1/
Default: ./models/huggingface/hub/models--pyannote--speaker-diarization-community-1/. This is
the standard huggingface_hub cache layout pyannote.audio 4.x uses for every gated model, not a
PyAnnote-specific directory — ./models/huggingface/hub/ also holds every other HuggingFace
model the app downloads.
Disk Space
speaker-diarization-community-1 is a single self-contained repo — segmentation, embedding, and
PLDA weights bundled together — ~500MB total.
Plus, downloaded by scripts/download-models.sh:
- WhisperX transcription models — the largest single item, and the one that
varies most with
WHISPER_MODEL - Wav2Vec2 alignment and the gender classifier
- NLTK tokenizers and sentence-transformers embeddings
- Chat reranker (cross-encoder, used by RAG chat)
- OpenSearch neural-search models
- Content-redaction models (PII / toxicity)
Total: several GB. It is not a fixed number — it depends on WHISPER_MODEL
and on whether you set DOWNLOAD_ALL_OPENSEARCH_MODELS=true, so budget disk
generously rather than to a specific figure.
Offline Use
Once models are downloaded:
- ✅ No internet required for transcription
- ✅ Models cached permanently
- ✅ Works in airgapped environments
- Initial download requires internet
Alternative: Offline Installation
For airgapped/offline environments:
-
Download models on internet-connected machine:
# Set token and download the pipeline the app actually loadsexport HUGGINGFACE_TOKEN=hf_your_token_herepython3 -c "from pyannote.audio import Pipeline; Pipeline.from_pretrained('pyannote/speaker-diarization-community-1')" -
Copy model cache to offline machine:
# On internet machinetar -czf pyannote-models.tar.gz ~/.cache/huggingface/hub/models--pyannote--speaker-diarization-community-1/# On offline machinetar -xzf pyannote-models.tar.gz -C /path/to/opentranscribe/models/huggingface/hub/ -
Configure
.envon offline machine:HUGGINGFACE_TOKEN=hf_your_token_here # Still requiredMODEL_CACHE_DIR=./models
See Offline Installation for complete airgapped setup guide.
Quick Reference
URLs
- Create Account: https://huggingface.co/join
- Token Settings: https://huggingface.co/settings/tokens
- Diarization Model: https://huggingface.co/pyannote/speaker-diarization-community-1
Environment Variables
# Required for speaker diarization
HUGGINGFACE_TOKEN=hf_your_token_here
# Model cache location
MODEL_CACHE_DIR=./models
# Speaker detection range
MIN_SPEAKERS=1
MAX_SPEAKERS=20
Verification Commands
# Check token configured
grep HUGGINGFACE_TOKEN .env
# Check the diarization pipeline was downloaded
ls -lh models/huggingface/hub/ | grep speaker-diarization-community-1
# Check backend startup for native diarizer provisioning
./opentr.sh logs backend | grep -i diar-native
# Check container logs for the in-process PyAnnote fallback
./opentr.sh logs celery-worker | grep -i pyannote
Next Steps
- Docker Compose Installation - Complete installation guide
- GPU Setup - Configure GPU acceleration
- First Transcription - Test speaker diarization
- Troubleshooting - Fix common issues