[gitdm][PATCH 1/1] Convert to Python 3

Heinrich Schuchardt heinrich.schuchardt at canonical.com
Wed Jun 7 07:57:54 CEST 2023


This is the result of running 2to3 and manually converting the comparison
functions to lambda expressions.

Signed-off-by: Heinrich Schuchardt <heinrich.schuchardt at canonical.com>
---
 ConfigFile.py |   4 +-
 csvdump.py    |   4 +-
 database.py   |  22 +++++------
 gitdm         |  27 ++++++-------
 gitlog.py     |   8 ++--
 logparser.py  |   6 +--
 reports.py    | 106 +++++++++++++++-----------------------------------
 utils.py      |   4 +-
 8 files changed, 70 insertions(+), 111 deletions(-)

diff --git a/ConfigFile.py b/ConfigFile.py
index 3a1e208..e58c601 100644
--- a/ConfigFile.py
+++ b/ConfigFile.py
@@ -147,10 +147,10 @@ def ReadFileType (filename):
         m = regex_file_type.match (line)
         if not m or len (m.groups ()) != 2:
             ConfigFile.croak ('Funky file type line "%s"' % (line))
-        if not patterns.has_key (m.group (1)):
+        if m.group (1) not in patterns:
             patterns[m.group (1)] = []
         if m.group (1) not in order:
-            print '%s not found, appended to the last order' % m.group (1)
+            print('%s not found, appended to the last order' % m.group (1))
             order.append (m.group (1))
 
         patterns[m.group (1)].append (re.compile (m.group (2), re.IGNORECASE))
diff --git a/csvdump.py b/csvdump.py
index 9d1a65e..55e38a0 100644
--- a/csvdump.py
+++ b/csvdump.py
@@ -50,7 +50,7 @@ def store_patch(patch):
         ChangeSets.append([patch.commit, str(patch.date),
                            patch.email, domain, author, employer,
                            patch.added, patch.removed])
-        for (filetype, (added, removed)) in patch.filetypes.iteritems():
+        for (filetype, (added, removed)) in patch.filetypes.items():
             FileTypes.append([patch.commit, filetype, added, removed])
 
 
@@ -82,7 +82,7 @@ def OutputCSV (file):
     writer = csv.writer (file, quoting=csv.QUOTE_NONNUMERIC)
     writer.writerow (['Name', 'Email', 'Affliation', 'Date',
                       'Added', 'Removed', 'Changesets'])
-    for date, stat in PeriodCommitHash.items():
+    for date, stat in list(PeriodCommitHash.items()):
         # sanitise names " is common and \" sometimes too
         empl_name = stat.employer.name.replace ('"', '.').replace ('\\', '.')
         author_name = stat.name.replace ('"', '.').replace ('\\', '.')
diff --git a/database.py b/database.py
index bf13227..b267ed5 100644
--- a/database.py
+++ b/database.py
@@ -40,7 +40,7 @@ class Hacker:
                 for edate, empl in self.employer[i]:
                     if edate > date:
                         return empl
-        print 'OOPS.  ', self.name, self.employer, self.email, email, date
+        print('OOPS.  ', self.name, self.employer, self.email, email, date)
         return None # Should not happen
 
     def addpatch (self, patch):
@@ -124,11 +124,11 @@ def LookupStoreHacker(name, email, mapunknown = True):
 
 
 def AllHackers ():
-    return HackersByID.values ()
+    return list(HackersByID.values ())
 
 def DumpDB ():
     out = open ('database.dump', 'w')
-    names = HackersByName.keys ()
+    names = list(HackersByName.keys ())
     names.sort ()
     for name in names:
         h = HackersByName[name]
@@ -149,7 +149,7 @@ def DumpDB ():
 # push it backward through the changes we've already seen.
 #
 def ApplyFirstTag (tag):
-    for n in HackersByName.keys ():
+    for n in list(HackersByName.keys ()):
         if HackersByName[n].versions:
             HackersByName[n].versions = [tag]
 
@@ -185,7 +185,7 @@ def GetEmployer (name):
         return e
 
 def AllEmployers ():
-    return Employers.values ()
+    return list(Employers.values ())
 
 #
 # Certain obnoxious developers, who will remain nameless (because we
@@ -215,8 +215,8 @@ class VirtualEmployer (Employer):
         self.__init__ (name) # Reset counts just in case
 
     def store (self):
-        if Employers.has_key (self.name):
-            print Employers[self.name]
+        if self.name in Employers:
+            print(Employers[self.name])
             sys.stderr.write ('WARNING: Virtual empl %s overwrites another\n'
                               % (self.name))
         if len (self.splits) == 0:
@@ -235,7 +235,7 @@ class FileType:
         order = order or self.order
 
         for file_type in order:
-            if patterns.has_key (file_type):
+            if file_type in patterns:
                 for patt in patterns[file_type]:
                     if patt.search (filename):
                         return file_type
@@ -261,7 +261,7 @@ def MixVirtuals ():
 EmailAliases = { }
 
 def AddEmailAlias (variant, canonical):
-    if EmailAliases.has_key (variant):
+    if variant in EmailAliases:
         sys.stderr.write ('Duplicate email alias for %s\n' % (variant))
     EmailAliases[variant] = canonical
 
@@ -288,7 +288,7 @@ def AddEmailEmployerMapping (email, employer, end = nextyear):
         for i in range (0, len(l)):
             date, xempl = l[i]
             if date == end:  # probably both nextyear
-                print 'WARNING: duplicate email/empl for %s' % (email)
+                print('WARNING: duplicate email/empl for %s' % (email))
             if date > end:
                 l.insert (i, (end, empl))
                 return
@@ -305,7 +305,7 @@ def MapToEmployer (email, unknown = 0):
         pass
     namedom = email.split ('@')
     if len (namedom) < 2:
-        print 'Oops...funky email %s' % email
+        print('Oops...funky email %s' % email)
         return [(nextyear, GetEmployer ('Funky'))]
     s = namedom[1].split ('.')
     for dots in range (len (s) - 2, -1, -1):
diff --git a/gitdm b/gitdm
index 61318ad..f426cc7 100755
--- a/gitdm
+++ b/gitdm
@@ -1,4 +1,4 @@
-#!/usr/bin/pypy
+#!/usr/bin/python3
 #-*- coding:utf-8 -*-
 #
 
@@ -15,7 +15,8 @@
 
 import database, csvdump, ConfigFile, reports
 import getopt, datetime
-import os, re, sys, rfc822, string, os.path
+from email.utils import parsedate_tz
+import os, re, sys, string, os.path
 import logparser
 from patterns import patterns
 
@@ -108,7 +109,7 @@ def ParseOpts():
         elif opt[0] == '-p':
             CSVPrefix = opt[1]
         elif opt[0] == '-r':
-            print 'Filter on "%s"' % (opt[1])
+            print('Filter on "%s"' % (opt[1]))
             FileFilter = re.compile(opt[1])
         elif opt[0] == '-s':
             AuthorSOBs = 0
@@ -120,7 +121,7 @@ def ParseOpts():
             ReportUnknowns = True
         elif opt[0] == '-x':
             CSVFile = open(opt[1], 'w')
-            print "open output file " + opt[1] + "\n"
+            print("open output file " + opt[1] + "\n")
         elif opt [0] == '-w':
             Aggregate = 'week'
         elif opt [0] == '-y':
@@ -172,7 +173,7 @@ DateMap = { }
 
 def AddDateLines(date, lines):
     if lines > 1000000:
-        print 'Skip big patch (%d)' % lines
+        print('Skip big patch (%d)' % lines)
         return
     try:
         DateMap[date] += lines
@@ -180,7 +181,7 @@ def AddDateLines(date, lines):
         DateMap[date] = lines
 
 def PrintDateStats():
-    dates = DateMap.keys()
+    dates = list(DateMap.keys())
     dates.sort()
     total = 0
     datef = open('datelc.csv', 'w')
@@ -195,7 +196,7 @@ def PrintDateStats():
 # Let's slowly try to move some smarts into this class.
 #
 class patch:
-    (ADDED, REMOVED) = range(2)
+    (ADDED, REMOVED) = list(range(2))
 
     def __init__(self, commit):
         self.commit = commit
@@ -219,7 +220,7 @@ class patch:
         self.reports.append(reporter)
 
     def addfiletype(self, filetype, added, removed):
-        if self.filetypes.has_key(filetype):
+        if filetype in self.filetypes:
             self.filetypes[filetype][self.ADDED] += added
             self.filetypes[filetype][self.REMOVED] += removed
         else:
@@ -330,7 +331,7 @@ def grabpatch(logpatch):
         #
         m = patterns['date'].match(Line)
         if m:
-            dt = rfc822.parsedate(m.group(2))
+            dt = parsedate_tz(m.group(2))
             p.date = datetime.date(dt[0], dt[1], dt[2])
             if p.date > Today:
                 sys.stderr.write('Funky date: %s\n' % p.date)
@@ -389,7 +390,7 @@ def GripeAboutAuthorName(name):
     if name in GripedAuthorNames:
         return
     GripedAuthorNames.append(name)
-    print '%s is an author name, probably not what you want' % (name)
+    print('%s is an author name, probably not what you want' % (name))
 
 def ApplyFileFilter(line, ignore):
     #
@@ -462,14 +463,14 @@ TotalChanged = TotalAdded = TotalRemoved = 0
 #
 # Snarf changesets.
 #
-print >> sys.stderr, 'Grabbing changesets...\r',
+print('Grabbing changesets...\r', end=' ', file=sys.stderr)
 
 patches = logparser.LogPatchSplitter(sys.stdin)
 printcount = CSCount = 0
 
 for logpatch in patches:
     if (printcount % 50) == 0:
-        print >> sys.stderr, 'Grabbing changesets...%d\r' % printcount,
+        print('Grabbing changesets...%d\r' % printcount, end=' ', file=sys.stderr)
     printcount += 1
 
     # We want to ignore commits on svn tags since in Subversion
@@ -528,7 +529,7 @@ for logpatch in patches:
         CSCount += 1
     csvdump.AccumulatePatch(p, Aggregate)
     csvdump.store_patch(p)
-print >> sys.stderr, 'Grabbing changesets...done       '
+print('Grabbing changesets...done       ', file=sys.stderr)
 
 if DumpDB:
     database.DumpDB()
diff --git a/gitlog.py b/gitlog.py
index 71efee1..4b1c5d6 100644
--- a/gitlog.py
+++ b/gitlog.py
@@ -61,7 +61,7 @@ S_DONE = 5
 def get_header(patch, line, input):
     if line == '':
         if patch.author == '':
-            print 'Funky auth line in', patch.commit
+            print('Funky auth line in', patch.commit)
             patch.author = database.LookupStoreHacker('Unknown',
                                                       'unknown at hacker.net')
         return S_DESC
@@ -78,7 +78,7 @@ def get_header(patch, line, input):
 
 def get_desc(patch, line, input):
     if not line:
-        print 'Missing desc in', patch.commit
+        print('Missing desc in', patch.commit)
         return S_CHANGELOG
     patch.desc = line
     line = getline(input)
@@ -188,7 +188,7 @@ def grabpatch(input):
         return None
     m = patterns['commit'].match(line)
     if not m:
-        print 'noncommit', line
+        print('noncommit', line)
         return None
     p = patch(m.group(1))
     state = S_HEADER
@@ -199,7 +199,7 @@ def grabpatch(input):
         line = getline(input)
         if line is None:
             if state != S_NUMSTAT:
-                print 'Ran out of patch', state
+                print('Ran out of patch', state)
                 return None
             return p
         state = grabbers[state](p, line, input)
diff --git a/logparser.py b/logparser.py
index b375034..88293c5 100644
--- a/logparser.py
+++ b/logparser.py
@@ -41,7 +41,7 @@ class LogPatchSplitter:
     def __iter__(self):
         return self
 
-    def next(self):
+    def __next__(self):
         patch = self.__grab_patch__()
         if not patch:
             raise StopIteration
@@ -85,6 +85,6 @@ if __name__ == '__main__':
     patches = LogPatchSplitter(sys.stdin)
 
     for patch in patches:
-        print '---------- NEW PATCH ----------'
+        print('---------- NEW PATCH ----------')
         for line in patch:
-            print line,
+            print(line, end=' ')
diff --git a/reports.py b/reports.py
index d7a96bc..3e03e69 100644
--- a/reports.py
+++ b/reports.py
@@ -69,11 +69,8 @@ def EndReport():
 #
 # Comparison and report generation functions.
 #
-def ComparePCount(h1, h2):
-    return len(h2.patches) - len(h1.patches)
-
 def ReportByPCount(hlist, cscount):
-    hlist.sort(ComparePCount)
+    hlist.sort(key=lambda h: -len(h.patches))
     count = 0
     BeginReport('Developers with the most changesets')
     for h in hlist:
@@ -87,11 +84,8 @@ def ReportByPCount(hlist, cscount):
             break
     EndReport()
             
-def CompareLChanged(h1, h2):
-    return h2.changed - h1.changed
-
 def ReportByLChanged(hlist, totalchanged):
-    hlist.sort(CompareLChanged)
+    hlist.sort(key=lambda h: -h.changed)
     count = 0
     BeginReport('Developers with the most changed lines')
     for h in hlist:
@@ -103,11 +97,8 @@ def ReportByLChanged(hlist, totalchanged):
             break
     EndReport()
             
-def CompareLRemoved(h1, h2):
-    return (h2.removed - h2.added) - (h1.removed - h1.added)
-
 def ReportByLRemoved(hlist, totalremoved):
-    hlist.sort(CompareLRemoved)
+    hlist.sort(key=lambda h: h.added - h.removed)
     count = 0
     BeginReport('Developers with the most lines removed')
     for h in hlist:
@@ -121,11 +112,8 @@ def ReportByLRemoved(hlist, totalremoved):
             break
     EndReport()
 
-def CompareEPCount(e1, e2):
-    return e2.count - e1.count
-
 def ReportByPCEmpl(elist, cscount):
-    elist.sort(CompareEPCount)
+    elist.sort(key=lambda e: -e.count)
     count = 0
     BeginReport('Top changeset contributors by employer')
     for e in elist:
@@ -137,11 +125,8 @@ def ReportByPCEmpl(elist, cscount):
     EndReport()
 
 
-def CompareELChanged(e1, e2):
-    return e2.changed - e1.changed
-
 def ReportByELChanged(elist, totalchanged):
-    elist.sort(CompareELChanged)
+    elist.sort(key=lambda e: -e.changed)
     count = 0
     BeginReport('Top lines changed by employer')
     for e in elist:
@@ -154,11 +139,8 @@ def ReportByELChanged(elist, totalchanged):
 
 
 
-def CompareSOBs(h1, h2):
-    return len(h2.signoffs) - len(h1.signoffs)
-
 def ReportBySOBs(hlist):
-    hlist.sort(CompareSOBs)
+    hlist.sort(key = lambda h: -len(h.signoffs))
     totalsobs = 0
     for h in hlist:
         totalsobs += len(h.signoffs)
@@ -176,11 +158,8 @@ def ReportBySOBs(hlist):
 #
 # Reviewer reporting.
 #
-def CompareRevs(h1, h2):
-    return len(h2.reviews) - len(h1.reviews)
-
 def ReportByRevs(hlist):
-    hlist.sort(CompareRevs)
+    hlist.sort(key=lambda h: -len(h.reviews))
     totalrevs = 0
     for h in hlist:
         totalrevs += len(h.reviews)
@@ -198,11 +177,8 @@ def ReportByRevs(hlist):
 #
 # tester reporting.
 #
-def CompareTests(h1, h2):
-    return len(h2.tested) - len(h1.tested)
-
 def ReportByTests(hlist):
-    hlist.sort(CompareTests)
+    hlist.sort(key=lambda h: -len(h.tested))
     totaltests = 0
     for h in hlist:
         totaltests += len(h.tested)
@@ -217,11 +193,8 @@ def ReportByTests(hlist):
             break
     EndReport()
 
-def CompareTestCred(h1, h2):
-    return h2.testcred - h1.testcred
-
 def ReportByTestCreds(hlist):
-    hlist.sort(CompareTestCred)
+    hlist.sort(key=lambda h: -h.testcred)
     totaltests = 0
     for h in hlist:
         totaltests += h.testcred
@@ -240,11 +213,8 @@ def ReportByTestCreds(hlist):
 #
 # Reporter reporting.
 #
-def CompareReports(h1, h2):
-    return len(h2.reports) - len(h1.reports)
-
 def ReportByReports(hlist):
-    hlist.sort(CompareReports)
+    hlist.sort(key=lambda h: -len(h.reports))
     totalreps = 0
     for h in hlist:
         totalreps += len(h.reports)
@@ -259,11 +229,8 @@ def ReportByReports(hlist):
             break
     EndReport()
 
-def CompareRepCred(h1, h2):
-    return h2.repcred - h1.repcred
-
 def ReportByRepCreds(hlist):
-    hlist.sort(CompareRepCred)
+    hlist.sort(key=lambda h: -h.repcred)
     totalreps = 0
     for h in hlist:
         totalreps += h.repcred
@@ -280,14 +247,11 @@ def ReportByRepCreds(hlist):
 #
 # Versions.
 #
-def CompareVersionCounts(h1, h2):
-    if h1.versions and h2.versions:
-        return len(h2.versions) - len(h1.versions)
-    if h2.versions:
-        return 1
-    if h1.versions:
-        return -1
-    return 0
+def VersionCount(h):
+    if h.versions:
+        return len(h.versions)
+    else:
+        return 0
 
 def MissedVersions(hv, allv):
     missed = [v for v in allv if v not in hv]
@@ -295,7 +259,7 @@ def MissedVersions(hv, allv):
     return ' '.join(missed)
 
 def ReportVersions(hlist):
-    hlist.sort(CompareVersionCounts)
+    hlist.sort(key=lambda h: -VersionCount(h))
     BeginReport('Developers represented in the most kernel versions')
     count = 0
     allversions = hlist[0].versions
@@ -307,11 +271,8 @@ def ReportVersions(hlist):
     EndReport()
 
 
-def CompareESOBs(e1, e2):
-    return e2.sobs - e1.sobs
-
 def ReportByESOBs(elist):
-    elist.sort(CompareESOBs)
+    elist.sort(key=lambda e: -e.sobs)
     totalsobs = 0
     for e in elist:
         totalsobs += e.sobs
@@ -325,11 +286,8 @@ def ReportByESOBs(elist):
             break
     EndReport()
    
-def CompareHackers(e1, e2):
-    return len(e2.hackers) - len(e1.hackers)
-
 def ReportByEHackers(elist):
-    elist.sort(CompareHackers)
+    elist.sort(key=lambda e: -len(e.hackers))
     totalhackers = 0
     for e in elist:
         totalhackers += len(e.hackers)
@@ -375,7 +333,7 @@ def ReportUnknowns(hlist, cscount):
     # mapping to (Unknown) is happening or not.
     #
     ulist = [ h for h in hlist if IsUnknown(h) ]
-    ulist.sort(ComparePCount)
+    ulist.sort(lambda h: len(h.patches))
     count = 0
     BeginReport('Developers with unknown affiliation')
     for h in ulist:
@@ -398,46 +356,46 @@ def ReportByFileType(hacker_list):
         by_hacker = {}
         for patch in h.patches:
             # Get a summary by hacker
-            for (filetype, (added, removed)) in patch.filetypes.iteritems():
-                if by_hacker.has_key(filetype):
+            for (filetype, (added, removed)) in patch.filetypes.items():
+                if filetype in by_hacker:
                     by_hacker[filetype][patch.ADDED] += added
                     by_hacker[filetype][patch.REMOVED] += removed
                 else:
                     by_hacker[filetype] = [added, removed]
 
                 # Update the totals
-                if total.has_key(filetype):
+                if filetype in total:
                     total[filetype][patch.ADDED] += added
                     total[filetype][patch.REMOVED] += removed
                 else:
                     total[filetype] = [added, removed, []]
 
         # Print a summary by hacker
-        print h.name
-        for filetype, counters in by_hacker.iteritems():
-            print '\t', filetype, counters
+        print(h.name)
+        for filetype, counters in by_hacker.items():
+            print('\t', filetype, counters)
             h_added = by_hacker[filetype][patch.ADDED]
             h_removed = by_hacker[filetype][patch.REMOVED]
             total[filetype][2].append([h.name, h_added, h_removed])
 
     # Print the global summary
     BeginReport('Contributions by type and developers')
-    for filetype, (added, removed, hackers) in total.iteritems():
-        print filetype, added, removed
+    for filetype, (added, removed, hackers) in total.items():
+        print(filetype, added, removed)
         for h, h_added, h_removed in hackers:
-            print '\t%s: [%d, %d]' % (h, h_added, h_removed)
+            print('\t%s: [%d, %d]' % (h, h_added, h_removed))
 
     # Print the very global summary
     BeginReport('General contributions by type')
-    for filetype, (added, removed, hackers) in total.iteritems():
-        print filetype, added, removed
+    for filetype, (added, removed, hackers) in total.items():
+        print(filetype, added, removed)
 
 #
 # The file access report is a special beast.
 #
 def FileAccessReport(name, accesses, total):
     outf = open(name, 'w')
-    files = accesses.keys()
+    files = list(accesses.keys())
     files.sort()
     for file in files:
         a = accesses[file]
diff --git a/utils.py b/utils.py
index 2b3be5d..9f17911 100644
--- a/utils.py
+++ b/utils.py
@@ -21,7 +21,7 @@ class accumulator:
             return default
 
     def append(self, key, item, unique = False):
-        if unique and self._data.has_key(key) and \
+        if unique and key in self._data and \
            item in self._data[key]:
             return
         try:
@@ -30,7 +30,7 @@ class accumulator:
             self._data[key] = [item]
 
     def keys(self):
-        return self._data.keys()
+        return list(self._data.keys())
 
     def __getitem__(self, key):
         return self._data[key]
-- 
2.39.2



More information about the U-Boot mailing list