Skip to main content

Quickstart

This page walks you through the fastest possible integration smoke test: register your system as a producer in the Kudos CRM operator console, copy the issued signing secret, sign a webhook.ping event, and POST it. You will know the integration is wire-correct when the operator console shows your event in the inbound stream.

The whole path is browser + one HTTP request. No SDK, no library, no toolchain.

1. Register a source in the CRM​

The Register integration source dialog — name, producer, sync base URL, sync API key, and the allowed event types.

A Kudos CRM operator with the admin role goes through this once per producer system.

  1. Open the operator console

    Sign in at https://app.kudoscrm.com and open Integrations → Inbound sources (direct path /integrations/sources).

  2. Register

    Click Register source. Fill in:

    • Name — internal label, e.g. Kudos Billing Production.
    • Producer — your system name, e.g. Kudos.
    • Sync base URL — https://api.your-system.example/api/v1 (skip if you are not implementing the pull channel yet).
    • Allowed event types — keep the default (all 36) or narrow down.
  3. Copy the signing secret

    A modal appears with the signing secret cleartext. This is the only time it will be displayed. Click Reveal, then Copy, then tick I have stored this credential securely, then Done.

  4. Note the source_id

    The new source row shows a src_… identifier. Copy it — it is part of your delivery URL.

You now have:

  • source_id — looks like src_AbCdEf0123456789abcdef01. Public-ish — not a credential, but unguessable.
  • signing_secret — looks like whsec_…. Treat like a database password. Store in your secret manager.

2. Sign and send your first event​

Kudos CRM requires every webhook to carry an HMAC signature over the raw request body plus a unix timestamp. The header format is identical to Stripe's:

X-Kudos-Signature: t=<unix_seconds>,v1=<hex_hmac>

Pick a language and run the snippet. Substitute the placeholders:

BODY='{"schema_version":1,"event_id":"evt_'"$(uuidgen | tr -d - | head -c 25)"'","event_type":"webhook.ping","fired_at":"'"$(date -u +%Y-%m-%dT%H:%M:%SZ)"'","producer":{"name":"kudos","version":"1.0.0"},"tenant":null,"data":{"hello":"world"}}'
TS=$(date +%s)
SECRET='whsec_REPLACE_ME'
SIG=$(printf '%s.%s' "$TS" "$BODY" | openssl dgst -sha256 -hmac "$SECRET" | sed 's/^.* //')
curl -sS -X POST \
-H "Content-Type: application/json" \
-H "User-Agent: Kudos-Webhook/1.0.0 (+https://kudos.example)" \
-H "X-Kudos-Signature: t=$TS,v1=$SIG" \
-H "X-Kudos-Event-Id: $(echo "$BODY" | python3 -c 'import json,sys;print(json.load(sys.stdin)["event_id"])')" \
-H "X-Kudos-Event-Type: webhook.ping" \
-H "X-Kudos-Schema-Version: 1" \
-H "X-Kudos-Delivery-Attempt: 1" \
-d "$BODY" \
https://api.kudoscrm.com/api/v1/ingest/webhooks/src_REPLACE_ME/events

A successful POST returns 202 Accepted with a small JSON envelope:

{ "data": { "received": true, "event_id": "evt_…", "duplicate": false } }

duplicate: true is returned when you replay an event_id Kudos CRM has already processed — that is intentional, not an error. The integration is idempotent on event_id. Always retry on 5xx; never invent new event_ids when retrying.

3. Verify in the operator console​

The CRM operator can verify the event arrived by:

  1. Navigating to Integrations → Inbound sources.
  2. Clicking the row → Last event updates to "a few seconds ago".
  3. The inbound-events drawer lists the webhook.ping event with status processed.

Where to go next​