UnifyPort Webhook Event Filters: subscribed_events or Wildcard?
Use explicit subscribed_events for a single-purpose production handler, and use ["*"] when the endpoint is a complete event collector or you are still discovering which events your workflow needs. The wildcard covers every public standard event, not internal raw events. For an inbound inbox, start with message.received and add account lifecycle events only if the same service owns connection health.
Key takeaways
subscribed_eventsaccepts exact public event names, or["*"]by itself for the full public catalogue.- Unknown event names are rejected when the endpoint is created or updated.
- Subscribing to an event does not mean every provider emits it; check the provider event matrix.
message.receivedcan describe inbound or outbound traffic, so inspectdata.message.direction.- Filtering, HMAC signing, acknowledgement, and retries are separate controls.
What subscribed_events controls
A UnifyPort webhook endpoint receives HTTP POST deliveries for the events selected in subscribed_events. The documented envelope always contains id, type, provider, account_id, occurred_at, and event-specific data. The standard event catalogue lists the accepted names and payload shapes.
The narrowest useful inbound subscription is:
{
"subscribed_events": ["message.received"]
}
That reduces unrelated account and receipt traffic, but the handler still needs this direction guard:
if (
event.type === 'message.received' &&
event.data?.message?.direction === 'inbound'
) {
await storeInboundMessage(event);
}
The event name means a message was observed on the connected messaging account. It is not an inbound-only promise.
The wildcard form is:
{
"subscribed_events": ["*"]
}
Use it as the complete selection rather than mixing "*" with named events. It includes all public standard events, while internal raw events remain unavailable.
Three practical event-filter patterns
1. Inbound inbox only
Choose this when one service stores and routes incoming customer messages:
{
"subscribed_events": ["message.received"]
}
Route only records whose data.message.direction is inbound. If the workflow later needs edits, deletions, reactions, or receipts, add those exact event names after defining how each will update stored state.
2. Inbound inbox plus account health
Choose this when the same service must also surface expired authorization or a disconnected runtime:
{
"subscribed_events": [
"message.received",
"account.status.updated",
"account.started",
"account.auth.required",
"account.auth.succeeded",
"account.auth.failed"
]
}
Do not treat every status event as an instruction to restart. Mirror auth_status and runtime_status, then reconcile the account before acting. The messaging account runtime recovery runbook explains when to refresh, reconnect, start, or reauthenticate.
3. Durable event collector
Choose ["*"] when the endpoint is your general event ingestion boundary and dispatch happens downstream. This works well when you want one signed queue for WhatsApp, Telegram, LINE, TikTok, Zalo, and X, while separate consumers process messages, receipts, groups, and account state.
A wildcard collector still needs explicit code for unknown future public event types. Store the envelope safely, acknowledge it, and route unsupported types to an observable dead-letter path instead of assuming every event is a message.
Create the endpoint with an explicit filter
The real API route is POST /v1/webhook-endpoints. This request creates an active signed endpoint for inbound messages and account health:
curl -X POST https://api.unifyport.ai/v1/webhook-endpoints \
-H "X-Api-Key: $UNIFYPORT_API_KEY" \
-H "Content-Type: application/json" \
-d "{
\"url\": \"https://inbox.example.com/webhooks/unifyport\",
\"status\": \"active\",
\"subscribed_events\": [
\"message.received\",
\"account.status.updated\",
\"account.auth.required\"
],
\"signing_secret\": \"$WEBHOOK_SIGNING_SECRET\",
\"retry_policy\": { \"max_attempts\": 3 }
}"
The Create webhook endpoint reference defines the request. retry_policy.max_attempts counts retries after the initial delivery: the documented default of 3 therefore allows the first request plus as many as three retries. Its valid range is 0 to 5.
To change the filter later, use the documented PATCH /v1/webhook-endpoints/{endpoint_id} route and send the revised subscribed_events. The same name validation applies to create and update.
Keep filtering separate from delivery security
An event filter decides what UnifyPort sends. A signing_secret decides whether deliveries carry X-Device-Timestamp and X-Device-Signature. When signing is enabled, verify the hex HMAC-SHA256 over the timestamp, a period, and the raw request body before parsing JSON.
Any 2xx response acknowledges a delivery. Connection errors and HTTP 408, 429, or 5xx responses are eligible for configured retries; other 4xx responses are not retried. Delivery is at least once, so ordinary event retries should be handled idempotently.
For the complete receiver implementation, use the webhook delivery and signature guide and the deeper HMAC replay protection and idempotency tutorial.
Check provider support before adding a name
The public catalogue defines valid event names, but provider parsers do not all map every event. message.received and key account events have broad coverage; events such as receipts, message edits, conversation changes, and group updates vary.
Before making a consumer depend on an event, check webhook event differences by provider. A valid subscription is a filter, not a guarantee that an upstream account will produce that event.
If you are building an automation workflow rather than a general collector, the n8n WhatsApp signed-webhook tutorial shows why verification and durable intake should sit before the AI workflow.
Limitations and trade-offs
Explicit filters reduce noise and make ownership clear, but they can omit a newly needed event until configuration is updated. The wildcard avoids that configuration gap, but consumers must tolerate more event types and future additions.
UnifyPort also has no general REST message-history read API or guaranteed replay for missed payloads. Register the receiver first and store required events on arrival. Limited WhatsApp history synchronization is continuity support, not a replacement for your event store.
UnifyPort is an unofficial interface. If you need an official platform certification path or a provider-specific capability outside the documented matrix, use the relevant official platform API instead.
FAQ
Should I use message.received or ["*"]?
Use message.received for a focused inbox handler. Use ["*"] for a general collector that stores and dispatches every public standard event.
Does message.received include only inbound messages?
No. Check data.message.direction and process inbound only when that is your workflow’s scope.
Can I subscribe to internal provider events?
No. subscribed_events accepts public standard names only, and the wildcard does not expose internal raw events.
What happens if I misspell an event name?
The create or update request rejects unknown event names instead of silently accepting a filter that never matches.
Does ["*"] guarantee every event from every provider?
No. It selects all public standard event types, but actual provider support and upstream availability still vary. Consult the provider event matrix.
Next step
Open the Create webhook endpoint reference, choose one of the three filters above, and register the receiver before connecting production messaging accounts.
Sources
Checked on August 19, 2026: