Skip to content

codex-project-instructions

Diagnose Codex instruction selection and the cumulative project byte limit

Severity warning (disabled)
Autofix -
Since v0.23.0
Repo Types agents-md, codex-project
Category OpenAI Codex

Why

OpenAI Codex reads instruction files such as AGENTS.md to learn how to work in your repository. These files can live at the project root and in subdirectories. Codex combines the files that apply to your working directory.

Codex limits their combined size to 32 KiB by default. If they exceed that limit, some instructions are left out, even though each file may seem small enough on its own. Guidance you wrote in a child directory may never reach Codex.

This rule checks which files Codex would select for the project root and working directory you specify. It then checks their combined byte usage and warns when the limit would cut off a file or leave later files out entirely. The rule is disabled by default; enable it when you want to check Codex's project instructions.

For example, these two files exceed the default budget together:

Selected file File size Bytes loaded Bytes lost
AGENTS.md 18 KiB 18 KiB 0
services/payments/AGENTS.md 18 KiB 14 KiB 4 KiB

The existing context-budget rule still checks estimated tokens per file.

Inspect a working directory

Pass the project root as the path and the working directory relative to it:

skillsaw tree /path/to/repo --codex-instructions --cwd services/payments

The report shows the selected files in loading order, how many bytes each uses, and the running total. Truncated or omitted lists files that lose content. It also shows where the settings came from and what skillsaw assumed. Add --format json for machine-readable output.

The report keeps the working directory you requested (requested_cwd) separate from its resolved absolute path (cwd). If the requested directory is missing, outside the root, or is a file, JSON cwd is null and the report is incomplete.

An Incomplete result means skillsaw could not inspect part of the chain. Check the reported paths, permissions, and exclusions before relying on the byte count. skillsaw does not skip an inaccessible override and assume Codex will use another file.

How to fix

Shorten the selected instruction files, or raise project_doc_max_bytes in the Codex configuration you use. Moving text between selected files does not help: they still share the budget. There is no autofix.

Enable the check in CI

Add the working directory and enable the rule in .skillsaw.yaml:

codex-instructions:
  cwd: services/payments
rules:
  codex-project-instructions:
    enabled: true
    severity: warning

Then run:

skillsaw lint /path/to/repo --strict

--strict makes warnings fail CI; --fail-on warning also works. The tree command is for inspection: it exits 0 when it can compute the result, even if instructions are cut off, and 1 when the result is incomplete.

Which settings skillsaw uses

skillsaw starts with the Codex defaults: 32,768 bytes and no fallback filenames. It reads project_doc_max_bytes and project_doc_fallback_filenames from .codex/config.toml files between the supplied root and working directory. For each setting, the nearest file wins. A fallback list replaces the earlier list rather than extending it.

Byte limits must be non-negative integers no larger than 9,223,372,036,854,775,807, the maximum accepted by Codex's TOML parser. For both instruction settings, skillsaw also checks integers nested in arrays or tables before merging values. An integer outside the signed 64-bit range makes the config unreadable to Codex, even if a later setting overrides it; skillsaw reports that analysis as incomplete. This check does not validate unrelated Codex settings.

To supply values from a global config, profile, or CLI flag, set them explicitly in .skillsaw.yaml. These values take priority for both tree and lint:

codex-instructions:
  cwd: services/payments
  project_doc_max_bytes: 65536
  project_doc_fallback_filenames: [TEAM_GUIDE.md, .agents.md]

These settings tell skillsaw what to check. They do not change Codex's configuration. skillsaw never reads global, managed, profile, or CLI settings.

Setting Special values
cwd Omitted or null means the supplied root. tree --cwd overrides it.
project_doc_max_bytes Omitted or null uses project config, then the default. 0 means no project instructions load.
project_doc_fallback_filenames Omitted or null uses project config, then the default. [] disables fallbacks.

Which files Codex selects

Codex visits each directory from the root to the working directory, including both ends. It selects at most one file per directory, in this order:

  1. AGENTS.override.md
  2. AGENTS.md
  3. The first existing file in the configured fallback list

For services/payments, the directories are the root, services, and services/payments. Siblings and deeper directories do not contribute. The final fallback list applies to every directory on this path.

An empty override still wins. Codex selects the file before reading it. If that file is empty or contains only whitespace, Codex does not try the standard file or a fallback. A directory with a candidate filename is skipped.

Fallback names are trimmed and duplicates removed. Entries must be filenames: skillsaw ignores ., .., and names containing / or NUL; on Windows it also ignores names containing \ or :. Symlinks are supported within the allowed scope. If two selected paths point to the same file, its bytes count twice.

How bytes are counted

Codex reads each selected file using the budget left by earlier files. Once the budget reaches zero, it stops loading files. The report still lists those later selections as omitted, including when the configured limit is zero. The byte report gets full file sizes from metadata and reads only the part that fits in the remaining budget. It processes those bytes in fixed-size chunks, so raising the limit does not require holding the selected text in memory. Reading time still grows with the number of bytes inspected.

  • Count bytes before decoding. Codex cuts the raw bytes to fit the remaining budget, then decodes UTF-8. Invalid or cut-off characters become replacement characters. A byte-order mark (BOM) and CRLF line endings count toward the limit.
  • Whitespace-only content is skipped. If the part read is empty or contains only Unicode whitespace, Codex drops it without spending any bytes. The empty status describes that part; truncated: true can still mean a suffix was lost.
  • Added text is separate. The two newlines (\n\n) between included files and any extra bytes from UTF-8 replacement characters do not count toward the limit. The final rendered project text can therefore exceed it. Global, user, and thread instructions and prompt wrappers are also outside this budget.

The report distinguishes file size, bytes read, bytes counted against the budget (charged_bytes), the running total (cumulative_bytes), and the size of the rendered project text.

Assumptions and limits

This check assumes one trusted local project. Codex 0.162.1 skips project instructions for an untrusted project. skillsaw does not inspect that trust decision or observe a running Codex session. JSON complete: true means the calculation succeeded under the report's assumptions.

Full Codex configuration validation is outside this check. One known parsing difference is an overflowing float literal such as 1e400: Codex rejects it, while skillsaw can report a complete result if a later setting replaces it. complete: true therefore does not guarantee that Codex will accept the configuration.

You choose the root. skillsaw does not search parent directories for root markers. Without a root marker, Codex normally uses only the working directory; pass that directory as skillsaw's root to check this case. A nested Git repository may need its own root. Remote execution and shared budgets across multiple environments are not modeled.

skillsaw respects excluded directories and lint-external-content: false. Excluded, unreadable, unresolved, or out-of-root instruction or config paths make the result incomplete. An exclusion for a file that does not exist has no effect on selection. Excluding the working directory still produces a finding at the supplied root, even if it contains no instruction files. Global and user instruction files are never read.

Standard content checks recognize AGENTS.override.md. They discover custom fallbacks when this analysis is requested. A selected fallback matched by content-paths receives the instruction role and its per-file token budget. The instruction-file-valid rule checks override and fallback prose for empty content and read failures; Codex's lossy decoding and byte accounting still apply independently. An override loaded as a plugin agent, command, rule, or configured OpenCode instruction keeps that role and its existing checks. Its full file bytes still count if Codex selects it. The content checks also apply when a plugin's README.md shares a file with an override through a symlink, or is selected as a fallback. Known configuration files keep their configuration checks even when named as fallbacks. Other hosts' files count toward the Codex budget only if explicitly configured as fallbacks.

An explicit working directory can reach instructions inside directories such as vendor/ that the ordinary repository scan skips. Those selected files also count as repository-type evidence, so rules configured with enabled: auto can run. skillsaw explain uses the same configured working directory when showing whether a rule is enabled. Explicit exclusions and the external-content policy still apply.

Selected .codex/ layers also receive the existing hook checks for both hooks.json and inline hooks in config.toml. Hook discovery does not change which instruction files count toward the byte limit.

Sources

The selection and byte rules were verified against the released Codex 0.162.1 loader, its configuration code, and local codex debug prompt-input checks. The official guide explains the default limit and file precedence.

Configuration

rules:
  codex-project-instructions:
    enabled: false  # true | false | auto
    severity: warning

Run skillsaw explain codex-project-instructions to see this documentation and the rule's effective configuration in your terminal.