2

偶尔,我会遇到一个非常奇怪和令人沮丧的 git 问题。我提交并推送一些包含新文件和修改文件的更改,而我的同事将一些其他不相关的内容提交到不同的文件。

现在,当他拉出我的更改时,我新添加的文件在他这边显示为未跟踪,并且我的更改被还原。没有意识到这一点,他提交并推送到存储库,而我的更改完全被 git 忘记了。

例如,如果我更改了 file A,那么如果我这样做git log -p A了,我根本看不到他对我的更改的还原,我也看不到我更改它的提交。但是如果我查看 git 历史并找到那个提交,我的更改就在那个提交中。我的提交仍然存在于 git 历史记录中,但没有 git commit 可以恢复我的东西,但不知何故,它在最新的 master 中被恢复了,因为我的提交中的更改已以某种方式从 master 分支中删除。

有没有人遇到过类似的事情?我的第一个想法是他在提交自己的更改之前正在拉取,但他声称他在拉取之前就提交了。另一种可能性是他有一个 IDE(PyCharm),里面有一个 git 客户端(但他使用命令行 git),它以某种方式破坏了他机器中的 git。另一件需要注意的是,他运行 Windows 而我运行 OS X,所以可能是 git 版本冲突。

另一件可能很重要的事情:Doinggit log -p myfile不会显示我更改它的提交,显示我的更改,但没有git log --follow -p myfile显示恢复它的其他更改。

当我发布时git log,我可以看到我做出更改的提交以及与之相关的更改fileA。只有当我发布时,git log -p fileA我才能看到对fileA. 所以,提交在那里,合并到主控,但它的影响已经消失了。

有任何想法吗?

4

1 回答 1

3

看起来推动更改的人(或他正在使用的 IDE)正在执行强制推送(即git push -fgit 覆盖历史记录)。

为了证实这个理论,你可以这样做:

创建一个全新的 repo 克隆(因为在您当前的 repo 中,提交可能仍然可以通过某些本地分支或标签访问):

mkdir -p ~/temp-git-dir
cd ~/temp-git-dir
git clone <REPO-URL>
git fsck --unreachable --no-reflogs 2>/dev/null | grep 'unreachable commit' | awk '{print $3;}' | xargs -r -n 1 git show --oneline --name-status

如果您的提交是列出的提交之一,那么它证实了这一理论。

解决方案

允许强制推送 repo 总是一个坏主意,尤其是当工作流涉及多个开发人员时。您可以与您的 SCM 管理员交谈,看看他们是否可以禁止强制推送或仅在真正需要时才允许。

工作流程应该涉及每个开发人员尝试从远程获取更改,并将本地提交与来自远程的新提交合并或重新设置,然后将更新的 refspec 推送回远程。

于 2013-04-16T20:20:55.450 回答