Definition
护照的 Webhook 如何运作?
当护照、事件或凭证发生变化时,CirculeID 会向您的端点推送一次带签名的回调。投递保证为至少一次并采用指数退避,因此处理程序必须校验签名、把重复的投递标识视为空操作,并在执行动作前通过 API 回读当前状态。
Treat a payload as a notification, not as the record. That single habit removes the entire class of bug where a delayed retry overwrites newer data with older data.
事件
您可以订阅什么
| Event | Fires when | Typical handler |
|---|---|---|
| passport.created | A passport is issued against an identifier | Print or encode the data carrier |
| passport.updated | The record changes materially | Re-read state; refresh a cached storefront view |
| event.recorded | An EPCIS event is appended to an object | Advance an internal workflow |
| credential.issued | A supplier signs a claim against your product | Clear the compliance gap for that field |
| credential.revoked | An issuer withdraws a claim | Re-open the gap; review anything that relied on it |
| passport.gap_detected | A delegated act change leaves a field unmet | Raise it to the compliance owner |
验证
先验证,再解析
import { createHmac, timingSafeEqual } from 'node:crypto';
export function verify(rawBody, header, secret) {
const [ts, signature] = parseHeader(header);
// Reject replays before doing any work.
if (Math.abs(Date.now() / 1000 - Number(ts)) > 300) return false;
const expected = createHmac('sha256', secret)
.update(`${ts}.${rawBody}`) // raw body, exactly as received
.digest();
// Constant-time: a fast reject leaks the signature one byte at a time.
return timingSafeEqual(Buffer.from(signature, 'hex'), expected);
}合同
平台保证什么
已签名的负载
以每个端点独立的密钥对原始请求体计算的 HMAC,外加时间戳。
至少一次投递
对于会重试的系统而言,这是诚实的保证。处理程序必须是幂等的。
指数退避
在较长时间窗内重试,因此短暂的中断不会给您造成任何损失。
每份载荷都带版本
若某次投递描述的是您已经越过的版本,请直接忽略。
可见的失败日志
投递失败会被列出并可重放,而不是被悄悄丢弃。
精确限定的订阅
按事件类型分别订阅,让每个端点只接收自己会处理的内容。
答疑
常见问题
我如何确认某个 Webhook 确实来自 CirculeID?
每一次投递都带有对原始请求体的签名以及时间戳。请在解析之前用端点密钥校验签名,并拒绝时间戳超出容差窗口的投递。一个信任未经校验负载的端点,就是任何人都能向其投递的端点。
投递是否有序?
按对象尽力保证顺序 —— 但请不要依赖它。重试与网络状况都可能让较早的事件晚于较新的事件到达。每个负载都带有它所反映的对象版本,因此处理程序应当忽略描述已越过版本的投递,而不是假定到达顺序。
如果我的端点宕机了会怎样?
投递会在较长的时间窗内以指数退避方式重试,失败日志在您的账户中可见,而不是悄无声息。时间窗到期后,该次投递被标记为失败;但底层变更仍可通过 API 查询,因此 Webhook 故障造成的是延迟,而非数据丢失。
同一条事件会被投递两次吗?
会的,而且您应当默认它会发生。至少投递一次,是任何具备重试机制的系统所能给出的诚实保证。每次投递都带有稳定的标识符,因此正确的处理程序会记录该标识符,并把重复视为空操作——这也让重放失败时间窗变得安全。
Webhook 的负载可以当作完整记录来信任吗?
请把载荷当作通知,而不是事实来源。它告诉您有内容发生了变化,并提供足够的信息让您判断是否需要关注;若要据此行动,请通过 API 回读当前状态。这样一来,过期或乱序的投递就无法把旧数据写入您的系统。