
Tôi dùng Claude Code mỗi ngày, nên khi Chaofan Shou phát hiện hôm nay rằng Anthropic đã phát hành một file .map cùng với package npm của Claude Code — chứa toàn bộ source code CLI ở dạng đọc được — tôi lập tức muốn xem bên trong.
Package sau đó đã bị gỡ xuống, nhưng không kịp trước khi code được mirror rộng rãi (bao gồm cả tôi) và bị phân tích kỹ trên Hacker News.
Đây là lần thứ hai trong một tuần Anthropic vô tình lộ dữ liệu (vụ leak model spec chỉ mới vài ngày trước), và một số người trên Twitter bắt đầu nghi ngờ có ai đó nội bộ cố tình làm vậy. Có lẽ không, nhưng dù sao nhìn cũng không ổn.
Thời điểm này cũng đáng chú ý: chỉ 10 ngày trước, Anthropic đã đe dọa pháp lý OpenCode, buộc họ gỡ xác thực Claude vì tool bên thứ ba dùng API nội bộ để truy cập Opus với giá subscription thay vì pay-per-token. Toàn bộ câu chuyện đó khiến các phát hiện dưới đây trở nên “cay” hơn.
Vì vậy, tôi dành cả buổi sáng đọc comment trên HN và source bị leak. Đây là những gì tôi tìm thấy — sắp xếp theo độ “spicy”.
Anti-distillation: inject tool giả để phá data copy
Trong claude.ts (dòng 301–313), có một flag tên ANTI_DISTILLATION_CC. Khi bật, Claude Code sẽ gửi anti_distillation: ['fake_tools'] trong request API.
Điều này khiến server âm thầm inject các tool giả vào system prompt.
Mục đích: nếu ai đó ghi lại traffic API để train model cạnh tranh, data sẽ bị “nhiễu” bởi các tool giả.
Tính năng này được kiểm soát bởi GrowthBook flag (tengu_anti_distill_fake_tool_injection) và chỉ bật cho CLI chính chủ.
Ngoài ra còn có cơ chế thứ hai trong betas.ts (dòng 279–298): tóm tắt text giữa các lần gọi tool. API sẽ buffer output, tạo summary kèm chữ ký, và chỉ trả summary. Ở lượt sau, text gốc được khôi phục từ signature.
Nếu bạn record traffic, bạn chỉ thấy summary — không thấy reasoning đầy đủ.
Workaround? Không khó.
Fake tool injection chỉ hoạt động khi thỏa 4 điều kiện: flag compile-time, entrypoint CLI, API chính chủ, và flag GrowthBook bật.
Chỉ cần MITM proxy xóa field anti_distillation khỏi request là bypass được hoàn toàn.
Hoặc set env CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS để tắt.
Hoặc dùng API bên thứ ba / SDK thay vì CLI — thì logic này không chạy.
Cơ chế summary còn hẹp hơn: chỉ dành cho user nội bộ (USER_TYPE === 'ant').
Nói ngắn gọn: ai thực sự muốn distill thì chỉ mất khoảng 1 giờ đọc code để bypass.
Bảo vệ thật sự có lẽ là pháp lý, không phải kỹ thuật.
Undercover mode: AI giả làm người
File undercover.ts (~90 dòng) implement chế độ ẩn toàn bộ dấu vết nội bộ khi Claude Code dùng trong repo bên ngoài.
Model bị cấm nhắc đến:
- Codenames nội bộ như “Capybara”, “Tengu”
- Slack nội bộ
- Tên repo
- Thậm chí cả cụm “Claude Code”
Dòng 15 ghi rõ:
“Không có cách tắt. Điều này nhằm tránh lộ codename.”
Bạn có thể bật bằng CLAUDE_CODE_UNDERCOVER=1, nhưng không thể tắt.
Trong build external, code này còn bị tối giản hoàn toàn.
Điều này có nghĩa: commit hoặc PR do AI viết trong repo open-source sẽ không có dấu hiệu nào cho thấy đó là AI.
Ẩn codename thì hợp lý. Nhưng việc AI giả làm người là một câu chuyện khác.
Phát hiện người dùng bực bội bằng regex (đúng vậy, regex)
Trong userPromptKeywords.ts có một regex để detect frustration:
/\b(wtf|wth|ffs|omfg|shit(ty|tiest)?|dumbass|horrible|awful|
piss(ed|ing)? off|piece of (shit|crap|junk)|what the (fuck|hell)|
fucking? (broken|useless|terrible|awful|horrible)|fuck you|
screw (this|you)|so frustrating|this sucks|damn it)\b/
Một công ty LLM dùng regex để phân tích cảm xúc nghe hơi “mỉa mai”.
Nhưng thực tế: regex nhanh và rẻ hơn nhiều so với gọi LLM chỉ để check xem user có đang chửi hay không.
Xác thực client ở tầng native (dưới JS runtime)
Trong system.ts (dòng 59–95), request API chứa placeholder cch=00000.
Trước khi request được gửi đi, Bun (viết bằng Zig) sẽ thay 5 số 0 này bằng hash tính toán.
Server dùng hash này để xác nhận request đến từ binary Claude Code thật.
Họ dùng placeholder cùng độ dài để không làm thay đổi Content-Length hoặc phải reallocate buffer.
Phần tính toán diễn ra dưới JS runtime, nên không thể can thiệp từ JS.
Về bản chất: đây là DRM cho API call, ở tầng HTTP transport.
Đây cũng là nền tảng kỹ thuật phía sau vụ tranh chấp với OpenCode.
Anthropic không chỉ yêu cầu tool bên thứ ba không dùng API — mà binary còn chứng minh cryptographically nó là client thật.
Tuy nhiên, hệ thống này không hoàn hảo.
Nó phụ thuộc vào flag compile-time NATIVE_CLIENT_ATTESTATION.
Header có thể bị tắt bằng env CLAUDE_CODE_ATTRIBUTION_HEADER hoặc GrowthBook killswitch.
Nếu rebuild JS và chạy trên Bun/Node thường, placeholder sẽ giữ nguyên là “00000”.
Server có reject hay không thì chưa rõ.
Nói chung: không phải bypass 1 click, nhưng cũng không đủ mạnh để ngăn client bên thứ ba lâu dài.
250.000 API call bị lãng phí mỗi ngày
Một comment trong autoCompact.ts (dòng 68–70):
“BQ 2026-03-10: 1.279 session có hơn 50 lần lỗi liên tiếp (có session lên tới 3.272 lỗi), gây lãng phí ~250.000 API call mỗi ngày trên toàn cầu.”
Cách fix? Một dòng config:
MAX_CONSECUTIVE_AUTOCOMPACT_FAILURES = 3
Sau 3 lần lỗi liên tiếp, auto-compact sẽ bị tắt cho phần còn lại của session.
Chỉ vài dòng code để tiết kiệm hàng trăm nghìn API call mỗi ngày.
KAIROS: chế độ agent tự động chưa ra mắt
Trong toàn bộ codebase có nhiều chỗ nhắc đến một mode tên KAIROS.
Dựa trên các code path trong main.tsx, đây có vẻ là một chế độ agent tự động chưa được phát hành, với các tính năng:
- Skill
/dreamđể “distill memory vào ban đêm” - Log dạng append-only theo ngày
- Subscribe webhook GitHub
- Worker chạy nền (daemon)
- Refresh theo cron mỗi 5 phút
Đây có thể là tiết lộ roadmap sản phẩm lớn nhất từ vụ leak.
Hiện implementation vẫn bị khóa bởi nhiều flag, nên chưa rõ mức độ hoàn thiện.
Nhưng rõ ràng nền tảng cho một agent chạy nền 24/7 đã tồn tại.
Các chi tiết khác
Ngày mai là 1/4, và source có vẻ chứa trò đùa April Fools:
buddy/companion.ts implement một hệ thống thú ảo kiểu Tamagotchi.
Mỗi user sẽ có một “sinh vật” được generate deterministic từ user ID (18 loài, độ hiếm từ common đến legendary, 1% shiny, có stat kiểu RPG như DEBUGGING, SNARK).
Tên loài được encode bằng String.fromCharCode() để tránh bị build system phát hiện.
Phần render terminal trong ink/screen.ts và ink/optimizer.ts dùng kỹ thuật từ game engine:
- Pool ký tự ASCII bằng
Int32Array - Style encode bằng bitmask
- Optimizer merge cursor move
- Cache width tự động evict (~50x giảm gọi
stringWidth)
Nghe có vẻ overkill — cho đến khi nhớ rằng token được stream từng ký tự.
Mọi lệnh bash đều chạy qua 23 bước kiểm tra bảo mật trong bashSecurity.ts:
- Block 18 built-in của Zsh
- Chống bypass bằng
=curl - Unicode zero-width injection
- IFS null-byte injection
- Bypass token malformed (phát hiện qua HackerOne)
Hiếm thấy tool nào có threat model chi tiết cho Zsh như vậy.
Kinh tế của prompt cache ảnh hưởng mạnh đến kiến trúc.
promptCacheBreakDetection.ts track 14 nguyên nhân phá cache, có “sticky latch” để tránh toggle mode làm mất cache.
Một hàm được đặt tên rất thẳng:
DANGEROUS_uncachedSystemPromptSection()
Khi mỗi token đều tốn tiền, cache invalidation không còn là joke — mà là vấn đề kế toán.
Coordinator đa-agent trong coordinatorMode.ts cũng đáng chú ý:
Thuật toán orchestration không nằm trong code — mà nằm trong prompt.
Ví dụ:
- “Không được chấp nhận output yếu”
- “Phải hiểu kết quả trước khi giao task tiếp theo”
- “Không được outsource việc hiểu cho agent khác”
Codebase cũng có điểm yếu:
print.ts dài 5.594 dòng, một function dài 3.167 dòng với 12 cấp nested.
Họ dùng Axios cho HTTP — khá trớ trêu vì Axios vừa dính vụ npm bị cài mã độc.
Vậy kết luận là gì?
Một số người cho rằng vụ này không nghiêm trọng vì Gemini CLI hay OpenAI Codex đã open source.
Nhưng những công ty đó chỉ open source SDK (toolkit), không phải toàn bộ hệ thống nội bộ.
Thiệt hại thực sự không phải là code.
Mà là feature flags.
KAIROS, anti-distillation… đây là thông tin roadmap mà đối thủ giờ đã thấy.
Code có thể refactor. Nhưng “yếu tố bất ngờ chiến lược” thì không thể lấy lại.
Và còn một chi tiết đáng chú ý:
Anthropic đã mua lại Bun vào cuối năm ngoái, và Claude Code chạy trên Bun.
Một bug trong Bun (oven-sh/bun#28001) báo rằng source map vẫn bị serve ở production dù docs nói là không.
Bug này được report từ ngày 11/3 và vẫn chưa fix.
Nếu đây là nguyên nhân leak, thì chính toolchain của Anthropic đã làm lộ source của họ.
Như một comment trên Twitter nói:
“Việc vô tình publish source map lên npm nghe như điều không thể — cho đến khi bạn nhớ rằng phần lớn code có thể được viết bởi chính AI mà bạn đang phát hành.”