Coding agents that run in a terminal can read files, run commands and commit code. That is the point of them, and it is also why they change where secrets are exposed. A .env file that was a harmless local convenience becomes something an automated process can read, and anything the process can read can end up in a prompt, a log or a command someone else steered it into running.
We provide managed hosting and website maintenance at ResaHost, and we set up and manage 1Password Business for customers, so we have a commercial interest in how teams handle secrets. This article uses 1Password only as one documented example, and the principles apply to any secrets manager.
The risk is not only a bad model, it is untrusted input
OWASP's LLM01 entry on prompt injection describes indirect prompt injection: the model accepts input from external sources such as websites or files, and that content alters its behaviour. OWASP lists disclosure of sensitive information, unauthorised access to functions available to the model and executing arbitrary commands in connected systems among the possible outcomes. It also states that it is unclear whether fool-proof prevention exists, and recommends limiting the impact instead.
For a developer this means a README, an issue comment, a dependency's documentation or a web page the agent fetches can contain text meant for the agent. You cannot rely on reading every input yourself. The design question becomes: if the agent follows a hostile instruction, what can it reach?
OWASP's mitigations map directly onto that question. They include enforcing privilege control and least privilege access, requiring human approval for high-risk actions, and segregating untrusted external content from instructions.
Principle 1: the agent should not hold more than the task needs
The OWASP Secrets Management Cheat Sheet notes that many organisations hard-code secrets in source or leave them in configuration files, and recommends centralising storage, provisioning, auditing and rotation. It also says engineers should not have access to all secrets in the system, and that fine-grained access control should apply least privilege.
For an agent session, apply the same rule:
- Use a separate, low-privilege credential for the agent, not your personal admin token.
- Do not give it production credentials unless the task is a production task.
- Prefer credentials that are limited to one repository, one environment or one API scope.
Principle 2: short-lived beats long-lived
OWASP recommends dynamic secrets where possible, with a short lease and revocation when they are no longer needed, and automated rotation for static secrets. An API key that expires after an hour is worth much less to anyone who extracts it than a key that lives for years. If your provider supports scoped, expiring tokens, use them for agent sessions.
Principle 3: keep secrets off disk and out of history
Plaintext .env files get committed, copied, backed up and read by whatever runs in the directory. Two documented ways to reduce that:
- Secret references. With the 1Password CLI, you store a reference such as
op://vault/item/fieldin your configuration instead of the secret.op runreplaces the reference with the real value only for the subprocess it starts. The documentation recommends service accounts that are restricted to specific vaults, so processes in the session can only access the items needed. - An SSH agent. The 1Password SSH agent lets Git and SSH clients authenticate without being able to read the private key, and only clients you explicitly authorise can use the key until 1Password locks.
Be precise about what this achieves. Secret references keep the value out of files and shell history. They do not make the value invisible to a process you start with them. A subprocess that receives a secret as an environment variable can print it, and an agent that can run arbitrary commands in that environment can be asked to. So the second half of the defence is scope: the vault or service account behind the reference should contain only what that session needs.
Principle 4: catch what leaks anyway
Mistakes happen, so add detection. OWASP suggests secrets detection at developer level, in the IDE or through a pre-commit hook, so secrets are not committed. On the repository side, GitHub secret scanning detects credentials committed to repositories, and push protection is a related feature. When a secret is exposed, rotate or revoke it. OWASP is explicit that removing it from the exposed system is part of the response.
Principle 5: keep a human at the risky steps
Do not run an agent in an auto-approve mode with broad credentials. Require review of the diff before a commit lands, and approval before the agent runs commands that touch deployment, billing, DNS or credentials. If an agent suddenly asks for access to something the task does not need, stop the session and look at what it read before that point. This is the OWASP recommendation of human approval for high-risk actions, applied to a terminal.
Also keep an audit trail. OWASP lists what to log at a minimum: who requested a secret and for which system, whether the request was approved, when it was used, and when it expired.
A starting checklist
- Move every long-lived key out of
.envfiles and into a secrets manager. - Create a dedicated, scoped credential for agent sessions.
- Turn on secret scanning and push protection for your repositories.
- Keep production credentials out of agent sessions by default.
- Review diffs before commits, and require approval for high-risk commands.
- Rotate any key an agent session may have seen.
We list eight related controls for terminal-based coding in our article on AI-assisted coding in the terminal. The ones above are the part that concerns secrets, and each rests on a public source.
