docs: add Profile-Based Module Assembly pattern (Section 3.5)
- Section 3.5 "Team Configuration at Scale" in ultimate-guide.md: profiles YAML + shared modules + skeleton + assembler script; 59% context token reduction measured on 5-dev production team; includes CI drift detection, 5-step replication guide, trade-offs - New workflow: guide/workflows/team-ai-instructions.md (6 phases, scaling thresholds, troubleshooting table) - New templates: examples/team-config/ (profile-template.yaml, claude-skeleton.md, sync-script.ts) - reference.yaml: 9 new entries for team_ai_instructions_* - README: templates count 161 → 164, date Feb 19 → Feb 20 - CHANGELOG [Unreleased]: resource evaluations (AGENTS.md ETH Zürich 4/5, Sylvain Chabaud 3/5), spec-first Task Granularity section, methodologies ATDD expansion Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
146d15e958
commit
6d847d24de
14 changed files with 1528 additions and 14 deletions
|
|
@ -65,6 +65,12 @@ Use existing battle-tested repositories as scaffolding for new projects.
|
|||
|
||||
**When to use**: Starting new projects, standardizing team patterns, rapid prototyping from proven foundations
|
||||
|
||||
### [Team AI Instructions](./team-ai-instructions.md)
|
||||
|
||||
Scale CLAUDE.md across a multi-developer, multi-tool team with profile-based module assembly.
|
||||
|
||||
**When to use**: Team 5+ devs, multiple AI tools (Claude Code + Cursor/Windsurf), mixed OS
|
||||
|
||||
---
|
||||
|
||||
## 🎨 Design & Content
|
||||
|
|
@ -112,6 +118,7 @@ Systematically explore and understand unfamiliar codebases.
|
|||
| **UI implementation** | [Design to Code](./design-to-code.md) |
|
||||
| **Code quality** | [Iterative Refinement](./iterative-refinement.md) |
|
||||
| **New project from template** | [Skeleton Projects](./skeleton-projects.md) |
|
||||
| **Team AI instructions** | [Team AI Instructions](./team-ai-instructions.md) |
|
||||
| **Documentation** | [PDF Generation](./pdf-generation.md) |
|
||||
| **Audio feedback** | [TTS Setup](./tts-setup.md) |
|
||||
|
||||
|
|
@ -132,4 +139,4 @@ New workflow ideas? Open an issue or PR in the main repository.
|
|||
|
||||
---
|
||||
|
||||
**Last updated**: January 2026
|
||||
**Last updated**: February 2026
|
||||
|
|
|
|||
|
|
@ -16,12 +16,13 @@ Define what you want in CLAUDE.md BEFORE asking Claude to build. One well-struct
|
|||
|
||||
1. [TL;DR](#tldr)
|
||||
2. [The Pattern](#the-pattern)
|
||||
3. [CLAUDE.md Spec Templates](#claudemd-spec-templates)
|
||||
4. [Step-by-Step Workflow](#step-by-step-workflow)
|
||||
5. [Integration with Tools](#integration-with-tools)
|
||||
6. [When to Use](#when-to-use)
|
||||
7. [Anti-Patterns](#anti-patterns)
|
||||
8. [See Also](#see-also)
|
||||
3. [Task Granularity: Sizing Work for Agents](#task-granularity-sizing-work-for-agents)
|
||||
4. [CLAUDE.md Spec Templates](#claudemd-spec-templates)
|
||||
5. [Step-by-Step Workflow](#step-by-step-workflow)
|
||||
6. [Integration with Tools](#integration-with-tools)
|
||||
7. [When to Use](#when-to-use)
|
||||
8. [Anti-Patterns](#anti-patterns)
|
||||
9. [See Also](#see-also)
|
||||
|
||||
---
|
||||
|
||||
|
|
@ -58,6 +59,41 @@ The spec becomes the source of truth that:
|
|||
|
||||
---
|
||||
|
||||
## Task Granularity: Sizing Work for Agents
|
||||
|
||||
Before writing the spec, verify the task is the right size. Agents work best with **vertical slices** — thin, end-to-end units that cut through all layers but implement exactly one complete user behavior (e.g. "password reset via email", not "authentication system").
|
||||
|
||||
**Rule of thumb**: One agent session = one vertical slice. If the task description requires "and" between two user behaviors, split it.
|
||||
|
||||
### PRD Quality Checklist
|
||||
|
||||
Run this before handing any task to an agent. Six dimensions to verify:
|
||||
|
||||
| Dimension | Question to ask | Red flag |
|
||||
|-----------|----------------|----------|
|
||||
| **Problem Clarity** | Is the problem statement unambiguous? | "Improve performance" |
|
||||
| **Testable Criteria** | Can completion be verified automatically? | "Works well" |
|
||||
| **Scope Boundaries** | What is explicitly OUT of scope? | Nothing listed as excluded |
|
||||
| **Observable Done** | What does "done" look like to a user? | Internal-only description |
|
||||
| **Requirements Clarity** | No implementation details in the spec? | "Use Redis for caching" |
|
||||
| **Terminology** | Same terms used throughout? | "user" and "account" mixed |
|
||||
|
||||
A task that fails 2+ dimensions needs rework before an agent touches it. The spec review catches ambiguity that will otherwise surface as incorrect implementation mid-session.
|
||||
|
||||
```
|
||||
❌ Too big, ambiguous:
|
||||
"Add user authentication to the app"
|
||||
|
||||
✅ One vertical slice:
|
||||
"Users can log in with email + password.
|
||||
- POST /auth/login returns JWT on success, 401 on failure
|
||||
- Invalid credentials show 'Email or password incorrect' (not which is wrong)
|
||||
- Session expires after 24h
|
||||
- Out of scope: OAuth, password reset, remember me"
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## CLAUDE.md Spec Templates
|
||||
|
||||
### Feature Spec (Most Common)
|
||||
|
|
@ -828,3 +864,4 @@ Claude: Reads CLAUDE.md + @CLAUDE-api.md (relevant context only)
|
|||
- [Spec Kit Documentation](https://github.blog/ai-and-ml/generative-ai/spec-driven-development-with-ai-get-started-with-a-new-open-source-toolkit/)
|
||||
- [OpenSpec Documentation](https://github.com/Fission-AI/OpenSpec)
|
||||
- [tdd-with-claude.md](./tdd-with-claude.md) — Combine with TDD
|
||||
- [Spec-to-Code Factory](https://github.com/SylvainChabaud/spec-to-code-factory) — Implémentation référence complète avec enforcement outillé (6 gates via Node.js, invariants "No Spec No Code" + "No Task No Commit", ~900K tokens/projet)
|
||||
|
|
|
|||
331
guide/workflows/team-ai-instructions.md
Normal file
331
guide/workflows/team-ai-instructions.md
Normal file
|
|
@ -0,0 +1,331 @@
|
|||
---
|
||||
title: "Team AI Instructions Management"
|
||||
description: "Scale CLAUDE.md across a multi-developer team using Profile-Based Module Assembly"
|
||||
tags: [workflow, team, claude-md, configuration]
|
||||
---
|
||||
|
||||
# Team AI Instructions Management
|
||||
|
||||
Manage AI instructions (CLAUDE.md, .cursorrules) across a team without fragmentation.
|
||||
|
||||
**Pattern**: Profile-Based Module Assembly — shared modules + per-dev profiles + automated assembler.
|
||||
|
||||
**When to use**: Team 5+ developers, multiple AI tools (Claude Code + Cursor/Windsurf), mixed OS.
|
||||
**Skip if**: Solo developer, homogeneous team (same tool, same OS), short project (<3 months).
|
||||
|
||||
---
|
||||
|
||||
## The Problem: N x M x P Fragmentation
|
||||
|
||||
When a team grows, AI instructions fragment fast:
|
||||
|
||||
| Factor | Values | Example |
|
||||
|--------|--------|---------|
|
||||
| **N developers** | 5-20 | Alice, Bob, Charlie... |
|
||||
| **M tools** | 2-4 | Claude Code, Cursor, Windsurf, Copilot |
|
||||
| **P operating systems** | 2-3 | macOS, Linux, WSL |
|
||||
|
||||
**Total variants**: N x M x P = 5 x 3 x 2 = **30 possible configurations**.
|
||||
|
||||
Without a system, what happens:
|
||||
|
||||
```
|
||||
Week 1: Team agrees on shared CLAUDE.md
|
||||
Week 3: Alice adds TypeScript strict rules locally
|
||||
Week 5: Bob copies Alice's file, removes half the rules
|
||||
Week 8: New hire Charlie gets Bob's outdated copy
|
||||
Week 12: 5 developers, 5 different CLAUDE.md files, nobody knows what's canonical
|
||||
```
|
||||
|
||||
**Root cause**: CLAUDE.md is treated as a monolithic file instead of a composed configuration.
|
||||
|
||||
---
|
||||
|
||||
## Architecture Overview
|
||||
|
||||
```
|
||||
profiles/ modules/
|
||||
├── alice.yaml ├── core-standards.md
|
||||
├── bob.yaml ├── git-workflow.md
|
||||
├── charlie.yaml ├── typescript-rules.md
|
||||
│ ├── test-conventions.md
|
||||
│ ├── macos-paths.md
|
||||
│ ├── linux-paths.md
|
||||
│ ├── cursor-rules.md
|
||||
│ └── communication-verbose.md
|
||||
│
|
||||
├── skeleton/
|
||||
│ └── claude-skeleton.md ← Template with {{MODULE:name}} placeholders
|
||||
│
|
||||
└── sync-ai-instructions.ts ← Reads profile → injects modules → writes output
|
||||
│
|
||||
▼
|
||||
output/
|
||||
├── alice/CLAUDE.md ← Generated (read-only)
|
||||
├── bob/CLAUDE.md
|
||||
└── charlie/CLAUDE.md
|
||||
```
|
||||
|
||||
**Flow**: Profile (YAML) + Skeleton (template) + Modules (fragments) → Assembler → Generated CLAUDE.md
|
||||
|
||||
---
|
||||
|
||||
## Phase 1: Audit Your Current CLAUDE.md
|
||||
|
||||
**Goal**: Classify every line as universal, conditional, or personal.
|
||||
|
||||
```markdown
|
||||
# Audit template
|
||||
|
||||
## Universal (all devs, all tools)
|
||||
- Architecture: hexagonal
|
||||
- Tests: must pass before PR
|
||||
- Naming: kebab-case for files
|
||||
|
||||
## Conditional (depends on tool or OS)
|
||||
- Cursor: use @filename syntax → module: cursor-rules
|
||||
- macOS paths: /opt/homebrew → module: macos-paths
|
||||
- Linux paths: /usr/local → module: linux-paths
|
||||
|
||||
## Personal (individual preference)
|
||||
- Style: verbose explanations → profile preference
|
||||
- Language: French comments → profile preference
|
||||
```
|
||||
|
||||
**Command to measure**:
|
||||
```bash
|
||||
wc -l CLAUDE.md # Total lines before modularization
|
||||
# Tag each line with [U]niversal, [C]onditional, [P]ersonal
|
||||
# Count by category to estimate module split
|
||||
```
|
||||
|
||||
**Typical result**: 60% universal, 25% conditional, 15% personal.
|
||||
|
||||
---
|
||||
|
||||
## Phase 2: Extract Modules
|
||||
|
||||
**Goal**: One `.md` file per thematic group.
|
||||
|
||||
**Recommended structure**:
|
||||
|
||||
```
|
||||
modules/
|
||||
├── core-standards.md # Architecture, naming, patterns (all devs)
|
||||
├── git-workflow.md # Git conventions (all devs)
|
||||
├── typescript-rules.md # TS strict config (if TypeScript)
|
||||
├── test-conventions.md # Testing patterns (all devs)
|
||||
├── macos-paths.md # macOS-specific paths (if macOS)
|
||||
├── linux-paths.md # Linux paths (if Linux)
|
||||
├── cursor-rules.md # Cursor-specific rules (if Cursor)
|
||||
└── communication-verbose.md # Verbose explanation style (if preferred)
|
||||
```
|
||||
|
||||
**Module format** (each module is a standalone Markdown fragment):
|
||||
|
||||
```markdown
|
||||
<!-- modules/typescript-rules.md -->
|
||||
## TypeScript Rules
|
||||
|
||||
- Use strict mode: `"strict": true` in tsconfig
|
||||
- Prefer `type` over `interface` for unions
|
||||
- No `any` — use `unknown` + type guards
|
||||
- Zod for runtime validation at boundaries
|
||||
```
|
||||
|
||||
**Guidelines**:
|
||||
- Keep modules self-contained (no cross-references between modules)
|
||||
- 15-50 lines per module is the sweet spot
|
||||
- Name modules for their domain, not their audience
|
||||
- One module = one reason to change
|
||||
|
||||
---
|
||||
|
||||
## Phase 3: Create Developer Profiles
|
||||
|
||||
**Goal**: One YAML per developer, listing their modules.
|
||||
|
||||
```yaml
|
||||
# profiles/alice.yaml
|
||||
name: "Alice"
|
||||
os: "macos"
|
||||
tools:
|
||||
- claude-code
|
||||
- cursor
|
||||
communication_style: "concise"
|
||||
modules:
|
||||
core:
|
||||
- core-standards
|
||||
- git-workflow
|
||||
- typescript-rules
|
||||
- test-conventions
|
||||
conditional:
|
||||
- macos-paths # auto-included when os: macos
|
||||
- cursor-rules # auto-included when cursor in tools
|
||||
preferences:
|
||||
language: "english"
|
||||
```
|
||||
|
||||
**Profile rules**:
|
||||
- `core` modules: included for every dev (team standards)
|
||||
- `conditional` modules: included based on `os` and `tools` fields
|
||||
- `preferences`: personal settings injected into skeleton variables
|
||||
|
||||
**Template for new team members**: See [profile-template.yaml](../../examples/team-config/profile-template.yaml)
|
||||
|
||||
---
|
||||
|
||||
## Phase 4: Write the Assembler Script
|
||||
|
||||
**Goal**: Script that reads profile, injects modules, outputs CLAUDE.md.
|
||||
|
||||
```typescript
|
||||
// sync-ai-instructions.ts (simplified ~30 lines)
|
||||
import { readFileSync, writeFileSync, mkdirSync } from 'fs';
|
||||
import { parse } from 'yaml';
|
||||
import { join } from 'path';
|
||||
|
||||
const profile = parse(readFileSync(`profiles/${process.argv[2]}.yaml`, 'utf8'));
|
||||
let skeleton = readFileSync('skeleton/claude-skeleton.md', 'utf8');
|
||||
|
||||
// Collect modules from profile
|
||||
const modules = [...profile.modules.core, ...profile.modules.conditional];
|
||||
|
||||
// Replace each placeholder with module content
|
||||
for (const mod of modules) {
|
||||
const content = readFileSync(`modules/${mod}.md`, 'utf8');
|
||||
skeleton = skeleton.replace(`{{MODULE:${mod}}}`, content);
|
||||
}
|
||||
|
||||
// Remove unused placeholders
|
||||
skeleton = skeleton.replace(/\{\{MODULE:\w+\}\}/g, '');
|
||||
|
||||
// Write output
|
||||
const outDir = `output/${process.argv[2]}`;
|
||||
mkdirSync(outDir, { recursive: true });
|
||||
writeFileSync(join(outDir, 'CLAUDE.md'), skeleton);
|
||||
console.log(`Generated ${outDir}/CLAUDE.md (${modules.length} modules)`);
|
||||
```
|
||||
|
||||
**Run**:
|
||||
```bash
|
||||
npx ts-node sync-ai-instructions.ts alice # Single dev
|
||||
npx ts-node sync-ai-instructions.ts --all # Generate all profiles
|
||||
npx ts-node sync-ai-instructions.ts --check # Verify no drift
|
||||
```
|
||||
|
||||
Full template: [sync-script.ts](../../examples/team-config/sync-script.ts)
|
||||
|
||||
---
|
||||
|
||||
## Phase 5: CI Drift Detection
|
||||
|
||||
**Goal**: Catch when output files are out of sync with profiles/modules.
|
||||
|
||||
```yaml
|
||||
# .github/workflows/ai-instructions-check.yml
|
||||
name: AI Instructions Drift Check
|
||||
on:
|
||||
push:
|
||||
paths:
|
||||
- 'modules/**'
|
||||
- 'profiles/**'
|
||||
- 'skeleton/**'
|
||||
schedule:
|
||||
- cron: '0 9 * * 1-5' # Weekdays at 9am
|
||||
|
||||
jobs:
|
||||
check-drift:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- run: npx ts-node sync-ai-instructions.ts --check
|
||||
- name: Fail if drift detected
|
||||
run: |
|
||||
if git diff --quiet output/; then
|
||||
echo "No drift detected"
|
||||
else
|
||||
echo "::error::AI instructions are out of sync!"
|
||||
git diff output/
|
||||
exit 1
|
||||
fi
|
||||
```
|
||||
|
||||
**What it detects**:
|
||||
- A module was edited but the assembler wasn't re-run
|
||||
- A profile was added but no output CLAUDE.md exists
|
||||
- A dev manually edited their generated CLAUDE.md
|
||||
|
||||
**Policy**: Generated files are read-only. All changes go through profiles/modules, then re-run the assembler.
|
||||
|
||||
---
|
||||
|
||||
## Phase 6: Onboarding New Developers
|
||||
|
||||
**Goal**: New dev gets their CLAUDE.md in under 5 minutes.
|
||||
|
||||
```bash
|
||||
# 1. Clone repo
|
||||
git clone <repo>
|
||||
|
||||
# 2. Copy profile template
|
||||
cp examples/team-config/profile-template.yaml profiles/dave.yaml
|
||||
# Edit: name, os, tools, modules
|
||||
|
||||
# 3. Generate
|
||||
npx ts-node sync-ai-instructions.ts dave
|
||||
|
||||
# 4. Install
|
||||
cp output/dave/CLAUDE.md .claude/CLAUDE.md
|
||||
```
|
||||
|
||||
**CLAUDE.md placement reminder**:
|
||||
- Project-wide: `project/CLAUDE.md` (committed, for team conventions)
|
||||
- Personal overrides: `.claude/CLAUDE.md` (gitignored, for individual preferences)
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
| Problem | Cause | Fix |
|
||||
|---------|-------|-----|
|
||||
| Generated file too long | Too many modules included | Review profile: remove rarely-used modules |
|
||||
| Module missing in output | Placeholder typo in skeleton | Check `{{MODULE:name}}` matches filename |
|
||||
| CI drift alert | Output not regenerated after module edit | Run `sync-ai-instructions.ts` and commit |
|
||||
| Dev A has rules Dev B doesn't | Expected — it's the point | Verify profile is correct for that dev |
|
||||
| Stale output after merge | Merge didn't trigger regeneration | Run assembler post-merge (add git hook) |
|
||||
|
||||
---
|
||||
|
||||
## Scaling Thresholds
|
||||
|
||||
| Team size | Approach |
|
||||
|-----------|----------|
|
||||
| 1-2 devs | Shared CLAUDE.md + precedence rules ([Section 3.4](../ultimate-guide.md#34-precedence-rules)) |
|
||||
| 3-5 devs, same tools | Optional: modules only, no profiles |
|
||||
| 5+ devs or multi-tool | Profile-Based Module Assembly (this workflow) |
|
||||
| 20+ devs | Consider a CLAUDE.md config server + PR-based module changes |
|
||||
|
||||
---
|
||||
|
||||
## Measured Results
|
||||
|
||||
From a production team (5 developers, 3 tools, 2 OS):
|
||||
|
||||
| Metric | Before | After |
|
||||
|--------|--------|-------|
|
||||
| Lines per CLAUDE.md | ~380 (monolithic) | ~185 (assembled) |
|
||||
| Token reduction | — | 59% less context consumed |
|
||||
| Modules extracted | 0 | 12 |
|
||||
| Onboarding time | "copy someone's file" | 5 min (template + generate) |
|
||||
| Drift incidents | Weekly | 0 (CI catches) |
|
||||
|
||||
---
|
||||
|
||||
## Related
|
||||
|
||||
- [Section 3.5 Team Configuration at Scale](../ultimate-guide.md#35-team-configuration-at-scale) — Concept overview and measured results
|
||||
- [Section 3.4 Precedence Rules](../ultimate-guide.md#34-precedence-rules) — How Claude reads multiple CLAUDE.md files
|
||||
- [profile-template.yaml](../../examples/team-config/profile-template.yaml) — Profile template
|
||||
- [claude-skeleton.md](../../examples/team-config/claude-skeleton.md) — Skeleton template
|
||||
- [sync-script.ts](../../examples/team-config/sync-script.ts) — Full assembler script
|
||||
Loading…
Add table
Add a link
Reference in a new issue