驗證已簽名的 Webhook

許多服務會在傳送的 webhook 上簽名,以便接收方能驗證該請求確實來自該服務,且在傳輸過程中未遭篡改。若將 webhook 的驗證方式設定為 HMAC,系統會在任何資料傳送至 Shopify Flow 之前,先檢查該簽名。未能通過檢查的請求將被以 401 狀態碼拒絕,且絕不會執行任何工作流程。

有兩種設定方式:從清單中選擇發件人,或描述其簽名方式。

內建提供者

在**「簽名提供者**」下選擇提供者,並貼上其簽名密鑰。應用程式隨後會根據該提供者所記載的方式進行驗證 - - 包括正確的標頭、編碼、已簽名內容及重播視窗 - - 因此無需進行其他設定。每個提供者皆有專屬的設定指南,內容涵蓋從建立端點到建構「Shopify Flow」工作流程等步驟。

供應商 設定指南 此外還涵蓋
Calendly 如何將 Calendly 連接到 Shopify Flow -
Customer.io 如何將 Customer.io 連接到 Shopify Flow -
GitHub 如何將 GitHub 連接到 Shopify Flow -
檸檬擠汁器 如何將 Lemon Squeezy 連接到 Shopify Flow -
線性 如何將 Linear 連接至 Shopify Flow -
莫莉 如何將 Mollie 連接到 Shopify Flow -
槳 如何將 Paddle 連接到 Shopify Flow -
Paystack 如何將 Paystack 連接到 Shopify Flow -
Razorpay 如何將 Razorpay 連接至 Shopify Flow -
理智 如何將 Sanity 連接到 Shopify Flow -
Sendcloud 如何將 Sendcloud 連接到 Shopify Flow -
Sentry 如何將 Sentry 連接到 Shopify Flow -
Shopify 如何將 Shopify 連結至 Shopify Flow -
Slack 如何將 Slack 連接到 Shopify Flow -
正方形 如何將 Square 連接到 Shopify Flow -
標準 Webhooks 如何將標準 Webhooks 連接到 Shopify Flow OpenAI、Supabase 身份驗證鉤子
Stripe 如何將 Stripe 連接至 Shopify Flow -
Svix 如何將 Svix 連接到 Shopify Flow 文員、重新發送、超級牆
Typeform 如何將 Typeform 連接到 Shopify Flow -
Vercel 如何將 Vercel 連接到 Shopify Flow -
WooCommerce 如何將 WooCommerce 連接至 Shopify Flow -
Zendesk 如何將 Zendesk 連接到 Shopify Flow -

每份指南都會詳細列出該應用程式會針對該寄件者檢查哪些項目,以及該處簽名密鑰的位置。

一個採用 HMAC 驗證且以 Stripe 作為簽名提供者的 Webhook,其中說明了「簽名密鑰」欄位、其驗證內容,以及「連接 Stripe」的步驟
已簽名的發送方(此處為 Stripe):選擇服務供應商、貼上其簽名密鑰,編輯器便會顯示哪些項目已勾選,以及如何進行連線。

自訂簽名:其他任何寄件者

如果您的發件人不在清單中,請選擇**「自訂簽名」**,並說明其簽名方式。您的服務供應商的文件中應包含類似以下這行內容:

X-Acme-Signature = hex(hmac_sha256(secret, timestamp + "." + body))

這一行代碼便能處理所有欄位:

場景設定 根據範例 這代表什麼意思
簽名標題 X-Acme-Signature 載有簽名的標題
演算法 hmac_sha256 SHA-256、SHA-1 或 SHA-512
編碼 hex 十六進位、Base64 或 Base64URL
已簽署的有效載荷 {timestamp}.{body} 簽署的具體文本如下:
時間戳記 例如 X-Acme-Timestamp 這樣的標頭 timestamp 的值會流向何處
重播容差 300 秒 拒絕早於此時間的請求

已簽名的有效載荷

請使用以下佔位符填寫寄件者的簽名:

佔位符 變成
{body} 原始請求內容,逐位元組呈現。必填。
{timestamp} 來自標頭或簽名標頭的時間戳記
{url} 此 Webhook 的 URL,即您在發送方處所輸入的內容
{header:name} 另一個請求標頭的值

常見格式:{body}、{timestamp}.{body}、{timestamp}{body}、v0:{timestamp}:{body}、{header:webhook-id}.{timestamp}.{body}。請使用**「從提供者開始」**功能,複製一個接近的格式,並僅修改不同之處。

簽名的位置

  • 普通格式:標頭值即為簽名,可選擇在您指定的前綴之後出現,例如 sha256= 或 v1,。
  • Key = value:此標頭包含諸如 t=1700000000,v1=abc... 之類的鍵值對。請指定存放簽名的鍵名稱(v1),可選地指定存放時間戳記的鍵名稱(t),並指定鍵值對是以 , 還是 ; 分隔。

如果一個標頭包含多個以空格分隔的簽名(某些發件人在您輪替密鑰時會這樣做),只要其中任何一個與要求相符,系統便會接受該簽名。

這個秘密

通常您只需將發送者顯示的密鑰直接貼上即可。有些發送者會提供帶有前綴的 Base64 編碼金鑰,例如 whsec_...:請選擇「Base64 編碼」,並輸入要移除的前綴。

上線前的測試

簽名測試器位於設定下方,並可處理尚未儲存的變更。

  • 貼上真實請求的正文和標頭,然後按下**「驗證」**。您將看到每個步驟 - - 找到標頭、讀取簽名、時間戳記在範圍內、建構有效載荷、比對簽名 - - 以及實際被簽名的精確文字,因此若出現不匹配的情況,系統會明確指出問題出在哪裡,而非僅顯示單純的「簽名無效」。
  • **「產生有效範例」**功能會根據您當前的設定,產生簽名正確的標頭以及可直接執行的 curl。若該請求獲得接受,即表示您的設定在端到端層面上是前後一致的。

該測試者永遠不會啟動工作流程,也不會向「歷史紀錄」寫入任何內容,且不計入您的方案配額。

簽名不符。我該檢查什麼?▾

依此順序:密鑰(最常見的原因,包括多餘的空格或錯誤的環境金鑰)、簽名載荷(時間戳記與正文之間缺少 . 或 :)、編碼方式(十六進位與 Base64),以及發送者與應用程式之間是否有所變更導致正文產生變化。 簽名涵蓋原始位元組,因此若代理伺服器重新格式化 JSON,便會破壞簽名。

請求失敗,錯誤訊息為「時間戳記超出容許範圍」▾

發送方的時鐘不準確、請求被延遲,或是使用過時的時間戳進行重試,又或是時間戳的單位不正確。請檢查您的發送方使用的是秒、毫秒還是 ISO 日期。

我的發件人需要先進行驗證握手▾

某些服務(Zoom、Dropbox、Asana、Trello、Notion)會在傳送任何事件之前,先發送一項驗證挑戰,端點必須以各自的方式進行回應。正因如此,這些服務並未被列為「一鍵式」提供者。若您需要其中任何一項服務,請聯絡支援團隊並提供您的發件人名稱。

簽名是否儲存於某處?▾

不。在「歷史紀錄」和「即時請求檢視器」中,簽名標頭會被遮罩,因為簽名可能在其容差範圍內被重播。