From afterthought to infrastructure: how AI config evolves in a real project
Nine months of AI configuration in one production project: evolving responsibilities, profile-based generation and a measured reduction in always-on lines.
Jump to summaryWritten by Florian Bruniaux
AI Founding Engineer at MΓ©thode Aristote, 13 years scaling engineering teams from developer to CTO. Builds open-source developer tools, see what else I've shipped.
TL;DR
| What | Details |
|---|---|
| Project | MΓ©thode Aristote EdTech platform, 9 months (Aug 2025 β Apr 2026) |
| Historical audit total | 506 reported commits; monthly rows sum to 495, an unreconciled discrepancy |
| Current scale | 407 files in .claude/, 34 rules, 15 hooks, 36 skills, 57 commands, 17 agents |
| Distribution | The listed monthly counts are concentrated in January through April |
| 5 phases | Afterthought β Documentation β Infrastructure β Engineering practice β Continuous improvement |
| Context Diet | Apr 2026: always-on context 2,518L β 646L (-74% lines); scorer denominators changed |
| The big bang | Jan 6, 2026: 86 files created in a single day (commit 1421e863) |
| Key insight | AI config doesnβt get designed upfront, you figure out what it needs by running into the friction. |
This is a post-mortem of AI configuration evolving over 9 months of serious use on a production codebase, rather than a guide to a perfect CLAUDE.md.
The original audit used git log --all --format="%ad" --date=format:"%Y-%m" -- CLAUDE.md .claude/ and reported 506 commits touching AI configuration, a stated 8.6% of repository activity, plus 149 changes to CLAUDE.md. These are historical audit claims, not a fresh count. The monthly figures retained below sum to 495. That discrepancy remains unreconciled; the reported total must not be treated as a validated denominator for the table.
The historical monthly breakdown
| Month | Reported AI-config commits |
|---|---|
| Aug 2025 | 5 |
| Sep 2025 | 24 |
| Oct 2025 | 34 |
| Nov 2025 | 27 |
| Dec 2025 | 27 |
| Jan 2026 | 138 |
| Feb 2026 | 81 |
| Mar 2026 | 116 |
| Apr 2026 | 43 (partial) |
| Sum of the listed rows | 495 |
| Original reported total | 506, unreconciled |
January and March are the two largest listed months. The account below connects those spikes to structural decisions in this project. It does not establish a universal investment curve.

Phase 1: config as afterthought (Aug-Sep, 29 commits)
The first AI config file. August 22, 2025, commit a48d5017b. CLAUDE.md, 282 lines, shipped in the first release.
The content was minimal. Project identity, the T3 stack (Next.js, tRPC, Prisma), basic conventions. A starting point, not a system.
Aug 22 βββ CLAUDE.md (282 lines) ββββββββ Born: AI config exists
Sep 05 βββ .claude/ directory ββββββββββββ Dedicated structure
Sep 11 βββ .claude/commands/ βββββββββββββ First slash commands
At this stage the mental model was basic: CLAUDE.md as a context file, you write down what the AI needs to know. Useful the way documentation is useful, better than nothing, but not yet a system.
The AI had the obvious stuff: project stack, naming conventions, basic architecture intent. Everything that mattered day-to-day was missing, meaning the business domain, the patterns weβd already established, the reasoning behind specific decisions, and what it should refuse to do.
24 commits in September added the .claude/ directory structure and first slash commands. Basic namespacing: tech:commit, tech:PR, tech:review. Useful shortcuts for repetitive operations.
At this point, one person maintains AI configuration informally, changing it whenever something breaks or feels missing. It is still a file someone cares about, rather than a system.
Phase 2: config as documentation (Oct-Dec, 88 commits)
Phase 2 is where the AI starts needing business context, not just technical context.
Oct 15 βββ .claude/agents/ (v0.8.0) ββββββ First custom agents
Oct 23 βββ knowledge-base.md (v0.10.0) βββ Business rules codified
Nov 04 βββ MCP Serena (v0.14.0) βββββββββββ Persistent memory
Nov 21 βββ CLAUDE.md -50% tokens ββββββββββ First optimization pass
October 23: doc/knowledge-base.md created. This is when the configuration started encoding business knowledge rather than just technical setup. Session mechanics (supervised vs autonomous, 15-minute tolerance, doublet/triplet offsets). User lifecycle rules. Tutor compensation logic. The glossary of French terms that appeared in the code.
Without this, the AI was technically capable but business-ignorant. It could write a repository method but didnβt know that a βsessionβ in this codebase meant something specific (SUPERVISED: 1h with a tutor, or AUTONOMOUS: 30min solo), with a lifecycle of SCHEDULED β STARTED β COMPLETED.
November 4 (v0.14.0): MCP Serena integration. Persistent memory across sessions. The AI could now remember architectural decisions made in previous sessions without restating them every time.
November 21 (v0.15.6): CLAUDE.md optimized, 50% token reduction. The file had grown organically and accumulated noise. First deliberate compression pass.
By Phase 2 the mental model had shifted: AI configuration as onboarding documentation, the kind youβd write for a new senior hire. Business rules, conventions, architectural decisions, the βwhyβ behind the patterns.
Phase 3: config as infrastructure (Jan, 138 commits)
January 2026 is the first turning point. The configuration stops being a file and becomes a system, faster than any planned migration would have allowed.
January 6, 2026. Commit 1421e863. 86 files created in a single day.
Jan 06 βββ 12 agents + 5 hooks + settings.json βββ Big Bang (86 files, 1 day)
Jan 09 βββ .claude/rules/ ββββββββββββββββββββββββ Guardrails formalized (21 files)
Jan 16 βββ grepai MCP ββββββββββββββββββββββββββββ Semantic code search
Jan 19 βββ Pre-push security hooks βββββββββββββββ Defense at commit level
Jan 26 βββ Tasks API (450 lines doc) ββββββββββββββ Multi-session management
Jan 26 βββ Perplexity MCP, Jam.dev MCP ββββββββββββ Expanded context sources
Jan 29 βββ SonarQube MCP βββββββββββββββββββββββββ Real-time quality analysis
Jan 29 βββ 283 tests added βββββββββββββββββββββββ TDD enforcement in practice
Jan 29 βββ RTK enforcement hook βββββββββββββββββββ Token optimization mandatory
What triggered the explosion was team growth. Augustin was joining, and the configuration that worked for one developer (me, on macOS, with a specific workflow) now had to cover multiple people on different setups, tools, and levels of experience. A single monolithic CLAUDE.md couldnβt absorb that, so a system had to.
Skills: 12 agents and the first skills created on January 6, growing to 36 skills today. Loaded on-demand rather than burning context permanently. TDD methodology, security playbooks, database patterns, accessibility rules, all available on trigger and silent otherwise.
Hooks: 5 hooks created on January 6 in a single commit: dangerous-actions-blocker.sh, security-gate.sh, activity-logger.sh, auto-format.sh, notification.sh. Pre-push security checks, token optimization enforcement (RTK mandatory for all CLI operations). These run automatically without requiring the developer to remember to run them. For a full breakdown of hook events and what each can deterministically block, see Claude Code Under the Hood.
Rules: First 3 rule files on January 9, growing to 34 today. Guardrails that fire during coding sessions. Silent catches, hidden fallbacks, and unvalidated nullable access are out. A failing test before implementation code is mandatory, hence the blunt version of the rule: βWrite code before the test? Delete it and start over.β
6 MCP servers integrated in 3 weeks: Serena (persistent memory), grepai (semantic code search), Perplexity (web search with citations), Jam.dev (bug recording), SonarQube (code quality), Postgres read-only (direct production queries for context).
By Phase 3, AI configuration has its own PRs, review process, and maintenance burden. It is infrastructure in practice. You optimize it, test it, and measure the impact when changes land.
Phase 4: config as engineering practice (Feb, 81 commits)
81 commits in 28 days = 2.9 commits per day on AI configuration alone.
Feb 03 βββ .cursor/ config ββββββββββββββββ Cursor support (Augustin)
Feb 05 βββ profiles/ + modules/ YAML ββββββ Modular system
Feb 09 βββ Zod validation + CI ββββββββββββ Config has tests
Feb 11 βββ Cross-editor sync ββββββββββββββ Claude + Cursor synchronized
Feb 13 βββ Memory compression -6.2K tokens β Ongoing optimization
February 5 (PR #598): The modular system. Instead of one CLAUDE.md that everyone reads, a generation pipeline:
- 5 YAML profiles (one per developer)
- 14 modules (composable content blocks)
- A TypeScript pipeline that assembles them with Zod validation
- Generated outputs: CLAUDE.md (703 lines for Florian, Claude Code, all modules) and .cursorrules (289 lines for Augustin, Cursor, minimal modules)
February 9 (PR #614): The generated outputs have their own tests. The pipeline validates that no placeholder remains unresolved. The CI catches configuration regressions.
The AI configuration now has the properties we expect from production code:
- Version controlled (source files, not generated outputs)
- Validated (Zod schema with 7 fields, 5 valid tone values, 6 valid feature modules)
- Tested (pipeline tests, CI checks)
- Reviewed (PRs for configuration changes, same process as feature PRs)
- Documented (450 lines of documentation for the Tasks API alone)
Phase 5: config as continuous improvement (Mar, 116 commits)
March 2026 produced the second-largest monthly count in the retained table, after January.
Mar 04 βββ ACE pipeline + 12 ADRs ββββββββ Commit 3fc8c14f (43 files)
Mar 04 βββ Compound engineering patterns ββ Architecture decisions codified
Mar ββββββ multi-agent-coordination.md ββββ Agent orchestration rules
Mar ββββββ research-output.md βββββββββββββ Structured research protocol
Mar ββββββ retex-review.md ββββββββββββββββ Post-task retrospective system
Commit 3fc8c14f contained the ACE pipeline complet, 12 Architecture Decision Records, compound engineering patterns, and 43 files. The configuration had matured enough to start encoding how to evolve itself.
Phase 5 goes past βmore rulesβ. The configuration starts capturing meta-patterns: how to coordinate agents, how to structure research before implementation, how to extract learnings after each task. The system began codifying its own methodology.
April 2026: the context diet
The next inflection wasnβt a spike in commits. It was a deliberate reduction.
By April 2026, the configuration had grown to 23 always-on rules loaded into every Claude session, regardless of what you were working on. 2,518 lines of guardrails firing unconditionally, whether you were touching a React component or a Prisma migration. That is a line-count inventory of always-on material, not a measured share of model context or billed tokens.
The branch fix-improve-context ran in 5 phases over a single week.
Phase 0, baseline. I built a scoring script (scripts/ai/score-ai-context.ts) before touching anything, because βbetterβ needed to mean something measurable. The recorded baseline was 85/100, grade A. Later checks changed the scoring denominator, so the final raw score is a separate checkpoint rather than a directly comparable gain.
Phase 1, triage. Every rule classified against one question: does Claude need this without being asked? Three categories emerged. CONSTRAINT means always-on, non-negotiable. PROCEDURE means step-by-step workflows that load on demand. HYBRID is a short directive plus a long protocol. Of 23 always-on rules, 13 turned out to be procedures or hybrids masquerading as constraints.
Phase 2, extraction. Nine procedural rules converted to skills: code-duplication.md became /tech:dupes, defensive-code-audit.md became /tech:audit, implementation-checklist.md became /tech:checklist. Each always-on version got replaced by a 5-to-15 line stub keeping the directive, while the protocol itself moved on-demand. A smart-suggest.sh pattern was added to every extracted skill so Claude surfaces it when relevant context appears, without loading it permanently.
Phase 3, compression. Rules that belonged in always-on but were too verbose got trimmed. rtk-enforcement.md disappeared entirely since RTK already lives in the global CLAUDE.md, making the per-project copy redundant. debugging-methodology.md dropped from 112L to 43L, with three more rules cut alongside it. Net result, 2,518L down to 646L in always-on context, a 74% reduction.
Phase 3+, Cursor parity. The .cursorrules file had grown into a 703L monolith. Converted to a 133L stub (metadata plus pointers) with 23 .cursor/rules/*.mdc path-scoped rules carrying the real content. Cursor now loads rules only when file paths match, so the same economy applies to Claude.
Phase 4, machine-readable index. Three new generated files landed in machine-readable/:
ai-config.yaml(~270L): structured index of all 27 rules, 36 skills, 59 commands, 16 agents, 15 hooks, module list, profile list. One@reference answers βwhatβs available?β in a new session without grep.llms.txt(~50L): standard llms.txt format for LLM crawlers and context injection.llms-full.txt(~4,500L): full content concat of all rules, modules, and skeletons, for offline/no-tools fallback.
All three generated by pnpm ai:sync. Three new canary checks (C18-C20) were added, worth +10pts to the quality scorer.
The final numbers:
Always-on context: 2,518L β 646L (-74%)
.cursorrules: 703L β 133L (-81%)
ai:score: 85/100 β 125/145 (changed scoring denominator)
Canary checks: 17/17 β 20/20

The January and March spikes followed the same pattern. Friction made the cost visible, measurement made the improvement verifiable, and the tooling (scoring script, canary checks, generated index) catches the next drift before it compounds. The grade records one checkpoint; the scoring script, canary checks, and generated index catch the next accumulation before it becomes a cleanup sprint.
Why two spikes appeared
Thereβs no planning failure here. You canβt write the rules for problems you havenβt hit yet.
Day one, you donβt know what your AI configuration needs to be. You find out by running into the friction.
The January spike was team-driven. Rules that prevent silent catches showed up after we caught AI-generated code doing exactly that. The TDD enforcement rule landed after a stretch of shipping code without tests. The profile system appeared once a second developer with a different setup needed the configuration that had been tuned for one person. Guardrails encode lessons, and you canβt write those down until youβve hit the problem theyβre solving.
The March spike was scale-driven. The system had become complex enough to require architectural governance. The 12 ADRs codified decisions that had been made implicitly over months. Compound engineering patterns emerged from observing what worked across 1,100 commits. The configuration caught up with the maturity of the codebase.
Team size shapes the investment curve too. Phase 1-2 configuration works fine for a solo developer. Phase 3-4 becomes necessary once someone else joins and the monolithic setup stops fitting their machine or context. Collaboration is what eventually forces the systematization, while solo use rarely asks for it.
Lessons from the commit history
If I were starting from scratch today, I wouldnβt try to skip to Phase 3. Those abstractions encode lessons I didnβt have yet. The rules describe problems that hadnβt happened. Start with a CLAUDE.md that honestly reflects what you know: stack, conventions, the business domain youβve figured out so far. The rest shows up when it needs to. That climb from a plain file to versioned, tested infrastructure is the ladder the six-level context engineering guide lays out one level at a time. This article is that ladder playing out in one repo over nine months; the guide is the version without the commit archaeology.
The things I would track earlier are hook execution rates and token counts. A score turns βbetterβ into something more than a feeling. 703 lines versus 289 lines is a measurable configuration-size difference; billing requires its own measurement. Once I had the scoring script, optimization became verifiable instead of intuitive. I later built ccboard to watch exactly that: hook activity, per-session cost, and MCP health in one view. That is the instrumentation I wish Iβd had in this phase.
The retained monthly figures show more activity in January through April than in the first five months, even though the audit total remains unreconciled. In this repository, the systemβs needs became visible when friction appeared.
The original audit reported 506 AI-configuration commits in a 5,820-commit repository. Its stated 8.6% share and monthly breakdown remain historical claims with the discrepancy noted above. More than most business logic files received. If that feels like a lot, consider that the alternative is a stale CLAUDE.md and an AI that drifts from the codebase itβs supposed to understand. The factual half of that drift, the paths and scripts and version numbers that quietly stop matching the code, is what ctxharness checks automatically, so the stale-CLAUDE.md case gets caught instead of noticed months later.
This dataset gives a concrete answer on timing: later than any upfront plan would suggest, and then much faster than expected once the teamβs complexity makes it unavoidable.
Beyond the two-person team
This dataset is one project, two developers, one stack. The friction that shaped the 506 commits was scoped to that size: a second dev joining, one monorepo to cover, one set of conventions to encode.
At organizational scale, the friction shifts shape. Across multiple repos, the same rule ends up duplicated in N CLAUDE.md files and drifts the moment someone updates one without the others. Across stacks, a rule about TypeScript Result types does not translate to a Rust repo using anyhow::Result. Once multiple teams are in the mix, profiles proliferate from 5 YAML profiles to 50, most of that variance with legitimate reasons behind it.
A likely pattern is a dedicated AI config repository as the source of truth, consumed by downstream projects. A few shapes this can take:
- Git submodule: the config repo is pinned at a commit, reproducible across machines, stack-agnostic. The cost is submodule UX, which is real but manageable with a wrapper script.
- Published package (npm, cargo, pip): versioned with semver, distributed through existing release workflows. Works well when your org is stack-homogeneous, less well when a TypeScript team and a Rust team both need the same base rules. Itβs the shape I used for a narrower slice of the same problem, reusable hooks and templates rather than full org config: claude-code-plugins ships 181 of them as installable plugins, versioned and pulled in per project.
- Shared config CLI that fetches + assembles (think Terraform modules or a dotfiles manager): purpose-built, cross-stack, but itβs another tool to maintain.
Whichever shape, the mental model is the same: org modules + team modules + project modules, composed by a pipeline. The modular system that emerged at Phase 4 for one project is the same shape, scaled up one level.
I havenβt run this setup myself. The projection rests on the principle that made Phases 3-4 work: systematize when collaboration demands it, not before. At org scale, that demand jumps from repo-internal to cross-repo. The investment curve likely mirrors what happened here, a long slow accumulation followed by a spike once a second repo needs the same rules that had been tuned for one.
If youβre in that situation, the prediction is concrete: youβll resist the central repo for months because your team-level configs feel fine, and then youβll build it in two weeks because version drift across four repos became impossible to manage.
If youβve already hit that inflection point at org scale, Iβd be curious to hear what shape it took.
Single project (this article) β CLAUDE.md + .claude/ scoped to one repo
Multi-repo org (logical next step) β Shared AI config repo + per-project override
A reported 506 commits, no upfront blueprint
AI configuration grew from one informally maintained file into a system with tests, a generation pipeline, and its own PR review process. The historically reported configuration work came from measuring the tooling and responding to friction as it appeared. Each phase encoded a problem we had already hit. Start with a CLAUDE.md that reflects what you know, then instrument hook execution rates, token counts, and a scoring script early enough to see the next source of friction. In this repository, the investment curve back-loaded itself.
The modular AI instruction system described here (YAML profiles, modules, generation pipeline with Zod validation) is documented in the Claude Code Ultimate Guide. Source data from the MΓ©thode Aristote repository git history (5,820 commits, v0.1.0 β current). The archaeology command: git log --all --format="%ad" --date=format:"%Y-%m" -- CLAUDE.md .claude/ | sort | uniq -c.
YSNK
(You should now know)
- January and March are the two largest listed months; the table sums to 495 while the historical total is 506, so its original percentage distribution is not validated
- Classifying every always-on rule against one question, does Claude need this without being asked, found that 13 of 23 rules were actually procedures or hybrids masquerading as constraints
rtk-enforcement.mddisappeared entirely during the cleanup because it duplicated a rule that already lived in the global CLAUDE.md, redundant the moment someone checkedpnpm ai:syncnow also generates a machine-readable index (ai-config.yaml,llms.txt,llms-full.txt), so a new session can answer βwhatβs available?β with one reference instead of grepping the repo- At org scale, the same friction repeats one level up: a rule duplicated across N CLAUDE.md files drifts the moment one gets updated without the others, which is why a dedicated shared config repo becomes the next inflection point
Go Further in the Claude Code Guide
Practical resources selected to help you take the next step.
Open-source galaxy
Projects used in this path
Related appearances
Live appearances and podcast episodes about this article.
Related articles
Claude is my second contributor: what real Git stats show
6 contributors in our git history. One is an AI. What the commit patterns actually look like after months of Claude Code, beyond the marketing claims.
UVAL: the protocol I built to stop accepting code I don't understand
Jeremy Twei coined it. Addy Osmani popularized it. Margaret-Anne Storey extended it to teams. Here's what I built to fight all three.
AI velocity is bidirectional
Everyone talks about shipping 10x faster with AI. Nobody talks about accumulating debt 10x faster. 7 months of production data from a real EdTech platform.
Go deeper
Step-by-step guides that put this into practice.
Plan-execute: running 20+ agents on a migration
A worked example of a 243-file migration split across bounded agents, with a shared brief, local checks and sequential merge validation.
Une seule source configure Claude Code et Codex
Une configuration d'agents inspectΓ©e, partagΓ©e par Claude Code et Codex : releases immuables, 4 couches d'exΓ©cution, routage BM25 des skills et Γ©carts relevΓ©s. Rapport complet Γ lire en ligne.
One source configures Claude Code and Codex
An inspected agent configuration shared by Claude Code and Codex: immutable releases, 4 execution layers, BM25 skill routing and the gaps found. Full report to read online.