title: "Project Memory — Claude Code" tested_with: claude-code: "1.0.x" last_updated: 2026-03-21 status: proven difficulty: beginner prerequisites: [01-your-first-hour]
Project Memory in Claude Code
Claude Code uses CLAUDE.md files as its project memory system. These files are loaded automatically at the start of every session, giving the agent persistent context about your project's architecture, conventions, and workflows without you repeating yourself.
Where CLAUDE.md Lives
CLAUDE.md can exist at multiple levels in your project:
- Project root (
./CLAUDE.md) — loaded in every session. This is your primary configuration file. - Subdirectories (
./src/api/CLAUDE.md) — loaded when the agent works in that directory. Use these for module-specific conventions. - Home directory (
~/.claude/CLAUDE.md) — loaded in every project. Use this sparingly, for personal preferences that apply everywhere.
Note: The filename must be exactly
CLAUDE.md(uppercase). Claude Code will not recognizeclaude.mdorClaude.md.
How Claude Code Loads It
When you start a session, Claude Code automatically:
- Reads
CLAUDE.mdfrom your project root - Reads any
CLAUDE.mdfiles in the current working directory and its parents - Reads
~/.claude/CLAUDE.mdif it exists - Merges all instructions, with more specific files taking precedence
You do not need to reference, import, or include these files. They are loaded silently and automatically. The agent follows the instructions without you needing to mention them in your prompts.
The Anatomy of a Great CLAUDE.md
A well-structured CLAUDE.md has five sections. Not every project needs all five, but this is the framework to build from.
Project Overview
One to two sentences of technical context. This is not your elevator pitch — it is the minimum an agent needs to understand what it is working on.
## Project Overview
SaaSKit is a Next.js 14 multi-tenant SaaS starter using App Router, Drizzle ORM with Postgres, and Stripe for billing. The app serves ~2000 DAU in production.
Architecture
Key directories and what lives in them. Focus on navigation — where should the agent look for things?
## Architecture
- `src/app/` — Next.js App Router pages and layouts
- `src/components/` — Shared React components (barrel exports via index.ts)
- `src/lib/` — Business logic, utilities, and third-party wrappers
- `src/db/` — Drizzle schema, migrations, and seed data
- `src/api/` — tRPC routers and procedures
- `tests/` — Vitest unit and integration tests (mirrors src/ structure)
Conventions
The rules that make your code look like it belongs in your project. This section prevents the most corrections.
## Conventions
- TypeScript strict mode — no `any` types, no `@ts-ignore`
- Use named exports, not default exports
- React components: functional components with arrow syntax
- State management: Zustand stores in `src/stores/`, never prop drill more than 2 levels
- API calls: always go through tRPC hooks, never raw fetch
- Error handling: use Result types from `src/lib/result.ts`, not try/catch in business logic
- File naming: kebab-case for files, PascalCase for components
Common Tasks
How to build, test, and deploy. The agent uses these to verify its work.
## Common Tasks
- **Dev server**: `pnpm dev` (port 3000)
- **Run tests**: `pnpm test` (Vitest, runs in ~30s)
- **Run single test**: `pnpm test -- path/to/test.ts`
- **Type check**: `pnpm typecheck`
- **Lint**: `pnpm lint` (ESLint + Prettier)
- **DB migrations**: `pnpm db:push` (development), `pnpm db:migrate` (production)
- **Seed data**: `pnpm db:seed`
What NOT to Do
Anti-patterns specific to your project. This section is surprisingly high-value — it prevents the agent from making mistakes your team has already learned from.
## What NOT to Do
- Do NOT use the `prisma` package — we migrated to Drizzle in Q3. The old Prisma schema still exists but is not used.
- Do NOT modify files in `src/legacy/billing/` — these are being deprecated and have complex Stripe webhook dependencies.
- Do NOT use `className` strings directly — always use the `cn()` utility from `src/lib/utils.ts`.
- Do NOT add new environment variables without adding them to `src/env.ts` (Zod validation).
Starter CLAUDE.md Template
Copy this into your project root and customize it. This takes five minutes and delivers immediate value.
# Project Instructions
## Project Overview
<!-- One to two sentences: what is this project, what tech stack, any key context. -->
## Architecture
<!-- List 4-6 key directories and their purpose. -->
## Conventions
<!-- List 3-5 coding conventions that matter most in this project. -->
## Common Tasks
- **Install**: `<!-- your install command -->`
- **Dev server**: `<!-- your dev command -->`
- **Run tests**: `<!-- your test command -->`
- **Lint**: `<!-- your lint command -->`
## What NOT to Do
<!-- List 2-3 project-specific anti-patterns. -->
Intermediate Example: Real-World CLAUDE.md
Here is a more complete example showing what a CLAUDE.md looks like after a few weeks of iterative refinement:
# Project Instructions
## Project Overview
Conveyor is an internal tool for managing our ML model deployment pipeline. Python 3.12, FastAPI backend, React 18 frontend in a monorepo. ~15 engineers actively contributing.
## Architecture
- `api/` — FastAPI application (routers in `api/routers/`, services in `api/services/`)
- `api/models/` — SQLAlchemy ORM models (Postgres)
- `api/schemas/` — Pydantic request/response schemas (separate from ORM models)
- `web/` — React SPA (Vite, TanStack Router, TanStack Query)
- `web/src/components/` — Shared components using Radix UI primitives
- `infra/` — Pulumi IaC (Python) for AWS deployment
- `scripts/` — Development and CI helper scripts
- `tests/` — Pytest tests mirroring api/ structure; Vitest tests in web/
## Conventions
- Python: Ruff for formatting and linting, strict type hints on all public functions
- Python imports: use absolute imports from project root, never relative
- FastAPI: every router function must have explicit response_model
- Pydantic schemas: always inherit from our BaseSchema in `api/schemas/base.py`
- React: use TanStack Query for all server state, Zustand for client state only
- React components: named exports, co-locate styles using CSS modules
- Git: conventional commits (feat:, fix:, chore:, etc.)
- All database queries go through service layer, never directly in routers
- Test naming: `test_{function_name}_{scenario}_{expected_result}`
## Common Tasks
- **API dev**: `cd api && uvicorn main:app --reload`
- **Frontend dev**: `cd web && pnpm dev`
- **Run all tests**: `./scripts/test.sh` (runs both Python and JS tests)
- **Run Python tests**: `cd api && pytest`
- **Run frontend tests**: `cd web && pnpm test`
- **Type check Python**: `cd api && mypy .`
- **DB migration**: `cd api && alembic revision --autogenerate -m "description"` then `alembic upgrade head`
- **Seed dev data**: `cd api && python -m scripts.seed`
## What NOT to Do
- Do NOT use `requests` library — use `httpx` (async support)
- Do NOT add dependencies without checking `pyproject.toml` for existing alternatives
- Do NOT use raw SQL — always go through SQLAlchemy ORM
- Do NOT create new Pydantic models without inheriting BaseSchema
- Do NOT put business logic in router functions — it belongs in the service layer
- Do NOT use `useEffect` for data fetching — use TanStack Query hooks
Advanced Patterns
Directory-Level Overrides
Place a CLAUDE.md in a subdirectory to add context specific to that part of the codebase:
<!-- File: src/billing/CLAUDE.md -->
## Billing Module
This module handles Stripe integration. Key constraints:
- All Stripe API calls go through `stripe_client.py` — never instantiate a Stripe client directly
- Webhook handlers in `webhooks.py` must be idempotent — Stripe retries on failure
- Use `Decimal` for all monetary amounts, never `float`
- Test with Stripe test mode keys only — see `.env.test` for configuration
This keeps your root CLAUDE.md lean while giving the agent deep context exactly where it needs it.
Conditional Instructions
When your project has modes or environments that change behavior:
## Environment-Specific Notes
- When writing tests: use the factories in `tests/factories/` to generate test data, never create objects manually
- When modifying the database schema: always create an Alembic migration, never modify models without one
- When working in the `infra/` directory: be extremely conservative, explain changes before making them
The .claude/ Directory
Claude Code stores project-level settings in a .claude/ directory:
.claude/settings.json— project-specific settings like allowed/denied tool permissions. This file can be committed to your repo so the entire team shares the same agent permissions..claude/settings.local.json— personal settings that override project settings. This file should be in.gitignore.
Note: The
.claude/directory is for Claude Code settings, not for your instructions. Your instructions go inCLAUDE.md.
Testing Your CLAUDE.md
After creating or updating your CLAUDE.md, verify it is working:
- Start a new session (old sessions do not reload CLAUDE.md changes).
- Ask the agent about your conventions:
What conventions should you follow when writing code in this project? - The agent should echo back your conventions. If it gives generic answers, your CLAUDE.md is not being loaded — check the filename and location.
- Run a small task and check whether the output follows your conventions without prompting.
This simple test catches the most common issues: wrong filename, wrong directory, or instructions that are too vague for the agent to act on.
Quick Reference
| What | Where |
|---|---|
| Root instructions | ./CLAUDE.md |
| Directory instructions | ./path/to/dir/CLAUDE.md |
| Personal global instructions | ~/.claude/CLAUDE.md |
| Project settings | .claude/settings.json |
| Personal settings | .claude/settings.local.json |