All guides
Connecting other dialers (Mojo, RedX, BatchDialer, etc.) via Zapier

Connecting other dialers (Mojo, RedX, BatchDialer, etc.) via Zapier

~10 min read

Closr has a generic dialer ingest endpoint that accepts a normalized call event from any source. If your dialer has a Zapier trigger (most do), you can bridge it to Closr without waiting for us to build a native integration. The Zap fires when your dialer logs a call, transforms the payload, and posts it to Closr — where it lands in the contact timeline alongside calls you make through Closr's built-in dialer.

Who this is for

  • **Mojo Dialer** — triple-line cold-call dialer. Has a Zapier trigger on "Call Logged."
  • **RedX** (Real Estate Data X) — expired/FSBO dialer. Zapier trigger on "Call Completed."
  • **BatchDialer** — newer triple-line dialer. Zapier app available.
  • **Vulcan7** — expired listing dialer.
  • **Espresso Agent** — premium expired/FSBO.
  • **PhoneBurner** — multi-industry power dialer.
  • **CallTools** and most other call-center dialers.
  • **Anything else with a Zapier app.** If your dialer can fire a Zap when a call completes, it can post to Closr.

If you're on **Quo** (formerly OpenPhone), use the dedicated Quo integration instead — it's HMAC-signed, no Zapier needed. See the "Connecting Quo" guide. The generic endpoint actively blocks `provider: "quo"` so unsigned events can't land in the Quo namespace.

What you'll need

  • A **team API key** from Closr (one of your team's keys; generate one in Settings → Integrations → Zapier).
  • A **Zapier account** (the free tier covers basic Zaps; paid tiers are needed for >100 calls/month on most plans).
  • Your dialer connected as a Zap source.

Generating your Closr team API key

  1. 1Settings → Integrations → click the **Zapier** tile (or the API keys section).
  2. 2Click **New API key**. Give it a label tied to the dialer (e.g. "Mojo dialer Zap") so you can revoke individually later.
  3. 3Closr generates and shows the full key **once**. Copy it now. After this screen, only the first 8 characters are stored for display — the rest is hashed.

Generate a separate key per Zap. If you ever want to disconnect one dialer without breaking another, revoke just that key.

Set up the Zap

  1. 1In Zapier, create a new Zap. **Trigger:** your dialer's "Call completed" / "Call logged" event (the exact label varies by dialer).
  2. 2Connect your dialer account when prompted. Send a test event so Zapier captures a sample payload — you'll need to map fields against it.
  3. 3**Action:** "Webhooks by Zapier" → "POST."
  4. 4**URL:** `https://getclosr.app/api/integrations/dialer/event`
  5. 5**Method:** `POST`. **Data Pass-Through:** off. **Data:** see field mapping below. **Wrap Request In Array:** off.
  6. 6**Headers:**
  • `x-api-key`: paste your Closr team API key from the previous section
  • `Content-Type`: `application/json`

Map the payload fields

Closr's generic endpoint expects a normalized JSON body. Map your dialer's fields to these keys:

  • `provider` (required) — short string identifying the source: `"mojo"`, `"redx"`, `"batch"`, `"vulcan7"`, `"phoneburner"`, etc. Pick a stable slug; it surfaces in the timeline chip and is part of the dedup key.
  • `externalCallId` (required) — the dialer's call ID. Used for idempotency, so re-deliveries don't create duplicate rows.
  • `direction` (required) — `"INBOUND"` or `"OUTBOUND"` (exact case).
  • `from` (required) — caller phone (E.164 preferred: `+14165550123`). For OUTBOUND, this is your dialer number; for INBOUND, it's the contact who called.
  • `to` (required) — recipient phone (E.164 preferred). For OUTBOUND, this is the contact you dialed.
  • `duration` (required) — call length in **seconds** as a number.
  • `status` (required) — provider-native status string (`"completed"`, `"voicemail"`, `"busy"`, etc. — pass through whatever your dialer uses).
  • `startedAt` (required) — ISO 8601 timestamp (`"2026-05-31T14:32:00Z"`).
  • `transcript` (optional) — full transcript text, if your dialer provides one.
  • `aiSummary` (optional) — short AI-generated summary. **If present, Closr fires `CALL_COMPLETED` automations on this call.** If absent, the call still lands but no automation triggers.
  • `nextSteps` (optional) — array of strings, each a follow-up action your dialer's AI extracted.

If your dialer's AI summary feature is on, map `aiSummary` from it. That's the single fire-site for the `CALL_COMPLETED` automation — without it, automations don't run for these calls. (We chose this design because Zapier-fed providers typically batch transcript + summary into a single payload, so the summary's presence is the right signal.)

Provider-specific tips

  • **Mojo:** the call-logged event includes a `Call_ID` field — map to `externalCallId`. Mojo timestamps are usually local — convert to ISO 8601 in Zapier with a Formatter step.
  • **RedX:** the dialer fires after a call ends; map their `call_uuid` to `externalCallId`. RedX duration arrives in milliseconds — divide by 1000 with Zapier Formatter to get seconds.
  • **BatchDialer:** has a clean webhook payload that almost matches Closr's format already. Their `id` → `externalCallId`, `started_at` → `startedAt`, `duration_seconds` → `duration`.
  • **Vulcan7 / Espresso:** may require a paid Zapier integration plan. The triggers vary; check their Zapier app for "Call Outcome Recorded" or similar.
  • **PhoneBurner:** rich payloads — also includes `recording_url`. You can store the URL in a custom field if you need it; the generic endpoint doesn't accept recording URLs (recordings are vendor-side for non-Quo).

Test the Zap end-to-end

  1. 1In Zapier, click **Test action**. Zapier sends your mapped payload as a POST to Closr.
  2. 2Expect a **200 OK** response with a body like `{ "status": "created", "callRecordId": "..." }`.
  3. 3Open `/app/contacts/<id>` for the contact whose phone matches the call. You should see a new call row with chip `CALL · <PROVIDER> · MmSSs`.
  4. 4If you mapped `aiSummary`, open Settings → Automations and verify any `CALL_COMPLETED` automation fired (execution log shows the event).
  5. 5Turn the Zap on. Future calls will sync automatically.

Troubleshooting

  • **401 Unauthorized.** Your API key is missing or wrong. Verify the `x-api-key` header is set (not the URL query) and the key is the full one Zapier never truncated.
  • **400 Bad Request** — "provider, externalCallId, direction required" — one of the required fields is missing from the payload. Re-check your field mapping.
  • **400** — "provider \"quo\" not accepted on this endpoint" — you tried to use `"quo"` as the provider slug. Use the native Quo integration instead; this endpoint rejects unsigned Quo writes by design.
  • **Call lands but isn't attached to a contact.** The phone number in your `to`/`from` doesn't match the contact's `Contact.phone` in Closr. Closr uses an exact-string match — `+14165550123` doesn't match `(416) 555-0123`. Normalize to E.164 in your Zap with a Formatter step.
  • **CALL_COMPLETED automation didn't fire.** Verify the `aiSummary` field is in your payload. The automation trigger is gated on summary presence, not on call completion alone (intentional — see the field-mapping tip above).
  • **Duplicates.** Closr dedupes on `(provider, externalCallId)`. If you're seeing duplicates, your dialer is sending different IDs for the same call (rare) — re-check the field mapping.

If your dialer doesn't have a Zapier app but does have a webhook output, you can point its webhook directly at `https://getclosr.app/api/integrations/dialer/event` with the `x-api-key` header. Same contract, no middleware.