Learn > Claude > Claude Code: custom command & skill

Claude Code: custom command & skill

Tự đóng gói việc lặp lại trong Claude Code: custom slash command bằng file Markdown với $ARGUMENTS, và skill — folder có skill.md, bắt đầu từ verification.

  • Custom command: tự tạo slash command bằng file Markdown trong .claude/commands/ (tên file = tên lệnh, VD audit.md → /audit; tự nhận, không cần restart). Nhận tham số qua placeholder $ARGUMENTS (string bất kỳ, không chỉ file path). Lợi ích: automation, consistency, context, flexibility; commit vào repo để cả team dùng chung.
  • Skill: một FOLDER chứa skill.md (name + description + procedure) trong .claude/skills; khác custom command ở chỗ TỰ FIRE khi task khớp description (không phải gõ /tên). Chỉ description load vào context tới khi cần → đóng gói bao nhiêu procedure cũng không tốn context. Folder mang thêm reference.md (Claude chỉ đọc khi cần chiều sâu) và SCRIPT (Claude chạy, không nạp nội dung) → giữ skill.md lean, đẩy phần nặng ra side file. Verification là skill nên xây ĐẦU TIÊN: nó gỡ sự phụ thuộc "phải nhớ kiểm" — tự chạy test, đọc diff, kiểm test không bị âm thầm nới lỏng, báo pass/fail kèm bằng chứng. Done = gate được CHẠY và QUAN SÁT, không phải "code nhìn ổn". Rule of thumb: gõ cùng chỉ thị nhiều-bước hai lần → làm skill. Bộ ba: convention luôn-đúng → CLAUDE.md; procedure theo loại task → skill; luật không được skip → hook (code chạy thật, không phải instruction làm theo).

TL;DR — Hai cách đóng gói việc lặp: custom command là một file Markdown trong .claude/commands/ (có $ARGUMENTS) — nhanh, hợp việc một bước; skill là một folderskill.md mô tả cả quy trình, hợp việc nhiều bước. Skill nên xây đầu tiên là verification — định nghĩa "Done" nghĩa là gì, vì đó là thứ Claude hay tự cho qua nhất.

Phần 5/7 của ghi chú khoá Claude Code in Action — đề thi thử 219 câu (chấm điểm + giải thích) nằm ở tab "Đề thi thử" trên trang tổng quan.

Custom command — tự đóng gói slash command của riêng mình

Claude Code có sẵn nhiều built-in command (gõ / để xem). Nhưng ta còn tự tạo được custom command để tự động hoá các task lặp đi lặp lại hay chạy.

Tạo một custom command

Chỉ cần dựng đúng cấu trúc thư mục trong project:

  1. Tìm thư mục .claude trong project.
  2. Tạo thư mục con commands bên trong.
  3. Tạo một file Markdown đặt tên theo command muốn có (VD audit.md).

Tên file = tên command: audit.md sinh ra lệnh /audit. Claude Code tự nhận ngay — KHÔNG cần restart.

Ví dụ: lệnh /audit

Một command soi lỗ hổng dependency, làm 3 việc:

  1. Chạy npm audit — tìm package đã cài có lỗ hổng.
  2. Chạy npm audit fixáp update.
  3. Chạy test — verify update không làm vỡ gì.

Nội dung file chỉ là văn bản chỉ thị (prompt) dặn Claude làm 3 bước đó.

Command có tham số — $ARGUMENTS

Custom command nhận argument qua placeholder $ARGUMENTS → linh hoạt, tái dùng được. VD write_tests.md:

Write comprehensive tests for: $ARGUMENTS

Testing conventions:
* Use Vitest with React Testing Library
* Place test files in a __tests__ directory in the same folder as the source file
* Name test files as [filename].test.ts(x)
* Use @/ prefix for imports

Coverage:
* Test happy paths
* Test edge cases
* Test error states

Chạy: /write_tests the use-auth.ts file in the hooks directory → phần chuỗi sau lệnh được thế vào $ARGUMENTS. Argument không nhất thiết là file path — bất kỳ string nào để cấp context/direction cho task.

Bốn lợi ích

  • Automation — workflow lặp → gói thành một lệnh.
  • Consistency — đảm bảo cùng các bước mỗi lần.
  • Context — nhét sẵn chỉ thị + convention của project.
  • Flexibility — dùng argument cho input khác nhau.

Đặc biệt hợp cho workflow riêng của dự án: chạy test suite, deploy code, hay sinh boilerplate theo convention của team.

Ngoài project-level .claude/commands/, còn có user-level ~/.claude/commands/ cho lệnh cá nhân dùng xuyên mọi project — đúng cặp phân cấp như CLAUDE.md. (Khoá gốc không nhắc; biết để linh hoạt.)

Áp dụng thực tế: custom command = đóng gói một SOP thành một nút bấm. Đặt cạnh hai cơ chế đã học: hook là việc bắt buộc, tất định (luôn chạy); custom commandquy trình gọi-khi-cần, lại nhận được tham số. Vì file nằm trong .claude/commands/ commit được vào repo, cả team dùng chung một bộ lệnh — y như cách chia sẻ CLAUDE.md/hooks. Tôi hay dùng để chuẩn hoá những thứ đội dễ làm lệch tay: một /review bám đúng checklist, một /deploy-check chạy đúng thứ tự bước trước khi ship. Nó biến "tài liệu quy trình mà không ai đọc" thành "một lệnh ai cũng gõ".

Skill — đóng gói việc lặp lại, bắt đầu từ verification

Custom command ở trên phải anh gõ /tên mới chạy. Skill là bước tiến hơn: nó tự fire khi task khớp description của nó — anh khỏi phải nhớ gọi.

Một skill là một folder chứa skill.md: một name, một description (thứ kích hoạt nó), và procedure (các bước). Điểm hay về context: chỉ description được load vào context tới khi skill thật sự cầnđóng gói bao nhiêu procedure cũng không tốn context. Check vào .claude/skills của project → cả team thừa hưởng cùng một "nước đi".

Custom command Skill
Nằm ở .claude/commands/<tên>.md .claude/skills/<tên>/skill.md (cả folder)
Kích hoạt User gõ /tên Tự fire khi task khớp description
Mang theo 1 file prompt skill.md + reference.md + script

Vì sao verification là skill nên xây ĐẦU TIÊN

Nghĩ cách anh thường kiểm việc của Claude: nhờ nó refactor, xong rồi anh phải nhớ kiểm lại — bảo nó chạy test, hoặc tự đọc diff. Vấn đề: việc kiểm phụ thuộc anh NHỚ yêu cầu. Quên một lần → code lỗi lọt lưới.

Một verification skill gỡ bỏ sự phụ thuộc đó. Hình dạng của nó: anh nhờ refactor, xong → thay đổi khớp description của skill → skill tự fire, rồi:

  1. Chạy test suite.
  2. Đọc diff.
  3. Kiểm không có test nào bị âm thầm nới lỏng để pass.
  4. Báo pass/fail, kèm bằng chứng.

Cả luồng chạy không cần anh yêu cầu, và đi đúng các bước đó mỗi lần.

Chú ý bước 3: chạy test thấy xanh là chưa đủ — một test có thể bị nới lỏng lặng lẽ cho pass bất kể gì. Nên skill đọc diff xác nhận test không bị làm yếu. "Done" không phải "code nhìn ổn" khi chỉ đọc diff — Done là các cổng (gates) được CHẠY và QUAN SÁT, kết quả nêu tường minh.

Cùng hình dạng này gánh mọi quy trình đội lặp lại: release checklist, migration recipe, pre-PR check. Rule of thumb: gõ cùng một chỉ thị nhiều-bước HAI lần → đó là một skill.

Folder skill chứa nhiều hơn instruction

Đây là chỗ skill mạnh cho verification — folder quanh skill.md mang thêm được:

  • reference.md đặt cạnh, skill.md link tới. Claude chỉ đọc khi thật sự cần chiều sâu → file chính giữ ngắn.
  • Script để trong folder. Claude chạy nó, KHÔNG nạp nội dung vào context → skill mang tooling riêng, VD check.sh chạy hết gates.

Chốt: giữ skill.md lean; đẩy phần nặng (giải thích dài + script chạy được) ra side file. File lean mô tả làm gì; side file giữ chiều sâu + công cụ.

Mặt nào sở hữu luật nào — CLAUDE.md vs Skill vs Hook

Giờ có ba nơi đặt instruction, dễ lẫn. Cách phân cho gọn:

  • Convention lúc-nào-cũng-đúng (naming, file đặt đâu) → CLAUDE.md.
  • Procedure/reference gắn một LOẠI taskskill.
  • Luật Claude KHÔNG được phép skiphook, không phải hai cái trên. Vì CLAUDE.md và skill đều là instruction Claude làm theo; hook là code thật sự chạy. Nếu skip là không chấp nhận được → đừng phó cho instruction-following.

Áp dụng thực tế: repo này là ca gần-thành-skill điển hình. Tôi đã có gate (npm run validate:learn, validate-pages-js, cả chuỗi build) và đã có reference (docs/learn.md) — nhưng chúng rải ở 3 nơi: luật "nhớ chạy validate" trong CLAUDE.md, chi tiết trong docs/, script trong scripts/. Đúng bài học, tôi có thể gói thành một .claude/skills/verify-learn/: skill.md lean (description tự-fire khi đụng src-learn/), reference.md trỏ docs/learn.md, check.sh chạy validate + build. "Check test không bị nới lỏng" trong thế giới của tôi chính là: đọc diff xem perf contract có bị phá âm thầm không (ai đó thêm lại display:none vào #learn-ssr-body, bỏ content-visibility), và đề thi có lộ answer/explain ra SSR không — validator bắt một phần, còn lại là kỷ luật quan sát diff. Và luật thật sự không được skip (validate phải pass trước push) thì thuộc về hook, không phải chữ trong CLAUDE.md: skill lo lúc đang làm, hook là phòng tuyến cuối lúc push. Với Delivery, đây đúng là "Definition of Done" đóng thành hạ tầng: không còn "tôi tin là đã kiểm", mà là gate chạy + quan sát + nêu bằng chứng, và cả đội thừa hưởng vì skill commit vào repo.


Phần tiếp theo: Claude Code: MCP server & tích hợp GitHub

Nguồn: Claude Code in Action (Anthropic Academy) — Copyright Anthropic. Phần đề thi thử cho khoá này nằm ở tab "Đề thi thử" trên trang tổng quan khoá.

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

Làm sao tạo một custom slash command trong Claude Code?
Tạo một file Markdown trong thư mục .claude/commands/ của project — tên file chính là tên lệnh (audit.md tạo ra /audit). Nội dung file là chỉ thị (prompt) cho Claude thực hiện. Claude Code tự nhận command mới ngay, KHÔNG cần restart. Vì file nằm trong .claude/commands/ nên commit vào repo là cả team dùng chung một bộ lệnh. Ngoài project-level còn có user-level ~/.claude/commands/ cho lệnh cá nhân xuyên mọi project.
Placeholder $ARGUMENTS trong custom command dùng để làm gì?
$ARGUMENTS là chỗ để truyền tham số vào command, giúp nó linh hoạt và tái dùng được. Ví dụ chạy "/write_tests the use-auth.ts file in the hooks directory" thì phần chuỗi sau tên lệnh được thế vào $ARGUMENTS trong file command. Argument không nhất thiết là file path — có thể là bất kỳ string nào để cấp context và định hướng cho task.
Skill khác custom command thế nào?
Custom command là một file .claude/commands/<tên>.md, phải USER GÕ /tên mới chạy. Skill là một FOLDER .claude/skills/<tên>/ chứa skill.md, và TỰ FIRE khi task khớp description của nó — không cần gõ. Chỉ description của skill được load vào context tới khi skill thật sự cần, nên đóng gói bao nhiêu skill cũng không tốn context. Skill còn mang thêm reference.md và script trong folder, còn custom command chỉ là một file prompt. Cả hai commit vào repo để cả team dùng chung.
Vì sao verification là skill nên xây đầu tiên?
Vì cách kiểm việc thông thường phụ thuộc bạn NHỚ yêu cầu Claude kiểm — quên một lần là code lỗi lọt lưới. Một verification skill gỡ bỏ sự phụ thuộc đó: khi thay đổi khớp description, skill tự fire và đi đúng các bước mỗi lần — chạy test suite, đọc diff, kiểm không có test nào bị âm thầm nới lỏng để pass, rồi báo pass/fail kèm bằng chứng. Cùng hình dạng này gánh mọi quy trình lặp lại: release checklist, migration recipe, pre-PR check.
Trong một verification skill, "Done" nghĩa là gì?
Done KHÔNG phải "chạy test thấy xanh" hay "code nhìn ổn khi đọc diff". Một test có thể bị nới lỏng lặng lẽ để pass bất kể gì, nên bước quan trọng là đọc diff xác nhận test không bị làm yếu. Done là các cổng (gates) được CHẠY và QUAN SÁT, với kết quả nêu tường minh kèm bằng chứng — không phải phán đoán "trông có vẻ đúng".
Một folder skill chứa được gì ngoài skill.md?
Ngoài skill.md, folder mang thêm được: reference.md (tài liệu chi tiết đặt cạnh, skill.md link tới — Claude chỉ đọc khi thật sự cần chiều sâu, nhờ đó file chính giữ ngắn), và script (Claude CHẠY nó chứ không nạp nội dung vào context, VD check.sh chạy hết các gate). Nguyên tắc: giữ skill.md lean, đẩy phần nặng (giải thích dài + script chạy được) ra side file — file lean mô tả làm gì, side file giữ chiều sâu và công cụ.
CLAUDE.md, skill và hook — luật nào nên đặt ở đâu?
Convention áp dụng lúc-nào-cũng-đúng (naming, file đặt ở đâu) thuộc CLAUDE.md. Procedure và reference gắn với một LOẠI task cụ thể thuộc một skill. Còn luật mà Claude KHÔNG được phép skip thì thuộc hook, không phải hai cái trên — vì CLAUDE.md và skill đều là instruction Claude làm theo (có thể lệch), còn hook là code thật sự chạy. Nếu skip là không chấp nhận được thì đừng phó cho instruction-following.