为什么将代码推送到非裸远程库不等同于从该远程库获取代码?

3
首先,我了解与将内容推送到非裸 git 远程相关的“如何”,包括使用 git 配置选项 `receive.denyCurrentBranch` 和其他解决方法,因此我不需要像这里提供的答案那样:Git push error '[remote rejected] master -> master (branch is currently checked out)'Push to a non-bare Git repositoryGit pushing to non-bare repo, save current worktreeGit: making pushes to non-bare repositories safe
这更像是一个关于 git 实现/表示/哲学问题。
为什么不能将 `git push ` 到非裸远程视为从远程获取 `git fetch ` 的双重或本质相同?这样,我的本地工作目录可能过时(落后于)新内容,甚至可能有本地更改(提交前缀,甚至是已暂存/未暂存/已储藏/任何内容),但是该工作目录完全不会受到推送操作的影响?如果是这样,那么一旦在远程上,我就可以合并或重新基于或进行任何必要的操作。实际上,这正是这个 kernel.org git faq 条目所声称的。
这样做的动机与提出“如何”问题的其他人完全相同:由于{防火墙、nat、安全}原因,我没有任何简便的方法访问推送的“源”。
也许我缺少一些关于 git 如何跟踪事物的基本知识,“如果我只理解 XXXX”,我就会知道答案;请启发我。

也许更可以将其与 git pull 进行比较。您可能还会发现 https://dev59.com/53A75IYBdhLWcg3wYH3I 对于更多概念性的东西有用。直到我看到索引和暂存区,我才明白它的含义。在那之前,我只是一个愚蠢的 git。 - Michael Durrant
谢谢你的指引,Michael。里面有一些有用的信息,写得也很好,但不完全是我想要的。我正在尝试具体理解为什么在推送到非裸远程时必须更新工作树。至少我认为这是正确的问题。 - crimson-egret
最好能够直接推送到仓库的FETCH_HEAD而不是HEAD。这个问题与此相同:以一种仅分离头部的方式进行推送将是不错的选择。对我来说,我只是想将更改集合存储起来。就像Git不能在不更新引用的情况下执行该操作一样... - binki
1个回答

0
问题在于推送重写引用。 HEAD 是最新的检出的同义词,重写该引用会默默地使工作树和索引无效 - 在该存储库中提交将丢失已推送的更改,而没有任何指示表明已发生这种情况。 拒绝推送是最简单的解决方案。 如果在目标位置执行git pull不是一个选项,则将其推送到一个可抛弃的位置并修复引用。
git push origin master:fakemaster
cd $origindir
git checkout -B master fakemaster
git branch -D fakemaster

感谢您的回复,虽然您的解决方法和我的解决方法实际上是等效的,但我真正想了解的是为什么在更新索引时必须更新工作树。如果我理解fetch正在做什么,它会更新引用(特别是refs/heads/master),而不会更新索引或工作树。因此,为什么不能通过对非裸远程进行git push来完成相同的操作呢? - crimson-egret
我暂时想不到另一种在别人的版本库中将HEAD + index + 工作目录解除同步的方法 - 而且默认情况下fetch不会更新你的主分支,它会更新你的远程跟踪分支(在refs/remotes中)。 - jthill
@eggo,我认为对于你上面的评论,答案实际上是:“是的”。引用会被更新,索引和工作树不会被更新。这正是它的工作原理。诀窍在于,如果您更改当前检出的分支引用,还会影响非裸远程的HEAD(指向您刚刚更改的分支),并且这会使索引中的任何内容以及该远程上的工作树中的任何更改无效。当然,您可以约定永远不在该远程上进行更改...但那么您应该首先使用一个裸仓库。 - Wildcard
@Wildcard - 谢谢你,显然我的git内部工作模型还没有达到解决基本理论混乱的任务。具体来说,是工作树和索引之间(显然)的基本链接。最终,我有了一个可行的解决方案,看起来类似于jthill的答案。实际问题是我有(N个独立的)远程服务器没有出站访问权限,但允许入站(通过ssh)。 - crimson-egret
如果你有一个需要推送并且进行工作的盒子,只需在该盒子上创建一个裸仓库用于推送,以及在同一盒子上创建一个单独的非裸仓库,您可以从本地裸仓库中git fetch。@eggo - Wildcard

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接