Skip to content

Thiết kế hệ thống phong cách FAANG: Làm chủ framework 4S và 5 thiết kế kinh điển

By Nhân Nguyễn on Apr 28, 2026

Thiết kế hệ thống phong cách FAANG: Làm chủ framework 4S và 5 thiết kế kinh điển

Chào mừng bạn đến với thế giới của những vòng phỏng vấn System Design tại các công ty công nghệ hàng đầu (FAANG). Nếu bạn đã dành hàng trăm giờ để chinh phục các bài toán thuật toán trên LeetCode, thì đây chính là chân trời tiếp theo bạn cần khám phá. Vòng thiết kế hệ thống không chỉ kiểm tra kiến thức kỹ thuật, mà còn đánh giá khả năng đánh đổi (trade-off), tư duy về quy mô (scale) và giao tiếp của bạn.

Bài viết này sẽ cung cấp cho bạn một lộ trình rõ ràng, được đúc kết từ những thiết kế kinh điển nhất. Chúng ta sẽ cùng nhau mổ xẻ Framework 4S — khung cấu trúc câu trả lời “bất bại” trong 45 phút, và đi sâu vào 5 thiết kế biểu tượng: URL Shortener, News Feed (Twitter), Ride Sharing (Uber), Chat App (WhatsApp) và Video Streaming (YouTube).


[1] Framework 4S: Cấu trúc “Vàng” cho mọi buổi phỏng vấn

Trong một vòng phỏng vấn kéo dài 45 (cho L4) đến 60 phút (cho L5+), thời gian là vàng bạc. Bạn không thể nói lan man. Framework 4S sẽ giúp bạn kiểm soát nhịp độ và đảm bảo không bỏ sót bất kỳ khía cạnh quan trọng nào. Nó đại diện cho 4 bước: Scenario, Service, Storage, Scale. Hãy nghĩ về nó như việc xây một ngôi nhà: trước tiên bạn phải hiểu ai sẽ ở, bao nhiêu người (Scenario); sau đó mới vẽ kiến trúc tổng thể (Service); tiếp đến là thiết kế cách sắp xếp đồ đạc, tủ kệ (Storage); và cuối cùng là gia cố cho nó chịu được bão lũ, đông người (Scale).

graph LR
    A[S1: Scenario (5 phút)] --> B[S2: Service (10 phút)];
    B --> C[S3: Storage (10 phút)];
    C --> D[S4: Scale (15 phút)];
    D --> E[Q&A (5 phút)];

S1: Scenario — Đặt câu hỏi để phá băng (5 phút)

Nhiều ứng viên mắc sai lầm chí mạng là “cắm đầu” vẽ ngay kiến trúc mà không một câu hỏi nào. Đây là bước bạn thể hiện tư duy sản phẩm và khả năng ước lượng. Nhiệm vụ của bạn là làm rõ ba thứ:

  1. Yêu cầu chức năng (Functional Requirements - FR): Người dùng có thể làm gì? Đâu là tính năng lõi, đâu là “nice-to-have”?
  2. Yêu cầu phi chức năng (Non-Functional Requirements - NFR): Hệ thống cần “ngon” đến mức nào? (Độ trễ, tính sẵn sàng, tính nhất quán…)
  3. Ước lượng quy mô (Capacity Estimation): Chúng ta đang nói đến bao nhiêu người dùng, bao nhiêu dữ liệu?

Mẹo “sinh tồn” cho S1: Đừng hỏi những câu có sẵn trong đề bài. Hãy hỏi để làm rõ. Bạn có thể dùng bộ câu hỏi mẫu sau như một cái “phao”:

  • “Tôi giả định hệ thống này sẽ có 100 triệu người dùng hoạt động hàng ngày (DAU), tỉ lệ đọc/ghi là 100:1. Liệu giả định này có hợp lý không?"
  • "Chúng ta cần đảm bảo độ trễ P99 (99% request nhanh nhất) dưới 100ms, và tính nhất quán cuối cùng (eventual consistency) là chấp nhận được. Anh/chị thấy sao?”

Bảng “bỏ túi” về ước lượng dung lượng: Đây là những con số bạn nên thuộc nằm lòng để nhanh chóng tính QPS (Query Per Second - Số truy vấn mỗi giây) và dung lượng lưu trữ.

MụcGiá trị ước tính cho dễ nhớ
1 ngày~ 100,000 giây (86,400s)
1 ký tự (char)1-4 bytes (UTF-8 trung bình 2 bytes)
1 UUID16 bytes (binary) hoặc 36 bytes (string)
1 Tweet~ 560 bytes (280 ký tự × 2)
1 tấm ảnh (JPEG)500 KB - 5 MB
1 phút video~ 10 MB
Độ trễ đọc RAM100 ns (nano giây)
Độ trễ đọc SSD0.1 ms (mili giây)
Độ trễ khứ hồi US-EU100 ms

S2: Service — Vẽ bản thiết kế (10 phút)

Đây là lúc bạn bắt đầu vẽ các hộp và mũi tên (box-and-arrow). Sơ đồ của bạn nên trừu tượng nhưng không mơ hồ. Một kiến trúc High-Level Design (HLD) điển hình sẽ có các thành phần:

Client → CDN → Load Balancer → API Gateway → Services → Cache / DB / Message Queue → Workers / Storage

Ví dụ, bạn có thể phác thảo các API chính (top 5) một cách gọn gàng:

POST /api/v1/users - Tạo tài khoản POST /api/v1/login - Đăng nhập, trả về token GET /api/v1/feed/{userId} - Lấy bảng tin POST /api/v1/posts - Đăng bài viết mới GET /api/v1/post/{postId} - Xem chi tiết bài viết

Việc liệt kê API ngay từ đầu giúp bạn và người phỏng vấn thống nhất về “hợp đồng” (contract) của hệ thống, tránh hiểu nhầm về sau.

S3: Storage — Chọn “tủ đựng đồ” (10 phút)

Đây là nơi bạn thể hiện sự uyên bác về cơ sở dữ liệu. Bạn cần trả lời 3 câu hỏi: (1) Chọn loại DB nào? (2) Schema (lược đồ) ra sao? (3) Sharding (phân mảnh) như thế nào?

Ma trận lựa chọn Database “cứu cánh”:

Khi bạn cần…Lựa chọn ưu tiên
Giao dịch ACID (tính nguyên tử, nhất quán), truy vấn phức tạpPostgreSQL, MySQL
Quy mô khổng lồ, tính nhất quán cuối cùng (eventual)Cassandra, DynamoDB
Dữ liệu dạng tài liệu (JSON) linh hoạtMongoDB, DocumentDB
Tìm kiếm toàn văn bản (Full-text search)Elasticsearch
Cache (bộ nhớ đệm)Redis, Memcached
Lưu trữ file/đối tượng (Object Storage)Amazon S3, Google Cloud Storage
Dữ liệu chuỗi thời gian (Time-series)InfluxDB, TimescaleDB

Giải thích thuật ngữ:

  • ACID: Bộ thuộc tính của giao dịch database đảm bảo dữ liệu hợp lệ dù có lỗi xảy ra.
  • ACID transactions (giao dịch ACID): Một tập hợp các thao tác database được coi là một đơn vị logic duy nhất, đảm bảo tính toàn vẹn dữ liệu.
  • Eventual consistency (tính nhất quán cuối cùng): Một mô hình mà dữ liệu sẽ được đồng bộ trên tất cả các node sau một khoảng thời gian, chấp nhận sự không nhất quán tạm thời để đổi lấy hiệu năng và khả năng mở rộng.

S4: Scale — “Gia cố” cho “ngôi nhà” (15 phút)

Đây là phần khó nhất và cũng là lúc bạn tỏa sáng. Mọi kiến trúc đẹp đẽ đều có điểm yếu. Hãy chủ động chỉ ra và giải quyết chúng bằng “bottleneck checklist” (danh sách điểm nghẽn) này:

  1. Đọc quá nhiều? -> Dùng Cache (Redis), CDN.
  2. Ghi quá nhiều? -> Dùng Hàng đợi bất đồng bộ (Message Queue như Kafka, SQS) để tách biệt luồng xử lý.
  3. Điểm nóng (Hot key)? -> Dùng Consistent Hashing và nhân bản dữ liệu ở các node nóng.
  4. Điểm chết đơn lẻ (SPOF - Single Point of Failure)? -> Nhân bản (Replication), triển khai trên nhiều vùng sẵn sàng (Multi-AZ).
  5. Độ trễ cao ở các khu vực địa lý khác nhau? -> Triển khai đa vùng (Geo-distributed), dùng DNS để định tuyến đến máy chủ gần nhất.

Nghệ thuật đánh đổi (Trade-offs): Người phỏng vấn muốn nghe bạn phân tích “được - mất”. Đừng chỉ nói “Tôi chọn Cassandra”. Hãy nói: “Tôi chọn Cassandra thay vì MySQL vì chúng ta cần khả năng ghi cao (write throughput). Tuy nhiên, chúng ta phải hy sinh các giao dịch ACID phức tạp và chấp nhận tính nhất quán cuối cùng. Điều này chấp nhận được vì bảng tin của người dùng có thể hiển thị chậm 1-2 giây.” Một framework hữu ích khác cần ghi nhớ là Định lý CAP và phần mở rộng PACELC:

  • CAP (Consistency, Availability, Partition Tolerance): Trong một hệ thống phân tán, khi xảy ra sự cố phân vùng mạng (network partition), bạn chỉ có thể chọn một trong hai: Tính nhất quán (CP) hoặc Tính sẵn sàng (AP).
  • PACELC: Mở rộng của CAP, nhấn mạnh rằng ngay cả khi hệ thống không có sự cố phân vùng (else - E), bạn vẫn phải đánh đổi giữa Độ trễ (Latency - L) và Tính nhất quán (Consistency - C).

[2] 5 Thiết kế Hệ thống Kinh điển (Walk-through)

Giờ là lúc áp dụng 4S vào thực tế. Chúng ta sẽ đi qua 5 “tượng đài” mà bất cứ ai luyện System Design cũng phải biết.

Thiết kế 1: URL Shortener (Dạng bài “Cơ bản mà chí mạng”)

Đây thường là bài thiết kế khởi đầu.

  • S1 Scenario:

    • FR: Rút gọn URL dài thành ngắn, khi truy cập link ngắn thì chuyển hướng (redirect) sang link gốc. Có thể có thêm analytics, custom alias.
    • NFR: Tạo 100M link/ngày (1.000 lượt ghi/giây), tỉ lệ Đọc:Ghi là 100:1 (100.000 lượt đọc/giây), độ trễ P99 < 100ms.
  • S3 Storage:

    • Schema (Cassandra/DynamoDB): short_code (Khóa chính), long_url, user_id, created_at, expiry.
    • Tạo short code: Đây là bài toán thú vị. Thuật toán mã hóa base62 (dùng 62 ký tự [a-z, A-Z, 0-9]) từ một số nguyên tuần tự (counter) là phổ biến nhất. Với 7 ký tự, bạn có tới 62^7 ~ 3.500 tỷ URL.
  • S4 Scale & Bottlenecks:

    • Nút thắt 100K lượt đọc/giây: Dùng Redis cache với chính sách hết hạn (TTL). Tỉ lệ cache hit 80% giúp giảm tải cho DB chính.
    • Nút thắt sinh ID đơn điệu: Mỗi máy chủ ứng dụng được cấp trước một dải số từ ZooKeeper, tránh tranh chấp khóa tập trung.
    • Nút thắt về lưu trữ 45 TB: Phân mảnh (shard) dữ liệu trên nhiều node bằng Consistent Hashing dựa trên short_code.

    Giải thích Consistent Hashing: Một kỹ thuật phân tán dữ liệu giúp giảm thiểu số lượng dữ liệu phải di chuyển khi thêm hoặc bớt node trong cụm. Thay vì hash(key) % N (với N là số server), nó sắp xếp các server và key trên một vòng tròn hash.

Thiết kế 2: News Feed (Twitter/Facebook) - “Bài toán Fan-out”

Bài toán kinh điển về việc tối ưu hóa giữa chi phí đọc và chi phí ghi.

  • S1 Scenario: 200M DAU, mỗi người theo dõi ~200 người, đăng 2 tweet/ngày.
  • S3 Storage:
    • Tweets Table (Cassandra): Phân vùng theo tweet_id.
    • Timelines (Redis): Mỗi user có một list trong Redis (user:{userId}:home_timeline) chứa ID của các tweet mới nhất, được sắp xếp theo thời gian. Dùng lệnh LPUSH để thêm và LTRIM để giới hạn kích thước (ví dụ 800 tweet).
  • S4 Scale & Bottlenecks - Vấn đề “Justin Bieber”:
    • Cách 1: Pull (Fan-out khi đọc): Khi bạn mở app, hệ thống vào DB lấy tất cả tweet từ ~200 người bạn follow, trộn lại và hiển thị. -> Ưu điểm: Ghi rẻ. Nhược điểm: Đọc rất chậm với người follow nhiều người.
    • Cách 2: Push (Fan-out khi ghi): Khi bạn đăng tweet, hệ thống “đẩy” tweet đó vào Timeline list của tất cả người theo dõi bạn. -> Ưu điểm: Đọc siêu nhanh (load 1 list trong Redis). Nhược điểm: Ghi cực kỳ đắt với Celebrity có 100M follower.
    • Giải pháp lai (Hybrid - Industry Standard): Dùng Push cho người dùng thường và Pull cho Celebrity (khi follower > 10,000). Khi bạn mở feed, hệ thống sẽ “trộn” timeline được Push của bạn với các tweet được Pull từ các Celebrity bạn follow.

Thiết kế 3: Ride Sharing (Uber) - “Vũ điệu định vị”

Bài toán về dữ liệu không gian-thời gian và độ trễ cực thấp.

  • S1 Scenario: 1 triệu tài xế online, ping vị trí mỗi 4 giây -> 250K lượt ghi/giây.
  • S3 Storage:
    • Driver Location (Redis với lệnh GEO): Dùng GEOADD để cập nhật tọa độ và GEORADIUS để tìm tài xế xung quanh hành khách trong bán kính 5km.
  • S4 Scale:
    • Phân mảnh theo Geohash: Thế giới được chia thành các ô địa lý (geohash). Mỗi ô được quản lý bởi một server riêng. Khi tìm tài xế, server chỉ cần truy vấn 9 ô (3x3) quanh vị trí hành khách. Điều này cho phép song song hóa ở mức tối đa.
    • Kết nối thời gian thực (WebSocket): Cả app của tài xế và người dùng đều duy trì kết nối WebSocket hai chiều với máy chủ. Khi có cuốc xe mới, hệ thống sẽ “đẩy” thông báo match đến tài xế thay vì để tài xế liên tục “hỏi”.

Thiết kế 4: Chat App (WhatsApp) - “Mạng lưới kết nối bền vững”

Bài toán về hàng triệu kết nối đồng thời và độ tin cậy của tin nhắn.

  • S1 Scenario: 2 tỷ người dùng, 1 tỷ DAU, 100 tỷ tin nhắn/ngày (1.2 triệu tin/giây).
  • S3 Storage:
    • Messages (Cassandra): Phân vùng theo chat_id, sắp xếp theo message_id (gắn timestamp).
    • User Connections (Redis): Một map đơn giản: online:{user_id} -> "server_id_42" (máy chủ nào đang nắm kết nối của user này).
  • S4 Scale:
    • Luồng gửi tin nhắn: A gửi tin -> Máy chủ của A lưu vào Cassandra -> Tra cứu Redis thấy B đang online ở server_42 -> Chuyển tiếp tin nhắn qua RPC nội bộ tới server_42 -> server_42 “đẩy” tin nhắn qua WebSocket tới app của B.
    • Group Chat Fan-out: Một tin nhắn cần được gửi tới 256 thành viên. Dùng một Kafka topic cho mỗi nhóm. Các worker tiêu thụ message từ topic đó và xử lý việc gửi tới từng thành viên, giúp giải phóng máy chủ chính.

Thiết kế 5: Video Streaming (YouTube) - “Đế chế Exabyte”

Bài toán về lưu trữ khổng lồ, xử lý video và phân phối toàn cầu.

  • S1 Scenario: 2 tỷ DAU, mỗi phút có 500 giờ video được upload, tổng 1 tỷ giờ xem/ngày (35 triệu luồng xem đồng thời).
  • S3 Storage:
    • Metadata (DynamoDB): Lưu thông tin video (title, duration, danh sách độ phân giải).
    • Video Files (S3): Lưu dưới dạng các phân đoạn nhỏ (segments) và tệp kê khai (manifest) cho giao thức HLS/DASH. Ví dụ: s3://yt-videos/{video_id}/1080p_segment_001.ts.
  • S4 Scale:
    • Encoding Pipeline (Quy trình mã hóa): Video gốc được upload lên S3 -> Sự kiện được đẩy vào Kafka -> Các worker sử dụng FFmpeg để chuyển mã video thành nhiều độ phân giải (360p, 720p, 1080p, 4K) và cắt nhỏ thành các segment vài giây.
    • CDN Strategy (Chiến lược Mạng phân phối nội dung): Đây là linh hồn của hệ thống. Dữ liệu được phân cấp: Video “nóng” (hot) được lưu ở các Edge server gần người dùng nhất. Video “ấm” ở Regional server. Và toàn bộ thư viện “lạnh” ở Origin (S3). Cơ chế đuổi cache (eviction) dựa trên LRU (Least Recently Used - Bỏ cái ít dùng nhất) và dự đoán bằng Machine Learning (ML).

[3] Phân biệt Kỳ vọng ở các Cấp độ FAANG

Hiểu rõ bạn đang nhắm đến cấp độ nào là rất quan trọng, vì độ sâu của câu trả lời quyết định tất cả.

  • L4 (Kỹ sư phần mềm):

    • Vẽ được HLD hoàn chỉnh trong 30-45 phút.
    • Nhận diện được 2-3 điểm nghẽn.
    • Ước lượng dung lượng đúng bậc (order of magnitude).
    • Nắm vững các đánh đổi cơ bản: SQL vs NoSQL, Push vs Pull.
  • L5 (Kỹ sư phần mềm Cao cấp):

    • L4 + Chiều sâu: Sẵn sàng đào sâu vào Low-Level Design (LLD) cho một service quan trọng (thiết kế class, interface).
    • Đánh đổi đa chiều: “Nếu chọn Cassandra ta được X, mất Y; nhưng nếu dùng Google Spanner, ta sẽ có Z nhưng chi phí là W.”
    • Câu chuyện chuyển đổi (Migration Story): Làm thế nào để nâng cấp từ hệ thống cũ lên thiết kế mới mà không gây gián đoạn dịch vụ?
  • L6 (Staff Kỹ sư):

    • L5 + Tầm nhìn tổ chức: Thiết kế hệ thống trải dài trên 5+ team, phân tích ROI (Lợi tức đầu tư), lộ trình phát triển đội ngũ và sản phẩm nhiều năm.

[4] Lời nguyền “Anti-Patterns”: Những cạm bẫy “chết người” cần tránh

Ngay cả những ứng viên giỏi cũng có thể mắc phải những lỗi cơ bản này. Hãy nhận diện chúng để phòng tránh!

  1. ❌ Nhảy cóc vào Service: “Tôi sẽ dùng 3 services và…“. ✅ Hãy làm đúng: Luôn bắt đầu bằng việc đặt câu hỏi để làm rõ yêu cầu (Scenario).
  2. ❌ “Ném Kafka vào mọi thứ”: Đừng biến Kafka thành “con dao đa năng”. ✅ Hãy chọn lọc: Chỉ dùng Kafka khi cần bất đồng bộ, replay, và khả năng chịu tải cao. Những tác vụ đơn giản hơn có thể chỉ cần SQS.
  3. ❌ “Vô vàn người dùng, vô vàn dữ liệu”: Nói mơ hồ là tự đào hố chôn mình. ✅ Hãy định lượng: “100M DAU, mỗi bản ghi 1KB, 1 ngày ~100K giây -> khoảng 1.2K lượt ghi/giây.”
  4. ❌ “Kubernetes tự động scale”: Đây là câu trả lời “lấp liếm” điển hình. ✅ Hãy cụ thể: “Sử dụng auto-scaling dựa trên CPU. Khi CPU trên 70%, tăng số lượng Read Replica từ 2 lên 10.”
  5. ❌ Câm lặng trước Trade-off: Chỉ nói “Tôi chọn Cassandra”. ✅ Hãy phân tích: Vì sao bạn chọn nó? Cái giá phải trả là gì?
  6. ❌ “Mổ xẻ” một cách “vi mô”: Dành 20 phút cho một chi tiết nhỏ như Bloom filter. ✅ Hãy “nhảy cóc” khi cần: Nói “Tôi sẽ dùng Bloom filter ở đây để lọc nhanh cache” và đi tiếp, đừng sa lầy.
  7. ❌ Thiết kế bằng lời nói: Không có sơ đồ. ✅ Hãy tập vẽ: Một sơ đồ hộp và mũi tên rõ ràng trên Excalidraw hay giấy bút đáng giá bằng cả ngàn lời nói.

Lời kết:

Hy vọng cẩm nang chi tiết này sẽ là người bạn đồng hành đắc lực trên con đường chinh phục các vòng phỏng vấn System Design đầy cam go của bạn. Đừng chỉ đọc, hãy thực hành. Hãy tự mock interview một mình, với bạn bè, và tập phản xạ với 4S Framework. Hãy nhớ rằng, mục tiêu không phải là một kiến trúc “hoàn hảo” trên lý thuyết, mà là một cuộc trò chuyện thể hiện tư duy kỹ thuật sắc bén và sự trưởng thành trong cách bạn giải quyết vấn đề.

Chúc bạn may mắn và tự tin tỏa sáng!

Hãy kết nối

Nếu bạn quan tâm tới việc hợp tác, có câu hỏi về bài viết, hay chỉ đơn giản muốn chuyện trò về backend — cứ ping mình nhé.