Files
Dmitriy Dementiev dae9d107c9 docs: уточнены ограничения авто-профиля и профиль turbo
- Зачем:
  - документация обещала large-v3-turbo на NVIDIA, где он недоступен, и умалчивала, что модель по умолчанию без CUDA понимает только русскую речь.
- Что:
  - large-v3-turbo перенесён из таблицы faster-whisper в раздел OpenVINO с измеренными размерами моделей.
  - языковое ограничение авто-профиля и предупреждение CLI описаны в README, gpu.md и ADR-006.
  - в backlog добавлен пункт про turbo для faster-whisper, в gpu.md снято расхождение по скорости openvino-cpu.
- Проверка:
  - вычитка diff, проверка якорной ссылки на docs/gpu.md.
2026-08-12 11:53:09 +03:00

204 lines
13 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# PRD: local-transcriber — Локальный CLI для транскрипции аудио/видео
## 1. Обзор продукта
**Название**: `local-transcriber`
**Тип**: CLI-утилита (Python, управление зависимостями через uv)
**Назначение**: Принимает аудио- или видеофайл, выполняет распознавание речи локально (без внешних API), и создаёт рядом с исходным файлом markdown-файл с транскриптом и таймкодами.
**Пример использования**:
```bash
transcribe meeting-2026-03-17.mp4
# → создаёт meeting-2026-03-17-transcript.md
```
## 2. Целевые пользователи и сценарии
- Разработчик/инженер, которому нужен текст из записи встречи, лекции, подкаста
- Дальнейшая обработка транскрипта ИИ (суммаризация, извлечение action items и т.д.) — вне скоупа, но учитывается в формате вывода
- Машины с GPU (NVIDIA, CUDA) и без GPU (CPU-only fallback)
- Windows (native / WSL2) и Linux
## 3. Функциональные требования
### 3.1. Основной flow
1. Пользователь вызывает CLI, передаёт путь к файлу (или glob-маску, post-MVP)
2. Файл валидируется по пути, размеру и расширению
3. По `device` выбирается backend; аудио декодируется через PyAV без отдельного
извлечения дорожки
4. Результат форматируется в markdown с таймкодами
5. Файл `<имя>-transcript.md` сохраняется рядом с исходным (кодировка: UTF-8)
**Поведение при перезаписи**:
- Явный вызов по файлу → транскрипт перезаписывается, даже если уже существует
- Батч-режим (glob-маска, post-MVP) → пропускать файлы, для которых транскрипт уже существует; `--force` для принудительной перезаписи
**Пустая речь**: если модель не распознала ни одного сегмента — файл транскрипта всё равно создаётся (шапка с метаданными + `*Речь не обнаружена.*` в теле), выводится предупреждение в stderr: `⚠ Речь не обнаружена в файле <имя>`
### 3.2. CLI-интерфейс
```
transcribe <путь_к_файлу> [опции]
Опции:
--model, -m Модель распознавания
По умолчанию: medium (CUDA) / gigaam-v3-e2e-rnnt (ONNX)
--language, -l Язык (ru|en|auto)
По умолчанию: ru
--output, -o Путь к выходному файлу
По умолчанию: <input_stem>-transcript.md
--device, -d Устройство (auto|cpu|cuda|onnx|openvino|openvino-gpu|openvino-cpu)
По умолчанию: auto (CUDA при наличии, иначе ONNX CPU)
--compute-type Тип вычислений
По умолчанию: float16 (CUDA) / int8 (ONNX)
--verbose, -v Подробный вывод (прогресс сегментов)
```
### 3.3. Формат выходного файла
Файл `*-transcript.md`:
```markdown
# Транскрипт: meeting-2026-03-17.mp4
- **Дата транскрипции**: 2026-03-17 14:30:05
- **Модель**: large-v3
- **Язык**: ru (задан явно) / ru (определён автоматически)
- **Длительность**: 01:23:45
- **Устройство**: CUDA (NVIDIA GeForce RTX 3060)
---
[00:00.00 - 00:04.82] Добрый день, коллеги. Сегодня мы обсудим результаты квартала.
[00:04.82 - 00:09.15] Первый вопрос — по метрикам продукта.
[00:09.15 - 00:15.40] Как вы видите на слайде, MAU вырос на двадцать три процента
по сравнению с предыдущим кварталом.
...
```
**Правила форматирования**:
- Таймкоды в формате `[MM:SS.ss - MM:SS.ss]` (минуты:секунды.сотые)
- Для записей длиннее 1 часа — `[HH:MM:SS.ss - HH:MM:SS.ss]`
- Соседние сегменты объединяются в абзац до паузы 2 секунды или длительности 60 секунд
- Метаданные в шапке файла
- Пустая строка между абзацами для читаемости
### 3.4. Поддерживаемые форматы
**Аудио**: mp3, wav, flac, ogg, m4a, wma, aac
**Видео**: mp4, mkv, avi, mov, webm, ts
Определение типа — по расширению. Фактическое декодирование выполняет PyAV с
встроенными библиотеками FFmpeg; системная установка `ffmpeg` не требуется.
## 4. Нефункциональные требования
### 4.1. Производительность
| Конфигурация | Ожидаемая скорость (real-time factor) |
|---------------------------|---------------------------------------|
| RTX 3060 + large-v3 | ~10-15x (1 час аудио ≈ 4-6 мин) |
| RTX 4050 + large-v3 | ~12-18x (1 час аудио ≈ 3-5 мин) |
| Quadro M3000M + large-v3 | ~3-5x (1 час аудио ≈ 12-20 мин) |
| CPU + ONNX GigaAM RNN-T | ~10-14x (1 час аудио ≈ 4-6 мин) |
| CPU + OpenVINO Turbo INT8 | ~7-10x (1 час аудио ≈ 6-9 мин) |
| CPU (modern) + large-v3 | ~0.5-1x (1 час аудио ≈ 60-120 мин) |
| CPU + small | ~3-5x (1 час аудио ≈ 12-20 мин) |
### 4.1.1. Совместимость GPU
| GPU | VRAM | large-v3 int8 (~2.5 GB) | large-v3 float16 (~4.5 GB) | Рекомендация |
|-------------------|-------|--------------------------|----------------------------|-------------------------|
| RTX 3060 | 6 GB | ✅ | ✅ (впритык) | int8 — безопасный выбор |
| RTX 4050 | 6 GB | ✅ | ✅ (впритык) | int8 — безопасный выбор |
| Quadro M3000M | 4 GB | ✅ | ⚠️ может OOM | int8 обязательно |
| Без GPU | — | ONNX GigaAM INT8 | — | auto выбирает ONNX |
Device-aware дефолты выбирают `float16` для CUDA и `int8` для ONNX/OpenVINO.
### 4.2. Требования к окружению
- Python ≥ 3.13
- Для GPU: Linux/WSL2 — cuBLAS из nvidia-cublas-cu12 (ставится автоматически через `uv sync`); Windows — системный CUDA toolkit (см. ADR-001)
- Дисковое пространство для моделей: зависит от выбранного backend и модели
- Выходные файлы: UTF-8 (явная кодировка при записи)
### 4.3. Кроссплатформенность
- Linux: нативный запуск
- Windows: нативный Python или WSL2
- macOS: ONNX CPU в auto-режиме; FasterWhisper CPU доступен явно
## 5. Технический стек
| Компонент | Технология |
|---------------------|-------------------------------------------------|
| Язык | Python 3.13+ |
| Управление проектом | uv (pyproject.toml) |
| Распознавание речи | faster-whisper, ONNX Runtime, OpenVINO GenAI |
| Медиа-декодирование | PyAV со встроенными библиотеками FFmpeg |
| CLI-фреймворк | typer |
| Прогресс | rich (progress bar + статус) |
### 5.1. Почему несколько backend
- faster-whisper оптимизирован для NVIDIA CUDA и поддерживает много языков
- ONNX GigaAM RNN-T даёт быстрый читаемый результат на CPU
- OpenVINO предоставляет явные профили для Intel GPU и x86 CPU
- Все backend работают локально через Python API, без Docker и облачных ключей
- Модели загружаются автоматически и кешируются локально
### 5.2. Структура проекта
```
local-transcriber/
├── pyproject.toml
├── README.md
├── src/
│ └── local_transcriber/
│ ├── __init__.py
│ ├── cli.py # CLI entry point (typer)
│ ├── transcriber.py # Оркестрация backend и fallback
│ ├── backends/ # Адаптеры FasterWhisper, ONNX и OpenVINO
│ ├── formatter.py # Форматирование в markdown
│ └── utils.py # Проверки файлов и определение device
└── tests/
└── ...
```
## 6. Риски и ограничения
| Риск | Влияние | Митигация |
|------|---------|-----------|
| Качество распознавания русского текста | Среднее | large-v3 хорошо справляется с ru; при проблемах — попробовать `--language ru` вместо auto |
| Нет разделения по спикерам | Низкое | Осознанно выведено за скоуп MVP; добавление diarization (pyannote.audio) — возможное расширение |
| Первый запуск: долгая загрузка модели | Низкое | Прогресс-бар при скачивании; модели кешируются в `~/.cache/huggingface/` |
| CUDA несовместимость на Windows | Среднее | Автоматический fallback на CPU + предупреждение; в README — инструкция по CUDA |
| Большие файлы (>2 часов) | Среднее | Учитывать память выбранного backend; чанкование рассматривается отдельно |
| OOM на GPU с 4 GB VRAM | Среднее | CUDA использует float16; при OOM — fallback на CPU с предупреждением или явный более лёгкий профиль |
| Файл без речи (тишина, музыка, шум) | Низкое | Создаётся транскрипт с шапкой метаданных и `*Речь не обнаружена.*` в теле + предупреждение в stderr |
## 7. Вне скоупа MVP
- Разделение по спикерам (speaker diarization)
- Веб-интерфейс / GUI
- Пакетная обработка нескольких файлов (батч) — см. post-MVP
- Стриминг с микрофона (real-time)
- Интеграция с LLM для пост-обработки транскрипта
- Перевод (translation mode)
- Вывод в форматах SRT / VTT / JSON
- Аудиофильтрация / шумоподавление (faster-whisper сам нормализует; ручной препроцессинг может ухудшить результат)
## 8. Возможные расширения (post-MVP)
1. **Speaker diarization** — pyannote.audio, требует отдельной модели + GPU
2. **Батч-режим**`transcribe ./recordings/*.mp4`; по умолчанию пропускает файлы, для которых транскрипт уже есть; `--force` для перезаписи
3. **Экспорт в SRT/VTT** — для субтитров
4. **Watch-режим** — мониторинг директории, автотранскрипция новых файлов
5. **Интеграция с LLM**`--summarize` для генерации саммари поверх транскрипта
6. **Конфигурационный файл**`.transcriber.toml` для дефолтов проекта