OLD | NEW |
1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
2 # Copyright 2014 the V8 project authors. All rights reserved. | 2 # Copyright 2014 the V8 project authors. All rights reserved. |
3 # Redistribution and use in source and binary forms, with or without | 3 # Redistribution and use in source and binary forms, with or without |
4 # modification, are permitted provided that the following conditions are | 4 # modification, are permitted provided that the following conditions are |
5 # met: | 5 # met: |
6 # | 6 # |
7 # * Redistributions of source code must retain the above copyright | 7 # * Redistributions of source code must retain the above copyright |
8 # notice, this list of conditions and the following disclaimer. | 8 # notice, this list of conditions and the following disclaimer. |
9 # * Redistributions in binary form must reproduce the above | 9 # * Redistributions in binary form must reproduce the above |
10 # copyright notice, this list of conditions and the following | 10 # copyright notice, this list of conditions and the following |
(...skipping 29 matching lines...) Expand all Loading... |
40 | 40 |
41 def RunStep(self): | 41 def RunStep(self): |
42 if os.path.exists(self.Config("ALREADY_MERGING_SENTINEL_FILE")): | 42 if os.path.exists(self.Config("ALREADY_MERGING_SENTINEL_FILE")): |
43 if self._options.force: | 43 if self._options.force: |
44 os.remove(self.Config("ALREADY_MERGING_SENTINEL_FILE")) | 44 os.remove(self.Config("ALREADY_MERGING_SENTINEL_FILE")) |
45 elif self._options.step == 0: # pragma: no cover | 45 elif self._options.step == 0: # pragma: no cover |
46 self.Die("A merge is already in progress") | 46 self.Die("A merge is already in progress") |
47 open(self.Config("ALREADY_MERGING_SENTINEL_FILE"), "a").close() | 47 open(self.Config("ALREADY_MERGING_SENTINEL_FILE"), "a").close() |
48 | 48 |
49 self.InitialEnvironmentChecks(self.default_cwd) | 49 self.InitialEnvironmentChecks(self.default_cwd) |
50 if self._options.revert_bleeding_edge: | 50 if self._options.revert_master: |
51 # FIXME(machenbach): Make revert bleeding_edge obsolete? | 51 # FIXME(machenbach): Make revert master obsolete? |
52 self["merge_to_branch"] = "bleeding_edge" | 52 self["merge_to_branch"] = "master" |
53 elif self._options.branch: | 53 elif self._options.branch: |
54 self["merge_to_branch"] = self._options.branch | 54 self["merge_to_branch"] = self._options.branch |
55 else: # pragma: no cover | 55 else: # pragma: no cover |
56 self.Die("Please specify a branch to merge to") | 56 self.Die("Please specify a branch to merge to") |
57 | 57 |
58 self.CommonPrepare() | 58 self.CommonPrepare() |
59 self.PrepareBranch() | 59 self.PrepareBranch() |
60 | 60 |
61 | 61 |
62 class CreateBranch(Step): | 62 class CreateBranch(Step): |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
104 | 104 |
105 def RunStep(self): | 105 def RunStep(self): |
106 | 106 |
107 # Stringify: [123, 234] -> "r123, r234" | 107 # Stringify: [123, 234] -> "r123, r234" |
108 self["revision_list"] = ", ".join(map(lambda s: "r%s" % s, | 108 self["revision_list"] = ", ".join(map(lambda s: "r%s" % s, |
109 self["full_revision_list"])) | 109 self["full_revision_list"])) |
110 | 110 |
111 if not self["revision_list"]: # pragma: no cover | 111 if not self["revision_list"]: # pragma: no cover |
112 self.Die("Revision list is empty.") | 112 self.Die("Revision list is empty.") |
113 | 113 |
114 if self._options.revert and not self._options.revert_bleeding_edge: | 114 if self._options.revert and not self._options.revert_master: |
115 action_text = "Rollback of %s" | 115 action_text = "Rollback of %s" |
116 else: | 116 else: |
117 action_text = "Merged %s" | 117 action_text = "Merged %s" |
118 | 118 |
119 # The commit message title is added below after the version is specified. | 119 # The commit message title is added below after the version is specified. |
120 msg_pieces = [ | 120 msg_pieces = [ |
121 "\n".join(action_text % s for s in self["full_revision_list"]), | 121 "\n".join(action_text % s for s in self["full_revision_list"]), |
122 ] | 122 ] |
123 msg_pieces.append("\n\n") | 123 msg_pieces.append("\n\n") |
124 | 124 |
(...skipping 24 matching lines...) Expand all Loading... |
149 TextToFile(patch, self.Config("TEMPORARY_PATCH_FILE")) | 149 TextToFile(patch, self.Config("TEMPORARY_PATCH_FILE")) |
150 self.ApplyPatch(self.Config("TEMPORARY_PATCH_FILE"), self._options.revert) | 150 self.ApplyPatch(self.Config("TEMPORARY_PATCH_FILE"), self._options.revert) |
151 if self._options.patch: | 151 if self._options.patch: |
152 self.ApplyPatch(self._options.patch, self._options.revert) | 152 self.ApplyPatch(self._options.patch, self._options.revert) |
153 | 153 |
154 | 154 |
155 class PrepareVersion(Step): | 155 class PrepareVersion(Step): |
156 MESSAGE = "Prepare version file." | 156 MESSAGE = "Prepare version file." |
157 | 157 |
158 def RunStep(self): | 158 def RunStep(self): |
159 if self._options.revert_bleeding_edge: | 159 if self._options.revert_master: |
160 return | 160 return |
161 # This is used to calculate the patch level increment. | 161 # This is used to calculate the patch level increment. |
162 self.ReadAndPersistVersion() | 162 self.ReadAndPersistVersion() |
163 | 163 |
164 | 164 |
165 class IncrementVersion(Step): | 165 class IncrementVersion(Step): |
166 MESSAGE = "Increment version number." | 166 MESSAGE = "Increment version number." |
167 | 167 |
168 def RunStep(self): | 168 def RunStep(self): |
169 if self._options.revert_bleeding_edge: | 169 if self._options.revert_master: |
170 return | 170 return |
171 new_patch = str(int(self["patch"]) + 1) | 171 new_patch = str(int(self["patch"]) + 1) |
172 if self.Confirm("Automatically increment PATCH_LEVEL? (Saying 'n' will " | 172 if self.Confirm("Automatically increment PATCH_LEVEL? (Saying 'n' will " |
173 "fire up your EDITOR on %s so you can make arbitrary " | 173 "fire up your EDITOR on %s so you can make arbitrary " |
174 "changes. When you're done, save the file and exit your " | 174 "changes. When you're done, save the file and exit your " |
175 "EDITOR.)" % VERSION_FILE): | 175 "EDITOR.)" % VERSION_FILE): |
176 text = FileToText(os.path.join(self.default_cwd, VERSION_FILE)) | 176 text = FileToText(os.path.join(self.default_cwd, VERSION_FILE)) |
177 text = MSub(r"(?<=#define PATCH_LEVEL)(?P<space>\s+)\d*$", | 177 text = MSub(r"(?<=#define PATCH_LEVEL)(?P<space>\s+)\d*$", |
178 r"\g<space>%s" % new_patch, | 178 r"\g<space>%s" % new_patch, |
179 text) | 179 text) |
180 TextToFile(text, os.path.join(self.default_cwd, VERSION_FILE)) | 180 TextToFile(text, os.path.join(self.default_cwd, VERSION_FILE)) |
181 else: | 181 else: |
182 self.Editor(os.path.join(self.default_cwd, VERSION_FILE)) | 182 self.Editor(os.path.join(self.default_cwd, VERSION_FILE)) |
183 self.ReadAndPersistVersion("new_") | 183 self.ReadAndPersistVersion("new_") |
184 self["version"] = "%s.%s.%s.%s" % (self["new_major"], | 184 self["version"] = "%s.%s.%s.%s" % (self["new_major"], |
185 self["new_minor"], | 185 self["new_minor"], |
186 self["new_build"], | 186 self["new_build"], |
187 self["new_patch"]) | 187 self["new_patch"]) |
188 | 188 |
189 | 189 |
190 class CommitLocal(Step): | 190 class CommitLocal(Step): |
191 MESSAGE = "Commit to local branch." | 191 MESSAGE = "Commit to local branch." |
192 | 192 |
193 def RunStep(self): | 193 def RunStep(self): |
194 # Add a commit message title. | 194 # Add a commit message title. |
195 if self._options.revert and self._options.revert_bleeding_edge: | 195 if self._options.revert and self._options.revert_master: |
196 # TODO(machenbach): Find a better convention if multiple patches are | 196 # TODO(machenbach): Find a better convention if multiple patches are |
197 # reverted in one CL. | 197 # reverted in one CL. |
198 self["commit_title"] = "Revert on master" | 198 self["commit_title"] = "Revert on master" |
199 else: | 199 else: |
200 self["commit_title"] = "Version %s (cherry-pick)" % self["version"] | 200 self["commit_title"] = "Version %s (cherry-pick)" % self["version"] |
201 self["new_commit_msg"] = "%s\n\n%s" % (self["commit_title"], | 201 self["new_commit_msg"] = "%s\n\n%s" % (self["commit_title"], |
202 self["new_commit_msg"]) | 202 self["new_commit_msg"]) |
203 TextToFile(self["new_commit_msg"], self.Config("COMMITMSG_FILE")) | 203 TextToFile(self["new_commit_msg"], self.Config("COMMITMSG_FILE")) |
204 self.GitCommit(file_name=self.Config("COMMITMSG_FILE")) | 204 self.GitCommit(file_name=self.Config("COMMITMSG_FILE")) |
205 | 205 |
206 | 206 |
207 class CommitRepository(Step): | 207 class CommitRepository(Step): |
208 MESSAGE = "Commit to the repository." | 208 MESSAGE = "Commit to the repository." |
209 | 209 |
210 def RunStep(self): | 210 def RunStep(self): |
211 self.GitCheckout(self.Config("BRANCHNAME")) | 211 self.GitCheckout(self.Config("BRANCHNAME")) |
212 self.WaitForLGTM() | 212 self.WaitForLGTM() |
213 self.GitPresubmit() | 213 self.GitPresubmit() |
214 self.vc.CLLand() | 214 self.vc.CLLand() |
215 | 215 |
216 | 216 |
217 class TagRevision(Step): | 217 class TagRevision(Step): |
218 MESSAGE = "Create the tag." | 218 MESSAGE = "Create the tag." |
219 | 219 |
220 def RunStep(self): | 220 def RunStep(self): |
221 if self._options.revert_bleeding_edge: | 221 if self._options.revert_master: |
222 return | 222 return |
223 print "Creating tag %s" % self["version"] | 223 print "Creating tag %s" % self["version"] |
224 self.vc.Tag(self["version"], | 224 self.vc.Tag(self["version"], |
225 self.vc.RemoteBranch(self["merge_to_branch"]), | 225 self.vc.RemoteBranch(self["merge_to_branch"]), |
226 self["commit_title"]) | 226 self["commit_title"]) |
227 | 227 |
228 | 228 |
229 class CleanUp(Step): | 229 class CleanUp(Step): |
230 MESSAGE = "Cleanup." | 230 MESSAGE = "Cleanup." |
231 | 231 |
232 def RunStep(self): | 232 def RunStep(self): |
233 self.CommonCleanup() | 233 self.CommonCleanup() |
234 if not self._options.revert_bleeding_edge: | 234 if not self._options.revert_master: |
235 print "*** SUMMARY ***" | 235 print "*** SUMMARY ***" |
236 print "version: %s" % self["version"] | 236 print "version: %s" % self["version"] |
237 print "branch: %s" % self["merge_to_branch"] | 237 print "branch: %s" % self["merge_to_branch"] |
238 if self["revision_list"]: | 238 if self["revision_list"]: |
239 print "patches: %s" % self["revision_list"] | 239 print "patches: %s" % self["revision_list"] |
240 | 240 |
241 | 241 |
242 class MergeToBranch(ScriptsBase): | 242 class MergeToBranch(ScriptsBase): |
243 def _Description(self): | 243 def _Description(self): |
244 return ("Performs the necessary steps to merge revisions from " | 244 return ("Performs the necessary steps to merge revisions from " |
245 "bleeding_edge to other branches, including trunk.") | 245 "master to other branches, including candidates.") |
246 | 246 |
247 def _PrepareOptions(self, parser): | 247 def _PrepareOptions(self, parser): |
248 group = parser.add_mutually_exclusive_group(required=True) | 248 group = parser.add_mutually_exclusive_group(required=True) |
249 group.add_argument("--branch", help="The branch to merge to.") | 249 group.add_argument("--branch", help="The branch to merge to.") |
250 group.add_argument("-R", "--revert-bleeding-edge", | 250 group.add_argument("-R", "--revert-master", |
251 help="Revert specified patches from bleeding edge.", | 251 help="Revert specified patches from master.", |
252 default=False, action="store_true") | 252 default=False, action="store_true") |
253 parser.add_argument("revisions", nargs="*", | 253 parser.add_argument("revisions", nargs="*", |
254 help="The revisions to merge.") | 254 help="The revisions to merge.") |
255 parser.add_argument("-f", "--force", | 255 parser.add_argument("-f", "--force", |
256 help="Delete sentinel file.", | 256 help="Delete sentinel file.", |
257 default=False, action="store_true") | 257 default=False, action="store_true") |
258 parser.add_argument("-m", "--message", | 258 parser.add_argument("-m", "--message", |
259 help="A commit message for the patch.") | 259 help="A commit message for the patch.") |
260 parser.add_argument("--revert", | 260 parser.add_argument("--revert", |
261 help="Revert specified patches.", | 261 help="Revert specified patches.", |
262 default=False, action="store_true") | 262 default=False, action="store_true") |
263 parser.add_argument("-p", "--patch", | 263 parser.add_argument("-p", "--patch", |
264 help="A patch file to apply as part of the merge.") | 264 help="A patch file to apply as part of the merge.") |
265 | 265 |
266 def _ProcessOptions(self, options): | 266 def _ProcessOptions(self, options): |
267 # TODO(machenbach): Add a test that covers revert from bleeding_edge | 267 # TODO(machenbach): Add a test that covers revert from master |
268 if len(options.revisions) < 1: | 268 if len(options.revisions) < 1: |
269 if not options.patch: | 269 if not options.patch: |
270 print "Either a patch file or revision numbers must be specified" | 270 print "Either a patch file or revision numbers must be specified" |
271 return False | 271 return False |
272 if not options.message: | 272 if not options.message: |
273 print "You must specify a merge comment if no patches are specified" | 273 print "You must specify a merge comment if no patches are specified" |
274 return False | 274 return False |
275 options.bypass_upload_hooks = True | 275 options.bypass_upload_hooks = True |
276 # CC ulan to make sure that fixes are merged to Google3. | 276 # CC ulan to make sure that fixes are merged to Google3. |
277 options.cc = "ulan@chromium.org" | 277 options.cc = "ulan@chromium.org" |
(...skipping 29 matching lines...) Expand all Loading... |
307 CommitLocal, | 307 CommitLocal, |
308 UploadStep, | 308 UploadStep, |
309 CommitRepository, | 309 CommitRepository, |
310 TagRevision, | 310 TagRevision, |
311 CleanUp, | 311 CleanUp, |
312 ] | 312 ] |
313 | 313 |
314 | 314 |
315 if __name__ == "__main__": # pragma: no cover | 315 if __name__ == "__main__": # pragma: no cover |
316 sys.exit(MergeToBranch().Run()) | 316 sys.exit(MergeToBranch().Run()) |
OLD | NEW |