Index: drover.py |
=================================================================== |
--- drover.py (revision 109378) |
+++ drover.py (working copy) |
@@ -6,7 +6,9 @@ |
import optparse |
import os |
import re |
+import string |
import sys |
+import urllib2 |
import breakpad # pylint: disable=W0611 |
@@ -25,6 +27,10 @@ |
--merge <revision> --branch <branch_num> |
Example: %(app)s --merge 12345 --branch 187 |
+[Merge from trunk to milestone] |
+--merge <revision> --milestone <milestone_num> |
+Example: %(app)s -- merge 12345 --milestone 16 |
+ |
[Merge from trunk to local copy] |
--merge <revision> --local |
Example: %(app)s --merge 12345 --local |
@@ -357,6 +363,62 @@ |
""" |
return ['%s/%s' % (f[2], f[3]) for f in files_info] |
M-A Ruel
2011/11/11 21:23:24
another empty line
James Hawkins
2011/11/11 21:50:25
Done.
|
+def getBranchForMilestone(milestone): |
+ """Queries omahaproxy.appspot.com for the branch number given |milestone|. |
+ """ |
+ OMAHA_PROXY_URL = "http://omahaproxy.appspot.com" |
+ request = urllib2.Request(OMAHA_PROXY_URL) |
+ try: |
+ response = urllib2.urlopen(request) |
+ except urllib2.HTTPError, e: |
+ print "Failed to query %s: %d" % (OMAHA_PROXY_URL, e.code) |
+ return None |
+ |
+ # Dictionary of [branch: major]. When searching for the appropriate branch |
+ # matching |milestone|, all major versions that match are added to the |
+ # dictionary. If all of the branches are the same, this branch value is |
+ # returned; otherwise, the user is prompted to accept the largest branch |
+ # value. |
+ branch_dict = {} |
+ |
+ # Slice the first line since it's column information text. |
+ for line in response.readlines()[1:]: |
+ # Version data is CSV. |
+ parameters = string.split(line, ',') |
+ |
+ # Version is the third parameter and consists of a quad of numbers separated |
+ # by periods. |
+ version = string.split(parameters[2], '.') |
+ major = int(version[0], 10) |
+ if major != milestone: |
+ continue |
+ |
+ # Branch number is the third value in the quad. |
+ branch_dict[version[2]] = major |
+ |
+ if not branch_dict: |
+ # |milestone| not found. |
+ print "Milestone provided is invalid" |
+ return None |
+ |
+ # The following returns a sorted list of the keys of |branch_dict|. |
+ sorted_branches = sorted(branch_dict.iterkeys()) |
M-A Ruel
2011/11/11 21:23:24
sorted_branches = sorted(branch_dict)
James Hawkins
2011/11/11 21:50:25
Done.
|
+ branch = sorted_branches[0] |
+ |
+ # If all keys match, the branch is the same for all platforms given |
+ # |milestone|. This is the safe case, so return the branch. |
+ if len(sorted_branches) == 1: |
+ return branch |
+ |
+ # Not all of the platforms have the same branch. Prompt the user and return |
+ # the greatest (by value) branch on success. |
+ if prompt("Not all platforms have the same branch number, " |
+ "continue with branch %s?" % branch): |
+ return branch |
+ |
+ # User cancelled. |
+ return None |
+ |
M-A Ruel
2011/11/11 21:23:24
another empty line
James Hawkins
2011/11/11 21:50:25
Done.
|
def prompt(question): |
while True: |
print question + " [y|n]:", |
@@ -386,6 +448,12 @@ |
SKIP_CHECK_WORKING = True |
PROMPT_FOR_AUTHOR = False |
+ # Translate a given milestone to the appropriate branch number. |
+ if options.milestone: |
+ options.branch = getBranchForMilestone(options.milestone) |
laforge
2011/11/11 21:06:47
I'm not sure that you'll be able to set this value
James Hawkins
2011/11/11 21:11:41
Per-offline, manual tests show that this assignmen
|
+ if options.branch is None: |
M-A Ruel
2011/11/11 21:23:24
if not options.branch:
James Hawkins
2011/11/11 21:50:25
Done.
|
+ return 1 |
+ |
DEFAULT_WORKING = "drover_" + str(revision) |
if options.branch: |
DEFAULT_WORKING += ("_" + options.branch) |
@@ -522,6 +590,8 @@ |
help='Revision to merge from trunk to branch') |
option_parser.add_option('-b', '--branch', |
help='Branch to revert or merge from') |
+ option_parser.add_option('-M', '--milestone', type="int", |
+ help='Milestone to revert or merge from') |
option_parser.add_option('-l', '--local', action='store_true', |
help='Local working copy to merge to') |
option_parser.add_option('-s', '--sbranch', |
@@ -543,14 +613,19 @@ |
option_parser.error("You need at least --merge or --revert") |
return 1 |
M-A Ruel
2011/11/11 21:23:24
optional: maybe:
reference = bool(options.branch o
James Hawkins
2011/11/11 21:50:25
Done.
|
- if options.merge and not options.branch and not options.local: |
+ if (options.merge and not options.branch and not options.milestone and |
+ not options.local): |
option_parser.error("--merge requires either --branch or --local") |
M-A Ruel
2011/11/11 21:23:24
or --milestone ?
James Hawkins
2011/11/11 21:50:25
Done.
|
return 1 |
- if options.local and (options.revert or options.branch): |
+ if options.local and (options.revert or options.branch or options.milestone): |
option_parser.error("--local cannot be used with --revert or --branch") |
M-A Ruel
2011/11/11 21:23:24
or --milestone
James Hawkins
2011/11/11 21:50:25
Done.
|
return 1 |
+ if options.branch and options.milestone: |
+ option_parser.error("--branch cannot be used with --milestone") |
+ return 1 |
+ |
return drover(options, args) |