Claude Code and Codex are agentic tools: they read the repository, edit files and run commands on their own instead of completing a single line. To make an agent helpful rather than harmful you need three things: a project instruction file (AGENTS.md or CLAUDE.md) with commands and restrictions, permissions and a sandbox that technically limit what it can do, and a task with verifiable acceptance criteria. The agent's output goes through the same tests and review as human code.
After this you will be able to
- write an
AGENTS.mdinstruction file for your project and load it in Claude Code throughCLAUDE.md - configure Claude Code permissions in
.claude/settings.jsonand the Codex sandbox in.codex/config.toml, then check them withdoctor - give an agent a task with context, acceptance criteria and a verification command
- review an agent's changes with a checklist: diff scope, tests, secrets, dependencies and licenses
Know beforehand
Verified with
Claude Code 2.1.296Codex CLI 0.162.1markdownlint-cli2 0.23.3Node.js 24 LTS (24.18)
Checked against docs: October 12, 2026
Contents
An agent, not autocomplete
Autocomplete suggests the next line in your editor, and a person decides at every step. An agentic tool takes the whole task: it finds the relevant files, plans, edits several files, runs tests and terminal commands, reads the errors and fixes them. That is how Claude Code from Anthropic and Codex from OpenAI work — in the terminal, in IDE extensions, in desktop apps and in the cloud.
The cost of a mistake grows with the capabilities. A bad autocomplete suggestion is one line you can see. An agent can change twenty files, install a package, run a migration or read a file with keys. So working with an agent rests on three pillars: project instructions, technical limits and a verifiable result.
Autocomplete
- A suggestion in the current file
- A person accepts every line
- Does not run commands
- Context is the open file and its neighbours
Agent: Claude Code, Codex
- A whole task across several files
- Acts on its own within its permissions
- Runs tests, builds, git and other tools
- Finds the context it needs in the repository
Installation and first run
Both tools install with a single command. For Claude Code the documentation recommends the native installer; Homebrew, WinGet and an npm package are also available, and the npm package needs Node.js 22 or later. Codex CLI installs with a standalone installer from chatgpt.com, via npm or Homebrew. You also need an account: on first launch Claude Code asks you to sign in with a Claude subscription or an Anthropic Console account, and Codex with ChatGPT or another available sign-in method.
# Claude Code: native installer (macOS, Linux, WSL)
curl -fsSL https://claude.ai/install.sh | bash
# Codex CLI: standalone installer (macOS, Linux)
curl -fsSL https://chatgpt.com/codex/install.sh | sh
# Alternative for both: global npm packages
npm install -g @anthropic-ai/claude-code
npm install -g @openai/codex$ claude --version
2.1.296 (Claude Code)
$ codex --version
codex-cli 0.162.1Start the agent from the repository root with claude or codex. The working directory determines both which instruction files it reads and the boundary within which it may write. Before a task, commit the current state or create a branch: the Codex documentation recommends Git checkpoints before and after a task so you can revert the changes.
Instruction files: AGENTS.md and CLAUDE.md
Every agent session starts with a clean context. What you would otherwise explain every time goes into a project instruction file. Codex reads AGENTS.md: first the global one in ~/.codex, then the files from the project root down to the current directory; the one closest to the working directory is read last and refines the general rules. The combined size is capped at 32 KiB by default (project_doc_max_bytes). AGENTS.md is an open format that other agents support too; it is described at agents.md.
Claude Code reads CLAUDE.md in the project, ~/.claude/CLAUDE.md with personal rules and CLAUDE.local.md with settings that stay out of git. If a project has only AGENTS.md, recent Claude Code versions read it directly, but when a CLAUDE.md exists, they read only that. A reliable way to keep one source of rules for both tools is a shared AGENTS.md plus a short CLAUDE.md that imports it with an @AGENTS.md line. You can get a first draft with /init: Claude Code analyses the project and proposes commands and conventions.
Build, test and lint commands the agent cannot guess
- Leave out
- Anything the agent can learn by reading the code
Code rules that differ from common conventions
- Leave out
- Generic advice like “write clean code”
Where things live and the project's architectural decisions
- Leave out
- A description of every file
Restrictions: secrets, applied migrations, deployment, git push
- Leave out
- Detailed API documentation — link to it instead
The definition of done
- Leave out
- Information that changes often
# AGENTS.md
## Project
- Online booking for a beauty salon: Next.js (App Router), TypeScript,
PostgreSQL via Prisma.
- Application code is in `src/`, tests are in `tests/`,
migrations are in `prisma/migrations/`.
## Commands
- Install dependencies: `npm ci`
- Type check: `npm run typecheck`
- Lint: `npm run lint`
- All tests: `npm test`
- One test file: `npm test -- tests/bookings.test.ts`
## Conventions
- TypeScript strict mode; no `any` in new code.
- Validate every external input with `zod` at the boundary
(`src/schemas/`).
- Database access only through `src/db/`;
never build SQL by string concatenation.
- New UI strings go to both `messages/ru.json` and `messages/en.json`.
## Workflow
- For changes that touch more than one file, propose a plan first
and wait for confirmation.
- After changes, run type check, lint and the related tests,
and show the output.
- Keep the diff limited to the task: no unrelated refactoring or reformatting.
- Ask before adding a production dependency.
## Security
- Never read, print or commit `.env` files, keys or tokens.
If a new variable is needed, name it in the summary
and leave the value to a human.
- Do not edit applied migrations in `prisma/migrations/`;
create a new migration instead.
- Never run `git push`, deployments or commands
against production databases.
## Definition of done
- Type check, lint and tests pass.
- New behavior is covered by a test.
- The summary lists what changed, how it was verified
and what is still uncertain.markdownlint-cli2# CLAUDE.md
@AGENTS.md
## Claude Code
- Use plan mode for any change under `src/payments/`.
- Before reporting a task as done, review the diff
against the acceptance criteria of the task.CLAUDE.md imports the shared rules and adds what applies to Claude Code onlyKeep the file short. The Claude Code documentation recommends under 200 lines per file and asking of every line whether the agent would make a mistake without it: a long file consumes context, and important rules get lost in it. A good reason to add a line is the agent repeating the same mistake twice, or a review catching something it should have known. Rules for only part of the code go into a nested AGENTS.md (Codex) or into .claude/rules/ scoped to paths (Claude Code).
Permissions and sandboxing
This is where the real boundary is. A Claude Code permission mode defines what the agent does without asking. Since version 2.1.283, interactive sessions in the terminal and VS Code start in auto mode by default: a separate classifier model reviews actions and blocks risky ones. You change the mode with the --permission-mode flag, with Shift+Tab in a session or with the permissions.defaultMode setting.
plan
- What it does without asking
- Reads files and runs read-only commands
- When it fits
- Exploration, unfamiliar code, a plan before changes
manual (default in settings)
- What it does without asking
- Reads only; edits and commands need approval
- When it fits
- Sensitive repositories, first sessions
acceptEdits
- What it does without asking
- Edits files and runs simple file commands in the working directory
- When it fits
- A clear task, you review the diff at the end
auto
- What it does without asking
- A classifier reviews actions and blocks risky ones
- When it fits
- Long tasks with configured rules
dontAsk
- What it does without asking
- Only what is pre-approved; everything else is silently denied
- When it fits
- Scripts and CI with a narrow set of commands
bypassPermissions
- What it does without asking
- Everything except the few actions no mode approves
- When it fits
- Only a container or VM where the agent cannot break anything
On top of the mode, allow, ask and deny rules in .claude/settings.json apply. They are evaluated deny first, then ask, then allow: a broad deny cannot be bypassed by a narrower allow, and deny rules hold in every mode. Commit the project file so the whole team gets the rules; personal exceptions go into .claude/settings.local.json.
{
"$schema": "https://json.schemastore.org/claude-code-settings.json",
"permissions": {
"allow": [
"Bash(npm run typecheck)",
"Bash(npm run lint)",
"Bash(npm test *)"
],
"ask": [
"Bash(git push *)",
"Bash(npm install *)"
],
"deny": [
"Read(./.env)",
"Read(./.env.*)",
"Read(./secrets/**)",
"Bash(npx prisma migrate deploy *)"
],
"disableBypassPermissionsMode": "disable"
}
}git push and package installs need approval, secrets and production migrations are denied. disableBypassPermissionsMode turns off the no-checks modeAn important caveat from the documentation: Read and Bash rules are not an absolute guarantee. A Read(./.env) deny applies to the built-in tools and recognised commands such as cat, but not to a Node.js or Python script that opens the file itself; a Bash(curl *) rule does not stop sh -c 'curl …'. OS-level enforcement comes from the sandbox (/sandbox), and the most reliable option is not to keep production secrets in the working copy at all.
Codex separates two layers. The sandbox_mode defines what the agent can technically do: read-only, workspace-write or danger-full-access. The approval_policy defines when it must ask: on-request or never. In the Auto preset (workspace-write with on-request) Codex writes only inside the working directory, network access for commands is off, .git and .codex are write-protected, and it asks before going beyond those limits. The --dangerously-bypass-approvals-and-sandbox flag (alias --yolo) turns off both the sandbox and the prompts — the documentation reserves it for externally isolated environments.
# Project config: Codex loads it only after you mark the project as trusted
sandbox_mode = "workspace-write"
approval_policy = "on-request"
[sandbox_workspace_write]
network_access = false~/.codex/config.tomlMake sure the settings are understood the way you intended. Both tools have a doctor command that parses the configuration without starting a session or calling a model.
$ codex doctor
✓ config loaded
config.toml parse ok
✓ sandbox restricted fs + restricted network · approval OnRequest
$ claude doctor
Invalid settings
- .claude/settings.json › permissions.defaultMode: Invalid value. Expected one of: "acceptEdits", "auto", "bypassPermissions", "default", "dontAsk", "plan"settings.json there is no Invalid settings sectionHow to write a task
An agent stops when the work “looks done”. If the task has no check the agent can run itself, you become the check. A good task answers four questions: where to look (files, modules, the related issue), what the result is (behaviour, not “improve it”), how to verify it (a test, a command, an expected response) and what not to touch.
# Task: limit booking attempts per phone number
## Context
- The booking handler is `src/app/api/bookings/route.ts`.
- A rate limit helper already exists in `src/lib/rate-limit.ts`; reuse it.
- Tests for bookings are in `tests/bookings.test.ts`.
## Goal
Reject more than 3 booking requests from the same phone number
within 10 minutes.
## Acceptance criteria
- [ ] The 4th request for the same phone within 10 minutes returns HTTP 429
with the body `{ "error": "too_many_requests" }`.
- [ ] Requests for other phone numbers are not affected.
- [ ] The limit resets after 10 minutes; the test uses fake timers,
not real waiting.
- [ ] No new dependencies and no changes outside `src/app/api/bookings/`,
`src/lib/` and `tests/`.
## Verification
Run `npm run typecheck`, `npm run lint`
and `npm test -- tests/bookings.test.ts`, then show the output.
## Out of scope
- UI changes.
- Database schema changes.
## How to work
1. Read the files above and propose a plan. Wait for my confirmation.
2. Write a failing test first, then the implementation.
3. Summarize the diff and list anything you were unsure about.- Write criteria as verifiable facts — a status code, a body, an edge case — not “works correctly”.
- Name existing code to reuse, otherwise the agent may write its own copy.
- Limit the scope: a list of folders and an “out of scope” section protect against drive-by refactoring.
- Ask to see the output of the checks rather than the phrase “tests pass”: reviewing output is faster.
- One session, one task. The Claude Code documentation recommends clearing the context with
/clearbetween unrelated tasks and, after two failed corrections, starting over with a better initial prompt.
The workflow: plan → changes → tests → review
Plan
Switch to
planmode in Claude Code or toread-onlyin Codex (the/permissionscommand). The agent reads the code and proposes which files to change. Fix the plan before any code appears: redoing a plan is cheaper than redoing a diff. An edit you can describe in one sentence does not need a plan.Changes
Switch to a working mode and ask for the plan to be implemented, starting with a failing test. Work on a separate branch and keep parallel tasks in separate worktrees.
Tests
The agent runs the type check, linter and tests from
AGENTS.mdand fixes errors until the checks pass. Require it to fix the cause, not to disable the check or the test.Review
Automated first: in Codex,
/reviewchecks uncommitted changes or a branch against its base; in Claude Code, the built-in/code-reviewor a subagent compares the diff with the task's criteria. Then your own review with the checklist below.Pull request
An agent's changes take the same path as human code: a pull request, CI, a colleague's review, a protected branch.
Reviewing agent code and where not to trust it
Generated code looks confident whether or not it is correct. Read the whole diff, not just the agent's final summary: the summary describes the intent, the diff shows the result.
- The diff is limited to the task: no edits to unrelated files, no drive-by formatting, no deleted tests
- Tests check the behaviour from the criteria rather than mirroring the implementation; no skipped or weakened assertions
- Checks were run, their output is shown, CI is green
- No secrets in code, logs, test data or commit messages
- New dependencies are really needed, exist under that exact name, are maintained, and their license is compatible with the project
- External input is validated, SQL is parameterised, HTML output is escaped, permissions are checked on the server
- New migrations do not change already applied files
- Errors are not silently swallowed
Security: sign-in, permissions, payments, cryptography
- Risk
- Plausible code with a hole: permission checks only on the client, home-made hashing
- What to do
- Review by someone who knows the area, tests for the failure cases, a check against OWASP
Secrets
- Risk
- A key in a prompt, a log or a test file; the agent read
.env - What to do
- Read denies, secrets outside the working copy, a secret scanner in CI
Licenses and dependencies
- Risk
- A package with an incompatible license or a look-alike name owned by someone else
- What to do
- Check the registry, repository and license of every new package
Untrusted content
- Risk
- Instructions in a README, an issue or a web page change the agent's behaviour — prompt injection
- What to do
- Do not give the agent broad permissions while it handles third-party content; network by allowlist
Architecture and an unfamiliar domain
- Risk
- A locally reasonable solution contradicts how the system works or the business rules
- What to do
- A person makes the decision; the agent implements and explores
With architecture and an unfamiliar domain the problem is not syntax but missing context: the agent does not know agreements that are not in the code and will not ask about them unless you tell it to. If you cannot assess the result yourself, the agent does not take the responsibility for checking it off your hands. The Claude Code documentation puts it bluntly: if you cannot verify it, do not ship it.
How this was verified4 · passed1 · not runchecked 12 October 2026
“Run” means the code was executed in a scratch project or container and the output in the article comes from that run. “Partial” means it was checked against stubs instead of external services. “Not run” means it needs a device, an account or a key; the steps were checked against the official documentation. The verification project files and run logs are kept in the InterLAB archive.