Files
satellite/docs/integration/vad-wakeword.md
sirmrakandQwen-Coder adac79e765 Документация: рефакторинг структуры docs/ и очистка мусора
- Перемещена документация в docs/ с четкой структурой:
  - tutorials/ — пошаговые руководства (2mic-hat, installer)
  - integration/ — техническая интеграция (vad-wakeword, mqtt-led)
  - deployment/ — развёртывание (systemd-services)
  - architecture/ — архитектура проекта (overview)
- Обновлён README.md с навигацией по документации
- DEPLOY.md сокращён до quick start с ссылками на docs/
- Добавлен docs/README.md — индекс документации
- Создан QWEN.md — контекст для ИИ-ассистента
- Удалён мусор:
  - wyoming_satellite.zip (build artifact)
  - wyoming-led.service, wyoming-satellite.service (дубликаты)
  - .qwen/settings.json.orig (бэкап)
  - .lgd-nfy0 (пустой файл)
  - docker/run (заглушка)
- Обновлён .gitignore:
  - examples/led_brightness_config.json (автогенерируемый конфиг)
  - *.old, *.bak, *~ (бэкапы)
  - *.zip (архивы)
  - .qwen/settings.json.orig
  - *.lgd-* (пустые файлы)
- led_brightness_config.json исключён из отслеживания (assume-unchanged)

Co-authored-by: Qwen-Coder <qwen-coder@alibabacloud.com>
2026-05-19 20:12:20 +03:00

63 lines
6.9 KiB
Markdown
Executable File
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.
## Интеграция VAD и Wakeword: выводы и план
### 1) Картина текущей архитектуры (Wyoming Satellite)
- **Режимы работы спутника**:
- AlwaysStreaming — всегда стримит аудио, VAD/Wake не участвуют.
- VadStreaming — локальный VAD решает момент старта стриминга; при активации отправляется предречь (pre-roll), опционально действует таймаут на ожидание wakeword.
- WakeStreaming — аудио уходит в локальный wakeword-сервис (Wyoming-протокол); при Detection начинается стриминг на сервер (STT/интенты).
- **VAD по умолчанию**: `SileroVad` с интерфейсом `__call__(audio_bytes|None) -> bool`, поддержка `reset()` через передачу `None`. Предречь хранится в кольцевом буфере, при активации догружается первой.
- **Wakeword**: внешние сервисы по Wyoming (например, openWakeWord, Porcupine, Snowboy), принимают `Audio*` события и отдают `Detection`.
### 2) Что есть в `myproject`
- **VAD** (`myproject/vad_core.py`):
- Использует `webrtcvad.Vad` + энерго-критерии, адаптивный порог, простое шумоподавление и автоусиление.
- Имеет предбуфер и основной буфер записи сегмента речи; по завершении вызывает callback с целым кусочком аудио.
- Ввод аудио сейчас завязан на PyAudio внутри класса, то есть детектор и источник аудио слиты.
- **Wakeword на Vosk** (`myproject/vosk_local_STT.py` + `commands.py`):
- Собирает грамматику из `commands.yaml` (в т.ч. секцию `Wakewords`) и распознаёт текст.
- Факт wakeword определяется как точное совпадение распознанной фразы с элементами из `Wakewords` (то есть post-utterance wakeword через STT).
### 3) Сопоставление и ключевые различия
- В Wyoming VAD — быстрый фрейм-по-фрейм решатель с мгновенным флагом активации, а у вас — сегментатор с внутренним циклом и завершением по тишине.
- В Wyoming wakeword — отдельный потоковый сервис (KWS-подобное поведение), а у вас — определение wakeword как часть STT после завершения фразы.
### 4) Варианты интеграции
1. **Заменить локальный VAD на ваш (рекомендуется этап 2):**
- Выделить из `VADPolling` чистый детектор без PyAudio-ввода (API вида: `process(frame_bytes) -> { started/stopped/speech_detected, prebuffer, ... }`).
- Добавить фабрику VAD в спутник: `settings.vad.system: "silero"|"my_webrtc_vad"`, инициализировать нужную реализацию.
- При активации отдавать предбуфер и стартовать стриминг — совместимо с текущей логикой VadStreaming.
2. **Оформить wakeword на Vosk как Wyoming-сервис (рекомендуется этап 1):**
- Небольшой сервер по Wyoming-протоколу, который:
- подгружает грамматику только из `Wakewords`;
- принимает `AudioStart/AudioChunk/AudioStop` и кормит чанк в `KaldiRecognizer.AcceptWaveform`;
- при совпадении фразы — отправляет `Detection(name=...)` немедленно.
- Подключается как `wake.system: "vosk_wake"`, аналогично `openWakeWord`/`porcupine1`.
### 5) Минимальные изменения кода
- **Для wakeword (этап 1):**
- Реализовать отдельный модуль `vosk_wake` (сервер Wyoming): запуск по TCP, обработка событий, генерация `Detection` по фразам из `Wakewords`.
- Unit-файл/скрипт запуска по аналогии с `local/services/wyoming-wakeword.service` и запись в конфиг `wake.system`.
- **Для VAD (этап 2):**
- Вынести логику детектора из `VADPolling` в отдельный класс без I/O.
- Добавить флаг `vad.system` и фабрику выбора реализации; адаптер, который преобразует `AudioChunk` → фреймы и использует ваш детектор для решения «старт/стоп/предречь».
### 6) Пошаговый план внедрения
1) Wakeword на Vosk (быстрый выигрыш):
- Сделать `vosk_wake` сервис: узкая грамматика = только `Wakewords`, немедленный `Detection` при совпадении.
- Прописать сервис в systemd/скрипте, указать URI и `wake.system`.
- Протестировать в режиме `WakeStreamingSatellite`.
2) Замена VAD:
- Рефакторинг `VADPolling`: отделить детектор от аудио-источника.
- Добавить `vad.system` и внедрить адаптер под текущий интерфейс Wyoming.
- Протестировать в `VadStreamingSatellite` с предбуфером и таймаутом wakeword.
### 7) Риски и примечания
- Vosk как wakeword — это распознавание текста; для «на лету» задержка может быть выше, чем у специализированного KWS. С узкой грамматикой (только wakewords) будет быстрее и устойчивее.
- Ваши улучшения VAD (AGC/NR/адаптивные пороги) полезны; главное — отделить I/O и обеспечить детерминированный фреймовый API, совместимый с Wyoming.
### 8) Резюме
- Этап 1: добавить `vosk_wake` как Wyoming-сервис wakeword — минимум инвазивности и быстрая интеграция.
- Этап 2: внедрить ваш VAD через фабрику и адаптер — получить продвинутую локальную активацию речи, сохранив предречь и таймауты.