高可靠 · 雙向 Webhook · 外部整合中樞
作為十月飛雲微服務體系對外資料交換的標準化轉發站,提供外部回呼接收、HMAC-SHA256 簽名防偽、指數退避重試佇列、OAuth Client 憑證發行與標準化事件格式對齊。
Webhook 接入通訊協議規範
所有對外或進站之 Webhook 事件皆必須嚴格遵循以下簽章與防重放安全協議。
📥 進站 Webhook 驗證 (Inbound)
外部供應商(金流、外部網站)將回呼發送至 /webhook/inbound/{provider}。系統自動比對約定 Secret 執行 HMAC-SHA256 驗簽與時間戳防重放,並透過 Event ID 執行冪等去重。
📤 出站 Webhook 簽署 (Outbound)
由 USP 內部微服務發起之推播事件,閘道自動計算 X-USP-Signature: sha256=... 並附帶 X-USP-Timestamp 與唯一 X-USP-Delivery-ID,確保接收端可驗證真實性。
🔄 高可靠指數退避重試 (Retry & DLQ)
當外部接收端暫時離線或回應 5xx 錯誤時,任務自動進入指數退避排程(1分鐘、5分鐘、15分鐘、1小時、6小時)。若 5 次重試均失敗,自動封存於死信佇列 (DLQ)。
🔑 獨立 Service Identity 與 M2M 憑證
遵循 USP-024 規範,每個外部整合對象配置獨立 Service Identity。支援發行 API Key(int_live_...)與 OAuth 2.0 Client 憑證(Argon2id 安全雜湊存儲),細緻分配 Scope。
🔀 事件標準化轉換 (Event Transformer)
將不同外部金流業者或電商網站的多樣化回呼 Payload,依據 JSON Schema 自動轉換為 USP 標準化結構,下游微服務無需重複開發第三方解析器。
🔗 全域分散式呼叫鏈追蹤 (X-Request-ID)
每個進出站事件皆繼承或指派 UUIDv4 呼叫鏈識別標頭,並記錄至 SHA-256 雜湊鏈存證日誌,實現全生命週期透明追溯。
USP 標準非同步事件目錄 (Event Catalog)
已標準化定義並支援出站訂閱廣播之核心事件規格。
| 事件代碼 (Event Type) | 中文名稱 | 業務場景描述 | 標準觸發微服務 |
|---|---|---|---|
usp.payment.succeeded |
支付成功事件 | 當付款完成、對帳通過後由 payment 微服務廣播至外部整合端點 | payment |
usp.payment.failed |
支付失敗事件 | 付款被拒或過期作廢時觸發 | payment |
usp.order.created |
訂單建立事件 | 外部商店或內部預約系統新訂單成立 | order |
usp.order.status_updated |
訂單狀態更新事件 | 訂單履約、出貨、完成或取消 | order |
usp.inventory.changed |
庫存變動事件 | 商品庫存增減或售罄警報 | inventory |
usp.notify.broadcast |
系統廣播通知 | 需推播至 Discord Webhook 或外部通知管道之事件 | notify |
usp.security.alert |
重大安全預警事件 | 觸發 WAF 重大阻斷、高頻重放攻擊或異常登入時的系統警報 | security |
進站 Webhook 驗簽驗收範例 (PHP)
外部接收端驗證來自 USP 之出站 Webhook 範例代碼。
$payload = file_get_contents('php://input');
$signatureHeader = $_SERVER['HTTP_X_USP_SIGNATURE'] ?? '';
$timestamp = (int)($_SERVER['HTTP_X_USP_TIMESTAMP'] ?? 0);
$secret = 'your_webhook_signing_secret';
// 1. 檢查時效性 (防止重放攻擊,容錯 300 秒)
if (abs(time() - $timestamp) > 300) {
http_response_code(400);
exit('Timestamp expired');
}
// 2. 驗證 HMAC-SHA256 數位簽章
$expectedSignature = 'sha256=' . hash_hmac('sha256', "{$timestamp}.{$payload}", $secret);
if (!hash_equals($expectedSignature, $signatureHeader)) {
http_response_code(401);
exit('Invalid signature');
}
// 簽章正確,執行內部業務邏輯
$event = json_decode($payload, true);
http_response_code(200);
echo json_encode(['status' => 'received']);