OLD | NEW |
---|---|
1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
2 # Copyright 2014 The Chromium Authors. All rights reserved. | 2 # Copyright 2014 The Chromium Authors. All rights reserved. |
3 # Use of this source code is governed by a BSD-style license that can be | 3 # Use of this source code is governed by a BSD-style license that can be |
4 # found in the LICENSE file. | 4 # found in the LICENSE file. |
5 | 5 |
6 import codecs | 6 import codecs |
7 import copy | 7 import copy |
8 import cStringIO | 8 import cStringIO |
9 import ctypes | 9 import ctypes |
10 import json | 10 import json |
(...skipping 446 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
457 finally: | 457 finally: |
458 os.remove(gclient_output_file) | 458 os.remove(gclient_output_file) |
459 | 459 |
460 | 460 |
461 def gclient_runhooks(gyp_envs): | 461 def gclient_runhooks(gyp_envs): |
462 gclient_bin = 'gclient.bat' if sys.platform.startswith('win') else 'gclient' | 462 gclient_bin = 'gclient.bat' if sys.platform.startswith('win') else 'gclient' |
463 env = dict([env_var.split('=', 1) for env_var in gyp_envs]) | 463 env = dict([env_var.split('=', 1) for env_var in gyp_envs]) |
464 call(gclient_bin, 'runhooks', env=env) | 464 call(gclient_bin, 'runhooks', env=env) |
465 | 465 |
466 | 466 |
467 def create_less_than_or_equal_regex(number): | |
468 """ Return a regular expression to test whether an integer less than or equal | |
469 to 'number' is present in a given string. | |
470 """ | |
471 | |
472 # In three parts, build a regular expression that match any numbers smaller | |
473 # than 'number'. | |
474 # For example, 78656 would give a regular expression that looks like: | |
475 # Part 1 | |
476 # (78356| # 78356 | |
477 # Part 2 | |
478 # 7835[0-5]| # 78350-78355 | |
479 # 783[0-4][0-9]| # 78300-78349 | |
480 # 78[0-2][0-9]{2}| # 78000-78299 | |
481 # 7[0-7][0-9]{3}| # 70000-77999 | |
482 # [0-6][0-9]{4}| # 10000-69999 | |
483 # Part 3 | |
484 # [0-9]{1,4} # 0-9999 | |
485 | |
486 # Part 1: Create an array with all the regexes, as described above. | |
487 # Prepopulate it with the number itself. | |
488 number = str(number) | |
489 expressions = [number] | |
490 | |
491 # Convert the number to a list, so we can translate digits in it to | |
492 # expressions. | |
493 num_list = list(number) | |
494 num_len = len(num_list) | |
495 | |
496 # Part 2: Go through all the digits in the number, starting from the end. | |
497 # Each iteration appends a line to 'expressions'. | |
498 for index in range (num_len - 1, -1, -1): | |
499 # Convert this digit back to an integer. | |
500 digit = int(num_list[index]) | |
501 | |
502 # Part 2.1: No processing if this digit is a zero. | |
503 if digit == 0: | |
504 continue | |
505 | |
506 # Part 2.2: We switch the current digit X by a range "[0-(X-1)]". | |
507 if digit == 1: | |
508 num_list[index] = '0' | |
509 else: | |
510 num_list[index] = '[0-%d]' % (digit - 1) | |
511 | |
512 # Part 2.3: We set all following digits to be "[0-9]". | |
513 # Since we just decrementented a digit in a most important position, all | |
514 # following digits don't matter. The possible numbers will always be smaller | |
515 # than before we decremented. | |
516 if (index + 1) < num_len: | |
517 if (num_len - (index + 1)) == 1: | |
518 num_list[index + 1] = '[0-9]' | |
519 else: | |
520 num_list[index + 1] = '[0-9]{%s}' % (num_len - (index + 1)) | |
521 | |
522 # Part 2.4: Add this new sub-expression to the list. | |
523 expressions.append(''.join(num_list[:min(index+2, num_len)])) | |
524 | |
525 # Part 3: We add all the full ranges to match all numbers that are at least | |
526 # one order of magnitude smaller than the original numbers. | |
527 if num_len == 2: | |
528 expressions.append('[0-9]') | |
529 elif num_len > 2: | |
530 expressions.append('[0-9]{1,%s}' % (num_len - 1)) | |
531 | |
532 # All done. We now have our final regular expression. | |
533 regex = '(%s)' % ('|'.join(expressions)) | |
534 return regex | |
535 | |
536 | |
537 def get_svn_rev(git_hash, dir_name): | 467 def get_svn_rev(git_hash, dir_name): |
538 pattern = r'^\s*git-svn-id: [^ ]*@(\d+) ' | 468 pattern = r'^\s*git-svn-id: [^ ]*@(\d+) ' |
539 lkcr_pattern = r'^\s*LK[CG]R w/ DEPS up to revision (\d+)' | |
540 log = git('log', '-1', git_hash, cwd=dir_name) | 469 log = git('log', '-1', git_hash, cwd=dir_name) |
541 match = re.search(pattern, log, re.M) | 470 match = re.search(pattern, log, re.M) |
542 if not match: | 471 if not match: |
543 # This might be a patched checkout, try the parent commit. | 472 return None |
544 log = git('log', '-1', '%s^' % git_hash, cwd=dir_name) | |
545 match = re.search(pattern, log, re.M) | |
546 if not match: | |
547 # Might be patched on top of LKCR, which has a special message. | |
548 match = re.search(lkcr_pattern, log, re.M) | |
549 if not match: | |
550 return None | |
551 return int(match.group(1)) | 473 return int(match.group(1)) |
552 | 474 |
553 | 475 |
554 def get_git_hash(revision, dir_name): | 476 def get_git_hash(revision, sln_dir): |
555 match = "^git-svn-id: [^ ]*@%s " % create_less_than_or_equal_regex(revision) | 477 """We want to search for the SVN revision on the git-svn branch. |
478 | |
479 Note that for this to work, the git checkout in sln_dir must be newer and in | |
480 the same lineage as the commit we are searching for. This is because Git | |
481 searches backwards from the current commit. | |
iannucci
2014/05/08 23:50:06
s/current commit/HEAD
though you could specify th
hinoka
2014/05/10 00:54:08
Redid this to always start from origin/master
| |
482 """ | |
483 match = "^git-svn-id: [^ ]*@%s " % revision | |
556 cmd = ['log', '-E', '--grep', match, '--format=%H', '--max-count=1'] | 484 cmd = ['log', '-E', '--grep', match, '--format=%H', '--max-count=1'] |
557 results = git(*cmd, cwd=dir_name).strip().splitlines() | 485 result = git(*cmd, cwd=sln_dir).strip() |
558 if results: | 486 if result: |
559 return results[0] | 487 return result |
560 raise Exception('We can\'t resolve svn revision %s into a git hash' % | 488 raise SVNRevisionNotFound('We can\'t resolve svn r%s into a git hash in %s' % |
561 revision) | 489 (revision, sln_dir)) |
562 | 490 |
563 | 491 |
564 def get_revision_mapping(root, addl_rev_map): | 492 def get_revision_mapping(root, addl_rev_map): |
565 result = {} | 493 result = {} |
566 if root in GOT_REVISION_MAPPINGS: | 494 if root in GOT_REVISION_MAPPINGS: |
567 result.update(GOT_REVISION_MAPPINGS[root]) | 495 result.update(GOT_REVISION_MAPPINGS[root]) |
568 if addl_rev_map: | 496 if addl_rev_map: |
569 result.update(json.loads(addl_rev_map)) | 497 result.update(json.loads(addl_rev_map)) |
570 return result | 498 return result |
571 | 499 |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
701 raise ctypes.WinError() | 629 raise ctypes.WinError() |
702 return (total.value, free.value) | 630 return (total.value, free.value) |
703 | 631 |
704 else: | 632 else: |
705 st = os.statvfs(cwd) | 633 st = os.statvfs(cwd) |
706 free = st.f_bavail * st.f_frsize | 634 free = st.f_bavail * st.f_frsize |
707 total = st.f_blocks * st.f_frsize | 635 total = st.f_blocks * st.f_frsize |
708 return (total, free) | 636 return (total, free) |
709 | 637 |
710 | 638 |
711 def git_checkout(solutions, revision, shallow): | 639 def get_revision(folder_name, git_url, revisions): |
640 normalized_name = folder_name.strip('/') | |
641 if normalized_name in revisions: | |
642 return revisions[normalized_name] | |
643 if git_url in revisions: | |
644 return revisions[git_url] | |
645 return None | |
646 | |
647 | |
648 def force_revision(folder_name, revision): | |
649 # We do this first because git log --grep only traverses backwards. | |
650 # TODO(hinoka): Prefer origin/git-svn if it exists. | |
iannucci
2014/05/08 23:50:06
You should just pass origin/master to `git log` in
hinoka
2014/05/10 00:54:08
Done.
| |
651 git('checkout', 'origin/master', cwd=folder_name) | |
652 if revision and revision.lower() != 'head': | |
653 if revision and revision.isdigit() and len(revision) < 40: | |
654 # rev_num is really a svn revision number, convert it into a git hash. | |
655 git_ref = get_git_hash(int(revision), folder_name) | |
656 else: | |
657 # rev_num is actually a git hash or ref, we can just use it. | |
658 git_ref = revision | |
659 git('checkout', git_ref, cwd=folder_name) | |
660 | |
661 | |
662 def git_checkout(solutions, revisions, shallow): | |
712 build_dir = os.getcwd() | 663 build_dir = os.getcwd() |
713 # Before we do anything, break all git_cache locks. | 664 # Before we do anything, break all git_cache locks. |
714 if path.isdir(CACHE_DIR): | 665 if path.isdir(CACHE_DIR): |
715 git('cache', 'unlock', '-vv', '--force', '--all', '--cache-dir', CACHE_DIR) | 666 git('cache', 'unlock', '-vv', '--force', '--all', '--cache-dir', CACHE_DIR) |
716 for item in os.listdir(CACHE_DIR): | 667 for item in os.listdir(CACHE_DIR): |
717 filename = os.path.join(CACHE_DIR, item) | 668 filename = os.path.join(CACHE_DIR, item) |
718 if item.endswith('.lock'): | 669 if item.endswith('.lock'): |
719 raise Exception('%s exists after cache unlock' % filename) | 670 raise Exception('%s exists after cache unlock' % filename) |
720 # Revision only applies to the first solution. | |
721 first_solution = True | 671 first_solution = True |
722 for sln in solutions: | 672 for sln in solutions: |
723 # This is so we can loop back and try again if we need to wait for the | 673 # This is so we can loop back and try again if we need to wait for the |
724 # git mirrors to update from SVN. | 674 # git mirrors to update from SVN. |
725 done = False | 675 done = False |
726 tries_left = 60 | 676 tries_left = 60 |
727 while not done: | 677 while not done: |
728 done = True | 678 done = True |
729 name = sln['name'] | 679 name = sln['name'] |
730 url = sln['url'] | 680 url = sln['url'] |
(...skipping 21 matching lines...) Expand all Loading... | |
752 # Lets wipe the checkout and try again. | 702 # Lets wipe the checkout and try again. |
753 chromium_utils.RemoveDirectory(sln_dir) | 703 chromium_utils.RemoveDirectory(sln_dir) |
754 git(*clone_cmd) | 704 git(*clone_cmd) |
755 git('checkout', '--force', 'origin/master', cwd=sln_dir) | 705 git('checkout', '--force', 'origin/master', cwd=sln_dir) |
756 git('reset', '--hard', cwd=sln_dir) | 706 git('reset', '--hard', cwd=sln_dir) |
757 else: | 707 else: |
758 raise | 708 raise |
759 | 709 |
760 git('clean', '-df', cwd=sln_dir) | 710 git('clean', '-df', cwd=sln_dir) |
761 git('fetch', 'origin', cwd=sln_dir) | 711 git('fetch', 'origin', cwd=sln_dir) |
762 # TODO(hinoka): We probably have to make use of revision mapping. | |
763 if first_solution and revision and revision.lower() != 'head': | |
764 if revision and revision.isdigit() and len(revision) < 40: | |
765 # rev_num is really a svn revision number, convert it into a git hash. | |
766 git_ref = get_git_hash(int(revision), name) | |
767 # Lets make sure our checkout has the correct revision number. | |
768 got_revision = get_svn_rev(git_ref, sln_dir) | |
769 if not got_revision or int(got_revision) != int(revision): | |
770 tries_left -= 1 | |
771 if tries_left > 0: | |
772 # If we don't have the correct revision, wait and try again. | |
773 print 'We want revision %s, but got revision %s.' % ( | |
774 revision, got_revision) | |
775 print 'The svn to git replicator is probably falling behind.' | |
776 print 'waiting 5 seconds and trying again...' | |
777 time.sleep(5) | |
778 done = False | |
779 continue | |
780 raise SVNRevisionNotFound | |
781 else: | |
782 # rev_num is actually a git hash or ref, we can just use it. | |
783 git_ref = revision | |
784 git('checkout', git_ref, cwd=sln_dir) | |
785 else: | |
786 git('checkout', 'origin/master', cwd=sln_dir) | |
787 if first_solution: | |
788 git_ref = git('log', '--format=%H', '--max-count=1', | |
789 cwd=sln_dir).strip() | |
790 | 712 |
713 revision = get_revision(name, url, revisions) or 'HEAD' | |
714 try: | |
715 force_revision(sln_dir, revision) | |
716 except SVNRevisionNotFound: | |
717 tries_left -= 1 | |
718 if tries_left > 0: | |
719 # If we don't have the correct revision, wait and try again. | |
720 print 'We can\'t find revision %s.' % revision | |
721 print 'The svn to git replicator is probably falling behind.' | |
722 print 'waiting 5 seconds and trying again...' | |
723 time.sleep(5) | |
iannucci
2014/05/08 23:50:06
ick :/
hinoka
2014/05/10 00:54:08
As long as we are mirroring, we need a sleep somew
| |
724 done = False | |
725 continue | |
726 raise | |
727 | |
728 if first_solution: | |
729 git_ref = git('log', '--format=%H', '--max-count=1', | |
730 cwd=sln_dir).strip() | |
791 first_solution = False | 731 first_solution = False |
792 return git_ref | 732 return git_ref |
793 | 733 |
794 | 734 |
795 def _download(url): | 735 def _download(url): |
796 """Fetch url and return content, with retries for flake.""" | 736 """Fetch url and return content, with retries for flake.""" |
797 for attempt in xrange(RETRIES): | 737 for attempt in xrange(RETRIES): |
798 try: | 738 try: |
799 return urllib2.urlopen(url).read() | 739 return urllib2.urlopen(url).read() |
800 except Exception: | 740 except Exception: |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
859 for dir_name, property_name in got_revision_mapping.iteritems(): | 799 for dir_name, property_name in got_revision_mapping.iteritems(): |
860 if dir_name not in solutions_output: | 800 if dir_name not in solutions_output: |
861 continue | 801 continue |
862 solution_output = solutions_output[dir_name] | 802 solution_output = solutions_output[dir_name] |
863 if solution_output.get('scm') is None: | 803 if solution_output.get('scm') is None: |
864 # This is an ignored DEPS, so the output got_revision should be 'None'. | 804 # This is an ignored DEPS, so the output got_revision should be 'None'. |
865 git_revision = revision = None | 805 git_revision = revision = None |
866 else: | 806 else: |
867 # Since we are using .DEPS.git, everything had better be git. | 807 # Since we are using .DEPS.git, everything had better be git. |
868 assert solution_output.get('scm') == 'git' | 808 assert solution_output.get('scm') == 'git' |
869 git_revision = get_real_git_hash(solution_output['revision'], dir_name) | 809 git_revision = git('log', '-1', '--format=%H', cwd=dir_name).strip() |
iannucci
2014/05/08 23:50:06
er... `git rev-parse HEAD` ?
hinoka
2014/05/10 00:54:08
Done.
| |
870 if use_svn_revs: | 810 if use_svn_revs: |
871 revision = get_svn_rev(git_revision, dir_name) | 811 revision = get_svn_rev(git_revision, dir_name) |
872 if not revision: | 812 if not revision: |
873 revision = git_revision | 813 revision = git_revision |
874 else: | 814 else: |
875 revision = git_revision | 815 revision = git_revision |
876 | 816 |
877 properties[property_name] = revision | 817 properties[property_name] = revision |
878 if revision != git_revision: | 818 if revision != git_revision: |
879 properties['%s_git' % property_name] = git_revision | 819 properties['%s_git' % property_name] = git_revision |
880 | 820 |
881 return properties | 821 return properties |
882 | 822 |
883 | 823 |
884 def emit_json(out_file, did_run, gclient_output=None, **kwargs): | 824 def emit_json(out_file, did_run, gclient_output=None, **kwargs): |
885 """Write run information into a JSON file.""" | 825 """Write run information into a JSON file.""" |
886 output = {} | 826 output = {} |
887 output.update(gclient_output if gclient_output else {}) | 827 output.update(gclient_output if gclient_output else {}) |
888 output.update({'did_run': did_run}) | 828 output.update({'did_run': did_run}) |
889 output.update(kwargs) | 829 output.update(kwargs) |
890 with open(out_file, 'wb') as f: | 830 with open(out_file, 'wb') as f: |
891 f.write(json.dumps(output)) | 831 f.write(json.dumps(output)) |
892 | 832 |
893 | 833 |
894 def ensure_checkout(solutions, revision, first_sln, target_os, target_os_only, | 834 def ensure_deps_revisions(deps_url_mapping, solutions, revisions): |
835 """Ensure correct DEPS revisions, ignores solutions.""" | |
836 for deps_name, deps_data in sorted(deps_url_mapping.items()): | |
837 if deps_name.strip('/') in solutions: | |
838 # This has already been forced to the correct solution by git_checkout(). | |
839 continue | |
840 revision = get_revision(deps_name, deps_data.get('url', None), revisions) | |
841 if not revision: | |
842 continue | |
843 # TODO(hinoka): Catch SVNRevisionNotFound error maybe? | |
844 force_revision(deps_name, revision) | |
845 | |
846 | |
847 def ensure_checkout(solutions, revisions, first_sln, target_os, target_os_only, | |
895 root, issue, patchset, patch_url, rietveld_server, | 848 root, issue, patchset, patch_url, rietveld_server, |
896 revision_mapping, buildspec_name, gyp_env, shallow): | 849 revision_mapping, buildspec_name, gyp_env, shallow): |
897 # Get a checkout of each solution, without DEPS or hooks. | 850 # Get a checkout of each solution, without DEPS or hooks. |
898 # Calling git directly because there is no way to run Gclient without | 851 # Calling git directly because there is no way to run Gclient without |
899 # invoking DEPS. | 852 # invoking DEPS. |
900 print 'Fetching Git checkout' | 853 print 'Fetching Git checkout' |
901 git_ref = git_checkout(solutions, revision, shallow) | 854 git_ref = git_checkout(solutions, revisions, shallow) |
902 | 855 |
903 # If either patch_url or issue is passed in, then we need to apply a patch. | 856 # If either patch_url or issue is passed in, then we need to apply a patch. |
904 if patch_url: | 857 if patch_url: |
905 # patch_url takes precidence since its only passed in on gcl try/git try. | 858 # patch_url takes precidence since its only passed in on gcl try/git try. |
906 apply_issue_svn(root, patch_url) | 859 apply_issue_svn(root, patch_url) |
907 elif issue: | 860 elif issue: |
908 apply_issue_rietveld(issue, patchset, root, rietveld_server, | 861 apply_issue_rietveld(issue, patchset, root, rietveld_server, |
909 revision_mapping, git_ref) | 862 revision_mapping, git_ref) |
910 | 863 |
911 if buildspec_name: | 864 if buildspec_name: |
912 buildspecs2git(root, buildspec_name) | 865 buildspecs2git(root, buildspec_name) |
913 elif first_sln == root: | 866 elif first_sln == root: |
914 # Run deps2git if there is a DEPS commit after the last .DEPS.git commit. | 867 # Run deps2git if there is a DEPS commit after the last .DEPS.git commit. |
915 # We only need to ensure deps2git if the root is not overridden, since | 868 # We only need to ensure deps2git if the root is not overridden, since |
916 # if the root is overridden, it means we are working with a sub repository | 869 # if the root is overridden, it means we are working with a sub repository |
917 # patch, which means its impossible for it to touch DEPS. | 870 # patch, which means its impossible for it to touch DEPS. |
918 ensure_deps2git(root, shallow) | 871 ensure_deps2git(root, shallow) |
919 | 872 |
920 # Ensure our build/ directory is set up with the correct .gclient file. | 873 # Ensure our build/ directory is set up with the correct .gclient file. |
921 gclient_configure(solutions, target_os, target_os_only) | 874 gclient_configure(solutions, target_os, target_os_only) |
922 | 875 |
923 # Let gclient do the DEPS syncing. | 876 # Let gclient do the DEPS syncing. |
924 gclient_output = gclient_sync(buildspec_name) | 877 gclient_output = gclient_sync(buildspec_name) |
925 if buildspec_name: | 878 if buildspec_name: |
926 # Run gclient runhooks if we're on an official builder. | 879 # Run gclient runhooks if we're on an official builder. |
927 # TODO(hinoka): Remove this when the official builders run their own | 880 # TODO(hinoka): Remove this when the official builders run their own |
928 # runhooks step. | 881 # runhooks step. |
929 gclient_runhooks(gyp_env) | 882 gclient_runhooks(gyp_env) |
883 | |
884 # Finally, ensure that all DEPS are pinned to the correct revision. | |
885 dir_names = [sln['name'] for sln in solutions] | |
886 ensure_deps_revisions(gclient_output.get('solutions', {}), | |
887 dir_names, revisions) | |
930 return gclient_output | 888 return gclient_output |
931 | 889 |
932 | 890 |
891 def parse_revisions(revisions, root): | |
892 """Turn a list of revision specs into a nice dictionary. | |
893 | |
894 We will always return a dict with {root: something}. By default if root | |
iannucci
2014/05/08 23:50:06
is 'root' like 'src' or 'src/tools/gyp' ?
hinoka
2014/05/10 00:54:08
both!
I'm expecting things like src and src/third_
| |
895 is unspecified, or if revisions is [], then revision will be assigned 'HEAD' | |
896 """ | |
897 results = {root.strip('/'): 'HEAD'} | |
898 for revision in revisions: | |
899 split_revision = revision.split('@') | |
900 if len(split_revision) == 1: | |
901 # This is just a plain revision, set it as the revision for root. | |
902 results[root] = split_revision[0] | |
903 elif len(split_revision) == 2: | |
904 # This is an alt_root@revision argument. | |
905 current_root, current_rev = split_revision | |
906 | |
907 # We want to normalize svn/git urls into .git urls. | |
908 parsed_root = urlparse.urlparse(current_root) | |
909 if parsed_root.scheme == 'svn': | |
910 if parsed_root.path in RECOGNIZED_PATHS: | |
911 normalized_root = RECOGNIZED_PATHS[parsed_root.path] | |
912 else: | |
913 print 'WARNING: SVN path %s not recognized, ignoring' % current_root | |
iannucci
2014/05/08 23:50:06
in general I would recommend using the logging mod
hinoka
2014/05/10 00:54:08
I'll agree, but that sounds like a rabbit hole. I
| |
914 continue | |
915 elif parsed_root.scheme in ['http', 'https']: | |
916 normalized_root = 'https://%s/%s' % (parsed_root.netloc, | |
917 parsed_root.path) | |
918 if not normalized_root.endswith('.git'): | |
919 normalized_root = '%s.git' % normalized_root | |
920 elif parsed_root.scheme: | |
921 print 'WARNING: Unrecognized scheme %s, ignoring' % parsed_root.scheme | |
922 continue | |
923 else: | |
924 # This is probably a local path. | |
925 normalized_root = current_root.strip('/') | |
926 | |
927 results[normalized_root] = current_rev | |
928 else: | |
929 print ('WARNING: %s is not recognized as a valid revision specification,' | |
iannucci
2014/05/08 23:50:06
I would use %r (everywhere) to get automatic quoti
hinoka
2014/05/10 00:54:08
Done.
| |
930 'skipping' % revision) | |
931 return results | |
932 | |
933 | |
933 def parse_args(): | 934 def parse_args(): |
934 parse = optparse.OptionParser() | 935 parse = optparse.OptionParser() |
935 | 936 |
936 parse.add_option('--issue', help='Issue number to patch from.') | 937 parse.add_option('--issue', help='Issue number to patch from.') |
937 parse.add_option('--patchset', | 938 parse.add_option('--patchset', |
938 help='Patchset from issue to patch from, if applicable.') | 939 help='Patchset from issue to patch from, if applicable.') |
939 parse.add_option('--patch_url', help='Optional URL to SVN patch.') | 940 parse.add_option('--patch_url', help='Optional URL to SVN patch.') |
940 parse.add_option('--root', help='Repository root.') | 941 parse.add_option('--root', help='Repository root.') |
941 parse.add_option('--rietveld_server', | 942 parse.add_option('--rietveld_server', |
942 default='codereview.chromium.org', | 943 default='codereview.chromium.org', |
943 help='Rietveld server.') | 944 help='Rietveld server.') |
944 parse.add_option('--specs', help='Gcilent spec.') | 945 parse.add_option('--specs', help='Gcilent spec.') |
945 parse.add_option('--master', help='Master name.') | 946 parse.add_option('--master', help='Master name.') |
946 parse.add_option('-f', '--force', action='store_true', | 947 parse.add_option('-f', '--force', action='store_true', |
947 help='Bypass check to see if we want to be run. ' | 948 help='Bypass check to see if we want to be run. ' |
948 'Should ONLY be used locally.') | 949 'Should ONLY be used locally.') |
949 parse.add_option('--revision_mapping') | 950 parse.add_option('--revision_mapping') |
950 parse.add_option('--revision-mapping') # Backwards compatability. | 951 parse.add_option('--revision-mapping') # Backwards compatability. |
951 # TODO(hinoka): Support root@revision format. | 952 parse.add_option('--revision', action='append', default=[], |
952 parse.add_option('--revision', | |
953 help='Revision to check out. Can be an SVN revision number, ' | 953 help='Revision to check out. Can be an SVN revision number, ' |
954 'git hash, or any form of git ref.') | 954 'git hash, or any form of git ref. Can prepend ' |
955 'root@<rev> to specify which repository, where root ' | |
956 'is either a filesystem path, git https url, or ' | |
957 'svn url. To specify Tip of Tree, set rev to HEAD.') | |
iannucci
2014/05/08 23:50:06
Note that gclient would accept `--revision src@<re
hinoka
2014/05/10 00:54:08
Discussed offline - All revision handling is done
| |
955 parse.add_option('--slave_name', default=socket.getfqdn().split('.')[0], | 958 parse.add_option('--slave_name', default=socket.getfqdn().split('.')[0], |
956 help='Hostname of the current machine, ' | 959 help='Hostname of the current machine, ' |
957 'used for determining whether or not to activate.') | 960 'used for determining whether or not to activate.') |
958 parse.add_option('--builder_name', help='Name of the builder, ' | 961 parse.add_option('--builder_name', help='Name of the builder, ' |
959 'used for determining whether or not to activate.') | 962 'used for determining whether or not to activate.') |
960 parse.add_option('--build_dir', default=os.getcwd()) | 963 parse.add_option('--build_dir', default=os.getcwd()) |
961 parse.add_option('--flag_file', default=path.join(os.getcwd(), | 964 parse.add_option('--flag_file', default=path.join(os.getcwd(), |
962 'update.flag')) | 965 'update.flag')) |
963 parse.add_option('--shallow', action='store_true', | 966 parse.add_option('--shallow', action='store_true', |
964 help='Use shallow clones for cache repositories.') | 967 help='Use shallow clones for cache repositories.') |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1035 print '@@@STEP_TEXT@%s@@@' % step_text | 1038 print '@@@STEP_TEXT@%s@@@' % step_text |
1036 if not options.shallow: | 1039 if not options.shallow: |
1037 options.shallow = total_disk_space < SHALLOW_CLONE_THRESHOLD | 1040 options.shallow = total_disk_space < SHALLOW_CLONE_THRESHOLD |
1038 | 1041 |
1039 # By default, the root should be the name of the first solution, but | 1042 # By default, the root should be the name of the first solution, but |
1040 # also make it overridable. The root is where patches are applied on top of. | 1043 # also make it overridable. The root is where patches are applied on top of. |
1041 options.root = options.root or dir_names[0] | 1044 options.root = options.root or dir_names[0] |
1042 # The first solution is where the primary DEPS file resides. | 1045 # The first solution is where the primary DEPS file resides. |
1043 first_sln = dir_names[0] | 1046 first_sln = dir_names[0] |
1044 | 1047 |
1048 # Split all the revision specifications into a nice dict. | |
1049 print 'Revisions: %s' % options.revision | |
1050 revisions = parse_revisions(options.revision, options.root) | |
1051 # This is meant to be just an alias to the revision of the main solution. | |
1052 root_revision = revisions[options.root] | |
1053 print 'Fetching Git checkout at %s@%s' % (options.root, root_revision) | |
1054 | |
1045 try: | 1055 try: |
1046 checkout_parameters = dict( | 1056 checkout_parameters = dict( |
1047 # First, pass in the base of what we want to check out. | 1057 # First, pass in the base of what we want to check out. |
1048 solutions=git_solutions, | 1058 solutions=git_solutions, |
1049 revision=options.revision, | 1059 revisions=revisions, |
1050 first_sln=first_sln, | 1060 first_sln=first_sln, |
1051 | 1061 |
1052 # Also, target os variables for gclient. | 1062 # Also, target os variables for gclient. |
1053 target_os=specs.get('target_os', []), | 1063 target_os=specs.get('target_os', []), |
1054 target_os_only=specs.get('target_os_only', False), | 1064 target_os_only=specs.get('target_os_only', False), |
1055 | 1065 |
1056 # Then, pass in information about how to patch on top of the checkout. | 1066 # Then, pass in information about how to patch on top of the checkout. |
1057 root=options.root, | 1067 root=options.root, |
1058 issue=options.issue, | 1068 issue=options.issue, |
1059 patchset=options.patchset, | 1069 patchset=options.patchset, |
(...skipping 28 matching lines...) Expand all Loading... | |
1088 patch_root=options.root, | 1098 patch_root=options.root, |
1089 step_text=step_text, | 1099 step_text=step_text, |
1090 properties=got_revisions) | 1100 properties=got_revisions) |
1091 else: | 1101 else: |
1092 # If we're not on recipes, tell annotator about our got_revisions. | 1102 # If we're not on recipes, tell annotator about our got_revisions. |
1093 emit_properties(got_revisions) | 1103 emit_properties(got_revisions) |
1094 | 1104 |
1095 | 1105 |
1096 if __name__ == '__main__': | 1106 if __name__ == '__main__': |
1097 sys.exit(main()) | 1107 sys.exit(main()) |
OLD | NEW |