Ir para a navegação

Processamento em batch

Process multiple lipsync generations efficiently

O batch Sync Labs API processa até 500 gerações lip sync em uma única solicitação, enviada como um arquivo JSONL ou como um array JSON de linhas. Ela foi feita para grandes volumes de clipes curtos, como campanhas de video personalizadas ou localização de conteúdo, em que os resultados podem chegar ao longo de várias horas.

Quem pode usar a API de lotes?

A API de lotes exige um plano Scale ou superior e aprovação para sua organização. O acesso fica desativado por padrão, inclusive em novas assinaturas Scale. Entre em contato com o suporte para solicitar acesso. Usuários existentes também precisam de aprovação após uma análise de uso e faturamento.

Sem aprovação, a organização recebe 403 com errorCode: batch_access_not_enabled, inclusive com dry_run. Após a aprovação, os demais planos e as contas gratuitas recebem 402 com errorCode: plan_feature_unavailable. requiredPlan é scale, ou enterprise nos planos de créditos.

A remoção do acesso para criar lotes não interrompe os lotes já aceitos. Você pode consultar o status e baixar os resultados disponíveis.

  • Um batch comporta de 20 a 500 registros por padrão, ou o limite próprio da sua conta.
  • Cada batch ativo ocupa uma vaga do seu limite de batches, que é o limite de simultaneidade do seu plano. Os registros dele não contam para a simultaneidade de /v2/generate.
  • A saída estimada de cada registro pode ter no máximo 30 segundos. Um registro mais longo falha no arquivo de resultados com Input files exceed 30s duration, which is not supported in batch mode, enquanto o restante do batch é executado.
  • Cada registro é cobrado como a geração que ele executa.

Em uma solicitação multipart, envie exatamente um arquivo JSONL no campo input (file também funciona). Outros campos de arquivo ou vários arquivos retornam 400. Um erro 503 upload_capacity_unavailable não cria nenhum batch. Repita a mesma solicitação após o tempo indicado em Retry-After ou envie um corpo JSON com rows.

Quando usar batch, e quando não usar

Um batch é um pipeline com fila. Todos os registros são baixados e verificados antes que qualquer um comece, e os resultados podem levar horas, com um prazo alvo de até 24 horas. Use-o para grandes volumes de clipes curtos que não precisam terminar imediatamente.

Ele não é a forma de enviar algumas gerações ao mesmo tempo. Para isso:

Limites de simultaneidade em batch

Quando você já executa tantos batches quanto o limite de simultaneidade do seu plano, a API retorna 429 Too Many Requests com errorCode: concurrency_limit_reached:

{
"statusCode": 429,
"error": "Too Many Requests",
"errorCode": "concurrency_limit_reached",
"message": "Batch concurrency limit reached. You have 3 active batches and your plan allows 3. Please wait for existing batches to complete or upgrade your plan for higher limits.",
"activeBatches": 3,
"concurrencyLimit": 3,
"retryAfterSeconds": 20
}

A resposta inclui um cabeçalho Retry-After (em segundos) e um cabeçalho X-Sync-Concurrency-Limit. Em vez de tentar novamente de imediato, aguarde retryAfterSeconds ou até que um dos seus batches ativos termine.

Como faço para criar um trabalho batch?

1

Prepare seu arquivo de entrada

Crie um arquivo JSON Lines (.jsonl) com suas solicitações de geração. Cada linha deve conter um request_id exclusivo, o endpoint (deve ser "/v2/generate") e um payload com o formato de solicitação de geração padrão (igual a Gerar API). O arquivo deve estar no formato JSON Lines (.jsonl) com tamanho máx de arquivo de 5 MB e comportar de 20 a 500 registros por padrão.

input.jsonl
{"request_id": "request-1", "endpoint": "/v2/generate", "payload": {"model": "lipsync-2", "input": [{"type": "video", "url": "https://assets.sync.so/docs/example-video.mp4"}, {"type": "audio", "url": "https://assets.sync.so/docs/example-audio.wav"}]}}
{"request_id": "request-2", "endpoint": "/v2/generate", "payload": {"model": "lipsync-2", "input": [{"type": "video", "url": "https://assets.sync.so/docs/example-video.mp4"}, {"type": "audio", "url": "https://assets.sync.so/docs/example-audio.wav"}]}}
2

Crie um batch

<CodeGroup> <CodeBlock>```python from sync import Sync

sync = Sync()

batch = sync.batch.create( input=open(“input.jsonl”, “rb”) )

print(f”Batch created with ID: {batch.id}”)

<CodeBlock>```typescript
import * as fs from "node:fs";
import { SyncClient } from "@sync.so/sdk";
const client = new SyncClient();
const batch = await client.batch.create(fs.createReadStream("input.jsonl"));
console.log('Batch created with ID:', batch.id)
```</CodeBlock>
<CodeBlock>```bash curl
curl -X POST https://api.sync.so/v2/batch \
-H "x-api-key: <your-api-key>" \
-H "Content-Type: multipart/form-data" \
-F "input=@input.jsonl"
```</CodeBlock>
<CodeBlock>
```bash curl (JSON rows)
curl -X POST https://api.sync.so/v2/batch \
-H "x-api-key: <your-api-key>" \
-H "Content-Type: application/json" \
-d '{
"rows": [
{"request_id": "request-1", "endpoint": "/v2/generate", "payload": {"model": "lipsync-2", "input": [{"type": "video", "url": "https://assets.sync.so/docs/example-video.mp4"}, {"type": "audio", "url": "https://assets.sync.so/docs/example-audio.wav"}]}},
{"request_id": "request-2", "endpoint": "/v2/generate", "payload": {"model": "lipsync-2", "input": [{"type": "video", "url": "https://assets.sync.so/docs/example-video.mp4"}, {"type": "audio", "url": "https://assets.sync.so/docs/example-audio.wav"}]}}
],
"dry_run": true
}'
```</CodeBlock>
</CodeGroup>
Em vez de fazer upload de um arquivo, você pode enviar `application/json` com os registros em `rows`. Cada linha é o mesmo objeto que uma linha do JSONL, e as duas formas são validadas da mesma maneira: os limites de registros acima, 5 MB ou menos quando escritas como JSONL e valores de `request_id` exclusivos. Quando um registro é recusado, o erro indica sua linha. As recusas de edição de diálogo a retornam no campo `lineNumber`; outros erros de registro, como JSON inválido ou `request_id` ausente, a indicam apenas em `message` (por exemplo `Record at line 4: payload is required`). As linhas contam registros não vazios, não linhas físicas, então linhas em branco em um arquivo JSONL são ignoradas; com um corpo JSON, a linha N é `rows[N-1]`. Os exemplos acima mostram dois registros para simplificar; um batch precisa de pelo menos 20.
**Parâmetros opcionais:** - `webhook_url`: Receba notificações quando o batch for concluído - `dry_run`: Defina como `true` para validar sua entrada sem processamento. Uma entrada válida retorna `{"status": "VALIDATED"}` e não cria nenhum batch.
A criação de batch não é coberta pelas [solicitações idempotentes](/api-reference/guides/idempotency). Se uma solicitação de criação atingir o tempo limite, liste seus batches com `GET /v2/batch` antes de enviar novamente, para não executar as mesmas linhas duas vezes.
</Step>
<Step title="Verifique o status do batch">
Monitore o progresso do seu batch pesquisando o status:
<CodeGroup>
<CodeBlock>```python Check batch status
batch = sync.batch.get(batch_id)
print(f"Status: {batch.status}")
print(f"Progress: {batch.metrics}")
```</CodeBlock>
<CodeBlock>```typescript
const batch = await client.batch.get(batch_id);
console.log('Status:', batch.status);
console.log('Progress:', batch.metrics);
```</CodeBlock>
<CodeBlock>```bash
curl "https://api.sync.so/v2/batch/<batch_id>" \
-H "x-api-key: <your-api-key>"
```</CodeBlock>
</CodeGroup>
Um batch pode ter um dos seguintes status:
1. **`PENDING`**: Batch criado, aguardando início do processamento
2. **`PROCESSING`**: Gerações estão sendo processadas
3. **`COMPLETED`**: Todas as gerações finalizadas (com sucesso ou com falhas)
4. **`FAILED`**: O processamento em batch falhou totalmente
</Step>
<Step title="Verifique os resultados do batch">
Quando um batch é concluído, os resultados ficam disponíveis como um arquivo de linhas JSON no `outputUrl` da resposta de obtenção do batch. Um `GET` para esse URL retorna um redirecionamento `302` para um arquivo de resultado assinado; os clientes que seguem redirecionamentos automaticamente podem ler a resposta JSONL diretamente. Cada linha contém:
```jsonl output.jsonl
{"request_id": "request-1", "endpoint": "/v2/generate", "payload": {...}, "status": "COMPLETED", "error": null, "response": {...}, "updated_at": "2024-01-15T10:35:00Z"}
{"request_id": "request-2", "endpoint": "/v2/generate", "payload": {...}, "status": "FAILED", "error": {"code": "INVALID_INPUT", "message": "..."}, "response": null, "updated_at": "2024-01-15T10:35:00Z"}

O campo response contém os mesmos dados que respostas individuais Gerar API. Os nomes de campos no arquivo de resultados estão em snake_case, portanto o video de uma linha concluída fica em response.output_url e o ID da geração em response.id. Associe cada linha à sua entrada pelo request_id.

Para obter um exemplo funcional completo, consulte o exemplo de processamento batch em nosso repositório de exemplos.

Notificações de webhook

Ao fornecer um webhook_url, você receberá uma notificação POST quando seu batch for concluído ou falhar. Ela é assinada com um cabeçalho Sync-Signature como os webhooks de geração e segue a mesma política de novas tentativas: até 6 tentativas ao longo de cerca de 2 horas, com o mesmo cabeçalho Sync-Delivery-Id em todas.

Diferente da resposta de Get Batch, o payload do webhook usa nomes de campo em camelCase:

webhook_payload.json
{
"id": "batch_abc123",
"createdAt": "2024-01-15T10:30:00Z",
"status": "COMPLETED",
"webhookUrl": "https://your-webhook-url.com/batch-webhook",
"metrics": {
"totalGenerations": 5,
"successCount": 4,
"failedCount": 1,
"pendingCount": 0
},
"options": {},
"outputUrl": "https://api.sync.so/v2/batches/batch_abc123/result"
}

O webhook de conclusão pode ser entregue mais de uma vez para o mesmo batch. Use o cabeçalho Sync-Delivery-Id ou o id do batch para ignorar notificações que você já processou.

Linhas de edição de diálogo (acesso antecipado)

Uma linha de batch pode renderizar uma prévia de edição de diálogo concluída, em vez de combinar um video com um novo áudio. Use isso para transformar um video gravado em muitas variantes, como uma por nome de destinatário. Mensagens de vídeo personalizadas tem um script completo.

As linhas de edição de diálogo estão em acesso antecipado e são habilitadas por organização. Entre em contato para ativá-las. Até lá, as linhas que contêm dialogueEdit são recusadas no envio.

O payload de cada linha contém:

  • model, por exemplo sync-3.
  • input com exatamente um video: o mesmo video de origem a partir do qual a prévia foi feita.
  • dialogueEdit: {"id": "..."}: o ID de uma prévia concluída de POST /v2/dialogue-edits na sua organização.

Não adicione entradas de áudio ou texto, segments ou dubParams; a prévia fornece o áudio.

{
"rows": [
{
"request_id": "line-2",
"endpoint": "/v2/generate",
"payload": {
"model": "sync-3",
"input": [{"type": "video", "url": "https://assets.sync.so/docs/example-video.mp4"}],
"dialogueEdit": {"id": "7644754c-bdfc-4d51-a78f-e0cb0cbbd40f"}
}
}
],
"dry_run": true
}

Os mesmos objetos de linha funcionam como linhas em um upload de arquivo JSONL.

No envio, cada linha de edição de diálogo é expandida exatamente na solicitação que POST /v2/generate monta para essa prévia, e é cobrada da mesma forma que essa geração. O payload no arquivo de resultados mostra a solicitação expandida (o video, o áudio da prévia e os segmentos editados), não a linha que você enviou. Envie primeiro o batch com dry_run: true: ele executa todas as verificações abaixo, incluindo a expansão, sem renderizar nada.

  • Todas as linhas de edição de diálogo em um batch devem usar prévias feitas a partir do mesmo video de origem. Para vários videos, envie um batch por video.
  • Os limites usuais de batch se aplicam: de 20 a 500 registros por padrão e 5 MB. A expansão adiciona o áudio da prévia e os segmentos editados a cada linha. O limite de 5 MB também se aplica ao batch expandido. Um batch com menos de 5 MB no envio pode ser recusado com um erro de tamanho de arquivo e status 400. Uma execução de teste também informa esse erro. Se isso acontecer, divida as linhas em batches menores.
  • A maioria das prévias é renderizada como segmentos editados do video. Uma prévia que só pode ser renderizada como lip sync do video inteiro é aceita em um batch apenas quando essa renderização tem 30 segundos ou menos; renderize as mais longas com POST /v2/generate.

Se alguma linha de edição de diálogo não puder ser renderizada, a solicitação inteira é recusada e nenhum batch é criado. A resposta traz o errorCode que POST /v2/generate retornaria para essa prévia, além do lineNumber da primeira linha com falha:

{
"statusCode": 422,
"errorCode": "dialogue_edit_not_found",
"lineNumber": 3,
"message": "Record at line 3: The dialogue edit was not found in this organization."
}
errorCodeStatusCausaCorreção
dialogue_edit_not_found422O ID é desconhecido ou pertence a outra organização.Use uma prévia criada pela sua organização.
dialogue_edit_not_completed422A prévia ainda está PENDING ou PROCESSING, ou está FAILED.Enquanto ela estiver pendente ou em processamento, consulte GET /v2/dialogue-edits/{id} periodicamente até que seja concluída e depois envie. Uma prévia FAILED é definitiva: crie uma nova.
dialogue_edit_source_mismatch422O video da linha não é o video a partir do qual a prévia foi feita.Envie o video de origem original da prévia.
dialogue_edit_retime_required422A prévia não tem o ajuste de tempo (retiming) necessário para ser renderizada (segmentLipsyncEnabled ou sectionExpansionEnabled está como false nela).Crie uma nova prévia. Se ela ainda informar false, entre em contato conosco.
dialogue_edit_removal_too_large422A edição remove mais fala do que as imagens ao redor conseguem absorver.Restaure algumas palavras e crie uma nova prévia.
dialogue_edit_audio_conflict422A linha também tem uma entrada de áudio ou texto, segments ou dubParams.Envie apenas a entrada de video e dialogueEdit.
dialogue_edit_unsupported422O API não consegue renderizar esta prévia, incluindo uma renderização do video inteiro com mais de 30 segundos.Crie uma nova prévia do video inteiro com uma chave de API ou renderize esta com POST /v2/generate.
dialogue_edit_batch_mixed_sources422As prévias do batch vêm de videos de origem diferentes.Envie um batch por video de origem.
generation_input_validation_failed400dialogueEdit não é um objeto com um id UUID, ou input não contém exatamente um video.Corrija o formato da linha.

Apenas a primeira linha com falha é informada. Corrija-a e repita o dry run até que ele retorne {"status": "VALIDATED"}.

Recursos relacionados - Limites de taxa - entenda API rate limiting para planejar seus tamanhos batch de maneira eficaz - Guia de Webhooks - configure notificações webhook para eventos de conclusão batch - Tratamento de erros - referência para códigos de erro específicos do batch e solução de problemas