如何在git repo中取回已删除和提交的文件?

时间:2013-04-05 18:52:00

标签: git githooks

我有一个关于git的项目。我的项目有以下文件:

file1.js
file2.html
file3.js
file4.css
file5.html
file6.jpg
file7.html
file8.js
file9.css

我为所有文件做了一个git -rm文件名并提交了它们,直到我留下了

file1.js
file2.html

我需要取回我的file6.jpg

我如何获得file6.jpg所以我的回购将有

file1.js
file2.html
file6.jpg

4 个答案:

答案 0 :(得分:2)

git checkout HEAD~N -- file6.jpg

Nfile6.jpg出现时提交的提交次数。

答案 1 :(得分:1)

git checkout可能是单个文件最简单的选项。

  1. 使用git log查看您的提交历史记录。在删除相关文件之前,找到提交的哈希值。例如:

    commit 5faff7e3f74c3408985acecd1dbb90feeb7b1d75 <--- "hash"
    Author: Nick Tomlin <myemail@email.com>
    Date:   Fri Apr 5 11:34:03 2013 -0500
    
  2. 然后使用上面的字符串运行git checkout <hash> path/to/file6.jpg替换<hash>(通常只需要最后5个左右,但现在让我们使用它们都是安全的。如果你是在file6.jpg所在的目录中,您可以执行git checkout <hash> file6.jpg

  3. 这是一种访问提交的更长形式的方法,可以使用HEAD~6,但在引用比HEAD~3更远的提交时,我通常更喜欢它。使用相对~引用更容易引用错误的提交,我最终查看我的日志以确切地知道我需要哪个提交:)。

答案 2 :(得分:0)

git checkout $(git log -1 --pretty='%h' -- <path>)^ -- <path>

细分

使用git log查找影响所需文件的最后一次提交

$(git log -1 --pretty='%h' -- <path>)

  • 使用仅显示哈希值的git log格式运行--pretty命令。
  • 使用--分隔符显式指定文件而不是提交引用。
  • 后跟我们要检索的文件的路径和文件名。
  • $()中包含所有这些内容,以便我们可以将其嵌入到另一个git命令中,如变量。
  • 这将返回删除给定文件的提交。

如果您只是想知道该文件何时被删除,这当然可以在没有$()的情况下单独使用 - 更改或删除漂亮的格式将为您提供有关它找到的提交的更多信息。

使用git checkout检索在给定提交中的文件

git checkout <ref>^ -- <path>

  • 使用提交运行git checkout并指定路径。
  • 当指定路径时,git只是在提供的引用处重新创建该路径的状态。
  • 通过在引用中添加胡萝卜^,我们实际上指向了直接的祖先。
  • 我们想要直接的祖先,因为我们从日志中获取的提交将不会有文件 - 因为它是文件被删除的提交。

将所有内容放在一起,然后在文件被删除之前检查文件处于提交状态。如果您对尚未删除的文件运行此操作,则只会撤消最近对该文件所做的更改。

<强>别名

git config --global alias.unrm '!COMMIT=$(git log -1 --pretty='%h' -- "$1"); git checkout $COMMIT^ -- "$1"'

我创建了一个名为unrm的别名,就像取消删除一样。如果你运行上面的命令,那么你只需要运行..

git unrm <path>

编辑:我在命令中添加了一些反馈。

git config --global alias.unrm '!COMMIT=$(git log -1 --pretty='%h' -- "$1"); git checkout $COMMIT^ -- "$1"; echo "File: $1, was restored from commit $COMMIT"; git show -s $COMMIT'

现在它会通知您它已完成的操作,并向您显示已从中恢复文件的提交。

答案 3 :(得分:-1)

假设先前已提交file6.jpg,您可以通过以下方式获取git存储库中file6.jpg的所有修订:

git rev-list --objects --all | grep file6.jpg

然后您可以使用

恢复文件
git cat-file {sha} > file6.jpg

添加文件并提交。

另请参阅此答案,讨论如何从git存储库中获取所有对象:https://stackoverflow.com/a/7350019

这个网站关于git对象的内部结构: http://git-scm.com/book/en/Git-Internals-Git-Objects