AI Agent Permissions: How to Stop Your Coding Agent From Breaking Production
Table of Contents
ToggleAI coding agents can do much more than autocomplete a function. Give an agent access to a repository, and it can inspect files, edit code, run tests, install dependencies, execute shell commands, call services, and prepare changes for review. That capability is useful until the agent has access to something it should never have touched.
This is where AI agent permissions become an engineering problem. The goal is not to make an agent harmless by removing every useful capability. The goal is to give it enough access to finish its job while keeping sensitive files, credentials, production systems, and irreversible actions behind explicit boundaries.
If you have been following Ediccrew’s discussion of AI coding agents, this is the next layer to understand. AI tools are creating developers who can’t debug, which shows why human verification still matters. Permissions add another control: even when the model makes a bad decision, the environment should limit the damage.
What AI Agent Permissions Actually Control
An AI agent does not operate in a vacuum. It interacts with an execution environment through tools. Those tools might include a filesystem API, terminal, package manager, browser, database client, Git commands, cloud CLI, or custom MCP server.
Every tool creates a permission question.
Can the agent read this file? Can it modify it? Can it execute this command? Can it reach this host? Can it use this credential? Can it deploy the resulting change?
A useful permission model separates read, write, execute, and external access. Each has a different risk profile.
Treating these as one permission called “coding” is the mistake. Reading a repository is not equivalent to executing commands, and running a unit test is not equivalent to accessing a production database.
The OWASP AI Agent Security Cheat Sheet covers related risks including excessive agency, tool abuse, prompt injection, and privilege escalation. An agent can be manipulated by untrusted content, so permissions need to constrain what happens after the model makes a decision.
AI Agent Permissions Should Follow the Task
The cleanest rule is simple: grant the minimum access required for the current task.
Suppose an agent is asked to fix a Python function and add tests. It probably needs read and write access to the project directory. It needs permission to run the project’s test command. It may need network access to install a missing package.
It probably does not need:
- Your SSH private keys
- Cloud provider credentials
- Production database credentials
- Access to your entire home directory
- Permission to modify system configuration
- Permission to deploy
- Unrestricted outbound network access
This is the principle of least privilege applied to agentic development.
The practical difference is enormous. If an agent receives a malicious instruction from a repository file and tries to read a secret outside the project directory, a filesystem boundary can stop the attempt before the model’s reasoning matters.
The same idea applies to shell commands. Rather than assuming that a command is safe because the agent generated it, treat execution as a separate capability with its own controls.
A permission policy might look conceptually like this:
Project source:
read/write
Tests:
execute
Package installation:
allowed
Local network:
restricted
Secrets directory:
denied
Production database:
denied
Deployment command:
approval required
Coding Agent Security Starts With Isolation
Permissions are stronger when the agent operates inside a sandbox.
A sandbox gives the agent a bounded environment. It can modify a working copy, execute builds, and run tests without unrestricted host access.
GitHub’s documentation on coding-agent sandboxes describes this kind of separation between an agent and the surrounding system. The exact implementation varies, but the security principle is consistent: isolate the workspace and explicitly control capabilities such as filesystem and network access.
For local development, isolation can mean a container or virtual machine. A hosted coding agent may use an ephemeral environment. If that workspace disappears after the task, temporary credentials can expire and generated files can be discarded.
A simple Docker-based pattern illustrates the idea:
docker run --rm \
--network none \
--read-only \
--tmpfs /tmp \
-v "$PWD":/workspace \
-w /workspace \
coding-agent-sandbox
Real projects may need package downloads, compilers, caches, or service containers. Add those requirements deliberately instead of starting with unrestricted access.

The Filesystem Is a Permission Boundary
Many developers focus on shell access because commands look dangerous. The filesystem deserves the same attention.
An agent that can read every directory available to your operating-system user can potentially discover configuration files, credentials, SSH keys, cloud credentials, source repositories, and personal documents.
The safer pattern is to expose a narrow workspace.
For example:
/workspace
src/
tests/
pyproject.toml
README.md
/secret
denied
/home/developer/.ssh
denied
/home/developer/.aws
denied
The agent should normally read and write /workspace, while everything outside that boundary remains unavailable.
Also distinguish read-only from writable paths. Documentation and caches may only need read access, while source files need write access. Deployment configuration may need review before modification. If an agent cannot access a directory, decide whether that missing permission is actually necessary.
Shell Access Is Where Things Get Interesting
A coding agent with terminal access has enormous power.
It can run tests, inspect Git history, create files, invoke compilers, and automate repetitive work. It can also execute destructive commands.
Shell access does not always need to be disabled. It needs boundaries. Start by separating commands into risk levels.
Low-risk examples might include:
pytest
python -m compileall src
git diff
git status
Higher-risk examples include:
rm -rf
chmod
chown
sudo
curl ... | sh
git push --force
terraform apply
kubectl delete
A denylist alone is weak because there are many ways to achieve the same outcome. Blocking rm -rf does not prevent an agent from writing a Python script that deletes files.
The stronger design is environmental. Give the agent a disposable workspace, run it as a non-root user, restrict mounted directories, limit network access, and require approval for operations that affect external systems.
This is also why OpenAI’s guidance on running Codex safely emphasises sandboxing, approvals, network policies, and telemetry rather than relying on the model to behave perfectly.
Network Access Should Be Treated as a Capability
Network access changes the threat model.
Without network access, an agent can still damage its local environment, but its ability to exfiltrate data or interact with external services is reduced.
With unrestricted network access, a compromised workflow can potentially send sensitive information outside the environment, download untrusted software, interact with APIs, or reach services that were never intended to be part of the task.
Do not assume the answer is “no network ever.” Define what the task needs.
A frontend build may need access to an npm registry. A Python project may need PyPI. A test suite may need a local database. A deployment task may require a cloud API.
Expose those destinations deliberately.
Conceptually:
Allowed:
package-registry.example
internal-test-db.example
Denied:
arbitrary internet destinations
production-admin.example
metadata service
Network controls are especially valuable when combined with filesystem isolation. One boundary limits what the agent can read. Another limits where it can send data.
Never Hand the Agent More Secrets Than It Needs
Secrets deserve their own policy.
Do not solve authentication by dumping every environment variable into the agent’s process. That makes debugging convenient and security painful.
Instead, use short-lived credentials scoped to a specific operation.
For example, a test agent might receive a token that can access a disposable test API but cannot create users, change billing information, or deploy infrastructure.
A deployment agent may require a separate workflow entirely. The agent can prepare a deployment plan, but a human or CI policy can decide whether the plan is executed.
This creates a useful separation:
Agent:
inspect -> modify -> test -> propose
Control layer:
validate -> approve -> deploy
The agent does not need unrestricted production authority simply because it can prepare the change.
AI Agent Permissions Must Survive Prompt Injection
Agents also consume untrusted text.
A repository README can contain instructions. An issue can contain instructions. A web page can contain instructions. A generated log can contain instructions.
The model may interpret those instructions as part of the task. That is prompt injection.
Do not rely only on telling the model to “ignore malicious instructions.” Make dangerous actions impossible or approval-gated at the environment level.
Imagine a repository contains a malicious instruction telling the agent to search the user’s home directory for credentials.
If the agent has no access to that directory, the instruction has nowhere to go.
That is the central security principle:
Do not rely on the model to enforce a boundary that the operating environment can enforce instead.
This is why MCP and tool access deserve careful attention. Every additional tool expands what an agent can do. Tool design should therefore expose narrow operations rather than unrestricted general-purpose access whenever possible.
Use Approval Gates for Irreversible Actions
Not every action needs a human prompt. If approval appears before every test command, developers will eventually disable it. Approval should appear where consequences change.
Good candidates include:
- Production deployments
- Destructive database operations
- Infrastructure changes
- Permission changes
- Sending external communications
- Publishing packages
- Accessing sensitive credentials
- Force-pushing protected branches
A useful approval message should explain the action, target, and consequence.
Bad:
Allow command? [y/n]
Better:
Production deployment requested.
Target: api-prod
Changes: 14 files
Migration: 1 database migration
Rollback: available
Approve deployment? [y/n]
The human is deciding whether a high-impact transition should happen.
Build a Permission Matrix Before You Build the Agent
Before giving an agent more capabilities, write down the task and its required tools.
| Task | Files | Shell | Network | Secrets | Production |
| Explain code | Read | No | No | No | No |
| Fix bug | Read/Write | Tests | Limited | No | No |
| Upgrade dependency | Read/Write | Package manager | Registry | No | No |
| Prepare release | Read/Write | Build tools | Limited | Scoped | No |
| Deploy | Read | CI/deploy tool | Specific | Scoped | Approval |
This matrix exposes unnecessary permissions quickly and gives you something to test.
For each task, verify that allowed actions work and denied actions fail. Security controls that exist only in documentation are not controls.
A useful test intentionally attempts to access a forbidden file:
from pathlib import Path
forbidden = Path("/home/developer/.ssh/id_rsa")
try: forbidden.read_text()
raise
RuntimeError("Permission boundary failed")
except PermissionError:
print("Boundary enforced")
The mechanism depends on your sandbox and agent platform. Test the boundary from inside the environment.
Monitor the Agent Instead of Trusting It
A secure agent workflow should leave evidence.
Record tool calls, command execution, approvals, denied actions, network requests, and significant file changes where practical.
Logs answer questions that prompts cannot. What did the agent try to do? Which tool did it call? What was denied? Who approved the production change?
Telemetry also helps refine permissions. If an agent repeatedly requests a capability that turns out to be unnecessary, tighten the policy. If a legitimate workflow is constantly blocked, identify the smallest additional permission required.
This makes security an iterative engineering process rather than a one-time configuration.
A Practical Secure Workflow
A useful coding-agent workflow can be reduced to five stages:
1. Define task
|
2. Create isolated workspace
|
3. Grant task-specific permissions
|
4. Agent edits and tests
|
5. Human or CI approves high-impact changes
The agent gets enough freedom to work. The sandbox limits its reach. Tests catch defects. Approval gates protect high-impact operations.

The Production Rule Is Simple
AI agent permissions should make the safe path easy and the dangerous path difficult.
Give the agent its workspace. Give it the tools required by the task. Keep secrets outside its reach unless they are genuinely necessary. Restrict network destinations. Run risky work in disposable environments. Require approval when an action crosses into production or creates an irreversible consequence.
Most importantly, separate intelligence from authority.
The model can decide that a deployment appears necessary. It does not have to possess unrestricted authority to perform that deployment.
That distinction becomes more important as coding agents become more autonomous. Faster agents are useful because they can take more actions with less supervision. Those same capabilities increase the cost of a bad decision.
The answer is not to stop using agents. It is to design the environment around them properly.
If you are building an agentic development workflow, start with the smallest permission set that can complete one real task. Measure what it needs. Add access deliberately. Test every boundary. Then expand.
Your coding agent should be powerful inside its box.
Production should remain outside it.
Discover more from ediccrew
Subscribe to get the latest posts sent to your email.





The part about network access being a capability really stood out. A coding agent doesn’t necessarily need the whole internet just because it needs to install one package.