-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathbootstrap_models.py
More file actions
111 lines (96 loc) · 4.56 KB
/
Copy pathbootstrap_models.py
File metadata and controls
111 lines (96 loc) · 4.56 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
#!/usr/bin/env python3
"""Pre-stage the offline Whisper model Hearthwave needs.
Hearthwave is designed for fully offline operation — the server never attempts
to fetch a model at runtime. Run this script once on a machine with internet
access; the resulting Models/ directory is portable and can be copied to
air-gapped target machines alongside the source tree.
Usage:
python bootstrap_models.py # default: small.en
python bootstrap_models.py --model base.en # smaller, faster
python bootstrap_models.py --model medium.en # higher accuracy
# Two-tier RX pipeline — stage the streaming model and the final-pass
# model in one run. large-v3-turbo is what the install scripts stage by
# default and what whisper_model_final="auto" prefers:
python bootstrap_models.py --model small.en large-v3-turbo
# GPU final pass (HF transformers format, staged at Models/STT/<name>-hf):
python bootstrap_models.py --final-model large-v3-turbo --final-backend gpu
"""
import argparse
import os
import sys
WHISPER_REPOS = {
"tiny.en": "Systran/faster-whisper-tiny.en",
"base.en": "Systran/faster-whisper-base.en",
"small.en": "Systran/faster-whisper-small.en",
"medium.en": "Systran/faster-whisper-medium.en",
"large-v3": "Systran/faster-whisper-large-v3",
# Distilled large: ~large-v2 accuracy at a fraction of the compute —
# the recommended whisper_model_final for the two-pass RX pipeline.
"distil-large-v3": "Systran/faster-distil-whisper-large-v3",
# Community CT2 conversion of openai/whisper-large-v3-turbo (no official
# Systran repo exists). Verified 2026-07-01: downloads, loads in
# faster-whisper 1.2.1, transcribes. Final-pass only — too slow for the
# 2 s streaming slices.
"large-v3-turbo": "deepdml/faster-whisper-large-v3-turbo-ct2",
}
# HF transformers-format repos for the GPU final pass (distinct from the CT2
# faster-whisper repos above). Staged under Models/STT/<name>-hf/.
HF_FINAL_REPOS = {
"distil-large-v3": "distil-whisper/distil-large-v3",
"large-v3": "openai/whisper-large-v3",
"large-v3-turbo": "openai/whisper-large-v3-turbo",
}
def final_target(name: str, backend: str):
"""Return (repo_id, local_dir) for a final-pass model and backend.
backend 'cpu' -> CT2 faster-whisper repo, dir Models/STT/<name>.
backend 'gpu' -> HF transformers repo, dir Models/STT/<name>-hf."""
if backend == "gpu":
return HF_FINAL_REPOS[name], os.path.join("Models", "STT", name + "-hf")
return WHISPER_REPOS[name], os.path.join("Models", "STT", name)
def main():
parser = argparse.ArgumentParser(
description=__doc__,
formatter_class=argparse.RawDescriptionHelpFormatter,
)
parser.add_argument(
"--model",
default=["small.en"],
nargs="+",
choices=sorted(WHISPER_REPOS),
metavar="MODEL",
help="faster-whisper variant(s) to fetch (default: small.en). Pass "
"more than one to stage the two-tier pipeline's streaming and "
"final-pass models together.",
)
parser.add_argument("--final-model", metavar="NAME", default=None,
help="Stage a final-pass model in the format for --final-backend.")
parser.add_argument("--final-backend", choices=("cpu", "gpu"), default="cpu",
help="Format for --final-model: cpu (CT2) or gpu (HF transformers).")
args = parser.parse_args()
try:
from huggingface_hub import snapshot_download
except ImportError:
print(
"huggingface_hub is required. Install it with:\n"
" pip install -r backend/requirements.txt",
file=sys.stderr,
)
return 1
# Preserve order but drop duplicates (e.g. --model small.en small.en).
models = list(dict.fromkeys(args.model))
for model in models:
target = os.path.join("Models", "STT", model)
os.makedirs(target, exist_ok=True)
repo_id = WHISPER_REPOS[model]
print(f"Whisper: downloading {repo_id} -> {target}")
snapshot_download(repo_id=repo_id, local_dir=target)
print(f"Whisper: done. Loaded at runtime from {target}/")
if args.final_model:
repo_id, target = final_target(args.final_model, args.final_backend)
os.makedirs(target, exist_ok=True)
print(f"Final ({args.final_backend}): downloading {repo_id} -> {target}")
snapshot_download(repo_id=repo_id, local_dir=target)
print(f"Final: done. Loaded at runtime from {target}/")
return 0
if __name__ == "__main__":
sys.exit(main())