{"openapi":"3.1.0","info":{"title":"Messaging Me API","version":"1","description":"The public API of Messaging Me: contacts, sends, conversations, templates and outgoing webhooks. Errors are { error, code }; code is absent only on generic failures."},"servers":[{"url":"https://api.messagingme.app"}],"security":[{"bearer":[]}],"tags":[{"name":"Conversations"},{"name":"Contacts"},{"name":"Messages"},{"name":"Sends"},{"name":"Templates"},{"name":"Outgoing webhooks"},{"name":"Catalogs"}],"paths":{"/v1/conversations":{"get":{"operationId":"listConversations","summary":"Lists conversations, most recent first, page by page.","tags":["Conversations"],"security":[{"bearer":[]}],"x-required-scope":"conversations:read","description":"Requires the conversations:read scope.","parameters":[{"name":"limit","in":"query","required":false,"schema":{"default":50,"description":"Page size.","type":"integer","minimum":1,"maximum":100}},{"name":"cursor","in":"query","required":false,"schema":{"type":"string","maxLength":200,"description":"The nextCursor of the previous page, as is."}},{"name":"needsReply","in":"query","required":false,"schema":{"type":"boolean","description":"Only the conversations waiting for your reply."}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"contact":{"type":"object","properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}]},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"externalId":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["id","phone","name","externalId"]},"lastMessageAt":{"type":"string","description":"ISO 8601 date-time"},"lastDirection":{"anyOf":[{"type":"string","enum":["in","out"]},{"type":"null"}]},"windowExpiresAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"handledBy":{"type":"string","enum":["team","meta_agent","automation"]},"needsReply":{"type":"boolean"},"archived":{"type":"boolean"}},"required":["id","contact","lastMessageAt","lastDirection","windowExpiresAt","handledBy","needsReply","archived"]}},"nextCursor":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["data","nextCursor"]}}}},"400":{"description":"Error: invalid_body, invalid_cursor.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/conversations/{conversationId}":{"get":{"operationId":"getConversation","summary":"Reads a conversation: the contact, who handles it, the 24-hour window.","tags":["Conversations"],"security":[{"bearer":[]}],"x-required-scope":"conversations:read","description":"Requires the conversations:read scope.","parameters":[{"name":"conversationId","in":"path","required":true,"schema":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string"},"contact":{"type":"object","properties":{"id":{"anyOf":[{"type":"string"},{"type":"null"}]},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"externalId":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["id","phone","name","externalId"]},"lastMessageAt":{"type":"string","description":"ISO 8601 date-time"},"lastDirection":{"anyOf":[{"type":"string","enum":["in","out"]},{"type":"null"}]},"windowExpiresAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"handledBy":{"type":"string","enum":["team","meta_agent","automation"]},"needsReply":{"type":"boolean"},"archived":{"type":"boolean"}},"required":["id","contact","lastMessageAt","lastDirection","windowExpiresAt","handledBy","needsReply","archived"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: conversation_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/conversations/{conversationId}/messages":{"get":{"operationId":"listConversationMessages","summary":"A conversation’s messages, most recent first, page by page.","tags":["Conversations"],"security":[{"bearer":[]}],"x-required-scope":"conversations:read","description":"Requires the conversations:read scope.","parameters":[{"name":"conversationId","in":"path","required":true,"schema":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"}},{"name":"limit","in":"query","required":false,"schema":{"default":50,"description":"Page size.","type":"integer","minimum":1,"maximum":100}},{"name":"cursor","in":"query","required":false,"schema":{"type":"string","maxLength":200,"description":"The nextCursor of the previous page, as is."}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"conversationId":{"type":"string"},"direction":{"type":"string","enum":["in","out"]},"channel":{"type":"string","enum":["whatsapp","rcs"]},"type":{"anyOf":[{"type":"string"},{"type":"null"}]},"text":{"anyOf":[{"type":"string"},{"type":"null"}]},"buttonPayload":{"anyOf":[{"type":"string"},{"type":"null"}]},"transcription":{"anyOf":[{"type":"string"},{"type":"null"}]},"media":{"anyOf":[{"type":"object","properties":{"mimeType":{"anyOf":[{"type":"string"},{"type":"null"}]},"filename":{"anyOf":[{"type":"string"},{"type":"null"}]},"expired":{"type":"boolean"}},"required":["mimeType","filename","expired"]},{"type":"null"}]},"status":{"anyOf":[{"type":"string","enum":["sent","delivered","read","failed"]},{"type":"null"}]},"statusAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"error":{"anyOf":[{"type":"object","properties":{"code":{"anyOf":[{"type":"number"},{"type":"null"}]},"reason":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["code","reason"]},{"type":"null"}]},"createdAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["id","conversationId","direction","channel","type","text","buttonPayload","transcription","media","status","statusAt","error","createdAt"]}},"nextCursor":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["data","nextCursor"]}}}},"400":{"description":"Error: invalid_body, invalid_cursor.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: conversation_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/messages/{messageId}":{"get":{"operationId":"getMessage","summary":"Reads a message by its ID.","tags":["Conversations"],"security":[{"bearer":[]}],"x-required-scope":"conversations:read","description":"Requires the conversations:read scope.","parameters":[{"name":"messageId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string"},"conversationId":{"type":"string"},"direction":{"type":"string","enum":["in","out"]},"channel":{"type":"string","enum":["whatsapp","rcs"]},"type":{"anyOf":[{"type":"string"},{"type":"null"}]},"text":{"anyOf":[{"type":"string"},{"type":"null"}]},"buttonPayload":{"anyOf":[{"type":"string"},{"type":"null"}]},"transcription":{"anyOf":[{"type":"string"},{"type":"null"}]},"media":{"anyOf":[{"type":"object","properties":{"mimeType":{"anyOf":[{"type":"string"},{"type":"null"}]},"filename":{"anyOf":[{"type":"string"},{"type":"null"}]},"expired":{"type":"boolean"}},"required":["mimeType","filename","expired"]},{"type":"null"}]},"status":{"anyOf":[{"type":"string","enum":["sent","delivered","read","failed"]},{"type":"null"}]},"statusAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"error":{"anyOf":[{"type":"object","properties":{"code":{"anyOf":[{"type":"number"},{"type":"null"}]},"reason":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["code","reason"]},{"type":"null"}]},"createdAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["id","conversationId","direction","channel","type","text","buttonPayload","transcription","media","status","statusAt","error","createdAt"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: message_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/messages/{messageId}/media":{"get":{"operationId":"getMessageMedia","summary":"Downloads the file of a received message.","tags":["Conversations"],"security":[{"bearer":[]}],"x-required-scope":"conversations:read","description":"Requires the conversations:read scope.","parameters":[{"name":"messageId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"The file, served with its own content type (image, audio, video, document).","content":{"*/*":{}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: message_not_found, no_media.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"410":{"description":"Error: media_expired.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: media_unavailable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/contacts":{"post":{"operationId":"upsertContact","summary":"Creates or updates a record.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:write","description":"Requires the contacts:write scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"contactId":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$"},"externalId":{"type":"string","maxLength":512},"phone":{"type":"string","maxLength":64},"bsuid":{"type":"string","maxLength":200},"name":{"type":"string"},"fields":{"type":"object","propertyNames":{"type":"string","maxLength":64},"additionalProperties":{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"}]}},"tags":{"maxItems":20,"type":"array","items":{"anyOf":[{"type":"string"},{"type":"number"}]}},"consent":{"type":"string","enum":["opted_in","opted_out"]},"consentSource":{"type":"string","minLength":1,"maxLength":100},"optIn":{"not":{}},"optInSource":{"not":{}}}}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"contactId":{"type":"string"},"status":{"type":"string","enum":["created","updated"]}},"required":["contactId","status"]}}}},"400":{"description":"Error: invalid_body, invalid_recipient, invalid_phone.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"402":{"description":"Error: plan_limit_reached.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: identity_conflict, opted_out.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/contacts/batch":{"post":{"operationId":"upsertContacts","summary":"Creates or updates up to 50 records in one call.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:write","description":"Requires the contacts:write scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"contacts":{"minItems":1,"maxItems":50,"type":"array","items":{"type":"object","properties":{"contactId":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$"},"externalId":{"type":"string","maxLength":512},"phone":{"type":"string","maxLength":64},"bsuid":{"type":"string","maxLength":200},"name":{"type":"string"},"fields":{"type":"object","propertyNames":{"type":"string","maxLength":64},"additionalProperties":{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"}]}},"tags":{"maxItems":10,"type":"array","items":{"anyOf":[{"type":"string"},{"type":"number"}]}},"consent":{"type":"string","enum":["opted_in","opted_out"]},"consentSource":{"type":"string","minLength":1,"maxLength":100},"optIn":{"not":{}},"optInSource":{"not":{}}}}}},"required":["contacts"],"additionalProperties":false}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"results":{"type":"array","items":{"anyOf":[{"type":"object","properties":{"index":{"type":"number"},"status":{"type":"string","enum":["created","updated"]},"contactId":{"type":"string"}},"required":["index","status","contactId"]},{"type":"object","properties":{"index":{"type":"number"},"status":{"type":"string","const":"error"},"code":{"type":"string","enum":["invalid_body","invalid_recipient","invalid_phone","unauthorized","missing_scope","tenant_locked","unknown_contact","duplicate","identity_conflict","blocked_contact","opted_out","no_consent","window_closed","missing_variable","no_phone","rcs_unreachable","rcs_not_enabled","no_whatsapp_number","meta_rejected","invalid_header_media","template_rejected","meta_auth_failed","webhook_not_found","delivery_not_found","delivery_not_replayable","webhooks_unavailable","field_exists","number_unlinked","number_suspended","scenario_not_found","node_not_found","template_not_found","rcs_message_not_found","send_not_found","conversation_not_found","message_not_found","invalid_cursor","no_media","media_expired","media_unavailable","scenario_ambiguous","unsendable_target","template_category_unknown","idempotency_key_required","idempotency_in_progress","idempotency_key_reused","rate_limited","quota_exceeded","plan_feature_unavailable","plan_limit_reached","route_not_found","internal_error"]},"reason":{"type":"string"}},"required":["index","status","code","reason"]}]}},"created":{"type":"number"},"updated":{"type":"number"},"errors":{"type":"number"}},"required":["results","created","updated","errors"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/contacts/{contactId}":{"get":{"operationId":"getContact","summary":"Reads a record.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:read","description":"Requires the contacts:read scope.","parameters":[{"name":"contactId","in":"path","required":true,"schema":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"contactId":{"type":"string"},"externalId":{"anyOf":[{"type":"string"},{"type":"null"}]},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"bsuid":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"fields":{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},"tags":{"type":"array","items":{"type":"string"}},"consent":{"type":"object","properties":{"status":{"type":"string","enum":["opted_in","opted_out","unknown"]},"source":{"anyOf":[{"type":"string"},{"type":"null"}]},"optedOutAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]}},"required":["status","source","optedOutAt"]},"rcsOptedOutAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"blocked":{"type":"boolean"},"reachability":{"type":"object","properties":{"whatsapp":{"anyOf":[{"type":"boolean"},{"type":"null"}]},"rcs":{"anyOf":[{"type":"boolean"},{"type":"null"}]}},"required":["whatsapp","rcs"]},"engagementRisk":{"anyOf":[{"type":"object","properties":{"level":{"type":"string","enum":["inconnu","faible","moyen","eleve"]},"score":{"anyOf":[{"type":"number"},{"type":"null"}]},"reasons":{"type":"array","items":{"type":"string","enum":["stop","bloque","silence_60j","silence_30j","sans_reponse","non_lu","reclamation","negatif","insatisfait","injoignable"]}},"computedAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["level","score","reasons","computedAt"]},{"type":"null"}]},"lastAnalysis":{"anyOf":[{"type":"object","properties":{"intent":{"type":"string","enum":["demande_devis","sav","reclamation","information","prise_rdv","achat","suivi_commande","retour","autre"]},"sentiment":{"type":"string","enum":["positif","neutre","negatif"]},"satisfaction":{"anyOf":[{"type":"number"},{"type":"null"}]},"urgency":{"anyOf":[{"type":"number"},{"type":"null"}]},"resolved":{"type":"boolean"},"topic":{"type":"string"},"handledBy":{"type":"string","enum":["humain","automatise","mba"]},"actionSuggestion":{"type":"string","enum":["creer_devis","rappeler","relancer","escalader","aucune"]},"analyzedAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["intent","sentiment","satisfaction","urgency","resolved","topic","handledBy","actionSuggestion","analyzedAt"]},{"type":"null"}]},"createdAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["contactId","externalId","phone","bsuid","name","fields","tags","consent","rcsOptedOutAt","blocked","reachability","engagementRisk","lastAnalysis","createdAt"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"delete":{"operationId":"deleteContact","summary":"Erases a record for good (GDPR), within the plan’s daily limit.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:admin","description":"Requires the contacts:admin scope.","parameters":[{"name":"contactId","in":"path","required":true,"schema":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"deleted":{"type":"boolean","const":true},"conversations":{"type":"number"},"messages":{"type":"number"}},"required":["deleted","conversations","messages"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"402":{"description":"Error: plan_limit_reached.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"patch":{"operationId":"updateContact","summary":"Updates a record’s fields, tags, consent or external id.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:write","description":"Requires the contacts:write scope.","parameters":[{"name":"contactId","in":"path","required":true,"schema":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"fields":{"type":"object","propertyNames":{"type":"string","maxLength":64},"additionalProperties":{"anyOf":[{"anyOf":[{"type":"string"},{"type":"number"},{"type":"boolean"}]},{"type":"null"}]}},"addTags":{"maxItems":20,"type":"array","items":{"anyOf":[{"type":"string"},{"type":"number"}]}},"removeTags":{"maxItems":20,"type":"array","items":{"anyOf":[{"type":"string"},{"type":"number"}]}},"consent":{"type":"string","enum":["opted_in","opted_out"]},"consentSource":{"type":"string","minLength":1,"maxLength":100},"externalId":{"type":"string","maxLength":512},"phone":{"not":{}},"bsuid":{"not":{}}}}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"contactId":{"type":"string"}},"required":["contactId"]}}}},"400":{"description":"Error: invalid_body, invalid_phone.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: identity_conflict, opted_out.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/contacts/search":{"post":{"operationId":"searchContact","summary":"Finds a record by phone, BSUID or external id.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:read","description":"Requires the contacts:read scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"externalId":{"type":"string","maxLength":512},"phone":{"type":"string","maxLength":64},"bsuid":{"type":"string","maxLength":200}},"description":"Exactly one of phone, bsuid or externalId."}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"contact":{"anyOf":[{"type":"object","properties":{"contactId":{"type":"string"},"externalId":{"anyOf":[{"type":"string"},{"type":"null"}]},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"bsuid":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"fields":{"type":"object","propertyNames":{"type":"string"},"additionalProperties":{}},"tags":{"type":"array","items":{"type":"string"}},"consent":{"type":"object","properties":{"status":{"type":"string","enum":["opted_in","opted_out","unknown"]},"source":{"anyOf":[{"type":"string"},{"type":"null"}]},"optedOutAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]}},"required":["status","source","optedOutAt"]},"rcsOptedOutAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"blocked":{"type":"boolean"},"reachability":{"type":"object","properties":{"whatsapp":{"anyOf":[{"type":"boolean"},{"type":"null"}]},"rcs":{"anyOf":[{"type":"boolean"},{"type":"null"}]}},"required":["whatsapp","rcs"]},"engagementRisk":{"anyOf":[{"type":"object","properties":{"level":{"type":"string","enum":["inconnu","faible","moyen","eleve"]},"score":{"anyOf":[{"type":"number"},{"type":"null"}]},"reasons":{"type":"array","items":{"type":"string","enum":["stop","bloque","silence_60j","silence_30j","sans_reponse","non_lu","reclamation","negatif","insatisfait","injoignable"]}},"computedAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["level","score","reasons","computedAt"]},{"type":"null"}]},"lastAnalysis":{"anyOf":[{"type":"object","properties":{"intent":{"type":"string","enum":["demande_devis","sav","reclamation","information","prise_rdv","achat","suivi_commande","retour","autre"]},"sentiment":{"type":"string","enum":["positif","neutre","negatif"]},"satisfaction":{"anyOf":[{"type":"number"},{"type":"null"}]},"urgency":{"anyOf":[{"type":"number"},{"type":"null"}]},"resolved":{"type":"boolean"},"topic":{"type":"string"},"handledBy":{"type":"string","enum":["humain","automatise","mba"]},"actionSuggestion":{"type":"string","enum":["creer_devis","rappeler","relancer","escalader","aucune"]},"analyzedAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["intent","sentiment","satisfaction","urgency","resolved","topic","handledBy","actionSuggestion","analyzedAt"]},{"type":"null"}]},"createdAt":{"type":"string","description":"ISO 8601 date-time"}},"required":["contactId","externalId","phone","bsuid","name","fields","tags","consent","rcsOptedOutAt","blocked","reachability","engagementRisk","lastAnalysis","createdAt"]},{"type":"null"}]}},"required":["contact"]}}}},"400":{"description":"Error: invalid_body, invalid_phone.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/fields":{"get":{"operationId":"listFields","summary":"Lists the custom fields: the keys to use in fields.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:read","description":"Requires the contacts:read scope.","responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"key":{"type":"string"},"label":{"type":"string"},"type":{"type":"string"}},"required":["key","label","type"]}}},"required":["data"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"post":{"operationId":"createField","summary":"Creates a custom field; its key comes from the label.","tags":["Contacts"],"security":[{"bearer":[]}],"x-required-scope":"contacts:admin","description":"Requires the contacts:admin scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"label":{"type":"string","minLength":1,"maxLength":100},"type":{"type":"string","enum":["text","number","date","datetime","boolean","url"]}},"required":["label","type"],"additionalProperties":false}}}},"responses":{"201":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"key":{"type":"string"},"label":{"type":"string"},"type":{"type":"string"}},"required":["key","label","type"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: field_exists.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/messages":{"post":{"operationId":"sendMessage","summary":"Sends a message in Meta’s format: image, document, location, buttons, list, link button.","tags":["Messages"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"messaging_product":{"type":"string","const":"whatsapp"},"recipient_type":{"type":"string","const":"individual"},"to":{"type":"string","pattern":"^\\+?\\d{8,15}$"},"contactId":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$"},"externalId":{"type":"string","maxLength":512},"type":{"type":"string","enum":["text","image","video","audio","document","location","reaction","interactive"]},"text":{"type":"object","properties":{"body":{"type":"string","minLength":1,"maxLength":4096},"preview_url":{"type":"boolean"}},"required":["body"],"additionalProperties":false},"image":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"},"caption":{"type":"string","minLength":1,"maxLength":1024}},"required":["link"],"additionalProperties":false},"video":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"},"caption":{"type":"string","minLength":1,"maxLength":1024}},"required":["link"],"additionalProperties":false},"audio":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"},"voice":{"type":"boolean"}},"required":["link"],"additionalProperties":false},"document":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"},"caption":{"type":"string","minLength":1,"maxLength":1024},"filename":{"type":"string","minLength":1,"maxLength":240}},"required":["link"],"additionalProperties":false},"location":{"type":"object","properties":{"latitude":{"type":"number","minimum":-90,"maximum":90},"longitude":{"type":"number","minimum":-180,"maximum":180},"name":{"type":"string","minLength":1,"maxLength":1000},"address":{"type":"string","minLength":1,"maxLength":1000}},"additionalProperties":false,"required":["latitude","longitude"]},"reaction":{"type":"object","properties":{"message_id":{"type":"string","minLength":1,"maxLength":200},"emoji":{"type":"string","maxLength":16}},"required":["message_id","emoji"],"additionalProperties":false},"interactive":{"oneOf":[{"type":"object","properties":{"type":{"type":"string","const":"button"},"header":{"oneOf":[{"type":"object","properties":{"type":{"type":"string","const":"text"},"text":{"type":"string","minLength":1,"maxLength":60}},"required":["type","text"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"image"},"image":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"}},"required":["link"],"additionalProperties":false}},"required":["type","image"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"video"},"video":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"}},"required":["link"],"additionalProperties":false}},"required":["type","video"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"document"},"document":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"},"filename":{"type":"string","minLength":1,"maxLength":240}},"required":["link"],"additionalProperties":false}},"required":["type","document"],"additionalProperties":false}]},"body":{"type":"object","properties":{"text":{"type":"string","minLength":1,"maxLength":1024}},"required":["text"],"additionalProperties":false},"footer":{"type":"object","properties":{"text":{"type":"string","minLength":1,"maxLength":60}},"required":["text"],"additionalProperties":false},"action":{"type":"object","properties":{"buttons":{"minItems":1,"maxItems":3,"type":"array","items":{"type":"object","properties":{"type":{"type":"string","const":"reply"},"reply":{"type":"object","properties":{"id":{"type":"string","minLength":1,"maxLength":256},"title":{"type":"string","minLength":1,"maxLength":20}},"required":["id","title"],"additionalProperties":false}},"required":["type","reply"],"additionalProperties":false}}},"required":["buttons"],"additionalProperties":false}},"required":["type","body","action"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"list"},"header":{"type":"object","properties":{"type":{"type":"string","const":"text"},"text":{"type":"string","minLength":1,"maxLength":60}},"required":["type","text"],"additionalProperties":false},"body":{"type":"object","properties":{"text":{"type":"string","minLength":1,"maxLength":4096}},"required":["text"],"additionalProperties":false},"footer":{"type":"object","properties":{"text":{"type":"string","minLength":1,"maxLength":60}},"required":["text"],"additionalProperties":false},"action":{"type":"object","properties":{"button":{"type":"string","minLength":1,"maxLength":20},"sections":{"minItems":1,"maxItems":10,"type":"array","items":{"type":"object","properties":{"title":{"type":"string","minLength":1,"maxLength":24},"rows":{"minItems":1,"type":"array","items":{"type":"object","properties":{"id":{"type":"string","minLength":1,"maxLength":200},"title":{"type":"string","minLength":1,"maxLength":24},"description":{"type":"string","minLength":1,"maxLength":72}},"required":["id","title"],"additionalProperties":false}}},"required":["rows"],"additionalProperties":false}}},"required":["button","sections"],"additionalProperties":false}},"required":["type","body","action"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"cta_url"},"header":{"oneOf":[{"type":"object","properties":{"type":{"type":"string","const":"text"},"text":{"type":"string","minLength":1,"maxLength":60}},"required":["type","text"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"image"},"image":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"}},"required":["link"],"additionalProperties":false}},"required":["type","image"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"video"},"video":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"}},"required":["link"],"additionalProperties":false}},"required":["type","video"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"document"},"document":{"type":"object","properties":{"link":{"type":"string","maxLength":2048,"format":"uri"},"filename":{"type":"string","minLength":1,"maxLength":240}},"required":["link"],"additionalProperties":false}},"required":["type","document"],"additionalProperties":false}]},"body":{"type":"object","properties":{"text":{"type":"string","minLength":1,"maxLength":1024}},"required":["text"],"additionalProperties":false},"footer":{"type":"object","properties":{"text":{"type":"string","minLength":1,"maxLength":60}},"required":["text"],"additionalProperties":false},"action":{"type":"object","properties":{"name":{"type":"string","const":"cta_url"},"parameters":{"type":"object","properties":{"display_text":{"type":"string","minLength":1,"maxLength":20},"url":{"type":"string","maxLength":2048,"format":"uri"}},"required":["display_text","url"],"additionalProperties":false}},"required":["name","parameters"],"additionalProperties":false}},"required":["type","body","action"],"additionalProperties":false}]}},"required":["type"],"additionalProperties":false,"description":"Name the person with to (the number with its country code), contactId or externalId. type names the content, and the object of the same name carries it, as at Meta."}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"messageId":{"type":"string"},"conversationId":{"anyOf":[{"type":"string"},{"type":"null"}]},"channel":{"type":"string","enum":["whatsapp","rcs"]}},"required":["messageId","conversationId","channel"]}}}},"400":{"description":"Error: invalid_body, invalid_recipient, invalid_phone.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: identity_conflict, blocked_contact, opted_out, no_whatsapp_number, number_unlinked, number_suspended, meta_auth_failed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: window_closed, meta_rejected.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/messages/whatsapp":{"post":{"operationId":"sendWhatsappText","summary":"Sends a WhatsApp text right away to an existing record.","tags":["Messages"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"contactId":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$"},"externalId":{"type":"string","maxLength":512},"phone":{"type":"string","maxLength":64},"bsuid":{"type":"string","maxLength":200},"text":{"type":"string","minLength":1,"maxLength":4096}},"required":["text"],"additionalProperties":false}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"messageId":{"type":"string"},"conversationId":{"anyOf":[{"type":"string"},{"type":"null"}]},"channel":{"type":"string","enum":["whatsapp","rcs"]}},"required":["messageId","conversationId","channel"]}}}},"400":{"description":"Error: invalid_body, invalid_recipient, invalid_phone.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: identity_conflict, blocked_contact, opted_out, no_whatsapp_number, number_unlinked, number_suspended, meta_auth_failed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: window_closed, meta_rejected.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/messages/rcs":{"post":{"operationId":"sendRcsText","summary":"Sends an RCS text right away to an existing record.","tags":["Messages"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"contactId":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$"},"externalId":{"type":"string","maxLength":512},"phone":{"type":"string","maxLength":64},"bsuid":{"type":"string","maxLength":200},"text":{"type":"string","minLength":1,"maxLength":3072}},"required":["text"],"additionalProperties":false}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"messageId":{"type":"string"},"conversationId":{"anyOf":[{"type":"string"},{"type":"null"}]},"channel":{"type":"string","enum":["whatsapp","rcs"]}},"required":["messageId","conversationId","channel"]}}}},"400":{"description":"Error: invalid_body, invalid_recipient, invalid_phone.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: unknown_contact.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: identity_conflict, blocked_contact, opted_out, no_consent, rcs_not_enabled.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: no_phone, rcs_unreachable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/sends":{"post":{"operationId":"createSend","summary":"Starts an asynchronous, idempotent send to 1 to 50 recipients.","tags":["Sends"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","parameters":[{"name":"Idempotency-Key","in":"header","required":false,"schema":{"type":"string"},"description":"Makes the call safe to replay: the same key returns the first result. Required unless the body has idempotencyKey."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"idempotencyKey":{"type":"string"},"target":{"anyOf":[{"type":"object","properties":{"template":{"type":"object","properties":{"name":{"type":"string","minLength":1,"maxLength":512},"language":{"type":"string","minLength":1,"maxLength":20}},"required":["name","language"],"additionalProperties":false}},"required":["template"],"additionalProperties":false},{"type":"object","properties":{"scenario":{"type":"string","minLength":1,"maxLength":200}},"required":["scenario"],"additionalProperties":false},{"type":"object","properties":{"node":{"type":"string","minLength":1,"maxLength":200}},"required":["node"],"additionalProperties":false},{"type":"object","properties":{"rcsMessage":{"type":"string","minLength":1,"maxLength":120}},"required":["rcsMessage"],"additionalProperties":false}]},"recipients":{"minItems":1,"maxItems":50,"type":"array","items":{"type":"object","properties":{"contactId":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12})$"},"externalId":{"type":"string","maxLength":512},"phone":{"type":"string","maxLength":64},"bsuid":{"type":"string","maxLength":200},"consent":{"type":"string","enum":["opted_in","opted_out"]},"consentSource":{"type":"string","minLength":1,"maxLength":100},"variables":{"description":"Values for this recipient only, never written on the record: the {{name}} of an RCS message, or a template parameter of source variable.","type":"object","propertyNames":{"type":"string"},"additionalProperties":{"type":"string"}}}}},"params":{"description":"Template parameters: positions run from 1 to N, with no gap and no repeat.","type":"array","items":{"type":"object","properties":{"position":{"type":"integer","minimum":1,"maximum":9007199254740991},"source":{"anyOf":[{"type":"object","properties":{"type":{"type":"string","const":"field"},"key":{"type":"string"}},"required":["type","key"]},{"type":"object","properties":{"type":{"type":"string","const":"attribute"},"key":{"type":"string","enum":["name","phone","bsuid","wa_id"]}},"required":["type","key"]},{"type":"object","properties":{"type":{"type":"string","const":"now"}},"required":["type"]},{"type":"object","properties":{"type":{"type":"string","const":"literal"},"value":{"type":"string"}},"required":["type","value"]},{"type":"object","properties":{"type":{"type":"string","const":"variable"},"key":{"type":"string"}},"required":["type","key"]}]},"fallback":{"type":"string"}},"required":["position","source"],"additionalProperties":false}},"category":{"type":"string","enum":["marketing","utility"]},"ratePerMinute":{"type":"integer","minimum":1,"maximum":80},"phoneNumberId":{"type":"string","minLength":1,"maxLength":64}},"required":["target","recipients"],"additionalProperties":false,"description":"One target, 1 to 50 recipients. A malformed recipient is skipped (see skipped in the response), it does not fail the send."}}}},"responses":{"201":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"sendId":{"type":"string"},"opening":{"type":"string","enum":["whatsapp_template","whatsapp_session","rcs"]},"recipientCount":{"type":"number"},"created":{"type":"number"},"matched":{"type":"number"},"skipped":{"type":"array","items":{"type":"object","properties":{"index":{"type":"number"},"reason":{"type":"string","enum":["invalid_recipient","invalid_phone","unknown_contact","duplicate","identity_conflict","blocked_contact","opted_out","no_consent","window_closed","missing_variable","no_phone","plan_limit_reached"]}},"required":["index","reason"]}},"skippedTotal":{"type":"number"}},"required":["sendId","opening","recipientCount","created","matched","skipped","skippedTotal"]}}}},"400":{"description":"Error: invalid_body, idempotency_key_required.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"402":{"description":"Error: plan_feature_unavailable, plan_limit_reached.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: template_not_found, scenario_not_found, node_not_found, rcs_message_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: idempotency_in_progress, no_whatsapp_number, number_unlinked, number_suspended, scenario_ambiguous, rcs_not_enabled.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: idempotency_key_reused, template_category_unknown, unsendable_target.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/sends/{sendId}":{"get":{"operationId":"getSend","summary":"Reads the state and results of a send.","tags":["Sends"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","parameters":[{"name":"sendId","in":"path","required":true,"schema":{"type":"string","format":"uuid","pattern":"^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"sendId":{"type":"string"},"status":{"type":"string","enum":["draft","running","paused","completed","failed","scheduled"]},"target":{"anyOf":[{"type":"object","properties":{"template":{"type":"object","properties":{"name":{"type":"string"},"language":{"type":"string"}},"required":["name","language"]}},"required":["template"]},{"type":"object","properties":{"scenario":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["scenario"]},{"type":"object","properties":{"node":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["node"]},{"type":"object","properties":{"rcsMessage":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["rcsMessage"]}]},"opening":{"anyOf":[{"type":"string","enum":["whatsapp_template","whatsapp_session","rcs"]},{"type":"null"}]},"createdAt":{"type":"string","description":"ISO 8601 date-time"},"counts":{"type":"object","properties":{"pending":{"type":"number"},"sending":{"type":"number"},"sent":{"type":"number"},"failed":{"type":"number"},"skipped":{"type":"number"}},"required":["pending","sending","sent","failed","skipped"]},"recipientsTotal":{"type":"number"},"recipients":{"type":"array","items":{"type":"object","properties":{"contactId":{"type":"string"},"externalId":{"anyOf":[{"type":"string"},{"type":"null"}]},"channel":{"type":"string","enum":["whatsapp","rcs","email"]},"status":{"type":"string"},"messageId":{"anyOf":[{"type":"string"},{"type":"null"}]},"delivery":{"anyOf":[{"type":"string"},{"type":"null"}]},"error":{"anyOf":[{"type":"object","properties":{"message":{"type":"string"},"metaCode":{"anyOf":[{"type":"number"},{"type":"null"}]}},"required":["message","metaCode"]},{"type":"null"}]},"sentAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]}},"required":["contactId","externalId","channel","status","messageId","delivery","error","sentAt"]}}},"required":["sendId","status","target","opening","createdAt","counts","recipientsTotal","recipients"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: send_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/templates":{"post":{"operationId":"createTemplate","summary":"Creates a template in Meta’s format and submits it for review.","tags":["Templates"],"security":[{"bearer":[]}],"x-required-scope":"templates:write","description":"Requires the templates:write scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string","pattern":"^[a-z0-9_]{1,512}$"},"language":{"type":"string"},"category":{"type":"string","enum":["UTILITY","MARKETING"]},"parameter_format":{"type":"string","const":"POSITIONAL"},"components":{"minItems":1,"maxItems":4,"type":"array","items":{"oneOf":[{"type":"object","properties":{"type":{"type":"string","const":"HEADER"},"format":{"type":"string","enum":["TEXT","IMAGE","VIDEO","DOCUMENT"]},"text":{"type":"string","minLength":1,"maxLength":60},"example":{"type":"object","properties":{"header_url":{"minItems":1,"maxItems":1,"type":"array","items":{"type":"string","maxLength":2000,"format":"uri"}},"header_handle":{}},"additionalProperties":false}},"required":["type","format"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"BODY"},"text":{"type":"string","minLength":1,"maxLength":1024},"example":{"type":"object","properties":{"body_text":{"minItems":1,"maxItems":1,"type":"array","items":{"type":"array","items":{"type":"string","maxLength":200}}}},"required":["body_text"],"additionalProperties":false}},"required":["type","text"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"FOOTER"},"text":{"type":"string","minLength":1,"maxLength":60}},"required":["type","text"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"BUTTONS"},"buttons":{"minItems":1,"maxItems":10,"type":"array","items":{"oneOf":[{"type":"object","properties":{"type":{"type":"string","const":"QUICK_REPLY"},"text":{"type":"string","minLength":1,"maxLength":25}},"required":["type","text"],"additionalProperties":false},{"type":"object","properties":{"type":{"type":"string","const":"URL"},"text":{"type":"string","minLength":1,"maxLength":25},"url":{"type":"string","maxLength":2000,"format":"uri"}},"required":["type","text","url"],"additionalProperties":false}]}}},"required":["type","buttons"],"additionalProperties":false}]}}},"required":["name","language","components","category"],"additionalProperties":false}}}},"responses":{"201":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"language":{"type":"string"},"category":{"type":"string"},"status":{"type":"string"}},"required":["id","name","language","category","status"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: meta_auth_failed, no_whatsapp_number.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: invalid_header_media, template_rejected, meta_rejected.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"get":{"operationId":"listTemplates","summary":"Lists the approved, sendable WhatsApp templates.","tags":["Catalogs"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"templates":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"language":{"type":"string"},"category":{"type":"string","enum":["marketing","utility"]},"header":{"type":"string","enum":["none","text","image","video","document"]},"variables":{"type":"array","items":{"type":"object","properties":{"position":{"type":"number"},"source":{"anyOf":[{"anyOf":[{"type":"object","properties":{"type":{"type":"string","const":"field"},"key":{"type":"string"}},"required":["type","key"]},{"type":"object","properties":{"type":{"type":"string","const":"attribute"},"key":{"type":"string","enum":["name","phone","bsuid","wa_id"]}},"required":["type","key"]},{"type":"object","properties":{"type":{"type":"string","const":"now"}},"required":["type"]},{"type":"object","properties":{"type":{"type":"string","const":"literal"},"value":{"type":"string"}},"required":["type","value"]},{"type":"object","properties":{"type":{"type":"string","const":"variable"},"key":{"type":"string"}},"required":["type","key"]}]},{"type":"null"}]}},"required":["position","source"]}}},"required":["name","language","category","header","variables"]}}},"required":["templates"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: meta_auth_failed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: meta_rejected.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/templates/{name}":{"get":{"operationId":"getTemplateStatus","summary":"Reads a template’s status at Meta, language by language.","tags":["Templates"],"security":[{"bearer":[]}],"x-required-scope":"templates:write","description":"Requires the templates:write scope.","parameters":[{"name":"name","in":"path","required":true,"schema":{"type":"string"}},{"name":"language","in":"query","required":false,"schema":{"type":"string","maxLength":20}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string"},"languages":{"type":"array","items":{"type":"object","properties":{"language":{"type":"string"},"status":{"type":"string"},"category":{"anyOf":[{"type":"string"},{"type":"null"}]},"rejectedReason":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["language","status","category","rejectedReason"]}}},"required":["name","languages"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: template_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: meta_auth_failed, no_whatsapp_number.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"422":{"description":"Error: meta_rejected.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks":{"get":{"operationId":"listWebhooks","summary":"Lists the endpoints, the plan limit and the available types.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"url":{"type":"string"},"description":{"type":"string"},"types":{"type":"array","items":{"type":"string"}},"active":{"type":"boolean"},"createdAt":{"type":"string","description":"ISO 8601 date-time"},"previousSecretValidUntil":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"lastDeliveredAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"retrying":{"type":"number"},"failed":{"type":"number"}},"required":["id","url","description","types","active","createdAt","previousSecretValidUntil","lastDeliveredAt","retrying","failed"]}},"limit":{"anyOf":[{"type":"number"},{"type":"null"}],"description":"The plan’s maximum number of endpoints; null: unlimited."},"types":{"type":"array","items":{"type":"string","enum":["message.received","message.delivered","message.read","message.failed","link.clicked","contact.opted_out","conversation.analyzed","contact.risk_changed","template.status_changed"]}},"defaultTypes":{"type":"array","items":{"type":"string","enum":["message.received","message.delivered","message.read","message.failed","link.clicked","contact.opted_out","conversation.analyzed","contact.risk_changed","template.status_changed"]}}},"required":["data","limit","types","defaultTypes"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"post":{"operationId":"createWebhook","summary":"Registers an endpoint and returns its secret, only once.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"url":{"type":"string","minLength":1,"maxLength":2048},"description":{"type":"string","maxLength":200},"types":{"minItems":1,"maxItems":9,"type":"array","items":{"type":"string","enum":["message.received","message.delivered","message.read","message.failed","link.clicked","contact.opted_out","conversation.analyzed","contact.risk_changed","template.status_changed"]}}},"required":["url"],"additionalProperties":false}}}},"responses":{"201":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"webhook":{"type":"object","properties":{"id":{"type":"string"},"url":{"type":"string"},"description":{"type":"string"},"types":{"type":"array","items":{"type":"string"}},"active":{"type":"boolean"},"createdAt":{"type":"string","description":"ISO 8601 date-time"},"previousSecretValidUntil":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"lastDeliveredAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"retrying":{"type":"number"},"failed":{"type":"number"}},"required":["id","url","description","types","active","createdAt","previousSecretValidUntil","lastDeliveredAt","retrying","failed"]},"secret":{"type":"string","description":"whsec_…, returned only here and at rotation."}},"required":["webhook","secret"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"402":{"description":"Error: plan_limit_reached.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"503":{"description":"Error: webhooks_unavailable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks/{webhookId}":{"get":{"operationId":"getWebhook","summary":"Reads an endpoint and the state of its deliveries.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string"},"url":{"type":"string"},"description":{"type":"string"},"types":{"type":"array","items":{"type":"string"}},"active":{"type":"boolean"},"createdAt":{"type":"string","description":"ISO 8601 date-time"},"previousSecretValidUntil":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"lastDeliveredAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"retrying":{"type":"number"},"failed":{"type":"number"}},"required":["id","url","description","types","active","createdAt","previousSecretValidUntil","lastDeliveredAt","retrying","failed"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"patch":{"operationId":"updateWebhook","summary":"Changes the types, the description, or pauses the endpoint.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"description":{"type":"string","maxLength":200},"types":{"minItems":1,"maxItems":9,"type":"array","items":{"type":"string","enum":["message.received","message.delivered","message.read","message.failed","link.clicked","contact.opted_out","conversation.analyzed","contact.risk_changed","template.status_changed"]}},"active":{"type":"boolean"}},"additionalProperties":false}}}},"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string"},"url":{"type":"string"},"description":{"type":"string"},"types":{"type":"array","items":{"type":"string"}},"active":{"type":"boolean"},"createdAt":{"type":"string","description":"ISO 8601 date-time"},"previousSecretValidUntil":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"lastDeliveredAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"retrying":{"type":"number"},"failed":{"type":"number"}},"required":["id","url","description","types","active","createdAt","previousSecretValidUntil","lastDeliveredAt","retrying","failed"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"402":{"description":"Error: plan_limit_reached.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"delete":{"operationId":"deleteWebhook","summary":"Deletes an endpoint.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"204":{"description":"Success, no content."},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks/{webhookId}/rotate-secret":{"post":{"operationId":"rotateWebhookSecret","summary":"Rotates the secret; the old one still signs for 24 h.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"secret":{"type":"string"},"previousSecretValidUntil":{"type":"string","description":"ISO 8601 date-time"}},"required":["secret","previousSecretValidUntil"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"503":{"description":"Error: webhooks_unavailable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks/{webhookId}/test":{"post":{"operationId":"testWebhook","summary":"Sends a signed test event and returns the app’s answer.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"eventId":{"type":"string"},"delivered":{"type":"boolean"},"statusCode":{"anyOf":[{"type":"number"},{"type":"null"}]},"response":{"type":"string"}},"required":["eventId","delivered","statusCode","response"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"503":{"description":"Error: webhooks_unavailable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks/{webhookId}/deliveries":{"get":{"operationId":"listWebhookDeliveries","summary":"Reads an endpoint’s log, most recent first.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}},{"name":"before","in":"query","required":false,"schema":{"type":"string","format":"date-time","pattern":"^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$"}},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":100}}],"responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"eventId":{"type":"string"},"type":{"type":"string"},"status":{"type":"string","enum":["pending","delivered","failed"]},"attempts":{"type":"number"},"lastStatusCode":{"anyOf":[{"type":"number"},{"type":"null"}]},"lastResponse":{"anyOf":[{"type":"string"},{"type":"null"}]},"nextAttemptAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"createdAt":{"type":"string","description":"ISO 8601 date-time"},"deliveredAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]},"body":{"type":"string","description":"The exact body that was sent, byte for byte."}},"required":["id","eventId","type","status","attempts","lastStatusCode","lastResponse","nextAttemptAt","createdAt","deliveredAt","body"]}},"nextBefore":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}],"description":"Pass it as before for the next page."}},"required":["data","nextBefore"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks/deliveries/{deliveryId}/replay":{"post":{"operationId":"replayWebhookDelivery","summary":"Replays a finished delivery, with the same body.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"deliveryId","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"202":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"replayed":{"type":"boolean","const":true}},"required":["replayed"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: delivery_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"409":{"description":"Error: delivery_not_replayable.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/webhooks/{webhookId}/replay-failures":{"post":{"operationId":"replayWebhookFailures","summary":"Replays the failed deliveries since a date.","tags":["Outgoing webhooks"],"security":[{"bearer":[]}],"x-required-scope":"webhooks:write","description":"Requires the webhooks:write scope.","parameters":[{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"since":{"type":"string","format":"date-time","pattern":"^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$"}},"required":["since"],"additionalProperties":false}}}},"responses":{"202":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"replayed":{"type":"number","description":"How many deliveries were replayed."}},"required":["replayed"]}}}},"400":{"description":"Error: invalid_body.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"404":{"description":"Error: webhook_not_found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/scenarios":{"get":{"operationId":"listScenarios","summary":"Lists the published scenarios and their opening message.","tags":["Catalogs"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"scenarios":{"type":"array","items":{"type":"object","properties":{"code":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"type":"string"},"opening":{"anyOf":[{"type":"string","enum":["whatsapp_template","whatsapp_session","rcs"]},{"type":"null"}]},"openingTemplate":{"anyOf":[{"type":"object","properties":{"name":{"type":"string"},"language":{"type":"string"}},"required":["name","language"]},{"type":"null"}]},"entryNode":{"anyOf":[{"type":"string"},{"type":"null"}]},"publishedAt":{"anyOf":[{"type":"string","description":"ISO 8601 date-time"},{"type":"null"}]}},"required":["code","name","opening","openingTemplate","entryNode","publishedAt"]}}},"required":["scenarios"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}},"/v1/rcs-messages":{"get":{"operationId":"listRcsMessages","summary":"Lists the RCS messages of the library.","tags":["Catalogs"],"security":[{"bearer":[]}],"x-required-scope":"sends:create","description":"Requires the sends:create scope.","responses":{"200":{"description":"Success.","content":{"application/json":{"schema":{"type":"object","properties":{"rcsMessages":{"type":"array","items":{"type":"object","properties":{"name":{"type":"string"},"kind":{"type":"string","enum":["text","card","carousel"]},"variables":{"type":"array","items":{"type":"string"}}},"required":["name","kind","variables"]}}},"required":["rcsMessages"]}}}},"401":{"description":"Error: unauthorized.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"403":{"description":"Error: missing_scope, tenant_locked.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Error: rate_limited, quota_exceeded. Wait for Retry-After (seconds) before retrying.","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Seconds to wait."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"500":{"description":"Error: internal_error.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}}},"webhooks":{"message.received":{"post":{"summary":"A contact sent a message (WhatsApp or RCS).","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"message.received"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"channel":{"type":"string","enum":["whatsapp","rcs"]},"message_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"message_type":{"anyOf":[{"type":"string"},{"type":"null"}]},"text":{"anyOf":[{"type":"string"},{"type":"null"}]},"transcription":{"anyOf":[{"type":"string"},{"type":"null"}]},"button":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["contact","channel","message_id","message_type","text","transcription","button"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"message.delivered":{"post":{"summary":"A message we sent was delivered.","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"message.delivered"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"channel":{"type":"string","enum":["whatsapp","rcs"]},"message_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"origin":{"anyOf":[{"type":"string"},{"type":"null"}]},"send_id":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["contact","channel","message_id","origin","send_id"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"message.read":{"post":{"summary":"A message we sent was read.","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"message.read"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"channel":{"type":"string","enum":["whatsapp","rcs"]},"message_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"origin":{"anyOf":[{"type":"string"},{"type":"null"}]},"send_id":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["contact","channel","message_id","origin","send_id"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"message.failed":{"post":{"summary":"A message we sent failed.","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"message.failed"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"channel":{"type":"string","enum":["whatsapp","rcs"]},"message_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"origin":{"anyOf":[{"type":"string"},{"type":"null"}]},"send_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"reason":{"anyOf":[{"type":"string"},{"type":"null"}]},"meta_code":{"anyOf":[{"type":"number"},{"type":"null"}]}},"required":["contact","channel","message_id","origin","send_id","reason","meta_code"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"link.clicked":{"post":{"summary":"A contact clicked a tracked link.","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"link.clicked"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"link":{"type":"string"},"template":{"anyOf":[{"type":"string"},{"type":"null"}]},"destination":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["contact","link","template","destination"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"contact.opted_out":{"post":{"summary":"A contact opted out (STOP).","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"contact.opted_out"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"channel":{"anyOf":[{"type":"string","enum":["whatsapp","rcs"]},{"type":"null"}]},"source":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["contact","channel","source"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"conversation.analyzed":{"post":{"summary":"A conversation was analyzed (intent, sentiment, satisfaction, urgency).","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"conversation.analyzed"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"conversation_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"intent":{"type":"string"},"sentiment":{"type":"string"},"satisfaction":{"anyOf":[{"type":"number"},{"type":"null"}]},"urgency":{"anyOf":[{"type":"number"},{"type":"null"}]},"resolved":{"type":"boolean"},"topic":{"type":"string"},"action_suggestion":{"type":"string"},"handled_by":{"type":"string"},"exchanges_count":{"type":"number"},"summary":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["contact","conversation_id","intent","sentiment","satisfaction","urgency","resolved","topic","action_suggestion","handled_by","exchanges_count","summary"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"contact.risk_changed":{"post":{"summary":"A contact’s disengagement risk level changed.","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"contact.risk_changed"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},"level":{"type":"string","enum":["inconnu","faible","moyen","eleve"]},"previous_level":{"anyOf":[{"type":"string","enum":["inconnu","faible","moyen","eleve"]},{"type":"null"}]},"score":{"anyOf":[{"type":"number"},{"type":"null"}]},"reasons":{"type":"array","items":{"type":"string","enum":["stop","bloque","silence_60j","silence_30j","sans_reponse","non_lu","reclamation","negatif","insatisfait","injoignable"]}}},"required":["contact","level","previous_level","score","reasons"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"template.status_changed":{"post":{"summary":"Meta approved, rejected, paused or disabled one of your templates.","description":"Sent to every webhook endpoint subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"template.status_changed"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"template":{"type":"object","properties":{"id":{"type":"string"},"name":{"type":"string"},"language":{"type":"string"}},"required":["id","name","language"]},"status":{"type":"string","description":"Meta’s event, lowercase: approved, rejected, paused, disabled…"},"reason":{"anyOf":[{"type":"string"},{"type":"null"}]}},"required":["template","status","reason"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"conversation.needs_reply":{"post":{"summary":"Your application should reply.","description":"Sent only to the endpoint designated as the responder (the workspace answers through your application), whether or not it subscribed to this type. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"conversation.needs_reply"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"contact":{"anyOf":[{"type":"object","properties":{"id":{"type":"string"},"phone":{"anyOf":[{"type":"string"},{"type":"null"}]},"name":{"anyOf":[{"type":"string"},{"type":"null"}]},"external_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"opted_out":{"type":"object","properties":{"whatsapp":{"type":"boolean"},"rcs":{"type":"boolean"}},"required":["whatsapp","rcs"]}},"required":["id","phone","name","external_id","opted_out"]},{"type":"null"}]},"conversation_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"channel":{"type":"string","const":"whatsapp"},"message_id":{"anyOf":[{"type":"string"},{"type":"null"}]},"message_type":{"anyOf":[{"type":"string"},{"type":"null"}]},"text":{"anyOf":[{"type":"string"},{"type":"null"}]},"transcription":{"anyOf":[{"type":"string"},{"type":"null"}]},"reply_with":{"type":"object","properties":{"method":{"type":"string","const":"POST"},"path":{"type":"string","const":"/v1/messages/whatsapp"}},"required":["method","path"]}},"required":["contact","conversation_id","channel","message_id","message_type","text","transcription","reply_with"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}},"test":{"post":{"summary":"A test event.","description":"Sent only by POST /v1/webhooks/{webhookId}/test, to that endpoint. Signed per Standard Webhooks.","security":[],"parameters":[{"name":"webhook-id","in":"header","required":true,"schema":{"type":"string"},"description":"The event id (evt_…), stable across retries."},{"name":"webhook-timestamp","in":"header","required":true,"schema":{"type":"string"},"description":"Unix time in seconds; reject a timestamp more than 5 minutes away."},{"name":"webhook-signature","in":"header","required":true,"schema":{"type":"string"},"description":"v1,<base64 HMAC-SHA256 of id.timestamp.body>, keyed with the base64-decoded part of the secret after whsec_; during a rotation, two signatures separated by a space."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","description":"evt_ followed by 32 hex characters; stable across retries and replays. Also sent in webhook-id."},"type":{"type":"string","const":"test"},"created_at":{"type":"string","description":"ISO 8601 date-time"},"workspace_id":{"type":"string","description":"The workspace (tenant) ID."},"data":{"type":"object","properties":{"message":{"type":"string"}},"required":["message"]}},"required":["id","type","created_at","workspace_id","data"]}}}},"responses":{"2XX":{"description":"Acknowledged. Anything else is retried for 24 hours."}}}}},"components":{"securitySchemes":{"bearer":{"type":"http","scheme":"bearer","description":"An API key (mba_…), created in the console (Developers > API keys), in Authorization: Bearer."}},"schemas":{"Error":{"type":"object","properties":{"error":{"type":"string","description":"A human-readable message (French)."},"code":{"type":"string","enum":["invalid_body","invalid_recipient","invalid_phone","unauthorized","missing_scope","tenant_locked","unknown_contact","duplicate","identity_conflict","blocked_contact","opted_out","no_consent","window_closed","missing_variable","no_phone","rcs_unreachable","rcs_not_enabled","no_whatsapp_number","meta_rejected","invalid_header_media","template_rejected","meta_auth_failed","webhook_not_found","delivery_not_found","delivery_not_replayable","webhooks_unavailable","field_exists","number_unlinked","number_suspended","scenario_not_found","node_not_found","template_not_found","rcs_message_not_found","send_not_found","conversation_not_found","message_not_found","invalid_cursor","no_media","media_expired","media_unavailable","scenario_ambiguous","unsendable_target","template_category_unknown","idempotency_key_required","idempotency_in_progress","idempotency_key_reused","rate_limited","quota_exceeded","plan_feature_unavailable","plan_limit_reached","route_not_found","internal_error"],"description":"The stable machine-readable code, on every JSON error response of the API. A 5xx may arrive without this body (a generic error page replaced it on the way)."},"metaCode":{"type":["integer","null"],"description":"On meta_rejected: Meta’s own error number (131047, 132000…), null when Meta gives none."},"upgradeUrl":{"type":"string","description":"On 402 (plan_feature_unavailable, plan_limit_reached): the page where the plan is upgraded."}},"required":["error"]}}}}