有始有終的 Replicate Webhook。
你的處理程式要儲存輸出、通知使用者,也許還要再串一次執行。AnyHook 在邊緣節點回應 Replicate,所以這些都不必在 Replicate 的傳遞時限內完成。
時限問題
模型執行完成時,Replicate 會發出 Webhook。這部分運作正常。問題在於你要拿結果做什麼:保存產出的檔案、通知使用者、再送給第二個模型、發一則 Slack 訊息。
每一項都是一次網路往返,加起來可能比請求還長。Replicate 會重試,最後一次重試大約在預測(prediction)完成後一分鐘。你的下游副作用可能觸發兩次,也可能完全沒觸發。AnyHook 在邊界解決時間問題,讓處理程式保持線性、一目了然。
60 秒–5 分鐘
Replicate 執行時間(影片模型)
約 1 分鐘
預測完成後,Replicate 送出最後一次重試的時間
重播
按一下就重新處理過去的執行
已加密
輸出網址以 AES-256-GCM 加密儲存
透過 AnyHook 接收 Replicate 的執行完成通知
把 AnyHook 的接收網址(inbound URL)當作預測的 `webhook` 參數傳入。下游的處理程式就有足夠的時間把結果分送出去。
import Replicate from "replicate";
import { verifyWebhook } from "anyhook-verify";
const replicate = new Replicate();
// 1. Start the prediction with AnyHook as the callback target.
await replicate.predictions.create({
version: "...",
input: { prompt: "..." },
webhook: `https://in.anyhook.net/${userSlug}/${appSlug}`,
webhook_events_filter: ["completed"],
});
// 2. Handler, runs after AnyHook has already acked Replicate.
export async function POST(req: Request) {
if (!(await verifyWebhook(req, process.env.ANYHOOK_SIGNING_SECRET!))) {
return new Response("invalid", { status: 401 });
}
const { id, output } = await req.json();
await persistOutput(id, output); // 3s
await notifyUser(id); // 2s
await chainNextModel(output); // 45s, inside even Free's 60s
return new Response("ok", { status: 200 });
}團隊常問的問題
- 所有 Replicate 模型類型都適用嗎?
- 適用,圖片、影片、音訊、語言模型都一樣。Webhook 的規格完全相同。AnyHook 把 payload 當成不透明的 JSON,原封不動地轉送。
- Replicate 已經會重試了,為什麼還需要 AnyHook?
- Replicate 會在傳輸失敗時重試,但時間窗很短,而且它只重試 Webhook 的傳遞,不會重試你下游的商業邏輯。AnyHook 以指數退避重試你的處理程式,Scale 方案最多 10 次,而且只要方案還保存著事件,任何事件按一下就能重播。
- 不用再回 Replicate 查,也能看到預測的輸出嗎?
- 可以。完整的 Webhook payload(包括 `output` 網址)都加密儲存在你的 AnyHook 事件紀錄裡:在儀表板開啟,或用 GET /api/v1/events/{id} 讀取。
- AnyHook 會驗證 Replicate 的簽章嗎?
- 會,設定好之後就會。Replicate 用 Standard Webhooks 機制簽章(webhook-id、webhook-timestamp、webhook-signature)。把 App(一個接收網址,對應一個 Webhook 來源)的來源設為 Standard Webhooks,貼上從 Replicate 的 GET /v1/webhooks/default/secret 取得的密鑰:偽造的請求會在邊緣節點被拒收。
換一個網址。Replicate 的處理程式不用改。
Free 方案每月涵蓋 10,000 個事件。不用 SDK:把 Replicate 指向你的 AnyHook 接收網址。