2009-03-05 121 views
144

我在一个分支上有8个提交,我想通过电子邮件发送给一些不是git开明的人。到目前为止,我所做的每件事都会给我8个补丁文件,或者从开始的时候开始为分支历史记录中的每个提交提供补丁文件。我使用git rebase --interactive来压缩提交,但现在我尝试的所有内容都是从一开始就为我提供了无数的补丁。我究竟做错了什么?你如何使用git format-patch来压缩一个补丁?

git format-patch master HEAD # yields zillions of patches, even though there's 
          # only one commit since master 
+0

我很好奇你将在下面的命题中使用哪种方法。让我们知道;) – VonC 2009-03-06 06:48:03

+3

我将使用Rob Di Marco建议的git diff。但是我已经离开了两周的工作,刚刚目睹了我第二个女婴的诞生,所以在我使用它之前会有一段时间! :) – skiphoppy 2009-03-06 19:56:49

+2

我很想看到git format-patch --squash master HEAD – schoetbi 2011-03-10 10:44:40

回答

168

我建议在一次性分支上进行如下操作。如果你的提交是在“换行”分支,您可以切换回你的“主人”分支已经,这应该做的伎俩:

[[email protected] example (master)]$ git checkout -b tmpsquash 
Switched to a new branch "tmpsquash" 

[[email protected] example (tmpsquash)]$ git merge --squash newlines 
Updating 4d2de39..b6768b2 
Fast forward 
Squash commit -- not updating HEAD 
test.txt | 2 ++ 
1 files changed, 2 insertions(+), 0 deletions(-) 

[[email protected] example (tmpsquash)]$ git commit -a -m "My squashed commits" 
[tmpsquash]: created 75b0a89: "My squashed commits" 
1 files changed, 2 insertions(+), 0 deletions(-) 

[[email protected] example (tmpsquash)]$ git format-patch master 
0001-My-squashed-commits.patch 

希望这有助于!

18

正如你所知道的,git format-patch -8 HEAD会给你八个补丁。

如果你希望你的8个提交呈现为一个,并且不介意重写你的分支(o-o-X-A-B-C-D-E-F-G-H)的历史,你可以:

git rebase -i 
// squash A, B, C, D, E ,F, G into H 

,或者这将是一个更好的解决方案,重播从X所有8个提交(你8个提交前提交)一个新的分支

git branch delivery X 
git checkout delivery 
git merge --squash master 
git format-patch HEAD 

这样的话,你只需要在“交货”分支一个承诺,它代表所有你的最后8℃ ommits

+0

`git merge master`只是做一个快进,不会压缩到一个。更改为`git merge --squash master`以获取所有提交在演出区域压扁并可见的提交。您的流量将适用于此更改。 (我使用的是git 2.1.0版。) – Stunner 2016-01-13 00:30:41

+0

@Stunner好点。我编辑了答案。 – VonC 2016-01-13 05:48:43

21

我一直在你的例子使用git的差异等等,像

git diff master > patch.txt 
120

只是多了一个解决方案添加到锅: 如果你用这个代替:

git format-patch master --stdout > my_new_patch.diff 

那么它会仍然是8个补丁...但它们都将在单个补丁文件中并且将与之一起应用:

git am < my_new_patch.diff 
17

这是亚当亚历山大答案的改编,以防您的更改在主分支中。这做到以下几点:。

  • 创建一个从我们想要的点(查找运行“混帐--log”或gitg的SHA密钥生成新的一次性分支“tmpsquash”选择你想提交tmpsquash头,那么在master中的提交将被压扁的提交)。
  • 合并从主机到tmpsquash的更改。
  • 将压扁的更改提交给tmpsquash。
  • 用压扁的提交创建补丁。
  • 去回主分支

[email protected]:~/example (master)$ git branch tmpsquash ba3c498878054e25afc5e22e207d62eb40ff1f38 
[email protected]:~/example (master)$ git checkout tmpsquash 
Switched to branch 'tmpsquash' 
[email protected]:~/example (tmpsquash)$ git merge --squash master 
Updating ba3c498..40386b8 
Fast-forward 
Squash commit -- not updating HEAD 

[snip, changed files] 

11 files changed, 212 insertions(+), 59 deletions(-) 
[email protected]:~/example (tmpsquash)$ git commit -a -m "My squashed commits" 
[test2 6127e5c] My squashed commits 
11 files changed, 212 insertions(+), 59 deletions(-) 
[email protected]:~/example (tmpsquash)$ git format-patch master 
0001-My-squashed-commits.patch 
[email protected]:~/example (tmpsquash)$ git checkout master 
Switched to branch 'master' 
[email protected]:~/example (master)$ 
0

基于亚当亚历山大的回答是:标签

git checkout newlines 
## must be rebased to master 
git checkout -b temporary 
# squash the commits 
git rebase -i master 
git format-patch master 
4

格式补丁之间有两个:

git checkout <source-tag> 
git checkout -b <tmpsquash> 
git merge --squash <target-tag> 
git commit -a -m "<message>" 
git format-patch <source-tag> 
4

最简单的方法是使用git diff,a如果你想要压缩方法输出的组合提交信息,可以在git log中添加。应用修补程序时

git diff abcd..1234 > patch.diff 
git log abcd..1234 > patchmsg.txt 

然后:例如,创建abcd1234之间提交补丁

git apply patch.diff 
git add -A 
git reset patch.diff patchmsg.txt 
git commit -F patchmsg.txt 

与非文本文件打交道时,不要忘了--binary参数git diff,例如图像或视频。