Техническая ветка для разработчиков Собрать руками

Локальный пайплайн голоса, видео и монтажа

Покажем, как объединить Whisper, Silero, OpenCV и FFmpeg в один локальный конвейер: запись → транскрипция → анализ → монтаж → экспорт — всё без внешних API.

Что такое локальный пайплайн голоса, видео и монтажа?

Это цепочка обработки аудио/видео-потоков, где каждый этап (запись, транскрипция, анализ эмоций, вырезание сегментов, монтаж) выполняется локально — на вашей машине — с использованием open-source моделей и инструментов. Цель: полный контроль, приватность, отсутствие latency и cost-переменных от облака.

Архитектура пайплайна

flowchart TD
    A[Ввод: микрофон/камера] --> B[Захват: PyAudio/OpenCV]
    B --> C[Предобработка: нормализация, VAD]
    C --> D[Транскрипция: Whisper Tiny/Small]
    D --> E[Анализ: эмоции (Wav2Vec2), ключевые фразы]
    E --> F[Сегментация: таймкоды речи/пауз]
    F --> G[Монтаж: FFmpeg + OpenCV]
    G --> H[Экспорт: MP4/MP3 + JSON-метаданные]

Минималистичный пример: захват + транскрипция

import pyaudio
import wave
import whisper
import numpy as np
from silero_vad import load_silero_vad, get_speech_timestamps

# 1. Захват аудио (44.1kHz, mono, 10 сек)
CHUNK, FORMAT, CHANNELS, RATE = 1024, pyaudio.paInt16, 1, 16000
p = pyaudio.PyAudio()
stream = p.open(format=FORMAT, channels=CHANNELS, rate=RATE, input=True, frames_per_buffer=CHUNK)
frames = []
for _ in range(0, int(RATE / CHUNK * 10)):
    data = stream.read(CHUNK)
    frames.append(np.frombuffer(data, dtype=np.int16).astype(np.float32) / 32768.0)
stream.stop_stream()
p.terminate()
audio = np.concatenate(frames)

# 2. VAD (Silero) → оставляем только речь
vad_model = load_silero_vad()
speech_ts = get_speech_timestamps(audio, vad_model, sampling_rate=RATE)
if speech_ts:
    voice_audio = np.concatenate([audio[ts['start']:ts['end']] for ts in speech_ts])
else:
    voice_audio = np.array([], dtype=np.float32)

# 3. Транскрипция (Whisper)
model = whisper.load_model("tiny")
result = model.transcribe(voice_audio, language="ru")
print("Текст:", result["text"])

Типичные ошибки и как их избежать

  • Слишком большой Whisper → на CPU «тихий» процессор убивает: используйте tiny или small, квантизуйте через GGUF.
  • Нет VAD → модель тратит токены на шум/паузы → рост latency и ошибок.
  • Несовместимость sample rate → Whisper требует 16kHz, а камера даёт 48kHz → всегда ресемплируйте через resampy или FFmpeg.
  • Монтаж без синхротаймкодов → видео и аудио «плывут» → сохраняйте frame_timestamps и audio_timestamps в JSON.

Практический кейс: «Авто-режиссёр» для локальных лекций

Вы записываете лекцию с веб-камеры и микрофона. Пайплайн:

  1. Захватываете видео (OpenCV) + аудио (PyAudio) в отдельные потоки.
  2. Транскрибируете каждую секунду (Whisper + sliding window).
  3. Определяете паузы и «неинтересные» сегменты (по эмоциям: нейтральный тон + отсутствие ключевых слов).
  4. Монтируете «чистую» версию: удаляете паузы >2с, вырезаете «эм» и «эээ».
  5. Экспортируете MP4 + JSON с таймкодами удалённых фрагментов.

Результат: 15-минутная лекция → 9 минут без пауз и «воды». Всё — локально, за 2 минуты.

Чеклист перед запуском

Что проверитьЗачем
Версия FFmpeg с поддержкой libvpx/libaomКодеки для高质量 видео без облака
Whisper в FP16 или INT8 (через llama.cpp)Ускорение на CPU без GPU
Синхронизация frame_pts и audio_timeИзбежать рассинхронизации при монтаже
Проверка VAD на вашем шуме (офис/улица)Слишком агрессивный VAD режет речь
Лимит по RAM ( Whisper + OpenCV + FFmpeg = ~3–6 ГБ)Избежать OOM на слабых машинах

Следующий шаг

Перейдите к «Как собрать агента с tool-calling» — научитесь, как превратить результаты монтажа (текст, таймкоды) в действия AI-агента: «вырезать паузы», «создать превью», «отправить в Telegram».