傳遞行為
取自服務商自己的文件,最後檢查於 2026-08-06。服務商沒寫數字的地方,這張表也不填。
| 回應時限 | 10 秒 |
|---|---|
| 重試 | 無。傳遞失敗後,GitHub 不會自動重新傳送 |
| 放棄 | 不會停用。3 天內可以手動重新傳送,之後紀錄就會消失 |
| 出處 | https://docs.github.com/en/webhooks/using-webhooks/best-practices-for-using-webhooks |
簽章
用一個經測試套件證明可運作的驗證程式核對過,不是照文件抄來的。最後驗證於 2026-08-20。
| 演算法 | HMAC-SHA256 |
|---|---|
| 簽章內容 | raw body |
| 編碼 | hex |
| 標頭 | x-hub-signature-256 = sha256=hex |
| 容許時間差 | 不強制 |
驗證簽章
要用原始請求主體(raw body),逐位元組原封不動,並在任何 JSON 解析之前取得。框架只要重新序列化 payload,這頁上的每一種機制就會立刻失效。
const crypto = require("node:crypto");
// x-hub-signature-256: "sha256=" + hex(HMAC-SHA256(secret, raw body))
const expected =
"sha256=" +
crypto.createHmac("sha256", webhookSecret).update(rawBody).digest("hex");
const received = Buffer.from(req.headers["x-hub-signature-256"] ?? "");
const wanted = Buffer.from(expected);
// timingSafeEqual throws on a length mismatch, so check that first.
const valid =
received.length === wanted.length && crypto.timingSafeEqual(received, wanted);容易踩的坑
你只有一次嘗試。這份清單上的其他發送端都會自己重試;GitHub 不會,所以 30 秒的部署空檔就會漏掉事件,沒有第二次機會。Redeliver(重新傳送)按鈕和 Redelivery API 都只能逐筆手動操作,期限 3 天;之後連紀錄本身都會消失。
延伸閱讀
AnyHook 架在接收 GitHub Webhook 的端點前面:大約 1 秒就回應,伺服器當機時依自己的排程重試,並讓每個事件都能重播。 換一個網址,程式碼不用動。