Publishing Credentialed Tool Packs
Applies to SDK 0.16+ · Last updated: 2026-06-12
A tool pack often needs an API key that belongs to the user — an Ahrefs key, an OpenAI key, a private service token. AgentNode is bring-your-own-key: the user supplies the key in their own environment, and AgentNode never stores, sees, or brokers it. As a publisher you do two things: declare which variables your pack needs, and declare the exact domains it is allowed to reach. Those two declarations are what make the key flow safe and, for community packs, what make it work at all.
1. Declare the credentials
Add an env_requirements list to your manifest. Each entry names one environment variable — names only, never values.
env_requirements:
- name: "AHREFS_API_KEY"
required: true
description: "Ahrefs API key"
- name: "AHREFS_WORKSPACE"
required: false
description: "Optional workspace id"| Field | Type | Required | Meaning |
|---|---|---|---|
| name | string | Yes | The environment variable name, e.g. AHREFS_API_KEY. Case-sensitive. Never a value. |
| required | boolean | No (default true) | If true, a run is blocked until the variable is set. If false, the tool runs without it (the key is passed through only when present). |
| description | string | No | A short human explanation shown on the package page and in the publish form, e.g. "Ahrefs API key". |
Your tool code reads the value the ordinary way — for example os.environ["AHREFS_API_KEY"]. The declaration does not inject anything; it tells AgentNode which names to check, prompt for, and pass through.
2. Declare the egress allowlist
A pack that carries a secret must also say exactly where that secret may go. Set permissions.network.level to restricted and list the API hosts in allowed_domains. For a community pack this is mandatory: a credentialed run with no valid allowlist is refused — a secret never rides an open or unrestricted network.
permissions:
network:
level: "restricted" # required for credentialed community packs
allowed_domains:
- "api.ahrefs.com" # the only host the key can reach
filesystem:
level: "none"
code_execution:
level: "none"List every host your tool actually calls, and nothing more. When the pack runs sandboxed, AgentNode starts an egress proxy limited to exactly these domains; a request to anywhere else is dropped. This is the mechanism that prevents a compromised or malicious pack from exfiltrating the user's key.
What the user experiences
| Step | What happens |
|---|---|
| install | The declared variables are listed with their set / not-set status. Required-but-unset ones are called out. |
| run (missing required key) | The run is refused before dispatch with a clear message naming the variable — no cryptic tool error. |
| run (community pack, sandboxed) | One consent prompt names the keys and the exact domains. The container runs on an egress proxy limited to those domains; the key is passed by name only (never on argv, in the process spec, or in logs). |
| run (curated / trusted, host) | The tool reads the key from the environment directly, as any host process would. |
The consent a user grants is bound to your exact package identity — slug, version, artifact hash, the declared key names, and the declared domains. If you publish a new version, change the key set, or change the domains, the user is asked again. Consent can never silently carry over to a different pack or a widened set of permissions.
Fail-closed rules to keep in mind
- A credentialed community pack with an empty or invalid
allowed_domainsis refused, not run without protection. - A missing
requiredvariable blocks the run up front with a message that names the variable. - Keys are passed to the container by name only. The value is read by the container runtime, never placed on the command line, in the process spec, or in any log.
env_requirementsandallowed_domainsare sealed into the user's lockfile at install. Tampering with either breaks lockfile integrity.- Non-credentialed packs are unaffected — declaring no
env_requirementskeeps the ordinary run path.
Publisher checklist
- Read the key in your tool code from the environment.
- Declare each variable under
env_requirements(name, required, description). - Set
network.level: restrictedand list every API host underallowed_domains. - Validate before publishing:
agentnode validate .— see the Publishing Guide and the ANP Manifest Reference.
For how AgentNode isolates execution per trust tier, see the Sandbox docs. For where a user's keys are stored, see Credentials & Connectors.