<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: rednakta</title>
    <description>The latest articles on DEV Community by rednakta (@rednakta).</description>
    <link>https://dev.to/rednakta</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3846751%2Fb5aa3bd8-c27c-4dff-addb-d4c47fa2bf3f.png</url>
      <title>DEV Community: rednakta</title>
      <link>https://dev.to/rednakta</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/rednakta"/>
    <language>en</language>
    <item>
      <title>Zero Token Architecture: Why Your AI Agent Should Never See Your Real API Key</title>
      <dc:creator>rednakta</dc:creator>
      <pubDate>Sat, 18 Apr 2026 10:59:02 +0000</pubDate>
      <link>https://dev.to/rednakta/zero-token-architecture-why-your-ai-agent-should-never-see-your-real-api-key-3a1n</link>
      <guid>https://dev.to/rednakta/zero-token-architecture-why-your-ai-agent-should-never-see-your-real-api-key-3a1n</guid>
      <description>&lt;p&gt;Hot take: every AI agent security guide I've read is solving the wrong problem.&lt;/p&gt;

&lt;p&gt;We spend hours sandboxing the runtime. We lock down the filesystem. We audit every package. We wrap the agent in Docker, then wrap Docker in a VM, then wrap the VM in policy.&lt;/p&gt;

&lt;p&gt;And then we hand the agent a plaintext API key and call it secure.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Stop protecting the token. Just don't hand it over.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  TL;DR
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Prompt injection + arbitrary package execution means any token your AI agent can see is a token it can leak.&lt;/li&gt;
&lt;li&gt;Instead of protecting the token after the agent has it, pass the agent a &lt;em&gt;fake&lt;/em&gt; token whose value equals its own name.&lt;/li&gt;
&lt;li&gt;Intercept the agent's outbound API call at the boundary and swap in the real token there.&lt;/li&gt;
&lt;li&gt;If the fake leaks, the attacker gets a useless string. The real token never leaves your trusted process.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The problem with "protect the token"
&lt;/h2&gt;

&lt;p&gt;Here's what an AI agent's environment typically looks like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nv"&gt;OPEN_API_TOKEN&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;sk-proj-1a2b3c4d5e...
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's a real, working key. The agent reads it, puts it in an &lt;code&gt;Authorization: Bearer&lt;/code&gt; header, and makes calls. Fine — until any of these happen:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Prompt injection&lt;/strong&gt; convinces the agent to &lt;code&gt;echo $OPEN_API_TOKEN&lt;/code&gt; into its next response.&lt;/li&gt;
&lt;li&gt;A &lt;strong&gt;malicious npm/pip package&lt;/strong&gt; the agent installed reads &lt;code&gt;process.env&lt;/code&gt; and POSTs it to a server far, far away.&lt;/li&gt;
&lt;li&gt;The agent &lt;strong&gt;writes a log file&lt;/strong&gt; that happens to include the header it just sent.&lt;/li&gt;
&lt;li&gt;A &lt;strong&gt;tool call&lt;/strong&gt; returns the token because the model decided it would be helpful.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Every mitigation we reach for — sandboxes, permission prompts, egress filtering, audit logs — is downstream of the mistake. The mistake is that the secret exists inside a process we do not trust.&lt;/p&gt;

&lt;p&gt;You cannot perfectly contain a value inside a process that runs arbitrary, model-generated code. You just can't. So stop trying.&lt;/p&gt;

&lt;h2&gt;
  
  
  The paradigm flip
&lt;/h2&gt;

&lt;p&gt;Ask a different question:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;What if the agent never had the real token in the first place?&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;This sounds impossible, because API calls need tokens. But the agent doesn't need the &lt;em&gt;real&lt;/em&gt; token — it just needs the call to succeed. If something else substitutes the real token on the way out, the agent's world is unchanged.&lt;/p&gt;

&lt;p&gt;That something else is a tiny proxy sitting between your agent and the upstream LLM. Let's call it the boundary.&lt;/p&gt;

&lt;h3&gt;
  
  
  Before
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# In the agent's environment&lt;/span&gt;
&lt;span class="nv"&gt;OPEN_API_TOKEN&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;sk-proj-1a2b3c4d5e...
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The real token sits inside the agent. Compromise the agent, compromise the token.&lt;/p&gt;

&lt;h3&gt;
  
  
  After
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# In the agent's environment&lt;/span&gt;
&lt;span class="nv"&gt;OPEN_API_TOKEN&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;OPEN_API_TOKEN
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's not a typo. The variable's &lt;strong&gt;value is its own name&lt;/strong&gt;. The agent reads it, builds &lt;code&gt;Authorization: Bearer OPEN_API_TOKEN&lt;/code&gt;, sends the request. It has no idea anything is weird.&lt;/p&gt;

&lt;p&gt;The boundary intercepts the outbound call, recognizes the placeholder, swaps in the real token (which lives encrypted, outside the agent's reach), and forwards the request upstream.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;┌───────────┐   OPEN_API_TOKEN   ┌──────────┐   sk-proj-real   ┌──────┐
│  Agent    │  ───────────────▶  │ Boundary │  ──────────────▶ │ LLM  │
└───────────┘                    └──────────┘                  └──────┘
     ▲                                                              │
     │                         response                             │
     └──────────────────────────────────────────────────────────────┘
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;From the agent's perspective: totally normal request, totally normal response. From the attacker's perspective, there's nothing worth stealing.&lt;/p&gt;

&lt;h2&gt;
  
  
  The hacker scenario
&lt;/h2&gt;

&lt;p&gt;Let's pretend the worst happened. Prompt injection, malicious dependency, whatever — the attacker exfiltrates everything in the agent's environment.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Old world:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;OPEN_API_TOKEN=sk-proj-1a2b3c4d5e...
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Game over. Billable incidents. Rotation storm. PagerDuty at 3am.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;New world:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;OPEN_API_TOKEN=OPEN_API_TOKEN
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Congratulations, they got a string. They can't call the LLM with it. They can't charge your account with it. They can't even prove which vendor it was for without extra context.&lt;/p&gt;

&lt;p&gt;The leak still &lt;em&gt;happened&lt;/em&gt;. We simply made the leaked value worthless.&lt;/p&gt;

&lt;p&gt;This is the same logic as a one-time password or a macaroon: assume the secret &lt;em&gt;will&lt;/em&gt; escape, and design so that escaping it costs the attacker nothing and you nothing.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why this matters right now
&lt;/h2&gt;

&lt;p&gt;Three trends collide:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Agents are running untrusted code.&lt;/strong&gt; Tool use, code interpreters, and "install this skill" flows mean agent processes routinely execute arbitrary inputs.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Prompt injection is not solved.&lt;/strong&gt; It's not going to be solved by a better system prompt. Treat agent processes as adversarial, always.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Tokens are expensive.&lt;/strong&gt; A leaked OpenAI or Anthropic key is not just a credential breach, it's a bill.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Every AI agent stack I see ships with the real token in an env var because that's how twelve-factor apps work. Agents aren't twelve-factor apps. They're sandboxes for arbitrary model output, except the sandbox is "a language model promised to be careful."&lt;/p&gt;

&lt;p&gt;The fix isn't a better sandbox. The fix is not putting the secret in the sandbox in the first place.&lt;/p&gt;

&lt;h2&gt;
  
  
  How to apply this
&lt;/h2&gt;

&lt;p&gt;If you're rolling your own agent harness:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Put a &lt;strong&gt;local HTTP proxy&lt;/strong&gt; between your agent and any upstream API.&lt;/li&gt;
&lt;li&gt;Give the agent a placeholder token (&lt;code&gt;KEY=KEY&lt;/code&gt; works fine).&lt;/li&gt;
&lt;li&gt;Store the real secret &lt;strong&gt;outside&lt;/strong&gt; the agent's process — OS keychain, a separate daemon, whatever.&lt;/li&gt;
&lt;li&gt;In the proxy, match on the placeholder and substitute the real bearer before forwarding.&lt;/li&gt;
&lt;li&gt;Refuse to forward requests that didn't come through the expected placeholder — this also catches agents trying to call arbitrary URLs.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you'd rather not build this yourself, this idea is the spine of &lt;a href="https://nilbox.run" rel="noopener noreferrer"&gt;&lt;strong&gt;nilbox&lt;/strong&gt;&lt;/a&gt;, an open-source desktop runtime for AI agents. It bundles the proxy, VM isolation, and an encrypted token store so any agent you install can't see your keys — even if it wants to. The full write-up lives in the &lt;a href="https://nilbox.dev/docs/tutorial-zero-token/introduction" rel="noopener noreferrer"&gt;Zero Token Architecture docs&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  The takeaway
&lt;/h2&gt;

&lt;p&gt;The whole security conversation around AI agents is framed as "how do we protect the token we gave the agent?" That's the wrong question.&lt;/p&gt;

&lt;p&gt;The right question is: &lt;strong&gt;why did we give it a token at all?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;If the agent never had it, the agent can't leak it. Everything else is downstream.&lt;/p&gt;

</description>
      <category>agents</category>
      <category>architecture</category>
      <category>security</category>
      <category>openclaw</category>
    </item>
  </channel>
</rss>
