Sign Up
Sign Up
← All guides

Automate leave workflows without code: Collabin webhooks in n8n and Make

Our Slack webhook guide builds a small Node.js bridge β€” but you don't have to write code at all. With n8n or Make, Collabin's webhook events become triggers for thousands of apps: Slack and Teams messages, Google Sheets rows, calendar entries, HR system updates. This guide builds the n8n version end to end, including proper signature verification, then covers Make and recipe ideas.

A 60-second webhook recap

Collabin sends a POST request to a URL of your choice whenever a subscribed event fires β€” leave.created (new request) or leave.status_changed (approved/rejected). The body carries an event name, a timestamp, a delivery_id, and the full leave object in data (with embedded user and leave_type). Each request is signed: the X-Collabin-Signature header contains sha256=<HMAC-SHA256 of the raw body>, computed with your webhook's secret. Webhooks require the Pro plan; full payload details are in the Slack guide.

Building it in n8n

Step 1: The Webhook trigger

Create a new workflow and add a Webhook node:

  • HTTP method: POST
  • Respond: Immediately β€” Collabin waits at most 10 seconds, so acknowledge first, work after.
  • In the node's settings, enable Raw Body. This matters: the signature is computed over the exact bytes Collabin sent, and a re-serialized JSON body would not match.

Copy the production webhook URL the node shows.

Step 2: Register it in Collabin

In the Collabin dashboard, open Webhooks, add a new one with your n8n URL, and pick the events. Collabin shows the webhook's secret once β€” copy it now; you'll need it in the next step.

Step 3: Verify the signature in a Code node

Add a Code node after the trigger (n8n's Code node can use Node's built-in crypto β€” this is configuration, not app code you have to host):

const crypto = require('crypto');

const secret = 'YOUR_WEBHOOK_SECRET'; // better: an n8n credential/env var
const rawBody = $input.first().binary.data
  ? Buffer.from($input.first().binary.data.data, 'base64')
  : Buffer.from(JSON.stringify($input.first().json.body));

const expected = 'sha256=' +
  crypto.createHmac('sha256', secret).update(rawBody).digest('hex');
const received = $input.first().json.headers['x-collabin-signature'] || '';

if (received !== expected) {
  throw new Error('Invalid webhook signature β€” dropping delivery.');
}

return [{ json: JSON.parse(rawBody.toString('utf8')) }];

If the signature doesn't match, the workflow stops and nothing downstream runs. From here on, every node can trust the payload.

Step 4: Route and act

Add a Switch node on {{ $json.event }} with one output per event, then attach whatever the workflow is for. A Slack branch is a single Slack node with a message like:

:palm_tree: {{ $json.data.user.name }} requested
{{ $json.data.leave_type.name }}: {{ $json.data.start_date.slice(0,10) }}
– {{ $json.data.end_date.slice(0,10) }}

Activate the workflow, submit a test leave request in Collabin, and watch the execution log light up.

The same in Make

In Make (formerly Integromat), the trigger is a Custom webhook module: create it, copy the URL, register it in Collabin the same way. Make parses the JSON automatically and you wire the following modules (Slack, Google Sheets, email…) from the mapped fields.

One honest caveat: Make's custom webhooks don't expose the raw request body to formulas, so HMAC verification is impractical there. The webhook URL itself is a long random secret, which is genuinely hard to guess β€” but it means anyone who learns the URL could send fake events. Two reasonable stances: accept that risk for low-stakes automations (a wrong Slack message), or keep signature-verified flows in n8n / a small code bridge for anything that writes into systems of record. Don't pipe unverified webhook data into payroll.

Recipe ideas

  • Approvals digest: leave.status_changed β†’ filter status = APPROVED β†’ append a row to a Google Sheet β€” a zero-effort audit trail your office manager can read.
  • Calendar without ICS: leave.status_changed (approved) β†’ create a Google Calendar event in a shared team calendar. (If you only need calendars, the built-in calendar feed does this without any automation.)
  • Rejection follow-up: leave.status_changed β†’ filter status = REJECTED β†’ notify HR by email with rejection_reason, so declined requests get a human follow-up.
  • Headcount heads-up: leave.created β†’ look up the team in a sheet β†’ if more than N teammates overlap, ping the lead before they approve.

Operating notes

Collabin treats any 2xx response as success and does not retry failed deliveries β€” keep the trigger's "respond immediately" setting so slow downstream apps can't cause losses, and remember failed attempts are visible in Collabin's system error log. One more habit worth keeping: give n8n and Make separate webhooks in Collabin, each with its own secret, so you can revoke one consumer without touching the other.