Ricevere messaggi WhatsApp
I messaggi in entrata finiscono sulla stessa risorsa di quelli in uscita, senza un endpoint inbox separato da interrogare. Leggili con la lista messaggi nella dashboard, oppure tramite la API con GET /v1/whatsapp/messages/{id} dopo aver filtrato la lista per i messaggi in entrata.
Ogni messaggio in entrata estende la finestra di assistenza clienti a 24 ore dopo il timestamp di quel messaggio, ed è ciò che rende recapitabile una risposta libera da parte tua. Un messaggio che raggiunge Bird in ritardo porta quindi la finestra effettivamente concessa dal contatto, e una scadenza successiva già registrata non viene mai accorciata.
Cosa contiene un messaggio in entrata
Ogni messaggio in entrata condivide un unico envelope: un id, direction: "inbound", il contatto in from, il tuo numero in to, un status di received e un created_at. Accanto a esso è presente esattamente un campo di contenuto, che indica cosa ha inviato il contatto:
Esempio di codice
{
"id": "wam_01kya19eknftrs2s6p82asmvnh",
"direction": "inbound",
"from": { "phone_number": "+14155550100" },
"to": { "phone_number": "+13124495569" },
"status": "received",
"text": { "body": "Is my order out for delivery yet?" },
"created_at": "2026-08-25T09:04:11Z"
}from identifica il contatto in base all'identità che WhatsApp riporta: un phone_number E.164, un bsuid, o entrambi, più username e display_name che il contatto pubblica. Un contatto che ha adottato un username WhatsApp può raggiungerti senza alcun numero di telefono; vedi ID utente con ambito business per sapere cosa memorizzare e come richiedere un numero.
Uno di questi campi di contenuto, un arm, porta ciò che il contatto ha inviato, e su ogni messaggio è impostato esattamente un arm. Ciascuno ha la propria pagina, con la struttura di lettura, il payload whatsapp.received e gli aspetti a cui prestare attenzione:
| Campo | Cosa contiene in entrata |
|---|---|
| text | body, il messaggio digitato dal contatto |
| image | Un id, url, mime_type e qualsiasi caption |
| video | Gli stessi campi media, più qualsiasi caption |
| audio | Gli stessi campi media, più voice su un messaggio vocale; non esiste caption |
| sticker | Gli stessi campi media, più animated |
| document | Gli stessi campi media, più qualsiasi filename e caption |
| location | latitude e longitude, e talvolta name, address o un url |
| contact_cards | Una o più schede contatto condivise dal contatto |
| interactive_reply | Il slug e il text del pulsante o della riga toccata dal contatto |
| unsupported | Il content type WhatsApp che API non modella, come un ordine |
Due tap arrivano su un arm inatteso. Una richiesta di posizione risponde come un normale location in entrata, e una richiesta di informazioni contatto risponde come contact_cards, quindi un'integrazione che controlla solo interactive_reply per un tap le perde entrambe.
Scaricare i media in entrata
Un image, video, audio, sticker o document in entrata arriva come riferimento a un file che Bird ha memorizzato, non come il file stesso:
Esempio di codice
{
"image": {
"id": "waf_01kyb2m4xq7whs0d8n3prv6tez",
"url": "https://platform.bird.com/v1/whatsapp/messages/wam_01kya19eknftrs2s6p82asmvnh/media/waf_01kyb2m4xq7whs0d8n3prv6tez",
"mime_type": "image/jpeg",
"caption": "Is this the right part?"
}
}Scarica i byte con il metodo media del canale, passando l'id del messaggio e il id del media:
const media = await bird.whatsapp.messages.media(
"wam_01kya19eknftrs2s6p82asmvnh",
"waf_01kyb2m4xq7whs0d8n3prv6tez",
);
console.log(media.contentType, media.contentLength);media = client.whatsapp.messages.media(
"wam_01kya19eknftrs2s6p82asmvnh", "waf_01kyb2m4xq7whs0d8n3prv6tez"
)
print(media.content_type, media.content_length)media, err := client.Whatsapp.Messages.Media(context.Background(),
"wam_01kya19eknftrs2s6p82asmvnh", "waf_01kyb2m4xq7whs0d8n3prv6tez")
if err != nil {
log.Fatal(err)
}
fmt.Println(media.ContentType, media.ContentLength)$media = $bird->whatsapp->messages->media('wam_01kya19eknftrs2s6p82asmvnh', 'waf_01kyb2m4xq7whs0d8n3prv6tez');
file_put_contents('photo.jpg', $media->data);
echo $media->contentType, ' ', $media->contentLength;bird whatsapp media <message-id> <media-id>curl -L -X GET "https://{region}.platform.bird.com/v1/whatsapp/messages/{message_id}/media/{media_id}" \
-H "Authorization: Bearer $TOKEN"Ricevi i byte con il mime_type di archiviazione dichiarato per essi. Un id che Bird non riconosce restituisce 404, e un messaggio in uscita non ha media memorizzati da servire.
Un messaggio è leggibile per 30 giorni dal suo arrivo, e i suoi media non sopravvivono oltre. Questo endpoint legge il messaggio prima di servire il file, quindi una volta scaduta la finestra entrambi rispondono 404. Memorizza qualsiasi file ti serva più a lungo finché il messaggio è ancora leggibile. L'unico caso in cui la scadenza arriva prima è quando i byte memorizzati vengono rimossi prima della fine della finestra: il fetch risponde 410 E15021, e il messaggio è ancora leggibile con mime_type e caption del media.
Internamente questo endpoint risponde 302 con un URL prefirmato valido per 15 minuti. Gli SDK e la CLI gestiscono quel passaggio per te. Chiamandolo direttamente, l'URL prefirmato porta la propria credenziale, quindi la richiesta reindirizzata non deve inviare anche il tuo header Authorization. Inviarli entrambi causa un errore. curl -L rimuove l'header su un redirect cross-host automaticamente; un client che inoltra gli header alla lettera deve scaricare il Location come richiesta separata e non autenticata.
Risposte con citazione
in_reply_to_message_id indica il messaggio a cui uno in entrata risponde, quando WhatsApp lo contrassegna come risposta:
Esempio di codice
{
"id": "wam_01kyb2m4xq7whs0d8n3prv6tez",
"direction": "inbound",
"in_reply_to_message_id": "wam_01kya19eknftrs2s6p82asmvnh",
"text": { "body": "Yes, that one" }
}WhatsApp non contrassegna ogni risposta, e una risposta non contrassegnata non porta alcun ID. Il campo viene anche omesso quando il messaggio citato non può essere associato a uno che Bird conserva: un messaggio inviato prima che questo spazio di lavoro iniziasse a registrarli, o uno oltre i 15 giorni in cui Bird conserva i message id di WhatsApp. Un mancato abbinamento omette il campo anziché riportarne uno, il che si legge come una risposta che non risponde a nulla.
Tratta il campo come un suggerimento, non come una chiave. metadata sul tuo invio non è utile qui, perché resta sul tuo messaggio e non viene mai trasferito alla risposta del contatto, quindi un'integrazione che deve sapere a quale domanda appartiene una risposta tiene traccia da sola dell'ultima domanda posta a quel contatto. Vedi Citare un messaggio per il lato in uscita.
Il webhook
Iscriviti a whatsapp.received per agire su un messaggio in entrata appena arriva, anziché interrogare la lista. Il payload porta il contenuto sopra l'envelope dell'evento, quindi un endpoint non ha bisogno di una lettura successiva:
Esempio di codice
{
"type": "whatsapp.received",
"timestamp": "2026-08-25T09:04:11.118Z",
"data": {
"whatsapp_id": "wam_01kyb2m4xq7whs0d8n3prv6tez",
"workspace_id": "ws_01ky7m235keycbnwyajabe1a6b",
"direction": "inbound",
"from": { "phone_number": "+14155550100", "display_name": "Alex Rivera" },
"to": { "phone_number": "+13124495569" },
"in_reply_to_message_id": "wam_01kya19eknftrs2s6p82asmvnh",
"interactive_reply": {
"type": "button",
"button": { "slug": "cancel-booking", "text": "Cancel" }
},
"tags": null,
"metadata": null
}
}Vedi eventi WhatsApp per l'envelope completo e il resto della lista eventi.
Prossimi passi
- Messaggi di servizio: il lato invio degli stessi arm di contenuto
- Inviare messaggi WhatsApp: rispondere all'interno della finestra di servizio e citare un messaggio
- Eventi WhatsApp: la lista completa degli eventi, tramite la API o i webhook
- Log WhatsApp: sfogliare la conversazione nella dashboard
Risorse correlate
Prosegui con la documentazione, le guide e gli esempi per questo argomento. Le risorse sono in inglese.
Guarda la guidaConnecting WhatsApp to Bird: from buying a number to a live channelComprendi il concettoWhat is the 24-hour customer service window on WhatsApp?Usa lo strumentoWhatsApp message builderEsplora la funzionalitàWhatsApp
Prova l'esercitazione e ottieni un brief di implementazione