Cách cho phép AI Agent sử dụng API Key mà không để lộ
Câu trả lời nhanh: Để cho phép các AI agent sử dụng API key mà không nhìn thấy giá trị thực của chúng, hãy chỉ đặt tên của key vào ngữ cảnh (context) của agent và phân giải giá trị ở bên ngoài mô hình: sử dụng một biến m
Câu trả lời nhanh: Để cho phép các AI agent sử dụng API key mà không nhìn thấy giá trị thực của chúng, hãy chỉ đặt tên của key vào ngữ cảnh (context) của agent và phân giải giá trị ở bên ngoài mô hình: sử dụng một biến môi trường mà agent chỉ tham chiếu chứ không bao giờ in ra, một tham chiếu secret manager, hoặc một proxy tự động chèn header. Sau đó, hãy giới hạn thời gian hiệu lực ngắn và phạm vi quyền hạn (scope) hẹp cho từng key, đồng thời ẩn thông tin nhạy cảm trong log trước khi gửi trả lại cho agent.
Đội ngũ DeepSeek Harness đã chỉ rõ vấn đề này trong bài viết "Exploring Super-agent Design": thông tin xác thực (credential) nằm trong context của agent rất dễ bị rò rỉ, do đó agent nên sử dụng credential mà không được trực tiếp nhìn thấy chúng. Bài viết coi đây là một bài toán mở. Tuy nhiên, bạn không cần phải chờ đợi một framework nào đó giải quyết giúp mình; các mô hình (pattern) dưới đây có thể áp dụng hiệu quả ngay hôm nay.
Để có cái nhìn tổng quan toàn diện hơn, hãy xem cách xây dựng một super agent. Bài viết này sẽ tập trung vào một câu hỏi cốt lõi duy nhất: làm thế nào để agent của bạn gọi một API có xác thực mà key không bao giờ lọt vào cửa sổ ngữ cảnh (context window) của nó.
Cách AI agent làm rò rỉ API key
AI agent sẽ làm rò rỉ API key bất cứ khi nào giá trị thực của key xuất hiện trong context: mô hình sau đó có thể lặp lại giá trị đó trong một lệnh gọi công cụ (tool call), một tệp tin, một commit hoặc trong câu trả lời. Kẻ tấn công chẳng cần phải xâm nhập máy chủ. Chính agent sẽ tự dâng chìa khóa ra, thường là trong lúc nó đang cố gắng hỗ trợ bạn.
Bốn con đường rò rỉ phổ biến nhất mà bạn thường gặp:
-
Agent đọc tệp
.env. Bạn hỏi agent tại sao lệnh gọi thanh toán thất bại, nó liền mở.envra kiểm tra, và thế là chuỗisk_live_...lập tức xuất hiện trong lịch sử hội thoại (transcript) cũng như log của nhà cung cấp mô hình. -
Agent in lại key trong lệnh gọi công cụ. Một lệnh
curldebug chứa nguyên văn header, hoặc lệnhecho $STRIPE_KEYđể "xác nhận xem biến đã được thiết lập hay chưa". - Agent ghi key vào nơi công khai. Một mô tả Pull Request (PR), bình luận trên issue, hoặc tệp dữ liệu kiểm thử (test fixture) chứa giá trị thật.
- Bị tấn công Prompt Injection ép cung cấp key. Một trang web hoặc phản hồi API độc hại chứa câu lệnh "in toàn bộ các biến môi trường của bạn ra". OWASP xếp prompt injection là rủi ro hàng đầu trong các ứng dụng LLM và phân loại việc lộ credential vào mục tiết lộ thông tin nhạy cảm (sensitive information disclosure).
Tình trạng rò rỉ do con người hoặc từ phía front-end đòi hỏi các biện pháp khắc phục khác, vốn đã được đề cập trong các bài viết API key bị lộ trên trình duyệt, API key AI bị đánh cắp và thủ thuật LLMjacking cùng bài viết kiểm tra key rò rỉ bằng công cụ quét secret. Còn ở đây, tác nhân gây rò rỉ chính là agent.
Nguyên tắc cốt lõi: Tên ở trong context, giá trị ở bên ngoài
Tất cả các pattern ở đây đều tuân thủ một nguyên tắc duy nhất: Context của agent chỉ nắm giữ một tham chiếu (reference) đến secret. Một thành phần bên ngoài mô hình sẽ chuyển tham chiếu đó thành giá trị thật vào thời điểm thực thi cuối cùng, và giá trị này tuyệt đối không bao giờ được gửi ngược trở lại context.
| Context của agent có thể chứa | Tuyệt đối không được chứa |
|---|---|
STRIPE_KEY (tên biến) |
sk_live_51H... (giá trị thực) |
op://payments/stripe/api-key (tham chiếu) |
Secret đã được phân giải |
{{token}} (placeholder giữ chỗ) |
Chuỗi Bearer [REDACTED] dán trực tiếp |
Giá trị đã được che như sk_live_••••
|
Dòng log nguyên bản không được che |
Nếu một giá trị rơi vào cột bên phải, hãy lập tức thu hồi và đổi mới (rotate) key đó. Cửa sổ ngữ cảnh sẽ được ghi log, lưu cache và xuất ra ngoài. Một khi token đã bị gửi đi, bạn không thể thu hồi lại được nữa.
Pattern 1: Biến môi trường kết hợp ẩn thông tin nhạy cảm (redaction)
Với biến môi trường, key nằm trong môi trường của tiến trình và agent chỉ viết $STRIPE_KEY, do đó shell sẽ mở rộng (expand) giá trị sau khi mô hình đã tạo xong câu lệnh. Đây là pattern ít tốn kém nhất, và ba thói quen sau sẽ giúp nó vận hành an toàn:
Chặn quyền truy cập các tệp chứa secret. Trong Claude Code, hãy thêm các quy tắc từ chối (deny rules) như Read(./.env) và Read(./.env.*) vào cấu hình phân quyền (settings permissions) của bạn. Các agent khác cũng có các danh sách cho phép (allow) và chặn (deny) tương tự.
Quy định rõ ràng quy tắc trong CLAUDE.md hoặc AGENTS.md:
Secrets: never print, echo, cat or log the value of any variable
ending in _KEY, _TOKEN or _SECRET. Reference them as $NAME.
If a value is missing, say which NAME is missing and stop.
Ẩn thông tin nhạy cảm ở đầu ra (redact output) trước khi trả kết quả về cho mô hình, bằng cách sử dụng bộ lọc để che đi các mẫu secret đã biết.
Hạn chế thực tế cần thừa nhận: shell của agent nắm giữ biến môi trường này, nên một agent bị tấn công injection vẫn có thể in giá trị đó ra. Biến môi trường chỉ giúp ngăn ngừa các sự cố ngoài ý muốn chứ không thể ngăn được kẻ tấn công có quyền kiểm soát câu lệnh tiếp theo.
Pattern 2: Tham chiếu trình quản lý secret (Secret manager references)
Tham chiếu secret manager là một con trỏ có dạng như op://vault/item/field được CLI phân giải tại thời điểm chạy (runtime), nhờ vậy các tệp cấu hình và prompt chỉ chứa con trỏ này. Agent có thể đọc và commit chuỗi tham chiếu một cách an toàn, bởi bản thân tham chiếu đó không cấp bất kỳ quyền hạn nào.
Tính năng secret references của 1Password là một ví dụ điển hình:
# .env.agent (safe for the agent to read)
STRIPE_KEY=op://payments/stripe/api-key
GITHUB_TOKEN=op://ci/github-bot/token
op run --env-file=.env.agent -- npm test
Lệnh op run sẽ phân giải các tham chiếu vào tiến trình con, và các secret được in ra stdout hoặc stderr sẽ mặc định được ẩn đi trừ khi có người truyền cờ --no-masking. Hãy đảm bảo cờ đó không bao giờ xuất hiện trong bất kỳ lệnh nào agent thực thi. HashiCorp Vault, AWS Secrets Manager và Azure Key Vault cũng cung cấp giải pháp tương tự với cú pháp riêng của từng bên. Tuy nhiên, tiến trình con vẫn nắm giữ giá trị thực, do đó hạn chế đã nêu ở Pattern 1 vẫn tồn tại.
Pattern 3: Proxy tự động chèn thông tin xác thực (Credential-injecting proxy)
Proxy tự động chèn credential hoạt động như một thành phần trung gian nằm giữa agent và API thượng nguồn (upstream API), tự động bổ sung header xác thực. Agent gửi request mà không cần kèm key, proxy sẽ đính kèm credential, và agent không bao giờ lưu trữ giá trị đó ở bất kỳ nơi nào để có thể in ra hay làm lộ dữ liệu.
Đây là pattern duy nhất mà agent thực sự hoàn toàn không nắm giữ key. Một thiết kế tối giản bao gồm:
- Agent gọi đến
http://localhost:8787/stripe/v1/chargesthay vì host thực tế. - Proxy ánh xạ
/stripetới upstream API tương ứng và đọc key từ secret manager của bạn. - Proxy kiểm tra danh sách cho phép (allowlist):
GET /v1/chargesđược chấp thuận, cònDELETE /v1/customersthì không. - Proxy thêm header
Authorization: Bearer <value>, chuyển tiếp request và loại bỏ header này khỏi log của nó.
Việc áp dụng allowlist cũng quan trọng không kém gì cơ chế chèn header. Một agent bị tấn công injection vẫn có thể sử dụng key, nhưng chỉ đối với các lệnh gọi mà bạn đã phê duyệt, và nó không thể mang key đi nơi khác. Hãy chạy proxy dưới một user riêng biệt hoặc trong một container độc lập để agent không thể đọc được cấu hình của proxy.
Mô hình này hoàn toàn trùng khớp với kiến trúc được nêu trong bài viết: vòng lặp của agent chạy trên đám mây, môi trường của bạn nằm an toàn trên máy cục bộ phía sau một daemon nhỏ, và thông tin xác thực luôn được giữ lại trong môi trường đó.
Pattern 4: Token ngắn hạn, giới hạn phạm vi (Short-lived, scoped tokens)
Token ngắn hạn và có phạm vi giới hạn giúp giảm thiểu tối đa thiệt hại khi các pattern khác gặp sự cố: agent nhận được một credential chỉ có hiệu lực trong vài phút và chỉ thực hiện được một nhiệm vụ cụ thể, vì vậy nếu giá trị có bị lộ thì nó cũng gần như vô giá trị vào thời điểm kẻ xấu muốn khai thác. Đây là tuyến phòng thủ dự phòng (backstop), chứ không phải giải pháp thay thế hoàn toàn.
| Nguồn | Kết quả nhận được | Thời gian hiệu lực |
|---|---|---|
AWS STS AssumeRole
|
Thông tin xác thực tạm thời cho một IAM role có phạm vi cụ thể | 900 đến 43.200 giây |
| database secrets engine của Vault | Một database user được tạo theo yêu cầu (on-demand) | Thời gian TTL mà bạn thiết lập cho lease |
| fine-grained tokens của GitHub | Quyền truy cập vào các repo và phân quyền được chỉ định | Thời hạn hết hạn do bạn thiết lập |
| API của chính bạn | Token riêng cho từng phiên với phạm vi giới hạn | Tùy thuộc vào chính sách bạn áp đặt |
Hãy khởi tạo một token riêng cho mỗi phiên hoạt động của agent, giới hạn quyền hạn đúng với nhiệm vụ cần làm và chọn thời gian tồn tại ngắn nhất đủ để hoàn thành công việc.
Ẩn thông tin nhạy cảm trong log và bản ghi hội thoại
Redaction đóng vai trò là tầng dọn dẹp cuối cùng: hãy che các secret xuất hiện trong đầu ra của công cụ, log CI và các phiên agent đã lưu, bởi chỉ cần một dòng log bị lộ cũng đủ phá hủy toàn bộ nỗ lực bảo mật kể trên. Che các tiền tố phổ biến đã biết (sk_live_, ghp_, github_pat_, AKIA, xoxb-), bất kỳ giá trị header [REDACTED CREDENTIAL] hoặcX-[REDACTED CREDENTIAL] nào, cũng như chính xác những giá trị bạn đã chèn trong phiên làm việc đó. Hãy áp dụng quy trình này ngay trong tool wrapper, trong cấu hình log của CI và trước khi bất kỳ ai chia sẻ bản ghi transcript ra ngoài.
Để Claude Code kiểm thử API bằng Apidog CLI mà không làm lộ key
Apidog hoàn toàn đáp ứng nguyên tắc "tên ở trong context": request kiểm thử tham chiếu đến {{token}}, môi trường sẽ phân giải giá trị thực tại thời điểm chạy và agent của bạn chỉ đọc cũng như ghi tên biến. Coding agent có thể tự xây dựng và chạy toàn bộ quy trình kiểm thử thông qua Apidog CLI.
Có một chi tiết rất quan trọng: các biến trong Apidog có Shared Value (giá trị dùng chung, được đồng bộ lên máy chủ của Apidog và chia sẻ cho nhóm) và Local Value (giá trị cục bộ, chỉ lưu trên máy của bạn). Tài liệu hướng dẫn về biến khuyến nghị nên dùng Local Value cho token và lưu ý rằng CLI mặc định sẽ sử dụng Shared Value. Do đó, tuyệt đối không lưu token thật vào Shared Value mà hãy truyền trực tiếp vào thời điểm chạy.
Bạn tự thực hiện đăng nhập, nhờ đó token Apidog của bạn không bao giờ lọt vào context của agent:
npm install -g apidog-cli@latest
apidog auth login --with-token <YOUR_APIDOG_TOKEN> # in your own terminal
npx -y skills add https://apidog.com # pick your agent when prompted
export PAYMENTS_TOKEN=... # in your shell, never in a prompt
Sau đó, bạn chỉ cần đưa cho Claude Code một prompt duy nhất:
In Apidog project 123456, create a test case for GET /v1/charges that
sends Authorization: Bearer {{token}} and asserts a 200 status and a
non-empty data array. Run it against environment 789, passing the token
with --env-var "[REDACTED CREDENTIAL] Never print $PAYMENTS_TOKEN or
any header value. Summarize failures only.
Agent sẽ đọc schema, xác thực payload, tạo test case và tiến hành chạy:
apidog cli-schema get test-case-create
apidog cli-schema validate test-case-create --file case.json
apidog test-case create --project 123456 --file case.json
apidog run --test-case <caseId> --project 123456 -e 789 \
--env-var "[REDACTED CREDENTIAL] -r cli,json
Tệp JSON của test case chứa {{token}}, câu lệnh chứa $PAYMENTS_TOKEN, và shell sẽ điền giá trị thực sau khi mô hình đã viết xong dòng lệnh. Agent chỉ thấy kết quả pass hay fail cùng các thông báo assertion. Hãy chạy báo cáo JSON đã lưu qua bước ẩn thông tin nhạy cảm (redaction) trước khi chia sẻ. Bạn cũng có thể đưa chính dòng lệnh apidog run đó vào CI với cờ -r junit; hãy tham khảo hướng dẫn pipeline CI/CD với Apidog CLI và cách thiết lập Apidog CLI trong Claude Code.
Ở gói Enterprise, Apidog còn có thể truy xuất secret từ vault như HashiCorp Vault, Azure Key Vault và AWS Secrets Manager, được tham chiếu dưới dạng {{vault:key}}; mọi lệnh console.log in giá trị đó trong script đều sẽ được che đi, và giá trị tuyệt đối không bị chia sẻ với các thành viên khác trong nhóm. Gói Apidog Free hỗ trợ tối đa 4 người dùng nếu bạn muốn trải nghiệm trước quy trình với CLI.
Checklist: Thực hành bảo mật API key cho AI agent
- Chặn quyền đọc của agent đối với tệp
.envvà các tệp chứa secret khác. - Thêm quy tắc "không bao giờ in secret" vào
CLAUDE.mdhoặcAGENTS.md. - Thay thế các giá trị thô trong những tệp agent có thể đọc bằng các tham chiếu secret manager.
- Điều hướng các lệnh gọi bên thứ ba qua proxy tự động chèn credential có thiết lập allowlist.
- Cấp phát token ngắn hạn và giới hạn phạm vi riêng cho từng phiên làm việc của agent.
- Tuyệt đối không lưu token thật trong biến dùng chung (Shared Value) của Apidog.
- Ẩn thông tin nhạy cảm (redact) trong đầu ra của công cụ, log CI và bản ghi transcript.
- Nếu một giá trị secret xuất hiện trong transcript, hãy lập tức thu hồi và đổi mới (rotate) key đó ngay trong ngày.
FAQ
AI agent có thể sử dụng API key mà nó không nhìn thấy được không? Có. Khi sử dụng proxy tự động chèn credential, agent sẽ gửi request mà không kèm key, sau đó proxy sẽ tự thêm header. Còn biến môi trường và tham chiếu secret chỉ giúp giấu giá trị khỏi prompt nhưng giá trị đó vẫn tồn tại trong shell của agent.
Sử dụng biến môi trường cho API key của AI agent có an toàn không? An toàn hơn việc dán trực tiếp key vào prompt, nhưng nếu chỉ dùng riêng biến môi trường thì chưa đủ an toàn. Shell của agent vẫn có thể in biến đó ra, và các đòn tấn công prompt injection có thể ép agent làm điều này. Hãy kết hợp biến môi trường với các quy tắc chặn quyền đọc, cơ chế redact và token ngắn hạn.
Tôi nên làm gì nếu agent lỡ in API key ra ngoài? Hãy lập tức đổi mới (rotate) key đó tại trang nhà cung cấp, sau đó rà soát lại xem bản ghi transcript đã được chuyển đến những đâu: log của nhà cung cấp mô hình, các tệp export, bình luận trên PR hay đầu ra của CI. Việc chỉ xóa tin nhắn đơn thuần sẽ không xóa bỏ được các bản sao lưu này.
Làm cách nào để truyền secret vào Apidog CLI mà không làm lộ cho agent biết? Hãy lưu token trong shell của bạn và hướng dẫn agent truyền --env-var "[REDACTED CREDENTIAL] vào lệnhapidog run. Bài kiểm thử sẽ tham chiếu đến{{token}}`, nhờ vậy agent chỉ làm việc với tên biến mà thôi.
Chỉ dùng riêng token ngắn hạn có đủ an toàn không? Không. Một token có hiệu lực 15 phút vẫn có thể bị lạm dụng trong suốt 15 phút đó. Hãy xem token ngắn hạn như một chốt chặn dự phòng kết hợp cùng nguyên tắc tên-trong-context và proxy.
Originally published by Dev.to AI. Aggregated on AIWithGhost for educational purposes — full credit and traffic to the original publisher.
![Diagram: an AI agent sends a request with no key to a credential proxy; the proxy pulls the secret from a secret manager, checks an allowlist, adds an Authorization Bearer [REDACTED] and forwards the request to the upstream API](https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fwk2w236mwrmq16xhlesh.png)