Lời dẫn
Nói trước kẻo mất lòng: bài này dành cho website, blog cá nhân, kiểu ngày có vài chục người vào, trong đó chắc 7 người là mình, 2 người là vợ mình, còn lại là bot Google.
Còn anh em nào làm web bán hàng traffic cả triệu, chạy flash sale 12.12, thì mời quay xe. Bài này không dành cho các anh, các anh giàu rồi, thuê hẳn kỹ sư DevOps đi.
Blog cá nhân thì đặc điểm là: ít người đọc, nhiều người tự ái. Thời gian đầu request lèo tèo, mà mình thì muốn tiết kiệm tiền để còn uống trà sữa. Vậy tính sao?
Phương án "truyền thống": thuê VPS
Cách phổ biến nhất: lên DigitalOcean thuê một con VPS, cài hết mọi thứ lên đó: web, database, nginx, redis, cả con mèo nếu nhét vừa.
- Gói rẻ nhất: $4/tháng, RAM 512MB. Nghe thì ngon, nhưng cứ bundle install hay assets:precompile là máy thở oxy, chết đứng giữa chừng. RAM 512MB chạy Rails cũng giống cho xe Wave chở tủ lạnh.
- Gói tối thiểu dùng được: $6/tháng, RAM 1GB, tức khoảng 160k/tháng.
160k thì cũng không phải nhiều, nhưng mà là 160k đều như vắt chanh, dù cả tháng blog có ma nào vào hay không thì tháng tháng cũng mất mấy ly trà sữa đấy.

Phương án "nói phét nhưng có thật": chạy serverless
Trong bài này, mình sẽ khoe bộ đồ nghề mình dùng để launch chính blog này, với chi phí khoảng 90k/tháng, tức cỡ 3k/ngày, đúng giá một ly trà đá vỉa hè. Rẻ bằng khoảng một nửa thuê VPS.
Đã thế còn xịn hơn: mỗi service chạy độc lập, không nhồi chung một server. App một nơi, database một nẻo, secret một chỗ, build một chỗ. Nghe cứ như kiến trúc của Netflix, chỉ khác là Netflix có người xem.
Anh em đọc xong, ngoài blog ra còn được thêm cái view về kiến trúc infra, đi phỏng vấn có cái để chém.
Cần chuẩn bị gì?
Đi cày thì cần có ruộng mới cày được chớ, phải không anh em. Nên là anh em cần 1 cái website đơn giản. Cái này bài không dạy được, bài chỉ dạy ném code lên mây thôi.
Ở đây mình dùng Ruby on Rails, vì mình là người có gu (và vì mình chỉ biết mỗi Rails).
Ngoài ra cần:
- Một tài khoản Google Cloud (có gắn thẻ, yên tâm là với traffic kiểu blog mình thì Google trừ tiền chắc cũng ngại)
- Một tài khoản TiDB Cloud
- Một cái domain (không có cũng được, nhưng blog-cua-toi-abc123-uc.a.run.app thì hơi khó in lên danh thiếp)
- Docker cơ bản
- Tinh thần thép khi đọc bill cuối tháng (nhưng yên tâm, không đau đầu)
Đội hình ra sân
| Vị trí | Cầu thủ | Nhiệm vụ | Tiền lương |
|---|---|---|---|
| Tiền đạo | Cloud Run | Chạy app Rails | Gần như free |
| Tiền vệ | Cloud Build | Build Docker image, deploy | Free tier dư dùng |
| Hậu vệ | Artifact Registry | Giữ Docker image | Vài nghìn lẻ |
| Thủ môn | Secret Manager | Giữ RAILS_MASTER_KEY, mật khẩu DB |
Gần như free |
| Tuyển thủ nhập tịch | TiDB Cloud | Database MySQL-compatible, serverless | Free tier |
1. Cloud Run: server "có mà như không"
Điểm ăn tiền của Cloud Run: không ai vào thì không tính tiền. App không có request thì Cloud Run cho nó ngủ, scale về 0 instance. Có người vào thì nó dậy phục vụ.
So với VPS chạy 24/7 kể cả lúc 3h sáng không ma nào vào, thì đây là mô hình "ăn bao nhiêu trả bấy nhiêu" đúng nghĩa.
Free tier hàng tháng của Cloud Run cho vài triệu request cùng một đống vCPU-giây và GiB-giây. Với blog cá nhân thì khả năng cao bạn còn chẳng tiêu hết phần free.
Nhược điểm (thành thật khai báo): cold start. Người đầu tiên vào sau một lúc lâu sẽ phải đợi vài giây cho Rails "ngủ dậy, đánh răng, rửa mặt". Mình gọi đó là tính năng: tạo cảm giác blog được tải công phu, trân trọng từng lượt xem.
À, cái cold start này, mỗi lần start server cũng tốn tiền nhé. Cuối bài mình sẽ bày tip trick để xử đẹp cái này.
2. Cloud Build + Artifact Registry: dây chuyền sản xuất
Tạo tag trên GitHub là Cloud Build tự build Docker image, đẩy vào Artifact Registry, rồi deploy lên Cloud Run.
Quan trọng là có đoạn giới hạn số lượng instance:
- --min-instances=0
- --max-instances=2
- --min-instances=0: đây chính là bí kíp tiết kiệm. Đặt lên 1 là hết trà đá, chuyển sang trà sữa full topping.
- --max-instances=2: phòng khi bài viết lỡ viral hoặc bị bot spam, bill không bay lên trời. Blog cá nhân mà cần hơn 2 instance thì chúc mừng, bạn nổi tiếng rồi, đi làm KOL đi.
3. Secret Manager: két sắt
RAILS_MASTER_KEY và chuỗi kết nối database mà hardcode vào code rồi push lên GitHub công khai thì xin chúc mừng, bạn vừa làm từ thiện cho hacker.
Cất hết vào Secret Manager, rồi dùng --set-secrets để Cloud Run nạp vào biến môi trường. Nhớ cấp quyền Secret Manager Secret Accessor cho service account của Cloud Run, không thì app dậy xong sẽ ngơ ngác như người mất ví.
- --set-secrets=RAILS_MASTER_KEY=rails-master-key:latest,DATABASE_URL=database-url:latest
4. TiDB Cloud: database xịn, giá bèo
Đây là "tuyển thủ nhập tịch" của đội hình. Cloud SQL của Google thì xịn thật, nhưng rẻ nhất cũng tốn cả trăm nghìn mỗi tháng, bằng nguyên cái VPS mình đang chê.
TiDB Cloud có gói serverless với free tier khá rộng rãi, lại tương thích MySQL, nên Rails dùng adapter mysql2 hay trilogy là chạy, gần như không phải sửa gì. Chọn region Singapore cho gần Cloud Run ở asia-southeast1, query đi qua lại nhanh như người yêu cũ lướt qua đời bạn.
Tổng kết hóa đơn
| Khoản | VPS DigitalOcean | Combo nói phét của mình |
|---|---|---|
| Server | ~160k/tháng, chạy cả khi không ai xem | Gần như 0đ nhờ free tier + scale về 0 |
| Database | Tự cài, tự backup, tự khóc | TiDB free tier, backup có sẵn |
| Deploy | SSH vào gõ lệnh tay | git push rồi đi uống nước |
| Bảo mật secret | File .env nằm chỏng chơ |
Secret Manager |
| Tổng | ~160k/tháng | ~90k/tháng ≈ 3k/ngày ≈ 1 ly trà đá |
Tránh cold start và tối ưu chi phí.
Mặc định khi không có request, cloudrun sẽ tự động chuyển sang chế độ ngủ đông. Khi có request mới bắt đầu "đánh răng, rửa mặt, tỉnh giấc" thời gian mất vài seconds.
Có một điều mình mới nhận thấy, chưa kiểm chứng: Một ngày mà cloudrun tỉnh giấc vài lần thì sẽ chi phí cũng tốn kha khá đấy. Mình tìm hiểu thì thấy được giải thích thế này: cloudrun tính tiền CPU theo thời gian phục vụ, tức là mỗi khi nó start, là nó tính tiền rồi. Còn khi nó đang tỉnh, thì nó chỉ tính tiền trên mỗi request nó phục vụ mà thôi.
Nên mình trick bằng cách tạo uptime check 1 phút 1 lần. Như vậy mỗi phút nó phục vụ 1 requests (khoảng vài ms), và container không bị cold down, phục vụ xong 1 requests, nó vẫn trong trạng thái ấm, nên sẵn sàng phục vụ request tiếp theo, không phải chờ, vừa tốn ít chi phí tính thời gian phục vụ start.

Mấy ngày đầu, mình chưa setup uptime check.
Lời kết
Vậy là với số tiền một ly trà đá mỗi ngày, bạn đã sở hữu một hệ thống:
- Tự động scale (từ 0 lên 2, nhưng vẫn là scale)
- CI/CD chuẩn chỉnh
- Database tách riêng, secret cất két
- Kiến trúc đủ để đi phỏng vấn chém gió 30 phút
Chúc anh em deploy không lỗi, bill không giật mình, trà luôn đủ đá.
À mà nếu chi phí có đắt hơn, thì là do trà đá tăng giá nha anh em, giờ cũng 4k 5k / cốc rồi đấy