Como enviar texto para um número?

Para texto, envie number ou chatid junto com text. Os dois destinos são strings; ao informar ambos, chatid prevalece. O telefone pode conter pontuação, que é removida antes da validação, e precisa resultar em 8 a 15 dígitos. Inclua os prefixos internacionais e de área, sem presumir que a API complete partes ausentes.

A instância é localizada pelo token permanente. A autenticação pode seguir no header token ou como Authorization: Bearer SEU_TOKEN. Os snippets abaixo usam a mesma URL fictícia e o mesmo corpo, para facilitar a comparação entre bibliotecas.

Rota O que faz
POST /send/text Envia texto a um número ou JID de conversa.
POST /send/media Envia imagem, vídeo, áudio, sticker ou documento conforme type.
POST /send/image Envia imagem com o mesmo corpo de mídia, fixando o tipo como imagem.

Corpo comum aos quatro exemplos:

{"number":"5511999999999","text":"Sua mensagem de teste"}

curl

curl -X POST 'https://SEU-DOMINIO/send/text' \
  -H 'Content-Type: application/json' \
  -H 'token: SEU_TOKEN' \
  --data '{"number":"5511999999999","text":"Sua mensagem de teste"}'

Node.js com fetch

const response = await fetch('https://SEU-DOMINIO/send/text', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    token: 'SEU_TOKEN',
  },
  body: JSON.stringify({
    number: '5511999999999',
    text: 'Sua mensagem de teste',
  }),
});

console.log(response.status, await response.json());

Python com requests

import requests

response = requests.post(
    'https://SEU-DOMINIO/send/text',
    headers={'token': 'SEU_TOKEN'},
    json={'number': '5511999999999', 'text': 'Sua mensagem de teste'},
)
print(response.status_code, response.json())

PHP com cURL

<?php
$ch = curl_init('https://SEU-DOMINIO/send/text');
curl_setopt_array($ch, [
    CURLOPT_POST => true,
    CURLOPT_HTTPHEADER => ['Content-Type: application/json', 'token: SEU_TOKEN'],
    CURLOPT_POSTFIELDS => json_encode([
        'number' => '5511999999999',
        'text' => 'Sua mensagem de teste',
    ]),
    CURLOPT_RETURNTRANSFER => true,
]);
$body = curl_exec($ch);
echo curl_getinfo($ch, CURLINFO_HTTP_CODE) . ' ' . $body;
curl_close($ch);

Troque domínio, token e destino pelos valores da sua instância. O exemplo é para integração e não representa uma mensagem entregue ou lida por uma pessoa.

Na escolha do destino, number é prático quando seu sistema guarda o telefone do contato. Use chatid quando já possui o identificador de conversa aceito pelo serviço. A API permite os dois campos, mas a precedência do chatid torna mais claro enviar apenas aquele que corresponde à conversa desejada. Revise também a normalização de telefone antes de montar lotes: espaços, parênteses e sinais não substituem o código internacional.

Antes de colocar uma rotina em produção, registre qual instância fez a chamada, o horário, o status HTTP e o identificador retornado. Evite registrar o token nos logs. Isso ajuda a distinguir erro de autenticação, indisponibilidade da sessão e falha de validação do corpo sem armazenar credenciais junto com o histórico da aplicação.

Como enviar imagem ou documento?

Mídia usa POST /send/media. O corpo requer um destino e url ou base64; também pode indicar type, mimetype, caption e, para arquivo, fileName. Para um documento hospedado em uma URL:

curl -X POST 'https://SEU-DOMINIO/send/media' \
  -H 'Content-Type: application/json' \
  -H 'Authorization: Bearer SEU_TOKEN' \
  --data '{"number":"5511999999999","type":"document","url":"https://exemplo.invalid/arquivo.pdf","mimetype":"application/pdf","fileName":"guia.pdf","caption":"Guia solicitado"}'

O domínio exemplo.invalid é ilustrativo e precisa ser substituído por uma URL que a API consiga acessar. Para imagem, use o tipo image e uma URL ou conteúdo Base64. A rota /send/image também recebe os campos de mídia e força o tipo imagem. Não há uma rota dedicada /send/document: o tipo documento pertence a /send/media.

Os tipos aceitos incluem imagem, vídeo, áudio, áudio enviado como PTT/voz, documento e sticker. Para arquivos, forneça um tipo reconhecido e dados de mídia utilizáveis, além do destino. caption pode acompanhar a mídia; fileName serve para informar o nome do arquivo. As flags opcionais de mídia são booleanas, enquanto os demais campos listados no contrato são strings. A documentação não define um limite máximo de bytes para URL ou Base64 nesse fluxo, então não trate um tamanho escolhido pela aplicação como limite oficial da API.

Quando usar a fila assíncrona?

O fluxo padrão processa o envio de forma síncrona. Para os envios compatíveis com fila, async: true no JSON pede processamento assíncrono. O exemplo mantém destino e texto do corpo anterior:

curl -X POST 'https://SEU-DOMINIO/send/text' \
  -H 'Content-Type: application/json' \
  -H 'token: SEU_TOKEN' \
  --data '{"number":"5511999999999","text":"Sua mensagem de teste","async":true}'

Uma resposta aceita na fila usa HTTP 202 e inclui campos como success, async, queued, job e endpoint. A consulta de estado usa GET /message/async; para limpar a fila, há DELETE /message/async. As duas rotas também exigem autenticação.

Rota O que faz
GET /message/async Consulta o estado da fila assíncrona.
DELETE /message/async Limpa a fila assíncrona da instância.

O processamento na fila informa que a API aceitou o trabalho, sem confirmar entrega ao destinatário. A API não aplica rate limit HTTP às rotas /send/*; a sessão e as regras do WhatsApp ainda têm limites.

Considere guardar o campo job da resposta aceita e consultar o estado da fila de acordo com a estratégia da sua aplicação. O endpoint de leitura informa dados da fila, sem confirmar que uma mensagem será entregue. Limpar a fila é uma ação diferente de consultar seu conteúdo; aplique DELETE apenas quando a intenção operacional for remover os trabalhos pendentes daquela instância.

O que significam as respostas HTTP?

No envio síncrono, HTTP 200 representa a resposta de sucesso da operação da API. HTTP 202 indica que o trabalho foi aceito para a fila. HTTP 429 é usado quando a fila está cheia. HTTP 409 indica que o serviço ou a sessão está indisponível ou reiniciando. Trate o corpo e o status como resultado da requisição, sem convertê-los em prova de leitura ou entrega.

Na prática, diferencie os casos antes de repetir a chamada. Uma resposta 429 aponta fila cheia; aumentar tentativas sem verificar o estado pode manter o cliente pressionando uma fila sem espaço. Já 409 indica indisponibilidade ou reinício, por isso a aplicação pode tratar a condição separadamente e tentar de novo após observar a disponibilidade. O HTTP 202 também tem tratamento próprio: guarde os dados do trabalho e consulte o endpoint da fila, em vez de considerar a operação síncrona concluída.

Para acompanhar etapas da integração, registre o status HTTP e o identificador de trabalho recebido na resposta da fila. Se você também precisa consumir eventos de execução, veja o guia de webhooks e SSE da GoZAP. Para outros recursos de envio, leia grupos, comunidades, canais e status e tipos de mensagem WhatsApp API.

Quando não escolher a GoZAP

Não escolha a GoZAP se a sua política exige exclusivamente a API oficial da Meta, ou se o sistema precisa operar sem um serviço hospedado. Confirme também se a sua aplicação aceita trabalhar com o ciclo e os limites de uma sessão WhatsApp. A GoZAP conecta por Web e Mobile, dois modos nativos fora da API oficial da Meta. Veja o modo Mobile.