{"openapi":"3.1.0","info":{"title":"Blooio v4 API","version":"4.0.0-beta","description":"The Blooio v4 API is a multi-channel messaging API for iMessage, SMS, RCS, WhatsApp, and Apple Messages for Business (AMB). It exposes channels, contacts and identities, chats, messages, reactions, polls, groups, webhooks, and a unified event feed.\n\n## Authentication\nAuthenticate with an API key as a bearer token: `Authorization: Bearer bl_live_...`. Create keys in the Blooio dashboard.\n\n## Conventions\n- **IDs** are prefixed and globally unique: channels `ch_`, contacts `ct_`, identities `cid_`, chats `chat_`, messages `msg_`, groups `grp_`, webhooks `wh_`, webhook deliveries `wdel_`, events `evt_`.\n- **List responses** return `{ \"data\": [...], \"has_more\": boolean, \"next_cursor\": string | null }` and use cursor pagination (`limit`, `cursor`).\n- **Item responses** return `{ \"data\": { ... } }`. Message send endpoints return the message object at the top level (not wrapped).\n- **Errors** use `{ \"error\": { \"code\": string, \"message\": string, \"details\": object } }`. Authentication failures at the middleware boundary use a flatter shape `{ \"error\": string, \"message\": string, \"status\": number }`.","contact":{"name":"Blooio Support","email":"help@blooio.com","url":"https://docs.blooio.com"}},"servers":[{"url":"https://api.blooio.com/v4","description":"Production"}],"security":[{"BearerApiKey":[]}],"x-blooio-status":"beta","tags":[{"name":"Account","description":"Authenticated account, sender numbers, and contact cards."},{"name":"Location","description":"Find My friend locations (device passthrough)."},{"name":"Channels","description":"Sending surfaces (iMessage/Blooio, Twilio, WhatsApp, RCS, AMB) and their capabilities."},{"name":"Contacts","description":"Contacts, their channel identities, capabilities, timeline, and tags."},{"name":"Chats","description":"Conversations and chat-level actions (typing, read, contact card, background)."},{"name":"Messages","description":"Send messages and read message history, status, events, and reactions."},{"name":"Polls","description":"Native iMessage polls (Blooio channels)."},{"name":"Groups","description":"Group chats on group-capable channels (Blooio, WhatsApp)."},{"name":"Webhooks","description":"Webhook subscriptions and delivery attempts for inbound + lifecycle events."},{"name":"Events","description":"Unified activity feed across messages, polls, groups, reactions, and typing."},{"name":"Phone Numbers","description":"Phone number lookup and geocoding (enterprise plans)."}],"paths":{"/me":{"get":{"tags":["Account"],"summary":"Get the authenticated account","description":"Returns the authenticated organization, linked devices/numbers, usage, and API key validity.","operationId":"getMe","responses":{"200":{"description":"Account context","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","additionalProperties":true}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/me/numbers":{"get":{"tags":["Account"],"summary":"List sender numbers","description":"Lists the phone numbers / sender addresses available to this API key.","operationId":"listNumbers","responses":{"200":{"description":"Sender numbers","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","additionalProperties":true}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/me/numbers/{number}/contact-card":{"get":{"tags":["Account"],"summary":"Get a number's contact card","operationId":"getContactCard","parameters":[{"$ref":"#/components/parameters/NumberParam"}],"responses":{"200":{"description":"Contact card","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Account"],"summary":"Update a number's contact card","description":"Updates the contact card (name, avatar, sharing settings) shared from this number. At least one field is required.","operationId":"updateContactCard","parameters":[{"$ref":"#/components/parameters/NumberParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"first_name":{"type":"string"},"last_name":{"type":"string"},"avatar":{"type":"string","description":"Public image URL or data URI."},"sharing":{"type":"object","properties":{"enabled":{"type":"boolean"},"audience":{"type":"string"},"name_format":{"type":"string"}}}}}}}},"responses":{"200":{"description":"Updated contact card","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/me/numbers/{number}/contact-card/avatar":{"post":{"tags":["Account"],"summary":"Upload a contact card avatar","description":"Uploads an avatar image for the number's contact card. Max 10MB.","operationId":"uploadContactCardAvatar","parameters":[{"$ref":"#/components/parameters/NumberParam"}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"avatar":{"type":"string","format":"binary"}},"required":["avatar"]}}}},"responses":{"200":{"description":"Avatar uploaded","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/me/numbers/{number}/call-forwarding":{"post":{"tags":["Account"],"summary":"Request call forwarding","operationId":"requestCallForwarding","parameters":[{"$ref":"#/components/parameters/NumberParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"forward_to":{"type":"string","description":"US E.164 number to forward calls to."}},"required":["forward_to"]}}}},"responses":{"200":{"description":"Call forwarding requested","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/location/contacts":{"get":{"tags":["Location"],"summary":"List Find My contacts","description":"Lists Find My friends sharing their location with the linked Apple account.","operationId":"listLocationContacts","responses":{"200":{"description":"Find My contacts","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","additionalProperties":true}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/location/contacts/refresh":{"get":{"tags":["Location"],"summary":"Refresh Find My locations (GET)","description":"Convenience GET form of the refresh endpoint. Forces a refresh of Find My location data from the device.","operationId":"refreshLocationContactsGet","responses":{"200":{"description":"Refresh result","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["Location"],"summary":"Refresh Find My locations","description":"Forces a refresh of Find My location data from the device.","operationId":"refreshLocationContacts","responses":{"200":{"description":"Refresh result","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/location/contacts/{handle}":{"get":{"tags":["Location"],"summary":"Get one Find My contact","operationId":"getLocationContact","parameters":[{"name":"handle","in":"path","required":true,"schema":{"type":"string"},"description":"Contact handle to resolve — a phone number in E.164 format, an email address, or an Apple ID. URL-encode the value."}],"responses":{"200":{"description":"Find My contact","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/channels":{"get":{"tags":["Channels"],"summary":"List channels","description":"Lists messaging channels for the organization. A `channel_id` (ch_...) is required to send messages.","operationId":"listChannels","parameters":[{"name":"type","in":"query","schema":{"$ref":"#/components/schemas/ChannelType"},"description":"Filter by channel type."},{"name":"status","in":"query","schema":{"$ref":"#/components/schemas/ChannelStatus"},"description":"Filter by channel status."},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of channels","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Channel"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}},"example":{"data":[{"id":"ch_018f7b2a-1c3d-7e4f-9a2b-0c1d2e3f4a5b","type":"blooio","display_address":"+15551234567","status":"active","capabilities":{"protocols":["imessage","sms","rcs"],"content":["text","media"]},"created_at":1718000000000}],"has_more":false,"next_cursor":null}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/channels/{channelId}":{"get":{"tags":["Channels"],"summary":"Get a channel","operationId":"getChannel","parameters":[{"$ref":"#/components/parameters/ChannelIdParam"}],"responses":{"200":{"description":"A channel","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Channel"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/channels/{channelId}/capabilities":{"get":{"tags":["Channels"],"summary":"Get channel capabilities","description":"Returns supported protocols, content types, actions, and interactive features for a channel.","operationId":"getChannelCapabilities","parameters":[{"$ref":"#/components/parameters/ChannelIdParam"}],"responses":{"200":{"description":"Channel capabilities","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channel_id":{"type":"string"},"type":{"$ref":"#/components/schemas/ChannelType"},"capabilities":{"$ref":"#/components/schemas/ChannelCapabilities"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/channels/{channelId}/profile":{"put":{"tags":["Channels"],"summary":"Update channel profile","description":"Stores channel profile metadata (e.g. display name, avatar). The profile object is stored verbatim under `metadata.profile`.","operationId":"updateChannelProfile","parameters":[{"$ref":"#/components/parameters/ChannelIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","additionalProperties":true,"description":"Channel-specific profile fields. The exact keys depend on the channel type (e.g. WhatsApp profile fields)."},"example":{"display_name":"Blooio Support","about":"We reply within minutes.","email":"support@blooio.com"}}}},"responses":{"200":{"description":"Updated profile","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"channel_id":{"type":"string"},"type":{"$ref":"#/components/schemas/ChannelType"},"profile":{"type":"object","additionalProperties":true}}}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/contacts":{"get":{"tags":["Contacts"],"summary":"List contacts","description":"Lists contacts. Filter by `identifier` (phone in E.164 or email) to find the contact owning an address.","operationId":"listContacts","parameters":[{"name":"identifier","in":"query","schema":{"type":"string"},"description":"Filter to the contact owning this phone/email."},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of contacts","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Contact"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["Contacts"],"summary":"Create a contact","description":"Creates a contact, optionally with one identity (phone/email on a channel type).","operationId":"createContact","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateContactRequest"}}}},"responses":{"201":{"description":"Created contact","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Contact"}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/contacts/{contactId}":{"get":{"tags":["Contacts"],"summary":"Get a contact","operationId":"getContact","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"responses":{"200":{"description":"A contact","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Contact"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"patch":{"tags":["Contacts"],"summary":"Update a contact","operationId":"updateContact","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string"}},"required":["name"]}}}},"responses":{"200":{"description":"Updated contact","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Contact"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}},"delete":{"tags":["Contacts"],"summary":"Delete a contact","description":"Soft-deletes a contact and its identities.","operationId":"deleteContact","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"responses":{"200":{"description":"Deleted","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"deleted":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/contacts/{contactId}/identities":{"get":{"tags":["Contacts"],"summary":"List contact identities","operationId":"listContactIdentities","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"responses":{"200":{"description":"Identities","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/ContactIdentity"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"post":{"tags":["Contacts"],"summary":"Attach an identity","description":"Attaches a phone/email identity (on a channel type) to a contact.","operationId":"attachContactIdentity","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/AttachIdentityRequest"}}}},"responses":{"201":{"description":"Attached identity","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/ContactIdentity"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/contacts/{contactId}/identities/{identityId}":{"delete":{"tags":["Contacts"],"summary":"Detach an identity","operationId":"detachContactIdentity","parameters":[{"$ref":"#/components/parameters/ContactIdParam"},{"name":"identityId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the contact identity (a phone/email tied to the contact), prefixed with `cid_`. Returned by the List contact identities endpoint."}],"responses":{"200":{"description":"Detached","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"detached":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/contacts/{contactId}/capabilities":{"get":{"tags":["Contacts"],"summary":"Get contact capabilities","description":"Returns per-identity reachability/capabilities (iMessage/SMS/RCS, etc.) for a contact.","operationId":"getContactCapabilities","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"responses":{"200":{"description":"Capabilities per identity","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"identifier":{"type":"string"},"channel_id":{"type":["string","null"]},"capabilities":{"type":"object","additionalProperties":true}}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/contacts/{contactId}/timeline":{"get":{"tags":["Contacts"],"summary":"Get contact timeline","description":"Cross-channel activity timeline (messages) for a contact.","operationId":"getContactTimeline","parameters":[{"$ref":"#/components/parameters/ContactIdParam"},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"Timeline page","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"chat_id":{"type":"string"},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"direction":{"$ref":"#/components/schemas/Direction"},"type":{"type":"string"},"text":{"type":["string","null"]},"status":{"type":"string"},"created_at":{"type":"integer"}}}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/contacts/{contactId}/tags":{"get":{"tags":["Contacts"],"summary":"List contact tags","operationId":"listContactTags","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"responses":{"200":{"description":"Tags","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"string"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"post":{"tags":["Contacts"],"summary":"Add contact tags","operationId":"addContactTags","parameters":[{"$ref":"#/components/parameters/ContactIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"tags":{"type":"array","items":{"type":"string"}},"tag":{"type":"string"}}}}}},"responses":{"200":{"description":"Merged tags","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"string"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/contacts/{contactId}/tags/{tag}":{"delete":{"tags":["Contacts"],"summary":"Remove a contact tag","operationId":"removeContactTag","parameters":[{"$ref":"#/components/parameters/ContactIdParam"},{"name":"tag","in":"path","required":true,"schema":{"type":"string"},"description":"The tag to remove from the contact. URL-encode values that contain spaces or special characters."}],"responses":{"200":{"description":"Remaining tags","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"string"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/groups":{"get":{"tags":["Groups"],"summary":"List groups","operationId":"listGroups","parameters":[{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of groups","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Group"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["Groups"],"summary":"Create a group","description":"Creates a group chat on a group-capable channel (blooio/whatsapp) with one or more members.","operationId":"createGroup","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateGroupRequest"}}}},"responses":{"201":{"description":"Created group","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Group"}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/groups/{groupId}":{"get":{"tags":["Groups"],"summary":"Get a group","operationId":"getGroup","parameters":[{"$ref":"#/components/parameters/GroupIdParam"}],"responses":{"200":{"description":"A group","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Group"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"patch":{"tags":["Groups"],"summary":"Update a group","operationId":"updateGroup","parameters":[{"$ref":"#/components/parameters/GroupIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string"}},"required":["name"]}}}},"responses":{"200":{"description":"Updated group","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Group"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}},"delete":{"tags":["Groups"],"summary":"Delete a group","operationId":"deleteGroup","parameters":[{"$ref":"#/components/parameters/GroupIdParam"}],"responses":{"200":{"description":"Deleted","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"deleted":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/groups/{groupId}/members":{"get":{"tags":["Groups"],"summary":"List group members","operationId":"listGroupMembers","parameters":[{"$ref":"#/components/parameters/GroupIdParam"}],"responses":{"200":{"description":"Members","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/GroupMember"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/groups/{groupId}/icon":{"post":{"tags":["Groups"],"summary":"Set group icon","description":"Uploads a group icon. Max 10MB; image/jpeg|png|gif|webp|heic|heif. Requires the group chat to be linked on a device.","operationId":"setGroupIcon","parameters":[{"$ref":"#/components/parameters/GroupIdParam"}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"icon":{"type":"string","format":"binary"}},"required":["icon"]}}}},"responses":{"200":{"description":"Icon set","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"icon_url":{"type":["string","null"]}}}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}},"delete":{"tags":["Groups"],"summary":"Remove group icon","operationId":"removeGroupIcon","parameters":[{"$ref":"#/components/parameters/GroupIdParam"}],"responses":{"200":{"description":"Icon removed","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"removed":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/chats":{"get":{"tags":["Chats"],"summary":"List chats","description":"Lists conversations, most recent first. Filter by channel type, state, channel, or contact.","operationId":"listChats","parameters":[{"name":"type","in":"query","schema":{"$ref":"#/components/schemas/ChannelType"}},{"name":"state","in":"query","schema":{"$ref":"#/components/schemas/ChatState"}},{"name":"channel_id","in":"query","schema":{"type":"string"}},{"name":"contact_id","in":"query","schema":{"type":"string"}},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of chats","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Chat"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["Chats"],"summary":"Find or create a chat","description":"Finds or creates a 1:1 chat with a recipient on a channel. Returns the chat (with `created` indicating whether it was newly created).","operationId":"createChat","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateChatRequest"}}}},"responses":{"200":{"description":"Existing chat","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChatCreated"}}}},"201":{"description":"Created chat","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ChatCreated"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/chats/{chatId}":{"get":{"tags":["Chats"],"summary":"Get a chat","operationId":"getChat","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"200":{"description":"A chat","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Chat"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"patch":{"tags":["Chats"],"summary":"Update a chat","description":"Sets chat state (`open`/`closed`) and/or merges metadata. At least one field is required.","operationId":"updateChat","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"state":{"type":"string","enum":["open","closed"]},"metadata":{"type":"object","additionalProperties":true}}}}}},"responses":{"200":{"description":"Updated chat","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Chat"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/chats/{chatId}/typing":{"post":{"tags":["Chats"],"summary":"Start/stop typing indicator","description":"Shows or clears a typing indicator. Blooio channels only.","operationId":"setTyping","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"requestBody":{"required":false,"content":{"application/json":{"schema":{"type":"object","properties":{"state":{"type":"string","enum":["started","stopped"],"default":"started"}}}}}},"responses":{"200":{"description":"Typing state applied","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"state":{"type":"string"},"at":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}},"delete":{"tags":["Chats"],"summary":"Stop typing indicator","operationId":"stopTyping","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"200":{"description":"Typing stopped","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"state":{"type":"string"},"at":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/chats/{chatId}/read":{"post":{"tags":["Chats"],"summary":"Mark chat as read","description":"Sends a read receipt. Blooio channels only.","operationId":"markChatRead","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"200":{"description":"Marked read","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"read":{"type":"boolean"},"at":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/chats/{chatId}/contact-card":{"post":{"tags":["Chats"],"summary":"Share contact card","description":"Shares the sender's contact card into a chat. Blooio channels only.","operationId":"shareContactCard","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"200":{"description":"Shared","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"shared":{"type":"boolean"},"at":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"}}}},"/chats/{chatId}/polls":{"post":{"tags":["Polls"],"summary":"Send a poll","description":"Sends a native iMessage poll to a chat. Requires a title and 2+ options. Blooio channels only.","operationId":"sendPoll","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendPollRequest"}}}},"responses":{"201":{"description":"Poll queued","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Poll"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/chats/{chatId}/polls/{pollId}/vote":{"post":{"tags":["Polls"],"summary":"Vote on a poll","description":"Casts or toggles a vote by `option_index` (0-based) or `option` text. Blooio channels only.","operationId":"votePoll","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"name":"pollId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the poll, prefixed with `msg_` (a poll shares the id of its underlying message)."}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/VotePollRequest"}}}},"responses":{"200":{"description":"All votes toggled off","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/PollVoteResult"}}}}}},"201":{"description":"Vote recorded","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/PollVoteResult"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/chats/{chatId}/polls/{pollId}":{"get":{"tags":["Polls"],"summary":"Get poll results","operationId":"getPollResults","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"name":"pollId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the poll, prefixed with `msg_` (a poll shares the id of its underlying message)."}],"responses":{"200":{"description":"Poll results","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/PollResults"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/chats/{chatId}/background":{"get":{"tags":["Chats"],"summary":"Get chat background","description":"Reads the chat's background image (Blooio channels). Reads live from the device.","operationId":"getChatBackground","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"200":{"description":"Background info","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"has_background":{"type":"boolean"},"background_id":{"type":["string","null"]},"background_version":{"type":["integer","null"]},"background_url":{"type":["string","null"]}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"put":{"tags":["Chats"],"summary":"Set chat background","description":"Uploads a chat background image. Max 10MB; image/jpeg|png|gif|webp|heic|heif. Blooio channels only.","operationId":"setChatBackground","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"requestBody":{"required":true,"content":{"multipart/form-data":{"schema":{"type":"object","properties":{"background":{"type":"string","format":"binary"}},"required":["background"]}}}},"responses":{"200":{"description":"Background set","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"background_id":{"type":"string"},"background_url":{"type":["string","null"]}}}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"delete":{"tags":["Chats"],"summary":"Remove chat background","operationId":"removeChatBackground","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"200":{"description":"Background removed","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"chat_id":{"type":"string"},"removed":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/chats/{chatId}/messages":{"get":{"tags":["Messages"],"summary":"List chat messages","description":"Lists messages in a chat, newest first by default. Use `order=asc` for oldest first.","operationId":"listChatMessages","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"name":"order","in":"query","schema":{"type":"string","enum":["asc","desc"],"default":"desc"}},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of messages","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Message"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"post":{"tags":["Messages"],"summary":"Send a message to a chat","description":"Sends a message into an existing chat (channel is inferred from the chat). Returns the message object at the top level (not wrapped in `data`).","operationId":"sendMessageToChat","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"$ref":"#/components/parameters/IdempotencyKeyHeader"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendToChatRequest"}}}},"responses":{"200":{"description":"Dry-run preview","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MessageSendResult"}}}},"201":{"description":"Message accepted. The message object is returned with its current `status`; a synchronously rejected send returns `status: \"failed\"` with an `error` object (still 201, since the message was created).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MessageSendResult"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"},"422":{"$ref":"#/components/responses/UnprocessableEntity"},"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/messages":{"post":{"tags":["Messages"],"summary":"Send a message","description":"Sends a message to one or more recipients on a channel. Requires `channel_id`. Multiple recipients on a group-capable channel (blooio/whatsapp) form a single group thread; on other channels they fan out to individual sends (max 100). Returns the message object at the top level, or a fan-out summary `{ data, fan_out, sent, failed }`.","operationId":"sendMessage","parameters":[{"$ref":"#/components/parameters/IdempotencyKeyHeader"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SendMessageRequest"},"examples":{"text":{"summary":"Simple text","value":{"channel_id":"ch_018f7b2a-1c3d-7e4f-9a2b-0c1d2e3f4a5b","to":{"identifier":"+15551234567"},"content":{"type":"text","text":"Hello from Blooio!"}}},"media":{"summary":"Image attachment","value":{"channel_id":"ch_018f7b2a-1c3d-7e4f-9a2b-0c1d2e3f4a5b","to":{"identifier":"+15551234567"},"content":{"type":"media","attachments":["https://example.com/photo.jpg"],"caption":"Check this out"}}},"dry_run":{"summary":"Validate/route only","value":{"channel_id":"ch_018f7b2a-1c3d-7e4f-9a2b-0c1d2e3f4a5b","to":{"identifier":"+15551234567"},"content":{"type":"text","text":"Test"},"dry_run":true}}}}}},"responses":{"200":{"description":"Dry-run preview","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MessageSendResult"}}}},"201":{"description":"Message accepted. The message object is returned with its current `status`; a synchronously rejected send returns `status: \"failed\"` with an `error` object (still 201, since the message was created).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/MessageSendResult"}}}},"207":{"description":"Multi-recipient fan-out with mixed results (some recipients sent, some failed). See per-recipient items in `data`.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/FanOutResult"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"},"422":{"description":"Validation failed, or a multi-recipient fan-out in which every recipient failed (in which case the body is a `FanOutResult` rather than an error envelope).","content":{"application/json":{"schema":{"oneOf":[{"$ref":"#/components/schemas/Error"},{"$ref":"#/components/schemas/FanOutResult"}]}}}},"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/chats/{chatId}/messages/{messageId}":{"get":{"tags":["Messages"],"summary":"Get a message","operationId":"getChatMessage","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"$ref":"#/components/parameters/MessageIdParam"}],"responses":{"200":{"description":"A message","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Message"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/chats/{chatId}/messages/{messageId}/status":{"get":{"tags":["Messages"],"summary":"Get message status","description":"Lightweight delivery status of a message.","operationId":"getMessageStatus","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"$ref":"#/components/parameters/MessageIdParam"}],"responses":{"200":{"description":"Message status","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/MessageStatus"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/chats/{chatId}/messages/{messageId}/events":{"get":{"tags":["Messages"],"summary":"List message events","description":"Lifecycle events for a message (sent, delivered, read, reactions, ...).","operationId":"listMessageEvents","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"$ref":"#/components/parameters/MessageIdParam"},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"Message events","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/MessageEvent"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/chats/{chatId}/messages/{messageId}/reactions":{"post":{"tags":["Messages"],"summary":"React to a message","description":"Adds or removes a tapback reaction. Use a `+` prefix to add and `-` to remove (e.g. `+love`, `-love`). Blooio channels only.","operationId":"addReaction","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"$ref":"#/components/parameters/MessageIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"reaction":{"type":"string","description":"e.g. '+love' to add, '-love' to remove.","examples":["+love","+like","+laugh","+emphasize","+question","+dislike"]}},"required":["reaction"]}}}},"responses":{"200":{"description":"Reaction applied","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"message_id":{"type":"string"},"reaction":{"type":"string"},"at":{"type":"integer"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"409":{"$ref":"#/components/responses/Conflict"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/webhooks":{"get":{"tags":["Webhooks"],"summary":"List webhooks","operationId":"listWebhooks","parameters":[{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of webhooks","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Webhook"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["Webhooks"],"summary":"Create a webhook","description":"Subscribes an HTTPS endpoint to events. Returns the signing secret once, on creation.","operationId":"createWebhook","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/CreateWebhookRequest"}}}},"responses":{"201":{"description":"Created webhook (includes signing_secret once)","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/WebhookWithSecret"}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}}},"/webhooks/{webhookId}":{"get":{"tags":["Webhooks"],"summary":"Get a webhook","operationId":"getWebhook","parameters":[{"$ref":"#/components/parameters/WebhookIdParam"}],"responses":{"200":{"description":"A webhook","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Webhook"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}},"patch":{"tags":["Webhooks"],"summary":"Update a webhook","description":"Updates url, event_types, or status (`active`/`disabled`).","operationId":"updateWebhook","parameters":[{"$ref":"#/components/parameters/WebhookIdParam"}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UpdateWebhookRequest"}}}},"responses":{"200":{"description":"Updated webhook","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Webhook"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"},"422":{"$ref":"#/components/responses/UnprocessableEntity"}}},"delete":{"tags":["Webhooks"],"summary":"Delete a webhook","operationId":"deleteWebhook","parameters":[{"$ref":"#/components/parameters/WebhookIdParam"}],"responses":{"200":{"description":"Deleted","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"deleted":{"type":"boolean"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/webhooks/{webhookId}/secret/rotate":{"post":{"tags":["Webhooks"],"summary":"Rotate webhook signing secret","description":"Rotates and returns a new signing secret (once).","operationId":"rotateWebhookSecret","parameters":[{"$ref":"#/components/parameters/WebhookIdParam"}],"responses":{"200":{"description":"New secret","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"signing_secret":{"type":"string"}}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/webhooks/{webhookId}/deliveries":{"get":{"tags":["Webhooks"],"summary":"List webhook deliveries","description":"Recent delivery attempts for a webhook. Also available at `/webhooks/{webhookId}/logs`.","operationId":"listWebhookDeliveries","parameters":[{"$ref":"#/components/parameters/WebhookIdParam"},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of deliveries","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/WebhookDelivery"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/webhooks/{webhookId}/deliveries/{deliveryId}/replay":{"post":{"tags":["Webhooks"],"summary":"Replay a webhook delivery","description":"Re-sends a past delivery. Also available at `/webhooks/{webhookId}/logs/{deliveryId}/replay`.","operationId":"replayWebhookDelivery","parameters":[{"$ref":"#/components/parameters/WebhookIdParam"},{"name":"deliveryId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the webhook delivery attempt, prefixed with `wdel_`. Returned by the List webhook deliveries endpoint."}],"responses":{"201":{"description":"Replay queued","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"object","properties":{"id":{"type":"string"},"replay_of":{"type":"string"},"status":{"type":"string"}}}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/events":{"get":{"tags":["Events"],"summary":"List events","description":"Unified activity feed (message lifecycle, polls, groups, reactions, typing). Filter by type, chat, or message.","operationId":"listEvents","parameters":[{"name":"type","in":"query","schema":{"type":"string"},"description":"Event type or wildcard, e.g. `message.received` or `message.*`."},{"name":"chat_id","in":"query","schema":{"type":"string"}},{"name":"message_id","in":"query","schema":{"type":"string"}},{"$ref":"#/components/parameters/LimitParam"},{"$ref":"#/components/parameters/CursorParam"}],"responses":{"200":{"description":"A page of events","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/Event"}},"has_more":{"type":"boolean"},"next_cursor":{"type":["string","null"]}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/events/{eventId}":{"get":{"tags":["Events"],"summary":"Get an event","operationId":"getEvent","parameters":[{"name":"eventId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the event, prefixed with `evt_`. Returned by the List events endpoint."}],"responses":{"200":{"description":"An event","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"$ref":"#/components/schemas/Event"}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/phone-numbers/lookup":{"get":{"tags":["Phone Numbers"],"summary":"Look up a phone number","description":"Returns parsed info / geocoding for a phone number. Requires an enterprise plan.","operationId":"lookupPhoneNumber","parameters":[{"name":"number","in":"query","required":true,"schema":{"type":"string"},"description":"Phone number in E.164."}],"responses":{"200":{"description":"Lookup result","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}},"post":{"tags":["Phone Numbers"],"summary":"Look up a phone number (POST)","description":"Same as the GET form, accepting the number in a JSON body. Returns parsed info / geocoding for a phone number. Requires an enterprise plan.","operationId":"lookupPhoneNumberPost","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"number":{"type":"string","description":"Phone number in E.164."}},"required":["number"]}}}},"responses":{"200":{"description":"Lookup result","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ItemEnvelope"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/phone-numbers/batch":{"post":{"tags":["Phone Numbers"],"summary":"Batch phone number lookup","description":"Looks up up to 100 phone numbers. Requires an enterprise plan.","operationId":"batchLookupPhoneNumbers","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"numbers":{"type":"array","items":{"type":"string"},"maxItems":100}},"required":["numbers"]}}}},"responses":{"200":{"description":"Lookup results","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"type":"array","items":{"type":"object","additionalProperties":true}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"403":{"$ref":"#/components/responses/Forbidden"}}}},"/chats/{chatId}/participants":{"get":{"tags":["Chats"],"summary":"List chat participants","operationId":"listChatParticipants","x-blooio-status":"planned","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}},"post":{"tags":["Chats"],"summary":"Add a chat participant","operationId":"addChatParticipant","x-blooio-status":"planned","parameters":[{"$ref":"#/components/parameters/ChatIdParam"}],"responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/chats/{chatId}/participants/{identityId}":{"delete":{"tags":["Chats"],"summary":"Remove a chat participant","operationId":"removeChatParticipant","x-blooio-status":"planned","parameters":[{"$ref":"#/components/parameters/ChatIdParam"},{"name":"identityId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the contact identity, prefixed with `cid_`. Returned by the List contact identities endpoint."}],"responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/attachments":{"post":{"tags":["Messages"],"summary":"Register an attachment","operationId":"createAttachment","x-blooio-status":"planned","responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/attachments/{attachmentId}":{"get":{"tags":["Messages"],"summary":"Get an attachment","operationId":"getAttachment","x-blooio-status":"planned","parameters":[{"name":"attachmentId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the attachment, as referenced on a message's content."}],"responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/templates":{"get":{"tags":["Messages"],"summary":"List templates","operationId":"listTemplates","x-blooio-status":"planned","responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}},"post":{"tags":["Messages"],"summary":"Create a template","operationId":"createTemplate","x-blooio-status":"planned","responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}}},"/templates/{templateId}":{"get":{"tags":["Messages"],"summary":"Get a template","operationId":"getTemplate","x-blooio-status":"planned","parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the message template. Returned when you create a template or by the List templates endpoint."}],"responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}},"delete":{"tags":["Messages"],"summary":"Delete a template","operationId":"deleteTemplate","x-blooio-status":"planned","parameters":[{"name":"templateId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the message template. Returned when you create a template or by the List templates endpoint."}],"responses":{"501":{"$ref":"#/components/responses/NotImplemented"}}}}},"components":{"securitySchemes":{"BearerApiKey":{"type":"http","scheme":"bearer","description":"Blooio API key as a bearer token, e.g. `Authorization: Bearer bl_live_...`."}},"parameters":{"LimitParam":{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":200,"default":50},"description":"Maximum number of items to return per page. Must be between 1 and 200; defaults to 50. Combine with `cursor` to paginate."},"CursorParam":{"name":"cursor","in":"query","required":false,"schema":{"type":"string"},"description":"Opaque pagination cursor. Pass the `next_cursor` value from a previous response to fetch the next page; omit it on the first request."},"IdempotencyKeyHeader":{"name":"Idempotency-Key","in":"header","required":false,"schema":{"type":"string"},"description":"Optional key for safe retries. Replaying the same key with an identical body returns the original result; a different body returns 409. Use a unique value (such as a UUID) per logical request."},"ChannelIdParam":{"name":"channelId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the channel (the sending surface), prefixed with `ch_`. Returned by the List channels endpoint."},"ContactIdParam":{"name":"contactId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the contact, prefixed with `ct_`. Returned when you create a contact or by the List contacts endpoint."},"ChatIdParam":{"name":"chatId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the chat, prefixed with `chat_`. Returned by the List chats endpoint."},"MessageIdParam":{"name":"messageId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the message, prefixed with `msg_`. Returned when you send a message or by the List messages endpoint."},"GroupIdParam":{"name":"groupId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the group, prefixed with `grp_`. Returned by the List groups endpoint."},"WebhookIdParam":{"name":"webhookId","in":"path","required":true,"schema":{"type":"string"},"description":"Unique identifier of the webhook subscription, prefixed with `wh_`. Returned when you create a webhook or by the List webhooks endpoint."},"NumberParam":{"name":"number","in":"path","required":true,"schema":{"type":"string"},"description":"Sender phone number in E.164 format, e.g. `+15551234567`."}},"responses":{"Unauthorized":{"description":"Authentication failed or missing.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthError"}}}},"Forbidden":{"description":"Authenticated but not allowed (e.g. blocked key or plan gate).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthError"}}}},"BadRequest":{"description":"Malformed request.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"NotFound":{"description":"Resource not found.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"Conflict":{"description":"Conflicting state (e.g. chat closed, idempotency reuse, channel not active).","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"UnprocessableEntity":{"description":"Validation failed.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"NotImplemented":{"description":"Endpoint is defined but not implemented yet.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"},"example":{"error":{"code":"not_implemented","message":"This v4 endpoint is defined but not implemented yet.","details":{"resource":"templates.list"}}}}}}},"schemas":{"Error":{"type":"object","description":"Standard v4 error envelope returned by route handlers.","properties":{"error":{"type":"object","properties":{"code":{"type":"string","description":"Machine-readable error code."},"message":{"type":"string"},"details":{"type":"object","additionalProperties":true}},"required":["code","message"]}},"required":["error"]},"AuthError":{"type":"object","description":"Flat error shape returned by the authentication middleware (401/403).","properties":{"error":{"type":"string"},"message":{"type":"string"},"status":{"type":"integer"},"code":{"type":"string"}}},"ItemEnvelope":{"type":"object","description":"Generic single-item envelope.","properties":{"data":{"type":"object","additionalProperties":true}}},"ChannelType":{"type":"string","enum":["blooio","twilio","whatsapp","whatsapp_business","rcs_business","amb"]},"ChannelStatus":{"type":"string","enum":["pending_verification","active","suspended","banned","deprecated"]},"ChatState":{"type":"string","enum":["open","closed","blocked","deprecated"]},"Direction":{"type":"string","enum":["inbound","outbound"]},"ChannelCapabilities":{"type":"object","description":"What a channel can do. Shape varies by channel type.","properties":{"protocols":{"type":"array","items":{"type":"string"}},"content":{"type":"array","items":{"type":"string"}},"actions":{"type":"array","items":{"type":"string"}},"interactive":{"type":"array","items":{"type":"string"}},"gates":{"type":"array","items":{"type":"string"}}},"additionalProperties":true},"Channel":{"type":"object","properties":{"id":{"type":"string","description":"Channel id (ch_...)."},"type":{"$ref":"#/components/schemas/ChannelType"},"display_address":{"type":["string","null"],"description":"Human-readable sender address."},"status":{"$ref":"#/components/schemas/ChannelStatus"},"capabilities":{"$ref":"#/components/schemas/ChannelCapabilities"},"created_at":{"type":"integer","description":"Epoch milliseconds."}}},"ContactIdentity":{"type":"object","properties":{"id":{"type":"string","description":"Identity id (cid_...)."},"contact_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"identifier":{"type":"string","description":"Phone (E.164) or email."},"channel_id":{"type":["string","null"],"description":"Required for AMB identities."},"created_at":{"type":"integer"}}},"Contact":{"type":"object","properties":{"id":{"type":"string","description":"Contact id (ct_...)."},"name":{"type":["string","null"]},"created_at":{"type":"integer"},"identities":{"type":"array","items":{"type":"object","properties":{"id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"identifier":{"type":"string"},"channel_id":{"type":["string","null"]},"created_at":{"type":"integer"}}}}}},"Chat":{"type":"object","properties":{"id":{"type":"string","description":"Chat id (chat_...)."},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"contact_id":{"type":["string","null"]},"identity_id":{"type":["string","null"]},"group_id":{"type":["string","null"]},"state":{"$ref":"#/components/schemas/ChatState"},"capabilities":{"type":"object","additionalProperties":true},"window_expires_at":{"type":["integer","null"]},"last_message_at":{"type":["integer","null"]},"created_at":{"type":"integer"}}},"ChatCreated":{"type":"object","properties":{"id":{"type":"string"},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"contact_id":{"type":["string","null"]},"identity_id":{"type":["string","null"]},"state":{"$ref":"#/components/schemas/ChatState"},"created":{"type":"boolean","description":"True if the chat was newly created."}}},"Message":{"type":"object","properties":{"id":{"type":"string","description":"Message id (msg_...)."},"chat_id":{"type":"string"},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"protocol":{"type":["string","null"],"description":"Resolved transport, e.g. imessage, sms."},"direction":{"$ref":"#/components/schemas/Direction"},"type":{"type":"string","description":"Content type, e.g. text, media, poll."},"text":{"type":["string","null"]},"status":{"type":"string","description":"queued, sent, delivered, read, failed, ..."},"provider_message_id":{"type":["string","null"]},"reply_to_message_id":{"type":["string","null"]},"error":{"type":["object","null"],"additionalProperties":true},"created_at":{"type":"integer"},"updated_at":{"type":"integer"}}},"MessageStatus":{"type":"object","properties":{"id":{"type":"string"},"status":{"type":"string"},"protocol":{"type":["string","null"]},"error":{"type":["object","null"],"additionalProperties":true},"created_at":{"type":"integer"},"updated_at":{"type":"integer"}}},"MessageEvent":{"type":"object","properties":{"id":{"type":"string","description":"Event id (evt_...)."},"message_id":{"type":"string"},"kind":{"type":"string","description":"Bare lifecycle kind, e.g. sent, delivered, read, reaction."},"occurred_at":{"type":"integer"},"metadata":{"type":"object","additionalProperties":true}}},"MessageSendResult":{"type":"object","description":"Returned at the top level (not wrapped in `data`) by send endpoints.","properties":{"id":{"type":"string"},"chat_id":{"type":"string"},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"protocol":{"type":["string","null"]},"direction":{"$ref":"#/components/schemas/Direction"},"type":{"type":"string"},"status":{"type":"string"},"error":{"type":["object","null"],"additionalProperties":true},"fallback":{"type":"object","description":"Present when a send could not be delivered on the requested channel and a different channel should be tried.","properties":{"recommended":{"type":"boolean","description":"True when falling back to another channel is recommended."},"reason":{"type":"string"}}},"to":{"type":"string","description":"Recipient identifier. Present only on per-recipient items inside a fan-out (FanOutResult) response."},"dry_run":{"type":"boolean"},"would_send":{"type":"boolean"},"preview":{"type":"object","additionalProperties":true}}},"FanOutResult":{"type":"object","description":"Returned when a multi-recipient send fans out to individual sends.","properties":{"data":{"type":"array","items":{"$ref":"#/components/schemas/MessageSendResult"}},"fan_out":{"type":"boolean"},"sent":{"type":"integer"},"failed":{"type":"integer"},"dry_run":{"type":"boolean"}}},"Group":{"type":"object","properties":{"id":{"type":"string","description":"Group id (grp_...)."},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"name":{"type":["string","null"]},"icon_url":{"type":["string","null"]},"chat_id":{"type":["string","null"]},"chat_linked":{"type":"boolean","description":"Whether the group is linked to a device chat."},"created_at":{"type":"integer"},"members":{"type":"array","items":{"$ref":"#/components/schemas/GroupMember"}}}},"GroupMember":{"type":"object","properties":{"identity_id":{"type":"string"},"contact_id":{"type":["string","null"]},"role":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"identifier":{"type":"string"}}},"Webhook":{"type":"object","properties":{"id":{"type":"string","description":"Webhook id (wh_...)."},"url":{"type":"string","format":"uri"},"event_types":{"type":"array","items":{"type":"string"}},"status":{"type":"string","enum":["active","disabled"]},"channel_id":{"type":["string","null"]},"channel_type":{"type":["string","null"]},"created_at":{"type":"integer"}}},"WebhookWithSecret":{"allOf":[{"$ref":"#/components/schemas/Webhook"},{"type":"object","properties":{"signing_secret":{"type":"string","description":"Returned once, on creation. Store it to verify signatures."}}}]},"WebhookDelivery":{"type":"object","properties":{"id":{"type":"string","description":"Delivery id (wdel_...)."},"webhook_id":{"type":"string"},"event_id":{"type":"string"},"event_type":{"type":"string"},"status":{"type":"string"},"attempt_count":{"type":"integer"},"response_status":{"type":["integer","null"]},"last_attempt_at":{"type":["integer","null"]},"next_attempt_at":{"type":["integer","null"]},"created_at":{"type":"integer"}}},"Event":{"type":"object","properties":{"id":{"type":"string","description":"Event id (evt_...)."},"type":{"type":"string","description":"e.g. message.delivered, poll.voted."},"message_id":{"type":["string","null"]},"chat_id":{"type":["string","null"]},"channel_type":{"type":["string","null"]},"occurred_at":{"type":"integer"},"data":{"type":"object","additionalProperties":true}}},"Poll":{"type":"object","properties":{"id":{"type":"string"},"chat_id":{"type":"string"},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"type":{"type":"string","enum":["poll"]},"status":{"type":"string"},"poll":{"type":"object","properties":{"title":{"type":"string"},"options":{"type":"array","items":{"type":"string"}}}}}},"PollVoteResult":{"type":"object","properties":{"id":{"type":"string"},"poll_id":{"type":"string"},"voted_option":{"type":"string"},"toggled":{"type":"string","enum":["on","off"]},"active_votes":{"type":"array","items":{"type":"string"}},"active_vote_indices":{"type":"array","items":{"type":"integer"}}}},"PollResults":{"type":"object","properties":{"poll_id":{"type":"string"},"chat_id":{"type":"string"},"title":{"type":"string"},"options":{"type":"array","items":{"type":"object","properties":{"text":{"type":"string"},"votes":{"type":"integer"}}}},"total_votes":{"type":"integer"}}},"LinkPreview":{"type":"object","properties":{"imageUrl":{"type":"string","format":"uri"},"title":{"type":"string"}}},"TextContent":{"type":"object","properties":{"type":{"type":"string","const":"text"},"text":{"type":"string"},"reply_to":{"type":"string","description":"Message id to reply to."},"effect":{"type":"string","description":"iMessage screen/bubble effect (Blooio)."},"link_preview":{"$ref":"#/components/schemas/LinkPreview"}},"required":["type","text"]},"MediaContent":{"type":"object","properties":{"type":{"type":"string","const":"media"},"attachments":{"type":"array","items":{"type":"string","format":"uri"},"description":"Public https URLs.","minItems":1},"caption":{"type":"string"}},"required":["type","attachments"]},"MultipartContent":{"type":"object","description":"Ordered text/media parts (Blooio only).","properties":{"type":{"type":"string","const":"multipart"},"parts":{"type":"array","items":{"type":"object","properties":{"text":{"type":"string"},"url":{"type":"string","format":"uri"}}},"minItems":1}},"required":["type","parts"]},"RichLinkContent":{"type":"object","properties":{"type":{"type":"string","const":"rich_link"},"url":{"type":"string","format":"uri"},"title":{"type":"string"}},"required":["type","url"]},"InteractiveContent":{"type":"object","description":"Interactive content (AMB / WhatsApp Business / RCS).","properties":{"type":{"type":"string","const":"interactive"},"kind":{"type":"string"}},"required":["type","kind"]},"InvitationContent":{"type":"object","description":"Invitation content (AMB).","properties":{"type":{"type":"string","const":"invitation"},"template_id":{"type":"string"}},"required":["type","template_id"]},"MessageContent":{"oneOf":[{"$ref":"#/components/schemas/TextContent"},{"$ref":"#/components/schemas/MediaContent"},{"$ref":"#/components/schemas/MultipartContent"},{"$ref":"#/components/schemas/RichLinkContent"},{"$ref":"#/components/schemas/InteractiveContent"},{"$ref":"#/components/schemas/InvitationContent"}],"discriminator":{"propertyName":"type","mapping":{"text":"#/components/schemas/TextContent","media":"#/components/schemas/MediaContent","multipart":"#/components/schemas/MultipartContent","rich_link":"#/components/schemas/RichLinkContent","interactive":"#/components/schemas/InteractiveContent","invitation":"#/components/schemas/InvitationContent"}}},"Recipient":{"description":"A single recipient, a list, or a comma-separated string of identifiers.","oneOf":[{"type":"object","properties":{"identifier":{"type":"string"}},"required":["identifier"]},{"type":"object","properties":{"identifiers":{"type":"array","items":{"type":"string"}}},"required":["identifiers"]},{"type":"array","items":{"type":"string"}},{"type":"string"}]},"SendMessageRequest":{"type":"object","properties":{"channel_id":{"type":"string","description":"Channel id (ch_...) to send from."},"to":{"$ref":"#/components/schemas/Recipient"},"content":{"$ref":"#/components/schemas/MessageContent"},"dry_run":{"type":"boolean","description":"Validate and route only; do not send."}},"required":["channel_id","to","content"]},"SendToChatRequest":{"type":"object","properties":{"content":{"$ref":"#/components/schemas/MessageContent"},"dry_run":{"type":"boolean"}},"required":["content"]},"CreateChatRequest":{"type":"object","properties":{"channel_id":{"type":"string"},"to":{"type":"object","properties":{"identifier":{"type":"string"}},"required":["identifier"]}},"required":["channel_id","to"]},"CreateContactRequest":{"type":"object","properties":{"name":{"type":"string"},"identifier":{"type":"string","description":"Phone (E.164) or email to attach as the first identity."},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"channel_id":{"type":"string","description":"Required when channel_type is amb."}}},"AttachIdentityRequest":{"type":"object","properties":{"identifier":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"},"channel_id":{"type":"string","description":"Required when channel_type is amb."}},"required":["identifier"]},"CreateGroupRequest":{"type":"object","properties":{"channel_id":{"type":"string","description":"Must be a group-capable channel (blooio/whatsapp)."},"members":{"type":"array","items":{"oneOf":[{"type":"string"},{"type":"object","properties":{"identifier":{"type":"string"}},"required":["identifier"]}]},"minItems":1,"description":"Member phone numbers (E.164) or emails, each given as a string or an object `{ \"identifier\": \"...\" }`."},"name":{"type":"string"}},"required":["channel_id","members"]},"SendPollRequest":{"type":"object","properties":{"title":{"type":"string"},"options":{"type":"array","items":{"type":"string"},"minItems":2}},"required":["title","options"]},"VotePollRequest":{"type":"object","description":"Provide option_index (0-based) or option text.","properties":{"option_index":{"type":"integer","description":"0-based option index."},"option":{"type":"string","description":"Option text."}}},"CreateWebhookRequest":{"type":"object","properties":{"url":{"type":"string","format":"uri","description":"HTTPS endpoint."},"event_types":{"type":"array","items":{"type":"string"},"description":"Subscription tokens: exact event types (e.g. `message.delivered`), category wildcards (`message.*`, `poll.*`, `group.*`, `typing.*`), `*` for everything, or the legacy v2 coarse buckets `all`, `message`, and `status` (expanded server-side for parity). Defaults to ['*']."},"channel_id":{"type":"string"},"channel_type":{"$ref":"#/components/schemas/ChannelType"}},"required":["url"]},"UpdateWebhookRequest":{"type":"object","properties":{"url":{"type":"string","format":"uri"},"event_types":{"type":"array","items":{"type":"string"}},"status":{"type":"string","enum":["active","disabled"]}}}}},"x-blooio-webhook-event-types":["message.received","message.queued","message.pending","message.sent","message.delivered","message.failed","message.read","message.reaction","poll.created","poll.received","poll.voted","group.name_changed","group.icon_changed","contact.shared","typing.started","typing.stopped"],"x-blooio-endpoints":["DELETE /v4/chats/:chatId/background","DELETE /v4/chats/:chatId/participants/:identityId","DELETE /v4/chats/:chatId/typing","DELETE /v4/contacts/:contactId","DELETE /v4/contacts/:contactId/identities/:identityId","DELETE /v4/contacts/:contactId/tags/:tag","DELETE /v4/groups/:groupId","DELETE /v4/groups/:groupId/icon","DELETE /v4/templates/:templateId","DELETE /v4/webhooks/:webhookId","GET /v4/attachments/:attachmentId","GET /v4/channels","GET /v4/channels/:channelId","GET /v4/channels/:channelId/capabilities","GET /v4/chats","GET /v4/chats/:chatId","GET /v4/chats/:chatId/background","GET /v4/chats/:chatId/messages","GET /v4/chats/:chatId/messages/:messageId","GET /v4/chats/:chatId/messages/:messageId/events","GET /v4/chats/:chatId/messages/:messageId/status","GET /v4/chats/:chatId/participants","GET /v4/chats/:chatId/polls/:pollId","GET /v4/contacts","GET /v4/contacts/:contactId","GET /v4/contacts/:contactId/capabilities","GET /v4/contacts/:contactId/identities","GET /v4/contacts/:contactId/tags","GET /v4/contacts/:contactId/timeline","GET /v4/events","GET /v4/events/:eventId","GET /v4/groups","GET /v4/groups/:groupId","GET /v4/groups/:groupId/members","GET /v4/location/contacts","GET /v4/location/contacts/:handle","GET /v4/location/contacts/refresh","GET /v4/me","GET /v4/me/numbers","GET /v4/me/numbers/:number/contact-card","GET /v4/phone-numbers/lookup","GET /v4/templates","GET /v4/templates/:templateId","GET /v4/webhooks","GET /v4/webhooks/:webhookId","GET /v4/webhooks/:webhookId/deliveries","GET /v4/webhooks/:webhookId/logs","PATCH /v4/chats/:chatId","PATCH /v4/contacts/:contactId","PATCH /v4/groups/:groupId","PATCH /v4/webhooks/:webhookId","POST /v4/attachments","POST /v4/chats","POST /v4/chats/:chatId/contact-card","POST /v4/chats/:chatId/messages","POST /v4/chats/:chatId/messages/:messageId/reactions","POST /v4/chats/:chatId/participants","POST /v4/chats/:chatId/polls","POST /v4/chats/:chatId/polls/:pollId/vote","POST /v4/chats/:chatId/read","POST /v4/chats/:chatId/typing","POST /v4/contacts","POST /v4/contacts/:contactId/identities","POST /v4/contacts/:contactId/tags","POST /v4/groups","POST /v4/groups/:groupId/icon","POST /v4/location/contacts/refresh","POST /v4/me/numbers/:number/call-forwarding","POST /v4/me/numbers/:number/contact-card/avatar","POST /v4/messages","POST /v4/phone-numbers/batch","POST /v4/phone-numbers/lookup","POST /v4/templates","POST /v4/webhooks","POST /v4/webhooks/:webhookId/deliveries/:deliveryId/replay","POST /v4/webhooks/:webhookId/logs/:deliveryId/replay","POST /v4/webhooks/:webhookId/secret/rotate","PUT /v4/channels/:channelId/profile","PUT /v4/chats/:chatId/background","PUT /v4/me/numbers/:number/contact-card"]}