Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.nedzo.ai/llms.txt

Use this file to discover all available pages before exploring further.

Nedzo emits a set of platform lifecycle webhooks when key things happen on an account: a user signs up, finishes onboarding, a new workspace is created, a user is invited, or a subscription changes. These are separate from the Post-conversation webhook (which fires per conversation) and the Workflow webhook trigger (which sends data into Nedzo). Use these events to sync your CRM, send transactional emails on signup, or trigger downstream automations when teams grow.
Lifecycle webhooks are configured per environment by Nedzo for whitelabel and enterprise customers. If you’d like to receive these events on your own endpoint, contact support@nedzo.ai with the URL you want them delivered to.

Delivery semantics

  • Fire-and-forget. Nedzo sends the request but does not retry on failure. Failures are logged but never surfaced to the user-triggering action (e.g. signup is not blocked if your endpoint is down).
  • Timeout. The request is aborted if your server takes longer than 10 seconds to respond.
  • Auth header. When configured, Nedzo includes the shared token in an Auth header. Use it to verify the request source.
  • HTTPS only in production. Nedzo rejects non-HTTPS URLs and internal IPs/metadata endpoints (SSRF protection).
  • Order. Events are sent in the order the underlying actions occur, but no ordering guarantee across events of different types.

Common request shape

All lifecycle events are sent as POST with Content-Type: application/json. The body schema is event-specific (see below). UTM/referrer fields are truncated server-side: 255 chars max for source/medium/campaign/code, 2048 chars max for URLs.

Events

EventFires when
registration_startedA new user finishes the welcome-email step during signup, before onboarding completes. Top-of-funnel signal.
registration_completedA new user finishes onboarding (account + workspace + user record all created).
workspace_addedA workspace is created in an existing account (excludes the initial workspace from onboarding).
user_addedA user is invited and accepted into an existing account (excludes the initial owner from onboarding, and excludes restoring a soft-deleted user).
subscription_startedA paid subscription begins on an account.
subscription_cancelledA subscription is cancelled on an account.

registration_started

Fires when a new user is sent the welcome email — before they complete onboarding. Lacks account context for self-serve signups (no account row exists yet) but includes account_id when the user signs up under an existing whitelabel account. Payload:
FieldTypeDescription
user_first_namestringNew user’s first name.
user_last_namestringNew user’s last name.
user_emailstringNew user’s email.
user_phonestring | nullPhone if provided at signup.
user_signup_datestring (ISO date)Date the welcome email was sent (YYYY-MM-DD).
account_idstring (UUID) | nullAccount ID for whitelabel signups, null for self-serve.
user_referrer_codestring | nullReferral code captured at signup.
user_referrer_sourcestring | nullUTM source.
user_referrer_mediumstring | nullUTM medium.
user_referrer_campaignstring | nullUTM campaign.
user_referrer_urlstring | nullFull referrer URL.
Example:
{
  "user_first_name": "John",
  "user_last_name": "Doe",
  "user_email": "john@example.com",
  "user_phone": "+14155551234",
  "user_signup_date": "2026-04-25",
  "account_id": null,
  "user_referrer_code": "PARTNER42",
  "user_referrer_source": "google",
  "user_referrer_medium": "cpc",
  "user_referrer_campaign": "spring-2026",
  "user_referrer_url": "https://google.com/search?q=ai+voice+agent"
}

registration_completed

Fires when a user finishes onboarding — account, workspace, and user records all exist and the user has reached the dashboard. Includes full account context so downstream CRM sync can attribute the signup to the right account. Payload:
FieldTypeDescription
user_first_namestringUser’s first name.
user_last_namestringUser’s last name.
user_emailstringUser’s email.
user_phonestring | nullPhone if captured.
user_signup_datestring (ISO date)Date onboarding completed (YYYY-MM-DD).
account_idstring (UUID)Account the user belongs to.
user_idstring (UUID)User record ID.
account_namestring | nullAccount / company name set during onboarding.
planstring | nullSubscription plan selected during onboarding. Re-read from the persisted account record after Stripe writes complete; 'payg' for pay-as-you-go signups, null if no plan was persisted.
industrystring | nullIndustry selected during onboarding.
user_referrer_codestring | nullReferral code.
user_referrer_sourcestring | nullUTM source.
user_referrer_mediumstring | nullUTM medium.
user_referrer_campaignstring | nullUTM campaign.
user_referrer_urlstring | nullFull referrer URL.
Example:
{
  "user_first_name": "John",
  "user_last_name": "Doe",
  "user_email": "john@example.com",
  "user_phone": "+14155551234",
  "user_signup_date": "2026-04-25",
  "account_id": "a1b2c3d4-1111-2222-3333-444455556666",
  "user_id": "u1u2u3u4-aaaa-bbbb-cccc-ddddeeeeffff",
  "account_name": "Acme Co",
  "plan": "pro",
  "industry": "real_estate",
  "user_referrer_code": "PARTNER42",
  "user_referrer_source": "google",
  "user_referrer_medium": "cpc",
  "user_referrer_campaign": "spring-2026",
  "user_referrer_url": "https://google.com/search?q=ai+voice+agent"
}

workspace_added

Fires when a workspace is created on an existing account. Skipped for the initial workspace created during onboarding (that signal is implicit in registration_completed). Fires for workspaces created via the dashboard and via the public API. Payload:
FieldTypeDescription
account_idstring (UUID)Account that owns the workspace.
account_namestring | nullAccount name.
workspace_idstring (UUID)Workspace record ID.
workspace_namestring | nullWorkspace name as set by the user.
total_workspacesnumberTotal number of non-deleted workspaces on the account after this one was added.
Example:
{
  "account_id": "a1b2c3d4-1111-2222-3333-444455556666",
  "account_name": "Acme Co",
  "workspace_id": "w1w2w3w4-aaaa-bbbb-cccc-ddddeeeeffff",
  "workspace_name": "EU Operations",
  "total_workspaces": 3
}

user_added

Fires when a user is invited and added to an existing account. Skipped for the initial owner (covered by registration_completed) and for re-invites of soft-deleted users (the restored path) so team-size growth isn’t double-counted in the CRM. Payload:
FieldTypeDescription
account_idstring (UUID)Account the user joined.
account_namestring | nullAccount name.
user_idstring (UUID)New user record ID.
user_first_namestring | nullUser’s first name.
user_last_namestring | nullUser’s last name.
user_emailstringUser’s email.
user_phonestring | nullPhone if provided on the invite (optional field on the invite payload).
total_usersnumberTotal number of non-deleted users on the account after this one was added.
Example:
{
  "account_id": "a1b2c3d4-1111-2222-3333-444455556666",
  "account_name": "Acme Co",
  "user_id": "u9u8u7u6-aaaa-bbbb-cccc-ddddeeeeffff",
  "user_first_name": "Jane",
  "user_last_name": "Smith",
  "user_email": "jane@acme.com",
  "user_phone": "+14155559876",
  "total_users": 7
}

subscription_started

Fires when a paid subscription begins on an account. Payload:
FieldTypeDescription
user_first_namestring | nullAccount owner’s first name.
user_last_namestring | nullAccount owner’s last name.
user_emailstringAccount owner’s email.
user_phonestring | nullPhone.
user_signup_datestring (ISO date) | nullOwner’s signup date.
user_subscription_statusstringStripe subscription status (e.g. active, trialing).
user_subscription_start_datestring (ISO date)Subscription start date.
user_subscription_end_datestring (ISO date) | nullPeriod end if known.
user_subscription_plan_namestringPlan name.
user_subscription_plan_valuenumberMonthly plan price in dollars.
user_referrer_*string | nullUTM/referrer fields, same shape as registration.

subscription_cancelled

Fires when a subscription is cancelled. Same shape as subscription_started with user_subscription_status always set to "canceled" and any unknown fields nullable.

Verifying requests

When configured, Nedzo includes a shared token in the Auth header:
POST /your-webhook HTTP/1.1
Host: yourdomain.com
Content-Type: application/json
Auth: <shared-token>

{ ... payload ... }
Compare the header value against the token you provided to Nedzo. Reject any request that doesn’t match.