docs: add project documentation and voice cloning notice
This commit is contained in:
160
README.md
Normal file
160
README.md
Normal file
@@ -0,0 +1,160 @@
|
||||
# VoxCPM2 + vLLM-Omni
|
||||
|
||||
PoC para servir o modelo `openbmb/VoxCPM2` com vLLM-Omni, usando GPU NVIDIA e Podman.
|
||||
|
||||
O serviço expõe uma API compatível com OpenAI em `POST /v1/audio/speech` e oferece:
|
||||
|
||||
- Síntese de voz em WAV;
|
||||
- Streaming de áudio PCM `s16le`, mono, 48 kHz;
|
||||
- Perfis de voz pré-calculados;
|
||||
- Criação de novos perfis de voz em um container temporário.
|
||||
|
||||
> Use somente áudios de referência com consentimento explícito e documentado.
|
||||
|
||||
## Pré-requisitos
|
||||
|
||||
No host:
|
||||
|
||||
- Oracle Linux 9 ou outra distribuição Linux compatível;
|
||||
- GPU NVIDIA compatível (a PoC foi validada em OCI `VM.GPU.A10.1`);
|
||||
- Driver NVIDIA funcional;
|
||||
- Podman e NVIDIA Container Toolkit/CDI configurados;
|
||||
- Acesso à internet no primeiro build e primeiro boot.
|
||||
|
||||
Valide a GPU no host:
|
||||
|
||||
```bash
|
||||
nvidia-smi -L
|
||||
```
|
||||
|
||||
Valide o acesso à GPU pelo Podman:
|
||||
|
||||
```bash
|
||||
podman run --rm \
|
||||
--device nvidia.com/gpu=all \
|
||||
--security-opt label=disable \
|
||||
ubuntu \
|
||||
nvidia-smi -L
|
||||
```
|
||||
|
||||
## Build
|
||||
|
||||
```bash
|
||||
git clone <URL_DO_REPOSITORIO>
|
||||
cd voxcpm-vllm-omni
|
||||
|
||||
mkdir -p runtime/hf-cache runtime/voices
|
||||
|
||||
podman build --pull=newer \
|
||||
-t voxcpm-omni:0.28.0-1 \
|
||||
-f Containerfile .
|
||||
```
|
||||
|
||||
## Executar o servidor
|
||||
|
||||
Para acesso apenas local:
|
||||
|
||||
```bash
|
||||
podman run -d \
|
||||
--name voxcpm-omni \
|
||||
--restart=always \
|
||||
--device nvidia.com/gpu=all \
|
||||
--security-opt label=disable \
|
||||
--ipc=host \
|
||||
-p 127.0.0.1:8000:8000 \
|
||||
-v "$PWD/runtime/hf-cache:/root/.cache/huggingface" \
|
||||
-v "$PWD/runtime/voices:/opt/voices:ro" \
|
||||
voxcpm-omni:0.28.0-1
|
||||
```
|
||||
|
||||
No primeiro boot, o modelo será baixado para `runtime/hf-cache/`.
|
||||
|
||||
```bash
|
||||
podman logs -f voxcpm-omni
|
||||
curl http://127.0.0.1:8000/v1/models
|
||||
curl http://127.0.0.1:8000/v1/audio/voices
|
||||
```
|
||||
|
||||
## Gerar WAV
|
||||
|
||||
```bash
|
||||
curl -sS -X POST http://127.0.0.1:8000/v1/audio/speech \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{
|
||||
"model": "openbmb/VoxCPM2",
|
||||
"input": "Olá. Este é um teste de síntese de voz.",
|
||||
"voice": "default",
|
||||
"response_format": "wav"
|
||||
}' \
|
||||
--output teste.wav
|
||||
```
|
||||
|
||||
Para usar uma voz pre-processada, substitua `default` pelo nome do perfil, por exemplo `carbonera`.
|
||||
|
||||
## Streaming PCM
|
||||
|
||||
```bash
|
||||
curl --no-buffer -sS -X POST http://127.0.0.1:8000/v1/audio/speech \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{
|
||||
"model": "openbmb/VoxCPM2",
|
||||
"input": "Olá. Este é um teste de streaming.",
|
||||
"voice": "default",
|
||||
"stream": true,
|
||||
"stream_format": "audio",
|
||||
"response_format": "pcm"
|
||||
}' \
|
||||
--output resposta.pcm
|
||||
```
|
||||
|
||||
Formato retornado: PCM `s16le`, mono, 48 kHz.
|
||||
|
||||
## Criar uma voz pre-processada
|
||||
|
||||
Os arquivos de referência não devem ir para o Git.
|
||||
|
||||
Com o serviço parado:
|
||||
|
||||
```bash
|
||||
podman stop voxcpm-omni
|
||||
|
||||
PROMPT_TEXT="$(tr '\n' ' ' < "$PWD/reference-audio/nome-da-voz.txt")"
|
||||
|
||||
podman run --rm \
|
||||
--device nvidia.com/gpu=all \
|
||||
--security-opt label=disable \
|
||||
--ipc=host \
|
||||
-v "$PWD/runtime/hf-cache:/root/.cache/huggingface" \
|
||||
-v "$PWD/runtime/voices:/opt/voices" \
|
||||
-v "$PWD/reference-audio/nome-da-voz.wav:/opt/input/voz.wav:ro" \
|
||||
voxcpm-omni:0.28.0-1 \
|
||||
python /opt/vllm-omni/examples/online_serving/text_to_speech/voxcpm2/precompute_custom_voice.py \
|
||||
--model openbmb/VoxCPM2 \
|
||||
--voice-name nome-da-voz \
|
||||
--ref-audio /opt/input/voz.wav \
|
||||
--prompt-text "$PROMPT_TEXT" \
|
||||
--mode ref_continuation \
|
||||
--output-dir /opt/voices \
|
||||
--device cuda
|
||||
|
||||
podman start voxcpm-omni
|
||||
```
|
||||
|
||||
Confira a nova voz:
|
||||
|
||||
```bash
|
||||
curl http://127.0.0.1:8000/v1/audio/voices
|
||||
```
|
||||
|
||||
## Dados persistentes
|
||||
|
||||
```text
|
||||
runtime/hf-cache/ Pesos baixados do modelo
|
||||
runtime/voices/ Perfis .safetensors e manifesto das vozes
|
||||
```
|
||||
|
||||
Esses diretórios não são versionados no Git. Para migrar vozes aprovadas entre hosts, copie `runtime/voices/` por um canal seguro.
|
||||
|
||||
## Segurança
|
||||
|
||||
Não exponha a porta 8000 diretamente à internet sem controles adicionais. Para acesso remoto, restrinja firewall e NSG/Security List da OCI ao IP ou à rede autorizada e use um proxy reverso com TLS e autenticação.
|
||||
59
VOICE_CLONING_NOTICE.md
Normal file
59
VOICE_CLONING_NOTICE.md
Normal file
@@ -0,0 +1,59 @@
|
||||
# Uso de clonagem de voz e responsabilidade
|
||||
|
||||
> **Minuta para revisão jurídica.** Este aviso complementa a documentação do
|
||||
> projeto; não substitui contratos, termos de uso, políticas de privacidade ou
|
||||
> parecer jurídico aplicáveis ao operador do serviço.
|
||||
|
||||
## Licença do código
|
||||
|
||||
O código deste repositório é disponibilizado publicamente sob a Licença Apache
|
||||
2.0, incluindo uso, alteração, distribuição e exploração comercial, nos termos
|
||||
do arquivo [LICENSE](LICENSE). Componentes de terceiros, modelos, pesos e
|
||||
dependências podem possuir licenças e condições próprias, que devem ser
|
||||
observadas pelo usuário.
|
||||
|
||||
## Responsabilidade por vozes, conteúdo e uso do serviço
|
||||
|
||||
Quem implanta, administra, integra, fornece ou utiliza este serviço
|
||||
("Operador") é exclusivamente responsável por:
|
||||
|
||||
1. obter, registrar e manter todas as autorizações, consentimentos, licenças e
|
||||
demais direitos necessários para gravar, enviar, processar, clonar,
|
||||
sintetizar, reproduzir, distribuir ou explorar comercialmente qualquer voz,
|
||||
áudio, texto, identidade ou outro conteúdo utilizado no serviço;
|
||||
2. confirmar que a clonagem ou síntese não viola direitos de personalidade,
|
||||
direitos autorais, direitos conexos, marcas, privacidade, proteção de dados,
|
||||
obrigações contratuais ou qualquer lei, regulamento ou ordem aplicável;
|
||||
3. informar adequadamente os titulares das vozes e os usuários finais sobre o
|
||||
tratamento de dados e sobre o uso de voz sintética, quando exigido;
|
||||
4. responder integralmente pela autoria, legitimidade, segurança, divulgação,
|
||||
distribuição e utilização dos áudios e conteúdos gerados; e
|
||||
5. manter controles técnicos e operacionais para impedir uso não autorizado,
|
||||
enganoso, fraudulento ou que permita se passar por terceiro sem autorização.
|
||||
|
||||
É proibido usar este projeto para clonar, imitar ou representar a voz de uma
|
||||
pessoa sem a autorização válida do respectivo titular ou outro fundamento
|
||||
jurídico aplicável. O Operador deverá fornecer, quando solicitado pela
|
||||
autoridade competente ou pelo titular, evidências das autorizações e da base
|
||||
legal adotada.
|
||||
|
||||
## Ausência de responsabilidade da Oracle
|
||||
|
||||
Na máxima extensão permitida pela legislação aplicável, a Oracle Corporation e
|
||||
suas afiliadas não são autoras, provedoras, controladoras, operadoras,
|
||||
coparticipantes, representantes ou garantidoras das vozes, áudios, perfis de
|
||||
voz, conteúdos, resultados ou serviços criados, hospedados ou disponibilizados
|
||||
pelo Operador a partir deste projeto.
|
||||
|
||||
O Operador assume, de forma exclusiva, toda a responsabilidade por reclamações,
|
||||
perdas, danos, sanções, custos e despesas decorrentes ou relacionados à coleta,
|
||||
clonagem, síntese, geração, armazenamento, transmissão, publicação,
|
||||
comercialização ou demais usos de vozes e conteúdos no serviço. Nada neste
|
||||
repositório constitui autorização, endosso, garantia, parceria, agência,
|
||||
sociedade ou coparticipação da Oracle com o Operador ou com os serviços por ele
|
||||
oferecidos.
|
||||
|
||||
Esta seção deve ser validada e, se necessário, substituída pelo texto aprovado
|
||||
pelo departamento jurídico da Oracle antes de qualquer divulgação externa ou
|
||||
uso contratual. Nenhuma pessoa pode vincular a Oracle ou suas afiliadas sem
|
||||
autorização expressa e por escrito.
|
||||
54
config/voxcpm2-a10.yaml
Normal file
54
config/voxcpm2-a10.yaml
Normal file
@@ -0,0 +1,54 @@
|
||||
# VoxCPM2 deploy: single-stage AR pipeline with per-request state batching.
|
||||
# Runs on large (H20 141GB) and small (24GB L4) cards alike: the KV cache is
|
||||
# pinned to a right-sized budget instead of ballooning to fill the card.
|
||||
#
|
||||
# VoxCPM2-local runtime knobs are passed through hf_overrides.
|
||||
async_chunk: false
|
||||
dtype: bfloat16
|
||||
|
||||
stages:
|
||||
- stage_id: 0
|
||||
custom_voice_dir: /home/opc/voxcpm-vllm-poc/runtime/voices
|
||||
max_num_seqs: 2
|
||||
#max_num_seqs: 8
|
||||
gpu_memory_utilization: 0.9
|
||||
# Right-size the KV cache instead of letting it fill gpu_memory_utilization.
|
||||
# max_num_seqs(8) * max_model_len(4096) ~= 32k tokens; 6 GiB leaves headroom
|
||||
# for longer live requests while keeping VoxCPM2 TTS decode batches small
|
||||
# enough to avoid the high ITL observed with large admission caps.
|
||||
# The remaining VRAM stays free for the VoxCPM2 diffusion side-path
|
||||
# (LocDiT / AudioVAE / code2wav + batch CUDA-graph pools), which allocates
|
||||
# outside vLLM's KV accounting during inference. Keeps peak ~13 GiB on any
|
||||
# card and avoids per-rebase OOM tuning on small CI GPUs.
|
||||
# Assumes prefix caching off and typical live decode concurrency <= ~8;
|
||||
# raise this cap if either grows or enable_prefix_caching is turned on.
|
||||
kv_cache_memory_bytes: 6442450944 # 6 GiB
|
||||
enforce_eager: true
|
||||
trust_remote_code: true
|
||||
enable_prefix_caching: false
|
||||
async_scheduling: true
|
||||
max_num_batched_tokens: 4096
|
||||
max_model_len: 4096
|
||||
devices: "0"
|
||||
engine_extras:
|
||||
hf_overrides:
|
||||
voxcpm2_runtime_config:
|
||||
audio_emit_every: 1
|
||||
vae_decode_every: 3
|
||||
enable_batched_cfm: true
|
||||
enable_batched_vae_decode: true
|
||||
coalesce_audio_d2h: true
|
||||
enable_loc_dit_fused_qkv: true
|
||||
enable_loc_dit_fused_mlp: true
|
||||
enable_loc_dit_zero_dt_cache: true
|
||||
enable_loc_dit_skip_qkv_contig: true
|
||||
enable_loc_dit_reduce_overhead_no_cg: true
|
||||
enable_unified_decode_graph: true
|
||||
unified_decode_graph_max_batch_size: 8
|
||||
default_sampling_params:
|
||||
temperature: 0.0
|
||||
top_p: 1.0
|
||||
top_k: -1
|
||||
max_tokens: 4096
|
||||
seed: 42
|
||||
repetition_penalty: 1.0
|
||||
Reference in New Issue
Block a user