← C4 Model: vẽ kiến trúc phần mềm

Bài 10 · Nâng cao · 30 phút

Dự án: mô hình hoá 3 hệ thống

Biên soạn bởi Nguyễn Anh Tuấn

Dự án tổng hợp: dựng mô hình C4 cho ba hệ thống - ví điện tử, app đặt đồ ăn, nền tảng học trực tuyến - vẽ đủ Context → Container → Component.

Chúc mừng - mèo con đã đi hết phần lõi của khoá! Trước khi bắt tay làm dự án, điểm lại bộ đồ nghề đã có:

  • Bốn mức zoom: Context (cho mọi người) → Container → Component → Code (thường bỏ).
  • Sơ đồ bổ trợ: System Landscape, Dynamic, Deployment - khi câu hỏi vượt khỏi "gồm gì".
  • Ký pháp tự-đứng-vững: tiêu đề, chú giải, nhãn quan hệ rõ hướng, nhất quán.
  • Diagrams as code (Mermaid/Structurizr) để sơ đồ luôn khớp và version cùng Git.
  • Giao tiếp: chọn mức zoom theo khán giả, kể chuyện thay vì đổ sơ đồ.

Cách duy nhất để những thứ này thành kỹ năng là tự làm. Dưới đây là ba dự án; widget cuối bài có sẵn cả ba (và một hệ thống ngân hàng) để mèo con đối chiếu sau khi tự làm.

Hệ thống đầu: một ví điện tử. Người dùng nạp tiền, chuyển tiền, thanh toán; chủ cửa hàng nhận thanh toán; ví nối tới ngân hàng và một dịch vụ định danh (eKYC).

Bắt đầu bằng Context. Đây là một cách viết nó bằng Mermaid để mèo con tham khảo:

vi-dien-tu-context.mmd - Mermaid C4 (render ra sơ đồ, không in terminal)

C4Context
  title System Context - Vi Dien Tu
  Person(nd, "Người dùng", "Nạp, chuyển, thanh toán")
  Person(ch, "Chủ cửa hàng", "Nhận thanh toán")
  System(vi, "Ví Điện Tử", "Thanh toán & chuyển tiền")
  System_Ext(bank, "Hệ thống ngân hàng", "Nạp/rút tiền")
  System_Ext(ekyc, "Dịch vụ eKYC", "Xác minh danh tính")
  Rel(nd, vi, "Nạp/chuyển/thanh toán", "HTTPS")
  Rel(ch, vi, "Nhận thanh toán", "HTTPS")
  Rel(vi, bank, "Nạp/rút tiền", "API")
  Rel(vi, ekyc, "Xác minh danh tính", "API")

Đoạn Mermaid trên render ra đúng sơ đồ này:

System Context - Ví Điện Tử

[Người dùng]

Người dùng

Nạp tiền, chuyển tiền, thanh toán.

[Người dùng]

Chủ cửa hàng

Nhận thanh toán từ khách.

[Hệ thống phần mềm]

Ví Điện Tử

Cho người dùng thanh toán & chuyển tiền.

[Hệ thống ngoài]

Hệ thống ngân hàng

Liên kết tài khoản, nạp/rút tiền.

[Hệ thống ngoài]

Dịch vụ định danh (eKYC)

Xác minh danh tính người dùng.

Nạp/chuyển/thanh toán [HTTPS]Nhận thanh toán [HTTPS]Nạp/rút tiền [API]Xác minh danh tính [API]

Việc của mèo con

Tự zoom tiếp xuống Container (app, API, cơ sở dữ liệu, hàng đợi) rồi Component cho API. Xong thì mở widget cuối bài, chọn "Ví Điện Tử" để so cách làm.

Hệ thống thứ hai: một app đặt đồ ăn. Thực khách đặt món, nhà hàng chuẩn bị, tài xế giao; nối tới cổng thanh toán và dịch vụ bản đồ.

  • Context: ba vai trò người dùng (thực khách, nhà hàng, tài xế) + hai hệ thống ngoài.
  • Container: app thực khách, app tài xế, API, cơ sở dữ liệu, và một hàng đợi để điều phối đơn.
  • Để ý: nhiều loại người dùng hơn ví điện tử - bức Context sẽ "đông" hơn ở phần Person.

Việc của mèo con

Vẽ Context → Container cho app đặt đồ ăn. Đối chiếu với widget (chọn "Mèo Đói").

Hệ thống thứ ba: một nền tảng học trực tuyến. Học viên học bài và làm quiz, giảng viên soạn bài; nối tới cổng thanh toán và dịch vụ email.

  • Làm đủ ba mức cho dự án này: Context → Container → Component (cho API).
  • Component: tách controller (đăng nhập, bài học), service (tiến độ, quiz), gateway truy cập dữ liệu.
  • So ba dự án: tư duy zoom GIỐNG HỆT nhau, chỉ khác phần tử cụ thể.

Việc của mèo con

Dựng đủ ba mức. Đối chiếu với widget (chọn "Lớp Học Trực Tuyến").

Sau khi tự làm, dùng widget dưới đây để so cách làm của mèo con với một cách hợp lý. Nhớ: khác không có nghĩa là sai - miễn mô hình của mèo con nhất quán và tự đứng vững.

🗺️ Bản đồ kiến trúc:

Nền tảng học online: học viên xem bài, làm quiz, theo dõi tiến độ.

Mức 1 Mức 2 Mức 3

Mức 1 - System Context

System Context - Lớp Học Trực Tuyến

Học viên
Mèo con học bài, làm quiz, xem tiến độ.
Giảng viên
Soạn bài giảng, chấm bài.
Cổng thanh toán ngoài
Thu học phí.
Dịch vụ Email ngoài
Gửi email thông báo.

Quan hệ (có nhãn & hướng)

  • Học viên Lớp Học Trực Tuyến : Học & làm bài [HTTPS]
  • Giảng viên Lớp Học Trực Tuyến : Soạn bài & chấm [HTTPS]
  • Lớp Học Trực Tuyến Cổng thanh toán : Thu học phí [API]
  • Lớp Học Trực Tuyến Dịch vụ Email : Gửi email [SMTP]
  • Đối chiếu ranh giới trong/ngoài: mèo con đặt hệ thống nào là "ngoài"?
  • Đối chiếu độ chi tiết: ở Container, mèo con có ghi công nghệ + giao thức chưa?
  • Trình bày thử: chọn một dự án, kể nó cho một "sếp kinh doanh" (chỉ Context) và một "lập trình viên" (tới Component).

Mèo con giờ đã biết mô hình hoá kiến trúc một hệ thống thật, trình bày nó cho từng phòng ban, và giữ sơ đồ khỏi lạc hậu bằng code. Đó là một kỹ năng quý mà nhiều lập trình viên lâu năm vẫn còn lúng túng.

  • Áp dụng ngay: vẽ C4 cho một hệ thống mèo con đang làm hoặc tò mò.
  • Thử Structurizr Lite để quản lý mô hình bằng code, sinh nhiều view.
  • C4 mô tả "hình"; muốn vững phần "ruột" nghiệp vụ thì học thêm thiết kế & kiến trúc code.

Còn nữa: phần mở rộng

Muốn đưa C4 vào QUY TRÌNH thật của công ty - tài liệu sống cùng repo, dùng AI dựng tài liệu, để từ CEO/Sales đến PO/PM/BA/DEV cùng hiểu - học tiếp phần mở rộng. Còn muốn THIẾT KẾ phần lõi nghiệp vụ cho vững, ghé khoá SOLIDClean & Onion Architecture. Chúc mèo con vẽ bản đồ thật đẹp! 🗺️

Câu hỏi thường gặp

Làm một dự án thật kỹ (đủ Context → Container → Component, có trình bày) còn giá trị hơn ba dự án hời hợt. Nhưng nếu làm được cả ba, mèo con sẽ thấy tư duy zoom lặp lại giống nhau dù lĩnh vực khác hẳn - đó mới là điều cần ngấm.

Không hẳn. C4 không có "đáp án đúng" duy nhất: ranh giới trong/ngoài và độ chi tiết tuỳ ngữ cảnh và người đọc. Widget chỉ là MỘT cách hợp lý để đối chiếu. Miễn mô hình của mèo con nhất quán, tự đứng vững và đúng mức cho khán giả, là ổn.

Cả hai đều được. Bản nháp đầu cứ vẽ tay/bảng trắng cho nhanh. Khi đã ưng, thử viết lại bằng Mermaid (render ngay trên GitHub) hoặc Structurizr (một model nhiều view) để luyện diagrams as code.

Tối thiểu Context + Container cho cả ba. Thêm một sơ đồ Component cho container chính (thường là API) của ít nhất một dự án để luyện zoom sâu. Mức Code thì bỏ qua như đã học.

Áp dụng ngay vào một hệ thống mèo con đang làm hoặc đang tò mò. Thử Structurizr Lite để quản lý mô hình bằng code. Và đọc tài liệu gốc súc tích tại c4model.com để củng cố.

Tài liệu chính thức: c4model.com →

Tick những điều em tự tin làm được. Càng lên cao, em càng hiểu sâu.

Tick những điều em tự tin làm được sau khi học bài này. 0/6

Trả lời vài câu để chắc rằng em đã nắm bài.

Câu 1/3 Điểm: 0

Mỗi dự án trong bài này tối thiểu nên có những mức sơ đồ nào?

  1. 1

    Dự án 1 - Ví điện tử: Context + Container

    Dựng sơ đồ System Context rồi Container cho một ví điện tử: người dùng, chủ cửa hàng, hệ thống ngân hàng và eKYC ngoài; bên trong có app, API, cơ sở dữ liệu, hàng đợi. Đối chiếu với widget (chọn "Ví Điện Tử").

    Hoàn thành khi: Hai sơ đồ có tiêu đề; Context không lộ công nghệ; Container ghi công nghệ + giao thức; mọi quan hệ có nhãn.

  2. 2

    Dự án 1 - Ví điện tử: Component

    Zoom vào container API của ví điện tử: tách thành controller, service, gateway. Vẽ luồng một giao dịch chuyển tiền đi qua các component.

    Hoàn thành khi: Có ≥1 controller, ≥1 service, ≥1 gateway; vẽ được một luồng từ controller tới cơ sở dữ liệu.

  3. 3

    Dự án 2 - App đặt đồ ăn

    Dựng Context → Container cho một app đặt đồ ăn (thực khách, nhà hàng, tài xế; thanh toán & bản đồ ngoài). Đối chiếu với widget (chọn "Mèo Đói").

    Hoàn thành khi: Context có ≥3 Person và ≥2 hệ thống ngoài; Container có app(s), API, dữ liệu, hàng đợi; quan hệ có nhãn.

  4. 4

    Dự án 3 - Nền tảng học trực tuyến

    Dựng Context → Container, rồi Component cho container API của một nền tảng học. Đối chiếu với widget (chọn "Lớp Học Trực Tuyến").

    Hoàn thành khi: Đủ ba mức cho dự án này; mức Component có controller/service/gateway và một luồng rõ ràng.

  5. 5

    Trình bày cho hai khán giả

    Chọn một trong ba dự án. Viết hai kịch bản trình bày ngắn: một cho sếp kinh doanh, một cho lập trình viên - mỗi kịch bản dùng mức sơ đồ phù hợp.

    Hoàn thành khi: Kịch bản business mở bằng Context, không thuật ngữ; kịch bản dev đi tới Component; mỗi kịch bản 3-5 câu.

  6. 6

    Viết bằng diagrams as code

    Chọn một sơ đồ bất kỳ trong ba dự án, viết lại bằng Mermaid hoặc Structurizr DSL rồi render thử.

    Hoàn thành khi: Bản code render ra đúng sơ đồ; nếu dùng Structurizr, có một model sinh ít nhất hai view.