从远程git存储库中提取更改

时间:2012-11-29 13:10:47

标签: git

我是git的新手。我所做的是分叉了几个我感兴趣的存储库,然后将它们克隆到我的计算机上与它们一起工作。

有些原始项目可能会因为我的本地副本混乱而大幅更新,或者我可能会做一些无关紧要的更改。

根据我的理解,我可以“改变”我的克隆,以“拉”原始的变化。

这对我的变化有什么影响?例如,假设原始文件中有DoSomething.cpp个文件。我修改它,可能修复一个小bug或添加一个功能。现在! 1年后,原始项目经历了许多修改,并且要好得多。我想把这些变化“拉”到我的克隆中,但也要保持我的变化! (所以这与推动相反)

这很容易吗?如果是这样,那么基本的想法是什么?

我想要的是我的克隆与原始克隆(我改变的东西)的任何变化都没有被覆盖,但我实际上可以合并我的更改和原始(在我的分支上)并被赋予能力实际上检查并接受更改。 (例如,如果在原始版本上更改了DoSomething.cpp,那么我需要比较更改以确保它们兼容。

我想这并不困难,因为我是fork的所有者我可以重新绑定或硬重置它然后将我的本地更改推送到我的fork? (不确定它是否会起作用,因为版本问题存在巨大潜力)

4 个答案:

答案 0 :(得分:1)

你是对的,变基是你保持代码最新的一种方式,并且非常常用。

根据我的经验,在管理你的git历史方面,变基更有用。它使您的历史保持良好和线性,这使得工作似乎顺序而不是并行发生。另一方面,定期合并将涉及许多分歧/融合提交。您可以使用git log --graph直观地看到这种差异。

简而言之,rebase接受您的提交,将它们转换为补丁,然后将它们应用到您正在重新定位的分支上。如果有冲突,git会停止并要求您解决它们,然后您可以继续。所以你仍然在合并和解决冲突,但只是让历史变得线性。

答案 1 :(得分:0)

  1. 找出您所在的分支,这是通过git status完成的,它会在第一行或第二行显示分支的名称。

  2. 为了进行测试,我建议先将更改分支到一个单独的分支中:

    git checkout -b my-patches
    
  3. 现在确保所有更改都已提交。为此,您再次调用git status。理想情况下,它应该显示工作目录清理,但如果不是这种情况,请使用git add将更改添加到索引,并git commit最终提交它们。如果您想将更改拆分为多个不同的补丁集(在发生冲突时可以很方便),我建议您阅读如何使用git commit -p。您这样做,直到所有更改都不再列在git status中。 git status中会列出一些您未触及的文件,可能是构建结果。如果没有任何变化,你有兴趣留在那里,你没事。

    如果有任何makefile或支持清理目录(例如make clean),请立即运行。

  4. 然后切换回原始分支,使用(将master替换为您在步骤1中找到的分支名称):

    git checkout master
    

    如果你想确保一切正常,请运行:

    git diff my-patches
    

    它应该列出你在fork中更改的行。如果没有,出了点问题。

  5. 现在出现了可怕的部分。你将丢掉现在对这个分支所做的任何更改。请注意,如果您将所有更改提交到单独的分支,如步骤3中所述,它们就可以了。如果您不确定,可以通过复制整个存储库文件夹进行备份。然后你跑(再次用以前的任何东西替换master):

    git fetch
    git reset --hard origin/master
    
  6. 理想情况下,您的分支现在应该具有origin/master分支的确切状态。确保一切看起来都不错。然后使用以下方法合并您的更改:

    git merge my-patches
    

    Git会尽可能地让它尽可能轻松,但可能会有冲突。 Git会使用>>>>`<<<<标记在相应文件中标记这些内容。为了解决冲突,我建议你做一些互联网研究或阅读the section about Basic Merge Conflicts in the open Git Book。确保之后提交合并。

  7. 困难的部分结束了。您现在可以删除临时分支:

    git branch -d my-patches
    

    我使用临时分支的原因是能够轻松地将存储库的状态恢复为合并尝试之前的状态。当然也可以在一个单独的分支中检查远程状态,但我更喜欢这样。

答案 2 :(得分:0)

您是否在分叉回购中添加了上游遥控器?这是保持fork与其主人同步的最简单方法。这是第3步here

答案 3 :(得分:0)

首先,您应该知道无论是“合并”还是“重新定位”,您都不会失去更改,而git会让您有机会提交更改&amp;解决冲突(如果有的话)然后将你的修改推回到你要拉的远程仓库。

当你git pull告诉git这样做时:(拉默认是使用“合并”)

  

从遥控器中提取最新的文件副本,将其与我的本地更改合并。如果存在您无法自动解决的冲突,请通知我,以便我手动解决;它很简单。

当你git pull --rebase告诉git这样做时:

  

临时删除*我本地副本(我的修改过的文件)中的更改,从遥控器中提取最新副本,将我的更改合并到它上面&amp;如果存在您无法自动解决的冲突,请通知我,以便我手动解决。 (从技术上讲,没有任何东西被删除;只是为了使这个模糊的逻辑清晰。

区别很微妙,在第二种情况下,您的更改似乎就像您刚从远程提取的最新副本顶部进行了这些更改...但正如您所看到的,两者都有如果您的更改肯定保留(否则git的用途是什么!)。

你应该合并还是变基?这是一个很长的讨论&amp;有些地方比其他地方更好,并且有最好的做法;本页已经提到了一些有用的评论,有关您可以在线搜索的更多信息,只需输入“git merge vs rebase”,您就会看到大量关于它的页面:)

希望这会有所帮助。