簡介
雲端改變了我們設計系統的方式。從購買實體伺服器開始,我們現在可以運行程式碼而無需管理基礎架構。本文探討了雲端原生原則和無伺服器架構。
1. 12 要素應用程式
12 nguyên tắc thiết kế ứng dụng Cloud-Native:
1. Codebase: 1 repo, nhiều deploys (staging, prod)
2. Dependencies: Khai báo rõ ràng (package.json, requirements.txt)
3. Config: Lưu trong environment variables (không hardcode)
4. Backing: Database, cache, queue là attached resources
5. Build/Release/Run: Tách biệt 3 stages
6. Processes: Stateless processes (không lưu state in-memory)
7. Port binding: Self-contained, export via port
8. Concurrency: Scale out bằng processes
9. Disposability: Fast startup, graceful shutdown
10. Dev/Prod parity: Giữ dev, staging, prod giống nhau
11. Logs: Treat logs as event streams (stdout)
12. Admin: One-off admin tasks cũng là code
2. 無伺服器運算
2.1 FaaS(函數即服務)
Traditional Server:
┌──────────────────────────┐
│ Server (24/7 running) │
│ OS, Runtime, App │
│ Bạn quản lý TẤT CẢ │
│ Trả tiền 24/7 │
└──────────────────────────┘
Container (CaaS):
┌──────────────────────────┐
│ Container (on demand) │
│ Runtime, App │
│ Cloud quản lý OS, Infra │
│ Trả tiền khi container chạy │
└──────────────────────────┘
Serverless (FaaS):
┌──────────────────────────┐
│ Function (on invocation) │
│ Chỉ viết code │
│ Cloud quản lý EVERYTHING │
│ Trả tiền per invocation │
│ Auto scale 0 → ∞ │
└──────────────────────────┘
2.2 執行模型
Request 1: → Cold Start (init container) → Execute → Return
Request 2: → Warm (reuse container) → Execute → Return
Request 3: → Warm (reuse container) → Execute → Return
... (idle 15 min) ...
Request 4: → Cold Start (new container) → Execute → Return
Cold Start Timeline:
├── Download code (100-500ms)
├── Init runtime (50-200ms)
├── Init dependencies (100-2000ms)
├── Execute function (varies)
└── Total cold start: 500ms - 5s
Mitigation:
- Provisioned concurrency (keep warm)
- Smaller packages (fewer dependencies)
- Choose fast runtimes (Go, Rust > Java, .NET)
3. 無伺服器模式
3.1 API閘道+Lambda
Client ──► API Gateway ──► Lambda ──► DynamoDB
│
├──► /users → UserFunction
├──► /orders → OrderFunction
└──► /search → SearchFunction
Ưu điểm: Auto-scale, pay per request
Nhược điểm: Cold start, 15m timeout limit
3.2 事件驅動的無伺服器
┌──────────┐ ┌────────┐ ┌──────────┐
│ S3 │────►│ Lambda │────►│ DynamoDB │
│ Upload │ │ Process│ │ Metadata │
└──────────┘ │ image │ └──────────┘
└────┬───┘
│
┌────▼───┐
│ S3 │
│ Thumb │
└────────┘
Events trigger functions:
- S3: File uploaded → Lambda resize
- SQS: Message → Lambda process
- DynamoDB Streams: Record change → Lambda sync
- CloudWatch: Schedule → Lambda cron job
- API Gateway: HTTP request → Lambda handler
3.3 無伺服器 Web 應用程式
┌──────────────────────────────────────────────────┐
│ │
│ CloudFront (CDN) │
│ │ │
│ ┌────▼────┐ │
│ │ S3 │ ← Static files (React/Vue SPA) │
│ │ Bucket │ │
│ └─────────┘ │
│ │
│ API Gateway → Lambda Functions │
│ │ │ │
│ │ ┌────▼─────┐ ┌──────────┐ │
│ │ │ DynamoDB │ │ Cognito │ │
│ │ │ (data) │ │ (auth) │ │
│ │ └──────────┘ └──────────┘ │
│ │ │
│ ┌────▼─────┐ │
│ │ SQS │ → Lambda (background) │
│ └──────────┘ │
└──────────────────────────────────────────────────┘
Chi phí (100K requests/tháng):
Lambda: ~$0.20
API Gateway: ~$3.50
DynamoDB: ~$1.00
S3 + CloudFront: ~$1.00
Total: ~$6/tháng (vs EC2 ~$20+/tháng)
4. 容器編排
4.1 Kubernetes 概述
┌─────────────────────────────────────────────────┐
│ Kubernetes Cluster │
│ │
│ Control Plane: │
│ ┌──────────┐ ┌──────────┐ ┌──────────┐ │
│ │API Server│ │Scheduler │ │Controller│ │
│ │ │ │ │ │Manager │ │
│ └──────────┘ └──────────┘ └──────────┘ │
│ │
│ Worker Nodes: │
│ ┌────────────────────────────────────────┐ │
│ │ Node 1 │ │
│ │ ┌──────────┐ ┌──────────┐ ┌────────┐ │ │
│ │ │Pod: App-1│ │Pod: App-2│ │Pod: DB │ │ │
│ │ └──────────┘ └──────────┘ └────────┘ │ │
│ └────────────────────────────────────────┘ │
│ ┌────────────────────────────────────────┐ │
│ │ Node 2 │ │
│ │ ┌──────────┐ ┌──────────┐ │ │
│ │ │Pod: App-3│ │Pod: Cache│ │ │
│ │ └──────────┘ └──────────┘ │ │
│ └────────────────────────────────────────┘ │
└─────────────────────────────────────────────────┘
K8s quản lý: Scheduling, Scaling, Self-healing,
Rolling updates, Service discovery, Load balancing
4.2 無伺服器、容器、虛擬機
| 特性 | 虛擬機器 | 貨櫃 | 無伺服器 |
|---|---|---|---|
| 新創公司 | 分鐘 | 秒 | 毫秒* |
| 縮放 | 手動/自動 | 汽車(K8s) | 即時 |
| 管理 | 完整版(作業系統+應用程式) | 應用程式 + 運行時 | 僅程式碼 |
| 成本模型 | 每小時 | 每小時 | 每次呼叫 |
| 最大運行時間 | 無限 | 無限 | 15 分鐘 |
| 狀態 | 有狀態 | 有狀態 | 無國籍 |
| 供應商鎖 | 低 | 低 | 高 |
5. 何時使用無伺服器?
✅ Dùng khi:
- Event-driven workloads (file processing, webhooks)
- Sporadic traffic (low/unpredictable)
- Rapid prototyping
- Scheduled tasks (cron jobs)
- Chatbots, IoT backends
- APIs with low-medium traffic
❌ KHÔNG dùng khi:
- Consistent high traffic (vì cost cao hơn containers)
- Long-running processes (> 15 minutes)
- Need WebSocket/persistent connections
- Heavy computation (ML training)
- Latency-sensitive (cold start vấn đề)
- Complex stateful workflows
6. 緩解供應商鎖定
Vấn đề: AWS Lambda code khó chạy trên GCP/Azure
Mitigation:
1. Serverless Framework / SAM / CDK:
Abstract cloud-specific config
2. Hexagonal Architecture:
Business logic tách biệt handlers
// Handler (cloud-specific)
export const handler = async (event) => {
return await orderService.createOrder(
parseRequest(event) // adapter
);
};
// Business logic (portable)
class OrderService {
async createOrder(data) { ... }
}
3. Multi-cloud tools:
Knative (serverless on K8s)
OpenFaaS (self-hosted FaaS)
總結
| 方法 | 最適合 | 權衡 |
|---|---|---|
| 雲端虛擬機 | 傳統,有狀態 | 完全控制,高操作 |
| 容器+K8s | 微服務 | 靈活、複雜的操作 |
| 無伺服器 FaaS | 事件驅動、可變負載 | 簡單,供應商鎖定 |
| 無伺服器容器 | 混合工作負載 | 平衡控制/簡單 |
練習
-
架構選擇: 新創SaaS:團隊3,API + Web儀表板,初始1K用戶,成長不確定。比較:無伺服器(Lambda + DynamoDB)與容器(ECS/K8s + PostgreSQL)。選擇哪一個?
-
12 因素審核: 審查您目前(或想像的)申請。檢查 12 個因素,列出哪些因素違規以及如何解決。
-
遷移計畫: Monolith Spring Boot 應用程式(10 個端點、PostgreSQL、Redis、cron 作業)。編寫向無伺服器遷移的計劃。哪個端點適合 Lambda?哪一個應該容納容器?