커밋되지 않은 변경 내용을 복구하는 방법


694

개발 지사에서 커밋되지 않은 변경 사항이 있었으며을 사용하여 git stash변경했습니다. 그러나 이러한 변경 사항 중 매우 중요한 변경 사항이있었습니다. 이러한 변경 사항을 되돌릴 수있는 방법이 있습니까?

또한 이후에 숨김 코드 파일을 일부 변경했습니다.

가능한 경우 새 지점에 대한 숨김 변경 사항을 검색 할 수있는 기회가 있습니까?


7
'stash pop'을 사용해 보셨습니까?
robert

아니요. 사실 저는 git을 처음 사용합니다. 모든 명령을 완전히 인식하지 못했기 때문에 다른 것을 시도하지 않았습니다! 나는 그 변화를 잃고 싶지 않습니다.
Aswathy P Krishnan

33
숨김 변경 사항을 잃지 않으려면 'git stash apply'를 사용해보십시오. 이렇게하면 숨김을 유지하면서 현재 변경 사항이 현재 분기에 적용됩니다. 모든 것이 정상이라면, 숨김을 적용한 후 'git stash drop'을 사용하여 숨김을 삭제할 수 있습니다.
robert

2
@robert 굉장히 복잡한 (초보자에게는) 받아 들여지는 답에 비해 간단한 대답에 감사드립니다.
Saheel Godhane

답변:


1186

쉬운 질문에 대한 쉬운 대답은 git stash apply

변경하려는 지점을 확인한 다음를 클릭하십시오 git stash apply. 그런 다음을 사용 git diff하여 결과를 확인하십시오.

변경 작업이 모두 완료된 후 ( apply모양이 양호하고 더 이상 숨김이 필요하지 않다고 확신 경우) git stash drop이를 사용 하여 제거하십시오.

나는 항상 git stash apply보다는 오히려 사용 하는 것이 좋습니다 git stash pop. 차이점은을 apply다시 시도 apply하거나 쉽게 볼 수 있도록 숨김 을 남기는 것입니다. 숨김 pop을 추출 할 수있는 경우 즉시 압축 drop을 해제하고 갑자기 어딘가에서 추출하려고한다고 생각하면 다른 (다른 지점에서) 또는와 함께 --index또는 일부는 쉽지 않습니다. 당신이 경우 apply, 당신 은 언제 선택할 수 있습니다 drop.

그래도 모두 아주 사소한 방법이며 초보자가 git을 사용하려면 거의 동일해야합니다. (그리고 나머지는 모두 건너 뛸 수 있습니다!)


더 발전되거나 복잡한 작업을 수행하는 경우 어떻게됩니까?

"git stash를 사용하는 방법"은 적어도 3 ~ 4 가지가 있습니다. 위의 "방법 1", "쉬운 방법"입니다 :

  1. 클린 브랜치에서 시작하여 일부 변경 작업을 수행 한 후 잘못된 브랜치에서 수행하고 있음을 깨달았습니다. 지금 변경 한 내용을 다른 지점으로 "이동"하려고합니다.

    이것은 위에서 설명한 쉬운 경우입니다. 실행하십시오 git stash save(또는 평범 git stash하고 똑같은 것). 다른 지점을 확인하고를 사용하십시오 git stash apply. 이것은 git의 강력한 병합 메커니즘을 사용하여 이전 변경 사항에서 git을 병합합니다. 조심스럽게 결과를 검사 (와 git diff) 그들처럼 당신이 있는지, 그리고 당신이 할 경우, 사용은 git stash drop마리화나를 드롭. 끝났습니다!

  2. 일부 변경 사항을 시작하고이를 저장했습니다. 그런 다음 다른 지점으로 전환하여 더 많은 변경을 시작했으며, 보관 된 지점을 잊어 버렸습니다.

    이제 이러한 변경 사항 을 유지하거나 이동 하고 숨김을 적용 하려고합니다 .

    변경 사항의 "스택"을 만들 때 실제로 git stash save다시 할 수 있습니다 git stash. 그렇게하면 두 개의 스 태쉬가 있는데, 하나는 방금 호출했지만 다른 하나는 철자 stash할 수 있습니다 . 그들 모두를 보려면 언제라도 사용하십시오 . 최신은 항상 가장 낮은 번호입니다. 을하면 최신 항목과 스택 맨 위로 이동 한 항목이 삭제 됩니다. 당신이 더 있었다면, 있던 사람은 된다 , 등등.stash@{0}stash@{1}git stash listgit stash dropstash@{1}stash@{2}stash@{1}

    apply다음과 drop같이 특정 숨김 을 수행 할 수 있습니다 git stash apply stash@{2}. 특정 숨김을 삭제하면 숫자가 높은 것만 다시 번호가 매겨집니다. 다시 말하지만, 숫자가없는 것도 stash@{0}.

    당신이 숨겨 놨다을 많이 쌓아 경우가 상당히 지저분 얻을 수 있습니다 (내가 원하는 숨김이었다 stash@{7}또는 그 것이었다는 stash@{4}?, 난 그냥 서로를 밀어 지금있는 거 (8) 5 기다립니다?). 브랜치에는 이름이 있으며 cleanup-attempt-in-December나보다 더 많은 것을 의미 하기 때문에 개인적으로 이러한 변경 사항을 새 브랜치로 이전하는 것을 선호합니다 stash@{12}. (이 git stash명령은 선택적 저장 메시지를 취하는데 도움이 될 수 있지만 어쨌든 내 모든 숨김은이라는 이름으로 시작 WIP on branch됩니다.)

  3. (엑스트라 고급) 당신이 사용했던 git stash save -p, 또는주의 git add및 / 또는 -ed git rm실행하기 전에 코드의 -ed 특정 비트를 git stash save. 스 태쉬 된 인덱스 / 스테이징 영역에 하나의 버전이 있고 작업 트리에 다른 (다른) 버전이 있습니다. 이 모든 것을 보존하고 싶습니다. 이제는을 사용 git stash apply --index하고 때로는 실패합니다.

    Conflicts in index.  Try without --index.
    
  4. git stash save --keep-index"확약 대상"을 테스트하기 위해 사용 하고 있습니다. 이것은이 답변의 범위를 벗어납니다. 대신 이 다른 StackOverflow 답변을 참조하십시오 .

복잡한 경우에는 현재 변경 사항을 커밋하여 (깨끗한 경우 새 브랜치에서) "깨끗한"작업 디렉토리에서 먼저 시작하는 것이 좋습니다. 그런 식으로 당신이 그것들을 적용하고있는 "어딘가"에는 아무것도없고, 당신은 막힌 변화를 시도 할 것입니다 :

git status               # see if there's anything you need to commit
                         # uh oh, there is - let's put it on a new temp branch
git checkout -b temp     # create new temp branch to save stuff
git add ...              # add (and/or remove) stuff as needed
git commit               # save first set of changes

이제 당신은 "깨끗한"출발점에 있습니다. 아니면 다음과 같이 진행될 수 있습니다.

git status               # see if there's anything you need to commit
                         # status says "nothing to commit"
git checkout -b temp     # optional: create new branch for "apply"
git stash apply          # apply stashed changes; see below about --index

기억해야 할 것은 "스 태쉬 (stash)" 커밋 (commit)이며, "브랜치 (branch)"가 아닌 약간 "재미 있고 이상한"커밋 일뿐입니다. apply당신이 지금 어디에 있든지 조작 (가) 변경 커밋 무슨 외모, 그리고 시도는 그것을 반복합니다. 은신처는 여전히 거기에있을 것입니다 ( apply계속 유지). 더 많이 보거나 이것이 잘못된 장소인지 결정 apply하고 다르게 또는 다른 방법으로 다시 시도하십시오.


은신처가있을 때마다 은신처에 git stash show -p있는 단순화 된 버전을 볼 수 있습니다 . (이 단순화 된 버전 은 별도로 복원되는 저장된 인덱스 변경이 아닌 "최종 작업 트리"변경 사항 만 살펴 봅니다 --index.) git stash apply없이 명령 은 작업 디렉토리에서 동일한 변경을 수행 --index하려고합니다 .

이미 약간의 변경이 있더라도 마찬가지입니다. 이 apply명령은 수정 된 작업 디렉토리에 숨김을 적용 하거나 최소한 적용하려고합니다. 예를 들어 다음과 같이 할 수 있습니다.

git stash apply stash      # apply top of stash stack
git stash apply stash@{1}  # and mix in next stash stack entry too

여기서 "적용"순서를 선택하여 특정 순서로 적용 할 특정 숨김을 선택하십시오. 그러나 기본적으로 "git merge"를 수행 할 때마다 그리고 병합 문서가 경고 할 때 다음과 같이주의하십시오.

사소한 커밋되지 않은 변경 사항으로 git merge를 실행하지 않는 것이 좋습니다.

클린 디렉토리로 시작하여 여러 git apply작업을 수행하는 경우 쉽게 git reset --hard제거 할 수 apply있습니다. 클린 상태로 돌아가고 작업을 변경하는 데 사용합니다 . (따라서 복잡한 작업을 위해 깨끗한 작업 디렉토리에서 시작하는 것이 좋습니다.)


최악의 경우는 어떻습니까?

Advanced Git Stuffs를 많이하고 있고 숨겨두고 싶다고 가정 해 봅시다 git stash apply --index.하지만 저장 한 후 저장 --index지점을 너무 많이 분기했기 때문에 저장된 숨김을 적용 할 수 없습니다 .

이것은 무엇 git stash branch을위한 것입니다.

만약 너라면:

  1. 원본을 할 때 있었던 커밋 을 확인한 stash다음
  2. 새로운 지점을 만들고 마지막으로
  3. git stash apply --index

변경 사항을 다시 만들려는 시도 확실히 효과 있습니다. 이것이하는 일 입니다. (그리고 성공적으로 적용되었으므로 숨김을 삭제합니다.)git stash branch newbranch


에 대한 마지막 단어 --index(도대체 무엇입니까?)

무엇을 --index하는 일은 설명하는 간단하지만 약간은 내부적으로 복잡 :

  • 변경 사항이 있으면 ing git add전에 변경 (또는 "스테이지")해야 commit합니다.
  • 당신이 실행할 때 따라서 git stash, 당신은 수있는 두 파일을 편집 foo하고 zorg,하지만 그 중 하나를 벌였다.
  • 따라서 숨김을 다시 요청 git add하면 added 항목을 추가하고 추가 되지 않은 항목을 사용하지 않는git add 것이 좋습니다. 즉,을 수행 하기 전에 add에드 foo하지만 zorg다시 돌아 오지 않은 경우 stash정확히 동일한 설정을하는 것이 좋습니다. 준비된 것은 다시 준비되어야한다. 수정되었지만 준비되지 않은 것은 다시 수정되지만 준비되지 않아야합니다.

--index에 플래그를 apply이런 식으로 설정하는 것을 시도합니다. 작업 트리가 깨끗하면 일반적으로 작동합니다. 작업 트리에 이미 add문제가있는 경우 여기에 몇 가지 문제가있는 방법을 확인할 수 있습니다. 제외 --index하면 apply작업이 전체 준비 / 무대 설정을 유지하지 않습니다. 대신 "stash bag" 의 작업 트리 커밋을 사용하여 git의 병합 기계를 호출합니다 . 단계적 / 무단 계화를 유지하는 데 신경 쓰지 않는다면, 외면하지 않아도 --index훨씬 쉽게 git stash apply할 수 있습니다.


2
귀하의 의견을 이해하지 못합니다. 당신은 의미 git stash pop합니까? 또는 일부 파일을 편집했지만 git stash아직 다시 실행 하지 않았습니까? 아니면 다른 의미가 있습니까?
torek

1
예. 내 (긴) 편집 apply에서 은닉 하기 전에 지금 가지고있는 것을 커밋하는 것이 좋습니다 . 이 작업을 수행 할 필요는 없지만보기 훨씬 간단 해집니다. rebase -i여러 커밋을 함께 스쿼시하거나 특정 변경 사항을 나중에 고르는 데 사용할 수 있습니다 .
torek

1
예 : git stash apply --index(두 대시를 기억하십시오). 당신이 떠나면 --index, 큰 거래; 유일한 점은 --index단계적 / 비 단계적 설정을 유지하는 것입니다. (처음에는 특별한 설정이 없었을 것입니다.) 그런 다음 git statusetc 등을 원하는대로 추가 / 커밋합니다. 모두 숨김 상태로 완료 git stash drop되면 버립니다.
torek

1
숨김 을 유지 (하지 drop않거나 pop) 하지 않는 한, 숨김 커밋 이므로 항상 원본 숨김 코드를 커밋에 안전하게 유지합니다 ! 정확하게 다시 지점으로 가져 오려면 사용 git stash branch하십시오 (위의 해당 섹션 또는 Shunya의 답변 에 있는 Pro Git 책 참조 ). 그러면 해당 지점 또는 해당 지점 에서 커밋 등을 수행 할 수 있습니다 .git checkoutgit cherry-pick
torek

2
@ChuckWolber : Git의 명명 규칙은 원하는대로 남겨 두었습니다 ( "원격", "추적"및 "분기"라는 단어에 얼마나 많은 다른 의미를 할당 할 수 있습니까?). 그래도 원래 숨김과 관련이없는 것에 숨김을 적용 할 수 있다는 점은 주목할 가치가 있습니다.
torek

57
git stash pop

모든 것을 제자리에 돌려 놓을 것입니다

주석에서 제안한 바와 같이 git stash branch newbranch새 분기에 숨김을 적용하는 데 사용할 수 있으며 이는 실행과 동일합니다.

git checkout -b newbranch
git stash pop

도와 주셔서 감사합니다. 변경 사항을 새 지점으로 가져올 수 있습니까? 지금은에 지점 개발하고
Aswathy P Krishnan

3
git stash branch newbranch는 숨김 변경 사항이있는 새 분기를 만듭니다.
robert

3
@ robert : git stash branch newbranch실제로 그렇게 할 것입니다; 그러나 그것이 완료 HEAD되었을 때의 커밋으로 설정된 부모를 사용하여 새 분기를 만듭니다 stash. 다시 말해, 그것은 당신이 긴 해킹 세션이나 그 이후에 돌아 왔을 때 엉망을 응시하고 "나는 그것을 숨기지 말고 지점에 두어야 했음"을 결정합니다. :-)
torek

내 질문을 편집했습니다. 가능한 경우 이러한 변경 사항을 새 지점으로 가져오고 싶습니다.
Aswathy P Krishnan

1
때때로 당신은 단지 TLDR 응답 : 원하는
sachinruk

24

이를 간단하게하기 위해 숨김을 다시 적용하는 두 가지 옵션이 있습니다.

  1. git stash pop -저장된 상태로 복원하지만 임시 저장소에서 숨김을 삭제합니다.
  2. git stash apply -저장된 상태로 복원하고 나중에 재사용 할 수 있도록 숨김 목록을 남겨 둡니다.

이 기사에서 자식 숨김 에 대한 자세한 내용을 읽을 수 있습니다 .


19

숨김 컨텐츠를 확인하려면 :-

자식 숨김 목록

숨김 목록에서 특정 숨김을 적용하십시오.

git stash apply stash @ {2}

또는 첫 번째 숨김을 적용하기 위해 :-

자식 숨김 팝

참고 : git stash pop은 숨김 목록에서 숨김을 제거하지만 git stash apply는 적용되지 않습니다. 따라서 적절하게 사용하십시오.


2

Mac에서 이것은 나를 위해 일했습니다 :

자식 숨김 목록 (모든 숨김 참조)

git stash list

자식 숨김 적용 (스 태시 목록에서 원하는 숫자 만)

이처럼 :

git stash apply 1

0

"git stash"를 사용하여 커밋되지 않은 변경 사항을 숨기고 "git checkout -b"를 사용하여 새 분기로 체크 아웃 한 다음 숨김 커밋 "git stash apply"를 적용 할 수 있습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.