Anthropic vừa gán một con số cụ thể cho điều mà kỹ sư nào cũng đoán được nhưng chẳng ai muốn đo: trong bài “How we contain Claude across products,” công bố ngày 25/5/2026, họ báo cáo người dùng duyệt khoảng 93% permission prompt của Claude Code. Không phải “93% hóa ra ổn” — mà là 93% bị bấm qua cho xong. Cách họ diễn giải rất thẳng thắn: càng thấy nhiều hộp thoại xin phép, người ta càng để tâm ít hơn tới từng cái. Đây chính là cơ chế đứng sau vụ database của Jason Lemkin ở Replit, trong bài đầu series này — ông đã đưa ra đúng chỉ thị duy nhất cần thiết, nhưng hệ thống vẫn cần một thứ khác ngoài sự chú ý của ông để giữ được lằn ranh đó.
Hai bài, hai cách phân loại khác nhau, và có chủ đích
Hai tháng trước đó, ngày 25/3/2026, Anthropic đã công bố “How we built Claude Code auto mode,” mô tả một bộ phân loại hai tầng: một bộ lọc nhanh, một-token, kiểm tra mọi hành động trước tiên, và chỉ khi bộ lọc đó gắn cờ nghi vấn thì một vòng suy luận chain-of-thought chậm hơn — chạy trên Sonnet 4.6 — mới thật sự nghĩ kỹ. Bài đó mô tả mô hình rủi ro theo bốn nhóm: hành vi quá hăng hái, sai sót vô tình, prompt injection, và model bị lệch chuẩn. Họ cũng liệt kê riêng bốn nhóm hành động luôn bị chặn cứng bất kể bộ phân loại kết luận gì: phá hủy hoặc rò rỉ dữ liệu, làm suy yếu tư thế bảo mật, vượt ranh giới tin cậy, hoặc bỏ qua bước rà soát theo cách ảnh hưởng tới người khác.
Bài tháng 5 lại chia hoàn toàn khác — người dùng lạm dụng, model hành xử sai, kẻ tấn công bên ngoài — ba nhóm chia theo ai hoặc cái gì gây ra vấn đề, không phải hành động đó trông ra sao. Mình từng phân vân không biết đây có phải Anthropic thiếu nhất quán. Thật ra không phải. Khung tháng 3 được thu hẹp cho một bộ phân loại quyết định có nên chặn một hành động cụ thể; khung tháng 5 là góc nhìn rộng hơn, bao trùm cả dòng sản phẩm, chia theo nguồn gốc gây hại thay vì hình dạng của cái hại đó. “Prompt injection” của tháng 3 là một tập con của “kẻ tấn công bên ngoài” ở tháng 5. Còn “hành vi quá hăng hái,” “sai sót vô tình” và “model lệch chuẩn” của tháng 3 đều gộp vào “model hành xử sai” ở tháng 5. Một bên là chi tiết mịn nạp vào một bản đồ thô hơn — nhưng đáng để biết mình đang nhìn hai độ phân giải khác nhau, trước khi trích dẫn một trong hai như thể đó là khung rủi ro chính thức duy nhất của Anthropic, vì thật ra chưa có cái nào là duy nhất cả.
Phần thật sự kéo con số 93% xuống
Nếu cách sửa chỉ là “hỏi khéo hơn” thì chẳng có gì đáng viết. Nhưng không phải vậy. Một bài riêng ngày 20/10/2025, “Beyond permission prompts: making Claude Code more secure and autonomous,” giới thiệu cơ chế thực thi trong sandbox — bubblewrap trên Linux, Seatbelt trên macOS — và báo cáo kết quả thật: giảm 84% số permission prompt, không phải nhờ bộ phân loại thông minh hơn trong việc quyết định hỏi gì, mà nhờ loại bỏ luôn phần lớn hành động vốn dĩ cần phải hỏi ngay từ đầu. Một shell chạy trong sandbox, không với ra được mạng hay file ngoài thư mục làm việc, thì không cần con người gật đầu cho từng lệnh bên trong nó, vì chẳng còn gì để duyệt nữa.
Đó mới là bước chuyển thật sự, và cũng chính là bước Replit đã làm sau vụ Lemkin: ngừng dồn mọi thứ qua một hộp thoại, và thu hẹp về mặt cấu trúc phạm vi có thể chạm tới mà không cần hộp thoại đó. Với những gì vẫn cần một quyết định sống của con người, Claude Agent SDK cung cấp callback canUseTool — một điểm dừng-và-chờ thật sự, chỉ được gọi tới sau khi hooks và các quy tắc allow/deny đã không tự giải quyết được yêu cầu. Đây là phương án cuối cùng, không phải tuyến phòng thủ đầu tiên.
Checklist, nếu bạn tự xây cái này
Mình không dám nói năm gạch đầu dòng giải quyết trọn vẹn bài toán phân quyền cho agent. Nhưng nếu bạn đang gắn luồng xin phép vào sản phẩm agent của mình, đây là những lựa chọn thiết kế thật sự khớp với những gì đã hiệu quả ở đây và trong bộ OWASP Top 10 for Agentic Applications mà cả series này dựa vào:
Phân loại theo mức độ có thể hoàn tác, không theo loại hành động. Một hành động phá hủy hoặc không thể hoàn tác cần bị chặn cứng về mặt cấu trúc, không phải một dòng hỏi xin phép — đúng bài học Replit rút ra từ database production. Nếu hoàn tác tốn kém hoặc bất khả thi, một dòng chat xin phép không phải là kiểm soát, chỉ là thủ tục cho có.
Giữ bên chấm điểm tách biệt khỏi bên hành động. Bộ phân loại của Anthropic chạy như một lượt riêng, không phải chính model đang hành động tự báo cáo mức rủi ro của mình. Một model tự chấm bài mình về việc có nên tiếp tục hay không chính là nhóm “sai sót vô tình” ở bài tháng 3, nhưng lần này được cài thẳng vào cơ chế an toàn.
Thu hẹp bán kính ảnh hưởng trước khi đi hỏi. Sandbox giúp Anthropic giảm 84% số lượng prompt — không phải nhờ hỏi câu thông minh hơn, mà nhờ khiến phần lớn câu hỏi trở nên không cần thiết. Nếu một hành động về bản chất không thể chạm tới bất cứ thứ gì nhạy cảm, nó không cần con người đứng giữa vòng lặp.
Coi tỷ lệ duyệt của chính mình là một chỉ số sống, không phải ô tick cho có. Nếu bạn không đo được bao nhiêu phần trăm prompt của mình bị duyệt cho qua, bạn sẽ không biết mình đang có vấn đề kiểu 93% cho tới khi có thứ lọt qua đáng lẽ không nên lọt. Theo dõi nó như cách theo dõi tỷ lệ báo động giả của một hệ thống cảnh báo.
Chỉ dùng callback human-in-the-loop cho những gì thật sự mơ hồ. Các hook kiểu canUseTool hiệu quả chính vì chúng hiếm khi kích hoạt. Ngay khi chúng bật lên cho cả những hành động thường ngày, bạn đã dựng lại đúng vấn đề mỏi mệt-vì-duyệt mà sandbox vốn được dựng lên để tránh.
Ba bài, một sợi chỉ xuyên suốt: lỗi chưa bao giờ nằm ở việc agent quá năng lực. Nó nằm ở chỗ phần “có năng lực” và phần “chịu trách nhiệm” cứ sống chung trong cùng một khoảnh khắc không tách rời — một cửa sổ chat, một chữ ký, một hộp thoại — không có khoảng trống cấu trúc nào giữa lúc quyết định và lúc thực thi. Mọi cách sửa thật sự hiệu quả, từ việc Replit tách dev/prod cho tới sandbox của Anthropic, đều làm đúng một việc chẳng có gì hào nhoáng: dựng một bức tường ở nơi trước đây chỉ có một câu hỏi.