如何在git中预览合并?

Gle*_*min 371 git git-merge

我有一个git分支(例如主线),我想在另一个开发分支中合并.或者我呢?

为了确定我是否真的想合并这个分支,我想看看合并将做什么的某种预览.最好能够查看正在应用的提交列表.

到目前为止,我能想到的最好的是merge --no-ff --no-commit,然后diff HEAD.

Jan*_*dec 382

  • git log ..otherbranch
    • 将合并到当前分支的更改列表.
  • git diff ...otherbranch
    • 从共同祖先(合并基础)到将要合并的头部的差异.注意三个点,与两个点相比具有特殊含义(见下文).
  • gitk ...otherbranch
    • 自上次合并以来分支的图形表示.

空字符串暗示HEAD,所以这就是为什么..otherbranch而不是HEAD..otherbranch.

对于diff而言,两点对三点的含义与列出修订(log,gitk等)的命令略有不同.对于日志和其他两个点(a..b)表示所有内容b但不是a三个点(a...b)表示只有一个a或中的所有内容b.但diff有两个版本,两个点(a..b)表示的简单情况是简单的差异a,b而三个点(a...b)表示共同祖先和b(git diff $(git merge-base a b)..b)之间的差异.

  • 第三点是我失踪的部分,谢谢!日志方法也很好,log -p --reverse ..otherbranch似乎是一个很好的方法来查看将要合并的内容. (7认同)
  • 这不完全准确,特别是樱桃采摘. (4认同)
  • `git show ..otherbranch`将显示将合并到当前分支的更改和差异列表. (3认同)
  • @ void.pointer,git在正常合并中不特别处理Cherry-pick,因此在这里也不会。可以编写一种合并策略,但是据我所知,从来没有。 (2认同)

Kas*_*apo 262

我发现最适合我的解决方案是只执行合并并在不喜欢结果的情况下中止它.这种特殊的语法让我感觉干净简单.如果你想确保你不会弄乱当前的分支,或者你不准备合并而不管是否存在冲突,只需创建一个新的子分支并合并它.

策略1:安全的方式 - 合并临时分支:

git checkout mybranch
git checkout -b mynew-temporary-branch
git merge some-other-branch
Run Code Online (Sandbox Code Playgroud)

这样,如果你只是想看看冲突是什么,你可以简单地扔掉临时分支.你不需要打扰"中止"合并,你可以回到你的工作 - 只需再次检查'mybranch',你的分支中就不会有任何合并代码或合并冲突.

这基本上是一个干运行.

策略2:当你肯定想要合并时,但只有在没有冲突的情况下

git checkout mybranch
git merge some-other-branch
Run Code Online (Sandbox Code Playgroud)

如果git报告冲突(并且只有在存在冲突的情况下),您可以执行以下操作:

git merge --abort
Run Code Online (Sandbox Code Playgroud)

如果合并成功,则无法中止(仅重置).

如果您还没准备好合并,请使用上面更安全的方法.

[编辑:2016年11月 - 我将战略1换成2,因为似乎大多数人都在寻找"安全的方式".策略2现在更像是一个注释,如果合并存在您尚未准备好处理的冲突,您可以简单地中止合并.如果阅读评论请记住!]

  • 我不敢相信这不是投票,似乎是如此直截了当 (7认同)
  • 如果您不想直接提交更改,可以执行`git merge --no-ff --no-commit`.这消除了对不同分支的"需求",使得更容易查看更改,imo. (6认同)
  • 策略的+1.临时分支,显示合并时将要进入的内容.策略1是我试图避免的特殊情况. (2认同)
  • 我建议改变策略,让更安全的策略先行(我的心理训练即将到来 - 大多数人会认为最好的选择是第一个,尽管明确使用"更安全"这个词)但除此之外,优秀工作. (2认同)

djs*_*hny 19

如果你像我一样,你正在寻找相当于svn update -n.以下似乎可以解决问题.请注意,请务必先执行此操作,git fetch以便本地仓库具有相应的更新以进行比较.

$ git fetch origin
$ git diff --name-status origin/master
D       TableAudit/Step0_DeleteOldFiles.sh
D       TableAudit/Step1_PopulateRawTableList.sh
A       manbuild/staff_companies.sql
M       update-all-slave-dbs.sh
Run Code Online (Sandbox Code Playgroud)

或者如果你想从你的头到远程的差异:

$ git fetch origin
$ git diff origin/master
Run Code Online (Sandbox Code Playgroud)

IMO这个解决方案比提出"合并然后中止"的顶级解决方案更容易且更不容易出错(因此风险更小).


mic*_*ael 6

添加到现有答案后,可以创建别名以在合并之前显示差异和/或日志.许多答案fetch在"预览"合并之前省略了要完成的事情; 这是一个别名,将这两个步骤合二为一(模仿类似于mercurial的hg incoming/ outgoing)

因此,在" git log ..otherbranch"的基础上,您可以添加以下内容~/.gitconfig:

...
[alias]
    # fetch and show what would be merged (use option "-p" to see patch)
    incoming = "!git remote update -p; git log ..@{u}"
Run Code Online (Sandbox Code Playgroud)

对于对称性,在推送之前,可以使用以下别名来显示已提交和将被推送的内容:

    # what would be pushed (currently committed)
    outgoing = log @{u}..
Run Code Online (Sandbox Code Playgroud)

然后你可以运行" git incoming"来显示很多变化,或者" git incoming -p"显示补丁(即"差异")," git incoming --pretty=oneline",简洁摘要等等.然后你可以(可选)运行" git pull"来实际合并.(虽然,既然你已经获取了,合并可以直接完成.)

同样地," git outgoing"表示如果你要跑" git push" 会推动什么.


Pab*_* C. 6

如果您已经获取了更改,我最喜欢的是:

git log ...@{u}
Run Code Online (Sandbox Code Playgroud)

这需要git 1.7.x我相信.该 @{u}符号是上游分支的"速记",因此它比它更具通用性git log ...origin/master.

注意:如果你使用zsh和扩展的glog,你可能需要做类似的事情:

git log ...@\{u\}
Run Code Online (Sandbox Code Playgroud)


hra*_*ban 5

此处的大多数答案都需要一个干净的工作目录和多个交互步骤(不利于脚本编写),或者不适用于所有情况,例如,过去的合并已将一些出色的更改带入目标分支,或者执行了相同。

要真正了解master分支合并后的变化develop,现在:

git merge-tree $(git merge-base master develop) master develop
Run Code Online (Sandbox Code Playgroud)

由于这是一个管道命令,它不能猜测您的意思,因此必须明确。它还不会使输出着色或使用您的寻呼机,因此完整的命令应为:

git merge-tree $(git merge-base master develop) master develop | colordiff | $(git var GIT_PAGER)
Run Code Online (Sandbox Code Playgroud)

https://git.seveas.net/previewing-a-merge-result.html

(感谢David Normington提供的链接)

PS:

如果您遇到合并冲突,它们将在输出中显示出通常的冲突标记,例如:

$ git merge-tree $(git merge-base a b ) a b 
added in both
  our    100644 78981922613b2afb6025042ff6bd878ac1994e85 a
  their  100644 61780798228d17af2d34fce4cfbdf35556832472 a
@@ -1 +1,5 @@
+<<<<<<< .our
 a
+=======
+b
+>>>>>>> .their
Run Code Online (Sandbox Code Playgroud)

PS 2:在我的机器(香草Mac OS X)上,GIT_PAGER行最终使用less,不喜欢彩色输入。我必须添加export LESS=FRX〜/ .bashrc使其可口。感谢https://unix.stackexchange.com/questions/153943/git-pager-is-less-but-what-is-causing-the-output-coloring

  • @dreftymac 找不到任何与此效果相关的内容。你可以使用类似`git merge-tree ... | grep -q '^[az].*在两个$' &amp;&amp; 回显冲突|| echo 可以安全地合并,但它很挑剔;我可能忘记了一个案例。也许您想检查冲突标记?例如,这可能不会捕获“他们的删除,我们的更改”风格冲突。(我刚刚检查过,甚至没有显示冲突标记,所以你需要一个细致的正则表达式才能在这里安全) (2认同)