Claude Code와 함께 로케일 목록 페이지를 만드는 중입니다. 목록 검색 작업이 절반쯤 진행됐는데, 저장된 페이지에서 제목 아래 설명이 잘못된 것을 발견했습니다. 수정은 2분이면 되지만, 미완성 검색 작업과 섞지 않고 따로 확인하고 싶습니다.

같은 저장소 안에서 두 번째 작업에 별도의 작업 폴더를 제공하고, 그곳에서 Claude Code 세션을 따로 연 뒤, 마지막에 헷갈리지 않게 결과를 저장하는 방법을 살펴봅니다. 폴더를 하나 더 만든다고 작업 속도가 빨라지는 것은 아닙니다. 두 작업의 파일이 뒤섞이지 않도록 분리하는 것이 목적입니다.

작업 폴더 하나로 부족할 때

학습 프로젝트 locale-guide는 로케일 목록을 보여 주는 브라우저 페이지입니다. 현재 폴더에서는 작업 A인 검색 기능을 진행 중이고, feature/search 브랜치에 미완성 변경 사항이 하나 있습니다.

git status --short
M app.js

이 변경 사항을 잃어서는 안 되고, 아직 완성된 결과로 볼 수도 없습니다. 그런데 검색과 무관한 작업 B가 생겼습니다. main에 저장된 버전의 index.html에서 설명 문구를 고쳐야 합니다.

가장 먼저 떠오르는 방법은 두 번째 터미널을 열고 같은 폴더에서 claude를 하나 더 실행하는 것입니다. 대화는 별개지만 파일은 똑같습니다. 두 작업자가 같은 부분을 수정하면 변경 사항이 섞일 수 있습니다. 이 간단한 예에서는 설명과 검색 기능이 서로 다른 파일에 있지만, 두 세션은 모두 미완성 프로젝트를 공유합니다. 브랜치를 전환하려 해도 현재 변경 사항을 먼저 살펴야 합니다.

해결책은 작업 B에 별도의 작업 공간을 주는 것입니다. Git에는 같은 저장소의 작업 폴더를 하나 더 두는 worktree가 있고, Claude Code에는 이 폴더를 준비하고 그 안에서 세션을 바로 시작하는 --worktree 플래그가 있습니다. 먼저 작동 원리를 살펴보고, 그다음 플래그를 알아보겠습니다.

저장소 하나와 작업 폴더 세 개. 각 폴더에는 main, feature-a, feature-b 브랜치가 있습니다
저장소 하나에 작업 폴더가 여러 개 있고, 각 폴더에는 자체 브랜치가 있습니다. 그림의 이름은 임의로 정했습니다. 여기서는 작업 폴더 두 개와 브랜치 세 개(main, feature/search, fix/label)를 사용합니다.

먼저 짚고 넘어갈 점이 있습니다. 모든 작업에 이 방식이 필요한 것은 아닙니다. 작업 트리가 깨끗하고 수정이 짧다면 폴더를 하나 더 만드는 수고만 늘어납니다. 한 폴더에서 작업을 번갈아 해도 전혀 문제없습니다.

브랜치, 작업 폴더, 세션

세 가지를 동시에 다루다 보면 서로 혼동하기 쉽습니다.

구분포함 내용위치
브랜치커밋과 기록 흐름을 가리키는 포인터저장소 안에 있으며 모든 작업 폴더가 공유
작업 폴더(worktree)현재 작업 중인 파일과 커밋을 위해 스테이징한 내용디스크에 있으며 폴더마다 별도
세션에이전트와의 대화 및 컨텍스트Claude Code 안

두 번째 터미널에 대한 답도 여기서 나옵니다. 새 세션은 대화를 분리하지만 파일은 분리하지 않습니다. 파일을 나누려면 작업 폴더가 하나 더 필요합니다.

저장소 하나, 작업 폴더 두 개. 각 폴더에는 브랜치와 Claude Code 세션이 따로 있습니다저장소 하나locale-guide브랜치feature/searchClaude Code 세션작업 A, 검색브랜치fix/labelClaude Code 세션작업 B, 설명작업 폴더locale-guide작업 폴더locale-guide-label커밋하지 않은 변경 사항은 각 작업 폴더에 남습니다
기록과 브랜치 목록은 공유하고, 파일과 세션은 분리됩니다.

기록과 브랜치는 공유됩니다. 두 폴더가 같은 저장소에 연결되어 있기 때문입니다. Git 설정도 기본적으로 공유되지만, worktree별 별도 설정도 지원합니다. 반면 작업 파일과 커밋을 위해 스테이징한 변경 사항은 폴더마다 다릅니다. 첫 번째 폴더에서 커밋하지 않은 검색 작업은 두 번째 폴더에 저절로 나타나지 않습니다.

일반적으로 같은 브랜치를 두 폴더에서 동시에 열 수는 없습니다. Git이 거부하면서 해당 브랜치를 이미 사용하는 폴더를 알려 줍니다.

fatal: 'fix/label' is already used by worktree at '/projects/locale-guide-label'

기준 상태를 선택하세요

학습 예제에서는 저장소가 이미 만들어져 있고 커밋이 하나 이상 있습니다. 로컬 main 브랜치와 feature/search 브랜치도 있습니다. 두 브랜치는 아직 같은 커밋을 가리키며, 검색 기능은 커밋하지 않은 변경 사항으로만 존재합니다. 기본 폴더에서 명령어 세 개로 현재 상태를 확인해 보겠습니다.

git status --short        # 현재 저장하지 않은 변경 사항
git branch --show-current # 기본 폴더의 브랜치
git log -1 --oneline main # main의 최신 커밋
 M app.js
feature/search
d5ec405 add locale guide page

설명을 검색 작업과 별도로 수정하려면 main을 선택합니다. 작업 B에는 현재 검색 상태가 아니라 저장된 페이지 버전이 필요합니다. 여기서 말하는 것은 컴퓨터의 로컬 main입니다. 원격 저장소의 같은 이름 브랜치와 일치하지 않을 수 있고, 이 명령어는 원격에서 아무것도 가져오지 않습니다.

두 번째 작업에 첫 번째 작업의 결과가 필요하다면, 어떤 저장된 커밋을 사용할지 먼저 정한 다음 그 커밋을 기준으로 폴더를 만드세요. 일반적인 git worktree add는 커밋하지 않은 변경 사항을 자동으로 옮기지 않습니다. 파일을 별도로 복사하거나 환경 준비 도구를 쓰는 것은 별개의 작업입니다.

두 번째 작업 폴더 만들기

locale-guide 폴더에서 실행합니다.

git worktree add -b fix/label ../locale-guide-label main

왼쪽에서 오른쪽 순서로 읽으면 됩니다. 새 fix/label 브랜치를 만들고, ../locale-guide-label 경로에 작업 폴더를 만든 다음, 기준점으로 main을 사용합니다. 마지막 인수 덕분에 기준 브랜치를 명시적으로 선택할 수 있습니다. 이 인수가 없다면 Git은 현재 feature/search 브랜치의 HEAD 커밋을 사용하지만, 커밋하지 않은 변경 사항은 가져오지 않습니다. 이 예에서는 두 브랜치가 아직 같은 커밋을 가리키므로 파일도 동일하게 만들어집니다. 검색 작업을 커밋하고 나면 기준 선택이 결과에 영향을 줍니다. Git은 대략 다음과 같이 응답합니다.

Preparing worktree (new branch 'fix/label')
HEAD is now at d5ec405 add locale guide page

이제 결과를 확인합니다. -C 플래그를 사용하면 해당 폴더로 이동하지 않고도 Git이 그곳에서 명령어를 실행합니다.

git worktree list
git -C ../locale-guide-label branch --show-current
git -C ../locale-guide-label status --short

아래는 학습용 출력 예시입니다. 실제 경로는 환경마다 다릅니다.

/projects/locale-guide        d5ec405 [feature/search]
/projects/locale-guide-label  d5ec405 [fix/label]

fix/label

목록에는 두 폴더와 각 폴더의 브랜치가 표시됩니다. 기본 폴더는 미완성 검색 작업이 있는 feature/search에 그대로 있고, 새 폴더는 fix/label을 사용합니다. 두 번째 폴더에서 status 명령어는 아무것도 출력하지 않습니다. 작업 트리가 깨끗하다는 뜻이며, 바로 이것이 우리가 원한 상태입니다.

경로나 브랜치 이름을 사용할 수 없으면 Git이 거부하고 already exists 또는 is already used by worktree 같은 이유를 알려 줍니다. worktree 목록과 브랜치, 해당 폴더의 내용을 확인하세요. 이전에 직접 실행한 작업이나 다른 작업의 결과일 수 있습니다. --force를 무작정 추가하지 말고, 무엇이 이미 존재하는지, 필요한 것인지 먼저 확인하세요.

Claude Code에서 두 번째 작업 열기

locale-guide-label을 별도의 IDE 창에서 열거나, 새 터미널에서 해당 폴더로 이동한 뒤 claude를 실행하세요. 새 세션은 작업 A에 대해 아무것도 모릅니다. 괜찮습니다. 이 세션에는 자체 컨텍스트만 있으면 됩니다.

예상 폴더: locale-guide-label, 브랜치: fix/label.
먼저 실제 폴더와 브랜치를 확인하세요. 다르면 멈추세요.
index.html을 읽으세요.
제목 아래 설명을 "로케일 목록: 코드, 언어, 국가"로 바꾸세요.
파일의 다른 내용은 변경하지 말고, 변경 사항을 보여 주세요.
첫 수정 전에 폴더를 확인하세요

Claude Code가 파일을 수정하기 전에 작업 폴더와 현재 브랜치를 말해 달라고 요청하고, 답변이 의도한 내용과 일치하는지 확인하세요. 엉뚱한 폴더에서 실행된 에이전트도 올바른 폴더에서처럼 자신 있게 작업합니다.

수정 후 두 터미널에서 각각 git status와 git diff를 확인하세요. 두 번째 폴더에서는 index.html의 설명만 바뀌고, 첫 번째 폴더에는 기존 app.js 수정 사항이 남아 있어야 합니다. status는 파일 이름만 보여 줄 뿐, 파일 내용이 보존되었는지는 증명하지 않습니다. 정확히 비교하려면 확인하는 동안 검색 작업을 잠시 멈추세요. 기본 폴더는 해당 터미널에서 확인하고, 격리된 세션의 에이전트에게 그쪽으로 이동하라고 시키지 마세요. 페이지도 반드시 두 번째 폴더에서 열어야 합니다. 그렇지 않으면 이전 설명이 보입니다.

더 간단한 방법도 있습니다. claude --worktree label-fix 명령어는 작업 폴더를 만들고 그 안에서 세션을 시작합니다. 현재 문서에 따르면 폴더는 저장소 안의 .claude/worktrees/label-fix/에 만들어지고, 브랜치 이름은 worktree-label-fix가 됩니다. 기준점은 현재 커밋이 아니라 원격 저장소의 기본 브랜치(보통 main)입니다. 원격 저장소가 설정되어 있지 않으면 현재 로컬 커밋이 기준점이 됩니다. 따라서 위 명령어처럼 main을 명시한 경우와는 다릅니다. 단순한 프로젝트에서는 결과가 같은 경우가 많습니다. 기본값은 설정으로 바꿀 수 있으니 사용 중인 버전의 문서를 확인하세요.

기준점이 적절하고 작업 공간을 빠르게 분리하고 싶을 때 이 플래그가 편리합니다. 이미 만든 폴더에서 다시 실행하지 마세요. 폴더가 하나 더 생깁니다. 또한 .claude/worktrees/를 .gitignore에 추가하는 편이 좋습니다. 그렇지 않으면 새 폴더의 내용이 기본 폴더에 추적되지 않는 파일로 나타납니다.

공유되는 것

별도 폴더가 분리해 주는 범위는 생각보다 좁습니다.

분리됨공유됨분리되지 않음
작업 파일, 커밋 준비 내용, 폴더별 현재 브랜치기록, 모든 브랜치, 저장소 설정, 원격 저장소 주소로컬 서버 포트, 외부 데이터베이스, 클라우드 서비스, 다른 디스크 영역에 대한 프로세스 접근

세 번째 열의 내용은 자주 놓치는 핵심입니다. Worktree는 Git 파일을 분리할 뿐, 컴퓨터 자체를 격리하지 않습니다. 같은 포트를 사용하는 로컬 서버 두 개는 함께 실행될 수 없고, 설정에 같은 외부 데이터베이스가 지정되어 있다면 두 폴더의 요청은 모두 그곳으로 전송됩니다. Claude Code가 별도 폴더에서 실행하는 확인 작업도 해당 폴더를 시스템 전체의 샌드박스로 만들지는 않습니다.

두 번째 폴더에는 선택한 커밋의 파일이 들어갑니다. 의존성과 로컬 설정을 Git에 저장하지 않는다면 대개 환경을 별도로 준비해야 합니다. 도구를 사용해 준비 과정을 자동화할 수도 있습니다. .env를 무작정 복사하지 마세요. 같은 인증 정보로 인해 두 실행 환경이 동일한 서비스에 연결될 수 있습니다. 이 정적 로케일 목록 페이지에는 서버나 비밀 정보가 필요하지 않습니다. 페이지를 파일로 열면 됩니다.

결과를 저장하고 옮기기

B 폴더에서 브라우저로 설명을 확인하고 git diff를 살펴본 다음, 필요한 파일만 커밋하세요.

git add index.html
git diff --cached
git commit -m "fix: correct locale list label"

커밋하기 전에 필요한 변경 사항만 스테이징했는지 확인하세요. git diff --cached에 다른 변경 사항이 있다면 먼저 내용을 확인하세요.

커밋은 공유 저장소에 기록되므로 기본 폴더에서도 확인할 수 있습니다. 하지만 자동으로 main이나 feature/search에 들어가지는 않습니다. 자체 브랜치에 남아 있으며, 병합 여부를 결정할 때까지 기다립니다.

작업 A가 완료되었거나 적어도 저장되어 있고 기본 폴더가 깨끗할 때만 결과를 옮기세요. 검색 작업이 끝나지 않은 상태에서 main으로 전환할 필요는 없습니다. 먼저 해당 작업을 정리하세요. 기본 폴더가 깨끗하다면 다음을 실행합니다.

git checkout main
git merge fix/label
Fast-forward
index.html | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)

이 출력은 fix/label을 만든 뒤 main이 변경되지 않은 경우에 해당합니다. Git이 충돌을 알리면 멈추고 병합 규칙에 따라 해결하세요. 자세한 내용은 "Git 브랜치와 병합" 글에서 다룹니다. 병합 후 페이지를 다시 열어 설명은 새 내용으로 바뀌고 로케일 목록은 그대로인지 확인하세요. feature/search 브랜치는 이 작업으로 업데이트되지 않았습니다. 검색을 다시 이어가기 전에 main의 수정을 이 브랜치에도 옮길지 별도로 결정하세요.

불필요한 폴더 정리하기

먼저 두 번째 폴더의 세션과 그곳에서 실행한 모든 항목을 닫으세요. 그런 다음 필요한 내용이 남아 있는지 확인합니다.

git -C ../locale-guide-label status --short --ignored

수정되거나 새로 생긴 파일은 바로 표시되고, --ignored 플래그를 사용하면 무시된 파일도 볼 수 있습니다. 무시된 파일에는 로컬 설정이나 메모가 들어 있는 경우가 많습니다. 결과가 올바른 브랜치에 저장된 것을 확인했다면 기본 폴더에서 해당 폴더를 제거하세요.

git worktree remove ../locale-guide-label
git worktree list

추적 중인 파일이 수정되었거나 무시 대상이 아닌 새 파일이 있으면 Git은 대개 폴더 삭제를 거부합니다.

fatal: '../locale-guide-label' contains modified or untracked files, use --force to delete it

메시지에 나온 조언을 첫 행동으로 바로 실행하지 마세요. 파일을 확인하고 필요한 내용을 저장하세요. 커밋하지 않은 데이터는 삭제 후 Git으로 복구하지 못할 수 있습니다. Git의 삭제 거부를 완전한 보호 장치로 여겨서도 안 됩니다. 무시된 파일은 --force 없이도 삭제될 수 있으므로 앞에서 따로 확인했습니다.

헷갈리기 쉬운 점이 하나 더 있습니다. Git 명령어는 작업 폴더를 삭제하지만 브랜치는 삭제하지 않습니다. 따라서 fix/label은 git branch 목록에 그대로 남습니다. 결과가 사라지지 않으니 유용합니다. 브랜치가 더 이상 필요 없고 필요한 내용도 모두 병합한 뒤에 별도로 삭제하세요.

Claude Code의 확인 창은 다른 경로입니다

--worktree로 시작한 세션을 종료하면 Claude Code가 폴더를 확인합니다. 변경 사항이나 새 커밋이 없고 세션에 이름도 없다면 묻지 않고 폴더와 브랜치를 삭제합니다. 작업 내용이 있다면 폴더를 유지할지 삭제할지 묻습니다. 이 확인 창에서 삭제를 선택하면 폴더와 Claude Code가 만든 브랜치, 그 안의 모든 내용이 함께 제거됩니다. 위의 Git 명령어와는 다릅니다. 결과가 필요하다면 "유지"를 선택하고 직접 옮기세요.

탐색기에서 Git을 거치지 않고 폴더를 삭제하지 마세요. 저장소는 해당 폴더가 여전히 있다고 인식하고, worktree 목록에는 이미 사라진 폴더가 남게 됩니다.

Claude Code에서 두 번째 작업 진행하기

전체 흐름은 여섯 단계로 정리할 수 있습니다.

  1. 두 번째 작업을 첫 번째 작업과 구분해 이름 붙이고, 어떤 저장된 상태를 기준으로 시작할지 정합니다.
  2. 기준점을 명시해 작업 폴더를 만들거나 기본값이 괜찮다면 claude --worktree를 실행합니다.
  3. 새 폴더에서 파일을 수정하기 전에 경로와 브랜치를 확인합니다.
  4. 옆 작업의 대화 내용은 빼고 이 작업에 필요한 컨텍스트만 세션에 제공합니다.
  5. 수정한 곳에서 변경 사항을 확인하고 결과를 저장합니다.
  6. 병합 여부를 결정한 뒤에 폴더를 정리합니다.

별도의 폴더가 코드를 검증하거나 작업을 대신 승인해 주지는 않습니다. 각 작업에 전용 파일을 제공할 뿐입니다. 이 예에서는 설명을 별도로 수정하고 확인하는 동안 미완성 검색 작업은 첫 번째 폴더에 그대로 둔 점에서 이점이 드러납니다.

직접 확인해 보세요

두 번째 폴더에 커밋하지 않은 검색 작업이 없습니다. 문제가 생긴 건가요?
아니요. 의도한 동작입니다. 폴더는 작업 A의 현재 파일이 아니라 main의 커밋을 기준으로 만들었습니다. 커밋하지 않은 변경 사항은 원래 폴더에 남습니다.

두 세션을 같은 폴더에서 열었습니다. 작업이 분리되나요?
대화는 분리되지만 파일은 공유됩니다. 두 작업이 같은 부분을 수정하면 변경 사항이 섞일 수 있습니다.

B 브랜치에서 커밋했는데 main에는 설명이 없습니다.
정상입니다. 커밋은 자체 브랜치에 있으며 다른 브랜치를 바꾸지 않습니다. 반영하려면 병합해야 합니다.

두 번째 로컬 서버가 같은 포트에서 실행되지 않습니다.
별도 폴더를 사용해도 포트는 분리되지 않습니다. 다른 포트에서 실행하세요.

Git이 작업 폴더 삭제를 거부했습니다.
거부 이유를 확인하세요. 저장하지 않은 파일 외에도 폴더가 잠겨 있거나 기본 작업 폴더일 수 있습니다. 필요한 내용을 저장하고 상태를 살펴보세요. --force를 무작정 추가하지 마세요.

직접 연습하고 싶다면 커밋이 몇 개 있는 별도의 학습용 저장소에서 해 보세요. 폴더 두 개를 만들고 두 번째 폴더에서만 텍스트를 바꾼 다음, 둘 다 확인하고 불필요한 폴더를 정리하면 됩니다. 서비스나 계정은 필요하지 않습니다.