OLD | NEW |
---|---|
1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
2 # Copyright 2013 the V8 project authors. All rights reserved. | 2 # Copyright 2013 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 27 matching lines...) Expand all Loading... | |
38 import subprocess | 38 import subprocess |
39 import sys | 39 import sys |
40 import textwrap | 40 import textwrap |
41 import time | 41 import time |
42 import urllib | 42 import urllib |
43 import urllib2 | 43 import urllib2 |
44 | 44 |
45 from git_recipes import GitRecipesMixin | 45 from git_recipes import GitRecipesMixin |
46 from git_recipes import GitFailedException | 46 from git_recipes import GitFailedException |
47 | 47 |
48 PERSISTFILE_BASENAME = "PERSISTFILE_BASENAME" | |
49 BRANCHNAME = "BRANCHNAME" | |
50 CHANGELOG_FILE = "CHANGELOG_FILE" | |
51 CHANGELOG_ENTRY_FILE = "CHANGELOG_ENTRY_FILE" | |
52 COMMITMSG_FILE = "COMMITMSG_FILE" | |
53 PATCH_FILE = "PATCH_FILE" | |
54 | |
55 VERSION_FILE = os.path.join("src", "version.cc") | 48 VERSION_FILE = os.path.join("src", "version.cc") |
56 | 49 |
57 # V8 base directory. | 50 # V8 base directory. |
58 DEFAULT_CWD = os.path.dirname( | 51 DEFAULT_CWD = os.path.dirname( |
59 os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) | 52 os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) |
60 | 53 |
61 | 54 |
62 def TextToFile(text, file_name): | 55 def TextToFile(text, file_name): |
63 with open(file_name, "w") as f: | 56 with open(file_name, "w") as f: |
64 f.write(text) | 57 f.write(text) |
(...skipping 222 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
287 def __setitem__(self, key, value): | 280 def __setitem__(self, key, value): |
288 # Convenience method to allow direct [] access on step classes for | 281 # Convenience method to allow direct [] access on step classes for |
289 # manipulating the backed state dict. | 282 # manipulating the backed state dict. |
290 self._state[key] = value | 283 self._state[key] = value |
291 | 284 |
292 def Config(self, key): | 285 def Config(self, key): |
293 return self._config[key] | 286 return self._config[key] |
294 | 287 |
295 def Run(self): | 288 def Run(self): |
296 # Restore state. | 289 # Restore state. |
297 state_file = "%s-state.json" % self._config[PERSISTFILE_BASENAME] | 290 state_file = "%s-state.json" % self._config["PERSISTFILE_BASENAME"] |
298 if not self._state and os.path.exists(state_file): | 291 if not self._state and os.path.exists(state_file): |
299 self._state.update(json.loads(FileToText(state_file))) | 292 self._state.update(json.loads(FileToText(state_file))) |
300 | 293 |
301 print ">>> Step %d: %s" % (self._number, self._text) | 294 print ">>> Step %d: %s" % (self._number, self._text) |
302 try: | 295 try: |
303 return self.RunStep() | 296 return self.RunStep() |
304 finally: | 297 finally: |
305 # Persist state. | 298 # Persist state. |
306 TextToFile(json.dumps(self._state), state_file) | 299 TextToFile(json.dumps(self._state), state_file) |
307 | 300 |
(...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
426 self.Die("Workspace is not clean. Please commit or undo your changes.") | 419 self.Die("Workspace is not clean. Please commit or undo your changes.") |
427 | 420 |
428 # Persist current branch. | 421 # Persist current branch. |
429 self["current_branch"] = self.GitCurrentBranch() | 422 self["current_branch"] = self.GitCurrentBranch() |
430 | 423 |
431 # Fetch unfetched revisions. | 424 # Fetch unfetched revisions. |
432 self.GitSVNFetch() | 425 self.GitSVNFetch() |
433 | 426 |
434 def PrepareBranch(self): | 427 def PrepareBranch(self): |
435 # Delete the branch that will be created later if it exists already. | 428 # Delete the branch that will be created later if it exists already. |
436 self.DeleteBranch(self._config[BRANCHNAME]) | 429 self.DeleteBranch(self._config["BRANCHNAME"]) |
437 | 430 |
438 def CommonCleanup(self): | 431 def CommonCleanup(self): |
439 self.GitCheckout(self["current_branch"]) | 432 self.GitCheckout(self["current_branch"]) |
440 if self._config[BRANCHNAME] != self["current_branch"]: | 433 if self._config["BRANCHNAME"] != self["current_branch"]: |
441 self.GitDeleteBranch(self._config[BRANCHNAME]) | 434 self.GitDeleteBranch(self._config["BRANCHNAME"]) |
442 | 435 |
443 # Clean up all temporary files. | 436 # Clean up all temporary files. |
444 for f in glob.iglob("%s*" % self._config[PERSISTFILE_BASENAME]): | 437 for f in glob.iglob("%s*" % self._config["PERSISTFILE_BASENAME"]): |
445 if os.path.isfile(f): | 438 if os.path.isfile(f): |
446 os.remove(f) | 439 os.remove(f) |
447 if os.path.isdir(f): | 440 if os.path.isdir(f): |
448 shutil.rmtree(f) | 441 shutil.rmtree(f) |
449 | 442 |
450 def ReadAndPersistVersion(self, prefix=""): | 443 def ReadAndPersistVersion(self, prefix=""): |
451 def ReadAndPersist(var_name, def_name): | 444 def ReadAndPersist(var_name, def_name): |
452 match = re.match(r"^#define %s\s+(\d*)" % def_name, line) | 445 match = re.match(r"^#define %s\s+(\d*)" % def_name, line) |
453 if match: | 446 if match: |
454 value = match.group(1) | 447 value = match.group(1) |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
519 line = re.sub("\d+$", self[prefix + "minor"], line) | 512 line = re.sub("\d+$", self[prefix + "minor"], line) |
520 elif line.startswith("#define BUILD_NUMBER"): | 513 elif line.startswith("#define BUILD_NUMBER"): |
521 line = re.sub("\d+$", self[prefix + "build"], line) | 514 line = re.sub("\d+$", self[prefix + "build"], line) |
522 elif line.startswith("#define PATCH_LEVEL"): | 515 elif line.startswith("#define PATCH_LEVEL"): |
523 line = re.sub("\d+$", self[prefix + "patch"], line) | 516 line = re.sub("\d+$", self[prefix + "patch"], line) |
524 output += "%s\n" % line | 517 output += "%s\n" % line |
525 TextToFile(output, version_file) | 518 TextToFile(output, version_file) |
526 | 519 |
527 def SVNCommit(self, root, commit_message): | 520 def SVNCommit(self, root, commit_message): |
528 patch = self.GitDiff("HEAD^", "HEAD") | 521 patch = self.GitDiff("HEAD^", "HEAD") |
529 TextToFile(patch, self._config[PATCH_FILE]) | 522 TextToFile(patch, self._config["PATCH_FILE"]) |
530 self.Command("svn", "update", cwd=self._options.svn) | 523 self.Command("svn", "update", cwd=self._options.svn) |
531 if self.Command("svn", "status", cwd=self._options.svn) != "": | 524 if self.Command("svn", "status", cwd=self._options.svn) != "": |
532 self.Die("SVN checkout not clean.") | 525 self.Die("SVN checkout not clean.") |
533 if not self.Command("patch", "-d %s -p1 -i %s" % | 526 if not self.Command("patch", "-d %s -p1 -i %s" % |
534 (root, self._config[PATCH_FILE]), | 527 (root, self._config["PATCH_FILE"]), |
535 cwd=self._options.svn): | 528 cwd=self._options.svn): |
536 self.Die("Could not apply patch.") | 529 self.Die("Could not apply patch.") |
537 self.Command( | 530 self.Command( |
538 "svn", | 531 "svn", |
539 "commit --non-interactive --username=%s --config-dir=%s -m \"%s\"" % | 532 "commit --non-interactive --username=%s --config-dir=%s -m \"%s\"" % |
540 (self._options.author, self._options.svn_config, commit_message), | 533 (self._options.author, self._options.svn_config, commit_message), |
541 cwd=self._options.svn) | 534 cwd=self._options.svn) |
542 | 535 |
543 | 536 |
544 class UploadStep(Step): | 537 class UploadStep(Step): |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
600 message = step_class.MESSAGE | 593 message = step_class.MESSAGE |
601 except AttributeError: | 594 except AttributeError: |
602 message = step_class.__name__ | 595 message = step_class.__name__ |
603 | 596 |
604 return step_class(message, number=number, config=config, | 597 return step_class(message, number=number, config=config, |
605 state=state, options=options, | 598 state=state, options=options, |
606 handler=side_effect_handler) | 599 handler=side_effect_handler) |
607 | 600 |
608 | 601 |
609 class ScriptsBase(object): | 602 class ScriptsBase(object): |
610 # TODO(machenbach): Move static config here. | 603 # TODO(machenbach): Move static config here. |
tandrii(chromium)
2014/09/23 14:45:25
Is this still TODO?
Michael Achenbach
2014/09/25 08:17:41
Ups no. This is exactly what the todo was about...
| |
611 def __init__(self, config, side_effect_handler=DEFAULT_SIDE_EFFECT_HANDLER, | 604 def __init__(self, |
605 config=None, | |
606 side_effect_handler=DEFAULT_SIDE_EFFECT_HANDLER, | |
612 state=None): | 607 state=None): |
613 self._config = config | 608 self._config = config or self._Config() |
614 self._side_effect_handler = side_effect_handler | 609 self._side_effect_handler = side_effect_handler |
615 self._state = state if state is not None else {} | 610 self._state = state if state is not None else {} |
616 | 611 |
617 def _Description(self): | 612 def _Description(self): |
618 return None | 613 return None |
619 | 614 |
620 def _PrepareOptions(self, parser): | 615 def _PrepareOptions(self, parser): |
621 pass | 616 pass |
622 | 617 |
623 def _ProcessOptions(self, options): | 618 def _ProcessOptions(self, options): |
624 return True | 619 return True |
625 | 620 |
626 def _Steps(self): # pragma: no cover | 621 def _Steps(self): # pragma: no cover |
627 raise Exception("Not implemented.") | 622 raise Exception("Not implemented.") |
628 | 623 |
624 def _Config(self): | |
625 return {} | |
626 | |
629 def MakeOptions(self, args=None): | 627 def MakeOptions(self, args=None): |
630 parser = argparse.ArgumentParser(description=self._Description()) | 628 parser = argparse.ArgumentParser(description=self._Description()) |
631 parser.add_argument("-a", "--author", default="", | 629 parser.add_argument("-a", "--author", default="", |
632 help="The author email used for rietveld.") | 630 help="The author email used for rietveld.") |
633 parser.add_argument("--dry-run", default=False, action="store_true", | 631 parser.add_argument("--dry-run", default=False, action="store_true", |
634 help="Perform only read-only actions.") | 632 help="Perform only read-only actions.") |
635 parser.add_argument("-g", "--googlers-mapping", | 633 parser.add_argument("-g", "--googlers-mapping", |
636 help="Path to the script mapping google accounts.") | 634 help="Path to the script mapping google accounts.") |
637 parser.add_argument("-r", "--reviewer", default="", | 635 parser.add_argument("-r", "--reviewer", default="", |
638 help="The account name to be used for reviews.") | 636 help="The account name to be used for reviews.") |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
684 if not self._ProcessOptions(options): | 682 if not self._ProcessOptions(options): |
685 parser.print_help() | 683 parser.print_help() |
686 return None | 684 return None |
687 return options | 685 return options |
688 | 686 |
689 def RunSteps(self, step_classes, args=None): | 687 def RunSteps(self, step_classes, args=None): |
690 options = self.MakeOptions(args) | 688 options = self.MakeOptions(args) |
691 if not options: | 689 if not options: |
692 return 1 | 690 return 1 |
693 | 691 |
694 state_file = "%s-state.json" % self._config[PERSISTFILE_BASENAME] | 692 state_file = "%s-state.json" % self._config["PERSISTFILE_BASENAME"] |
695 if options.step == 0 and os.path.exists(state_file): | 693 if options.step == 0 and os.path.exists(state_file): |
696 os.remove(state_file) | 694 os.remove(state_file) |
697 | 695 |
698 steps = [] | 696 steps = [] |
699 for (number, step_class) in enumerate(step_classes): | 697 for (number, step_class) in enumerate(step_classes): |
700 steps.append(MakeStep(step_class, number, self._state, self._config, | 698 steps.append(MakeStep(step_class, number, self._state, self._config, |
701 options, self._side_effect_handler)) | 699 options, self._side_effect_handler)) |
702 for step in steps[options.step:]: | 700 for step in steps[options.step:]: |
703 if step.Run(): | 701 if step.Run(): |
704 return 0 | 702 return 0 |
705 return 0 | 703 return 0 |
706 | 704 |
707 def Run(self, args=None): | 705 def Run(self, args=None): |
708 return self.RunSteps(self._Steps(), args) | 706 return self.RunSteps(self._Steps(), args) |
OLD | NEW |