Webflow CMS item webhook to Sume: ack first, three retries, one image

Webflow retries a failed webhook 3 times, 10 minutes apart, then deactivates it. Ack with 200, key the Sume job by item id, and check the signature timestamp.

4 min readSume
All posts

When a CMS item is created in Webflow, the collection_item_created webhook can start a Sume image job. Answer 200 quickly, key the Sume request by the item id, and skip draft items. Webflow retries a failed delivery 3 times at 10-minute intervals and deactivates a webhook that keeps failing, so a handler that blocks on generation can end up switching itself off.

This post gives the Sume side. Webflow's page describes signed requests, but write your verifier from that page and test it against a real delivery; the code below starts after verification.

What Webflow says about delivery

The webhook guide describes two headers, x-webflow-timestamp and x-webflow-signature, with the signed string built from the timestamp, a colon and the JSON body, and tells you to reject timestamps older than 5 minutes. It expects a 200 response, retries up to 3 times 10 minutes apart, and deactivates a webhook after repeated failures. A site can register up to 75 webhooks per trigger type.

The collection_item_created payload includes the item id, cmsLocaleId, fieldData with at least name and slug, and isDraft. That is all the Sume prompt needs: the name for the subject, and isDraft to avoid paying for images on items nobody will publish. When the editor later publishes the item, you can submit then, using the same key, and an earlier submit would simply be adopted.

Webflow rules and their Sume counterparts (read 2026-10-03)
Webflow ruleValueHandler decision
Expected response200Return it before slow work
Retries3, 10 minutes apartStable key from the item id
After repeated failureWebhook deactivatedDo not return 5xx for permanent errors
Replay windowReject timestamps older than 5 minutesCheck the timestamp header
Draft itemsisDraft true in payloadSkip, or wait for publish

Submitting from the payload

Pass the payload object from the verified webhook body. A 202 or a replay both count as success.

import os, requests

def submit_item_image(payload: dict) -> int:
    if payload.get("isDraft"):
        return 200
    name = (payload.get("fieldData") or {}).get("name", "")
    if not name:
        return 200
    try:
        r = requests.post(
            "https://api.sume.com/v1/images",
            headers={"Authorization": f"Bearer {os.environ['SUME_API_KEY']}",
                     "Idempotency-Key": f"webflow-item-{payload['id']}"},
            json={"model": "sume/auto", "mode": "async",
                  "prompt": f"Header illustration for a post titled: {name}"},
            timeout=15,
        )
    except requests.RequestException:
        return 503
    return 503 if r.status_code == 429 or r.status_code >= 500 else 200

Why the slow path is separate

Webflow's 10-minute spacing gives you a long gap between attempts, which is good for a transient Sume outage and bad for a handler that hangs. Return 200 from the web request as soon as the job is submitted, and collect the finished image through the Sume job webhook. Writing it back to the CMS item is then an independent step with its own retries.

Sources

Related posts

More in Integrations

All Integrations posts

Written by Sume