Solution Architect thực thụ: Không phải người vẽ những chiếc hộp
Solution Architect thực thụ không rời xa code. Họ bảo vệ business rules, trì hoãn quyết định kỹ thuật và giữ cho hệ thống dễ thay đổi theo thời gian.
29 tháng 7, 2026 · 12 phút đọc

Phần 1 Road to Pure Solution Architect
Trong nhiều công ty phần mềm, con đường phát triển nghề nghiệp thường được hình dung khá đơn giản:
Developer → Senior Developer → Technical Lead → Solution Architect
Càng đi lên, người kỹ sư càng viết ít code hơn. Đến một thời điểm nào đó, công việc của Solution Architect chủ yếu xoay quanh meeting, diagram, lựa chọn công nghệ và review giải pháp ở mức tổng quan.
Cách tổ chức này không hẳn sai. Một Solution Architect rõ ràng không thể dành toàn bộ thời gian để xử lý ticket như một developer trong team. Vấn đề bắt đầu xuất hiện khi khoảng cách giữa kiến trúc và implementation trở nên quá lớn. Lúc đó, kiến trúc sư chỉ còn nhìn thấy hệ thống qua slide, tài liệu và các buổi báo cáo. Trong khi đó, developer phải trực tiếp sống với những quyết định như một abstraction khó dùng, một dependency sai hướng, một framework bị đưa quá sâu vào business logic hay một thay đổi nhỏ nhưng kéo theo hàng loạt module liên quan.
Một architect không nên rời khỏi code đến mức không còn cảm nhận được những vấn đề này. Họ vẫn phải là một programmer có kinh nghiệm, đủ gần với implementation để hiểu kiến trúc mình đề xuất đang giúp team tiến nhanh hơn hay đang tạo thêm gánh nặng.
Kiến trúc chỉ có ý nghĩa khi đi được vào code
Một sơ đồ kiến trúc có thể trông rất hợp lý:
- Presentation Layer
- Application Layer
- Domain Layer
- Infrastructure Layer
- Event Bus
- API Gateway
- Database Cluster
Trên slide, các thành phần được đặt đúng vị trí, đường nối rõ ràng và dependency có vẻ sạch sẽ.
Nhưng khi bắt đầu implementation, hệ thống có thể phát sinh một thực tế hoàn toàn khác:
- Business logic phải kế thừa base class của framework.
- Domain model chứa annotation của ORM.
- Một use case đơn giản phải đi qua quá nhiều lớp trung gian.
- Unit test phải khởi động database hoặc web server.
- Một thay đổi dữ liệu làm ảnh hưởng đến nhiều module không liên quan.
- Developer mới không biết business rule thực sự nằm ở đâu.
Đây là khoảng cách rất phổ biến giữa architecture diagram và architecture trong codebase.
Một Solution Architect không nhất thiết phải nhận số lượng task ngang với developer. Tuy nhiên, họ vẫn cần duy trì khả năng đi từ một requirement xuống đến code thực tế và kiểm chứng xem cấu trúc đã thiết kế có hoạt động đúng như dự kiến hay không.
Điều đó có thể thể hiện qua nhiều hình thức:
- Xây dựng một vertical slice mẫu cho team.
- Viết proof of concept cho một quyết định có rủi ro cao.
- Review các đoạn code nằm trên architectural boundary.
- Trace một execution flow từ API xuống persistence.
- Kiểm tra dependency graph giữa các module.
- Đọc test để hiểu business rule đang được bảo vệ ở mức nào.
Code là nơi các quyết định kiến trúc phải đối mặt với thực tế. Nếu một nguyên tắc chỉ tồn tại trong tài liệu mà không thể duy trì trong implementation, nó chưa thực sự trở thành một phần của kiến trúc.
Chất lượng kiến trúc thể hiện qua chi phí thay đổi
Các buổi trình bày kiến trúc thường dành nhiều thời gian cho technology stack:
Hệ thống sử dụng microservices, Kubernetes, Kafka, Redis, MongoDB, PostgreSQL, Elasticsearch và event-driven architecture.
Danh sách này cho biết hệ thống dùng những công cụ gì, nhưng chưa nói được nhiều về chất lượng kiến trúc.
Một hệ thống có thể sử dụng toàn bộ công nghệ hiện đại nhưng vẫn rất khó duy trì. Chỉ cần thêm một rule mới đã phải sửa nhiều service, cập nhật hàng loạt contract và chạy lại một quy trình regression lớn. Ngược lại, một hệ thống có stack khá truyền thống vẫn có thể phát triển tốt nếu dependency rõ ràng và mỗi thay đổi được giới hạn trong phạm vi hợp lý.
Mục tiêu của kiến trúc là giảm lượng công sức con người cần bỏ ra để xây dựng và duy trì phần mềm theo thời gian.
Một kiến trúc tốt thường tạo ra những đặc điểm rất thực tế:
- Thêm use case mới mà không phải sửa hàng loạt module cũ.
- Thay đổi business rule mà không ảnh hưởng trực tiếp đến database.
- Test nghiệp vụ mà không cần khởi động toàn bộ application.
- Thay thế external service mà không phải viết lại core system.
- Nâng cấp framework mà không biến thành một dự án migration kéo dài.
- Giúp developer mới nhanh chóng tìm được nơi chứa logic chính.
Điểm đáng chú ý là các lợi ích này chỉ rõ ràng sau một thời gian vận hành. Kiến trúc tốt không nhất thiết làm cho những tuần đầu tiên nhanh hơn. Nó giúp hệ thống không chậm dần một cách mất kiểm soát khi số lượng feature, dependency và team cùng tăng lên.
Architect không cần quyết định mọi thứ từ ngày đầu
Một trong những kỳ vọng phổ biến đối với Solution Architect là phải chốt sớm toàn bộ nền tảng kỹ thuật:
- Programming language.
- Database.
- Cloud provider.
- Message broker.
- Frontend framework.
- ORM.
- Deployment model.
Một số quyết định đúng là cần được đưa ra sớm để team có thể bắt đầu. Tuy nhiên, không phải mọi quyết định đều cần được khóa ngay từ giai đoạn đầu.
Một kiến trúc tốt cho phép trì hoãn các quyết định kỹ thuật cho đến khi có đủ thông tin. Đây không phải là cách né tránh trách nhiệm, mà là một phần của việc quản lý rủi ro kiến trúc.
Giả sử một dự án chọn MongoDB từ đầu và xây toàn bộ domain model bám sát cấu trúc document. Sau vài tháng, team nhận ra dữ liệu có nhiều quan hệ, transaction phức tạp và yêu cầu báo cáo mạnh hơn dự kiến. PostgreSQL lúc này có thể phù hợp hơn, nhưng việc thay đổi trở nên rất đắt vì database model đã lan vào business logic, API contract và test cases.
Vấn đề không chỉ nằm ở việc chọn sai database. Vấn đề lớn hơn là một quyết định hạ tầng đã được phép chi phối toàn bộ cấu trúc của application.
Một kiến trúc có khả năng trì hoãn quyết định sẽ giữ business rule độc lập đủ lâu để team có thể học thêm về domain, workload và constraint thực tế. Khi cần chốt công nghệ, quyết định sẽ dựa trên dữ liệu tốt hơn thay vì giả định ban đầu.
Dependency Rule bảo vệ phần quan trọng nhất của hệ thống
Dependency Rule là một trong những nguyên tắc cốt lõi của Clean Architecture.
Source-code dependency cần hướng về các policy và business rule cấp cao, thay vì hướng ra những chi tiết như database, UI hay framework.
Ví dụ, use case ApproveLoan cần đọc thông tin khách hàng, áp dụng các rule đánh giá và lưu kết quả phê duyệt. Use case này không cần biết dữ liệu đến từ SQL Server, một external API, Kafka hay một in-memory repository dùng cho test.
Khi application core phụ thuộc trực tiếp vào Entity Framework hoặc Hibernate, business rule bắt đầu mang theo constraint của persistence layer. Điều này thường chưa gây vấn đề ngay lập tức, nhưng sẽ lộ rõ khi team cần test độc lập, thay đổi cách lưu dữ liệu hoặc tách một phần logic sang một deployment model khác.
Thay vì để application service phụ thuộc trực tiếp vào ORM:
ApproveOrderUseCase
→ EntityFrameworkDbContext
→ SQL Server
Ta có thể đảo chiều source-code dependency:
ApproveOrderUseCase
→ OrderRepository interface
SqlOrderRepository
→ OrderRepository interface
→ Entity Framework
→ SQL Server
Ở runtime, use case vẫn gọi repository và dữ liệu vẫn được lưu xuống SQL Server. Điểm khác biệt nằm ở source code: business rule chỉ biết đến contract mà nó cần, còn chi tiết persistence phụ thuộc vào contract đó.
Cách tổ chức này không có nghĩa mọi class đều phải có interface. Việc tạo abstraction cũng có chi phí và có thể làm codebase khó theo dõi nếu áp dụng máy móc.
Boundary chỉ thực sự có giá trị khi nó bảo vệ một phần code quan trọng khỏi một dependency có khả năng thay đổi, khó kiểm soát hoặc không nên chi phối business logic.
Cấu trúc project nên phản ánh domain
Một codebase được tổ chức theo các thư mục như sau khá quen thuộc:
/controllers
/services
/repositories
/entities
/configurations
/helpers
Cấu trúc này cho thấy team đang dùng layered architecture, nhưng chưa cho biết hệ thống giải quyết bài toán gì.
Một cách tổ chức khác có thể làm domain hiện ra rõ hơn:
/order-processing
/place-order
/cancel-order
/calculate-shipping
/inventory
/reserve-stock
/release-stock
/payment
/authorize-payment
/refund-payment
Chỉ cần nhìn vào cấu trúc này, developer đã có thể đoán được hệ thống xử lý đơn hàng, tồn kho và thanh toán.
Đây là tinh thần của Screaming Architecture. Kiến trúc nên thể hiện business capability và use case trước khi thể hiện framework hay công cụ.
Với một healthcare system, những khái niệm như PatientRegistration, AppointmentScheduling, PrescriptionManagement hay InsuranceClaim nên xuất hiện rõ ràng trong codebase.
Nếu cấu trúc project chỉ nổi bật Controllers, Repositories, Spring, MySQL hay Kafka, công nghệ đang chiếm vị trí đáng lẽ thuộc về domain.
Điều này không có nghĩa mọi dự án đều phải chuyển sang một folder structure giống nhau. Cách tổ chức cần phù hợp với quy mô team, mức độ phức tạp của domain và chiến lược modularization.
Điểm quan trọng là một developer mới có thể nhìn vào codebase và nhận ra hệ thống đang phục vụ những nghiệp vụ nào, thay vì chỉ nhận ra nó được xây bằng framework gì.
Framework và database nên nằm đúng vị trí
Framework, database và UI nên được xem là các chi tiết nằm ở vòng ngoài của hệ thống.
Cách diễn đạt này đôi khi bị hiểu thành việc xem nhẹ vai trò của công nghệ. Trên thực tế, lựa chọn database vẫn ảnh hưởng lớn đến consistency, performance, scalability và chi phí vận hành. Một framework không phù hợp cũng có thể tạo ra technical debt kéo dài nhiều năm.
Điểm cần phân biệt là những công nghệ này không phải lý do hệ thống tồn tại.
Một hệ thống thương mại điện tử tồn tại để quản lý sản phẩm, đơn hàng, thanh toán và giao hàng. Nó không tồn tại để sử dụng PostgreSQL hay Spring Boot.
Một hệ thống carbon trading tồn tại để quản lý tài sản carbon, giao dịch, kiểm toán và tuân thủ pháp lý. Nó không tồn tại để sử dụng .NET, Angular hay MongoDB.
Công nghệ phục vụ business capability. Khi business logic bị thiết kế như một extension của framework, thứ tự ưu tiên này đã bị đảo ngược.
Giữ framework và database ở vòng ngoài giúp application core ít bị ảnh hưởng hơn khi công nghệ thay đổi. Trong thực tế, không phải lúc nào team cũng thay database hoặc framework. Giá trị lớn hơn nằm ở việc giới hạn phạm vi ảnh hưởng của những chi tiết này.
Một migration framework sẽ dễ kiểm soát hơn khi annotation, lifecycle hook và API đặc thù không xuất hiện khắp domain model. Một thay đổi persistence strategy cũng ít rủi ro hơn khi use case không gọi trực tiếp ORM query.
Công việc thực tế của một Solution Architect
Solution Architect không chỉ chuyển requirement thành một diagram kỹ thuật.
Vai trò này nằm ở điểm giao giữa business, engineering, security, operation và delivery. Kiến trúc sư cần hiểu mục tiêu kinh doanh, nhưng đồng thời cũng phải biết quyết định kỹ thuật sẽ tạo ra tác động gì trong code và trong quá trình vận hành.
Khi một requirement mới xuất hiện, một architect có kinh nghiệm thường quan tâm đến nhiều lớp vấn đề cùng lúc:
- Business rule nào đang thực sự thay đổi.
- Phần nào của hệ thống cần giữ ổn định.
- Dependency mới sẽ đi theo hướng nào.
- Quyết định nào cần chốt ngay để team tiếp tục.
- Quyết định nào có thể trì hoãn.
- Nếu giả định hiện tại sai, chi phí thay đổi sẽ nằm ở đâu.
- Use case có thể test độc lập đến mức nào.
- Constraint về security, compliance và operation có tác động gì.
Những câu hỏi này không nhất thiết phải xuất hiện thành một checklist trong mọi buổi meeting. Chúng dần trở thành cách một architect nhìn hệ thống.
Một Solution Architect tốt có thể không phải người viết nhiều code nhất team, nhưng vẫn phải đủ gần để nhận ra một boundary đang bị phá vỡ, một abstraction đang làm chậm implementation hoặc một design chỉ đẹp trên diagram.
Họ cũng cần đủ thực tế để biết lúc nào nên chấp nhận coupling. Không phải mọi hệ thống đều cần Clean Architecture đầy đủ. Một internal tool có vòng đời ngắn và ít thay đổi có thể không cần nhiều lớp bảo vệ như một core banking platform hay một hệ thống chính phủ tồn tại hàng chục năm.
Kiến trúc luôn gắn với context. Cùng một quyết định có thể hợp lý ở dự án này nhưng trở thành over-engineering ở dự án khác.
Dấu hiệu của một kiến trúc đang xa rời implementation
Một kiến trúc sư bắt đầu mất kết nối với hệ thống khi phần lớn quyết định chỉ còn được đánh giá qua slide và tài liệu.
Một số dấu hiệu thường gặp gồm:
- Chọn công nghệ trước khi hiểu rõ domain.
- Chốt toàn bộ stack quá sớm dù còn nhiều giả định chưa được kiểm chứng.
- Đưa ra rule chung cho mọi service bất kể đặc điểm nghiệp vụ.
- Không kiểm tra diagram có phản ánh đúng dependency trong code hay không.
- Dùng số lượng component để thể hiện độ trưởng thành của kiến trúc.
- Xem coding là phần việc cấp thấp và không còn liên quan đến architect.
- Không trực tiếp trải nghiệm chi phí mà team phải trả để tuân thủ design.
Khi đó, kiến trúc dễ trở thành một lớp quản trị đứng ngoài development thay vì một phần hỗ trợ development.
Một architect thực thụ thường sẵn sàng mở IDE, đọc một đoạn code, trace một request, xem test hoặc kiểm tra dependency giữa các module. Họ không làm việc này để kiểm soát từng chi tiết implementation, mà để bảo đảm các quyết định cấp cao vẫn còn đúng khi đi vào thực tế.
Họ cũng cần sẵn sàng thay đổi quyết định khi implementation cho thấy giả định ban đầu không còn phù hợp.
Kiến trúc không phải một bản thiết kế bất biến. Nó là tập hợp các quyết định cần được kiểm chứng và điều chỉnh trong suốt vòng đời hệ thống.
Hands-on không đồng nghĩa với chỉ giỏi coding
Việc nhấn mạnh architect phải gần với code không có nghĩa người lập trình giỏi nhất sẽ tự động trở thành Solution Architect tốt.
Vai trò này vẫn cần nhiều năng lực ngoài programming:
- Hiểu business domain và mục tiêu chiến lược.
- Giao tiếp với stakeholder ở nhiều cấp độ.
- Đánh giá security, compliance và operational risk.
- Thiết kế integration giữa nhiều hệ thống.
- Cân bằng chất lượng, chi phí và timeline.
- Trình bày trade-off rõ ràng.
- Hướng dẫn team mà không trở thành bottleneck.
Một architect chỉ mạnh về coding có thể tạo ra design kỹ thuật tốt nhưng chưa chắc giải quyết đúng bài toán kinh doanh.
Ngược lại, một architect chỉ mạnh về giao tiếp và trình bày có thể tạo ra roadmap thuyết phục nhưng không nhận ra những vấn đề sẽ xuất hiện khi team bắt đầu implementation.
Solution Architect thực thụ cần đứng được ở cả hai phía. Họ hiểu business đủ sâu để chọn đúng vấn đề, và hiểu engineering đủ sâu để đưa ra một giải pháp có thể xây dựng, vận hành và thay đổi trong thực tế.
Thước đo cuối cùng nằm ở khả năng thay đổi
Sau tất cả diagram, architecture decision record, coding convention và technology evaluation, giá trị của kiến trúc vẫn quay về một vấn đề rất thực tế: hệ thống có tiếp tục thay đổi được với chi phí hợp lý hay không.
Khi có requirement mới, team có xác định nhanh được nơi cần sửa không?
Business rule có được tách khỏi framework và infrastructure ở mức phù hợp không?
Một thay đổi cục bộ có được giữ trong phạm vi cục bộ không?
Các use case có thể được hiểu và test độc lập không?
Tốc độ phát triển có giảm mạnh khi codebase lớn lên không?
Không phải hệ thống nào cũng trả lời hoàn hảo tất cả những câu hỏi này. Kiến trúc luôn là tập hợp của nhiều trade-off. Điều quan trọng là team hiểu mình đang đánh đổi điều gì và quyết định đó có phù hợp với vòng đời của sản phẩm hay không.
Một Solution Architect thực thụ không được đánh giá bằng số lượng diagram hay số công nghệ xuất hiện trong solution.
Giá trị của họ thể hiện ở khả năng giữ cho business rule không bị nhấn chìm bởi chi tiết kỹ thuật, giúp team nhìn rõ dependency, trì hoãn những quyết định chưa cần thiết và hạn chế chi phí của sự thay đổi.
Họ vẫn cần gần với code, bởi đó là nơi các quyết định kiến trúc bộc lộ tác dụng hoặc thất bại.
Khi hệ thống phát triển trong nhiều năm mà team vẫn có thể hiểu, sửa và mở rộng nó với mức effort hợp lý, kiến trúc đã hoàn thành đúng vai trò của mình.
Bài viết này hữu ích với bạn?
Bình luận (0)
Chưa có bình luận nào được xuất bản.
Hãy là người đầu tiên chia sẻ góc nhìn của bạn.

Zi
With more than 11 years of experience as a software engineer, I specialize in consulting on and designing robust enterprise systems. I am passionate about programming and software development, and I have mastered industry best practices and developed innovative solutions that improve operational efficiency. As a consultant, I am committed to understanding each client's unique needs and goals and developing tailored strategies to address their specific challenges. I would welcome the opportunity to contribute my expertise as a knowledgeable and proactive partner in helping your enterprise thrive.
Solution Architect