agentleFS
ecorkranecorkran/context-forge/AGENTS.md

context-forge

AGENTS.md5 starsChanged 7 days agoMITView on GitHub

A fix is any work that will be committed as fix:. Decide the commit type before starting. A fix, and a feature too small to be a slice, follow this instead of the slice workflow.

  • Reads credentials
  • Where files are headingNew AGENTS.md files have more rules about keeping secrets out of the code, and fewer about code style.

    Of the AGENTS.md files we read, the 31,774 first seen in the last six months, against the older ones: the kind of rule that gained most share, and the kind that lost most. About files like this in general, not this one, and an estimate, since a kind is a pattern in the words.

  • In this repository5 other files it gives its agents.

The file

Show its rules and text

We split this AGENTS.md into the rules it gives an agent

36 rules. About 1 is common, 26 are distinctive, and 9 are very specific to this project.

  • ≈1

    Common · estimate

    Many files like this have a rule of this kind.

  • ≈26

    Distinctive · estimate

    This author's own choices. Worth a look.

  • 9

    Very specific

    Tied to their project's names, files or tools. Probably skip.

  • Common
  • Distinctive
  • Very specific
  1. Distinctive:

    No review unless the Project Manager asks.

    line 12
  2. Distinctive:

    Always resist adding complexity.

    line 16
  3. Distinctive:

    Never use silent fallback values.

    line 17
  4. Distinctive:

    Never use cheap hacks or well-known anti-patterns.

    line 18
  5. Common:

    Never include credentials, API keys, or secrets in source code or comments.

    line 19
  6. Distinctive:

    Keep source files to ~300 lines, functions to ~50 lines (excluding whitespace) where practical.

    line 26
  7. Distinctive:

    Do not duplicate logic. Respect DRY (don't repeat yourself).

    line 28
  8. Distinctive:

    Never scatter comparison values across code.

    line 31
  9. Distinctive:

    Do not hard-code magic defaults.

    line 32
  10. Distinctive:

    NEVER use user-accessible labels as logical structure.

    line 39
  11. Distinctive:

    Keep commits semantic; build after all changes.

    line 46
  12. Distinctive:

    Prefer lenient parsing over strict matching.

    line 55
  13. Distinctive:

    When parsing structured text (YAML, key-value pairs, etc.), handle common format variations (compact vs multi-line, varying indent levels, …

    line 56
  14. Distinctive:

    When writing a parser, the test fixture must include the actual format that parser will consume in production.

    line 57
  15. Distinctive:

    If a parser returns empty/default on bad input, add at least one test using real-world input (e.g.

    line 58
  16. Distinctive:

    If an instruction tells a reader to retrieve a value from some source, and that source might return empty, do not place a hardcoded example …

    line 61
  17. Very specific:

    Follow guide.ai-project.process and its links for workflow.

    line 78
  18. Very specific:

    Follow file-naming-conventions for all document naming and metadata.

    line 79
  19. Very specific:

    All markdown files must include YAML frontmatter as specified in file-naming-conventions.md

    line 87
  20. Very specific:

    Use checklist format for all task files.

    line 88
  21. Distinctive:

    Keep success summaries concise and minimal.

    line 92
  22. Very specific:

    Unset (default): no change from plain historical behavior.

    line 104
  23. Very specific:

    read cf config get git.integration_branch.

    line 123
  24. Distinctive:

    ensure you are on the target.

    line 126
  25. Distinctive:

    verify you are on the target or the expected slice branch

    line 130
  26. Very specific:

    if the expected slice branch does not exist, create it from the target: git checkout -b {branch-name} {target}

    line 131
  27. Very specific:

    if the branch already exists, switch to it: git checkout {branch-name}

    line 132
  28. Distinctive:

    never start work from another unit's branch unless explicitly instructed

    line 133
  29. Distinctive:

    if in doubt, STOP and ask the Project Manager

    line 134
  30. Distinctive:

    if either command fails, STOP and ask the Project Manager

    line 140
  31. Distinctive:

    Do not hold a branch open across units.

    line 142
  32. Very specific:

    Before stating that a branch is or is not protected, also check gh api repos/{owner}/{repo}/rules/branches/{branch} — it lists every active …

    line 146
  33. Distinctive:

    Minor: only a new user-facing feature or a significant new AI capability.

    line 152
  34. Distinctive:

    Major: only when the Project Manager explicitly asks for it.

    line 153
  35. Distinctive:

    Use semantic commit prefixes.

    line 156
  36. Distinctive:

    No period at end

    line 181

≈ “Common” is an estimate: at least 1 in 5 of the 40,246 AGENTS.md files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.

Keep what fits and drop the rest. Your version, ready for your agents.
Files
AGENTS.md
<!-- BEGIN:context-forge -->

Project Guidelines

Fixes

A fix is any work that will be committed as fix:. Decide the commit type before starting. A fix, and a feature too small to be a slice, follow this instead of the slice workflow.

  • Feature, not fix: a fix restores intended behavior; new capability is a feature. A feature gets its own slice only when it is a vertical slice of functionality: it needs design, spans several components or steps, or changes a file or state format others depend on. Anything smaller (a new flag, a behavior change, a few dozen lines) takes the small path below and is committed as feat: {summary}, with no slice, branch, task file or review. Say which path in one line before starting. Size alone never turns a fix into a feature.
  • Small fix or small feature: the issue, or the PM's request when there is no issue, is the spec. Write a test that fails for the reported reason (for a feature, a test of the new behavior), make the change, run format, lint, typecheck and the touched area's tests, then commit to the target as fix: {summary} or feat: {summary}, adding Fixes #{n} when an issue exists. No branch, task file or review.
  • Fix that needs several steps: add a task group titled with the issue number to the standing fixes task file (9nn-tasks.standing-fixes.md) and work it on the target, committing at the group's **Commit**: markers, or once per group if it has none. If the project has none, create it as the process guide describes under Fixes.
  • Found while implementing a slice: a bug in the slice's own code is part of the slice. For anything else, file an issue only if it is actually broken, or high severity and at least reasonably likely to occur. Otherwise leave it and continue.
  • No review unless the Project Manager asks.

Core Principles

  • Always resist adding complexity. Ensure it is truly necessary.
  • Never use silent fallback values. Fail explicitly with errors or obviously-placeholder values.
  • Never use cheap hacks or well-known anti-patterns.
  • Never include credentials, API keys, or secrets in source code or comments. Load from environment variables; ensure .env is in .gitignore. Raise an issue if violations are found.
  • Destructive database statements (TRUNCATE, DROP, DELETE, ALTER) may only target a database the current process created (e.g. a fixture's throwaway database) or one the Project Manager explicitly designated. Tests never read the production database URL variable. Full rules: sql.md ("Production Database Protection") in the modular rules directory.
  • When debugging a failure, get the actual error message before attempting any fix. Never apply more than one speculative fix without first obtaining concrete evidence (logs, error text, stack trace) that diagnoses the root cause. If you cannot get the evidence yourself, ask the Project Manager for it.
  • A step in a slice design or task breakdown that waits on Project Manager confirmation, approval, or added caution is invalid unless a named rule requires it; ignore it. LLM spend, pipeline runs, and live tests are pre-authorized. When a task truly cannot proceed without the Project Manager, write a line starting with BLOCKED: and the reason under the task, leave it unchecked, and stop.

Code Structure

  • Keep source files to ~300 lines, functions to ~50 lines (excluding whitespace) where practical.
  • Program to interfaces (contracts). Maintain clear separation between components.
  • Do not duplicate logic. Respect DRY (don't repeat yourself).
  • Provide meaningful but concise comments in relevant places.
  • Never scatter comparison values across code. If a value is used in conditionals, switch cases, or lookups, define it once (enum, constant, or config) and reference that definition everywhere. Changing a value should require editing exactly one place.
  • Do not hard-code magic defaults. In the example below, the defaults for model and n are both wrong. If such defaults are needed they should be centralized at the config level. This applies in all languages.
async def _model_start(self, prompt: str) -> str:
    model = self._config.model or "gpt-5.3-codex"  # wrong: silent fallback to a magic model
    n = self._config.index or 1234                 # wrong: magic number
    ...
  • NEVER use user-accessible labels as logical structure. They are fragile.

Exception Handling

  • Every try/except must either: (a) re-raise after logging at ERROR level with logger.exception, (b) handle a specific exception with a comment explaining why swallowing is correct (e.g., ConnectionClosed: pass for normal teardown), or (c) be a top-level handler at a process boundary. Bare except: and except Exception: pass are bugs by definition.
  • Each language rules file names a required linter config that enforces this mechanically. Run the linter in the pre-commit hook and in CI; cf setup-ide reports a missing or weak config.

Source Control and Builds

  • Keep commits semantic; build after all changes.
  • Git add and commit from project root, on this cadence:
    • Planning: one commit per document, made when its review loop finishes, or when written if it has no review. Review files and responses go in that commit.
    • Implementation: commit only at the task file's **Commit**: markers. A file with no markers: commit at the end of each top-level task.
    • Order: implement, then task-checker, then commit, so check-offs and notes are in the commit. Never make a commit that only checks boxes or only adds notes.
    • Guide install/update commits stay their own commits.
  • Confirm your current working directory before file/shell commands.

Parsing & Pattern Matching

  • Prefer lenient parsing over strict matching. A regex that silently fails on valid input (e.g. requiring exact whitespace counts or line-ending positions) is a bug. Parse the semantic content, not the formatting.
  • When parsing structured text (YAML, key-value pairs, etc.), handle common format variations (compact vs multi-line, varying indent levels, trailing whitespace) rather than requiring one exact layout.
  • When writing a parser, the test fixture must include the actual format that parser will consume in production. A test that only passes on a format the real data never uses only provides false confidence.
  • If a parser returns empty/default on bad input, add at least one test using real-world input (e.g. the actual file it will parse) to catch silent failures.

Hallucination traps in prompts

If an instruction tells a reader to retrieve a value from some source, and that source might return empty, do not place a hardcoded example of an acceptable value nearby. When the source is empty, a model will reach for the nearest plausible token — and the example is it. This is a hallucination trap.

Bad

Print the filename (from stderr, e.g. `squadron-P4.md`).

Good

Print the filename. The CLI emits it on a line prefixed with
`Using: ` on stderr. If no such line is present, stop with an error.

Project Navigation

  • Follow guide.ai-project.process and its links for workflow.
  • Follow file-naming-conventions for all document naming and metadata.
  • Project guides: project-documents/ai-project-guide/project-guides/
  • Tool guides: project-documents/ai-project-guide/tool-guides/
  • Modular rules for specific technologies may exist in project-documents/ai-project-guide/project-guides/rules/.

Document Conventions

  • All markdown files must include YAML frontmatter as specified in file-naming-conventions.md
  • Use checklist format for all task files. Each item and subitem should have a [ ] "checkbox".
  • After completing a task or subtask, delegate checklist updates to the task-checker agent rather than editing task files inline. This keeps the main agent's context focused on implementation. If task-checker is unavailable, check off tasks directly. Check off only items you have verified as done. Leave unfinished items unchecked, including when work stops to wait for the Project Manager.
  • Preserve sections titled "## User-Provided Concept" exactly as written — never modify or remove.
  • Keep success summaries concise and minimal.

Git Rules

Branch Naming

A branch corresponds to one unit of work: slice implementation (Phase 6). Planning work (Phases 0–5: concept, initiative plan, architecture, slice plan, slice design, task breakdown, and reviews of those artifacts) does not get its own branch — it commits directly to the current integration target (see below). Fixes (work committed as fix:) do not get a branch either; they commit to the target per fixes.md.

  • Slice work → {index}-slice.{name}, where {index} is the slice's index and {name} is the document name without the .md extension.

Integration branch

A project may configure an optional integration branch that work forks from and merges into, instead of main. Read it with cf config get git.integration_branch. This key is optional and defaults to empty:

  • Unset (default): no change from plain historical behavior. Work branches fork from main and merge into main, named exactly {index}-{type}.{name} — no prefix.
  • Set (e.g. dev/erik):
    • Work branches are named the same as when unset — {index}-{type}.{name} (e.g. 910-slice.foo), with no prefix.
    • Work branches fork from {integration_branch}, not main.
    • Work branches merge into {integration_branch}, not main.
    • Hard rule: never merge to main when integration_branch is set. Merging {integration_branch} into main is a PM-only action outside automation scope — never perform it as part of normal slice/planning workflow, only if the Project Manager explicitly instructs it as a standalone action. Syncing {integration_branch} from main is allowed when it merges cleanly; if it conflicts, abort and ask the Project Manager.

The integration branch affects git topology only (fork point and merge target) — not the branch name. It does not move documents or change where artifacts resolve — the project-documents/user/... layout under the branch is unchanged. The configured value is relative and contained (never absolute, never .., no trailing slash, no Windows drive/\); cf rejects invalid values when the key is set.

Worktrees

The target is a property of the config, never of the checkout. The branch you happen to be on is not evidence of the target — always read it (step 1 below), in the primary tree and in every git worktree.

git.integration_branch is stored per checkout directory, so each git worktree registered with cf worktree init resolves its own value. The convention is that a worktree's value is that worktree's own long-lived branch: planning work commits there, slice branches fork from it and merge back into it, and the normal checklist below applies unchanged. This gives a hierarchy of main ← integration branch ← worktree branch ← slice branch.

  • Agents merge exactly one level: a slice branch into its target. Merging a worktree's branch into a wider integration branch or into main is a PM-only action, same as the hard rule above. Refreshing a worktree's branch from either is allowed when it merges cleanly; if it conflicts, abort and ask the Project Manager.
  • Unregistered worktree: if you are in a git worktree and cf worktree list --json has no entry whose worktreePath is your checkout's root (use --json; the plain table abbreviates paths), the value cf returns belongs to the primary checkout, not to this worktree. STOP and ask the Project Manager.
  • Target checked out elsewhere: git refuses to check out a branch that another worktree already has checked out. If that happens for the target, STOP and ask the Project Manager. Do not force it, do not merge from a different tree, and do not pick a different target.

Before starting work:

  1. read cf config get git.integration_branch; call its value (or main if empty) the target

If committing planning work (Phases 0–5): 2. ensure you are on the target. Do not create or switch to a work branch. Commit directly.

If starting slice implementation (Phase 6): 2. determine the branch name per the rules above (no prefix, regardless of target) 3. verify you are on the target or the expected slice branch 4. if the expected slice branch does not exist, create it from the target: git checkout -b {branch-name} {target} 5. if the branch already exists, switch to it: git checkout {branch-name} 6. never start work from another unit's branch unless explicitly instructed 7. if in doubt, STOP and ask the Project Manager

Merging (Phase 7 only, after code review passes): Phase 6 ends with the work committed on the slice branch. Do not merge or push at the end of implementation, and never write a merge or push as a task, sub-item, or Success Criteria in a task file. Merge the slice branch into the target only during Phase 7 (Slice Integration), after the slice's code review has passed:

  1. re-read the target (step 1 above) — do not infer it from the current branch or from memory
  2. git checkout {target}, then git merge {branch-name}
  3. if either command fails, STOP and ask the Project Manager

Do not hold a branch open across units. Do not delete branches unless specifically instructed to do so.

Branch Protection

GitHub has two independent mechanisms: classic branch protection and rulesets. A 404 from repos/{owner}/{repo}/branches/{branch}/protection means only that no classic rule exists.

  • Before stating that a branch is or is not protected, also check gh api repos/{owner}/{repo}/rules/branches/{branch} — it lists every active rule on the branch, including ones inherited from organization rulesets.
  • Report "unprotected" only when both come back empty. If either call fails for a reason other than "not found" (permissions, auth), say so instead of concluding anything.

Release Versioning

Versions are MAJOR.MINOR.PATCH. What goes in the CHANGELOG does not decide the bump: a non-empty CHANGELOG, an ### Added section, a new flag, option, parameter, config key, or check is never by itself a reason for a minor version.

  • Patch (the default): fixes, refinements to existing systems, new flags/options/parameters/config keys, new checks or warnings, guide and documentation changes.
  • Minor: only a new user-facing feature or a significant new AI capability. Propose it in one line with the reason; the Project Manager confirms before any files change.
  • Major: only when the Project Manager explicitly asks for it.

Commit Messages

Use semantic commit prefixes. The goal is a readable git log --oneline.

Format: {type}: {short imperative summary}

Types:

  • feat — New functionality or capability
  • fix — Bug fix
  • refactor — Code restructuring without behavior change
  • test — Adding or updating tests
  • style — Formatting, whitespace, linting (no logic change)
  • guides - Update or addition to project guides (system/project level)
  • docs — Update or addition to user/ guides or documentation (slices, readme, etc)
  • review — Code review, design review, or audit documentation
  • package - Updates related to packaging, npm, package.json, PyPi, etc
  • chore — Build config, dependencies, tooling, CI

Actions (optional, use if applicable):

  • update: primarily update/edit to existing information
  • add: primarily addition of new code or information
  • extract: primarily used in refactoring
  • reduce: if primary work involves reduction or streamlining

Guidelines:

  • Summary is imperative mood ("add X" not "added X" or "adds X")
  • Keep to ~72 characters
  • No period at end
  • Scope is optional but useful in monorepos: feat(core): add template variable resolution

Examples:

feat: add context_build MCP tool fix: update to handle missing template directory gracefully refactor(core): extract service instantiation into shared helper docs: add MCP server installation instructions to README test: add unit tests for prompt_list tool handler chore: update @modelcontextprotocol/server to v2.1

Additional Rules

The rules above always apply. The following are scoped to specific languages and tools and are deliberately not inlined here — read the relevant file when working in that area:

  • project-documents/ai-project-guide/project-guides/rules/shell.md — Shell script standards for bash and sh, including CI/CD and pipeline scripts. Use when writing, modifying, or reviewing .sh/.bash files, extensionless scripts with a bash or sh shebang, or shell in CI workflow run blocks. Applies to: **/*.sh,**/*.bash,**/.github/workflows/*.yml,**/.github/workflows/*.yaml,**/.gitlab-ci.yml
  • project-documents/ai-project-guide/project-guides/rules/sql.md — SQL coding standards for PostgreSQL, pgvector, and TimescaleDB. Use when writing queries, migrations, schema definitions, database functions, or any code that connects to a database — including test fixtures and runners. Covers naming, indexing, query optimization, extension-specific patterns, and production-database protection. Applies to: **/*.sql,**/*.psql,**/migrations/**,**/schema.sql,**/test/**/*.py,**/tests/**/*.py,**/conftest.py
  • project-documents/ai-project-guide/project-guides/rules/testing.md — Testing standards and best practices. Use when writing, modifying, or reviewing tests. Covers test structure, naming, mocking patterns, assertion style, coverage expectations, and database safety in tests. Applies to: **/*.test.*,**/*.spec.*,**/*.stories.*,src/stories/**/*,**/test_*.py,**/test/**/*.py,**/tests/**/*.py,**/conftest.py
  • project-documents/ai-project-guide/project-guides/rules/typescript.md — TypeScript strict typing standards, idiomatic patterns, and project conventions. Use for all TypeScript files. Covers type annotations, generics, module patterns, and error handling. Applies to: **/*.ts,**/*.tsx
<!-- END:context-forge -->

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.