Z Zise Developers 简体中文

member.suspended

Merchant-level suspension state changed; suspension and restoration share this event

When Emitted

Emitted after POST /v1/members/{id}/suspend actually changes merchant_status. Restoration emits the same event, with status: normal; status identifies the direction. A separate restoration event would require examining two event streams to answer whether the member can currently use the service. This flag only controls availability for the member under your merchant. Platform-level blocking is separate and not visible to you. ⚠ status_version is always 0, and this event can recur: suspend → restore → suspend again. This is therefore the one place among these events where ordering by created_at is genuinely necessary. Do not skip equal versions, or the restoration event will be discarded and the member will remain blocked on your side.

Payload

{
  "event_id": "evt_7c93a1d05e6b4a2f9d81c4e0f2a37b56",
  "event_type": "member.suspended",
  "created_at": "2026-08-12T10:02:11Z",
  "merchant_id": "acme",
  "livemode": true,
  "data": {
    "object": "member",
    "id": "4b7c1e02-9a3d-4f18-8c55-2d61ab0f9e77",
    "external_member_id": "u_88123",
    "status": "suspended",
    "status_version": 0
  }
}

Payload Fields

FieldTypeDescription
idstringUse this for deduplication. evt_… remains unchanged when the same event is redelivered.
typestringAlways member.suspended
created_atstringTime the event was created (RFC3339), not its delivery time. It is unchanged on redelivery.
data.objectstringObject type; determines which endpoint to query with data.id
data.idstringObject ID; use it to retrieve details.
data.statusstringTreat unrecognized values as unknown and raise an alert; do not fall back to “processing”
data.status_versionnumberMonotonically increasing; use it to discard older states that arrive late.

Signature Verification and Deduplication

Verify the signature against the raw request body bytes. Do not parse and reserialize the JSON: your JSON library may change key order or whitespace, which changes the signature and can look like a key configuration error.

// Node · Run before parsing JSON
const raw = await readRawBody(req);            // Buffer / string; do not use parsed req.body
const expect = crypto.createHmac("sha256", WEBHOOK_SECRET).update(raw).digest("hex");
const got = req.headers["z-signature"];        // Format: t=<unix>,v1=<hex>
if (!timingSafeEqual(expect, parseV1(got))) return res.status(400).end();

// Deduplicate using the envelope id, not data.id
if (await seen(JSON.parse(raw).id)) return res.status(200).end();

For the full procedure, including timestamp tolerance and redelivery semantics, see Webhook Guide.