在Git存储库中查找和恢复已删除的文件
说我在Git仓库。 我删除一个文件并提交更改。 我继续工作,做更多的承诺。 然后,我发现我需要恢复该文件。
我知道我可以使用git checkout HEAD^ foo.bar来签出一个文件,但是我不知道该文件何时被删除。 
- find删除给定文件名的提交最快的方法是什么?
- 将该文件恢复到我的工作副本最简单的方法是什么?
我希望我不必手动浏览我的日志,签出一个给定的SHA整个项目,然后手动将该文件复制到我原来的项目结帐。
find影响给定path的最后一个提交。 由于该文件不在HEAD提交中,因此该提交必须将其删除。
 git rev-list -n 1 HEAD -- <file_path> 
 然后使用脱字符号( ^ )符号检出之前提交的版本: 
 git checkout <deleting_commit>^ -- <file_path> 
 或者在一个命令中,如果$file是有问题的文件。 
 git checkout $(git rev-list -n 1 HEAD -- "$file")^ -- "$file" 
-  使用git log --diff-filter=D --summary获取删除文件和删除文件的所有提交;
-  使用git checkout $commit~1 filename来恢复被删除的文件。
要恢复文件夹中所有已删除的文件,请input以下命令。
 git ls-files -d | xargs git checkout -- 
 如果你疯了,使用git-bisect 。 这是做什么: 
 git bisect start git bisect bad git bisect good <some commit where you know the file existed> 
 现在是时候运行自动化testing了。 如果存在foo.bar ,shell命令'[ -e foo.bar ]'将返回0,否则返回1。  git-bisect的“run”命令将使用二进制search来自动查找testing失败的第一个提交。 它从给定的范围(从好到坏)开始中途,根据指定的testing结果将其减半。 
 git bisect run '[ -e foo.bar ]' 
 现在你在删除它的提交。 从这里开始,你可以跳回到将来,用git-revert来取消这个改变, 
 git bisect reset git revert <the offending commit> 
或者您可以返回一个提交并手动检查损坏情况:
 git checkout HEAD^ cp foo.bar /tmp git bisect reset cp /tmp/foo.bar . 
我来到这个问题寻找恢复我刚刚删除的文件,但我还没有承诺的变化。 万一你发现自己处在这种情况下,你只需要做以下事情:
 git checkout HEAD -- path/to/file.ext 
我最喜欢的别名,基于bonyiii的回答 (upvoted)和我自己的回答:“ 传递参数给Git别名命令 ”:
 git config alias.restore '!f() { git checkout $(git rev-list -n 1 HEAD -- $1)~1 -- $(git diff --name-status $(git rev-list -n 1 HEAD -- $1)~1 | grep '^D' | cut -f 2); }; f' 
 我已经丢失了一个文件,在几次提交之前被误删了? 
 快: 
 git restore my_deleted_file 
危机避免了。
罗伯特·戴利 在评论中提出了以下别名:
 restore-file = !git checkout $(git rev-list -n 1 HEAD -- "$1")^ -- "$1" 
而jegan补充说 :
为了从命令行设置别名,我使用了这个命令:
 git config --global alias.restore "\!git checkout \$(git rev-list -n 1 HEAD -- \"\$1\")^ -- \"\$1\"" 
恢复已删除并提交的文件:
 git reset HEAD some/path git checkout -- some/path 
它在Git版本1.7.5.4上进行了testing。
如果你知道文件名,这是一个简单的方法与基本的命令:
列出该文件的所有提交。
 git log -- path/to/file 
最后一个提交(最上面)是删除文件的提交。 所以你需要恢复第二个到最后一个提交。
 git checkout {second to last commit} -- path/to/file 
我有这个解决scheme 。
- 
使用以下某种方法获取文件被删除的提交的ID。 -  git log --grep=*word*
-  git log -Sword
-  git log | grep --context=5 *word*
-  git log --stat | grep --context=5 *word*git log --stat | grep --context=5 *word*#如果你几乎不记得任何东西,
 
-  
- 
你应该得到像这样的东西: 
提交bfe68bd117e1091c96d2976c99b3bcc8310bebe7作者:Alexander Orlovdate:四月12日星期四23:44:27 2011 +0200
replaced deprecated GWT class - gwtI18nKeySync.sh, an outdated (?, replaced by a Maven goal) I18n generation script提交3ea4e3af253ac6fd1691ff6bb89c964f54802302作者:Alexander Orlovdate:四月12日星期四22:10:22 2011 +0200
3 。 现在使用提交ID bfe68bd117e1091c96d2976c99b3bcc8310bebe7做:
 git checkout bfe68bd117e1091c96d2976c99b3bcc8310bebe7^1 yourDeletedFile.java 
 由于提交ID引用文件已经被删除的提交,你需要引用在bfe68b之前的提交,你可以通过追加^1 。 这意味着:在bfe68b之前给我提交。 
如果您只做了更改并删除了一个文件,但没有提交,现在您已经与您的更改分手了
 git checkout -- . 
但你删除的文件没有返回,你只需要执行下面的命令:
 git checkout <file_path> 
而且,你的文件又回来了。
 git checkout /path/to/deleted.file 
在许多情况下,将coreutils (grep,sed等)与Git结合使用会非常有用。 我已经很了解这些工具,但Git不那么重要。 如果我想要search已删除的文件,我会执行以下操作:
 git log --raw | grep -B 30 $'D\t.*deleted_file.c' 
当我find修订/提交时:
 git checkout <rev>^ -- path/to/refound/deleted_file.c 
就像其他人在我之前所说的一样。
该文件现在将恢复到删除之前的状态。 如果你想保留它,记得重新提交到工作树。
 git undelete path/to/file.ext 
- 
把它放在你的 .bash_profile(或者打开一个命令shell时加载的其他相关文件)中:git config --global alias.undelete '!sh -c "git checkout $(git rev-list -n 1 HEAD -- $1)^ -- $1" -'
- 
然后使用: git undelete path/to/file.ext
这个别名首先检查find这个文件存在的最后一个提交,然后从该文件存在的最后一个提交执行该文件path的git检出。 资源
所以我不得不从一个特定的提交恢复一堆已删除的文件,我用两个命令来pipe理它:
 git show <rev> --diff-filter=D --summary --name-only --no-commit-id | xargs git checkout <rev>^ -- git show <rev> --diff-filter=D --summary --name-only --no-commit-id | xargs git reset HEAD 
(注意每个命令末尾的尾部空格。)
这些文件已被添加到.gitignore文件,然后用git rm清除,我需要恢复文件,但是然后取消它们。 我有数百个文件要恢复,为每个文件手动input的东西,如在其他例子将是太慢了。
在我们的例子中,我们意外地删除了一个提交中的文件,稍后我们意识到我们的错误,并希望找回所有被删除的文件,但不是那些被修改的文件。
基于查尔斯·贝利的优秀答案,这里是我的一个class轮:
 git co $(git rev-list -n 1 HEAD -- <file_path>)~1 -- $(git diff --name-status $(git rev-list -n 1 HEAD -- <file_path>)~1 head | grep '^D' | cut -f 2) 
 user@bsd:~/work/git$ rm slides.tex user@bsd:~/work/git$ git pull Already up-to-date. user@bsd:~/work/git$ ls slides.tex ls: slides.tex: No such file or directory 
还原已删除的文件:
 user@bsd:~/work/git$ git checkout D .slides.tex.swp D slides.tex user@bsd:~/work/git$ git checkout slides.tex user@bsd:~/work/git$ ls slides.tex slides.tex 
 如果您知道删除文件的提交,请运行此命令,其中<SHA1_deletion>是删除该文件的提交: 
 git diff --diff-filter=D --name-only <SHA1_deletion>~1 <SHA1_deletion> | xargs git checkout <SHA1_deletion>~1 -- 
pipe道之前的部分列出了在提交中被删除的所有文件; 他们都是从以前的提交结算,以恢复他们。
如果您遇到这个问题的频率更高,而且您愿意使用Git GUI工具,请查看DeepGit并在其中使用File | Search 。