Piper TTS и FastAPI на Repka Pi 4: DIY синтезатор речи (2026) | AiManual
AiManual Logo Ai / Manual.
02 Апр 2026 Гайд

Как настроить синтезатор речи на Repka Pi 4: Piper TTS и FastAPI сервер

Подробное руководство по настройке нейросетевого синтеза речи Piper на Repka Pi 4 с созданием своего FastAPI сервера и автозагрузкой через systemd.

Зачем это вообще нужно?

Вы купили Repka Pi 4 для умной колонки, голосового помощника или просто чтобы похвастаться перед друзьями. Облачные TTS вроде Google или Yandex кушают трафик, требуют API-ключи и иногда режут уши металлическим тембром. Локальные решения? Многие тормозят на слабом железе или выглядят как артефакты из 2010 года.

Piper — это другая история. Нейросетевой синтезатор, который работает на процессоре, поддерживает кучу языков (включая русский) и звучит... почти по-человечески. А главное — он легкий. Мы обернем его в FastAPI сервер, чтобы любой девайс в вашей сети мог запросить аудио по HTTP. Без лишней магии, только рабочий код.

Проверено на Repka Pi 4 с 4 ГБ ОЗУ и Debian Bookworm. Если у вас другой дистрибутив — команды могут немного отличаться. Убедитесь, что система обновлена до актуального состояния на 02.04.2026.

Что понадобится перед началом

  • Repka Pi 4 (или любая другая плата с ARM-архитектурой). Можно и на x86, но тогда это уже не так героически.
  • SD-карта от 16 ГБ (рекомендую SanDisk Extreme — они меньше глючат при постоянной записи).
  • Стабильное интернет-соединение для загрузки моделей.
  • Базовые навыки работы с Linux через терминал. Если боитесь командной строки — возможно, вам стоит сначала посмотреть эту статью про умные колонки.

1 Устанавливаем Piper TTS

Не пытайтесь ставить Piper из системных репозиториев — там обычно древние версии. Собираем из исходников. Это гарантирует совместимость с последними моделями 2026 года.

# Обновляем систему и ставим зависимости
sudo apt update && sudo apt upgrade -y
sudo apt install -y cmake g++ libsndfile1-dev libonnxruntime-dev python3 python3-pip git
# Клонируем репозиторий Piper (используем официальный форк, если основной замерз)
git clone https://github.com/rhasspy/piper.git
cd piper
mkdir build && cd build
# Компилируем. На Repka Pi 4 это займет минут 15-20.
cmake .. -DCMAKE_BUILD_TYPE=Release
make -j4
💡
Флаг -j4 говорит использовать все 4 ядра процессора. Если сборка падает с ошибкой нехватки памяти, уменьшите до -j2. А лучше добавьте файл подкачки, если у вас 2 ГБ ОЗУ.

2 Качаем голосовые модели

Бинарник Piper без модели — как автомобиль без колес. На 2026 год актуальные модели лежат в основном на Hugging Face. Для русского языка я рекомендую модель на основе VITS — она дает наиболее естественное звучание.

# Создаем директорию для моделей
mkdir -p ~/.local/share/piper/models
cd ~/.local/share/piper/models
# Качаем русскую модель (пример, проверьте актуальность ссылки на 02.04.2026)
wget https://huggingface.co/rhasspy/piper-tts/resolve/main/ru/ru_RU/medium/ru_RU-medium.onnx
wget https://huggingface.co/rhasspy/piper-tts/resolve/main/ru/ru_RU/medium/ru_RU-medium.onnx.json

Модель medium — оптимальна по балансу качества и скорости. Если нужно максимальное быстродействие, возьмите low. Для максимального качества — high, но учтите, что она может подтормаживать на Pi 4. В обзоре легковесных TTS-моделей 2026 есть сравнение производительности.

3 Пишем FastAPI сервер

Теперь обернем Piper в HTTP API. Почему FastAPI? Потому что он быстрый, асинхронный и требует в два раза меньше кода, чем Flask. Устанавливаем.

pip3 install fastapi uvicorn pydantic

Создаем файл tts_server.py в удобном месте, например, в ~/piper_tts/.

from fastapi import FastAPI, HTTPException, Response
from pydantic import BaseModel
import subprocess
import tempfile
import os
from pathlib import Path

app = FastAPI(title="Piper TTS Server", version="2026.1")

# Пути (измените под свою систему)
PIPER_PATH = Path("/home/repka/piper/build/piper")  # Путь к бинарнику Piper
MODEL_PATH = Path("/home/repka/.local/share/piper/models/ru_RU-medium.onnx")

class TTSRequest(BaseModel):
    text: str
    speaker_id: int = 0  # Некоторые модели поддерживают несколько голосов
    length_scale: float = 1.0  # Скорость речи (1.0 = нормальная)
    noise_scale: float = 0.667  
    noise_w: float = 0.8

@app.post("/synthesize", response_class=Response)
async def synthesize(request: TTSRequest):
    """
    Синтезирует речь из текста, возвращает WAV аудио.
    """
    if not PIPER_PATH.exists():
        raise HTTPException(status_code=500, detail="Piper binary not found")
    if not MODEL_PATH.exists():
        raise HTTPException(status_code=500, detail="Model file not found")
    
    # Создаем временный файл для вывода
    with tempfile.NamedTemporaryFile(suffix=".wav", delete=False) as tmp_file:
        output_path = tmp_file.name
    
    try:
        # Вызываем Piper через subprocess
        cmd = [
            str(PIPER_PATH),
            "--model", str(MODEL_PATH),
            "--output_file", output_path,
            "--speaker", str(request.speaker_id),
            "--length_scale", str(request.length_scale),
            "--noise_scale", str(request.noise_scale),
            "--noise_w", str(request.noise_w)
        ]
        
        # Передаем текст через stdin
        process = subprocess.run(
            cmd,
            input=request.text.encode('utf-8'),
            capture_output=True,
            check=False
        )
        
        if process.returncode != 0:
            raise HTTPException(status_code=500, detail=f"Piper error: {process.stderr.decode()}")
        
        # Читаем сгенерированный WAV
        with open(output_path, "rb") as f:
            audio_data = f.read()
        
        # Удаляем временный файл
        os.unlink(output_path)
        
        return Response(content=audio_data, media_type="audio/wav")
        
    except Exception as e:
        if os.path.exists(output_path):
            os.unlink(output_path)
        raise HTTPException(status_code=500, detail=str(e))

@app.get("/health")
async def health():
    return {"status": "ok", "engine": "piper", "model": MODEL_PATH.name}

if __name__ == "__main__":
    import uvicorn
    uvicorn.run(app, host="0.0.0.0", port=8000)

В коде выше используется синхронный subprocess.run. Для высокой нагрузки (десятки запросов в секунду) лучше использовать asyncio.subprocess, но на Pi 4 вы вряд ли достигнете таких нагрузок. Главное — не блокировать цикл событий.

4 Настраиваем systemd для автозапуска

Чтобы сервер включался при загрузке и перезапускался при сбоях, создаем systemd-юнит. Это надежнее, чем скрипты в crontab.

sudo nano /etc/systemd/system/piper-tts.service
[Unit]
Description=Piper TTS FastAPI Server
After=network.target

[Service]
Type=simple
User=repka  # Замените на ваше имя пользователя
WorkingDirectory=/home/repka/piper_tts  # Путь к директории с tts_server.py
ExecStart=/usr/bin/python3 /home/repka/piper_tts/tts_server.py
Restart=always
RestartSec=10
Environment="PATH=/usr/bin"

[Install]
WantedBy=multi-user.target
# Активируем и запускаем
sudo systemctl daemon-reload
sudo systemctl enable piper-tts.service
sudo systemctl start piper-tts.service

Проверяем статус:

sudo systemctl status piper-tts.service

Если видите active (running) — все хорошо. Если нет — смотрите логи: sudo journalctl -u piper-tts.service -f.

5 Тестируем и используем

Сервер должен быть доступен на порту 8000. Откройте браузер на другом устройстве в той же сети и перейдите по адресу http://[IP_ВАШЕЙ_REPKA]:8000/health. Должен вернуться JSON.

Для синтеза речи отправьте POST-запрос:

curl -X POST http://localhost:8000/synthesize \
  -H "Content-Type: application/json" \
  -d '{"text": "Привет, мир! Это синтез речи на Repka Pi 4."}' \
  --output speech.wav

Теперь у вас есть свой облачный TTS, только локальный. Подключите его к AnyTTS для интеграции с ChatGPT или к самодельной умной колонке.

Где тонко, там и рвется: нюансы и косяки

Проблема Причина Решение
Piper падает с ошибкой сегментации Недостаточно памяти или модель повреждена Добавьте swap-файл (2 ГБ), перекачайте модель.
Задержка в несколько секунд перед ответом Модель загружается при каждом запросе Используйте флаг --cache при запуске Piper (если поддерживается в вашей версии).
Роботизированный голос, неестественные интонации Параметры noise_scale и noise_w не откалиброваны Поэкспериментируйте со значениями в диапазоне 0.5-1.0. Каждая модель — уникальна.
FastAPI сервер не стартует, порт занят Другой сервис использует порт 8000 Измените порт в uvicorn.run() или остановите конфликтующий сервис.

Частые вопросы (FAQ)

Можно ли использовать несколько языков?

Да. Скачайте модели для нужных языков и модифицируйте сервер, чтобы принимать параметр language. Либо запустите несколько экземпляров Piper с разными моделями и настройте семантический роутинг.

Piper vs Sonya TTS — кто лучше?

Sonya TTS — новее и выразительнее для русского языка (см. обзор Sonya TTS), но требует больше ресурсов. На Repka Pi 4 Piper — более безопасный выбор по стабильности.

Как увеличить скорость синтеза?

1. Используйте модель с пометкой low.
2. Уменьшите длину входного текста (разбивайте длинные тексты на фразы).
3. Рассмотрите аппаратное ускорение (но на Pi 4 с нейронным ускорителем это нетривиально).

Можно ли озвучивать книги таким setup?

Технически — да. Но для озвучки библиотек лучше использовать выделенный сервер с более мощным CPU/GPU. Посмотрите кейс «Прометей» для вдохновения.

И последнее: не зацикливайтесь только на Piper. Мир opensource TTS быстро меняется. Заглядывайте иногда в обзоры движков за 2026 год, чтобы быть в курсе новых вариантов вроде QwenTTS или Kokoro. Ваша Repka Pi 4 — это полигон для экспериментов, а не музейный экспонат.

Подписаться на канал