Avançado 15 minÁudio

Assistente vocal 100% local: Whisper + Ollama + Piper

Um assistente vocal local ouve, entende e responde em voz alta sem nunca enviar um byte para a nuvem. Este guia reúne três blocos open source — Whisper para reconhecimento de fala, um LLM executado por Ollama para raciocínio, e Piper para uma voz francesa natural — em um ciclo completo que funciona diretamente na sua própria máquina. Explicamos a cadeia STT → LLM → TTS, o equipamento recomendado e a latência real que você pode esperar.

Por Samir K.·Atualização 2026-08-27·Testado no Windows, macOS e Linux

#Por que usar um assistente de voz local

Alexa, Google Assistant e Siri compartilham o mesmo problema: cada frase que você diz é enviada para servidores distantes para ser transcrita e interpretada. Um assistente vocal local inverte esse modelo. O microfone, o reconhecimento, o raciocínio e a voz de resposta ficam todos no seu hardware. Nada passa pela internet e o assistente continua funcionando mesmo com a conexão interrompida.

Além da privacidade, a vantagem é o controle. Você escolhe o modelo de linguagem, sua personalidade por meio do prompt de sistema, a voz de saída e pode conectá-lo às suas próprias ferramentas — automação residencial, agenda, anotações — sem depender de uma API de terceiros que pode encerrar suas atividades ou mudar suas condições de um dia para o outro.

Privacidade
Nenhum comando de voz é gravado nem analisado por terceiros. Ideal para uso doméstico ou profissional sensível.
Offline
A cadeia completa funciona sem internet uma vez que os modelos forem baixados.
Personalizável
O prompt de sistema, a voz, o idioma, a palavra de ativação e as ferramentas estão todos sob seu controle.
Sem assinatura
Tudo é open source. O único custo é seu hardware e a eletricidade.

#A cadeia STT → LLM → TTS

O kit IA Local

Seu ChatGPT privado e gratuito na sua máquina em 1 hora — LM Studio, Ollama, Open WebUI, seus documentos, sem nuvem.

  • Espaço online vitalício
  • PDF + arquivos
  • Atualizações vitalícias

Um assistente de voz, por mais sofisticado que seja, é apenas uma sequência de três etapas. Entender essa divisão é a chave para diagnosticar a latência e substituir um componente sem comprometer o restante.

  1. 01
    STT — Speech To Text
    O microfone capta sua voz e o Whisper a transforma em texto. Isso é reconhecimento de voz. A qualidade depende do modelo Whisper escolhido e do ruído ambiente.
  2. 02
    LLM — raciocínio
    O texto transcrito é enviado a um modelo de linguagem disponibilizado pelo Ollama, com um prompt de sistema que define o papel do assistente. O LLM gera uma resposta escrita.
  3. 03
    TTS — Texto para Fala
    A resposta em texto é encaminhada para o Piper, que a pronuncia em voz alta com uma voz em francês. Isso é síntese vocal.
i
Três processos independentes
Cada bloco é um programa separado que se comunica com os outros por meio de arquivos de áudio, texto ou chamadas HTTP. Você pode testar cada componente isoladamente antes de conectar o ciclo completo — isso é altamente recomendado.

A latência percebida é a soma das três etapas: o tempo de transcrição Whisper, o tempo de geração do LLM (o mais variável) e o tempo de síntese Piper. Voltaremos a isso com mais detalhes mais abaixo.

#Pré-requisitos e equipamentos

Um assistente de voz local é mais exigente do que um simples chat de texto: Whisper e o LLM compartilham a GPU, e a rapidez de resposta importa. Veja as referências de hardware conforme o nível de ambição.

Mínimo (apenas CPU)
Whisper base + um pequeno LLM em Q4_K_M (≈2 GB), como Qwen 3.5 2B ou Granite 4.2 3B. Funciona, mas espere vários segundos de latência por turno de conversa. Aceitável para automação residencial em que não se fala continuamente.
Confortável
RTX 3060 12GB ou RTX 4070 12GB. Whisper small/medium em GPU + um LLM 8-9B Q4_K_M (≈5-7 GB), por exemplo Qwen 3.5 9B ou Granite 4.2 8B. Latência da ordem de 1 a 3 segundos por turno.
Fluido
RTX 4080 16GB / RTX 4090 24GB ou um Mac M4 Pro (24-48 GB de memória unificada). Whisper medium + um LLM mais potente (Gemma 4 12B ≈8 GB, ou Qwen 3.8 27B ≈18 GB em 24 GB), respostas quase imediatas.
Microfone e áudio
Um microfone USB adequado é suficiente. No Linux, PipeWire ou PulseAudio; no macOS/Windows, a configuração padrão serve.
→
Compartilhar a GPU de forma inteligente
Whisper e o LLM nunca trabalham exatamente ao mesmo tempo: Whisper transcreve e depois o LLM responde. Um GPU de 12 GB pode acomodar Whisper small e um 7B sem rodar os dois ao mesmo tempo em carga máxima.

Quanto ao software, pressupõe-se que o Ollama já esteja instalado e funcionando. Se não for o caso, comece pelo guia de instalação do Ollama antes de continuar. Verifique se o daemon responde.

Verificar Ollama
curl http://localhost:11434/api/tags
# doit renvoyer la liste JSON des modèles installés

#1. Escuta e transcrição (Whisper)

Whisper é o modelo de reconhecimento de voz da OpenAI, distribuído como código aberto. Para uso local em tempo real, priorizamos o faster-whisper, uma reimplementação otimizada que utiliza CTranslate2 e roda muito mais rápido que a versão de referência, tanto em CPU quanto em GPU.

Instalar faster-whisper
pip install faster-whisper sounddevice numpy

Os modelos Whisper estão disponíveis em vários tamanhos. Quanto maior o modelo, melhor a transcrição — especialmente em francês e em ambientes barulhentos —, mas mais lento ele será.

tiny / base
Muito rápidos, perfeitos para um CPU modesto ou para automação residencial. Transcrição correta de comandos curtos em francês.
small
Boa combinação entre velocidade e qualidade para a maioria dos assistentes. Recomendado como ponto de partida.
medium
Muito melhor com frases longas e sotaques, mas exige uma GPU para manter a fluidez.
large-v3
Qualidade máxima, reservada para GPUs com boa performance se a latência for importante.

Aqui está uma função de escuta que grava pelo microfone e retorna o texto transcrito. Definimos explicitamente o francês como idioma para evitar erros de detecção.

ecoute.py
import sounddevice as sd
import numpy as np
from faster_whisper import WhisperModel

# device='cuda' + compute_type='float16' sur GPU ; 'cpu' + 'int8' sinon
model = WhisperModel('small', device='cuda', compute_type='float16')

def ecouter(duree=5, samplerate=16000):
    print('🎙️  Parlez...')
    audio = sd.rec(int(duree * samplerate),
                   samplerate=samplerate, channels=1, dtype='float32')
    sd.wait()
    audio = np.squeeze(audio)
    segments, _ = model.transcribe(audio, language='fr', beam_size=5)
    texte = ' '.join(seg.text for seg in segments).strip()
    print(f'📝 {texte}')
    return texte
→
Detecção de fim de fala
Gravar por uma duração fixa é simples, mas pouco natural. Para um verdadeiro assistente, adicione detecção de atividade vocal (VAD) — a biblioteca silero-vad ou a opção vad_filter do faster-whisper — para interromper a gravação assim que você parar de falar.

#2. Raciocínio (Ollama)

O texto transcrito agora é enviado para o LLM. Ollama expõe uma API HTTP em http://localhost:11434; nós a consultamos em Python. A escolha do modelo depende da sua GPU: um modelo compacto como Qwen 3.5 9B (6,6 GB, 256k de contexto, Apache 2.0) ou Granite 4.2 8B (5,3 GB) em Q4_K_M oferece um excelente equilíbrio para um assistente conversacional.

Baixar um modelo
ollama pull qwen3.5:9b

O prompt de sistema é o que transforma um LLM genérico em um assistente de voz útil. Para a voz, uma instrução crucial: pedir respostas curtas. Um texto longo se torna interminável quando lido em voz alta.

raisonner.py
import requests

SYSTEM = (
    "Tu es un assistant vocal domestique en français. "
    "Réponds toujours de façon brève et naturelle, en une ou deux phrases, "
    "comme à l'oral. Pas de listes, pas de markdown, pas d'emojis."
)

def repondre(question, historique):
    historique.append({'role': 'user', 'content': question})
    r = requests.post('http://localhost:11434/api/chat', json={
        'model': 'qwen3.5:9b',
        'messages': [{'role': 'system', 'content': SYSTEM}] + historique,
        'stream': False,
        'options': {'temperature': 0.6, 'num_predict': 120},
    })
    reponse = r.json()['message']['content'].strip()
    historique.append({'role': 'assistant', 'content': reponse})
    return reponse
i
Manter o fio da conversa
O histórico enviado a cada chamada dá memória ao assistente: ele se lembra da pergunta anterior. Limite o tamanho desse histórico (por exemplo, às 10 últimas mensagens) para não aumentar o contexto e tornar a geração mais lenta.

#3. Síntese de voz em francês (Piper)

Piper é um motor de síntese vocal neural rápido e local, desenvolvido pela comunidade Home Assistant (projeto Rhasspy). Ele produz uma voz francesa muito mais natural do que os antigos motores como espeak, mantendo-se leve o suficiente para rodar em um Raspberry Pi.

Instalar Piper
pip install piper-tts

Piper funciona com vozes pré-treinadas, uma por língua e por timbre. Para o francês, várias vozes estão disponíveis (fr_FR) em diferentes qualidades. Cada voz é um par de arquivos: o modelo .onnx e sua configuração .onnx.json.

Baixar uma voz em francês
# Voix fr_FR « siwis » en qualité medium
python -m piper.download_voices fr_FR-siwis-medium

Em seguida, ele é usado para transformar uma frase em áudio e reproduzir esse áudio diretamente.

parler.py
import wave
import sounddevice as sd
import numpy as np
from piper import PiperVoice

voix = PiperVoice.load('fr_FR-siwis-medium.onnx')

def parler(texte):
    samples = []
    for chunk in voix.synthesize(texte):
        samples.append(np.frombuffer(chunk.audio_int16_bytes, dtype=np.int16))
    audio = np.concatenate(samples)
    sd.play(audio, samplerate=voix.config.sample_rate)
    sd.wait()
→
Escolher a qualidade da voz
As vozes Piper estão disponíveis em x_low, low, medium e high. medium é o melhor equilíbrio para um assistente: naturalidade convincente sem sobrecarga de CPU. high é mais lento e só oferece uma melhora audível em alto-falantes de boa qualidade.

#4. Montar o loop completo

Com os três componentes testados separadamente, só falta encadeá-los em um loop: ouvir, raciocinar, falar, repetir. Aqui está o assistente mínimo completo, reunindo as funções anteriores.

assistant.py
# On suppose importées : ecouter(), repondre(), parler()
historique = []

print('Assistant vocal prêt. Ctrl+C pour quitter.')
parler("Bonjour, je vous écoute.")

try:
    while True:
        question = ecouter(duree=5)
        if not question:
            continue
        if 'au revoir' in question.lower():
            parler('À bientôt !')
            break
        reponse = repondre(question, historique)
        parler(reponse)
except KeyboardInterrupt:
    print('\nArrêt.')

É isso: cerca de cem linhas distribuídas em três arquivos, e você tem um assistente de voz que ouve em francês, pensa com um LLM local e responde em voz alta, sem nenhuma chamada de rede de saída. A partir daí, é possível adicionar um wake-word (“Ok maison”) com openWakeWord, uma VAD para escuta contínua ou conectar ferramentas.

#Latência real e otimizações

A pergunta que determina o sucesso ou o fracasso de um assistente de voz: quanto tempo passa entre o fim da sua frase e o início da resposta falada? Veja algumas ordens de grandeza observadas em uma RTX 4070 com Whisper small e um modelo de 8–9B em Q4_K_M (como Qwen 3.5 9B).

Transcrição Whisper
≈ 0,3 a 0,8 s para uma frase de 5 s com o modelo small na GPU. Na CPU, considere 2 a 4 s.
Geração LLM
O componente mais variável. Um modelo de 8 a 9B em GPU gera a primeira resposta em aproximadamente 0,5 a 1,5 segundos, dependendo do comprimento. É aqui que num_predict baixo e um modelo rápido têm mais impacto.
Síntese Piper
≈ 0,2 a 0,5 s para uma ou duas frases com uma voz de qualidade medium. Muito rápido, raramente é o gargalo.
Tempo total percebido
Cerca de 1 a 3 s por turno em uma GPU de faixa intermediária. Ficar abaixo de um segundo exige hardware de ponta ou streaming.
→
O recurso mais eficaz: o streaming
Em vez de esperar a resposta completa do LLM antes de sintetizar, receba a geração em streaming, frase por frase, e envie cada frase concluída para o Piper enquanto o LLM continua. A voz começa muito mais cedo e a latência percebida cai significativamente.
Manter os modelos carregados
Configure OLLAMA_KEEP_ALIVE para evitar que o Ollama descarregue o modelo da memória entre duas perguntas — o recarregamento leva vários segundos.
Respostas curtas
Um num_predict baixo e um prompt de sistema que exige concisão reduzem diretamente o tempo de geração e a duração da leitura.
Whisper adaptado
Não use large-v3 se small for suficiente para suas condições acústicas: você economiza centenas de milissegundos a cada turno da conversa.

#5. Integrar ao Home Assistant

Se o seu objetivo é controlar uma casa conectada por voz, não é necessário reescrever todo o código. O Home Assistant integra nativamente o pipeline “Assist”, e tanto o Whisper quanto o Piper podem ser conectados a ele por meio de add-ons oficiais — eles, aliás, foram desenvolvidos nesse ecossistema.

  1. 01
    Instalar os complementos de voz
    Através de Configurações → Módulos Complementares, adicione 'Whisper' e 'Piper'. O Home Assistant os executa localmente como serviços de STT e TTS.
  2. 02
    Criar um pipeline Assist
    Em Configurações → Voz, crie um assistente: escolha Whisper para reconhecimento, Piper (voz fr_FR) para síntese.
  3. 03
    Conectar o LLM Ollama
    Home Assistant oferece uma integração « Ollama » como agente de conversa. Insira a URL http://localhost:11434 e seu modelo para substituir a análise de intenção padrão.
  4. 04
    Escolher um ponto de entrada de voz
    Um satélite ESP32 (Voice PE), um telefone antigo ou o aplicativo móvel servem como microfone/alto-falante nos cômodos.
i
Duas abordagens complementares
O script Python deste guia oferece controle total e serve como ambiente de aprendizado. O Home Assistant oferece uma integração de automação residencial pronta para usar. Muitos começam pelo script para entender a cadeia de processamento, depois passam para o Assist para uso em casa.

#Solução de problemas

Whisper transcreve em uma língua errada
Force language='fr' em transcribe(). Sem isso, uma frase curta pode ser detectada como inglês.
Nenhum som de saída
Verifique o dispositivo de saída do sounddevice (sd.query_devices()) e certifique-se de que a taxa de amostragem passada para sd.play corresponde à voix.config.sample_rate.
O microfone não grava nada
Teste sd.query_devices() para identificar o índice correto de entrada e verifique as permissões do microfone (macOS) ou a fonte PipeWire/PulseAudio (Linux).
Respostas muito longas e ilegíveis
Reforce a instrução de brevidade do prompt de sistema e reduza num_predict. Um LLM prolixo arruína a experiência de voz.
Latência que aumenta ao longo da conversa
O histórico aumenta o contexto. Limite-o às últimas N mensagens.
Ollama recarrega o modelo a cada pergunta
Aumente OLLAMA_KEEP_ALIVE (por exemplo, para 30m) para manter o modelo na VRAM entre as rodadas.

#Para se aprofundar

Seu assistente de voz depende de um LLM local bem escolhido e bem configurado. Estes guias do site complementam a configuração:

Whisper + Ollama : transcrição e resumo
Para se aprofundar na parte de áudio e processar arquivos longos em vez de trabalhar em tempo real.
LLM local para automação residencial
Para conectar seu assistente ao Home Assistant e controlar a casa por voz, preservando a privacidade.
Q4, Q5, Q8: qual quantização escolher
Para encontrar o melhor equilíbrio entre qualidade da resposta, velocidade e VRAM de acordo com sua GPU.
Este guia ajudou você?

Um comentário, um erro ou uma observação? Avise-nos; isso ajuda a melhorar o guia para todos.