← Help Center

Send alerts to Slack or a webhook

Alerts normally arrive by email. You can also send them to a Slack channel, or to any tool that accepts a webhook — and, once one of those is set up, turn the emails off.

What gets sent

The same alerts you'd get by email:

  • A monitored site goes down, and when it recovers
  • A health score regression, or a visual change on a page
  • Pages that regressed in a full-site crawl
  • Your monthly client reports being ready (Agency plan)

There is one Slack destination and one webhook per account, shared by all your websites. Everything below is set up on the Notifications page (account menu → Notifications).

Slack

1. Create an incoming webhook

  1. Go to api.slack.com/apps, click Create New App and choose From scratch. Name it something like "Cuttlefish QA" and pick your workspace.
  2. In the app's settings, open Incoming Webhooks and switch Activate Incoming Webhooks on.
  3. Click Add New Webhook to Workspace, choose the channel alerts should post to, and click Allow. (If you're not a workspace admin, Slack may ask an admin to approve it first.)
  4. Copy the Webhook URL. It starts with https://hooks.slack.com/services/.

Official guide: Sending messages using incoming webhooks. Menus change from time to time — Slack's own documentation is the source of truth.

2. Add it to Cuttlefish QA

  1. Open the Notifications page, paste the URL into the Slack box and click Save Slack webhook.
  2. Click Send test. A test message should appear in your channel within a few seconds.

Treat the webhook URL like a password: anyone who has it can post to that channel. We only show a shortened version of it on the page. If it leaks, delete the webhook in Slack and create a new one.

Webhook (Zapier, Make, n8n or your own code)

We send an HTTP POST with a JSON body to an address you choose. This is the route to use for anything that isn't Slack — a Zap that posts to Microsoft Teams or Discord, a row in a spreadsheet, a ticket in your issue tracker, or your own server.

1. Get a webhook address from your tool

  1. Create a Zap and choose Webhooks by Zapier as the trigger, with the event Catch Hook.
  2. Copy the Custom Webhook URL it gives you and save it on our Notifications page.
  3. Click Send test on our page, then Test trigger in Zapier so it can read the fields (event, title, message, url).
  4. Add the action you want, such as a Teams or Discord message or an email.

  1. Create a scenario that starts with the Webhooks module and the Custom webhook trigger.
  2. Add a webhook, copy its address and save it on our Notifications page.
  3. Click Send test on our page so Make can learn the data structure, then add your next module.

  1. Add a Webhook node, set the method to POST, and copy its Production URL.
  2. Save that address on our Notifications page and activate your workflow.

The address must be reachable from the internet over https, so a self-hosted n8n needs a public domain.

Create an endpoint that accepts POST requests with JSON and returns any 2xx status. Verify the signature (below) before trusting the request.

2. Requirements for the address

  • It must start with https:// and be reachable from the public internet. Addresses that point to private or internal networks (like localhost or 192.168.x.x) are refused.
  • Redirects are not followed. Use the final address.
  • Respond within a few seconds with a 2xx status. If we get a server error or a timeout we try once more.

3. What we send

POST /your/endpoint
Content-Type: application/json
X-Cuttlefish-Event: site.down
X-Cuttlefish-Signature: sha256=<hex digest>

{
  "version": 1,
  "event": "site.down",
  "title": "Your site is down: https://example.com",
  "message": "We couldn't reach …",
  "url": "https://cuttlefishqa.com/…",
  "occurred_at": "2026-10-16T09:00:00Z"
}

The event is one of:

EventWhen
site.downA monitored site has failed two checks in a row
site.recoveredA site that was reported down is back
scan.regressionA scan found the health score dropped or new issues appeared
visual.changeA visual check found a page looks different
crawl.regressionA full-site crawl found pages that got worse
reports.readyMonthly client reports are ready to download
testYou clicked Send test

url can be empty for some events. We may add new fields over time, so ignore ones you don't recognise.

4. Verify the signature

Anyone who learns your endpoint address could send it fake alerts. To check a request really came from us, compute an HMAC-SHA256 of the raw request body using your signing secret (shown on the Notifications page) and compare it with the X-Cuttlefish-Signature header.

Python

import hmac, hashlib

expected = "sha256=" + hmac.new(SECRET.encode(), raw_body, hashlib.sha256).hexdigest()
ok = hmac.compare_digest(expected, request.headers["X-Cuttlefish-Signature"])

Node.js

const crypto = require('crypto');

const expected = 'sha256=' + crypto.createHmac('sha256', SECRET).update(rawBody).digest('hex');
const given = req.get('X-Cuttlefish-Signature') || '';
const ok = given.length === expected.length &&
           crypto.timingSafeEqual(Buffer.from(expected), Buffer.from(given));

Use the body exactly as received, before any JSON parsing; re-serialising it changes the bytes and the signature won't match. Zapier, Make and n8n's basic webhook triggers don't check signatures, so for those the hard-to-guess address is the protection — keep it private.

If your secret leaks, click Regenerate secret on the Notifications page and update your receiver. The old secret stops matching straight away.

Turning alert emails off

Once Slack or a webhook is set up, the Email section of the Notifications page lets you switch alert emails off. A few rules keep alerts from disappearing:

  • You can only turn emails off while at least one Slack or webhook destination is saved.
  • If you remove your last destination, emails switch back on automatically.
  • Account emails such as password resets and email verification are not alerts and are always sent.

Troubleshooting

"That doesn't look like a Slack incoming webhook URL"
It must start with https://hooks.slack.com/services/. Copy the Webhook URL from the Incoming Webhooks page, not an app or channel link.
"That URL points to a private or internal address"
We can only send to addresses on the public internet. For local development, use a tunnel service that gives you a public https address.
The page says "Last delivery failed: HTTP 404"
The destination no longer exists. For Slack this usually means the webhook was deleted or the app was removed — create a new one and replace the URL. For a webhook, check the address, and that a Zap or workflow isn't switched off.
"HTTP 3xx: redirects aren't followed"
Your address redirects somewhere else (often http to https, or adding www). Save the final address instead.
"Could not connect"
Your endpoint didn't answer in time or refused the connection. Make sure it's online and not behind a firewall or bot protection that blocks our requests.
Signature check always fails
The usual cause is hashing the parsed JSON rather than the raw body, or using an old secret after regenerating it. Also check there's no extra whitespace in the secret you copied.
The test works but I'm not getting real alerts
Alerts only fire when something actually happens: for downtime, a monitored site must fail two checks in a row, and automatic monitoring depends on your plan. Check that the alert would have been sent by email too.

Still stuck? Contact us and tell us which destination you're setting up — we're happy to help.