Skip to content

Webhooks

Instead of polling the API for changes, register a webhook endpoint and GrowthOS will push events to you in real time. Every state change in the platform — a new contact, a referral conversion, an email bounce — fires an event that can be delivered to your HTTPS endpoint.

Async Delivery

Events are delivered asynchronously. Your users never wait on your webhook endpoint — GrowthOS fires and continues.

At-Least-Once Guarantee

Every event is delivered at least once. In rare cases (network hiccups, retries), you may receive a duplicate — use the idempotency_key to deduplicate.

Idempotency Keys

Every webhook payload includes a unique idempotency_key. Store it and check for duplicates before processing to ensure safe at-least-once delivery.

Full Observability

Every delivery attempt is logged in the dashboard with status code, latency, and response body. Replay any event with one click.


GrowthOS emits events across every domain in the platform. Subscribe to specific event types or use wildcard patterns (e.g. referral.*) to catch all events in a domain.

EventDescription
contact.createdNew contact identified via Ingest API or integration
contact.updatedOne or more contact traits changed
contact.mergedTwo contact records merged (includes both IDs)
contact.deletedContact soft-deleted (data retained for 30 days)
EventDescription
referral.link_createdNew referral link generated for a contact
referral.clickedReferral link clicked by a prospective user
referral.convertedReferred user completed the conversion action
referral.reward_issuedReward granted to the referrer
EventDescription
email.sentEmail dispatched to delivery provider
email.deliveredDelivery confirmed by recipient mail server
email.openedEmail opened (pixel-tracked)
email.clickedLink in email clicked
email.bouncedHard or soft bounce recorded
email.unsubscribedRecipient unsubscribed via link
email.complainedRecipient marked email as spam
EventDescription
survey.response_receivedSurvey response submitted
survey.nps_promoterNPS score of 9 or 10 received
survey.nps_detractorNPS score of 0 through 6 received
EventDescription
waitlist.entry_createdNew waitlist signup
waitlist.position_changedPosition moved (typically via referral bumps)
waitlist.entry_approvedEntry approved, invite sent to user
EventDescription
campaign.activatedCampaign started sending
campaign.completedAll sends in campaign complete
campaign.pausedCampaign paused by user or automation rule
EventDescription
billing.subscription_createdNew subscription started
billing.subscription_updatedPlan, quantity, or status changed
billing.payment_failedPayment attempt failed
billing.trial_expiringTrial period ending within 3 days

Every webhook delivery uses a standard envelope format regardless of event type. The data object varies per event, but the outer structure is always the same.

{
"id": "evt_abc123",
"type": "referral.converted",
"created_at": "2025-06-01T12:00:00Z",
"data": {
"referral_link_id": "rl_xyz",
"referrer_id": "usr_123",
"referred_id": "usr_456",
"program_id": "prog_001",
"reward": {
"type": "credit",
"amount": 20,
"currency": "USD"
}
},
"tenant_id": "tenant_abc",
"idempotency_key": "idk_unique123"
}
FieldTypeDescription
idstringUnique event ID (evt_ prefix)
typestringEvent type in domain.action format
created_atstringISO 8601 timestamp of when the event occurred
dataobjectEvent-specific payload (varies by type)
tenant_idstringYour tenant identifier
idempotency_keystringUnique key for deduplication (idk_ prefix)

GrowthOS uses exponential backoff to retry failed deliveries. Your endpoint must respond with a 2xx status code within 30 seconds or the attempt is considered failed.

  1. Attempt 1 — Immediate delivery
  2. Attempt 2 — 5 seconds after failure
  3. Attempt 3 — 30 seconds
  4. Attempt 4 — 2 minutes
  5. Attempt 5 — 15 minutes
  6. Attempt 6 — 1 hour
  7. Attempt 7 — 6 hours
  8. Final attempt — 24 hours

That is 7 retry attempts spanning approximately 31 hours total. After the final attempt, the event is marked as failed in the dashboard and you can manually replay it.

Your ResponseGrowthOS Behavior
2xxDelivery marked as successful
4xx (except 429)No retry — treated as a permanent rejection
429 Too Many RequestsRetried with backoff (respects Retry-After header)
5xxRetried with exponential backoff
Timeout (over 30s)Retried with exponential backoff
Connection refusedRetried with exponential backoff

Every webhook delivery is signed with your project’s webhook signing secret using HMAC-SHA256. Always verify the signature before processing the payload to ensure the request genuinely came from GrowthOS.

Three headers are included with every delivery:

HeaderDescription
X-GrowthOS-SignatureHMAC-SHA256 hex digest of the raw request body
X-GrowthOS-TimestampUnix timestamp of when the payload was signed
X-GrowthOS-Event-TypeThe event type (e.g. referral.converted)

To verify, concatenate the timestamp and the raw body with a . separator, then compute the HMAC-SHA256 using your webhook signing secret. Compare the result to the X-GrowthOS-Signature header value.


Respond Fast

Return 202 Accepted immediately, then process the event asynchronously in a background job or queue. Never do heavy processing inside the request handler.

Use Idempotency Keys

Store the idempotency_key from each payload. Before processing, check if you have already handled that key. This protects you from duplicate deliveries.

Verify Signatures

Always validate the X-GrowthOS-Signature header before trusting the payload. Without verification, an attacker could send fake events to your endpoint.

Monitor Webhook Logs

Use the Webhooks section of the GrowthOS dashboard to monitor delivery attempts, inspect payloads, view error responses, and replay failed events.

  1. Accept POST requests at a publicly reachable HTTPS URL.
  2. Verify the signature using your webhook signing secret.
  3. Check the timestamp to reject stale deliveries (over 5 minutes old).
  4. Deduplicate using the idempotency_key.
  5. Return 202 immediately — enqueue the event for async processing.
  6. Process the event in a background worker (e.g. Sidekiq, Celery, BullMQ).
  7. Log and alert on processing failures so you can investigate quickly.