在 Supabase Edge Functions 上使用 ffmpeg,整段工作交給一次 HTTPS 請求。
Edge Functions 跑在 Deno 上,沒有 child_process 可以用來啟動 ffmpeg 二進位檔。你的函式維持原樣,把編碼工作交給一次 HTTPS 請求,直接拿回成品檔案的 URL。
// supabase/functions/watermark/index.ts
Deno.serve(async (req) => {
const { videoUrl, logoUrl } = await req.json();
const res = await fetch("https://api.fotovid.co/v1/video/watermark", {
method: "POST",
headers: {
Authorization: `Bearer ${Deno.env.get("FOTOVID_API_KEY")}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
source_url: videoUrl, // a Supabase Storage signed URL works here
params: { type: "image", watermark_image_url: logoUrl, position: "bottom-right" },
}),
});
const { url } = await res.json();
return Response.json({ url });
});為什麼 ffmpeg 在你的 Edge Function 裡跑不起來
Supabase Edge Functions 跑在 Deno 執行環境上,而 Deno 沒有 child_process 或 subprocess API——就算你把 ffmpeg 二進位檔一起打包進去,也沒有任何方式可以把它啟動起來。除此之外,CPU 與總執行時間的上限是為輕量的請求邏輯而設計,撐不起媒體編碼那種動輒數秒到數分鐘的持續運算。檔案一落地就用 Storage 觸發器把工作「啟動」起來確實再適合不過,但真正的轉碼必須放在跑得動真正編碼器的地方。
- Deno 上沒有 child_process / subprocess,你無法執行 ffmpeg 二進位檔
- CPU 與總執行時間上限是為快速邏輯設計的,不是為媒體編碼
- Storage 觸發器很適合用來啟動工作,但實際運算必須放在別處
- 靜態編譯的 ffmpeg、WASM 與 layer 全都卡在執行環境本身,不只是檔案大小的問題
開發團隊在 Supabase 上執行 ffmpeg 的幾種嘗試
在 Fotovid 出現之前,你只有這些選項——每一個都是你不會想自己扛下來的工作。
| Option | What it costs you | Verdict |
|---|---|---|
| 把 ffmpeg 打包進你的 Supabase 函式 | Deno 沒有 child_process,根本啟動不了二進位檔 | |
| 自架容器或 VM | 全天候的機器成本,再加上更新、擴充與監控 | |
| 自建任務佇列 + worker | 多一整套基礎設施:佇列、worker、重試、死信處理 | |
| 在瀏覽器裡轉碼(WASM) | 速度慢、吃記憶體,在手機上還會直接當掉 | |
| 呼叫 Fotovid API | 一次 HTTPS 請求;不用自己跑、不用打包、不用擴充 |
三個步驟完成第一次呼叫
- 1免費取得 API 金鑰
註冊後建立一組金鑰。Fotovid 以用量計費的 credits 運作——$1 = 100 credits,多數操作只花 1 credit——所以你可以先把主打的浮水印呼叫串起來、從頭到尾完整測過一輪,再決定要不要花錢。
- 2從你的函式呼叫浮水印端點
在同一個 Edge Function 裡(或是上傳時觸發的 Storage 觸發器裡),帶上 Authorization: Bearer p6_<key_id>:<secret> 標頭,POST 到 https://api.fotovid.co/v1/video/watermark。送出標準的請求格式:一個指向影片 HTTPS URL 的 source_url——Supabase Storage 的簽章 URL 可以直接用——再加上描述疊加內容的 params 物件,例如 type 設為 image、一個 watermark_image_url、像 bottom-right 這樣的 position,以及 opacity 或 scale。你的函式只發出一次 HTTPS 請求;ffmpeg 的工作由 Fotovid 在平台外執行,所以你完全碰不到 Deno 的 CPU 與時間上限。
- 3使用託管的結果 URL
回應是扁平的 JSON:一個 id、一個 type,以及指向成品影片(由 Fotovid 託管)的 url。你可以把這個 url 直接回傳給呼叫端,或是下載下來、在 Supabase Storage 存一份自己的副本。請把託管 URL 視為暫時的——它帶有 expires_at——需要長期保存就自己留一份。
