Set up a webhook endpoint

Add an endpoint, choose its events, keep the signing secret, send a test and write a receiver that answers quickly.

An endpoint is a URL on your server that Dialgem calls. You can have several, each with its own events, agents and secret.

Add an endpoint

In the dashboard, open Settings, Webhooks and choose Add endpoint.

  1. Enter your URL.
  2. Pick the events you want. Pick All events to receive every event, including ones added later.
  3. Optionally limit the endpoint to some agents.
  4. Save, and copy the signing secret.

The signing secret is shown in full once. Store it in your secrets manager straight away: afterwards the dashboard shows only the last four characters. If you lose it, use Rotate secret (see Verify signatures).

Public HTTPS only

Endpoint URLs must use https:// and point at a public address. Addresses on private networks, loopback, link-local and cloud-metadata ranges are refused, both when you save the URL and on every delivery. Redirects are not followed. For local development, expose your machine with a tunnelling tool and use that public HTTPS address.

Send a test

Choose Send a test event on the endpoint. Dialgem makes one signed webhook_test request to your URL and reports the status and timing. It never shows your server's response body. Use it to check your URL, your firewall and your signature code before real calls arrive.

An agent-level webhook

You can also set a webhook on a single agent. It keeps working alongside any endpoints. Use an endpoint when you want one place to receive events for many agents, and an agent webhook for something specific to that agent. Campaign events go to endpoints only.

Write a receiver

A good receiver does four things: reads the raw body, verifies the signature, stores the event, and answers 2xx fast.

import express from "express"
import { Dialgem } from "@dialgem/sdk"

const app = express()

// The raw bytes matter: the signature covers them exactly.
app.post("/dialgem/webhook", express.raw({ type: "application/json" }), async (req, res) => {
  let event
  try {
    event = await Dialgem.webhooks.constructEvent(
      req.body,
      req.headers["x-dialgem-signature"],
      process.env.DIALGEM_WEBHOOK_SECRET,
    )
  } catch {
    return res.sendStatus(400)
  }

  await queue.add({ deliveryId: req.headers["x-dialgem-delivery"], event }) // store, then work later
  res.sendStatus(200)
})

Use the raw body

If a framework parses the JSON before you verify, and you re-serialize it, the bytes change and the signature fails. Read the raw request body for verification, and parse it only afterwards.

Which status to return

ReturnDialgem does
2xxTreats the delivery as done.
408, 425, 429, 5xx, a timeout or a connection errorRetries it on the schedule.
Any other status, such as 400 or 404Treats it as final and does not retry.

So return 400 for a signature you reject, and a 5xx only when you want Dialgem to try again.

Next