]>
Commit | Line | Data |
---|---|---|
1 | git-rerere(1) | |
2 | ============= | |
3 | ||
4 | NAME | |
5 | ---- | |
6 | git-rerere - Reuse recorded resolution of conflicted merges | |
7 | ||
8 | SYNOPSIS | |
9 | -------- | |
10 | 'git rerere' ['clear'|'forget' [<pathspec>]|'diff'|'status'|'gc'] | |
11 | ||
12 | DESCRIPTION | |
13 | ----------- | |
14 | ||
15 | In a workflow employing relatively long lived topic branches, | |
16 | the developer sometimes needs to resolve the same conflicts over | |
17 | and over again until the topic branches are done (either merged | |
18 | to the "release" branch, or sent out and accepted upstream). | |
19 | ||
20 | This command assists the developer in this process by recording | |
21 | conflicted automerge results and corresponding hand resolve results | |
22 | on the initial manual merge, and applying previously recorded | |
23 | hand resolutions to their corresponding automerge results. | |
24 | ||
25 | [NOTE] | |
26 | You need to set the configuration variable rerere.enabled in order to | |
27 | enable this command. | |
28 | ||
29 | ||
30 | COMMANDS | |
31 | -------- | |
32 | ||
33 | Normally, 'git rerere' is run without arguments or user-intervention. | |
34 | However, it has several commands that allow it to interact with | |
35 | its working state. | |
36 | ||
37 | 'clear':: | |
38 | ||
39 | This resets the metadata used by rerere if a merge resolution is to be | |
40 | aborted. Calling 'git am [--skip|--abort]' or 'git rebase [--skip|--abort]' | |
41 | will automatically invoke this command. | |
42 | ||
43 | 'forget' <pathspec>:: | |
44 | ||
45 | This resets the conflict resolutions which rerere has recorded for the current | |
46 | conflict in <pathspec>. The <pathspec> is optional. | |
47 | ||
48 | 'diff':: | |
49 | ||
50 | This displays diffs for the current state of the resolution. It is | |
51 | useful for tracking what has changed while the user is resolving | |
52 | conflicts. Additional arguments are passed directly to the system | |
53 | 'diff' command installed in PATH. | |
54 | ||
55 | 'status':: | |
56 | ||
57 | Like 'diff', but this only prints the filenames that will be tracked | |
58 | for resolutions. | |
59 | ||
60 | 'gc':: | |
61 | ||
62 | This prunes records of conflicted merges that | |
63 | occurred a long time ago. By default, unresolved conflicts older | |
64 | than 15 days and resolved conflicts older than 60 | |
65 | days are pruned. These defaults are controlled via the | |
66 | `gc.rerereunresolved` and `gc.rerereresolved` configuration | |
67 | variables respectively. | |
68 | ||
69 | ||
70 | DISCUSSION | |
71 | ---------- | |
72 | ||
73 | When your topic branch modifies an overlapping area that your | |
74 | master branch (or upstream) touched since your topic branch | |
75 | forked from it, you may want to test it with the latest master, | |
76 | even before your topic branch is ready to be pushed upstream: | |
77 | ||
78 | ------------ | |
79 | o---*---o topic | |
80 | / | |
81 | o---o---o---*---o---o master | |
82 | ------------ | |
83 | ||
84 | For such a test, you need to merge master and topic somehow. | |
85 | One way to do it is to pull master into the topic branch: | |
86 | ||
87 | ------------ | |
88 | $ git checkout topic | |
89 | $ git merge master | |
90 | ||
91 | o---*---o---+ topic | |
92 | / / | |
93 | o---o---o---*---o---o master | |
94 | ------------ | |
95 | ||
96 | The commits marked with `*` touch the same area in the same | |
97 | file; you need to resolve the conflicts when creating the commit | |
98 | marked with `{plus}`. Then you can test the result to make sure your | |
99 | work-in-progress still works with what is in the latest master. | |
100 | ||
101 | After this test merge, there are two ways to continue your work | |
102 | on the topic. The easiest is to build on top of the test merge | |
103 | commit `{plus}`, and when your work in the topic branch is finally | |
104 | ready, pull the topic branch into master, and/or ask the | |
105 | upstream to pull from you. By that time, however, the master or | |
106 | the upstream might have been advanced since the test merge `{plus}`, | |
107 | in which case the final commit graph would look like this: | |
108 | ||
109 | ------------ | |
110 | $ git checkout topic | |
111 | $ git merge master | |
112 | $ ... work on both topic and master branches | |
113 | $ git checkout master | |
114 | $ git merge topic | |
115 | ||
116 | o---*---o---+---o---o topic | |
117 | / / \ | |
118 | o---o---o---*---o---o---o---o---+ master | |
119 | ------------ | |
120 | ||
121 | When your topic branch is long-lived, however, your topic branch | |
122 | would end up having many such "Merge from master" commits on it, | |
123 | which would unnecessarily clutter the development history. | |
124 | Readers of the Linux kernel mailing list may remember that Linus | |
125 | complained about such too frequent test merges when a subsystem | |
126 | maintainer asked to pull from a branch full of "useless merges". | |
127 | ||
128 | As an alternative, to keep the topic branch clean of test | |
129 | merges, you could blow away the test merge, and keep building on | |
130 | top of the tip before the test merge: | |
131 | ||
132 | ------------ | |
133 | $ git checkout topic | |
134 | $ git merge master | |
135 | $ git reset --hard HEAD^ ;# rewind the test merge | |
136 | $ ... work on both topic and master branches | |
137 | $ git checkout master | |
138 | $ git merge topic | |
139 | ||
140 | o---*---o-------o---o topic | |
141 | / \ | |
142 | o---o---o---*---o---o---o---o---+ master | |
143 | ------------ | |
144 | ||
145 | This would leave only one merge commit when your topic branch is | |
146 | finally ready and merged into the master branch. This merge | |
147 | would require you to resolve the conflict, introduced by the | |
148 | commits marked with `*`. However, this conflict is often the | |
149 | same conflict you resolved when you created the test merge you | |
150 | blew away. 'git rerere' helps you resolve this final | |
151 | conflicted merge using the information from your earlier hand | |
152 | resolve. | |
153 | ||
154 | Running the 'git rerere' command immediately after a conflicted | |
155 | automerge records the conflicted working tree files, with the | |
156 | usual conflict markers `<<<<<<<`, `=======`, and `>>>>>>>` in | |
157 | them. Later, after you are done resolving the conflicts, | |
158 | running 'git rerere' again will record the resolved state of these | |
159 | files. Suppose you did this when you created the test merge of | |
160 | master into the topic branch. | |
161 | ||
162 | Next time, after seeing the same conflicted automerge, | |
163 | running 'git rerere' will perform a three-way merge between the | |
164 | earlier conflicted automerge, the earlier manual resolution, and | |
165 | the current conflicted automerge. | |
166 | If this three-way merge resolves cleanly, the result is written | |
167 | out to your working tree file, so you do not have to manually | |
168 | resolve it. Note that 'git rerere' leaves the index file alone, | |
169 | so you still need to do the final sanity checks with `git diff` | |
170 | (or `git diff -c`) and 'git add' when you are satisfied. | |
171 | ||
172 | As a convenience measure, 'git merge' automatically invokes | |
173 | 'git rerere' upon exiting with a failed automerge and 'git rerere' | |
174 | records the hand resolve when it is a new conflict, or reuses the earlier hand | |
175 | resolve when it is not. 'git commit' also invokes 'git rerere' | |
176 | when committing a merge result. What this means is that you do | |
177 | not have to do anything special yourself (besides enabling | |
178 | the rerere.enabled config variable). | |
179 | ||
180 | In our example, when you do the test merge, the manual | |
181 | resolution is recorded, and it will be reused when you do the | |
182 | actual merge later with the updated master and topic branch, as long | |
183 | as the recorded resolution is still applicable. | |
184 | ||
185 | The information 'git rerere' records is also used when running | |
186 | 'git rebase'. After blowing away the test merge and continuing | |
187 | development on the topic branch: | |
188 | ||
189 | ------------ | |
190 | o---*---o-------o---o topic | |
191 | / | |
192 | o---o---o---*---o---o---o---o master | |
193 | ||
194 | $ git rebase master topic | |
195 | ||
196 | o---*---o-------o---o topic | |
197 | / | |
198 | o---o---o---*---o---o---o---o master | |
199 | ------------ | |
200 | ||
201 | you could run `git rebase master topic`, to bring yourself | |
202 | up-to-date before your topic is ready to be sent upstream. | |
203 | This would result in falling back to a three-way merge, and it | |
204 | would conflict the same way as the test merge you resolved earlier. | |
205 | 'git rerere' will be run by 'git rebase' to help you resolve this | |
206 | conflict. | |
207 | ||
208 | ||
209 | Author | |
210 | ------ | |
211 | Written by Junio C Hamano <gitster@pobox.com> | |
212 | ||
213 | GIT | |
214 | --- | |
215 | Part of the linkgit:git[1] suite |