首先尝试以下命令(如有需要,请重新运行):
$ git fsck --full
$ git gc
$ git gc --prune=today
$ git fetch --all
$ git pull --rebase
如果您仍然遇到问题,可以尝试以下方法:
删除所有损坏的对象,例如
fatal: loose object 91c5...51e5 (stored in .git/objects/06/91c5...51e5) is corrupt
$ rm -v .git/objects/06/91c5...51e5
删除所有空对象,例如:error: object file .git/objects/06/91c5...51e5 is empty
$ find .git/objects/ -size 0 -exec rm -vf "{}" \;
检查“链接已损坏”消息的方法:
git ls-tree 2d9263c6d23595e7cb2a21e5ebbb53655278dff8
这将告诉您损坏blob文件来自哪个文件!
要恢复文件,您可能非常幸运,它可能是您在工作树中已经签出的版本:
git hash-object -w my-magic-file
再次运行,如果输出缺失的SHA1(4b945..),那么现在就完成了!
假设它是某个旧版本出了问题,最简单的方法是执行:
git log --raw --all --full-history -- subdirectory/my-magic-file
你可以使用该命令查看文件的完整日志(请注意,您可能不在顶级目录下,因此需要自行确定子目录),然后您现在可以再次使用hash-object命令重新创建缺失的对象。
获取所有缺失提交、树或blob的引用列表:
$ git for-each-ref --format='%(refname)' | while read ref; do git rev-list --objects $ref >/dev/null || echo "in $ref"; done
在使用常规的分支 -d 或标签 -d 命令删除一些引用时,由于可能会发现损坏,因此无法删除。因此,请改用管道命令 git update-ref -d $ref。请注意,在本地分支的情况下,该命令可能会在 .git/config 中留下过时的分支配置。可以手动删除它们(搜索 [branch "$ref"] 部分)。
在所有引用都已清除后,引用日志中仍可能存在损坏的提交。您可以使用 git reflog expire --expire=now --all 清除所有引用日志。如果不想失去所有引用日志,可以查找单个引用的损坏引用日志:
$ (echo HEAD; git for-each-ref --format='%(refname)') | while read ref; do git rev-list -g --objects $ref >/dev/null || echo "in $ref"; done
(请注意在 git rev-list 命令中添加了 -g 选项。) 然后,在每个受影响的引用上运行 git reflog expire --expire=now $ref。
当所有损坏的引用和 reflog 被删除后,运行 git fsck --full 以检查存储库是否干净。悬空对象是可以的。
以下是命令的高级用法,如果不明智地使用,可能导致数据丢失,请在意外造成更多损害之前备份您的git。如果您知道自己在做什么,请自行决定风险。
在获取后将当前分支拉到上游分支的顶部:
$ git pull --rebase
你也可以尝试检出一个新分支并删除旧的分支:
$ git checkout -b new_master origin/master
要查找 Git 中的损坏对象以进行删除,请尝试以下命令:
while [ true ]; do f=`git fsck --full 2>&1|awk '{print $3}'|sed -r 's/(^..)(.*)/objects\/\1\/\2/'`; if [ ! -f "$f" ]; then break; fi; echo delete $f; rm -f "$f"; done
对于OSX,使用sed -E
替代sed -r
。
另一个想法是从打包文件中解压所有对象,以重新生成.git/objects内的所有对象,因此请尝试在您的存储库中运行以下命令:
$ cp -fr .git/objects/pack .git/objects/pack.bak
$ for i in .git/objects/pack.bak/*.pack; do git unpack-objects -r < $i; done
$ rm -frv .git/objects/pack.bak
如果上述方法不起作用,您可以尝试从另一个存储库中复制git对象,例如:
$ rsync -varu git_server:/path/to/git/.git local_git_repo/
$ rsync -varu /local/path/to/other-working/git/.git local_git_repo/
$ cp -frv ../other_repo/.git/objects .git/objects
尝试检出以下分支时,修复已损坏的分支:
$ git checkout -f master
fatal: unable to read tree 5ace24d474a9535ddd5e6a6c6a1ef480aecf2625
尝试将其删除,然后再次从上游检出:
$ git branch -D master
$ git checkout -b master github/master
如果Git将您置于分离状态,请切换到master
并将分离的分支合并到其中。
另一个想法是递归地重新设置现有的主分支:
$ git reset HEAD --hard
$ git rebase -s recursive -X theirs origin/master
另请参见:
.git
文件夹)复制到刚刚克隆的存储库中...然后在新的存储库中执行git status
命令...git正确检测到了我文件的所有更改,我现在可以开始我的工作了。 - Rosdi Kasim