Diff
Modified: trunk/Tools/ChangeLog (206979 => 206980)
--- trunk/Tools/ChangeLog 2016-10-10 03:11:20 UTC (rev 206979)
+++ trunk/Tools/ChangeLog 2016-10-10 05:22:09 UTC (rev 206980)
@@ -1,5 +1,40 @@
2016-10-09 Simon Fraser <simon.fra...@apple.com>
+ Make validate-committer-lists show inactive reviewers
+ https://bugs.webkit.org/show_bug.cgi?id=163193
+
+ Reviewed by Sam Weinig.
+
+ In preparation for updating contributors.json with the WebKit policy of retiring
+ inactive reviewers, make validate-committer-lists show the list of reviewers who
+ have not reviewed in the past year.
+
+ This list is computed by grepping the output of 'git log --since=1.year" for
+ the reviewer line, and looking up reviewers via Contributor.mentioned_in_text(),
+ which looks for full names, aliases, irc nicks and email addresses.
+
+ Support for aliases is added to Contributor. Aliases are alternates
+ or misspellings of the reviewer's name. Some common aliases were added to
+ contributors.json by manual examination of "Reviewed by" lines.
+
+ * Scripts/validate-committer-lists:
+ (CommitterListFromGit.possibly_expired_committers):
+ (CommitterListFromGit):
+ (CommitterListFromGit.possibly_inactive_reviewers):
+ (CommitterListFromGit.print_possibly_expired_committers):
+ (CommitterListFromGit.print_possibly_inactive_reviewers):
+ * Scripts/webkitpy/common/config/committers.py:
+ (Contributor.__init__):
+ (Contributor.contains_string):
+ (Contributor.mentioned_in_text):
+ (Contributor.as_dict):
+ (Committer.__init__):
+ (Reviewer.__init__):
+ (CommitterList.load_json):
+ * Scripts/webkitpy/common/config/contributors.json:
+
+2016-10-09 Simon Fraser <simon.fra...@apple.com>
+
Convert contributors.json to a flat list
https://bugs.webkit.org/show_bug.cgi?id=163183
Modified: trunk/Tools/Scripts/validate-committer-lists (206979 => 206980)
--- trunk/Tools/Scripts/validate-committer-lists 2016-10-10 03:11:20 UTC (rev 206979)
+++ trunk/Tools/Scripts/validate-committer-lists 2016-10-10 05:22:09 UTC (rev 206980)
@@ -40,6 +40,7 @@
from optparse import OptionParser
from webkitpy.common.config.committers import CommitterList
+from webkitpy.common.checkout.changelog import ChangeLogEntry
from webkitpy.common.checkout.scm import Git
from webkitpy.common.net.bugzilla import Bugzilla
@@ -226,6 +227,29 @@
retired_authors_and_last_commits.append((author, last_commit))
return retired_authors_and_last_commits
+ def possibly_inactive_reviewers(self, committer_list):
+ git_log_args = ['git', 'log', '--since=1.year']
+ process = subprocess.Popen(git_log_args, stdout=subprocess.PIPE)
+ git_output, err = process.communicate()
+
+ comment_regex = re.compile(r'^Date: .+?\n+(.+?)(?:^commit |\Z)', re.MULTILINE | re.DOTALL)
+ reviewed_by_regexp = re.compile(ChangeLogEntry.reviewed_by_regexp, re.MULTILINE)
+
+ reviewers = committer_list.reviewers()
+
+ for comment in comment_regex.findall(git_output):
+ reviewer_match = reviewed_by_regexp.search(comment)
+ if reviewer_match:
+ reviewers_text = reviewer_match.group('reviewer').decode('utf-8', 'backslashreplace')
+ # reviewers might be something like "Darin Adler and Dave Hyatt".
+ # Rather than trying to fuzzy match names, find known reviewers and remove them from the list.
+ for reviewer in reviewers:
+ if reviewer.mentioned_in_text(reviewers_text):
+ reviewers.remove(reviewer)
+ break
+
+ return reviewers
+
def print_possibly_expired_committers(self, committer_list):
retired_authors_and_last_commits = self.possibly_expired_committers(committer_list)
column_widths = [13, 25]
@@ -237,6 +261,15 @@
last_commit_date = date.fromtimestamp(last_commit)
self._print_three_column_row(column_widths, (str(last_commit_date), author, committer_record))
+ def print_possibly_inactive_reviewers(self, committer_list):
+ inactive_reviewers = self.possibly_inactive_reviewers(committer_list)
+
+ column_widths = [13, 25]
+ print
+ print "Reviewers who have not reviewed within one year:"
+ for contributor in inactive_reviewers:
+ print "\"{}\" {}".format(contributor.full_name.encode("utf-8"), contributor.bugzilla_email())
+
def print_committers_missing_from_committer_list(self, committer_list):
missing_from_contributors_json = []
last_commit_time_by_author = self._last_commit_by_author()
@@ -294,7 +327,8 @@
if not Git.in_working_directory("."):
print """\n\nWARNING: validate-committer-lists requires a git checkout.
The following checks are disabled:
- - List of committers ordered by last commit
+ - List of inactive committers
+ - List of inactive reviewers
- List of historical committers missing from contributors.json
"""
return 1
@@ -301,6 +335,7 @@
svn_committer_list = CommitterListFromGit()
svn_committer_list.print_possibly_expired_committers(committer_list)
+ svn_committer_list.print_possibly_inactive_reviewers(committer_list)
svn_committer_list.print_committers_missing_from_committer_list(committer_list)
if options.check_bugzilla_emails:
Modified: trunk/Tools/Scripts/webkitpy/common/config/committers.py (206979 => 206980)
--- trunk/Tools/Scripts/webkitpy/common/config/committers.py 2016-10-10 03:11:20 UTC (rev 206979)
+++ trunk/Tools/Scripts/webkitpy/common/config/committers.py 2016-10-10 05:22:09 UTC (rev 206980)
@@ -38,7 +38,7 @@
from webkitpy.common.system.filesystem import FileSystem
class Contributor(object):
- def __init__(self, name, email_or_emails, irc_nickname_or_nicknames=None, expertise=None):
+ def __init__(self, name, email_or_emails, irc_nickname_or_nicknames=None, alias_or_aliases=None, expertise=None):
assert(name)
assert(email_or_emails)
self.full_name = name
@@ -48,10 +48,17 @@
self.emails = email_or_emails
self._case_preserved_emails = self.emails
self.emails = map(lambda email: email.lower(), self.emails) # Emails are case-insensitive.
+
if isinstance(irc_nickname_or_nicknames, str):
self.irc_nicknames = [irc_nickname_or_nicknames]
else:
self.irc_nicknames = irc_nickname_or_nicknames
+
+ if isinstance(alias_or_aliases, str):
+ self.aliases = [alias_or_aliases]
+ else:
+ self.aliases = alias_or_aliases
+
self.expertise = expertise
self.can_commit = False
self.can_review = False
@@ -84,11 +91,32 @@
for nickname in self.irc_nicknames:
if string in nickname.lower():
return True
+ if self.aliases:
+ for alias in self.aliases:
+ if string in alias.lower():
+ return True
for email in self.emails:
if string in email:
return True
return False
+ def mentioned_in_text(self, text):
+ lower_text = text.lower()
+ if self.full_name.lower() in lower_text:
+ return True
+ if self.irc_nicknames:
+ for nickname in self.irc_nicknames:
+ if nickname.lower() in lower_text:
+ return True
+ if self.aliases:
+ for alias in self.aliases:
+ if alias.lower() in lower_text:
+ return True
+ for email in self.emails:
+ if email in lower_text:
+ return True
+ return False
+
def matches_glob(self, glob_string):
if fnmatch.fnmatch(self.full_name, glob_string):
return True
@@ -104,6 +132,9 @@
def as_dict(self):
info = {"emails" : self._case_preserved_emails}
+ if self.aliases:
+ info["aliases"] = self.aliases
+
if self.can_review:
info["status"] = "reviewer"
elif self.can_commit:
@@ -119,14 +150,14 @@
class Committer(Contributor):
- def __init__(self, name, email_or_emails, irc_nickname=None, expertise=None):
- Contributor.__init__(self, name, email_or_emails, irc_nickname, expertise)
+ def __init__(self, name, email_or_emails, irc_nickname=None, alias_or_aliases=None, expertise=None):
+ Contributor.__init__(self, name, email_or_emails, irc_nickname, alias_or_aliases, expertise)
self.can_commit = True
class Reviewer(Committer):
- def __init__(self, name, email_or_emails, irc_nickname=None, expertise=None):
- Committer.__init__(self, name, email_or_emails, irc_nickname, expertise)
+ def __init__(self, name, email_or_emails, irc_nickname=None, alias_or_aliases=None, expertise=None):
+ Committer.__init__(self, name, email_or_emails, irc_nickname, alias_or_aliases, expertise)
self.can_review = True
@@ -162,14 +193,14 @@
contributor = None
status = data.get('status')
if status == "reviewer":
- contributor = Reviewer(name, data.get('emails'), data.get('nicks'), data.get('expertise'))
+ contributor = Reviewer(name, data.get('emails'), data.get('nicks'), data.get('aliases'), data.get('expertise'))
self._reviewers.append(contributor)
self._committers.append(contributor)
elif status == "committer":
- contributor = Committer(name, data.get('emails'), data.get('nicks'), data.get('expertise'))
+ contributor = Committer(name, data.get('emails'), data.get('nicks'), data.get('aliases'), data.get('expertise'))
self._committers.append(contributor)
else:
- contributor = Contributor(name, data.get('emails'), data.get('nicks'), data.get('expertise'))
+ contributor = Contributor(name, data.get('emails'), data.get('nicks'), data.get('aliases'), data.get('expertise'))
self._contributors.append(contributor)
Modified: trunk/Tools/Scripts/webkitpy/common/config/contributors.json (206979 => 206980)
--- trunk/Tools/Scripts/webkitpy/common/config/contributors.json 2016-10-10 03:11:20 UTC (rev 206979)
+++ trunk/Tools/Scripts/webkitpy/common/config/contributors.json 2016-10-10 05:22:09 UTC (rev 206980)
@@ -445,6 +445,9 @@
"status" : "committer"
},
"Andreas Kling" : {
+ "aliases" : [
+ "Andreas Goran Kling"
+ ],
"emails" : [
"akl...@apple.com",
"kl...@webkit.org",
@@ -845,6 +848,9 @@
"status" : "committer"
},
"Benjamin Poulain" : {
+ "aliases" : [
+ "Ben Poulain"
+ ],
"emails" : [
"benja...@webkit.org",
"bpoul...@apple.com",
@@ -858,6 +864,9 @@
"status" : "reviewer"
},
"Beth Dakin" : {
+ "aliases" : [
+ "Deth Bakin"
+ ],
"emails" : [
"bda...@apple.com"
],
@@ -1129,6 +1138,9 @@
"status" : "reviewer"
},
"Chris Dumez" : {
+ "aliases" : [
+ "Christophe Dumez"
+ ],
"emails" : [
"cdu...@apple.com",
"dch...@gmail.com",
@@ -1289,6 +1301,9 @@
"status" : "reviewer"
},
"Dan Bernstein" : {
+ "aliases" : [
+ "mitz"
+ ],
"emails" : [
"m...@webkit.org",
"m...@apple.com"
@@ -1430,6 +1445,9 @@
"status" : "reviewer"
},
"David Hyatt" : {
+ "aliases" : [
+ "Dave Hyatt"
+ ],
"emails" : [
"hy...@apple.com"
],
@@ -1441,6 +1459,9 @@
"status" : "reviewer"
},
"David Kilzer" : {
+ "aliases" : [
+ "Dave Kilzer"
+ ],
"emails" : [
"ddkil...@webkit.org",
"ddkil...@apple.com"
@@ -1661,6 +1682,9 @@
"status" : "committer"
},
"Don Melton" : {
+ "aliases" : [
+ "Gramps"
+ ],
"emails" : [
"gra...@apple.com"
],
@@ -1782,6 +1806,9 @@
"status" : "reviewer"
},
"Emil A Eklund" : {
+ "aliases" : [
+ "Emil Eklund"
+ ],
"emails" : [
"e...@chromium.org"
],
@@ -1933,6 +1960,9 @@
"status" : "committer"
},
"Filip Pizlo" : {
+ "aliases" : [
+ "Phil Pizlo"
+ ],
"emails" : [
"fpi...@apple.com"
],
@@ -2047,6 +2077,9 @@
"status" : "committer"
},
"Geoffrey Garen" : {
+ "aliases" : [
+ "Geoff Garen"
+ ],
"emails" : [
"gga...@apple.com"
],
@@ -2275,6 +2308,9 @@
"status" : "committer"
},
"Holger Freyther" : {
+ "aliases" : [
+ "Holger Hans Peter Freyther"
+ ],
"emails" : [
"ze...@selfish.org",
"ze...@webkit.org"
@@ -2883,6 +2919,9 @@
"status" : "committer"
},
"Jon Honeycutt" : {
+ "aliases" : [
+ "John Honeycutt"
+ ],
"emails" : [
"jhoneyc...@apple.com"
],
@@ -2986,6 +3025,9 @@
"status" : "committer"
},
"Joseph Pecoraro" : {
+ "aliases" : [
+ "Joe Pecoraro"
+ ],
"emails" : [
"joep...@webkit.org",
"pecor...@apple.com"
@@ -3212,6 +3254,9 @@
"status" : "committer"
},
"Kenneth Rohde Christiansen" : {
+ "aliases" : [
+ "Kenneth Christiansen"
+ ],
"emails" : [
"kenn...@webkit.org",
"kenneth.r.christian...@intel.com",
@@ -3227,6 +3272,9 @@
"status" : "reviewer"
},
"Kenneth Russell" : {
+ "aliases" : [
+ "Ken Russell"
+ ],
"emails" : [
"k...@google.com",
"k...@chromium.org"
@@ -4064,6 +4112,9 @@
]
},
"Myles C. Maxfield" : {
+ "aliases" : [
+ "Myles Maxfield"
+ ],
"emails" : [
"mmaxfi...@apple.com"
],
@@ -4177,6 +4228,9 @@
"status" : "committer"
},
"Nikolas Zimmermann" : {
+ "aliases" : [
+ "Niko Zimmermann"
+ ],
"emails" : [
"zimmerm...@kde.org",
"zimmerm...@physik.rwth-aachen.de",
@@ -5147,6 +5201,9 @@
]
},
"Tim Horton" : {
+ "aliases" : [
+ "Timothy Horton"
+ ],
"emails" : [
"thor...@apple.com",
"timothy_hor...@apple.com"
@@ -5172,6 +5229,9 @@
]
},
"Timothy Hatcher" : {
+ "aliases" : [
+ "Tim Hatcher"
+ ],
"emails" : [
"timo...@apple.com",
"timo...@hatcher.name"
@@ -5674,6 +5734,9 @@
"status" : "committer"
},
"Zoltan Herczeg" : {
+ "aliases" : [
+ "Zolt\u00e1n Herczeg"
+ ],
"emails" : [
"zherc...@webkit.org",
"zherc...@inf.u-szeged.hu"