Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(493)

Unified Diff: owners.py

Issue 11638019: Revert "Try again to land the improved owners algorithm." again :). (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/tools/depot_tools
Patch Set: Created 8 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | tests/owners_unittest.py » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: owners.py
diff --git a/owners.py b/owners.py
index a863a7853ca78ffa9740289cd1d90e558071e813..1b1775f08c48ecbbb720c7d622c30d5932e7f84e 100644
--- a/owners.py
+++ b/owners.py
@@ -49,7 +49,6 @@ Examples for all of these combinations can be found in tests/owners_unittest.py.
"""
import collections
-import random
import re
@@ -253,60 +252,60 @@ class Database(object):
('%s is not a "set" directive, "*", '
'or an email address: "%s"' % (line_type, directive)))
+
def _covering_set_of_owners_for(self, files):
- dirs_remaining = set(self._enclosing_dir_with_owners(f) for f in files)
- all_possible_owners = self._all_possible_owners(dirs_remaining)
- suggested_owners = set()
- while dirs_remaining:
- owner = self.lowest_cost_owner(all_possible_owners, dirs_remaining)
- suggested_owners.add(owner)
- for dirname, _ in all_possible_owners[owner]:
- dirs_remaining.remove(dirname)
- return suggested_owners
-
- def _all_possible_owners(self, dirs):
- """Returns a list of (potential owner, distance-from-dir) tuples; a
- distance of 1 is the lowest/closest possible distance (which makes the
- subsequent math easier)."""
- all_possible_owners = {}
+ # Get the set of directories from the files.
+ dirs = set()
+ for f in files:
+ dirs.add(self._enclosing_dir_with_owners(f))
+
+
+ owned_dirs = {}
+ dir_owners = {}
+
for current_dir in dirs:
+ # Get the list of owners for each directory.
+ current_owners = set()
dirname = current_dir
- distance = 1
- while True:
- for owner in self.owners_for.get(dirname, []):
- all_possible_owners.setdefault(owner, [])
- # It's possible the same owner might match a directory from
- # multiple files, and we only want the closest entry.
- if not any(current_dir == el[0] for el in all_possible_owners[owner]):
- all_possible_owners[owner].append((current_dir, distance))
+ while dirname in self.owners_for:
+ current_owners |= self.owners_for[dirname]
if self._stop_looking(dirname):
break
+ prev_parent = dirname
dirname = self.os_path.dirname(dirname)
- distance += 1
- return all_possible_owners
-
- @staticmethod
- def lowest_cost_owner(all_possible_owners, dirs):
- # We want to minimize both the number of reviewers and the distance
- # from the files/dirs needing reviews. The "pow(X, 1.75)" below is
- # an arbitrarily-selected scaling factor that seems to work well - it
- # will select one reviewer in the parent directory over three reviewers
- # in subdirs, but not one reviewer over just two.
- total_costs_by_owner = {}
- for owner in all_possible_owners:
- total_distance = 0
- num_directories_owned = 0
- for dirname, distance in all_possible_owners[owner]:
- if dirname in dirs:
- total_distance += distance
- num_directories_owned += 1
- if num_directories_owned:
- total_costs_by_owner[owner] = (total_distance /
- pow(num_directories_owned, 1.75))
-
- # Return the lowest cost owner. In the case of a tie, pick one randomly.
- lowest_cost = min(total_costs_by_owner.itervalues())
- lowest_cost_owners = filter(
- lambda owner: total_costs_by_owner[owner] == lowest_cost,
- total_costs_by_owner)
- return random.Random().choice(lowest_cost_owners)
+ if prev_parent == dirname:
+ break
+
+ # Map each directory to a list of its owners.
+ dir_owners[current_dir] = current_owners
+
+ # Add the directory to the list of each owner.
+ for owner in current_owners:
+ owned_dirs.setdefault(owner, set()).add(current_dir)
+
+ final_owners = set()
+ while dirs:
+ # Find the owner that has the most directories.
+ max_count = 0
+ max_owner = None
+ owner_count = {}
+ for dirname in dirs:
+ for owner in dir_owners[dirname]:
+ count = owner_count.get(owner, 0) + 1
+ owner_count[owner] = count
+ if count >= max_count:
+ max_owner = owner
+ max_count = count
+
+ # If no more directories have OWNERS, we're done.
+ if not max_owner:
+ break
+
+ final_owners.add(max_owner)
+
+ # Remove all directories owned by the current owner from the remaining
+ # list.
+ for dirname in owned_dirs[max_owner]:
+ dirs.discard(dirname)
+
+ return final_owners
« no previous file with comments | « no previous file | tests/owners_unittest.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698