branches.py 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150
  1. #
  2. # Copyright (C) 2009 The Android Open Source Project
  3. #
  4. # Licensed under the Apache License, Version 2.0 (the "License");
  5. # you may not use this file except in compliance with the License.
  6. # You may obtain a copy of the License at
  7. #
  8. # http://www.apache.org/licenses/LICENSE-2.0
  9. #
  10. # Unless required by applicable law or agreed to in writing, software
  11. # distributed under the License is distributed on an "AS IS" BASIS,
  12. # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. # See the License for the specific language governing permissions and
  14. # limitations under the License.
  15. import sys
  16. from color import Coloring
  17. from command import Command
  18. class BranchColoring(Coloring):
  19. def __init__(self, config):
  20. Coloring.__init__(self, config, 'branch')
  21. self.current = self.printer('current', fg='green')
  22. self.local = self.printer('local')
  23. self.notinproject = self.printer('notinproject', fg='red')
  24. class BranchInfo(object):
  25. def __init__(self, name):
  26. self.name = name
  27. self.current = 0
  28. self.published = 0
  29. self.published_equal = 0
  30. self.projects = []
  31. def add(self, b):
  32. if b.current:
  33. self.current += 1
  34. if b.published:
  35. self.published += 1
  36. if b.revision == b.published:
  37. self.published_equal += 1
  38. self.projects.append(b)
  39. @property
  40. def IsCurrent(self):
  41. return self.current > 0
  42. @property
  43. def IsPublished(self):
  44. return self.published > 0
  45. @property
  46. def IsPublishedEqual(self):
  47. return self.published_equal == len(self.projects)
  48. class Branches(Command):
  49. common = True
  50. helpSummary = "View current topic branches"
  51. helpUsage = """
  52. %prog [<project>...]
  53. Summarizes the currently available topic branches.
  54. """
  55. def _Options(self, p):
  56. p.add_option('-a', '--all',
  57. dest='all', action='store_true',
  58. help='show all branches, not just the majority')
  59. def Execute(self, opt, args):
  60. projects = self.GetProjects(args)
  61. out = BranchColoring(self.manifest.manifestProject.config)
  62. all = {}
  63. project_cnt = len(projects)
  64. for project in projects:
  65. for name, b in project.GetBranches().iteritems():
  66. b.project = project
  67. if name not in all:
  68. all[name] = BranchInfo(name)
  69. all[name].add(b)
  70. names = all.keys()
  71. names.sort()
  72. if not opt.all and not args:
  73. # No -a and no specific projects listed; try to filter the
  74. # results down to only the majority of projects.
  75. #
  76. n = []
  77. for name in names:
  78. i = all[name]
  79. if i.IsCurrent \
  80. or 80 <= (100 * len(i.projects)) / project_cnt:
  81. n.append(name)
  82. names = n
  83. width = 25
  84. for name in names:
  85. if width < len(name):
  86. width = len(name)
  87. for name in names:
  88. i = all[name]
  89. in_cnt = len(i.projects)
  90. if i.IsCurrent:
  91. current = '*'
  92. hdr = out.current
  93. else:
  94. current = ' '
  95. hdr = out.local
  96. if i.IsPublishedEqual:
  97. published = 'P'
  98. elif i.IsPublished:
  99. published = 'p'
  100. else:
  101. published = ' '
  102. hdr('%c%c %-*s' % (current, published, width, name))
  103. out.write(' |')
  104. if in_cnt < project_cnt and (in_cnt == 1 or opt.all):
  105. fmt = out.write
  106. paths = []
  107. if in_cnt < project_cnt - in_cnt:
  108. type = 'in'
  109. for b in i.projects:
  110. paths.append(b.project.relpath)
  111. else:
  112. fmt = out.notinproject
  113. type = 'not in'
  114. have = set()
  115. for b in i.projects:
  116. have.add(b.project)
  117. for p in projects:
  118. paths.append(p.relpath)
  119. s = ' %s %s' % (type, ', '.join(paths))
  120. if width + 7 + len(s) < 80:
  121. fmt(s)
  122. else:
  123. out.nl()
  124. fmt(' %s:' % type)
  125. for p in paths:
  126. out.nl()
  127. fmt(' %s' % p)
  128. out.nl()