Firebase 無主機開發 2026 完全指南:從 Cloud Functions 到 App Hosting,少寫一行伺服器配置的工程美學
Firebase 無主機開發 2026 完全指南:從 Cloud Functions 到 App Hosting,少寫一行伺服器配置的工程美學
我前陣子聽到一個案例:某家 SaaS 公司用 Firebase 開發 MVP,產品起飛後幾個月,使用者來到 1,000 萬,月帳單從 $1,200 飆到 $30,000,而且沒有任何告警,直接收到一張五位數帳單。最後他們花了三個月把後端整個改寫到 Supabase,月帳單回到 $25 (Horizon Dev 2026 比較報告 )。
這個故事我不是要嚇你「Firebase 不能用」,而是想說:無主機(Serverless)這條路,不是只有 firebase deploy 就萬事 OK。
Firebase 在 2026 年仍然是 BaaS 領域最完整的方案之一——根據 Tech Insider 2026 對比報告 與 Horizon Dev 比較 ,weekly npm downloads 約 320 萬,遙遙領先 Supabase 的 45 萬。但它的計費模式、Vendor Lock-in 風險、Firestore 與 SQL 思維的差異,每一項都可能讓沒做好功課的團隊吃苦頭。
這篇文章把官方文件、生產環境踩坑、2026 年最新定價、AI 整合(Genkit、Vertex AI)、和 Supabase 的最新對比通通整理在一起,讓你看完後能做出明確的架構決策——不只是「跟風用」,而是用得對、用得久、用得不爆預算。
本文前置知識:你需要對 Node.js / TypeScript、基礎雲端概念(容器、CDN、CI/CD)有一定理解。文中所有規格與定價以 2026 年 5 月官方文件為準。
一、什麼是 Firebase 無主機?拆解五層核心服務

「Serverless」字面意思是「沒有伺服器」,但這顯然不對——程式碼總得跑在某個地方。它的真正意涵是:伺服器的存在對你透明,你不用 SSH、不用 patch OS、不用設 nginx,雲端會在請求進來的瞬間動態分配資源,閒置時就回收。
Firebase 的無主機體系由五個核心組件構成:
| 組件 | 角色 | 主要負責 |
|---|---|---|
| Cloud Functions for Firebase | 運算層 | 執行後端邏輯、響應事件或 HTTPS 請求 |
| Cloud Firestore / Realtime Database | 資料層 | NoSQL 儲存與多端即時同步 |
| Firebase Authentication | 安全層 | 註冊登入、社群登入、多因素驗證 |
| Firebase Hosting / App Hosting | 部署層 | 靜態託管、SSR 應用、CDN 分發 |
| Cloud Storage for Firebase | 儲存層 | 圖片、影片等大型檔案 |
從架構視角看,這五層的關係是這樣的:
flowchart LR Client[Web / Mobile Client] -->|HTTPS| Hosting[Firebase Hosting / App Hosting] Client -->|SDK| Auth[Firebase Authentication] Client -->|SDK + Rules| FS[Cloud Firestore] Client -->|SDK| Storage[Cloud Storage] Hosting --> CF[Cloud Functions] Auth -.事件.-> CF FS -.事件.-> CF Storage -.事件.-> CF CF --> FS CF --> Storage
最關鍵的設計選擇在於:客戶端 SDK 直接打資料庫,不需要中間人(傳統的後端 API 伺服器)。這帶來兩個極端:
- 好處:開發者不用為每個 CRUD 寫 REST endpoint,前端工程師也能完成原本要兩個團隊才做得完的事
- 壞處:所有的權限驗證、資料 schema 防護,全靠 Security Rules 來把關。寫不好就是巨大的安全洞
每一層都有自己的 know-how。我們從跑邏輯的 Cloud Functions 開始拆。
二、Cloud Functions 1st vs 2nd Gen:終於不用為冷啟動煩惱了

Cloud Functions for Firebase 在 2022 年底推出第二代(2nd Gen),但很多 2020 年前的 Firebase 專案到今天還在跑 1st Gen——這幾乎可以說是「在用古董機種」。兩代差異不只是版本號,根本是不同層級的東西。
規格對比
引用自 官方 Firebase 版本對比文件 與 oneuptime 2026 v2 評測 :
| 規格 | 1st Gen | 2nd Gen |
|---|---|---|
| HTTP timeout | 9 分鐘(540s) | 60 分鐘(3600s) |
| 事件觸發 timeout | 9 分鐘 | 9 分鐘 |
| 最大記憶體 | 8 GB | 16 GiB(GA) |
| 最多 vCPU | 2 | 4(GA) |
| Concurrency | 1 req/instance | 預設 80,可設 1–1000 |
| 底層基礎 | Cloud Functions 原生 | Cloud Run + Eventarc |
| Min instances | 支援 | 原生支援 |
| Traffic splitting | 不支援 | 支援 |
最關鍵的差異是 concurrency。在 1st Gen 中,每個實例只能處理一個請求——意思是當 50 個請求同時湧入,系統就得啟動 50 個新實例,每個都要付出冷啟動代價(約 100ms 到數秒)。
但在 2nd Gen 中,一個實例可以同時處理最多 1000 個請求 。這意味著突發 50 個請求完全不會觸發冷啟動——一個實例就吃下了。
程式碼遷移範例
從 1st Gen 改寫到 2nd Gen,import 路徑是關鍵:
// 1st Gen — 舊版
const functions = require("firebase-functions/v1");
exports.helloWorld = functions.https.onRequest((req, res) => {
res.send("Hello from 1st Gen");
});
// 2nd Gen — 新版,加上 concurrency 設定
const { onRequest } = require("firebase-functions/v2/https");
exports.helloWorld = onRequest({
concurrency: 500, // 單一實例最多並行 500 請求
minInstances: 1, // 保持 1 個實例預熱,徹底消滅冷啟動
cpu: 1,
memory: "512MiB",
timeoutSeconds: 60,
}, (req, res) => {
res.send("Hello from 2nd Gen");
});
冷啟動三招實戰
冷啟動是無主機的「原罪」,但 2nd Gen 加上幾個技巧後幾乎可以忽略:
1. 設置 minInstances 對延遲敏感的函數(用戶登入、結帳),保留 1–2 個實例預熱。會多付一點錢,但首次請求延遲從 2 秒降到 50ms。
2. 延遲載入大型依賴
分析 Java Code Geeks 的 冷啟動深度報告 指出,JavaScript 函數的啟動時間幾乎全花在 require()/import:
// ❌ 全域載入:每次冷啟動都吃 800ms
const { BigQuery } = require("@google-cloud/bigquery");
exports.report = onRequest((req, res) => {
const bq = new BigQuery();
// ...
});
// ✅ 路徑內載入:只有實際用到時才載入
exports.report = onRequest((req, res) => {
if (req.path === "/heavy-report") {
const { BigQuery } = require("@google-cloud/bigquery");
const bq = new BigQuery();
// ...
}
});
3. 用 onInit() 推遲全域初始化
全域變數的初始化會在每次冷啟動時執行。把昂貴的初始化(連線池、SDK 客戶端)放進 onInit() hook,避免部署時 timeout。
Tip:1st Gen 還在運作,但 Google 已宣告 2025/02/18 起 1st Gen 強制使用 Artifact Registry 。新專案請直接從 2nd Gen 開始。
三、Firestore Security Rules:一張規則表救你十條 API

無主機架構下最大的安全爭議是「客戶端直接打資料庫」。傳統後端有 middleware 把關,Firebase 用什麼擋?答案是 Security Rules——一套部署在伺服器端、客戶端完全無法竄改的宣告式語言。
基本語法範例
service cloud.firestore {
match /databases/{database}/documents {
// 用戶只能讀寫自己的個人資料
match /users/{userId} {
allow read, write: if request.auth != null
&& request.auth.uid == userId;
}
// 任何登入者都能讀貼文,但只有作者能改/刪
match /posts/{postId} {
allow read: if request.auth != null;
allow create: if request.auth != null
&& request.resource.data.authorId == request.auth.uid;
allow update, delete: if request.auth != null
&& resource.data.authorId == request.auth.uid;
}
}
}
性能限制:那條 10 次 get() 的紅線
這是 Firebase 老手才知道的坑。根據 官方規則條件文件 ,規則中跨文件查詢有嚴格上限:
- 單一文件請求 / 查詢:最多 10 次
get()或exists() - 批次寫入 / 交易:總計 20 次,但每個操作仍受 10 次限制
- 超過任一上限 → permission denied error
舉個實際情境:
// ❌ 容易踩到 10 次上限的寫法
match /comments/{commentId} {
allow create: if get(/databases/$(database)/documents/posts/$(request.resource.data.postId)).data.authorId == request.auth.uid
|| get(/databases/$(database)/documents/admins/$(request.auth.uid)).data.role == "moderator"
|| get(/databases/$(database)/documents/teams/$(get(...).data.teamId)).data.members.hasAny([request.auth.uid]);
}
這種「rule 裡面跑 SQL」的寫法會立刻觸發上限。**正確解法是把權限資訊放進 Custom Claims **:
// ✅ 直接讀 token 裡的 custom claim,零 get() 呼叫
match /comments/{commentId} {
allow create: if request.auth.token.role in ["author", "moderator"];
}
註冊用戶時透過 Admin SDK 設定 claim:
import { getAuth } from "firebase-admin/auth";
await getAuth().setCustomUserClaims(uid, {
role: "moderator",
teamId: "team-42",
});
// 用戶下次 ID token 重新整理後就會帶上這些 claim
Tip:每個
get()/exists()都會被計算為一次 Firestore read,會收費——即使規則最終拒絕了請求。把權限放進 token 不只解決 10 次限制,也省下一筆讀取費用。
Security Rules 的其他冷知識限制
來自 code.build 規則完整指南 :
- 函數最多 7 個參數
- 最多 10 個
let變數 - 函數呼叫深度上限 20
- 單次請求最多評估 1000 個表達式
- 不支援 loop / recursion
這些限制乍看很嚴苛,但其實是為了讓規則評估維持在納秒級。如果你發現規則寫不下了,那是訊號——你的資料模型該重新設計了。
四、突破單一文件 1 寫/秒:分片計數器實戰

Firestore 對單一文件的寫入頻率有個硬性限制:約每秒 1 次(受 官方 best practices 文件 證實)。對「按讚數」、「即時觀看人數」、「投票統計」這類場景,1 寫/秒根本不夠用。
解法是分片計數器(Distributed Counters):把一個邏輯計數器拆成 N 個分片,寫入時隨機選一個。
完整實作範例
以下程式碼基於 oneuptime 2026 distributed counters 實作教學 :
import {
doc, setDoc, updateDoc, getDocs, collection,
increment, writeBatch, getFirestore
} from "firebase/firestore";
const db = getFirestore();
const NUM_SHARDS = 10;
// 1️⃣ 初始化(只做一次)
async function createCounter(counterPath) {
const batch = writeBatch(db);
batch.set(doc(db, counterPath), { numShards: NUM_SHARDS });
for (let i = 0; i < NUM_SHARDS; i++) {
batch.set(doc(db, `${counterPath}/shards/${i}`), { count: 0 });
}
return batch.commit();
}
// 2️⃣ 寫入:隨機挑分片(每秒可達 NUM_SHARDS 次寫入)
async function incrementCounter(counterPath, amount = 1) {
const shardId = Math.floor(Math.random() * NUM_SHARDS);
const shardRef = doc(db, `${counterPath}/shards/${shardId}`);
await updateDoc(shardRef, { count: increment(amount) });
}
// 3️⃣ 讀取:聚合所有分片
async function getCounterTotal(counterPath) {
const shardsSnap = await getDocs(collection(db, `${counterPath}/shards`));
let total = 0;
shardsSnap.forEach(snap => { total += snap.data().count; });
return total;
}
// 使用範例
await createCounter("counters/post-123-likes");
await incrementCounter("counters/post-123-likes");
const likes = await getCounterTotal("counters/post-123-likes");
寫入吞吐 vs 讀取成本的取捨
flowchart TB subgraph Write[寫入路徑] W1[Client 1] -->|increment| S0[Shard 0] W2[Client 2] -->|increment| S5[Shard 5] W3[Client 3] -->|increment| S9[Shard 9] end
subgraph Read[讀取路徑]
R[Client] -->|read all shards| Agg[Aggregate Sum]
Agg --> Total[Total Count]
end
S0 -.summed.-> Agg
S5 -.summed.-> Agg
S9 -.summed.-> Agg</div>
| 分片數 | 最大寫入吞吐 | 單次讀取成本 |
|---|---|---|
| 10 | 10 寫/秒 | 10 reads |
| 100 | 100 寫/秒 | 100 reads |
| 1000 | 1000 寫/秒 | 1000 reads |
明顯地,分片越多寫得越快,但每讀一次總和就要付 N 次 read 的錢。對讀多寫多的場景(社群媒體按讚),可以加一個 roll-up Cloud Function,定期把所有分片加總寫到一個單一的「rollup 文件」:
import { onSchedule } from "firebase-functions/v2/scheduler";
import { getFirestore } from "firebase-admin/firestore";
// 每分鐘聚合一次
export const rollupCounters = onSchedule("every 1 minutes", async () => {
const db = getFirestore();
const counterRef = db.doc("counters/post-123-likes");
const shards = await counterRef.collection("shards").get();
let total = 0;
shards.forEach(doc => { total += doc.data().count; });
await counterRef.update({ rollupTotal: total, rollupAt: new Date() });
});
前端只讀 counterRef 一次(1 read)就拿到接近即時的總數。
五、App Hosting vs Firebase Hosting:你該用哪個?

Firebase 在 2024 年中推出了 App Hosting,是給現代全端框架(Next.js、Angular、Astro)用的下一代託管方案。它和原本的 Firebase Hosting 差別很大,選錯會踩坑。
差異全表
引用 Firebase 官方部落格 App Hosting vs Hosting :
| 維度 | Firebase Hosting(原版) | Firebase App Hosting(2024+) |
|---|---|---|
| 適用場景 | 靜態網站 / SPA | 全棧 SSR / API routes |
| Framework 感知 | 部分(透過 web frameworks 實驗) | 原生 framework-aware |
| SSR 後端 | Cloud Functions | Cloud Run(直接) |
| 建置流程 | Firebase CLI | Cloud Native Buildpacks |
| 動態擴展 | 透過 Functions | 原生 Cloud Run scale-to-zero |
| GitHub 整合 | PR Preview Channels | 原生 Git push 部署 |
何時該用哪個?
用 Firebase Hosting(原版)的情況:
- 純前端 SPA(React、Vue、Svelte)
- 靜態文件網站(部落格、Marketing site)
- 需要極致 CDN 邊緣快取的場景
用 App Hosting 的情況:
- Next.js 13+(App Router、Server Components)
- Angular 17+ SSR
- 需要 API routes / middleware 的應用
- 想要 GitHub push 自動部署的工作流
Hosting 整合 GitHub 的「Git push 即部署」
執行 firebase init hosting:github 後,CLI 會幫你做這幾件事:
- 在 GCP 建立具部署權限的服務帳號
- 加密 JSON 金鑰並上傳到 GitHub Secrets
- 產生 YAML workflow,每個 PR 都會獲得獨立預覽 URL
- PR 合併到 main 後自動上線
對小團隊來說,這幾乎就是免費的 CI/CD pipeline,比起自己刻 GitHub Actions + AWS S3 簡單太多。
六、真實成本計算:Blaze、Supabase、VPS 三方對戰

成本是工程主管最關心的話題。我把 2026 年三方最新定價整理在一起,讓你看清楚不同規模下的真實差異。
Firebase Blaze 定價(2026/05)
引用自 Firebase 官方定價頁 與 Tekpon 2026 計算彙整 :
Firestore(資料層)
| 項目 | Spark 免費 | Blaze 計費 |
|---|---|---|
| Reads | 50K / 天 | $0.06 / 100K |
| Writes | 20K / 天 | $0.18 / 100K |
| Deletes | 20K / 天 | $0.02 / 100K |
| 儲存 | 1 GB | $0.108–$0.026 / GB(階梯) |
Cloud Functions(運算層)
| 項目 | Spark 免費 | Blaze 計費 |
|---|---|---|
| Invocations | 2M / 月 | $0.40 / 1M |
| GB-seconds | 400K / 月 | 隨資源量計 |
Hosting / Storage(部署與儲存層)
| 項目 | Spark 免費 | Blaze 計費 |
|---|---|---|
| Hosting 頻寬 | 10 GB / 月 | $0.15 / GB(cached)、$0.20 / GB(uncached) |
| Storage 流量 | — | $0.15 / GB egress |
| Auth phone SMS | — | $0.01–$0.06 / SMS |
2026/02/03 重大變更:Firebase Cloud Storage 現在強制需要 Blaze 計畫 ——即使你的用量在免費額度內。新專案如果只想用 Spark 計畫,得避開 Cloud Storage。
三種規模情境模擬
情境 A:MVP(1,000 DAU)
| 項目 | Firebase | Supabase | VPS(DigitalOcean) |
|---|---|---|---|
| 月費 | $0(Spark 涵蓋) | $0(Free tier) | $5–$20(固定) |
| 維運人力 | $0 | $0 | 工程師 20% 工時 |
| 小計 | $0 | $0 | $5 + 人力 |
情境 B:成長期(10,000 DAU、50K API/天)
| 項目 | Firebase | Supabase | VPS |
|---|---|---|---|
| Firestore / DB | $30 | $0 | $10(VPS DB) |
| Functions | $15 | $0 | $0 |
| Hosting + Storage | $10 | $0 | $5 |
| 小計 | $55 | $25(Pro 固定) | $25 + 人力 |
情境 C:規模化(10M DAU、read-heavy)
| 項目 | Firebase | Supabase | VPS |
|---|---|---|---|
| 資料庫 | $500–$1,500 | $200–$400 | 自管成本高 |
| Functions / Edge | $300–$800 | 含於 Pro | 自管 |
| 小計 | $1,000–$3,000 | $200–$600(3–5 倍便宜) | 複雜 |
數據驗證:Tech Insider 2026 對比 與 Horizon Dev 客戶案例 都指出 read-heavy 場景下 Supabase 比 Firebase 便宜 3–5 倍。
流量定價特別警告
如果你的應用是影音串流或大量檔案下載,Firebase Hosting 的 $0.20/GB egress 是個大坑。對比 GPU Per Hour 2026 egress 對比 :
| 平台 | Egress 單價(per TB) |
|---|---|
| Cloudflare R2 | $0(!) |
| Supabase | $90 |
| Google Cloud | $120 |
| Vercel | $150 |
| Firebase | $200 |
| Netlify | $550 |
對流媒體類產品,把靜態大檔案放 Cloudflare R2 + Firebase 處理動態邏輯是常見的混合架構。
七、生產踩坑:四個你絕對會遇到的問題

讀完官方文件就能寫出生產級應用的時代結束了。我把這四年看過的真實踩坑案例整理成四類——每一條都是某個團隊用真金白銀換來的教訓。
踩坑 1:把 SDK 滲透到業務邏輯(最深的鎖定)
// ❌ 業務邏輯直接呼叫 Firebase SDK
async function getUser(userId: string) {
const snap = await getDoc(doc(db, "users", userId));
return snap.data();
}
// ✅ 透過 Repository pattern 抽象
interface UserRepository {
findById(id: string): Promise<User | null>;
}
class FirestoreUserRepository implements UserRepository {
async findById(id: string) {
const snap = await getDoc(doc(db, "users", id));
return snap.exists() ? (snap.data() as User) : null;
}
}
// 業務層只依賴介面
async function getUser(userId: string, repo: UserRepository) {
return repo.findById(userId);
}
未來要遷到 Supabase / PostgreSQL 時,你只要新寫一個 PostgresUserRepository,業務層完全不動。
踩坑 2:把 Firestore 當 SQL 用(N+1 帳單炸彈)
// ❌ 渲染一個貼文列表,每篇貼文額外查作者 → N+1 reads
const posts = await getDocs(collection(db, "posts")); // 1 read × 100 = 100 reads
for (const post of posts.docs) {
const author = await getDoc(doc(db, "users", post.data().authorId)); // 100 reads
}
// 結果:渲染一個列表 = 200 reads,1000 個用戶看一次 = 200,000 reads
// ✅ 去規範化:把作者基本資訊存進貼文
// 寫入時:
await addDoc(collection(db, "posts"), {
title: "...",
content: "...",
authorId: user.uid,
authorName: user.displayName, // 冗餘
authorAvatar: user.photoURL, // 冗餘
});
// 讀取時:1 query 就拿到全部
const posts = await getDocs(collection(db, "posts")); // 100 reads only
「寧可複製 100 次小資料,也不要查 100 次資料庫」——這是 Firestore 的鐵律。
踩坑 3:全域初始化過載 → 部署 timeout
// ❌ 模組載入時就執行昂貴邏輯
import { GoogleAuth } from "google-auth-library";
const auth = new GoogleAuth({ /* ... */ });
const token = await auth.getAccessToken(); // 部署時就會跑 → timeout
export const myFunction = onRequest((req, res) => { /* ... */ });
// ✅ 用 onInit hook 推遲到實例真正啟動時
import { onInit } from "firebase-functions/v2/core";
let auth: GoogleAuth;
onInit(async () => {
auth = new GoogleAuth({ /* ... */ });
});
export const myFunction = onRequest((req, res) => {
// 在這裡 auth 已經初始化完成
});
踩坑 4:Security Rules 跨多文件 get() 觸發 10 次上限
承前面 Section 3 的範例,多層權限檢查很容易爆表。永遠優先用 Custom Claims,而不是寫巢狀 get()。
Q&A 補充:規則 deploy 後生效要多久?根據 zeriflow 安全最佳實踐 ,rules deployment 是原子操作,幾秒鐘內生效。但 client SDK 端可能因為網路快取延遲到 1 分鐘。生產部署時務必先在 Emulator Suite 跑完整測試。
八、AI 時代的 Firebase:Genkit 與 Vertex AI 整合

2026 年的 Firebase 已經不只是 BaaS——它正快速成為 AI 應用的後端首選。從 Firebase 在 Cloud Next 2026 的官方公告 加上社群觀察,三個值得注意的動向:
Genkit:開源 AI 應用框架
Genkit 是 Google Firebase 團隊推出的開源 AI 框架,支援 JS / Go / Python,提供統一介面接 Google、OpenAI、Anthropic、Ollama 等模型。
import { genkit, z } from "genkit";
import { googleAI } from "@genkit-ai/googleai";
const ai = genkit({
plugins: [googleAI()],
model: "googleai/gemini-2.5-flash",
});
export const summarize = ai.defineFlow(
{
name: "summarize",
inputSchema: z.string(),
outputSchema: z.string(),
},
async (text) => {
const { text: summary } = await ai.generate(`Summarize: ${text}`);
return summary;
}
);
flows 可以直接部署到 Cloud Functions / Cloud Run,所有 Telemetry 自動匯出到 Firebase Console。
Firebase AI Logic + Vertex AI
Firebase AI Logic 讓你直接從客戶端呼叫 Gemini 系列模型,免去自架 API Gateway。配合 App Check 確保只有你的 App 能呼叫。
最新支援的模型:
gemini-2.5-flash、gemini-2.5-flash-lite(生產推薦)imagen-4.0-generate-001、imagen-4.0-fast-generate-001、imagen-4.0-ultra-generate-001gemini-live-2.5-flash-native-audio(即時音訊)
注意 gemini-2.0-flash 系列將於 2026/06/01 停用,要遷到 2.5。
Google AI Studio + Firestore 全棧 = 自然語言寫 App
Cloud Next 2026 最重磅的更新是:Google AI Studio 現在直接整合 Firestore + Authentication ,可以用自然語言生成包含後端的全棧應用。底層用 Cloud Run 跑 server code,Security Rules 也能自動草擬。
對小型專案而言,這幾乎是「Vibe Coding」的終極形式。
九、決策清單:你該選 Firebase 還是 Supabase?
這個選擇沒有單一答案——同一家公司不同產品線可能要選不同方案。我把它拆成三個維度去問:你的產品在哪個階段?技術需求是什麼?規模有多大?
產品階段
| 階段 | 建議 | 理由 |
|---|---|---|
| MVP / 概念驗證 | Firebase | Auth、即時同步、CDN 開箱即用,可用免費額度撐 1–3 個月 |
| 已有 PMF、開始規模化 | 開始監控成本曲線 | 設定預算告警、檢視單頁 read 數 |
| 大規模生產(>100K DAU) | 重新評估 | 視 read/write 比例、流量類型決定是否遷移 |
技術需求
| 需求 | 建議 |
|---|---|
| 重度 mobile(iOS/Android/Flutter) | Firebase(離線快取、FCM 推播無人能敵) |
| 即時協作(聊天、Google Docs 級即時同步) | Firebase(Firestore listeners) |
| 複雜報表、多表 JOIN、聚合查詢 | Supabase / PostgreSQL |
| AI Agent 應用 | Firebase + Genkit |
| 大檔案下載 / 流媒體 | 混合架構(Firebase + Cloudflare R2) |
抽象層保險策略
無論最後選誰,在程式碼中保留抽象層是必做的。
// 把所有資料存取藏在 interface 後面
export interface DataStore {
users: UserRepository;
posts: PostRepository;
// ...
}
// 啟動時注入具體實作
const store: DataStore = useFirebase
? new FirebaseDataStore(db)
: new SupabaseDataStore(supabaseClient);
短期多寫一兩百行,長期省下你半年重構時間。
結語:不是不寫伺服器,是把伺服器寫進雲端基因
「無主機」聽起來像逃避,但它真正的意思是把伺服器的存在問題交給雲端、把心力放回業務邏輯上。
Firebase 在 2026 年做到的事情比 5 年前多太多了——2nd Gen Functions 解決了冷啟動、App Hosting 把 Next.js 部署簡化到極致、Genkit 讓 AI 應用三行 code 就能跑、AI Studio 開始能用自然語言寫全棧。
但你也看到了它的代價:Firestore 不是 SQL、Security Rules 有硬性上限、Egress 流量比同行貴一倍、Vendor Lock-in 風險真實存在。
回到開頭那家月帳單從 $1,200 飆到 $30,000 的 SaaS 公司——他們事後復盤發現,問題不是 Firebase「壞」,而是他們從第一天起就沒有任何抽象層,沒設預算告警,把 Firestore 當 PostgreSQL 用,列表頁觸發 N+1 reads。等到使用者破百萬,每多一個用戶就是一張帳單。
如果你正在開新專案,我會說:直接用 Firebase,但是寫 Repository 介面、設 Budget Alert、用 Custom Claims這三件事,請在第一週就做完。它們加起來不過半天工,能幫你避開 90% 的後悔。
無主機從來不是「免費的午餐」。它是一份你必須懂得怎麼吃的合約——讀懂它,你就能用一半的時間做出原本兩倍規模才做得出的產品。
延伸閱讀
- Firebase 官方文件 — Cloud Functions Version Comparison
- Firebase Blog — App Hosting vs Hosting 哪一個適合你?
- Firebase 官方文件 — Firestore Security Rules Conditions
- Firebase 官方文件 — Firestore Best Practices
- Firebase Blog — Cloud Next 2026 公告
- Genkit GitHub Repository
- Horizon Dev — Supabase vs Firebase 2026 startup 評測
- Tech Insider — Supabase vs Firebase 2026 三倍成本差距實測
- GPU Per Hour — 43+ 雲端供應商 Egress 定價總覽
- Java Code Geeks — Firebase Functions 冷啟動深度分析
這篇對你有幫助嗎? 如果你正在評估技術選型、或處理 Firebase 帳單失控的問題,歡迎留言分享你的踩坑經驗。下一篇我會寫「Firebase → Supabase 實戰遷移指南」,帶你看真實案例怎麼把 Firestore 結構翻譯成 PostgreSQL schema、Security Rules 改寫成 RLS。
本文最初發布於 HackMD @BASHCAT。
留言
張貼留言