Receive and acknowledge Zift (Zift Payments / payment gateway) webhook notifications. Use when setting up a Zift webhook receiver, understanding why there is no signature/HMAC header to verify, returning the required {"notificationId": ...} acknowledgement, or handling billing and processing events like billing.subscription-created, processing.chargeback, and processing.return.
Install with Codex or Claude Copy this prompt, paste it into Codex, Claude, or another assistant, and let it review the skill page and install it for you.
A direct command skips the review prompt. Inspect the source before running it.
The command stays on one line. Scroll horizontally to inspect it before copying.
Prefer a local copy? Download the files currently available to SkillsMP.
File Explorer
20 files
Showing SKILL.md
SKILL.md
Source instructions · Read-only preview
name
zift-webhooks
description
Receive and acknowledge Zift (Zift Payments / payment gateway) webhook notifications. Use when setting up a Zift webhook receiver, understanding why there is no signature/HMAC header to verify, returning the required {"notificationId": ...} acknowledgement, or handling billing and processing events like billing.subscription-created, processing.chargeback, and processing.return.
Zift (a payments platform / gateway) delivers notifications — billing and
processing events — to an HTTPS endpoint you register with Zift support. Each
delivery is a plain HTTPS POST with a JSON body. There is no signature,
no HMAC, and no auth header on the delivery. Instead, your endpoint proves it
received the notification by echoing the notificationId back in the response
body — that response is the acknowledgement, and skipping it triggers retries.
When to Use This Skill
How do I receive Zift webhook notifications?
How do I acknowledge a Zift webhook (the {"notificationId": ...} response)?
Why is there no X-Zift-Signature / HMAC header to verify?
How do I secure a Zift webhook endpoint with no signature?
How do I handle Zift billing.* and events (chargeback, return, NOC)?
processing.*
Why does Zift keep retrying / marking my webhook Failed?
Verification & Acknowledgement (core)
There is NO per-message signature/HMAC header on Zift notifications. Do not
look for X-Zift-Signature, webhook-signature, or any Standard Webhooks
header — none exists, and Zift sends no Basic/token auth on delivery either.
Authenticity relies on the transport and endpoint secrecy:
HTTPS only — publish the endpoint over TLS so the body can't be read or
tampered with in transit.
Endpoint-URL secrecy — treat the path as a shared secret; use a long,
unguessable path.
IP allowlisting (recommended) — restrict inbound to Zift's egress ranges
at your load balancer / firewall (confirm ranges with Zift support).
Because there is no body signature, ordinary JSON parsing is fine — the raw
bytes are not security-critical (unlike HMAC providers).
The critical part is the acknowledgement. To ACK a delivery your endpoint
MUST return a JSON body echoing the received notificationId (Zift accepts an
int or a string). Anything else — 200 OK, an empty body, {"received":true} —
is not an acknowledgement and triggers Zift's retry schedule.
// Zift acknowledgement: echo the received notificationId back, preserving its// type (Zift accepts int or string). This response body IS the ACK — returning// "OK" or {} instead causes Zift to retry (+5m, +15m, +60m, +24h, then Failed).functionackBody(payload) {
return { notificationId: payload.notificationId };
}
// Dispatch on the eventCode prefix: "billing.*" or "processing.*".functioneventCategory(eventCode) {
if (typeof eventCode !== 'string') return'unknown';
const category = eventCode.split('.')[0];
return category === 'billing' || category === 'processing' ? category : 'unknown';
}
For complete handlers with route wiring, event dispatch, and tests, see:
Dotted event name, e.g. billing.subscription-created
eventDate
number
Event time in epoch milliseconds
dataType
string
Describes the shape of data (e.g. subscription)
data
object
Event-specific payload
Common Event Types
Events are grouped by the eventCode prefix. Only billing.subscription-created
is documented verbatim; the others follow Zift's category.entity-action pattern
from the setup trigger names — confirm the exact literal strings with Zift
support at onboarding and dispatch on the billing / processing prefix.
eventCode
Category
Triggered when
billing.subscription-created
billing
A recurring subscription is created
billing.payment-option-created
billing
A payment option (method) is added
billing.allocation-created
billing
A billing allocation is created
billing.payment-processed
billing
A scheduled billing payment is processed
processing.chargeback
processing
A chargeback is received
processing.return
processing
An ACH/eCheck return occurs
processing.reversal
processing
A transaction is reversed
processing.noc
processing
An ACH Notice of Change (NOC) is received
See references/overview.md for the setup trigger names
(subscription~create, payment-option~create, chargeback, NOC, …).
Retry Behaviour
If your endpoint does not acknowledge with the notificationId, Zift retries at
+5 min, +15 min, +60 min, +24 h, then marks the notification Failed
with no further redelivery. Make your handler idempotent — a retry may deliver a
notification you already processed.
Environment Variables
Zift sends no secret on delivery, so no signing secret is required. The only
optional config is your own comma-separated IP allowlist (enforced by your
infra, shown here for documentation):
# Optional — Zift egress IP ranges to allow (confirm with Zift support).# Enforcement belongs at your load balancer / firewall; this is informational.
ZIFT_ALLOWED_IPS=
Zift webhooks are configured out-of-band: email Zift support your HTTPS
endpoint URL and the events you want. Webhooks are set at the
integrator/reseller level, not per-merchant. See
references/setup.md.
We recommend installing the webhook-handler-patterns skill alongside this one for handler sequence, idempotency, error handling, and retry logic. Key references (open on GitHub):
hookdeck-event-gateway - Webhook infrastructure that replaces your queue — guaranteed delivery, automatic retries, replay, rate limiting, and observability for your webhook handlers