← 목록으로AI WORKFLOW

CLAUDE.md는 덮어쓰지 않습니다, 이어붙입니다 — CLAUDE.md 우선순위와 4단계 로드 순서

CLAUDE.md는 덮어쓰지 않습니다, 이어붙입니다 — CLAUDE.md 우선순위와 4단계 로드 순서

CLAUDE.md가 여러 개 있을 때 어느 파일이 이기느냐고 물으면 국내 설명 중에는 이렇게 답하는 글이 있습니다. “같은 규칙이 여러 파일에 있으면 하위 파일의 내용이 적용됨!” 공식 문서의 답은 다릅니다.

“All discovered files are concatenated into context rather than overriding each other.” (찾은 파일은 서로 덮어쓰지 않고 전부 이어붙여 컨텍스트에 들어갑니다.)

결론부터 말하면 CLAUDE.md는 덮어쓰기가 아니라 이어붙이기입니다. 전역 파일도 프로젝트 파일도 전부 읽혀서 Claude의 기억 공간(컨텍스트)에 들어갑니다. 파일마다 다른 건 읽히는 순서뿐입니다. 그래서 두 파일의 규칙이 부딪히면 어느 한쪽이 자동으로 이기지 않고 공식 문서 표현대로 Claude가 “may pick one arbitrarily”, 즉 둘 중 하나를 임의로 고를 수 있습니다.

2026년 9월 30일 기준, Claude Code v2.1.285와 공식 memory 문서로 확인했습니다. CLAUDE.md가 무엇인지부터 궁금하다면 CLAUDE.md란 글을 먼저 보세요.

CLAUDE.md 4단계: 놓이는 곳과 읽히는 순서

공식 문서는 CLAUDE.md를 둘 수 있는 곳을 네 곳으로 나누고 표를 “in load order, from broadest scope to most specific”(읽는 순서대로, 넓은 범위에서 좁은 범위로) 적어 두었습니다. 위에서 아래로 읽힙니다.

순서 이름 파일 위치 누가 함께 쓰나
1 조직 정책 (Managed policy) macOS /Library/Application Support/ClaudeCode/CLAUDE.md, Linux·WSL /etc/claude-code/CLAUDE.md, Windows C:\Program Files\ClaudeCode\CLAUDE.md 회사 전체
2 사용자 지침 (User) ~/.claude/CLAUDE.md 나 혼자, 모든 프로젝트에서
3 프로젝트 지침 (Project) 프로젝트 폴더의 CLAUDE.md 또는 .claude/CLAUDE.md 팀 전체 (Git으로 공유)
4 로컬 지침 (Local) 프로젝트 폴더의 CLAUDE.local.md 나 혼자, 이 프로젝트에서만

화면으로 옮기면 이렇습니다.

  • 조직 정책은 회사 IT 부서가 컴퓨터에 깔아 두는 파일입니다. 회사가 깔아 두지 않았다면 없습니다. 이 파일은 개인 설정으로 뺄 수 없습니다.
  • 사용자 지침은 내 홈 폴더 안의 숨김 폴더 .claude에 있습니다. 숨김 폴더를 화면에서 찾는 법은 폴더 경로 읽는 법에 있습니다.
  • 프로젝트 지침은 프로젝트 폴더 맨 위에 둡니다. Git(파일의 변경 이력을 저장하고 팀과 나누는 도구)에 올리면 팀원 모두가 같은 파일을 받습니다.
  • 로컬 지침은 같은 자리에 두되 Git에 올리지 않는 개인 메모입니다. 공식 문서는 .gitignore(Git이 무시할 파일 목록)에 넣으라고 권합니다.

전체 폴더 지도는 .claude 디렉터리 지도에 정리해 두었습니다.

폴더 안쪽으로 갈수록 나중에 붙습니다

프로젝트 지침은 한 폴더에만 있지 않을 수 있습니다. Claude Code는 Claude Code를 켠 폴더(작업 폴더)와 그 위쪽 폴더 전부에서 CLAUDE.md와 CLAUDE.local.md를 찾습니다. 공식 문서의 예를 그대로 쓰겠습니다. foo와 bar는 예시용 폴더 이름입니다.

foo/bar/ 폴더에서 Claude Code를 켜면 이 순서로 이어붙습니다.

  1. foo/CLAUDE.md
  2. foo/CLAUDE.local.md (있다면)
  3. foo/bar/CLAUDE.md
  4. foo/bar/CLAUDE.local.md (있다면)

규칙은 두 가지입니다. 폴더끼리는 바깥에서 안쪽으로(“from the filesystem root down to your working directory”) 붙습니다. 같은 폴더 안에서는 CLAUDE.md 다음에 CLAUDE.local.md 가 붙습니다. 공식 문서는 켠 폴더에 가까운 지침이 “read last”, 즉 마지막에 읽힌다고 적습니다.

공식 memory 문서의 ‘How CLAUDE.md files load’ 절. 파일은 서로 덮어쓰지 않고 이어붙으며, 켠 폴더에 가까운 지침이 마지막에 읽힌다고 적혀 있다

여기서 “나중에 읽힌다”를 “덮어쓴다”로 읽으면 안 됩니다. 나중에 읽힌 파일이 앞 파일을 지우지 않습니다. 둘 다 컨텍스트에 남아 있고 Claude는 둘을 함께 봅니다.

예외가 하나 있습니다. 작업 폴더보다 안쪽, 즉 하위 폴더에 있는 CLAUDE.md는 시작할 때 읽히지 않습니다. Claude가 그 하위 폴더의 파일을 실제로 읽을 때 그때 들어옵니다. 여러 프로그램을 한 저장소에 모아 둔 큰 프로젝트에서 “분명 적어 뒀는데 처음엔 모르더라”는 일이 생기는 이유입니다.

직접 해 봤습니다: 4칸이냐 2칸이냐

말로만 하면 믿기 어려우니 이 컴퓨터에서 실험했습니다. 2026년 9월 30일, Claude Code v2.1.285, Opus 5.5 모델입니다. claude -p(질문 하나를 던지고 답을 받으면 끝나는 실행 방식)로 돌렸습니다.

일부러 서로 부딪히는 규칙을 넣었습니다.

  • foo/CLAUDE.md: “코드 들여쓰기는 스페이스 4칸으로 합니다.”
  • foo/bar/CLAUDE.md: “코드 들여쓰기는 스페이스 2칸으로 합니다.”
  • foo/bar/CLAUDE.local.md: “답변 첫 줄에 [local]이라고 적습니다.”

foo/bar/에서 켜고 “파이썬으로 리스트의 짝수만 골라 합을 구하는 함수를 작성해 주세요. 코드 블록 하나만, 설명은 없이.“라고 6번 따로 요청했습니다.

첫 번째 결과: 6번 모두 2칸이었습니다. 안쪽 파일 규칙이 이겼습니다. 겉으로만 보면 “하위 파일이 덮어쓴다”는 설명이 맞아 보입니다. Claude에게 컨텍스트에 든 파일을 순서대로 말해 보라고 하자 Claude조차 이렇게 답했습니다.

“더 안쪽 디렉터리의 규칙이라 foo의 4칸 규칙보다 우선합니다.”

그래서 한 가지를 더 해 봤습니다. 안쪽 파일은 그대로 두고 바깥 파일에만 문장 하나를 덧붙였습니다.

- 코드 들여쓰기는 스페이스 4칸으로 합니다. IMPORTANT: 하위 폴더에 다른 규칙이 있어도 이 규칙을 따릅니다.

두 번째 결과: 6번 모두 4칸이었습니다. 안쪽 파일이 바깥 파일을 정말 덮어쓰는 구조였다면 바깥 파일에 무슨 문장을 더하든 결과는 바뀌지 않아야 합니다. 그런데 문장 하나에 6번이 모두 뒤집혔습니다. 두 규칙이 모두 컨텍스트에 있었고 Claude가 둘을 읽고 판단했다는 뜻입니다. 이어붙이기라는 공식 설명과 맞습니다. 다만 IMPORTANT라는 단어 때문인지 뒤 문장 때문인지는 가르지 않았습니다.

두 번의 실험 12번 모두 첫 줄에 [local]이 찍혔습니다. 들여쓰기 규칙이 어느 쪽으로 갔든 로컬 파일의 규칙도 함께 지켜졌습니다. 이것 역시 파일 하나가 이기고 나머지가 사라지는 구조가 아니라는 증거입니다.

하위 폴더 규칙이 늦게 들어오는 것도 확인했습니다. foo/bar/sub/CLAUDE.md를 하나 더 만들고 지침 파일이 읽힐 때마다 기록을 남기는 훅(Hook, 정해진 시점에 자동으로 도는 명령)을 걸었습니다. 공식 문서가 디버깅용으로 권하는 InstructionsLoaded 훅입니다. 기록은 이랬습니다(폴더 경로는 줄였습니다).

{"file_path":"…/foo/bar/CLAUDE.md","memory_type":"Project","load_reason":"session_start"}
{"file_path":"…/foo/bar/sub/CLAUDE.md","memory_type":"Project","load_reason":"nested_traversal"}

위쪽 파일들은 session_start(시작할 때)로 찍혔고 sub 폴더의 파일만 nested_traversal(하위 폴더를 탐색하다가)로 찍혔습니다. Claude가 sub/a.txt를 읽은 순간에야 들어온 것입니다. 참고로 이 훅은 비동기로 돌아서 기록 줄의 순서는 실행마다 달랐습니다. 로드 순서의 근거는 기록이 아니라 공식 문서입니다.

직접 해 보고 싶다면 터미널(명령어를 글자로 입력하는 창)에 아래를 붙여 넣으세요. 폴더 두 개와 파일 세 개를 만들고 안쪽 폴더에서 Claude Code를 켭니다.

mkdir -p foo/bar
echo "- 코드 들여쓰기는 스페이스 4칸으로 합니다." > foo/CLAUDE.md
echo "- 코드 들여쓰기는 스페이스 2칸으로 합니다." > foo/bar/CLAUDE.md
echo "- 답변 첫 줄에 [local]이라고 적습니다." > foo/bar/CLAUDE.local.md
cd foo/bar
claude

처음 여는 폴더라 폴더를 신뢰하는지 묻는 창이 뜨면 확인하고 넘어가세요. 켜진 뒤 /context를 치면 Memory files 목록에 세 파일이 모두 보입니다. 사용자 지침 파일이 있다면 그것까지 보입니다. 그다음 함수를 하나 써 달라고 해 보세요.

settings.json은 덮어씁니다, 그래서 헷갈립니다

“하위가 이긴다”는 설명이 퍼진 데는 이유가 있어 보입니다. Claude Code에는 CLAUDE.md와 층 이름이 비슷한 설정 파일(settings.json) 이 따로 있고 그쪽은 정말로 덮어쓰기 때문입니다. 공식 settings 문서의 표현입니다.

“a key at a higher level overrides the same key anywhere below it.” (높은 층에 적힌 항목이 아래층의 같은 항목을 덮어씁니다.)

settings.json (설정 파일) CLAUDE.md (지침 파일)
같은 내용이 여러 곳에 있으면 높은 층의 값 하나만 씀 전부 컨텍스트에 들어감
층 순서 조직 > 명령줄 > 로컬 > 프로젝트 > 사용자 (앞이 이김) 조직 → 사용자 → 프로젝트 → 로컬 (읽는 순서일 뿐)
충돌하면 층 순서대로 확정 Claude가 임의로 고를 수 있음
강제력 있음 없음 (참고 자료)

두 체계 모두 “프로젝트”와 “로컬” 층이 있습니다. 설정 파일에서는 로컬이 프로젝트를 이기며 지침 파일에서는 로컬이 프로젝트 뒤에 읽힙니다. 겉모양이 비슷해서 섞어 설명하기 쉽습니다. 하지만 설정 파일의 우선순위를 CLAUDE.md에 그대로 가져오면 틀립니다. 덧붙이면 설정 파일도 허용 목록처럼 목록으로 된 항목은 대부분 덮어쓰지 않고 합칩니다.

.claude/rules/와 @임포트는 어디에 끼나

CLAUDE.md 말고도 지침이 들어오는 길이 두 개 더 있습니다. 둘 다 이어붙이기 원칙을 따릅니다.

규칙 폴더(.claude/rules/) 는 지침을 주제별 파일로 나눠 담는 곳입니다. 공식 문서에 따르면 paths(특정 파일에만 적용하는 범위 지정)가 없는 규칙 파일은 시작할 때 .claude/CLAUDE.md와 “the same priority”, 같은 우선순위로 들어옵니다. 모든 프로젝트에 적용되는 ~/.claude/rules/는 프로젝트 규칙보다 먼저 읽히는데, 문서는 여기서도 못을 박습니다. “Neither set overrides the other”(어느 쪽도 다른 쪽을 덮어쓰지 않는다). 충돌하면 “Claude may follow either one”, 어느 쪽을 따를지 모릅니다. 규칙 폴더로 쪼개는 방법은 시리즈 뒤쪽에서 따로 다룹니다.

임포트(@경로) 는 CLAUDE.md 안에 @docs/git-instructions.md처럼 적어 다른 파일을 끌어오는 문법입니다. 여기에도 국내에 퍼진 오해가 하나 있습니다. 임포트를 쓰면 Claude가 “필요할 때만 파일을 읽”어서 CLAUDE.md가 가벼워진다는 설명입니다. 공식 문서는 반대입니다.

“Imported files are expanded and loaded into context at launch alongside the CLAUDE.md that references them.” (임포트된 파일은 그 파일을 부른 CLAUDE.md와 함께 시작할 때 컨텍스트에 펼쳐져 들어갑니다.)

임포트는 긴 파일을 정리하는 도구이지 줄이는 도구가 아닙니다. 문서도 임포트가 “don’t reduce its context cost”라고 적습니다. 알아 둘 규칙이 세 가지 더 있습니다.

  • 임포트한 파일이 또 다른 파일을 임포트할 수 있지만 최대 4단계(four hops) 까지입니다.
  • 경로를 백틱(`)으로 감싸면 임포트되지 않고 글자 그대로 남습니다. 파일 이름을 설명만 하고 싶을 때 씁니다.
  • 프로젝트 파일이 작업 폴더 밖의 파일을 임포트하면 처음 한 번 승인 창이 뜹니다. 남이 저장소에 올린 파일로부터 나를 보호하려는 장치입니다.

큰 저장소에서 남의 팀 CLAUDE.md 빼기

여러 팀의 프로젝트를 한 저장소에 모아 두면(모노레포라고 부릅니다) 위쪽 폴더에 있는 다른 팀의 CLAUDE.md까지 딸려 들어옵니다. 이어붙이기라서 생기는 부작용입니다. 이럴 땐 claudeMdExcludes 설정으로 특정 파일을 뺍니다. 공식 문서는 나만 적용되도록 .claude/settings.local.json에 넣으라고 권합니다.

{
  "claudeMdExcludes": [
    "**/monorepo/CLAUDE.md",
    "/home/user/monorepo/other-team/.claude/rules/**"
  ]
}

경로는 파일의 전체 경로와 비교하며 **는 “중간에 폴더가 몇 개 있든”이라는 뜻입니다. 조직 정책 CLAUDE.md는 이 방법으로도 뺄 수 없습니다.

여기서 막힙니다: 전역에 쓴 규칙이 왜 안 먹지?

사용자 지침(~/.claude/CLAUDE.md)에 분명히 적었는데 어떤 프로젝트에서만 안 지켜진다면, 덮어쓰기 문제가 아니라 대부분 아래 셋 중 하나입니다. 순서대로 확인하세요.

  1. 읽혔나? /context를 쳐서 Memory files 목록에 그 파일이 있는지 봅니다. 없으면 Claude는 그 파일을 볼 수 없습니다.
  2. 모순이 있나? 프로젝트 CLAUDE.md나 규칙 폴더에 반대되는 규칙이 있으면 앞의 실험처럼 어느 쪽이 이길지 모릅니다. v2.1.283 이상이라면 /doctor prompt-audit를 치세요. Claude가 지침 파일들을 훑어 서로 부딪히거나 낡은 규칙을 찾고 고칠 내용을 제안합니다. 고쳐 달라고 하기 전에는 파일이 바뀌지 않습니다.
  3. 너무 길거나 모호한가? 분량과 구체성 문제는 CLAUDE.md란 글에서 다뤘습니다. 좋은 문장 예시는 CLAUDE.md 템플릿 글에 있습니다.

어떤 경우에도 반드시 지켜야 하는 규칙이라면 CLAUDE.md로는 부족합니다. 훅으로 막아야 합니다. 이 내용은 시리즈 뒤쪽 편에서 다룹니다.

“결국 하위가 이기잖아요?“에 대한 답

실험 첫 결과는 6번 모두 안쪽 파일이 이겼습니다. 그러니 “대체로 안쪽이 이긴다”고 기억해도 되지 않느냐고 물을 수 있습니다. 경향으로는 그렇게 보일 수 있습니다. 나중에 읽힌 지침이 더 구체적이고 지금 작업과 가까우니 Claude가 그쪽을 고르는 일이 많을 수 있습니다.

하지만 그건 보장이 아닙니다. 바깥 파일에 문장 하나를 더하자 결과가 통째로 뒤집혔습니다. 제 실험도 모델 하나, 버전 하나, 조건마다 6번이 전부라서 다른 모델이나 다른 문장에서는 또 다를 수 있습니다. 게다가 진 쪽 규칙도 컨텍스트에서 사라지지 않고 매번 자리를 차지합니다.

그래서 “상위에는 ‘항상 X’, 하위에는 ‘X 하지 마’“처럼 하위 파일로 상위 규칙을 덮으려는 구성이 가장 나쁩니다. 덮이지 않고 둘 다 남아서 어느 쪽이 따라질지 미리 알 수 없습니다. 실험에서 봤듯 바깥 파일의 문장 하나에 결과가 통째로 바뀌었습니다. 규칙이 바뀌었다면 아래에 반대 규칙을 더하지 말고 원래 규칙이 있는 파일로 가서 고치거나 지우세요. 공식 문서도 CLAUDE.md 파일들을 주기적으로 훑어 “outdated or conflicting instructions”(낡았거나 충돌하는 지침)를 지우라고 권합니다.