How to apply two patches against the same git revision?
This is a imaginary problem, but I'm having real problems with patches. Let's say I have a project with the following git history:
A - B - C
Now if I receive two patches, C1
and C2
, that are meant to be applied on C
, how should I handle them? If I apply patch C1
first, then I will not be able to apply patch C2
because the repository has become:
A - B - C - C1
Is it possible to apply them both, or do I have to reply to the person sending C2 telling him/her to update the patch?
Now suppose I go offline and work and commit so that the repository becomes:
A - B - C - D - E
Then I check my email an开发者_如何学God receive a patch for C
. Again, is it possible to simply apply that patch, or do I have to ask for an update to the patch?
The classic way is to:
- apply the received first patch,
- refuse any patch which isn't fast-forward and ask the sender to rebase his/her repo first, then re-check the patch, and resend it.
The general idea is that it isn't up to you to solve merge conflicts: only the creator of the patch has the necessary knowledge to solve any conflict with the current source code.
As Linus Torvalds (creator of Git) said in his 2007 Google talk:
So what happens is, remember, distribution means nobody is special.
So instead of me merging, I just push out my first tree, that did not have any merge issues, and I tell the second person:"hey, I tried to pull from you, but I had merge conflicts and they weren't completely trivial, so I decided you get to do the honors instead."
And they do. And they know what they are doing because it's their changes. So they can do the merges and they probably think I am a moron because the merge was so easy and it is obvious I should have taken their code, but they do the merge and they update their tree, and say "hey, can you pull from me now", and I pull from them and they did all the work for me.
That's what is all about: they did all the work for me. So,... and I take the credit. Now I just need to figure out the step 3: profit.
Most of the time, C2 will apply on top of C1. It's only if they're edits to overlapping sections of the same files that you'll get a merge conflict. Git will take all the parts of the patch that don't conflict, and insert conflict markers that help you resolve the merge.
As for what to do, it depends how large your project is and how competent you are in that section of the code -- I've always just fixed up the conflicts myself, as long as the submitter used a reasonably recent checkout as the base for their patch.
Another commenter mentioned Linus' quote saying that he always makes other people resolve conflicts, but even this isn't quite true; he often asks people to leave conflicts unresolved when sending pull requests so he gets a shot at them.
You can totally at least try to apply all these patches. You may potentially get merge conflicts, and as VonC suggests, you might want the patch submitters to solve them, or you might do it yourself as cjb says! In any case, here's what you want to do.
First case: two patches, C1 and C2.
# apply C1
git am C1.patch
# create a temporary branch (use a real name instead of C2)
git checkout -b C2 C
# apply C2
git am C2.patch
# return to master
git checkout master
# merge the other branch
git merge C2
# and delete the other branch
git branch -d C2
You can handle the second case similarly; it's just that instead of applying C1 you've made commits D and E yourself.
And of course, if the merge fails, and it looks too scary for you to sort through yourself, just blow it away and tell the submitter of C2 to fix it on their end. (git reset --merge; git branch -D C2
)
精彩评论