AI-native SDLC: khi code không còn là nút thắt, quy trình phải thành một vòng lặp
Agent viết code cực nhanh, nên nút thắt chuyển sang khâu con người duyệt và bàn giao. Playbook của Anthropic biến SDLC thẳng-một-chiều thành một vòng lặp có AI ở từng chặng — kèm mindmap tương tác để nắm trọn bức tranh trước khi đọc sâu.
Khi agent có thể viết code nhanh hơn rất nhiều, code không còn là nút thắt lớn nhất. Thứ cần thiết kế lại là toàn bộ quy trình: từ một dây chuyền bàn giao chậm chạp thành một vòng lặp, nơi AI tham gia ở từng chặng nhưng con người vẫn chịu trách nhiệm ở những cánh cổng quan trọng.
SDLC truyền thống được xây cho một thời kỳ mà viết code là phần tốn thời gian nhất. Ý tưởng đi qua product, rồi tới design, engineering, QA, security, release. Mỗi nhóm làm xong phần của mình, tạo một gói tài liệu hoặc ticket, sau đó bàn giao cho nhóm kế tiếp. Quy trình này hợp lý khi tốc độ triển khai bị giới hạn bởi số giờ một kỹ sư có thể ngồi gõ code.
Agent làm thay đổi giả định đó. Một thay đổi từng mất vài ngày để triển khai có thể được dựng lên trong vài giờ, đôi khi nhanh hơn thời gian một PR nằm chờ review. Khi năng lực tạo code tăng mạnh mà các cổng review, test, phê duyệt và deploy vẫn giữ nguyên, hệ thống rơi vào một thế khó: hoặc hàng đợi review phình ra, hoặc code được cho qua khi chưa ai hiểu đủ sâu, hoặc doanh nghiệp phải tăng thêm người chỉ để quản trị lượng thay đổi mới.
Câu trả lời không phải là bỏ kiểm soát để chạy nhanh hơn. Cũng không phải dựng thêm một lớp quy trình nặng nề quanh agent. Cách hợp lý hơn là biến SDLC thành một vòng lặp có AI ở từng điểm: AI giúp làm rõ ý định, tạo đặc tả, lập kế hoạch, triển khai, tự kiểm, review và theo dõi production. Con người không cần giữ từng thao tác nhỏ, nhưng vẫn chịu trách nhiệm ở những cánh cổng mà phán đoán, rủi ro và quyền phê duyệt thật sự quan trọng.
Có một mindmap tương tác phía dưới để bạn nắm trọn bức tranh trước khi đọc sâu.
Bài này mình viết lại (và bổ sung template + phần greenfield/brownfield) từ playbook gốc của Anthropic — đọc bản gốc tại đây.
Chuỗi artifact: từ ý định đến PR
Xương sống của quy trình này là một chuỗi artifact rất rõ:
intent.md → spec.md → plan.md → code → PR
Mỗi artifact trả lời một câu hỏi khác nhau.
intent.md nói mình MUỐN gì. Đây là cách người khởi xướng thay đổi diễn đạt vấn đề bằng ngôn ngữ của họ: chuyện gì đang không ổn, kết quả mong muốn là gì, ai bị ảnh hưởng, hệ thống nào liên quan, có ràng buộc nào và câu hỏi nào chưa có đáp án.
spec.md nói hệ thống sẽ LÀM GÌ. Nó biến ý định ban đầu thành yêu cầu, hành vi, luồng xử lý, ranh giới, điều kiện chấp nhận và các quyết định thiết kế đủ cụ thể để cả product lẫn engineering cùng kiểm tra.
plan.md nói đội ngũ sẽ làm THẾ NÀO. Nó chỉ ra file nào phải đổi, thứ tự triển khai, phần nào có rủi ro, cách chứng minh thay đổi hoạt động và những test nào cần chạy.
Sau đó mới tới code và PR.
Điểm hay không chỉ nằm ở việc tài liệu rõ hơn. Mỗi chặng kết thúc bằng một commit mà chặng kế tiếp có thể đọc. Chuỗi commit đó chính là audit trail: ai đưa ra ý định, đặc tả thay đổi lúc nào, kế hoạch nào đã được duyệt, code khác kế hoạch ở đâu và PR cuối cùng đã vượt qua những cổng nào.
Thay vì cố tái dựng lịch sử từ Slack, ticket, cuộc họp và trí nhớ của vài người, mình có toàn bộ tiến trình nằm cạnh code, trong git.
1. Plan — bắt lấy ý định
Cách cũ thường bắt đầu bằng một yêu cầu còn mơ hồ. Người đề xuất kể lại nhu cầu trong một cuộc họp. Product viết ticket. Engineering hỏi thêm. Mọi người họp tiếp. Sau vài vòng, ý tưởng ban đầu đã bị diễn giải qua nhiều lớp, nhưng những câu hỏi cốt lõi đôi khi vẫn chưa được trả lời.
Cách mới bắt đầu bằng một cuộc đối thoại giữa người có nhu cầu và Claude. Mục tiêu chưa phải viết một bản đặc tả hoàn chỉnh. Mục tiêu là giúp người đó nói cho ra điều họ thật sự muốn thay đổi.
Artifact của chặng này là intent.md. Một file tốt nên chứa ít nhất:
- Vấn đề đang xảy ra.
- Kết quả mong muốn.
- Người dùng và hệ thống bị ảnh hưởng.
- Những ràng buộc đã biết.
- Những câu hỏi còn mở.
- Những điều chưa thuộc phạm vi của thay đổi.
Điểm quan trọng là intent.md vẫn phải mang ngôn ngữ của người khởi xướng. Claude có thể hỏi, phản biện, phát hiện chỗ mâu thuẫn và giúp sắp xếp suy nghĩ, nhưng không nên biến ý định thật thành một tài liệu kỹ thuật nghe rất trơn tru mà người viết không còn nhận ra mình trong đó.
Người khởi xướng cũng không nhất thiết phải là kỹ sư. Product owner, vận hành, support hay compliance đều có thể làm bước này qua claude.ai hoặc Cowork, rồi dùng GitHub connector để đưa artifact vào repo. Khả năng này đáng giá vì tri thức thường nằm ở người đang chạm vào vấn đề, không phải lúc nào cũng nằm ở người viết code.
Khi intent.md được commit, tên tác giả và timestamp đã có sẵn trong git. Không cần phát minh thêm một hệ thống audit riêng cho bước khởi đầu. Quan trọng hơn, tổ chức có thể rút ngắn quá trình thu thập yêu cầu từ nhiều tuần trao đổi xuống một phiên làm việc tập trung, mà vẫn giữ được nguồn gốc của quyết định.
Mình thường giữ intent.md đủ ngắn để người viết, người duyệt và AI cùng hiểu mình đang giải quyết chuyện gì — trước khi bất kỳ ai nhảy vào chọn framework hay viết code.
# Intent: [tên tính năng]
Author: [tên người viết]
Status: Draft | Approved | Implemented
Timestamp: [YYYY-MM-DD HH:mm]
## 1. Problem
- [PRB-1] [Vấn đề cụ thể đang xảy ra]
- [PRB-2] [Ai đang gặp vấn đề, trong hoàn cảnh nào]
## 2. Proposed Outcome
- [OUT-1] [Kết quả mong muốn, map tới PRB-1]
- [OUT-2] [Hành vi hoặc thay đổi có thể quan sát được]
## 3. Affected Users & Systems
- Users: [persona / role bị ảnh hưởng]
- Systems: [service, database, frontend, integration liên quan]
- Existing flows: [luồng hiện tại có thể bị tác động]
## 4. Constraints
- Không thêm PII vào log.
- Tận dụng hệ thống Auth có sẵn.
- Ngân sách API call: [giới hạn chi phí / số request].
- [Ràng buộc kỹ thuật, pháp lý hoặc vận hành khác]
## 5. Open Questions
- [Q-1] [Điều gì chưa rõ và cần ai xác nhận?]
- [Q-2] [Giả định nào cần kiểm chứng trước khi viết spec?]
Một mẹo nhỏ là đánh stable ID cho từng vấn đề và kết quả như [PRB-1], [OUT-1], để về sau spec.md, plan.md và test đều trỏ ngược lại được.
2. Design — đặc tả sinh ra kèm chính sách
Theo cách cũ, product viết yêu cầu trước, engineering thiết kế sau, rồi tới cuối vòng mới có security, legal, compliance, brand hoặc UX vào xem. Lúc đó, một vấn đề chính sách nhỏ có thể buộc cả đội quay lại sửa từ kiến trúc, trong khi code đã viết gần xong.
Cách AI-native đưa những ràng buộc đó vào ngay lúc đặc tả được tạo.
Claude đọc intent.md, sau đó xây spec.md trong một phiên làm việc với product owner. Bản spec không chỉ mô tả tính năng. Nó phải làm rõ hành vi mong đợi, luồng chính, trường hợp biên, dữ liệu liên quan, quyền truy cập, tiêu chí chấp nhận và những quyết định thiết kế có ảnh hưởng tới hệ thống.
Điểm khác biệt nằm ở chỗ Claude đồng thời đọc các skills của tổ chức. Một skill có thể chứa nguyên tắc brand, yêu cầu accessibility, quy tắc bảo mật, chuẩn UX, chính sách lưu trữ dữ liệu hoặc những điều pháp lý phải áp dụng cho một loại sản phẩm.
Như vậy, chính sách không còn là thứ được phát hiện trong buổi review vài tuần sau. Nó tham gia vào quá trình viết spec ngay từ đầu.
Skills rất hữu ích cho kiến thức cần được áp dụng nhất quán trên nhiều repo hoặc nhiều đội. Chúng được version-control, nên khi chính sách thay đổi, mình biết phiên bản nào đã được dùng để tạo ra quyết định nào. Nhưng skills vẫn mang tính hướng dẫn. Agent có thể hiểu sai hoặc áp dụng không trọn vẹn. Bất kỳ quy tắc nào bắt buộc phải đúng đều cần một cơ chế deterministic như hook hoặc CI check ở các chặng sau.
Nếu Claude phát hiện một vấn đề cần chủ sở hữu chính sách quyết định, luồng công việc nên đi tới người đó trước khi engineering bắt đầu. Chẳng hạn, câu hỏi về thời hạn lưu dữ liệu phải được route tới privacy owner; câu hỏi về quyền truy cập cần tới security; một ngoại lệ thương hiệu cần người phụ trách brand xác nhận.
Kết thúc chặng Design, spec.md được commit cạnh intent.md. Một file giữ nguyên lý do thay đổi; file kia mô tả hệ thống sẽ đáp lại ý định đó ra sao. Product owner vẫn là người chịu trách nhiệm cho spec, thay vì đẩy toàn bộ việc hiểu yêu cầu sang kỹ sư.
Nếu intent.md nói rõ mình muốn thay đổi điều gì, thì spec.md khóa lại hệ thống phải hành xử ra sao và các quyết định kỹ thuật nào AI không được tự tiện đoán.
# Spec: [tên]
Derived from: intent/[tên-file].md
Status: Draft | Approved | Implemented
Owner: [tên người chịu trách nhiệm]
## 1. Functional Requirements
- [FR-1] Map tới [PRB-1]: [Hệ thống phải làm gì]
- Input: [dữ liệu đầu vào]
- Expected behavior: [hành vi mong đợi]
- Error behavior: [cách xử lý lỗi]
- Acceptance criteria: [điều kiện Pass/Fail]
## 2. Technical & Architecture Design
### API Contracts
- Endpoint / Function: [tên]
- Request: [JSON schema / parameters]
- Response: [status code + JSON schema]
- Errors: [error code + format]
### Data Model
- Entities / Tables: [tên]
- Fields: [tên, kiểu dữ liệu, nullable, default]
- Relationships: [quan hệ]
- Migration strategy: [cách thay đổi schema]
### Security & Permissions
- Authentication: [cơ chế Auth]
- Authorization: [role / permission]
- Sensitive data handling: [PII, secrets, logging]
### Frontend/UI Flow
- Entry point: [màn hình / route]
- User actions: [các tương tác chính]
- Loading / Empty / Error states: [hành vi tương ứng]
## 3. Policy Adherence
Áp dụng từ Skills:
- [POL-1] Rate limit: [quy tắc]
- [POL-2] Validate input: [schema / boundary]
- [POL-3] [Quy ước nội bộ khác]
## 4. Flagged Concerns & Trade-offs
- [CON-1] [Rủi ro hoặc điểm chưa chắc chắn]
- [TRD-1] [Phương án đã chọn, phương án bỏ qua và lý do]
## 5. Non-Goals
- [NG-1] [Điều cố ý không giải quyết trong lần này]
- [NG-2] [Phạm vi dành cho phiên bản sau]
Một solo dev vẫn nên viết spec.md vì đây là bài toán 80/20 rất lạnh lùng: một tính năng vừa phải có thể chứa khoảng 20 quyết định nhỏ — tên hàm, format JSON, schema, cách xử lý lỗi. Nếu AI có 80% khả năng đoán đúng từng quyết định, xác suất nó đoán đúng trọn vẹn chỉ còn 0.8^20 ≈ 1%. spec.md khóa trước API contract và data model, tước bớt quyền tự đoán bừa của model, ép nó dành năng lực cho phần thực thi.
3. Build — kế hoạch trước, code sau
Cách cũ thường mở đầu bằng việc đọc ticket rồi sửa code ngay. Với agent, thói quen này càng nguy hiểm vì code được tạo quá nhanh. Một giả định sai có thể lan qua hàng chục file trước khi kỹ sư kịp nhận ra hướng đi không ổn.
Chặng Build nên bắt đầu trong plan mode.
Ở chế độ này, Claude được đọc codebase nhưng chưa được thay đổi gì. Nó lần theo kiến trúc, tìm điểm tích hợp, xem test hiện có, đối chiếu intent.md với spec.md, rồi viết plan.md.
Một kế hoạch đủ dùng phải chỉ ra:
- Những file hoặc module dự kiến thay đổi.
- Thứ tự công việc.
- Interface, schema hay dependency bị ảnh hưởng.
- Rủi ro và giả định.
- Cách test.
- Bằng chứng nào cho thấy phần triển khai đã đáp ứng spec.
Kỹ sư cần chất vấn kế hoạch trước khi cho agent viết code. Vì sao phải đổi file này? Có cách nào ít ảnh hưởng hơn không? Migration có tương thích ngược không? Logic này đã tồn tại ở chỗ khác chưa? Có trường hợp nào spec chưa bao phủ?
Đây chính là design review, nhưng diễn ra khi chi phí đổi hướng chỉ là sửa một tài liệu. Nếu chờ tới lúc PR có hàng ngàn dòng diff mới bắt đầu tranh luận về kiến trúc thì mình đã chọn thời điểm đắt nhất để suy nghĩ.
Sau khi được chỉnh và commit, plan.md trở thành hợp đồng triển khai. Claude có thể bắt đầu code, còn kỹ sư có một mốc để kiểm tra xem quá trình thực hiện có trôi khỏi thiết kế hay không.
Để Claude làm việc tốt trong codebase, repo cần có CLAUDE.md. Đây là phần kiến thức nội bộ mà agent đọc lúc bắt đầu session: lệnh build và test, convention, kiến trúc, đường biên module, quy tắc đặt tên và những chỗ Claude thường hiểu sai.
Một nguyên tắc thực dụng là: nếu Claude mắc cùng một lỗi lần thứ hai, cách sửa nên được ghi vào CLAUDE.md. Tuy nhiên, file này cần ngắn, cụ thể và được chăm sóc như code. Nếu nó dài hàng chục trang hoặc chứa thông tin đã lỗi thời, phần hướng dẫn quan trọng sẽ chìm trong nhiễu. Một trang rõ ràng thường có giá trị hơn một cẩm nang không ai duy trì.
CLAUDE.md và skills không thay thế nhau. CLAUDE.md chứa kiến thức riêng của repo: chạy lệnh nào, code được tổ chức ra sao, cạm bẫy nằm ở đâu. Skills đóng gói năng lực hoặc chính sách có thể tái sử dụng ở nhiều nơi, thường nằm tại .claude/skills/<name>/SKILL.md.
Còn hooks là guardrails deterministic. Nếu agent không được phép sửa một thư mục, hook phải chặn thao tác đó. Nếu mọi thay đổi phải qua formatter và linter, hook có thể tự chạy. Nếu credential không được xuất hiện trong diff, hook kiểm tra và từ chối ngay. Quy tắc bắt buộc phải đúng không nên chỉ được viết bằng lời rồi hy vọng agent nhớ.
Năng suất cũng không nhất thiết chỉ đến từ một session. Một kỹ sư có thể điều khiển hai hoặc ba phiên Claude Code song song, mỗi phiên làm việc trong một git worktree riêng. Một phiên xử lý API, một phiên bổ sung test, một phiên rà migration. Con số hợp lý thường bị giới hạn bởi năng lực review của con người, không phải số agent có thể mở.
Subagents phù hợp với những nhiệm vụ hẹp hơn: kiểm chứng một giả định, tìm cách đơn giản hóa, nghiên cứu dependency hoặc rà riêng một vùng rủi ro. Chúng có context riêng và báo kết quả về session chính. Mục đích không phải tạo thêm thật nhiều hoạt động, mà là tách những câu hỏi độc lập để context chính không bị loãng.
Đến plan.md, mình không còn bàn tính năng “nên hoạt động thế nào” nữa. Mình chuyển spec thành một chuỗi thay đổi cụ thể, có thứ tự và có bằng chứng để biết lúc nào công việc thật sự hoàn tất.
# Plan: [tên] (Derived from spec.md)
## 1. Files That Change
- [New] `path/to/new-file.ts` — [trách nhiệm của file]
- [Modify] `path/to/existing-file.ts` — [thay đổi cụ thể]
- [New] `path/to/feature.test.ts` — [các hành vi cần kiểm chứng]
## 2. Order of Work
1. [Tạo hoặc cập nhật data model]
2. [Implement business logic]
3. [Thêm API endpoint / controller]
4. [Implement UI flow]
5. [Viết và chạy test]
6. [Chạy linter, build và kiểm tra tích hợp]
## 3. Risks & Edge Cases
- [RISK-1] [Rủi ro và cách giảm thiểu]
- [EDGE-1] [Input rỗng / sai định dạng / vượt giới hạn]
- [EDGE-2] [Thiếu quyền / session hết hạn]
- [EDGE-3] [Dependency hoặc API bên ngoài thất bại]
## 4. Proof of Correctness
- Pass/Fail: `[tên test]` pass đủ [số] case.
- Pass/Fail: Request `[method] [endpoint]` với `[payload]` trả HTTP 200.
- Pass/Fail: Screenshot implementation khớp mock đã duyệt.
- Pass/Fail: Linter clean, không có warning mới.
- Pass/Fail: Build succeeded.
Mục Files That Change chính là thứ để tách task ra nhiều git worktree chạy song song: hai task không đụng cùng file thì có thể chạy độc lập.
4. Test — để agent tự kiểm trước
Cách cũ thường để kỹ sư viết xong rồi mới giao cho QA, hoặc mở PR để reviewer phát hiện lỗi cơ bản. Khi code được tạo với tốc độ của agent, quy trình đó sẽ biến con người thành người chạy test thủ công cho máy.
Cách mới là cho chính session một vòng phản hồi đủ chặt trước khi bất kỳ ai phải nhìn vào kết quả.
Claude cần có khả năng chạy test, build ứng dụng, xem lỗi, chụp screenshot khi làm UI và tiếp tục sửa cho tới khi các kiểm tra vượt qua. Tốt nhất, toàn bộ bước xác minh được gói trong một lệnh duy nhất như make test, trả exit code khác 0 nếu có bất kỳ phần nào thất bại. Lệnh đó phải được ghi rõ trong CLAUDE.md.
Khi agent biết chính xác cách tự kiểm, chất lượng đầu ra tăng lên rõ rệt. Quan trọng hơn, vòng lặp phản hồi diễn ra ở nơi rẻ nhất: ngay trong session đang có đầy đủ context của thay đổi.
Bug fix cần kỷ luật mạnh hơn. Trước hết, hãy viết một test tái hiện lỗi và commit riêng test đang fail đó. Sau đó mới giao cho Claude sửa implementation để test pass. Trong thời gian sửa, một hook có thể chặn agent chỉnh lại chính file test.
Cơ chế này xử lý một cám dỗ rất thật: nếu agent được tự do sửa cả code lẫn tiêu chuẩn kiểm tra, nó có thể làm test “xanh” bằng cách làm yếu điều kiện. Khi một test tồn tại từ trước, agent không thể sửa nó và cuối cùng test đó pass, mình có bằng chứng đáng tin hơn rằng lỗi đã được xử lý.
Ở cấp tổ chức, test suite truyền thống vẫn chưa đủ. Mọi thay đổi đối với CLAUDE.md, skills, hooks, model hoặc prompt đều có thể làm hành vi của agent thay đổi trên nhiều loại nhiệm vụ. Vì vậy cần continuous evals trong CI.
Một bộ eval hữu ích có thể gồm 20–50 nhiệm vụ thật, đủ mới và đã có kết quả được chấp nhận. Khi cấu hình agent thay đổi, hệ thống chạy lại các nhiệm vụ này và đo pass rate. Nếu hiệu quả tụt xuống dưới ngưỡng, thay đổi cấu hình không được merge.
Continuous evals đóng vai trò gần giống stage-gate QA cho hệ thống AI-native. Mỗi incident ngoài production cũng nên trở thành một eval vĩnh viễn. Nhờ vậy, tổ chức không chỉ sửa một lỗi; tổ chức còn dạy hệ thống không lặp lại kiểu lỗi đó khi prompt, skill hay model thay đổi.
5. Deploy — review đều tay, cổng do người giữ
Cách review cũ phụ thuộc nhiều vào người được assign. Có PR được soi rất kỹ, có PR chỉ nhận một lượt nhìn nhanh. Reviewer dành phần lớn thời gian bắt lỗi cú pháp hoặc convention nên còn ít sức cho những câu hỏi quan trọng hơn: thay đổi này có đúng với ý định ban đầu không, mức rủi ro có chấp nhận được không, và nó có tạo ra một hệ quả mà spec chưa tính tới không?
Trong quy trình mới, Claude có thể tạo một lớp review đồng đều cho mọi PR. Nó đọc intent.md, spec.md, plan.md, diff và chính sách của repo, rồi rà theo cùng một tiêu chuẩn.
Tiêu chuẩn đó nên nằm trong REVIEW.md ở root: cần tìm bug, lỗ hổng security, vi phạm compliance và sai lệch so với spec hoặc plan như thế nào; phát hiện nào là Important, phát hiện nào chỉ là Nit; vùng nào không cần bình luận để tránh tạo tiếng ồn.
Claude vừa có thể cho review, vừa có thể nhận review. Khi một reviewer để lại comment kèm @claude, agent có thể phân tích, sửa code, chạy lại test và push commit mới. Nhưng quyền quyết định cuối không thuộc về agent.
Separation of duties phải được thực thi bằng kỹ thuật. Agent viết code không được có khả năng approve PR của chính nó. Không phải “được dặn là đừng approve”, mà token, permission và branch protection phải khiến hành động đó không thể xảy ra.
Các phát hiện review lặp lại cũng là dữ liệu để cải thiện hệ thống. Nếu Claude liên tục quên một convention riêng của repo, cập nhật CLAUDE.md. Nếu một chính sách tổ chức chưa được áp dụng đều, sửa skill. Nếu đó là điều không bao giờ được vi phạm, dựng hook hoặc CI check.
Ở chặng Deploy, hooks còn có thể đóng vai trò approval gates. Thay vì chỉ chặn một thao tác, hook tạm dừng và yêu cầu một người có tên hoặc vai trò cụ thể phê duyệt. Deploy production có thể bắt buộc release manager xác nhận. Trong môi trường regulated, những hook không thể thương lượng này nên nằm trong managed settings do admin sở hữu, để kỹ sư trong từng repo không tự ý tắt.
Claude cũng có thể chạy non-interactively trong CI/CD cho những bước cần phán đoán, nhưng phải nằm trong sandbox, dùng credential ngắn hạn và chỉ có scope cần thiết.
Nếu deployment được đưa ra qua MCP, agent không cần cầm một shell có quyền lực mơ hồ. Nó chỉ thấy những tool rõ ràng như Deploy, Status, Rollback, với quyền được giới hạn theo từng environment.
Mức tự chủ nên tăng dần theo rủi ro. Ở dev, agent có thể tự do hơn. Ở staging, agent được deploy và kiểm tra trong một số giới hạn. Ở production, agent chuẩn bị release, chạy validation và trình toàn bộ bằng chứng, nhưng release manager mới là người mở cổng.
Nguyên tắc rất đơn giản: agent có thể hành động cho tới sát cổng production, nhưng không thể tự bước qua.
Và nếu một đội chỉ tập deploy mà không tập rollback, họ mới diễn tập nửa dễ của công việc. Rollback phải là con đường được thử thường xuyên nhất, đủ rõ để cả người lẫn agent có thể kích hoạt an toàn khi production không đi đúng hướng.
6. Maintain — vòng lặp tự khởi động lại
Cách vận hành cũ thường bắt đầu bằng một cảnh báo, sau đó chờ một người đọc dashboard, gom dữ liệu, tìm owner, mở ticket và giải thích lại hiện tượng. Mỗi lần bàn giao làm mất thêm thời gian, trong khi production vẫn đang gặp vấn đề.
Trong vòng lặp AI-native, một trigger có thể gọi Claude mà chưa cần một người đứng giữa. Trigger đó có thể là metric vượt ngưỡng, ticket mới, tin nhắn trong channel hoặc một lịch chạy định kỳ.
Claude chẩn đoán bằng những quyền đã được giới hạn, hành động qua các route có gate, rồi ghi phát hiện thành một intent.md mới. Từ đó, chuỗi Design, Build, Test và Deploy chạy lại. Maintain không còn là phần cuối của SDLC. Nó là điểm vòng lặp quay về đầu.
Một mô hình giám sát hữu ích là control band. Phần phát hiện phải deterministic: một script theo dõi metric production có baseline ổn định, không cần model ngồi đoán xem biểu đồ có “hơi lạ” hay không.
Các ngưỡng có thể được định nghĩa trong bands.yaml. Ví dụ, lệch 1σ thì chỉ ghi log; 2σ thì gọi Claude chẩn đoán ở chế độ read-only; 3σ thì Claude được phép hành động trong phạm vi đã định, chẳng hạn mở một PR để đi vào cổng review.
Model phù hợp với việc giải thích và điều tra. Nó không nên là cảm biến duy nhất quyết định rằng sự cố đã xảy ra. Các band cũng cần được điều chỉnh bằng dữ liệu false positive, thay vì đặt một lần rồi để nguyên mãi.
Security scan định kỳ vận hành theo cùng tinh thần. Một dịch vụ như Claude Security có thể quét mọi repo theo lịch bằng model mạnh, kiểm chứng phát hiện và gắn confidence trước khi đưa chúng tới con người. Lần quét đầu tạo baseline. Một lỗi có phạm vi hẹp có thể đi thẳng thành patch qua PR gate. Một vấn đề rộng hơn phải trở thành intent.md, rồi quay lại Plan để tránh chữa triệu chứng mà bỏ qua nguyên nhân.
Claude cũng có thể tham gia on-call dưới danh tính riêng qua Claude Tag trong Slack hoặc Teams. Khi có incident, Claude là first responder: đọc tín hiệu, truy vấn metric qua MCP, đối chiếu thay đổi gần nhất, đề xuất hoặc thực hiện những hành động đã được phép, rồi xác nhận hệ thống phục hồi.
Channel khi đó trở thành một phần audit trail. Sau incident, Claude có thể soạn post-mortem và cập nhật một file lessons được version-control. Bài học không nằm yên trong một tài liệu ít người đọc; nó quay lại thành CLAUDE.md, skill, hook, test, eval hoặc control band mới.
Khi chưa có sẵn Business Vision: greenfield và brownfield
Chuỗi intent.md → spec.md → plan.md ngầm giả định rằng mình đã có định hướng sản phẩm, hiểu domain và biết những ràng buộc hệ thống quan trọng. Thực tế, dự án mới toanh lẫn codebase kế thừa thường không cho mình sự xa xỉ đó. Trước khi chạy vòng lặp ba artifact cho từng feature, mình phải dùng AI để phỏng vấn hoặc reverse-engineer kiến trúc gốc.
Greenfield: bắt đầu từ số 0
Bước đầu tiên, mình cho AI đóng vai Solution Architect và phỏng vấn ngược chính mình. Nó hỏi về domain, user persona, core use case, các giả định về scale và traffic, công nghệ mình ưu tiên, cùng những giới hạn kinh doanh chưa được viết xuống. Kết quả của cuộc phỏng vấn không phải code mà là ARCHITECTURE.md và DOMAIN_MODEL.md ở root — một blueprint đủ rõ để các quyết định sau không trôi theo từng phiên chat.
Tiếp theo, mình scaffolding khung dự án rồi chạy /init để tạo CLAUDE.md sơ khai. File này giữ các lệnh build, test, lint; quy ước thư mục; package nào được phép dùng; và những phần AI không nên tùy tiện thay đổi. Mình cũng viết trước vài SKILL.md nền như api-standards và db-conventions, để các chuẩn lặp lại được nạp đúng lúc thay vì nhồi tất cả vào một prompt dài.
Lúc bắt đầu feature đầu tiên, mình mới tạo intent/001-mvp.md. Khi ấy AI không còn viết spec trong chân không: nó đã có ARCHITECTURE.md, DOMAIN_MODEL.md, CLAUDE.md và các SKILL.md để sinh spec.md rồi plan.md sát với hệ thống mình thực sự muốn xây.
Brownfield: code cũ nhưng thiếu tài liệu
Với brownfield, codebase chính là đặc tả chân thực nhất — kể cả khi README nói một chuyện còn production đang chạy một chuyện khác.
Mình bắt đầu bằng /init để AI đọc cấu trúc tổng thể, sau đó giao một researcher subagent quét các vùng có tín hiệu cao. models/ và migrations/ tiết lộ data schema ngầm; routes/ và controllers/ cho thấy API contract ngầm; validation rải rác cùng middleware Auth chứa các business constraint mà có thể chưa từng được ghi thành tài liệu.
Tri thức ngầm tìm được cần được đóng gói lại trong .claude/skills/, chẳng hạn legacy-orm-rules hoặc auth-flow-policy. Song song đó, mình thêm hooks làm guardrail để chặn AI sửa file nhạy cảm, legacy migrations hoặc frozen packages. Đây không phải vì AI “không đủ thông minh”, mà vì một codebase lâu năm thường chứa những quyết định sống còn nhưng không thể suy ra chỉ từ tên file.
Sau đó mình gói lệnh test và build của app cũ thành một entry point ổn định, chẳng hạn make test, rồi ghi nó vào CLAUDE.md để AI có thể tự verify sau mỗi thay đổi. Nếu team đang track công việc trên Jira hoặc ServiceNow, mình cũng chọn rõ một cơ chế qua MCP connector: hoặc Linkage để artifact mới trỏ về ticket, hoặc Legacy-as-source-of-truth để ticket hiện tại tiếp tục là nguồn chuẩn và chuỗi artifact chỉ làm lớp triển khai chi tiết.
Nếu suy nghĩ theo kiểu intent-first, chính việc khám phá hệ thống cũng trở thành những intent.md cấp cao. Chẳng hạn, intent/system-domain.md có thể yêu cầu: “Đóng vai Solution Architect, phỏng vấn tôi để làm rõ use case, persona và ràng buộc kinh doanh.” Còn intent/audit-domain-rules.md có thể yêu cầu: “Khảo sát models/, controllers/, migrations/, rồi liệt kê mọi business constraint ngầm đang chạy.” Mọi thứ — research thị trường, trích business rule hay dựng blueprint — đều đi qua cùng một phễu intent → spec → plan.
Nhìn thấy thành công sớm hơn
intent.md, spec.md và plan.md có chuẩn đến đâu thì đầu ra của AI vẫn chưa chắc đúng. Mấu chốt là rút ngắn feedback loop: đưa công việc từ chữ nghĩa trừu tượng sang một thứ chạy được, nhìn thấy được và kiểm tra được càng sớm càng tốt.
Với UI, mình thường biến intent thành mockup hoặc prototype trước khi viết logic. AI implement một lát nhỏ, chụp screenshot, tự compare với mock rồi adjust. Chỉ sau hai hoặc ba vòng như vậy, mình đã thấy khoảng 80% bức tranh và phát hiện những hiểu lầm mà thêm vài trang mô tả cũng chưa chắc làm lộ ra.
Trong plan.md, phần Proof of Correctness phải nhị phân: payload cụ thể trả HTTP 200, test_x pass đủ bốn case, hoặc terminal in ra Build succeeded. Tiêu chí kiểu “xong tính năng X” không giúp model biết khi nào nên dừng, cũng không cho mình một cách khách quan để bác bỏ kết quả.
Mình cũng xẻ kế hoạch thành các vertical thin slices có thể chạy ngay, thường đi cùng test-first: hoàn thành API và test, verify xong rồi mới đi tiếp tới UI. Khi AI sinh mười file cùng lúc, lỗi ở file thứ hai có thể kéo cả chín file sau đi sai hướng; còn một lát cắt mỏng cho mình điểm kiểm tra trước khi sai số kịp tích tụ.
Sau khi code xong, mình giao việc kiểm chứng cho một verifier subagent độc lập với context mới. Subagent này không tham gia sinh code; nó chỉ nạp intent.md và plan.md, chạy app thật rồi báo cáo hành vi quan sát được. Khoảng cách context ấy rất có giá trị: verifier không mang theo bias của session vừa viết code và không có nhu cầu vô thức chứng minh rằng lời giải ban đầu của mình là đúng.
Sợi chỉ xuyên suốt: nhanh hơn vì kiểm soát rõ hơn
Sáu chặng này chỉ bền khi mọi thành phần quan trọng đều được version-control: intent.md, spec.md, plan.md, CLAUDE.md, REVIEW.md, policies, prompts, skills, hooks, cấu hình eval và quy tắc deploy.
Commit history không chỉ kể chuyện code đã thay đổi ra sao. Nó kể cả lý do, thiết kế, kế hoạch, bằng chứng test, quá trình review và quyền phê duyệt. Với tổ chức regulated, một nguồn sự thật duy nhất như vậy thường đáng tin hơn việc phân tán bằng chứng qua nhiều công cụ rồi cố ghép lại khi audit.
Separation of duties cũng không thể dựa vào thiện chí. Agent không được tự duyệt code của mình vì permission không cho phép. Production gate cần người giữ vì branch protection, hook và managed settings bắt buộc điều đó. Cấu hình quan trọng thuộc quyền admin, không phải thứ mỗi kỹ sư có thể tắt khi thấy bất tiện.
Việc tinh chỉnh hệ thống phải dựa trên dữ liệu. Review finding được phân loại để biết lỗi nào lặp lại. Control band được chỉnh theo false positive. Incident biến thành test hoặc eval. Một thay đổi prompt hay skill chỉ được chấp nhận nếu continuous evals chứng minh nó không làm hệ thống tệ đi.
Có vài anti-pattern nhìn rất tiện lúc đầu nhưng sẽ làm vòng lặp mất giá trị. Bỏ qua plan.md khiến agent tạo code trước khi con người kịp kiểm tra hướng đi. Nới lỏng test lúc fix bug làm bằng chứng biến mất. Để agent tự approve phá separation of duties. Bỏ mặc CLAUDE.md cũ khiến tri thức sai được lặp lại với tốc độ cao hơn.
Tương tự, không nên dùng model thay cho cơ chế phát hiện deterministic trong monitoring; không deploy code do agent tạo thẳng lên production; không coi skills là hàng rào bắt buộc; và không trộn nội dung riêng của repo trong CLAUDE.md với hướng dẫn tái sử dụng toàn tổ chức trong skills. Mỗi công cụ có một vai trò. Khi trộn chúng lại, mình vừa làm context khó hiểu, vừa không biết quy tắc nào thật sự được cưỡng chế.
Điều mình thích ở playbook này là nó từ chối một lựa chọn giả: hoặc chạy nhanh, hoặc làm an toàn. Agent có thể tăng tốc phần tạo ra thay đổi, còn quy trình dùng artifact, test, eval, hook và approval gate để giữ phán đoán của con người ở đúng chỗ. Bạn cũng không cần chờ một cuộc chuyển đổi lớn mới bắt đầu: có thể bắt từ việc ghi ý định vào intent.md, viết một CLAUDE.md đủ gọn cho repo, đóng gói những tri thức lặp lại thành skills, hoặc đơn giản là cho Claude một vòng phản hồi để tự chạy test trước khi mở PR. Câu hỏi đáng nghĩ không phải “AI có thay con người trong SDLC không?”, mà là: trong quy trình hiện tại của bạn, chỗ nào đang bắt con người làm việc của máy, và chỗ nào đang để máy đưa ra một phán đoán lẽ ra phải thuộc về con người?