将更改推送到远程存储库时,此Git警告消息是什么?


69

描述有点简洁。我只是在本地master分支上添加了一个文件,然后将其推回远程仓库。知道为什么会这样吗?

警告:更新当前分支
警告:更新当前已签出的分支可能会造成混乱,
警告:因为索引和工作树无法反映HEAD中的更改。
警告:因此,您可能会看到刚刚推送到其中的更改
警告:在那儿运行“ git diff”时已还原,您可能需要
警告:在开始恢复之前运行'git reset --hard'。
警告: 
警告:您可以将“ receive.denyCurrentBranch”配置变量设置为
警告:远程存储库中的“拒绝”禁止将其推入
警告:当前分支。
警告:要允许推送到当前分支,可以将其设置为“忽略”;
警告:但是不建议这样做,除非您安排更新其工作
警告:树与您以其他方式推送的内容相匹配。
警告: 
警告:要抑制此消息,可以将其设置为“警告”。
警告: 
警告:请注意,默认值将在git的将来版本中更改
警告:除非您有
警告:配置变量设置为“忽略”或“警告”。   

2
您使用的确切命令是什么?
Esko Luontola,2009年

2
现在,即使您要推送到已签出的分支,使用Git 2.3.0(2015年2月)也可以更加安全地推送到非裸仓库。请参阅下面的答案
VonC'2

Answers:


56

实际上,这实际上意味着它所说的内容:某人正在您要推送到的存储库中工作,并且某人当前已签出您要推送到的完全相同的分支。

这非常令人困惑,因为现在他们认为他们已经签出了分支的最新版本,而实际上您刚刚将分支更新为了较新的版本。因此,当它们现在运行时git commit提交实际上将还原您刚刚推送的所有提交。而且当他们运行时git diff,即使他们甚至什么都没有改变,他们都将看到与您所推动的一切相反的事情。

因此,通常推入非裸仓库是不明智的做法。您应该只推送到裸仓库,即没有附加工作副本的仓库。至少您应该确保不推送到当前已签出的分支,但是通常您不应该只是将代码推送到其他人的存储库中,而应该请他们从您的代码中提取。

在某些特殊情况下,例如当您从Git存储库提供网站并希望通过推送到网站来更新网站时,将其推送到当前已签出的分支实际上是有意义的,但是在这种情况下,您必须确保您已经安装了一个挂钩,该挂钩实际上会更新已签出的工作副本,否则您的网站将永远不会更新。


1
我管理您在上一段中提到的网站问题的方式是拥有一个要推送到的中央裸仓库,然后将其从该仓库拉到网站工作目录中。当然,此方法需要外壳程序访问Web服务器,而您的hook方法不一定需要这样做。
2009年

3
豪尔赫,谢谢您的回复。共享存储库不应具有工作目录,但我没有使用--bare对其进行初始化。它仅用于共享工作。有一个“工作”区域,但是没有人使用它。我应该重新开始吗?
Coocoo4Cocoa

嗯-我经常在没有集中存储库的情况下工作。我将使用分析代码在笔记本电脑和群集计算机上处​​理代码。它们都是我自己的存储库,有点像您描述的特殊情况。
Dave X

119

使用Git 2.3.0(2015年2月之后)

如果没有人在该远程非裸仓库中工作,则应该可以将其推送到已签出的分支。

但是为了确保操作安全,现在(在Git 2.3.0中,2015年2月)可以在该远程仓库中进行操作:

git config receive.denyCurrentBranch updateInstead

它比config安全得多receive.denyCurrentBranch=ignore:仅当您不覆盖正在进行的修改时,它才允许推送。

提交1404bcb约翰内斯Schindelin( )dscho

receive-pack:为添加另一个选项 receive.denyCurrentBranch

在工作目录之间进行同步时,可以方便地通过' push'而不是' pull'更新当前分支,例如,当从VM内部推送修订时,或推送在用户机器上进行的修订时(开发人员不在安装ssh守护程序的自由(更不用说知道用户密码了)。

此修补程序不再需要常见的解决方法-进入临时分支,然后合并到另一台计算机上。

新选项是:

updateInstead

相应地更新工作树,但是如果有任何未提交的更改,则拒绝这样做。


承诺4d7a5ce增加了更多的测试,并提到:

上一个仅测试以下情况:要通过推送部署更新的路径在目标工作树中具有不兼容的更改,该更改已经添加到索引中,但是功能本身希望将工作树设置为索引。比测试的要干净得多。

添加一些其他测试以保护功能部件免受将来错误地更改(从功能部件的发明者的角度出发),从而放松了对清洁度的要求,即:

  • 仅更改工作树而不更改索引仍然是要保护的更改;
  • 需要保护工作树中未被一键部署覆盖的未跟踪文件;
  • 碰巧使文件与要推送的文件相同的更改仍然是要保护的更改(即,功能的清洁度要求比签出更为严格)。

另外,测试仅对工作树进行仅统计的更改是否不是拒绝即按即用的原因。

Git <2.3.0(2015年2月之前)

最常见的方法是从非裸存储库创建裸存储库,并在新创建的裸存储库上同时具有远程/本地非裸git回购点。


4
这在配对或经常在不同机器之间切换同时试图使所有内容保持最新状态时非常有用。我还使用它来使我的开发服务器保持最新状态(它会在代码更改时自动重新启动),同时仍能够在需要时进行开发。这确实是imo所不能接受的答案的解决方案。
Thor84no

1
确实是@ Thor84no。并且不要忘记git 2.4的push-to-checkout钩子:stackoverflow.com/a/34575157/6309。注意:当时接受的答案是正确的(已经六岁了)
VonC

1
我正在使用Windows和git版本2.6.3.windows.1,并且我需要删除“ =”,即git config receive.denyCurrentBranch updateInstead
jdpilgrim

1
updateInstead非常适合我,谢谢。
Prometheus

1
非常
感谢

15

这是与该问题相同的问题,解决方案是使用git init --baregit clone --bare


2
它说,即使是裸回购。(我所做的只是将git软件从1.5版升级到1.7版)

2
从1.5升级到1.7似乎会触发此消息。我做了“ MV reponame reponame.old; git clone --bare reponame.old reponame”来解决这个问题。我还必须使用“ --shared = group”并修复组权限,因为我正在运行共享存储库。
肖恩·赖夫施奈德
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.