Browse code

Clean build scripts.

Change-Id: I7bcb4312f87876153878254492d4ceb69bc84cba
Reviewed-on: http://photon-jenkins.eng.vmware.com:8082/4756
Tested-by: gerrit-photon <photon-checkins@vmware.com>
Reviewed-by: Bo Gan <ganb@vmware.com>

xiaolin-vmware authored on 2018/02/07 12:57:21
Showing 18 changed files
1 1
new file mode 100644
... ...
@@ -0,0 +1,3 @@
0
+{
1
+    "mesos": "50"
2
+}
... ...
@@ -1,3 +1,4 @@
1
+# pylint: disable=invalid-name,missing-docstring
1 2
 import os.path
2 3
 from Logger import Logger
3 4
 from CommandUtils import CommandUtils
... ...
@@ -1,3 +1,4 @@
1
+# pylint: disable=invalid-name,missing-docstring
1 2
 import subprocess
2 3
 import os
3 4
 
... ...
@@ -30,12 +31,11 @@ class CommandUtils(object):
30 30
             cmd = chrootCmd + " " + cmd
31 31
         if logfilePath is None:
32 32
             logfilePath = os.devnull
33
-        logfile = open(logfilePath, "w")
34
-        process = subprocess.Popen("%s" %cmd, shell=True, stdout=logfile, stderr=logfile)
35
-        retval = process.wait()
36
-        logfile.close()
37
-        if retval == 0:
38
-            return True
33
+        with open(logfilePath, "w") as logfile:
34
+            process = subprocess.Popen("%s" %cmd, shell=True, stdout=logfile, stderr=logfile)
35
+            retval = process.wait()
36
+            if retval == 0:
37
+                return True
39 38
         return False
40 39
     @staticmethod
41 40
     def runCommandInShell2(cmd, chrootCmd=None):
... ...
@@ -1,11 +1,11 @@
1 1
 #!/usr/bin/env python3
2
-
2
+# pylint: disable=invalid-name,missing-docstring
3 3
 import os
4 4
 import json
5 5
 import sys
6 6
 import traceback
7
-from Logger import Logger
8 7
 from argparse import ArgumentParser
8
+from Logger import Logger
9 9
 from constants import constants
10 10
 from CommandUtils import CommandUtils
11 11
 from SpecData import SPECS
... ...
@@ -15,14 +15,22 @@ from SpecData import SPECS
15 15
 def main():
16 16
     usage = "Usage: %prog [options] <package name>"
17 17
     parser = ArgumentParser(usage)
18
-    parser.add_argument("-s", "--spec-path", dest="specPath", default="../../SPECS")
19
-    parser.add_argument("-l", "--log-path", dest="logPath", default="../../stage/LOGS")
20
-    parser.add_argument("-a", "--source-rpm-path", dest="sourceRpmPath", default="../../stage/SRPMS")
21
-    parser.add_argument("-j", "--output-dir", dest="outputDirPath", default="../../stage/")
22
-    parser.add_argument("-c", "--pullsources-config", dest="pullsourcesConfig", default="pullsources.conf")
23
-    parser.add_argument("-f", "--pkg-blacklist-file", dest="pkgBlacklistFile", default=None)
24
-    parser.add_argument("-p", "--generate-pkg-list", dest="generatePkgList", default=False, action="store_true")
25
-    parser.add_argument("-y", "--generate-yaml-files", dest="generateYamlFiles", default=False, action="store_true")
18
+    parser.add_argument("-s", "--spec-path", dest="specPath",
19
+                        default="../../SPECS")
20
+    parser.add_argument("-l", "--log-path", dest="logPath",
21
+                        default="../../stage/LOGS")
22
+    parser.add_argument("-a", "--source-rpm-path", dest="sourceRpmPath",
23
+                        default="../../stage/SRPMS")
24
+    parser.add_argument("-j", "--output-dir", dest="outputDirPath",
25
+                        default="../../stage/")
26
+    parser.add_argument("-c", "--pullsources-config", dest="pullsourcesConfig",
27
+                        default="pullsources.conf")
28
+    parser.add_argument("-f", "--pkg-blacklist-file", dest="pkgBlacklistFile",
29
+                        default=None)
30
+    parser.add_argument("-p", "--generate-pkg-list", dest="generatePkgList",
31
+                        default=False, action="store_true")
32
+    parser.add_argument("-y", "--generate-yaml-files", dest="generateYamlFiles",
33
+                        default=False, action="store_true")
26 34
 
27 35
     options = parser.parse_args()
28 36
     errorFlag = False
... ...
@@ -37,7 +45,8 @@ def main():
37 37
             if (options.pkgBlacklistFile is not None and
38 38
                     options.pkgBlacklistFile != "" and
39 39
                     not os.path.isfile(options.pkgBlacklistFile)):
40
-                logger.error("Given package blacklist file is not valid:" + options.pkgBlacklistFile)
40
+                logger.error("Given package blacklist file is not valid:"
41
+                             + options.pkgBlacklistFile)
41 42
                 errorFlag = True
42 43
 
43 44
         if not os.path.isdir(options.specPath):
... ...
@@ -49,7 +58,8 @@ def main():
49 49
             errorFlag = True
50 50
 
51 51
         if options.generateYamlFiles and not os.path.isfile(options.pullsourcesConfig):
52
-            logger.error("Given Source config file is not a valid file:" + options.pullsourcesConfig)
52
+            logger.error("Given Source config file is not a valid file:"
53
+                         + options.pullsourcesConfig)
53 54
             errorFlag = True
54 55
 
55 56
         if errorFlag:
... ...
@@ -77,7 +87,7 @@ def main():
77 77
             buildSRPMList(options.sourceRpmPath, options.outputDirPath, blackListPkgs, logger)
78 78
 
79 79
     except Exception as e:
80
-        print("Caught Exception: "+str(e))
80
+        print("Caught Exception: " + str(e))
81 81
         traceback.print_exc()
82 82
         sys.exit(1)
83 83
 
... ...
@@ -85,26 +95,25 @@ def main():
85 85
 
86 86
 
87 87
 def buildPackagesList(csvFilename):
88
-    csvFile = open(csvFilename, "w")
89
-    csvFile.write("Package,Version,License,URL,Sources,Patches\n")
90
-    listPackages = SPECS.getData().getListPackages()
91
-    listPackages.sort()
92
-    for package in listPackages:
93
-        name = package
94
-        version = SPECS.getData().getVersion(package)
95
-        license = SPECS.getData().getLicense(package)
96
-        listPatches = SPECS.getData().getPatches(package)
97
-        url = SPECS.getData().getURL(package)
98
-        listSourceNames = SPECS.getData().getSources(package)
99
-        sources = ""
100
-        patches = ""
101
-        if listPatches is not None:
102
-            patches = " ".join(listPatches)
103
-        if listSourceNames is not None:
104
-            sources = " ".join(listSourceNames)
105
-        csvFile.write(name + "," + version + "," + license + "," + url + "," + sources + "," + patches + "\n")
106
-    csvFile.close()
107
-
88
+    with open(csvFilename, "w") as csvFile:
89
+        csvFile.write("Package,Version,License,URL,Sources,Patches\n")
90
+        listPackages = SPECS.getData().getListPackages()
91
+        listPackages.sort()
92
+        for package in listPackages:
93
+            name = package
94
+            version = SPECS.getData().getVersion(package)
95
+            packagelicense = SPECS.getData().getLicense(package)
96
+            listPatches = SPECS.getData().getPatches(package)
97
+            url = SPECS.getData().getURL(package)
98
+            listSourceNames = SPECS.getData().getSources(package)
99
+            sources = ""
100
+            patches = ""
101
+            if listPatches is not None:
102
+                patches = " ".join(listPatches)
103
+            if listSourceNames is not None:
104
+                sources = " ".join(listSourceNames)
105
+            csvFile.write(name + "," + version + "," + packagelicense + "," + url + "," +
106
+                          sources + "," + patches + "\n")
108 107
 
109 108
 def readBlackListPackages(pkgBlackListFile):
110 109
     blackListPkgs = []
... ...
@@ -133,7 +142,7 @@ def buildSourcesList(yamlDir, blackListPkgs, logger, singleFile=True):
133 133
         ossversion = SPECS.getData().getVersion(package)
134 134
         modified = False
135 135
         listPatches = SPECS.getData().getPatches(package)
136
-        if listPatches is not None and len(listPatches) > 0:
136
+        if listPatches:
137 137
             modified = True
138 138
         url = SPECS.getData().getSourceURL(package)
139 139
         if url is None:
... ...
@@ -141,7 +150,7 @@ def buildSourcesList(yamlDir, blackListPkgs, logger, singleFile=True):
141 141
 
142 142
         sourceName = None
143 143
         listSourceNames = SPECS.getData().getSources(package)
144
-        if len(listSourceNames) > 0:
144
+        if listSourceNames:
145 145
             sourceName = listSourceNames[0]
146 146
             sha1 = SPECS.getData().getSHA1(package, sourceName)
147 147
             if sha1 is not None:
... ...
@@ -185,7 +194,8 @@ def buildSRPMList(srpmPath, yamlDir, blackListPkgs, logger, singleFile=True):
185 185
         ossversion = SPECS.getData().getVersion(package)
186 186
         ossrelease = SPECS.getData().getRelease(package)
187 187
 
188
-        listFoundSRPMFiles = cmdUtils.findFile(ossname + "-" + ossversion + "-" + ossrelease + ".src.rpm",
188
+        listFoundSRPMFiles = cmdUtils.findFile(ossname + "-" + ossversion + "-" + ossrelease
189
+                                               + ".src.rpm",
189 190
                                                srpmPath)
190 191
         srpmName = None
191 192
         if len(listFoundSRPMFiles) == 1:
... ...
@@ -199,7 +209,8 @@ def buildSRPMList(srpmPath, yamlDir, blackListPkgs, logger, singleFile=True):
199 199
             logger.error("SRPM file is not found:" + ossname)
200 200
 
201 201
         if not singleFile:
202
-            yamlFile = open(yamlSrpmDir + "/" + ossname + "-" + ossversion + "-" + ossrelease + ".yaml", "w")
202
+            yamlFile = open(yamlSrpmDir + "/" + ossname + "-" + ossversion + "-"
203
+                            + ossrelease + ".yaml", "w")
203 204
 
204 205
         yamlFile.write("baseos:" + ossname + ":" + ossversion + "-" + ossrelease + ":\n")
205 206
         yamlFile.write("  repository: BaseOS\n")
... ...
@@ -12,7 +12,7 @@ class Logger(object):
12 12
         if resetFile:
13 13
             open(logfile, 'w').close()
14 14
         logger = logging.getLogger(mymodule)
15
-        if len(logger.handlers) == 0:
15
+        if not logger.handlers:
16 16
             #creating file handler
17 17
             fhandler = logging.FileHandler(logfile)
18 18
             # create console handler
... ...
@@ -5,9 +5,9 @@ class MiscUtils(object):
5 5
     @staticmethod
6 6
     def isOutdated(listInputFiles, listOutputFiles):
7 7
         thresholdTimeStamp = None
8
-        if len(listInputFiles) == 0:
8
+        if not listInputFiles:
9 9
             return False
10
-        if len(listOutputFiles) == 0:
10
+        if not listOutputFiles:
11 11
             return True
12 12
         for f in listOutputFiles:
13 13
             t = os.path.getmtime(f)
... ...
@@ -31,6 +31,6 @@ class MiscUtils(object):
31 31
                 MiscUtils.getListSpecFiles(listSpecFiles, dirEntryPath)
32 32
 
33 33
 if __name__ == "__main__":
34
-    listInputFiles = ["SpecParser.py", "Logger.py"]
35
-    listOutputFiles = ["builder.py"]
36
-    print(MiscUtils.isOutdated(listInputFiles, listOutputFiles))
34
+    inputFiles = ["SpecParser.py", "Logger.py"]
35
+    outputFiles = ["builder.py"]
36
+    print(MiscUtils.isOutdated(inputFiles, outputFiles))
... ...
@@ -1,13 +1,12 @@
1
+# pylint: disable=invalid-name,missing-docstring
1 2
 import copy
3
+from collections import OrderedDict
2 4
 from Logger import Logger
3 5
 from constants import constants
4 6
 from SpecData import SPECS
5 7
 
6
-def removeDuplicateEntriesInList(myList):
7
-    myListCopy = []
8
-    for p in myList:
9
-        if p not in myListCopy:
10
-            myListCopy.append(p)
8
+def removeDuplicateEntries(myList):
9
+    myListCopy = list(OrderedDict.fromkeys(myList))
11 10
     return myListCopy
12 11
 
13 12
 class PackageBuildDataGenerator(object):
... ...
@@ -19,8 +18,6 @@ class PackageBuildDataGenerator(object):
19 19
             logName = "PackageBuildDataGenerator"
20 20
         if logPath is None:
21 21
             logPath = constants.logPath
22
-        self.logName = logName
23
-        self.logPath = logPath
24 22
         self.logger = Logger.getLogger(logName, logPath)
25 23
         self.__mapCyclesToPackageList = {}
26 24
         self.__mapPackageToCycle = {}
... ...
@@ -30,15 +27,20 @@ class PackageBuildDataGenerator(object):
30 30
         self.__sortedBuildDependencyGraph = {}
31 31
 
32 32
     def getPackageBuildData(self, listPackages):
33
-        self.__readDependencyGraphAndCyclesForGivenPackages(listPackages)
34
-        self.__getSortedBuildOrderListForGivenPackages(listPackages)
33
+        basePackages = set()
34
+        for pkg in listPackages:
35
+            basePackage = SPECS.getData().getSpecName(pkg)
36
+            basePackages.add(basePackage)
37
+
38
+        self._readDependencyGraphAndCyclesForGivenPackages(basePackages)
39
+        self._getSortedBuildOrderList()
35 40
         return self.__mapCyclesToPackageList, self.__mapPackageToCycle, self.__sortedPackageList
36 41
 
37 42
     #todo
38
-    def findCompleteListOfPackagesRequiredToBuildGivenPackages(self, listPackages):
43
+    def _findAllPackagesToBuild(self):
39 44
         return list(self.__buildDependencyGraph.keys())
40 45
 
41
-    def createSortListForPkg(self, pkg):
46
+    def _createSortListForPkg(self, pkg):
42 47
         runTimeDepPkgList = self.__runTimeDependencyGraph[pkg]
43 48
         runTimeDepPkgList.append(pkg)
44 49
         sortListForPkg = []
... ...
@@ -51,7 +53,7 @@ class PackageBuildDataGenerator(object):
51 51
 
52 52
         return sortListForPkg
53 53
 
54
-    def getCircularDependentPackages(self, pkg):
54
+    def _getCircularDependentPackages(self, pkg):
55 55
         circularDependentPackages = []
56 56
         if pkg in self.__mapPackageToCycle:
57 57
             circularDependentPackages.extend(
... ...
@@ -59,12 +61,11 @@ class PackageBuildDataGenerator(object):
59 59
             circularDependentPackages.remove(pkg)
60 60
         return circularDependentPackages
61 61
 
62
-    def __getSortedBuildOrderListForGivenPackages(self, listPackages):
62
+    def _getSortedBuildOrderList(self):
63 63
 
64
-        alreadyProcessedPackages = []
64
+        alreadyProcessedPackages = set()
65 65
         sortedList = []
66
-        completeListPackagesToBuild = self.findCompleteListOfPackagesRequiredToBuildGivenPackages(
67
-            listPackages)
66
+        completeListPackagesToBuild = self._findAllPackagesToBuild()
68 67
         packageIndexInSortedList = 0
69 68
         prevSortListLen = 0
70 69
 
... ...
@@ -74,7 +75,7 @@ class PackageBuildDataGenerator(object):
74 74
             pkg = None
75 75
             index = -1
76 76
             lenList = len(sortedList)
77
-            for  i in range(lenList):
77
+            for i in range(lenList):
78 78
                 if sortedList[i] in alreadyProcessedPackages:
79 79
                     continue
80 80
                 pkg = sortedList[i]
... ...
@@ -86,10 +87,11 @@ class PackageBuildDataGenerator(object):
86 86
                 packageIndexInSortedList = len(sortedList)
87 87
 
88 88
             #creating sort list for package
89
-            sortListForPkg = self.createSortListForPkg(pkg)
89
+            sortListForPkg = self._createSortListForPkg(pkg)
90 90
 
91
-            #remove any cyclic packages in sortListForPkg if they already exists in sortedList
92
-            circularDependentPackages = self.getCircularDependentPackages(pkg)
91
+            #remove any cyclic packages in sortListForPkg if they already
92
+            #exists in sortedList
93
+            circularDependentPackages = self._getCircularDependentPackages(pkg)
93 94
             for p in circularDependentPackages:
94 95
                 if p in sortedList and p in sortListForPkg:
95 96
                     sortListForPkg.remove(p)
... ...
@@ -104,25 +106,23 @@ class PackageBuildDataGenerator(object):
104 104
                     sortedList.insert(index, p)
105 105
                     index = index + 1
106 106
 
107
-            alreadyProcessedPackages.append(p)
107
+            alreadyProcessedPackages.add(p)
108 108
 
109 109
             # Remove duplicate entries in sorted list in intervals
110 110
             if (len(sortedList) - prevSortListLen) > 100:
111 111
                 self.logger.info("Removing duplicates in sortedList")
112
-                sortedList = removeDuplicateEntriesInList(sortedList)
112
+                sortedList = removeDuplicateEntries(sortedList)
113 113
             else:
114 114
                 prevSortListLen = len(sortedList)
115 115
 
116 116
         self.logger.info("Removing duplicates in sorted list")
117
-        sortedList = removeDuplicateEntriesInList(sortedList)
117
+        sortedList = removeDuplicateEntries(sortedList)
118 118
 
119 119
         self.logger.info("Sorted list:")
120 120
         self.logger.info(sortedList)
121 121
         self.__sortedPackageList = sortedList
122 122
 
123
-    def __constructBuildAndRunTimeDependencyGraph(self, package):
124
-        basePackage = SPECS.getData().getSpecName(package)
125
-
123
+    def _constructBuildAndRunTimeDependencyGraph(self, basePackage):
126 124
         addBuildTimeGraph = True
127 125
         addRunTimeGraph = True
128 126
         if basePackage in self.__buildDependencyGraph:
... ...
@@ -130,104 +130,120 @@ class PackageBuildDataGenerator(object):
130 130
         if basePackage in self.__runTimeDependencyGraph:
131 131
             addRunTimeGraph = False
132 132
 
133
-        nextPackagesToConstructGraph = []
133
+        nextPackagesToConstructGraph = set()
134 134
         if addBuildTimeGraph:
135
-            listDependentRpmPackages = SPECS.getData().getBuildRequiresForPackage(basePackage)
136
-            listDependentPackages = []
137
-            for rpmPkg in listDependentRpmPackages:
135
+            dependentRpmPackages = SPECS.getData().getBuildRequiresForPackage(basePackage)
136
+            dependentPackages = set()
137
+            for rpmPkg in dependentRpmPackages:
138 138
                 basePkg = SPECS.getData().getSpecName(rpmPkg)
139
-                if basePkg not in listDependentPackages:
140
-                    listDependentPackages.append(basePkg)
141
-            self.__buildDependencyGraph[basePackage] = listDependentPackages
142
-            nextPackagesToConstructGraph.extend(listDependentPackages)
139
+                dependentPackages.add(basePkg)
140
+            self.__buildDependencyGraph[basePackage] = dependentPackages
141
+            nextPackagesToConstructGraph.update(dependentPackages)
143 142
 
144 143
         if addRunTimeGraph:
145
-            listRpmPackages = SPECS.getData().getPackages(basePackage)
146
-            for rpmPkg in listRpmPackages:
147
-                listDependentRpmPackages = SPECS.getData().getRequiresAllForPackage(rpmPkg)
148
-                self.__runTimeDependencyGraph[rpmPkg] = listDependentRpmPackages[:]
149
-                nextPackagesToConstructGraph.extend(listDependentRpmPackages)
144
+            rpmPackages = SPECS.getData().getPackages(basePackage)
145
+            dependentPackages = set()
146
+            for rpmPkg in rpmPackages:
147
+                dependentRpmPackages = SPECS.getData().getRequiresAllForPackage(rpmPkg)
148
+                self.__runTimeDependencyGraph[rpmPkg] = copy.copy(dependentRpmPackages)
149
+                for pkg in dependentRpmPackages:
150
+                    dependentPackages.add(SPECS.getData().getSpecName(pkg))
151
+            nextPackagesToConstructGraph.update(dependentPackages)
150 152
 
151 153
         for pkg in nextPackagesToConstructGraph:
152
-            self.__constructBuildAndRunTimeDependencyGraph(pkg)
154
+            self._constructBuildAndRunTimeDependencyGraph(pkg)
153 155
 
154
-    def __readDependencyGraphAndCyclesForGivenPackages(self, listPackages):
156
+    def _readDependencyGraphAndCyclesForGivenPackages(self, basePackages):
155 157
         self.logger.info("Reading dependency graph to check for cycles")
156
-        for pkg in listPackages:
157
-            self.__constructBuildAndRunTimeDependencyGraph(pkg)
158 158
 
159
-        for pkg in self.__buildDependencyGraph.keys():
160
-            sortedPackageList, circularDependentPackages = self.topologicalSortPackages(
159
+        for pkg in basePackages:
160
+            self._constructBuildAndRunTimeDependencyGraph(pkg)
161
+
162
+        for pkg in self._findAllPackagesToBuild():
163
+            sortedPackageList, circularDependentPackages = self._topologicalSortPackages(
161 164
                 self.__buildDependencyGraph, pkg)
162
-            if len(circularDependentPackages) > 0:
165
+            if circularDependentPackages:
163 166
                 self.logger.error("Found circular dependency")
164 167
                 self.logger.error(circularDependentPackages)
165 168
                 raise Exception("Build Time Circular Dependency")
166 169
             self.__sortedBuildDependencyGraph[pkg] = sortedPackageList
167
-        sortedPackageList, circularDependentPackages = self.topologicalSortPackages(
170
+        sortedPackageList, circularDependentPackages = self._topologicalSortPackages(
168 171
             self.__runTimeDependencyGraph)
169
-        if len(circularDependentPackages) > 0:
170
-            self.__findCircularDependencies(circularDependentPackages)
171
-
172
-    def topologicalSortPackages(self, dependencyGraph, package=None):
173
-        noDepPackages = set()
174
-        sortedPackageList = []
175
-        dependentOfPackage = dict()
172
+        if circularDependentPackages:
173
+            self._findCircularDependencies(circularDependentPackages)
176 174
 
175
+    @staticmethod
176
+    def _buildDependentPackages(dependencyGraph, package):
177 177
         dependentPackages = {}
178 178
         if package is None:
179 179
             dependentPackages = copy.deepcopy(dependencyGraph)
180 180
         else:
181
-            listDepPkgs = set()
182
-            listDepPkgs.add(package)
183
-            while listDepPkgs:
184
-                pkg = listDepPkgs.pop()
181
+            depPkgs = set()
182
+            depPkgs.add(package)
183
+            while depPkgs:
184
+                pkg = depPkgs.pop()
185 185
                 if pkg in dependentPackages:
186 186
                     continue
187
-                dependentPackages[pkg] = dependencyGraph[pkg][:]
187
+                dependentPackages[pkg] = copy.copy(dependencyGraph[pkg])
188 188
                 for depPkg in dependencyGraph[pkg]:
189
-                    listDepPkgs.add(depPkg)
189
+                    depPkgs.add(depPkg)
190
+        return dependentPackages
190 191
 
191
-        #Find packages with no dependencies and generate dependentof_package edge list
192
+    @staticmethod
193
+    def _buildDependentOfPackages(dependentPackages):
194
+        dependentOfPackage = dict()
192 195
         for pkg in dependentPackages:
193
-            if len(dependentPackages[pkg]) == 0:
194
-                noDepPackages.add(pkg)
195
-            else:
196
+            if dependentPackages[pkg]:
196 197
                 for depPkg in dependentPackages[pkg]:
197 198
                     if depPkg not in dependentOfPackage:
198
-                        dependentOfPackage[depPkg] = [pkg]
199
+                        dependentOfPackage[depPkg] = {pkg}
199 200
                     else:
200
-                        if pkg not in dependentOfPackage[depPkg]:
201
-                            dependentOfPackage[depPkg].append(pkg)
201
+                        dependentOfPackage[depPkg].add(pkg)
202
+        return dependentOfPackage
203
+
204
+    @staticmethod
205
+    def _topologicalSortPackages(dependencyGraph, package=None):
206
+        sortedPackageList = []
207
+        noDepPackages = set()
208
+
209
+        dependentPackages = PackageBuildDataGenerator._buildDependentPackages(
210
+            dependencyGraph, package)
211
+        dependentOfPackage = PackageBuildDataGenerator._buildDependentOfPackages(
212
+            dependentPackages)
213
+
214
+        #Find packages with no dependencies and generate dependentof_package edge list
215
+        for pkg in dependentPackages:
216
+            if not dependentPackages[pkg]:
217
+                noDepPackages.add(pkg)
202 218
 
203 219
         while noDepPackages:
204 220
             pkg = noDepPackages.pop()
205 221
             sortedPackageList.append(pkg)
206
-            if dependentOfPackage.get(pkg) is not None:
207
-                for childPkg in list(dependentOfPackage.get(pkg)):
208
-                    dependentOfPackage.get(pkg).remove(childPkg)
222
+            if pkg in dependentOfPackage:
223
+                for childPkg in list(dependentOfPackage[pkg]):
224
+                    dependentOfPackage[pkg].remove(childPkg)
209 225
                     dependentPackages[childPkg].remove(pkg)
210
-                    if len(dependentPackages[childPkg]) == 0:
226
+                    if not dependentPackages[childPkg]:
211 227
                         noDepPackages.add(childPkg)
212 228
 
213 229
         # creating circular dependency graph for given dependency graph
214 230
         circularDependencyGraph = {}
215 231
         for pkg in dependentPackages.keys():
216
-            if len(dependentPackages[pkg]) != 0:
232
+            if dependentPackages[pkg]:
217 233
                 circularDependencyGraph[pkg] = dependentPackages[pkg]
218 234
 
219 235
         #return (non-circular dependent package in sorted order and circular dependent
220 236
         #package list in a dependencyGraph)
221 237
         return sortedPackageList, circularDependencyGraph
222 238
 
223
-    def __constructDependencyMap(self, yclicDependencyGraph):
239
+    def _constructDependencyMap(self, cyclicDependencyGraph):
224 240
         self.logger.info("Constructing dependency map from circular dependency graph.....")
225 241
         constructDependencyMap = {}
226 242
         for node in cyclicDependencyGraph.keys():
227
-            tmpDepNodeList = []
228
-            tmpDepNodeList.append(node)
243
+            tmpDepNodeList = set()
244
+            tmpDepNodeList.add(node)
229 245
             depNodeList = []
230
-            while len(tmpDepNodeList) != 0:
246
+            while tmpDepNodeList:
231 247
                 currentNode = tmpDepNodeList.pop()
232 248
                 addDepNodeList = cyclicDependencyGraph[currentNode]
233 249
                 depNodeList.append(currentNode)
... ...
@@ -236,19 +252,19 @@ class PackageBuildDataGenerator(object):
236 236
                         continue
237 237
                     else:
238 238
                         if depNode not in tmpDepNodeList:
239
-                            tmpDepNodeList.append(depNode)
239
+                            tmpDepNodeList.add(depNode)
240 240
             depNodeList.remove(node)
241 241
             constructDependencyMap[node] = depNodeList
242 242
         self.logger.info("Dependency Map:")
243 243
         self.logger.info(constructDependencyMap)
244 244
         return constructDependencyMap
245 245
 
246
-    def __findCircularDependencies(self, cyclicDependencyGraph):
246
+    def _findCircularDependencies(self, cyclicDependencyGraph):
247 247
         self.logger.info("Looking for circular dependencies")
248
-        if len(cyclicDependencyGraph) == 0:
248
+        if not cyclicDependencyGraph:
249 249
             return
250 250
         #step1: construct dependency map from dependency graph
251
-        constructDependencyMap = self.__constructDependencyMap(cyclicDependencyGraph)
251
+        constructDependencyMap = self._constructDependencyMap(cyclicDependencyGraph)
252 252
 
253 253
         #step2: find cycles in dependency map
254 254
         self.logger.info("Finding and adding cycles using constructed dependency map......")
... ...
@@ -262,7 +278,7 @@ class PackageBuildDataGenerator(object):
262 262
                     if node in x:
263 263
                         cycPkgs.append(depPkg)
264 264
 
265
-                if len(cycPkgs) != 0:
265
+                if cycPkgs:
266 266
                     cycPkgs.append(node)
267 267
                     cycleName = "cycle" + str(PackageBuildDataGenerator.cycleCount)
268 268
                     PackageBuildDataGenerator.cycleCount += 1
... ...
@@ -10,21 +10,28 @@ from SpecData import SPECS
10 10
 import docker
11 11
 
12 12
 class PackageBuilderBase(object):
13
-    def __init__(self, mapPackageToCycles, listAvailableCyclicPackages,
14
-                 pkgBuildType):
13
+    def __init__(self, mapPackageToCycles, pkgBuildType):
15 14
         # will be initialized in buildPackageFunction()
16 15
         self.logName = None
17 16
         self.logPath = None
18 17
         self.logger = None
19 18
         self.package = None
20 19
         self.mapPackageToCycles = mapPackageToCycles
21
-        self.listAvailableCyclicPackages = listAvailableCyclicPackages
22 20
         self.listNodepsPackages = ["glibc", "gmp", "zlib", "file", "binutils", "mpfr",
23 21
                                    "mpc", "gcc", "ncurses", "util-linux", "groff", "perl",
24 22
                                    "texinfo", "rpm", "openssl", "go"]
25 23
         self.pkgBuildType = pkgBuildType
26 24
 
27
-    def buildPackagePrepareFunction(self, package, outputMap, threadName):
25
+    def buildPackageFunction(self, package):
26
+        self._buildPackagePrepareFunction(package)
27
+        try:
28
+            self._buildPackage()
29
+        except Exception as e:
30
+            # TODO: self.logger might be None
31
+            self.logger.exception(e)
32
+            raise e
33
+
34
+    def _buildPackagePrepareFunction(self, package):
28 35
         self.package = package
29 36
         self.logName = "build-" + package
30 37
         self.logPath = constants.logPath + "/build-" + package
... ...
@@ -33,7 +40,7 @@ class PackageBuilderBase(object):
33 33
             cmdUtils.runCommandInShell("mkdir -p " + self.logPath)
34 34
         self.logger = Logger.getLogger(self.logName, self.logPath)
35 35
 
36
-    def findPackageNameFromRPMFile(self, rpmfile):
36
+    def _findPackageNameFromRPMFile(self, rpmfile):
37 37
         rpmfile = os.path.basename(rpmfile)
38 38
         releaseindex = rpmfile.rfind("-")
39 39
         if releaseindex == -1:
... ...
@@ -46,7 +53,7 @@ class PackageBuilderBase(object):
46 46
         packageName = rpmfile[0:versionindex]
47 47
         return packageName
48 48
 
49
-    def findInstalledPackages(self, instanceID):
49
+    def _findInstalledPackages(self, instanceID):
50 50
         pkgUtils = PackageUtils(self.logName, self.logPath)
51 51
         if self.pkgBuildType == "chroot":
52 52
             listInstalledRPMs = pkgUtils.findInstalledRPMPackages(instanceID)
... ...
@@ -54,12 +61,12 @@ class PackageBuilderBase(object):
54 54
             listInstalledRPMs = pkgUtils.findInstalledRPMPackagesInContainer(instanceID)
55 55
         listInstalledPackages = []
56 56
         for installedRPM in listInstalledRPMs:
57
-            packageName = self.findPackageNameFromRPMFile(installedRPM)
57
+            packageName = self._findPackageNameFromRPMFile(installedRPM)
58 58
             if packageName is not None:
59 59
                 listInstalledPackages.append(packageName)
60 60
         return listInstalledPackages, listInstalledRPMs
61 61
 
62
-    def checkIfPackageIsAlreadyBuilt(self):
62
+    def _checkIfPackageIsAlreadyBuilt(self):
63 63
         basePkg = SPECS.getData().getSpecName(self.package)
64 64
         listRPMPackages = SPECS.getData().getRPMPackages(basePkg)
65 65
         packageIsAlreadyBuilt = True
... ...
@@ -70,20 +77,17 @@ class PackageBuilderBase(object):
70 70
                 break
71 71
         return packageIsAlreadyBuilt
72 72
 
73
-    def findRunTimeRequiredRPMPackages(self, rpmPackage):
74
-        listRequiredPackages = SPECS.getData().getRequiresForPackage(rpmPackage)
75
-        return listRequiredPackages
73
+    def _findRunTimeRequiredRPMPackages(self, rpmPackage):
74
+        return SPECS.getData().getRequiresForPackage(rpmPackage)
76 75
 
77
-    def findBuildTimeRequiredPackages(self):
78
-        listRequiredPackages = SPECS.getData().getBuildRequiresForPackage(self.package)
79
-        return listRequiredPackages
76
+    def _findBuildTimeRequiredPackages(self):
77
+        return SPECS.getData().getBuildRequiresForPackage(self.package)
80 78
 
81
-    def findBuildTimeCheckRequiredPackages(self):
82
-        listRequiredPackages = SPECS.getData().getCheckBuildRequiresForPackage(self.package)
83
-        return listRequiredPackages
79
+    def _findBuildTimeCheckRequiredPackages(self):
80
+        return SPECS.getData().getCheckBuildRequiresForPackage(self.package)
84 81
 
85
-    def installPackage(self, pkgUtils, package, instanceID, destLogPath,
86
-                       listInstalledPackages, listInstalledRPMs):
82
+    def _installPackage(self, pkgUtils, package, instanceID, destLogPath,
83
+                        listInstalledPackages, listInstalledRPMs):
87 84
         latestRPM = os.path.basename(
88 85
             pkgUtils.findRPMFileForGivenPackage(package)).replace(".rpm", "")
89 86
         if package in listInstalledPackages and latestRPM in listInstalledRPMs:
... ...
@@ -91,60 +95,59 @@ class PackageBuilderBase(object):
91 91
         # mark it as installed -  to avoid cyclic recursion
92 92
         listInstalledPackages.append(package)
93 93
         listInstalledRPMs.append(latestRPM)
94
-        self.installDependentRunTimePackages(pkgUtils, package, instanceID, destLogPath,
95
-                                             listInstalledPackages, listInstalledRPMs)
94
+        self._installDependentRunTimePackages(pkgUtils, package, instanceID, destLogPath,
95
+                                              listInstalledPackages, listInstalledRPMs)
96 96
         noDeps = False
97
-        if package in self.mapPackageToCycles:
98
-            noDeps = True
99
-        if package in self.listNodepsPackages:
100
-            noDeps = True
101
-        if package in constants.noDepsPackageList:
97
+        if (package in self.mapPackageToCycles or
98
+                package in self.listNodepsPackages or
99
+                package in constants.noDepsPackageList):
102 100
             noDeps = True
103 101
         if self.pkgBuildType == "chroot":
104 102
             pkgUtils.installRPM(package, instanceID, noDeps, destLogPath)
105 103
         elif self.pkgBuildType == "container":
106 104
             pkgUtils.prepRPMforInstallInContainer(package, instanceID, noDeps, destLogPath)
107 105
 
108
-    def installDependentRunTimePackages(self, pkgUtils, package, instanceID, destLogPath,
109
-                                        listInstalledPackages, listInstalledRPMs):
110
-        listRunTimeDependentPackages = self.findRunTimeRequiredRPMPackages(package)
111
-        if len(listRunTimeDependentPackages) != 0:
106
+    def _installDependentRunTimePackages(self, pkgUtils, package, instanceID, destLogPath,
107
+                                         listInstalledPackages, listInstalledRPMs):
108
+        listRunTimeDependentPackages = self._findRunTimeRequiredRPMPackages(package)
109
+        if listRunTimeDependentPackages:
112 110
             for pkg in listRunTimeDependentPackages:
113
-                if pkg in self.mapPackageToCycles and pkg not in self.listAvailableCyclicPackages:
111
+                if pkg in self.mapPackageToCycles:
114 112
                     continue
115 113
                 latestPkgRPM = os.path.basename(
116 114
                     pkgUtils.findRPMFileForGivenPackage(pkg)).replace(".rpm", "")
117 115
                 if pkg in listInstalledPackages and latestPkgRPM in listInstalledRPMs:
118 116
                     continue
119
-                self.installPackage(pkgUtils, pkg, instanceID, destLogPath,
120
-                                    listInstalledPackages, listInstalledRPMs)
121
-
122
-class PackageBuilderContainer(object):
123
-    def __init__(self, mapPackageToCycles, listAvailableCyclicPackages,
124
-                 pkgBuildType):
117
+                self._installPackage(pkgUtils, pkg, instanceID, destLogPath,
118
+                                     listInstalledPackages, listInstalledRPMs)
119
+
120
+    def _findDependentPackagesAndInstalledRPM(self, instanceID):
121
+        listInstalledPackages, listInstalledRPMs = self._findInstalledPackages(instanceID)
122
+        self.logger.info(listInstalledPackages)
123
+        listDependentPackages = self._findBuildTimeRequiredPackages()
124
+        if constants.rpmCheck and self.package in constants.testForceRPMS:
125
+            listDependentPackages.extend(self._findBuildTimeCheckRequiredPackages())
126
+            testPackages = (set(constants.listMakeCheckRPMPkgtoInstall) -
127
+                            set(listInstalledPackages) -
128
+                            set([self.package]))
129
+            listDependentPackages.extend(testPackages)
130
+            listDependentPackages = list(set(listDependentPackages))
131
+        return listDependentPackages, listInstalledPackages, listInstalledRPMs
132
+
133
+
134
+class PackageBuilderContainer(PackageBuilderBase):
135
+    def __init__(self, mapPackageToCycles, pkgBuildType):
125 136
         self.buildContainerImage = "photon_build_container:latest"
126 137
         self.dockerClient = docker.from_env(version="auto")
127 138
 
128
-        self.base = PackageBuilderBase(mapPackageToCycles, listAvailableCyclicPackages,
129
-                                       pkgBuildType)
139
+        PackageBuilderBase.__init__(self, mapPackageToCycles, pkgBuildType)
130 140
 
131
-    def buildPackageFunction(self, package, outputMap, threadName):
132
-        self.base.buildPackagePrepareFunction(package, outputMap, threadName)
133
-        try:
134
-            self.buildPackage()
135
-            outputMap[threadName] = True
136
-        except Exception as e:
137
-            # TODO: self.logger might be None
138
-            self.base.logger.exception(e)
139
-            outputMap[threadName] = False
140
-            raise e
141
-
142
-    def prepareBuildContainer(self, containerTaskName, packageName,
143
-                              isToolChainPackage=False):
141
+    def _prepareBuildContainer(self, containerTaskName, packageName,
142
+                               isToolChainPackage=False):
144 143
         # Prepare an empty chroot environment to let docker use the BUILD folder.
145 144
         # This avoids docker using overlayFS which will cause make check failure.
146 145
         chrootName = "build-" + packageName
147
-        chrUtils = ChrootUtils(self.base.logName, self.base.logPath)
146
+        chrUtils = ChrootUtils(self.logName, self.logPath)
148 147
         returnVal, chrootID = chrUtils.createChroot(chrootName)
149 148
         if not returnVal:
150 149
             raise Exception("Unable to prepare build root")
... ...
@@ -159,8 +162,8 @@ class PackageBuilderContainer(object):
159 159
             constants.tmpDirPath: {'bind': '/tmp', 'mode': 'rw'},
160 160
             constants.rpmPath: {'bind': constants.topDirPath + "/RPMS", 'mode': 'rw'},
161 161
             constants.sourceRpmPath: {'bind': constants.topDirPath + "/SRPMS", 'mode': 'rw'},
162
-            constants.logPath + "/" + self.base.logName: {'bind': constants.topDirPath + "/LOGS",
163
-                                                          'mode': 'rw'},
162
+            constants.logPath + "/" + self.logName: {'bind': constants.topDirPath + "/LOGS",
163
+                                                     'mode': 'rw'},
164 164
             chrootID + constants.topDirPath + "/BUILD": {'bind': constants.topDirPath + "/BUILD",
165 165
                                                          'mode': 'rw'},
166 166
             constants.dockerUnixSocket: {'bind': constants.dockerUnixSocket, 'mode': 'rw'}
... ...
@@ -179,8 +182,8 @@ class PackageBuilderContainer(object):
179 179
                 pass
180 180
 
181 181
         try:
182
-            self.base.logger.info("BuildContainer-prepareBuildContainer: " +
183
-                                  "Starting build container: " + containerName)
182
+            self.logger.info("BuildContainer-prepareBuildContainer: " +
183
+                             "Starting build container: " + containerName)
184 184
             #TODO: Is init=True equivalent of --sig-proxy?
185 185
             privilegedDocker = False
186 186
             cap_list = ['SYS_PTRACE']
... ...
@@ -196,88 +199,80 @@ class PackageBuilderContainer(object):
196 196
                                                            volumes=mountVols,
197 197
                                                            command="/bin/bash -l -c /wait.sh")
198 198
 
199
-            self.base.logger.debug("Started Photon build container for task " + containerTaskName +
200
-                                   " ID: " + containerID.short_id)
199
+            self.logger.debug("Started Photon build container for task " + containerTaskName +
200
+                              " ID: " + containerID.short_id)
201 201
             if not containerID:
202 202
                 raise Exception("Unable to start Photon build container for task " +
203 203
                                 containerTaskName)
204 204
         except Exception as e:
205
-            self.base.logger.debug("Unable to start Photon build container for task " +
206
-                                   containerTaskName)
205
+            self.logger.debug("Unable to start Photon build container for task " +
206
+                              containerTaskName)
207 207
             raise e
208 208
         return containerID, chrootID
209 209
 
210
-    def buildPackage(self):
210
+    def _buildPackage(self):
211 211
         #do not build if RPM is already built
212 212
         #test only if the package is in the testForceRPMS with rpmCheck
213 213
         #build only if the package is not in the testForceRPMS with rpmCheck
214
-        if self.base.checkIfPackageIsAlreadyBuilt():
214
+        if self._checkIfPackageIsAlreadyBuilt():
215 215
             if not constants.rpmCheck:
216
-                self.base.logger.info("Skipping building the package:" + self.base.package)
216
+                self.logger.info("Skipping building the package:" + self.package)
217 217
                 return
218
-            elif constants.rpmCheck and self.base.package not in constants.testForceRPMS:
219
-                self.base.logger.info("Skipping testing the package:" + self.base.package)
218
+            elif constants.rpmCheck and self.package not in constants.testForceRPMS:
219
+                self.logger.info("Skipping testing the package:" + self.package)
220 220
                 return
221 221
 
222 222
         #should initialize a logger based on package name
223
-        containerTaskName = "build-" + self.base.package
223
+        containerTaskName = "build-" + self.package
224 224
         containerID = None
225 225
         chrootID = None
226 226
         isToolChainPackage = False
227
-        if self.base.package in constants.listToolChainPackages:
227
+        if self.package in constants.listToolChainPackages:
228 228
             isToolChainPackage = True
229
-        destLogPath = constants.logPath + "/build-" + self.base.package
229
+        destLogPath = constants.logPath + "/build-" + self.package
230 230
         try:
231
-            containerID, chrootID = self.prepareBuildContainer(
232
-                containerTaskName, self.base.package, isToolChainPackage)
231
+            containerID, chrootID = self._prepareBuildContainer(
232
+                containerTaskName, self.package, isToolChainPackage)
233 233
 
234
-            tcUtils = ToolChainUtils(self.base.logName, self.base.logPath)
235
-            if self.base.package in constants.perPackageToolChain:
236
-                self.base.logger.debug(constants.perPackageToolChain[self.base.package])
234
+            tcUtils = ToolChainUtils(self.logName, self.logPath)
235
+            if self.package in constants.perPackageToolChain:
236
+                self.logger.debug(constants.perPackageToolChain[self.package])
237 237
                 tcUtils.installCustomToolChainRPMSinContainer(
238 238
                     containerID,
239
-                    constants.perPackageToolChain[self.base.package],
240
-                    self.base.package)
241
-
242
-            listInstalledPackages, listInstalledRPMs = self.base.findInstalledPackages(containerID)
243
-            self.base.logger.info(listInstalledPackages)
244
-            listDependentPackages = self.base.findBuildTimeRequiredPackages()
245
-            if constants.rpmCheck and self.base.package in constants.testForceRPMS:
246
-                listDependentPackages.extend(self.base.findBuildTimeCheckRequiredPackages())
247
-                testPackages = (set(constants.listMakeCheckRPMPkgtoInstall) -
248
-                                set(listInstalledPackages) -
249
-                                set([self.base.package]))
250
-                listDependentPackages.extend(testPackages)
251
-                listDependentPackages = list(set(listDependentPackages))
252
-
253
-            pkgUtils = PackageUtils(self.base.logName, self.base.logPath)
254
-            if len(listDependentPackages) != 0:
255
-                self.base.logger.info("BuildContainer-buildPackage: " +
256
-                                      "Installing dependent packages..")
257
-                self.base.logger.info(listDependentPackages)
239
+                    constants.perPackageToolChain[self.package],
240
+                    self.package)
241
+
242
+            listDependentPackages, listInstalledPackages, listInstalledRPMs = (
243
+                self._findDependentPackagesAndInstalledRPM(containerID))
244
+
245
+            pkgUtils = PackageUtils(self.logName, self.logPath)
246
+            if listDependentPackages:
247
+                self.logger.info("BuildContainer-buildPackage: " +
248
+                                 "Installing dependent packages..")
249
+                self.logger.info(listDependentPackages)
258 250
                 for pkg in listDependentPackages:
259
-                    self.base.installPackage(pkgUtils, pkg, containerID, destLogPath,
260
-                                             listInstalledPackages, listInstalledRPMs)
251
+                    self._installPackage(pkgUtils, pkg, containerID, destLogPath,
252
+                                         listInstalledPackages, listInstalledRPMs)
261 253
                 pkgUtils.installRPMSInAOneShotInContainer(containerID, destLogPath)
262
-                self.base.logger.info("Finished installing the build time dependent packages....")
254
+                self.logger.info("Finished installing the build time dependent packages....")
263 255
 
264
-            self.base.logger.info("BuildContainer-buildPackage: Start building the package: " +
265
-                                  self.base.package)
266
-            pkgUtils.adjustGCCSpecsInContainer(self.base.package, containerID, destLogPath)
256
+            self.logger.info("BuildContainer-buildPackage: Start building the package: " +
257
+                             self.package)
258
+            pkgUtils.adjustGCCSpecsInContainer(self.package, containerID, destLogPath)
267 259
             pkgUtils.buildRPMSForGivenPackageInContainer(
268
-                self.base.package,
260
+                self.package,
269 261
                 containerID,
270 262
                 destLogPath)
271
-            self.base.logger.info("BuildContainer-buildPackage: Successfully built the package: " +
272
-                                  self.base.package)
263
+            self.logger.info("BuildContainer-buildPackage: Successfully built the package: " +
264
+                             self.package)
273 265
         except Exception as e:
274
-            self.base.logger.error("Failed while building package:" + self.base.package)
266
+            self.logger.error("Failed while building package:" + self.package)
275 267
             if containerID is not None:
276
-                self.base.logger.debug("Container " + containerID.short_id +
277
-                                       " retained for debugging.")
278
-            logFileName = os.path.join(destLogPath, self.base.package + ".log")
268
+                self.logger.debug("Container " + containerID.short_id +
269
+                                  " retained for debugging.")
270
+            logFileName = os.path.join(destLogPath, self.package + ".log")
279 271
             fileLog = os.popen('tail -n 20 ' + logFileName).read()
280
-            self.base.logger.debug(fileLog)
272
+            self.logger.debug(fileLog)
281 273
             raise e
282 274
 
283 275
         # Remove the container
... ...
@@ -285,90 +280,70 @@ class PackageBuilderContainer(object):
285 285
             containerID.remove(force=True)
286 286
         # Remove the dummy chroot
287 287
         if chrootID is not None:
288
-            chrUtils = ChrootUtils(self.base.logName, self.base.logPath)
288
+            chrUtils = ChrootUtils(self.logName, self.logPath)
289 289
             chrUtils.destroyChroot(chrootID)
290 290
 
291
-class PackageBuilderChroot(object):
292
-    def __init__(self, mapPackageToCycles, listAvailableCyclicPackages,
293
-                 pkgBuildType):
294
-        self.base = PackageBuilderBase(mapPackageToCycles, listAvailableCyclicPackages,
295
-                                       pkgBuildType)
296
-
297
-    def buildPackageFunction(self, package, outputMap, threadName):
298
-        self.base.buildPackagePrepareFunction(package, outputMap, threadName)
299
-        try:
300
-            self.buildPackage()
301
-            outputMap[threadName] = True
302
-        except Exception as e:
303
-            # TODO: self.logger might be None
304
-            self.base.logger.exception(e)
305
-            outputMap[threadName] = False
306
-            raise e
291
+class PackageBuilderChroot(PackageBuilderBase):
292
+    def __init__(self, mapPackageToCycles, pkgBuildType):
293
+        PackageBuilderBase.__init__(self, mapPackageToCycles, pkgBuildType)
307 294
 
308
-    def prepareBuildRoot(self):
295
+    def _prepareBuildRoot(self):
309 296
         chrootID = None
310
-        chrootName = "build-" + self.base.package
297
+        chrootName = "build-" + self.package
311 298
         try:
312
-            chrUtils = ChrootUtils(self.base.logName, self.base.logPath)
299
+            chrUtils = ChrootUtils(self.logName, self.logPath)
313 300
             returnVal, chrootID = chrUtils.createChroot(chrootName)
314
-            self.base.logger.debug("Created new chroot: " + chrootID)
301
+            self.logger.debug("Created new chroot: " + chrootID)
315 302
             if not returnVal:
316 303
                 raise Exception("Unable to prepare build root")
317
-            tUtils = ToolChainUtils(self.base.logName, self.base.logPath)
318
-            tUtils.installToolChainRPMS(chrootID, self.base.package, self.base.logPath)
304
+            tUtils = ToolChainUtils(self.logName, self.logPath)
305
+            tUtils.installToolChainRPMS(chrootID, self.package, self.logPath)
319 306
         except Exception as e:
320 307
             if chrootID is not None:
321
-                self.base.logger.debug("Deleting chroot: " + chrootID)
308
+                self.logger.debug("Deleting chroot: " + chrootID)
322 309
                 chrUtils.destroyChroot(chrootID)
323 310
             raise e
324 311
         return chrootID
325 312
 
326
-    def buildPackage(self):
313
+    def _buildPackage(self):
327 314
         #do not build if RPM is already built
328 315
         #test only if the package is in the testForceRPMS with rpmCheck
329 316
         #build only if the package is not in the testForceRPMS with rpmCheck
330
-        if self.base.checkIfPackageIsAlreadyBuilt():
317
+        if self._checkIfPackageIsAlreadyBuilt():
331 318
             if not constants.rpmCheck:
332
-                self.base.logger.info("Skipping building the package:" + self.base.package)
319
+                self.logger.info("Skipping building the package:" + self.package)
333 320
                 return
334
-            elif constants.rpmCheck and self.base.package not in constants.testForceRPMS:
335
-                self.base.logger.info("Skipping testing the package:" + self.base.package)
321
+            elif constants.rpmCheck and self.package not in constants.testForceRPMS:
322
+                self.logger.info("Skipping testing the package:" + self.package)
336 323
                 return
337 324
 
338
-        chrUtils = ChrootUtils(self.base.logName, self.base.logPath)
325
+        chrUtils = ChrootUtils(self.logName, self.logPath)
339 326
         chrootID = None
340 327
         try:
341
-            chrootID = self.prepareBuildRoot()
342
-            listInstalledPackages, listInstalledRPMs = self.base.findInstalledPackages(chrootID)
343
-            listDependentPackages = self.base.findBuildTimeRequiredPackages()
344
-            if constants.rpmCheck and self.base.package in constants.testForceRPMS:
345
-                listDependentPackages.extend(self.base.findBuildTimeCheckRequiredPackages())
346
-                testPackages = (set(constants.listMakeCheckRPMPkgtoInstall) -
347
-                                set(listInstalledPackages) -
348
-                                set([self.base.package]))
349
-                listDependentPackages.extend(testPackages)
350
-                listDependentPackages = list(set(listDependentPackages))
351
-
352
-            pkgUtils = PackageUtils(self.base.logName, self.base.logPath)
353
-            if len(listDependentPackages) != 0:
354
-                self.base.logger.info("Installing the build time dependent packages......")
328
+            chrootID = self._prepareBuildRoot()
329
+            listDependentPackages, listInstalledPackages, listInstalledRPMs = (
330
+                self._findDependentPackagesAndInstalledRPM(chrootID))
331
+
332
+            pkgUtils = PackageUtils(self.logName, self.logPath)
333
+            if listDependentPackages:
334
+                self.logger.info("Installing the build time dependent packages......")
355 335
                 for pkg in listDependentPackages:
356
-                    self.base.installPackage(pkgUtils, pkg, chrootID, self.base.logPath,
357
-                                             listInstalledPackages, listInstalledRPMs)
358
-                pkgUtils.installRPMSInAOneShot(chrootID, self.base.logPath)
359
-                self.base.logger.info("Finished installing the build time dependent packages....")
360
-
361
-            pkgUtils.adjustGCCSpecs(self.base.package, chrootID, self.base.logPath)
362
-            pkgUtils.buildRPMSForGivenPackage(self.base.package, chrootID,
363
-                                              self.base.logPath)
364
-            self.base.logger.info("Successfully built the package:" + self.base.package)
336
+                    self._installPackage(pkgUtils, pkg, chrootID, self.logPath,
337
+                                         listInstalledPackages, listInstalledRPMs)
338
+                pkgUtils.installRPMSInAOneShot(chrootID, self.logPath)
339
+                self.logger.info("Finished installing the build time dependent packages....")
340
+
341
+            pkgUtils.adjustGCCSpecs(self.package, chrootID, self.logPath)
342
+            pkgUtils.buildRPMSForGivenPackage(self.package, chrootID,
343
+                                              self.logPath)
344
+            self.logger.info("Successfully built the package:" + self.package)
365 345
         except Exception as e:
366
-            self.base.logger.error("Failed while building package:" + self.base.package)
367
-            self.base.logger.debug("Chroot with ID: " + chrootID +
368
-                                   " not deleted for debugging.")
369
-            logFileName = os.path.join(self.base.logPath, self.base.package + ".log")
346
+            self.logger.error("Failed while building package:" + self.package)
347
+            self.logger.debug("Chroot with ID: " + chrootID +
348
+                              " not deleted for debugging.")
349
+            logFileName = os.path.join(self.logPath, self.package + ".log")
370 350
             fileLog = os.popen('tail -n 100 ' + logFileName).read()
371
-            self.base.logger.debug(fileLog)
351
+            self.logger.debug(fileLog)
372 352
             raise e
373 353
         if chrootID is not None:
374 354
             chrUtils.destroyChroot(chrootID)
... ...
@@ -55,6 +55,5 @@ class PackageInfo(object):
55 55
         dirPath = os.path.basename(fileName)
56 56
         if not os.path.isdir(dirPath):
57 57
             cmdUtils.runCommandInShell("mkdir -p " + dirPath)
58
-        pkgInfoFile = open(fileName, 'w+')
59
-        json.dump(self.pkgList, pkgInfoFile, indent=4)
60
-        pkgInfoFile.close()
58
+        with open(fileName, 'w+') as pkgInfoFile:
59
+            json.dump(self.pkgList, pkgInfoFile, indent=4)
... ...
@@ -1,5 +1,6 @@
1 1
 import os
2 2
 import threading
3
+import copy
3 4
 from PackageBuildDataGenerator import PackageBuildDataGenerator
4 5
 from Logger import Logger
5 6
 from constants import constants
... ...
@@ -25,16 +26,48 @@ class PackageManager(object):
25 25
         self.mapCyclesToPackageList = {}
26 26
         self.mapPackageToCycle = {}
27 27
         self.sortedPackageList = []
28
-        self.listOfPackagesAlreadyBuilt = []
29
-        self.listThreads = {}
30
-        self.mapOutputThread = {}
31
-        self.mapThreadsLaunchTime = {}
32
-        self.listAvailableCyclicPackages = []
28
+        self.listOfPackagesAlreadyBuilt = set()
33 29
         self.pkgBuildType = pkgBuildType
34 30
         if self.pkgBuildType == "container":
35 31
             self.dockerClient = docker.from_env(version="auto")
36 32
 
37
-    def readPackageBuildData(self, listPackages):
33
+    def buildToolChain(self):
34
+        pkgCount = 0
35
+        try:
36
+            tUtils = ToolChainUtils()
37
+            pkgCount = tUtils.buildCoreToolChainPackages()
38
+        except Exception as e:
39
+            self.logger.error("Unable to build tool chain")
40
+            self.logger.error(e)
41
+            raise e
42
+        return pkgCount
43
+
44
+    def buildToolChainPackages(self, buildThreads):
45
+        pkgCount = self.buildToolChain()
46
+        if self.pkgBuildType == "container":
47
+            # Stage 1 build container
48
+            #TODO image name constants.buildContainerImageName
49
+            if pkgCount > 0 or not self.dockerClient.images.list("photon_build_container:latest"):
50
+                self._createBuildContainer()
51
+        self._buildGivenPackages(constants.listToolChainPackages, buildThreads)
52
+        if self.pkgBuildType == "container":
53
+            # Stage 2 build container
54
+            #TODO: rebuild container only if anything in listToolChainPackages was built
55
+            self._createBuildContainer()
56
+
57
+    def buildPackages(self, listPackages, buildThreads, pkgBuildType):
58
+        self.pkgBuildType = pkgBuildType
59
+        if constants.rpmCheck:
60
+            constants.rpmCheck = False
61
+            self.buildToolChainPackages(buildThreads)
62
+            self._buildTestPackages(buildThreads)
63
+            constants.rpmCheck = True
64
+            self._buildGivenPackages(listPackages, buildThreads)
65
+        else:
66
+            self.buildToolChainPackages(buildThreads)
67
+            self._buildGivenPackages(listPackages, buildThreads)
68
+
69
+    def _readPackageBuildData(self, listPackages):
38 70
         try:
39 71
             pkgBuildDataGen = PackageBuildDataGenerator(self.logName, self.logPath)
40 72
             self.mapCyclesToPackageList, self.mapPackageToCycle, self.sortedPackageList = (
... ...
@@ -46,23 +79,23 @@ class PackageManager(object):
46 46
             return False
47 47
         return True
48 48
 
49
-    def readAlreadyAvailablePackages(self):
50
-        listAvailablePackages = []
51
-        listFoundRPMPackages = []
52
-        listRPMFiles = []
53
-        listDirectorys = []
54
-        listDirectorys.append(constants.rpmPath)
49
+    def _readAlreadyAvailablePackages(self):
50
+        listAvailablePackages = set()
51
+        listFoundRPMPackages = set()
52
+        listRPMFiles = set()
53
+        listDirectorys = set()
54
+        listDirectorys.add(constants.rpmPath)
55 55
         if constants.inputRPMSPath is not None:
56
-            listDirectorys.append(constants.inputRPMSPath)
56
+            listDirectorys.add(constants.inputRPMSPath)
57 57
 
58
-        while len(listDirectorys) > 0:
58
+        while listDirectorys:
59 59
             dirPath = listDirectorys.pop()
60 60
             for dirEntry in os.listdir(dirPath):
61 61
                 dirEntryPath = os.path.join(dirPath, dirEntry)
62 62
                 if os.path.isfile(dirEntryPath) and dirEntryPath.endswith(".rpm"):
63
-                    listRPMFiles.append(dirEntryPath)
63
+                    listRPMFiles.add(dirEntryPath)
64 64
                 elif os.path.isdir(dirEntryPath):
65
-                    listDirectorys.append(dirEntryPath)
65
+                    listDirectorys.add(dirEntryPath)
66 66
         pkgUtils = PackageUtils(self.logName, self.logPath)
67 67
         for rpmfile in listRPMFiles:
68 68
             package, version, release = pkgUtils.findPackageInfoFromRPMFile(rpmfile)
... ...
@@ -70,7 +103,7 @@ class PackageManager(object):
70 70
                 specVersion = SPECS.getData().getVersion(package)
71 71
                 specRelease = SPECS.getData().getRelease(package)
72 72
                 if version == specVersion and release == specRelease:
73
-                    listFoundRPMPackages.append(package)
73
+                    listFoundRPMPackages.add(package)
74 74
         #Mark package available only if all sub packages are available
75 75
         for package in listFoundRPMPackages:
76 76
             basePkg = SPECS.getData().getSpecName(package)
... ...
@@ -82,28 +115,22 @@ class PackageManager(object):
82 82
                 if rpmpkg not in listFoundRPMPackages:
83 83
                     packageIsAlreadyBuilt = False
84 84
             if packageIsAlreadyBuilt:
85
-                listAvailablePackages.append(package)
85
+                listAvailablePackages.add(package)
86 86
         self.logger.info("List of Already built packages")
87 87
         self.logger.info(listAvailablePackages)
88 88
         return listAvailablePackages
89 89
 
90
-    def calculateParams(self, listPackages):
91
-        self.listThreads.clear()
92
-        self.mapOutputThread.clear()
93
-        self.mapThreadsLaunchTime.clear()
94
-        self.listAvailableCyclicPackages = []
90
+    def _calculateParams(self, listPackages):
95 91
         self.mapCyclesToPackageList.clear()
96 92
         self.mapPackageToCycle.clear()
97 93
         self.sortedPackageList = []
98 94
 
99
-        listOfPackagesAlreadyBuilt = []
100
-        listOfPackagesAlreadyBuilt = self.readAlreadyAvailablePackages()
101
-        self.listOfPackagesAlreadyBuilt = listOfPackagesAlreadyBuilt[:]
95
+        self.listOfPackagesAlreadyBuilt = self._readAlreadyAvailablePackages()
102 96
 
103 97
         updateBuiltRPMSList = False
104 98
         while not updateBuiltRPMSList:
105 99
             updateBuiltRPMSList = True
106
-            listOfPackagesAlreadyBuilt = self.listOfPackagesAlreadyBuilt[:]
100
+            listOfPackagesAlreadyBuilt = list(self.listOfPackagesAlreadyBuilt)
107 101
             for pkg in listOfPackagesAlreadyBuilt:
108 102
                 listDependentRpmPackages = SPECS.getData().getRequiresAllForPackage(pkg)
109 103
                 needToRebuild = False
... ...
@@ -114,98 +141,57 @@ class PackageManager(object):
114 114
                 if needToRebuild:
115 115
                     self.listOfPackagesAlreadyBuilt.remove(pkg)
116 116
 
117
-        listPackagesToBuild = listPackages[:]
117
+        listPackagesToBuild = copy.copy(listPackages)
118 118
         for pkg in listPackages:
119 119
             if (pkg in self.listOfPackagesAlreadyBuilt and
120 120
                     not constants.rpmCheck):
121 121
                 listPackagesToBuild.remove(pkg)
122 122
 
123
-        if not self.readPackageBuildData(listPackagesToBuild):
123
+        if not self._readPackageBuildData(listPackagesToBuild):
124 124
             return False
125 125
         return True
126 126
 
127
-    def buildToolChain(self):
128
-        pkgCount = 0
129
-        try:
130
-            tUtils = ToolChainUtils()
131
-            pkgCount = tUtils.buildCoreToolChainPackages()
132
-        except Exception as e:
133
-            self.logger.error("Unable to build tool chain")
134
-            self.logger.error(e)
135
-            raise e
136
-        return pkgCount
137
-
138
-    def buildToolChainPackages(self, buildThreads):
139
-        pkgCount = self.buildToolChain()
140
-        if self.pkgBuildType == "container":
141
-            # Stage 1 build container
142
-            #TODO image name constants.buildContainerImageName
143
-            if pkgCount > 0 or not self.dockerClient.images.list("photon_build_container:latest"):
144
-                self.createBuildContainer()
145
-        self.buildGivenPackages(constants.listToolChainPackages, buildThreads)
146
-        if self.pkgBuildType == "container":
147
-            # Stage 2 build container
148
-            #TODO: rebuild container only if anything in listToolChainPackages was built
149
-            self.createBuildContainer()
150
-
151
-    def buildTestPackages(self, buildThreads):
127
+    def _buildTestPackages(self, buildThreads):
152 128
         self.buildToolChain()
153
-        self.buildGivenPackages(constants.listMakeCheckRPMPkgtoInstall, buildThreads)
154
-
155
-    def buildPackages(self, listPackages, buildThreads, pkgBuildType):
156
-        self.pkgBuildType = pkgBuildType
157
-        if constants.rpmCheck:
158
-            constants.rpmCheck = False
159
-            self.buildToolChainPackages(buildThreads)
160
-            self.buildTestPackages(buildThreads)
161
-            constants.rpmCheck = True
162
-            self.buildGivenPackages(listPackages, buildThreads)
163
-        else:
164
-            self.buildToolChainPackages(buildThreads)
165
-            self.buildGivenPackages(listPackages, buildThreads)
129
+        self._buildGivenPackages(constants.listMakeCheckRPMPkgtoInstall, buildThreads)
166 130
 
167
-    def initializeThreadPool(self, statusEvent):
131
+    def _initializeThreadPool(self, statusEvent):
168 132
         ThreadPool.clear()
169 133
         ThreadPool.mapPackageToCycle = self.mapPackageToCycle
170
-        ThreadPool.listAvailableCyclicPackages = self.listAvailableCyclicPackages
171 134
         ThreadPool.logger = self.logger
172 135
         ThreadPool.statusEvent = statusEvent
173 136
         ThreadPool.pkgBuildType = self.pkgBuildType
174 137
 
175
-    def initializeScheduler(self, statusEvent):
138
+    def _initializeScheduler(self, statusEvent):
176 139
         Scheduler.setLog(self.logName, self.logPath)
177 140
         Scheduler.setParams(self.sortedPackageList, self.listOfPackagesAlreadyBuilt)
178 141
         Scheduler.setEvent(statusEvent)
179 142
         Scheduler.stopScheduling = False
180 143
 
181
-    def buildGivenPackages(self, listPackages, buildThreads):
144
+    def _buildGivenPackages(self, listPackages, buildThreads):
182 145
         if constants.rpmCheck:
183
-            alreadyBuiltRPMS = self.readAlreadyAvailablePackages()
146
+            alreadyBuiltRPMS = self._readAlreadyAvailablePackages()
184 147
             listPackages = (list(set(listPackages)|(set(constants.listMakeCheckRPMPkgtoInstall)-
185
-                                                    set(alreadyBuiltRPMS))))
148
+                                                    alreadyBuiltRPMS)))
186 149
 
187
-        returnVal = self.calculateParams(listPackages)
150
+        returnVal = self._calculateParams(listPackages)
188 151
         if not returnVal:
189 152
             self.logger.error("Unable to set paramaters. Terminating the package manager.")
190 153
             raise Exception("Unable to set paramaters")
191 154
 
192 155
         statusEvent = threading.Event()
193
-        self.initializeScheduler(statusEvent)
194
-        self.initializeThreadPool(statusEvent)
156
+        self._initializeScheduler(statusEvent)
157
+        self._initializeThreadPool(statusEvent)
195 158
 
196
-        i = 0
197
-        while i < buildThreads:
159
+        for i in range(0, buildThreads):
198 160
             workerName = "WorkerThread" + str(i)
199 161
             ThreadPool.addWorkerThread(workerName)
200 162
             ThreadPool.startWorkerThread(workerName)
201
-            i = i + 1
202 163
 
203 164
         statusEvent.wait()
204 165
         Scheduler.stopScheduling = True
205 166
         self.logger.info("Waiting for all remaining worker threads")
206
-        listWorkerObjs = ThreadPool.getAllWorkerObjects()
207
-        for w in listWorkerObjs:
208
-            w.join()
167
+        ThreadPool.join_all()
209 168
 
210 169
         setFailFlag = False
211 170
         allPackagesBuilt = False
... ...
@@ -229,7 +215,7 @@ class PackageManager(object):
229 229
 
230 230
         self.logger.info("Terminated")
231 231
 
232
-    def createBuildContainer(self):
232
+    def _createBuildContainer(self):
233 233
         self.logger.info("Generating photon build container..")
234 234
         try:
235 235
             #TODO image name constants.buildContainerImageName
... ...
@@ -4,8 +4,6 @@ import shutil
4 4
 import re
5 5
 import random
6 6
 import string
7
-import collections
8
-import json
9 7
 from CommandUtils import CommandUtils
10 8
 from Logger import Logger
11 9
 from constants import constants
... ...
@@ -43,37 +41,6 @@ class PackageUtils(object):
43 43
         self.rpmFilesToReInstallInAOneShot = ""
44 44
         self.noDepsRPMFilesToReInstallInAOneShot = ""
45 45
 
46
-    def getRPMArch(self, rpmName):
47
-        arch = ""
48
-        if rpmName.find("x86_64") != -1:
49
-            arch = "x86_64"
50
-        elif rpmName.find("aarch64") != -1:
51
-            arch = "aarch64"
52
-        elif rpmName.find("noarch") != -1:
53
-            arch = "noarch"
54
-        return arch
55
-
56
-    def getRPMDestDir(self, rpmName, rpmDir):
57
-        arch = self.getRPMArch(rpmName)
58
-        rpmDestDir = rpmDir + "/" + arch
59
-        return rpmDestDir
60
-
61
-    def copyRPM(self, rpmFile, destDir):
62
-        cmdUtils = CommandUtils()
63
-        rpmName = os.path.basename(rpmFile)
64
-        rpmDestDir = self.getRPMDestDir(rpmName, destDir)
65
-        # shutil is not atomic. copy & move to ensure atomicity.
66
-        rpmDestPath = rpmDestDir + "/" + rpmName
67
-        rpmDestPathTemp = (rpmDestDir + "/." +
68
-                           ''.join([random.choice(string.ascii_letters +
69
-                                                  string.digits) for n in range(10)]))
70
-        if os.geteuid() == 0:
71
-            if not os.path.isdir(rpmDestDir):
72
-                cmdUtils.runCommandInShell("mkdir -p " + rpmDestDir)
73
-            shutil.copyfile(rpmFile, rpmDestPathTemp)
74
-            shutil.move(rpmDestPathTemp, rpmDestPath)
75
-        return rpmDestPath
76
-
77 46
     def installRPM(self, package, chrootID, noDeps=False, destLogPath=None):
78 47
 #        self.logger.info("Installing rpm for package:"+package)
79 48
 #        self.logger.debug("No deps:"+str(noDeps))
... ...
@@ -83,7 +50,7 @@ class PackageUtils(object):
83 83
             self.logger.error("No rpm file found for package:" + package)
84 84
             raise Exception("Missing rpm file: " + package)
85 85
 
86
-        rpmDestFile = self.copyRPM(rpmfile, chrootID + constants.topDirPath + "/RPMS")
86
+        rpmDestFile = self._copyRPM(rpmfile, chrootID + constants.topDirPath + "/RPMS")
87 87
         rpmFile = rpmDestFile.replace(chrootID, "")
88 88
         if noDeps:
89 89
             self.noDepsRPMFilesToInstallInAOneShot += " " + rpmFile
... ...
@@ -117,67 +84,6 @@ class PackageUtils(object):
117 117
                 self.logger.error("Unable to install rpms")
118 118
                 raise Exception("RPM installation failed")
119 119
 
120
-    def verifyShaAndGetSourcePath(self, source, package):
121
-        cmdUtils = CommandUtils()
122
-        # Fetch/verify sources if sha1 not None.
123
-        sha1 = SPECS.getData().getSHA1(package, source)
124
-        if sha1 is not None:
125
-            PullSources.get(source, sha1, constants.sourcePath, constants.pullsourcesConfig,
126
-                            self.logger)
127
-
128
-        sourcePath = cmdUtils.findFile(source, constants.sourcePath)
129
-        if sourcePath is None or len(sourcePath) == 0:
130
-            sourcePath = cmdUtils.findFile(source, constants.specPath)
131
-            if sourcePath is None or len(sourcePath) == 0:
132
-                if sha1 is None:
133
-                    self.logger.error("No sha1 found or missing source for " + source)
134
-                    raise Exception("No sha1 found or missing source for " + source)
135
-                else:
136
-                    self.logger.error("Missing source: " + source +
137
-                                      ". Cannot find sources for package: " + package)
138
-                    raise Exception("Missing source")
139
-        else:
140
-            if sha1 is None:
141
-                self.logger.error("No sha1 found for "+source)
142
-                raise Exception("No sha1 found")
143
-        if len(sourcePath) > 1:
144
-            self.logger.error("Multiple sources found for source:" + source + "\n" +
145
-                              ",".join(sourcePath) +"\nUnable to determine one.")
146
-            raise Exception("Multiple sources found")
147
-        return sourcePath
148
-
149
-    def copySourcesTobuildroot(self, listSourceFiles, package, destDir):
150
-        for source in listSourceFiles:
151
-            sourcePath = self.verifyShaAndGetSourcePath(source, package)
152
-            self.logger.info("Copying... Source path :" + source +
153
-                             " Source filename: " + sourcePath[0])
154
-            shutil.copy2(sourcePath[0], destDir)
155
-
156
-    def copyAdditionalBuildFiles(self, listAdditionalFiles, chrootID):
157
-        cmdUtils = CommandUtils()
158
-        for additionalFile in listAdditionalFiles:
159
-            source = additionalFile["src"]
160
-            destDir = chrootID + additionalFile["dst"]
161
-            self.logger.info("Copying additional Source build files :" + source)
162
-            if os.path.exists(source):
163
-                if os.path.isfile(source):
164
-                    shutil.copy(source, destDir)
165
-                else:
166
-                    shutil.copytree(source, destDir)
167
-
168
-    def getAdditionalBuildFiles(self, package):
169
-        listAdditionalFiles = []
170
-        macros = []
171
-        if package in constants.buildOptions.keys():
172
-            pkg = constants.buildOptions[package]
173
-            filelist = pkg["files"]
174
-            for f in filelist:
175
-                listAdditionalFiles.append(f)
176
-            macrolist = pkg["macros"]
177
-            for macro in macrolist:
178
-                macros.append(macro)
179
-        return listAdditionalFiles, macros
180
-
181 120
     def buildRPMSForGivenPackage(self, package, chrootID, destLogPath=None):
182 121
         self.logger.info("Building rpm's for package:" + package)
183 122
 
... ...
@@ -194,24 +100,24 @@ class PackageUtils(object):
194 194
 
195 195
         # FIXME: some sources are located in SPECS/.. how to mount?
196 196
         #        if os.geteuid()==0:
197
-        self.copySourcesTobuildroot(listSourcesFiles, package, chrootSourcePath)
198
-        self.copySourcesTobuildroot(listPatchFiles, package, chrootSourcePath)
197
+        self._copySourcesTobuildroot(listSourcesFiles, package, chrootSourcePath)
198
+        self._copySourcesTobuildroot(listPatchFiles, package, chrootSourcePath)
199 199
         macros = []
200 200
 
201
-        listAdditionalFiles, macros = self.getAdditionalBuildFiles(package)
202
-        self.copyAdditionalBuildFiles(listAdditionalFiles, chrootID)
201
+        listAdditionalFiles, macros = self._getAdditionalBuildFiles(package)
202
+        self._copyAdditionalBuildFiles(listAdditionalFiles, chrootID)
203 203
 
204 204
         #Adding rpm macros
205 205
         listRPMMacros = constants.userDefinedMacros
206
-        for macroName in listRPMMacros.keys():
207
-            macros.append(macroName + " " + listRPMMacros[macroName])
206
+        for macroName, value in listRPMMacros.items():
207
+            macros.append(macroName + " " + value)
208 208
 
209 209
         listRPMFiles = []
210 210
         listSRPMFiles = []
211 211
         try:
212
-            listRPMFiles, listSRPMFiles = self.buildRPM(chrootSpecPath + specName,
213
-                                                        chrootLogsFilePath, chrootCmd,
214
-                                                        package, macros)
212
+            listRPMFiles, listSRPMFiles = self._buildRPM(chrootSpecPath + specName,
213
+                                                         chrootLogsFilePath, chrootCmd,
214
+                                                         package, macros)
215 215
             self.logger.info("Successfully built rpm:" + package)
216 216
         except Exception as e:
217 217
             self.logger.error("Failed while building rpm:" + package)
... ...
@@ -232,74 +138,10 @@ class PackageUtils(object):
232 232
         self.logger.info("RPM build is successful")
233 233
 
234 234
         for rpmFile in listRPMFiles:
235
-            self.copyRPM(chrootID + "/" + rpmFile, constants.rpmPath)
235
+            self._copyRPM(chrootID + "/" + rpmFile, constants.rpmPath)
236 236
 
237 237
         for srpmFile in listSRPMFiles:
238
-            srpmDestFile = self.copyRPM(chrootID + "/" + srpmFile, constants.sourceRpmPath)
239
-
240
-    def buildRPM(self, specFile, logFile, chrootCmd, package, macros):
241
-
242
-        rpmBuildcmd = self.rpmbuildBinary + " " + self.rpmbuildBuildallOption
243
-
244
-        if constants.rpmCheck and package in constants.testForceRPMS:
245
-            self.logger.info("#" * (68 + 2 * len(package)))
246
-            if not SPECS.getData().isCheckAvailable(package):
247
-                self.logger.info("####### " + package +
248
-                                 " MakeCheck is not available. Skipping MakeCheck TEST for " +
249
-                                 package + " #######")
250
-                rpmBuildcmd = self.rpmbuildBinary + " --clean"
251
-            else:
252
-                self.logger.info("####### " + package +
253
-                                 " MakeCheck is available. Running MakeCheck TEST for " +
254
-                                 package + " #######")
255
-                rpmBuildcmd = self.rpmbuildBinary + " " + self.rpmbuildCheckOption
256
-            self.logger.info("#" * (68 + 2 * len(package)))
257
-        else:
258
-            rpmBuildcmd += " " + self.rpmbuildNocheckOption
259
-
260
-        for macro in macros:
261
-            rpmBuildcmd += ' --define \\\"%s\\\"' % macro
262
-        rpmBuildcmd += " " + specFile
263
-
264
-        cmdUtils = CommandUtils()
265
-        self.logger.info("Building rpm....")
266
-        self.logger.info(rpmBuildcmd)
267
-        returnVal = cmdUtils.runCommandInShell(rpmBuildcmd, logFile, chrootCmd)
268
-        if constants.rpmCheck and package in constants.testForceRPMS:
269
-            if not SPECS.getData().isCheckAvailable(package):
270
-                constants.testLogger.info(package + " : N/A")
271
-            elif returnVal:
272
-                constants.testLogger.info(package + " : PASS")
273
-            else:
274
-                constants.testLogger.error(package + " : FAIL")
275
-
276
-        if constants.rpmCheck:
277
-            if not returnVal and constants.rpmCheckStopOnError:
278
-                self.logger.error("Checking rpm is failed " + specFile)
279
-                raise Exception("RPM check failed")
280
-        else:
281
-            if not returnVal:
282
-                self.logger.error("Building rpm is failed " + specFile)
283
-                raise Exception("RPM build failed")
284
-
285
-        #Extracting rpms created from log file
286
-        logfile = open(logFile, 'r')
287
-        fileContents = logfile.readlines()
288
-        logfile.close()
289
-        listRPMFiles = []
290
-        listSRPMFiles = []
291
-        for i in range(0, len(fileContents)):
292
-            if re.search("^Wrote:", fileContents[i]):
293
-                listcontents = fileContents[i].split()
294
-                if ((len(listcontents) == 2) and
295
-                        listcontents[1].strip().endswith(".rpm") and
296
-                        "/RPMS/" in listcontents[1]):
297
-                    listRPMFiles.append(listcontents[1])
298
-                if ((len(listcontents) == 2) and
299
-                        listcontents[1].strip().endswith(".src.rpm") and
300
-                        "/SRPMS/" in listcontents[1]):
301
-                    listSRPMFiles.append(listcontents[1])
302
-        return listRPMFiles, listSRPMFiles
238
+            srpmDestFile = self._copyRPM(chrootID + "/" + srpmFile, constants.sourceRpmPath)
303 239
 
304 240
     def findRPMFileForGivenPackage(self, package):
305 241
         cmdUtils = CommandUtils()
... ...
@@ -327,19 +169,6 @@ class PackageUtils(object):
327 327
                               "Unable to determine the rpm file for package:" + package)
328 328
             raise Exception("Multiple rpm files found")
329 329
 
330
-    def findPackageNameFromRPMFile(self, rpmfile):
331
-        rpmfile = os.path.basename(rpmfile)
332
-        releaseindex = rpmfile.rfind("-")
333
-        if releaseindex == -1:
334
-            self.logger.error("Invalid rpm file:" + rpmfile)
335
-            raise Exception("Invalid RPM")
336
-        versionindex = rpmfile[0:releaseindex].rfind("-")
337
-        if versionindex == -1:
338
-            self.logger.error("Invalid rpm file:" + rpmfile)
339
-            raise Exception("Invalid RPM")
340
-        packageName = rpmfile[0:versionindex]
341
-        return packageName
342
-
343 330
     def findPackageInfoFromRPMFile(self, rpmfile):
344 331
         rpmfile = os.path.basename(rpmfile)
345 332
         rpmfile = rpmfile.replace("." + platform.machine() + ".rpm", "")
... ...
@@ -391,59 +220,13 @@ class PackageUtils(object):
391 391
         self.logger.error("Failed while adjusting gcc specs")
392 392
         raise Exception("Failed while adjusting gcc specs")
393 393
 
394
-    def copySourcesToContainer(self, listSourceFiles, package, containerID, destDir):
395
-        cmdUtils = CommandUtils()
396
-        for source in listSourceFiles:
397
-            sourcePath = self.verifyShaAndGetSourcePath(source, package)
398
-            self.logger.info("Copying source file: " + sourcePath[0])
399
-            copyCmd = "docker cp " + sourcePath[0] + " " + containerID.short_id + ":" + destDir
400
-            cmdUtils.runCommandInShell(copyCmd)
401
-
402
-    def copyAdditionalBuildFilesToContainer(self, listAdditionalFiles, containerID):
403
-        cmdUtils = CommandUtils()
404
-        #self.logger.debug("VDBG-PU-copyAdditionalBuildFilesToContainer id: " +
405
-        #                  containerID.short_id)
406
-        #self.logger.debug(listAdditionalFiles)
407
-        for additionalFile in listAdditionalFiles:
408
-            source = additionalFile["src"]
409
-            destDir = additionalFile["dst"]
410
-            destPath = containerID.short_id + ":" + destDir
411
-            #TODO: exit status of exec_run
412
-            containerID.exec_run("mkdir -p " + destDir)
413
-            if os.path.exists(source):
414
-                copyCmd = "docker cp " + source
415
-                if os.path.isfile(source):
416
-                    self.logger.info("Copying additional source file: " + source)
417
-                    copyCmd += " " + destPath
418
-                else:
419
-                    self.logger.info("Copying additional source file tree: " + source)
420
-                    copyCmd += "/. " + destPath
421
-                #TODO: cmd error code
422
-                cmdUtils.runCommandInShell(copyCmd)
423
-
424
-    def getRPMPathInContainer(self, rpmFile, containerID):
425
-        rpmName = os.path.basename(rpmFile)
426
-        #TODO: Container path from constants
427
-        if "PUBLISHRPMS" in rpmFile:
428
-            rpmPath = "/publishrpms/"
429
-        elif "PUBLISHXRPMS" in rpmFile:
430
-            rpmPath = "/publishxrpms/"
431
-        else:
432
-            rpmPath = constants.topDirPath + "/RPMS/"
433
-        if "noarch" in rpmFile:
434
-            rpmPath += "noarch/"
435
-        else:
436
-            rpmPath += platform.machine()+"/"
437
-        rpmPath += rpmName
438
-        return rpmPath
439
-
440 394
     def prepRPMforInstallInContainer(self, package, containerID, noDeps=False, destLogPath=None):
441 395
         rpmfile = self.findRPMFileForGivenPackage(package)
442 396
         if rpmfile is None:
443 397
             self.logger.error("No rpm file found for package: " + package)
444 398
             raise Exception("Missing rpm file")
445 399
 
446
-        rpmDestFile = self.getRPMPathInContainer(rpmfile, containerID)
400
+        rpmDestFile = self._getRPMPathInContainer(rpmfile, containerID)
447 401
         if noDeps:
448 402
             self.noDepsRPMFilesToInstallInAOneShot += " " + rpmDestFile
449 403
             self.noDepsPackagesToInstallInAOneShot += " " + package
... ...
@@ -575,22 +358,22 @@ class PackageUtils(object):
575 575
         #        if os.geteuid()==0:
576 576
         #TODO: mount it in, don't copy
577 577
         macros = []
578
-        self.copySourcesToContainer(listSourcesFiles, package, containerID, sourcePath)
578
+        self._copySourcesToContainer(listSourcesFiles, package, containerID, sourcePath)
579 579
         #TODO: mount it in, don't copy
580
-        self.copySourcesToContainer(listPatchFiles, package, containerID, sourcePath)
581
-        listAdditionalFiles, macros = self.getAdditionalBuildFiles(package)
582
-        self.copyAdditionalBuildFilesToContainer(listAdditionalFiles, containerID)
580
+        self._copySourcesToContainer(listPatchFiles, package, containerID, sourcePath)
581
+        listAdditionalFiles, macros = self._getAdditionalBuildFiles(package)
582
+        self._copyAdditionalBuildFilesToContainer(listAdditionalFiles, containerID)
583 583
 
584 584
         # Add rpm macros
585 585
         listRPMMacros = constants.userDefinedMacros
586
-        for macroName in listRPMMacros.keys():
587
-            macros.append(macroName + " " + listRPMMacros[macroName])
586
+        for macroName, value in listRPMMacros.items():
587
+            macros.append(macroName + " " + value)
588 588
 
589 589
         # Build RPMs
590 590
         listRPMFiles = []
591 591
         listSRPMFiles = []
592 592
         try:
593
-            listRPMFiles, listSRPMFiles = self.buildRPMinContainer(
593
+            listRPMFiles, listSRPMFiles = self._buildRPMinContainer(
594 594
                 specPath + specName,
595 595
                 rpmLogFile,
596 596
                 destLogFile,
... ...
@@ -617,7 +400,7 @@ class PackageUtils(object):
617 617
         # Verify RPM and SRPM files exist as success criteria
618 618
         for rpmFile in listRPMFiles:
619 619
             rpmName = os.path.basename(rpmFile)
620
-            rpmDestDir = self.getRPMDestDir(rpmName, constants.rpmPath)
620
+            rpmDestDir = self._getRPMDestDir(rpmName, constants.rpmPath)
621 621
             rpmDestFile = rpmDestDir + "/" + rpmName
622 622
             if not os.path.isfile(rpmDestFile):
623 623
                 self.logger.error("Could not find RPM file: " + rpmDestFile)
... ...
@@ -625,13 +408,217 @@ class PackageUtils(object):
625 625
 
626 626
         for srpmFile in listSRPMFiles:
627 627
             srpmName = os.path.basename(srpmFile)
628
-            srpmDestDir = self.getRPMDestDir(os.path.basename(srpmFile), constants.sourceRpmPath)
628
+            srpmDestDir = self._getRPMDestDir(os.path.basename(srpmFile), constants.sourceRpmPath)
629 629
             srpmDestFile = srpmDestDir + "/" + srpmName
630 630
             if not os.path.isfile(srpmDestFile):
631 631
                 self.logger.error("Could not find RPM file: " + srpmDestFile)
632 632
                 raise Exception("Built SRPM file not found.")
633 633
 
634
-    def buildRPMinContainer(self, specFile, rpmLogFile, destLogFile, containerID, package, macros):
634
+    def _getRPMArch(self, rpmName):
635
+        arch = ""
636
+        if "x86_64" in rpmName:
637
+            arch = "x86_64"
638
+        elif "aarch64" in rpmName:
639
+            arch = "aarch64"
640
+        elif "noarch" in rpmName:
641
+            arch = "noarch"
642
+        return arch
643
+
644
+    def _getRPMDestDir(self, rpmName, rpmDir):
645
+        arch = self._getRPMArch(rpmName)
646
+        rpmDestDir = rpmDir + "/" + arch
647
+        return rpmDestDir
648
+
649
+    def _copyRPM(self, rpmFile, destDir):
650
+        cmdUtils = CommandUtils()
651
+        rpmName = os.path.basename(rpmFile)
652
+        rpmDestDir = self._getRPMDestDir(rpmName, destDir)
653
+        # shutil is not atomic. copy & move to ensure atomicity.
654
+        rpmDestPath = rpmDestDir + "/" + rpmName
655
+        rpmDestPathTemp = (rpmDestDir + "/." +
656
+                           ''.join([random.choice(string.ascii_letters +
657
+                                                  string.digits) for n in range(10)]))
658
+        if os.geteuid() == 0:
659
+            if not os.path.isdir(rpmDestDir):
660
+                cmdUtils.runCommandInShell("mkdir -p " + rpmDestDir)
661
+            shutil.copyfile(rpmFile, rpmDestPathTemp)
662
+            shutil.move(rpmDestPathTemp, rpmDestPath)
663
+        return rpmDestPath
664
+
665
+    def _verifyShaAndGetSourcePath(self, source, package):
666
+        cmdUtils = CommandUtils()
667
+        # Fetch/verify sources if sha1 not None.
668
+        sha1 = SPECS.getData().getSHA1(package, source)
669
+        if sha1 is not None:
670
+            PullSources.get(source, sha1, constants.sourcePath, constants.pullsourcesConfig,
671
+                            self.logger)
672
+
673
+        sourcePath = cmdUtils.findFile(source, constants.sourcePath)
674
+        if not sourcePath:
675
+            sourcePath = cmdUtils.findFile(source, constants.specPath)
676
+            if not sourcePath:
677
+                if sha1 is None:
678
+                    self.logger.error("No sha1 found or missing source for " + source)
679
+                    raise Exception("No sha1 found or missing source for " + source)
680
+                else:
681
+                    self.logger.error("Missing source: " + source +
682
+                                      ". Cannot find sources for package: " + package)
683
+                    raise Exception("Missing source")
684
+        else:
685
+            if sha1 is None:
686
+                self.logger.error("No sha1 found for "+source)
687
+                raise Exception("No sha1 found")
688
+        if len(sourcePath) > 1:
689
+            self.logger.error("Multiple sources found for source:" + source + "\n" +
690
+                              ",".join(sourcePath) +"\nUnable to determine one.")
691
+            raise Exception("Multiple sources found")
692
+        return sourcePath
693
+
694
+    def _copySourcesTobuildroot(self, listSourceFiles, package, destDir):
695
+        for source in listSourceFiles:
696
+            sourcePath = self._verifyShaAndGetSourcePath(source, package)
697
+            self.logger.info("Copying... Source path :" + source +
698
+                             " Source filename: " + sourcePath[0])
699
+            shutil.copy2(sourcePath[0], destDir)
700
+
701
+    def _copyAdditionalBuildFiles(self, listAdditionalFiles, chrootID):
702
+        cmdUtils = CommandUtils()
703
+        for additionalFile in listAdditionalFiles:
704
+            source = additionalFile["src"]
705
+            destDir = chrootID + additionalFile["dst"]
706
+            self.logger.info("Copying additional Source build files :" + source)
707
+            if os.path.exists(source):
708
+                if os.path.isfile(source):
709
+                    shutil.copy(source, destDir)
710
+                else:
711
+                    shutil.copytree(source, destDir)
712
+
713
+    def _getAdditionalBuildFiles(self, package):
714
+        listAdditionalFiles = []
715
+        macros = []
716
+        if package in constants.buildOptions.keys():
717
+            pkg = constants.buildOptions[package]
718
+            filelist = pkg["files"]
719
+            for f in filelist:
720
+                listAdditionalFiles.append(f)
721
+            macrolist = pkg["macros"]
722
+            for macro in macrolist:
723
+                macros.append(macro)
724
+        return listAdditionalFiles, macros
725
+
726
+
727
+    def _buildRPM(self, specFile, logFile, chrootCmd, package, macros):
728
+
729
+        rpmBuildcmd = self.rpmbuildBinary + " " + self.rpmbuildBuildallOption
730
+
731
+        if constants.rpmCheck and package in constants.testForceRPMS:
732
+            self.logger.info("#" * (68 + 2 * len(package)))
733
+            if not SPECS.getData().isCheckAvailable(package):
734
+                self.logger.info("####### " + package +
735
+                                 " MakeCheck is not available. Skipping MakeCheck TEST for " +
736
+                                 package + " #######")
737
+                rpmBuildcmd = self.rpmbuildBinary + " --clean"
738
+            else:
739
+                self.logger.info("####### " + package +
740
+                                 " MakeCheck is available. Running MakeCheck TEST for " +
741
+                                 package + " #######")
742
+                rpmBuildcmd = self.rpmbuildBinary + " " + self.rpmbuildCheckOption
743
+            self.logger.info("#" * (68 + 2 * len(package)))
744
+        else:
745
+            rpmBuildcmd += " " + self.rpmbuildNocheckOption
746
+
747
+        for macro in macros:
748
+            rpmBuildcmd += ' --define \\\"%s\\\"' % macro
749
+        rpmBuildcmd += " " + specFile
750
+
751
+        cmdUtils = CommandUtils()
752
+        self.logger.info("Building rpm....")
753
+        self.logger.info(rpmBuildcmd)
754
+        returnVal = cmdUtils.runCommandInShell(rpmBuildcmd, logFile, chrootCmd)
755
+        if constants.rpmCheck and package in constants.testForceRPMS:
756
+            if not SPECS.getData().isCheckAvailable(package):
757
+                constants.testLogger.info(package + " : N/A")
758
+            elif returnVal:
759
+                constants.testLogger.info(package + " : PASS")
760
+            else:
761
+                constants.testLogger.error(package + " : FAIL")
762
+
763
+        if constants.rpmCheck:
764
+            if not returnVal and constants.rpmCheckStopOnError:
765
+                self.logger.error("Checking rpm is failed " + specFile)
766
+                raise Exception("RPM check failed")
767
+        else:
768
+            if not returnVal:
769
+                self.logger.error("Building rpm is failed " + specFile)
770
+                raise Exception("RPM build failed")
771
+
772
+        #Extracting rpms created from log file
773
+        listRPMFiles = []
774
+        listSRPMFiles = []
775
+        with open(logFile, 'r') as logfile:
776
+            fileContents = logfile.readlines()
777
+            for i in range(0, len(fileContents)):
778
+                if re.search("^Wrote:", fileContents[i]):
779
+                    listcontents = fileContents[i].split()
780
+                    if ((len(listcontents) == 2) and
781
+                            listcontents[1].strip().endswith(".rpm") and
782
+                            "/RPMS/" in listcontents[1]):
783
+                        listRPMFiles.append(listcontents[1])
784
+                    if ((len(listcontents) == 2) and
785
+                            listcontents[1].strip().endswith(".src.rpm") and
786
+                            "/SRPMS/" in listcontents[1]):
787
+                        listSRPMFiles.append(listcontents[1])
788
+        return listRPMFiles, listSRPMFiles
789
+
790
+
791
+    def _copySourcesToContainer(self, listSourceFiles, package, containerID, destDir):
792
+        cmdUtils = CommandUtils()
793
+        for source in listSourceFiles:
794
+            sourcePath = self._verifyShaAndGetSourcePath(source, package)
795
+            self.logger.info("Copying source file: " + sourcePath[0])
796
+            copyCmd = "docker cp " + sourcePath[0] + " " + containerID.short_id + ":" + destDir
797
+            cmdUtils.runCommandInShell(copyCmd)
798
+
799
+    def _copyAdditionalBuildFilesToContainer(self, listAdditionalFiles, containerID):
800
+        cmdUtils = CommandUtils()
801
+        #self.logger.debug("VDBG-PU-copyAdditionalBuildFilesToContainer id: " +
802
+        #                  containerID.short_id)
803
+        #self.logger.debug(listAdditionalFiles)
804
+        for additionalFile in listAdditionalFiles:
805
+            source = additionalFile["src"]
806
+            destDir = additionalFile["dst"]
807
+            destPath = containerID.short_id + ":" + destDir
808
+            #TODO: exit status of exec_run
809
+            containerID.exec_run("mkdir -p " + destDir)
810
+            if os.path.exists(source):
811
+                copyCmd = "docker cp " + source
812
+                if os.path.isfile(source):
813
+                    self.logger.info("Copying additional source file: " + source)
814
+                    copyCmd += " " + destPath
815
+                else:
816
+                    self.logger.info("Copying additional source file tree: " + source)
817
+                    copyCmd += "/. " + destPath
818
+                #TODO: cmd error code
819
+                cmdUtils.runCommandInShell(copyCmd)
820
+
821
+    def _getRPMPathInContainer(self, rpmFile, containerID):
822
+        rpmName = os.path.basename(rpmFile)
823
+        #TODO: Container path from constants
824
+        if "PUBLISHRPMS" in rpmFile:
825
+            rpmPath = "/publishrpms/"
826
+        elif "PUBLISHXRPMS" in rpmFile:
827
+            rpmPath = "/publishxrpms/"
828
+        else:
829
+            rpmPath = constants.topDirPath + "/RPMS/"
830
+        if "noarch" in rpmFile:
831
+            rpmPath += "noarch/"
832
+        else:
833
+            rpmPath += platform.machine()+"/"
834
+        rpmPath += rpmName
835
+        return rpmPath
836
+
837
+
838
+    def _buildRPMinContainer(self, specFile, rpmLogFile, destLogFile, containerID, package, macros):
635 839
 
636 840
         rpmBuildCmd = self.rpmbuildBinary + " " + self.rpmbuildBuildallOption
637 841
 
... ...
@@ -688,20 +675,19 @@ class PackageUtils(object):
688 688
         #Extracting rpms created from log file
689 689
         listRPMFiles = []
690 690
         listSRPMFiles = []
691
-        logfile = open(destLogFile, 'r')
692
-        rpmBuildLogLines = logfile.readlines()
693
-        logfile.close()
694
-        for i in range(0, len(rpmBuildLogLines)):
695
-            if re.search("^Wrote:", rpmBuildLogLines[i]):
696
-                listcontents = rpmBuildLogLines[i].split()
697
-                if ((len(listcontents) == 2) and
698
-                        listcontents[1].strip().endswith(".rpm") and
699
-                        "/RPMS/" in listcontents[1]):
700
-                    listRPMFiles.append(listcontents[1])
701
-                if ((len(listcontents) == 2) and
702
-                        listcontents[1].strip().endswith(".src.rpm") and
703
-                        "/SRPMS/" in listcontents[1]):
704
-                    listSRPMFiles.append(listcontents[1])
691
+        with open(destLogFile, 'r') as logfile:
692
+            rpmBuildLogLines = logfile.readlines()
693
+            for i in range(0, len(rpmBuildLogLines)):
694
+                if re.search("^Wrote:", rpmBuildLogLines[i]):
695
+                    listcontents = rpmBuildLogLines[i].split()
696
+                    if ((len(listcontents) == 2) and
697
+                            listcontents[1].strip().endswith(".rpm") and
698
+                            "/RPMS/" in listcontents[1]):
699
+                        listRPMFiles.append(listcontents[1])
700
+                    if ((len(listcontents) == 2) and
701
+                            listcontents[1].strip().endswith(".src.rpm") and
702
+                            "/SRPMS/" in listcontents[1]):
703
+                        listSRPMFiles.append(listcontents[1])
705 704
         #if not listRPMFiles:
706 705
         #    self.logger.error("Building rpm failed for " + specFile)
707 706
         #    raise Exception("RPM Build failed")
... ...
@@ -1,7 +1,7 @@
1 1
 import threading
2 2
 from queue import PriorityQueue
3 3
 import json
4
-import ThreadPool
4
+from ThreadPool import ThreadPool
5 5
 from constants import constants
6 6
 from Logger import Logger
7 7
 from SpecData import SPECS
... ...
@@ -9,9 +9,9 @@ from SpecData import SPECS
9 9
 class Scheduler(object):
10 10
 
11 11
     lock = threading.Lock()
12
-    listOfAlreadyBuiltPackages = []
12
+    listOfAlreadyBuiltPackages = set()
13 13
     listOfPackagesToBuild = []
14
-    listOfPackagesCurrentlyBuilding = []
14
+    listOfPackagesCurrentlyBuilding = set()
15 15
     sortedList = []
16 16
     listOfPackagesNextToBuild = PriorityQueue()
17 17
     listOfFailedPackages = []
... ...
@@ -19,7 +19,6 @@ class Scheduler(object):
19 19
     dependencyGraph = {}
20 20
     priorityMap = {}
21 21
     pkgWeights = {}
22
-    isPriorityScheduler = 1
23 22
     logger = None
24 23
     event = None
25 24
     stopScheduling = False
... ...
@@ -33,7 +32,73 @@ class Scheduler(object):
33 33
         Scheduler.logger = Logger.getLogger(logName, logPath)
34 34
 
35 35
     @staticmethod
36
-    def getBuildRequiredPackages(package):
36
+    def setParams(sortedList, listOfAlreadyBuiltPackages):
37
+        Scheduler.sortedList = sortedList
38
+        Scheduler.listOfAlreadyBuiltPackages = listOfAlreadyBuiltPackages
39
+        for x in Scheduler.sortedList:
40
+            if x not in Scheduler.listOfAlreadyBuiltPackages or x in constants.testForceRPMS:
41
+                Scheduler.listOfPackagesToBuild.append(x)
42
+        Scheduler.listOfPackagesCurrentlyBuilding = set()
43
+        Scheduler.listOfPackagesNextToBuild = PriorityQueue()
44
+        Scheduler.listOfFailedPackages = []
45
+        Scheduler._setPriorities()
46
+
47
+    @staticmethod
48
+    def notifyPackageBuildCompleted(package):
49
+        with Scheduler.lock:
50
+            if package in Scheduler.listOfPackagesCurrentlyBuilding:
51
+                Scheduler.listOfPackagesCurrentlyBuilding.remove(package)
52
+                Scheduler.listOfAlreadyBuiltPackages.add(package)
53
+
54
+    @staticmethod
55
+    def notifyPackageBuildFailed(package):
56
+        with Scheduler.lock:
57
+            if package in Scheduler.listOfPackagesCurrentlyBuilding:
58
+                Scheduler.listOfPackagesCurrentlyBuilding.remove(package)
59
+                Scheduler.listOfFailedPackages.append(package)
60
+
61
+    @staticmethod
62
+    def isAllPackagesBuilt():
63
+        if Scheduler.listOfPackagesToBuild:
64
+            return False
65
+        return True
66
+
67
+    @staticmethod
68
+    def isAnyPackagesFailedToBuild():
69
+        if Scheduler.listOfFailedPackages:
70
+            return True
71
+        return False
72
+
73
+    @staticmethod
74
+    def getNextPackageToBuild():
75
+        Scheduler.logger.info("Waiting to acquire scheduler lock")
76
+        with Scheduler.lock:
77
+            if Scheduler.stopScheduling:
78
+                return None
79
+
80
+            if not Scheduler.listOfPackagesToBuild:
81
+                if Scheduler.event is not None:
82
+                    Scheduler.event.set()
83
+
84
+            if Scheduler.listOfPackagesNextToBuild.empty():
85
+                Scheduler._getListNextPackagesReadyToBuild()
86
+
87
+            if Scheduler.listOfPackagesNextToBuild.empty():
88
+                return None
89
+
90
+            packageTup = Scheduler.listOfPackagesNextToBuild.get()
91
+
92
+            package = packageTup[1]
93
+            Scheduler.logger.info("PackagesNextToBuild " + str(packageTup))
94
+            if Scheduler.listOfPackagesNextToBuild.qsize() > 0:
95
+                ThreadPool.activateWorkerThreads(
96
+                    Scheduler.listOfPackagesNextToBuild.qsize())
97
+            Scheduler.listOfPackagesCurrentlyBuilding.add(package)
98
+            Scheduler.listOfPackagesToBuild.remove(package)
99
+            return package
100
+
101
+    @staticmethod
102
+    def _getBuildRequiredPackages(package):
37 103
         listRequiredRPMPackages = []
38 104
         listRequiredRPMPackages.extend(SPECS.getData().getBuildRequiresForPackage(package))
39 105
 
... ...
@@ -48,10 +113,10 @@ class Scheduler(object):
48 48
 
49 49
 
50 50
     @staticmethod
51
-    def getDependencies(package, parentPackage, k):
51
+    def _getDependencies(package, parentPackage, k):
52 52
 
53 53
         for node in list(Scheduler.alldependencyGraph[package].keys()):
54
-            Scheduler.getDependencies(node, package, k)
54
+            Scheduler._getDependencies(node, package, k)
55 55
 
56 56
         if parentPackage is None:
57 57
             return
... ...
@@ -62,90 +127,77 @@ class Scheduler(object):
62 62
                         Scheduler.alldependencyGraph[parentPackage][node],
63 63
                         Scheduler.alldependencyGraph[package][node] * k)
64 64
                 except KeyError:
65
-                    Scheduler.alldependencyGraph[parentPackage][node] = \
66
-                        Scheduler.alldependencyGraph[package][node] * k
65
+                    Scheduler.alldependencyGraph[parentPackage][node] = (
66
+                        Scheduler.alldependencyGraph[package][node] * k)
67 67
 
68 68
     @staticmethod
69
-    def makeGraph():
70
-        k = 3
69
+    def _makeGraph():
70
+        k = 2
71 71
         for package in Scheduler.sortedList:
72 72
             for child_pkg in list(Scheduler.dependencyGraph[package].keys()):
73
-                Scheduler.getDependencies(child_pkg, package, k)
73
+                Scheduler._getDependencies(child_pkg, package, k)
74 74
                 for node in list(Scheduler.alldependencyGraph[child_pkg].keys()):
75 75
                     try:
76 76
                         Scheduler.dependencyGraph[package][node] = max(
77 77
                             Scheduler.dependencyGraph[package][node],
78 78
                             Scheduler.alldependencyGraph[child_pkg][node] * k)
79 79
                     except KeyError:
80
-                        Scheduler.dependencyGraph[package][node] = \
81
-                            Scheduler.alldependencyGraph[child_pkg][node] * k
80
+                        Scheduler.dependencyGraph[package][node] = (
81
+                            Scheduler.alldependencyGraph[child_pkg][node] * k)
82 82
         if constants.publishBuildDependencies:
83 83
             dependencyLists = {}
84 84
             for package in list(Scheduler.dependencyGraph.keys()):
85 85
                 dependencyLists[package] = []
86 86
                 for dependency in list(Scheduler.dependencyGraph[package].keys()):
87 87
                     dependencyLists[package].append(dependency)
88
-            graphfile = open(str(constants.logPath) + "/BuildDependencies.json", 'w')
89
-            graphfile.write(json.dumps(dependencyLists, sort_keys=True, indent=4))
90
-            graphfile.close()
88
+            with open(str(constants.logPath) + "/BuildDependencies.json", 'w') as graphfile:
89
+                graphfile.write(json.dumps(dependencyLists, sort_keys=True, indent=4))
91 90
 
92 91
     @staticmethod
93
-    def parseWeights():
92
+    def _parseWeights():
94 93
         Scheduler.pkgWeights.clear()
95
-        weightFile = open(constants.packageWeightsPath, 'r')
96
-        Scheduler.pkgWeights = json.load(weightFile)
97
-        weightFile.close()
94
+        with open(constants.packageWeightsPath, 'r') as weightFile:
95
+            Scheduler.pkgWeights = json.load(weightFile)
98 96
 
99 97
     @staticmethod
100
-    def getWeight(package):
98
+    def _getWeight(package):
101 99
         try:
102 100
             return float(Scheduler.pkgWeights[package])
103 101
         except KeyError:
104 102
             return 0
105 103
 
106 104
     @staticmethod
107
-    def setPriorities():
105
+    def _setPriorities():
108 106
         if constants.packageWeightsPath is None:
109 107
             Scheduler.logger.info("Priority Scheduler disabled")
110
-            Scheduler.isPriorityScheduler = 0
111 108
         else:
112
-            Scheduler.parseWeights()
113
-
114
-        for package in Scheduler.sortedList:
115
-            Scheduler.dependencyGraph[package] = {}
116
-            Scheduler.alldependencyGraph[package] = {}
117
-            for child_package in Scheduler.getBuildRequiredPackages(package):
118
-                Scheduler.dependencyGraph[package][child_package] = 1
119
-            for child_package in Scheduler.getRequiredPackages(package):
120
-                Scheduler.alldependencyGraph[package][child_package] = 1
121
-        Scheduler.makeGraph()
122
-        for package in Scheduler.sortedList:
123
-            try:
124
-                Scheduler.priorityMap[package] = Scheduler.getWeight(package)
125
-            except KeyError:
126
-                Scheduler.priorityMap[package] = 0
127
-            for child_pkg in Scheduler.dependencyGraph[package].keys():
128
-                Scheduler.priorityMap[child_pkg] = Scheduler.priorityMap[child_pkg] \
129
-                                                 + (Scheduler.dependencyGraph[package][child_pkg]
130
-                                                    * (Scheduler.getWeight(package)))
131
-        Scheduler.logger.info("set Priorities: Priority of all packages")
132
-        Scheduler.logger.info(Scheduler.priorityMap)
109
+            Scheduler.logger.info("Priority Scheduler enabled")
110
+            Scheduler._parseWeights()
111
+
112
+            for package in Scheduler.sortedList:
113
+                Scheduler.dependencyGraph[package] = {}
114
+                Scheduler.alldependencyGraph[package] = {}
115
+                for child_package in Scheduler._getBuildRequiredPackages(package):
116
+                    Scheduler.dependencyGraph[package][child_package] = 1
117
+                for child_package in Scheduler._getRequiredPackages(package):
118
+                    Scheduler.alldependencyGraph[package][child_package] = 1
119
+            Scheduler._makeGraph()
120
+            for package in Scheduler.sortedList:
121
+                try:
122
+                    Scheduler.priorityMap[package] = Scheduler._getWeight(package)
123
+                except KeyError:
124
+                    Scheduler.priorityMap[package] = 0
125
+                for child_pkg in Scheduler.dependencyGraph[package].keys():
126
+                    Scheduler.priorityMap[child_pkg] = (
127
+                        Scheduler.priorityMap[child_pkg]
128
+                        + (Scheduler.dependencyGraph[package][child_pkg]
129
+                        * (Scheduler._getWeight(package))))
130
+            Scheduler.logger.info("set Priorities: Priority of all packages")
131
+            Scheduler.logger.info(Scheduler.priorityMap)
133 132
 
134 133
 
135 134
     @staticmethod
136
-    def setParams(sortedList, listOfAlreadyBuiltPackages):
137
-        Scheduler.sortedList = sortedList
138
-        Scheduler.listOfAlreadyBuiltPackages = listOfAlreadyBuiltPackages
139
-        for x in Scheduler.sortedList:
140
-            if x not in Scheduler.listOfAlreadyBuiltPackages or x in constants.testForceRPMS:
141
-                Scheduler.listOfPackagesToBuild.append(x)
142
-        Scheduler.listOfPackagesCurrentlyBuilding = []
143
-        Scheduler.listOfPackagesNextToBuild = []
144
-        Scheduler.listOfFailedPackages = []
145
-        Scheduler.setPriorities()
146
-
147
-    @staticmethod
148
-    def getRequiredPackages(package):
135
+    def _getRequiredPackages(package):
149 136
         listRequiredRPMPackages = []
150 137
         listRequiredRPMPackages.extend(SPECS.getData().getBuildRequiresForPackage(package))
151 138
         listRequiredRPMPackages.extend(SPECS.getData().getRequiresAllForPackage(package))
... ...
@@ -160,92 +212,17 @@ class Scheduler(object):
160 160
         return listRequiredPackages
161 161
 
162 162
     @staticmethod
163
-    def __getListNextPackagesReadyToBuild():
164
-        listOfPackagesNextToBuild = PriorityQueue()
163
+    def _getListNextPackagesReadyToBuild():
165 164
         Scheduler.logger.info("Checking for next possible packages to build")
166 165
         for pkg in Scheduler.listOfPackagesToBuild:
167 166
             if pkg in Scheduler.listOfPackagesCurrentlyBuilding:
168 167
                 continue
169
-            listRequiredPackages = Scheduler.getRequiredPackages(pkg)
168
+            listRequiredPackages = Scheduler._getRequiredPackages(pkg)
170 169
             canBuild = True
171
-            Scheduler.logger.info("Required packages for " + pkg + " are:")
172
-            Scheduler.logger.info(listRequiredPackages)
173 170
             for reqPkg in listRequiredPackages:
174 171
                 if reqPkg not in Scheduler.listOfAlreadyBuiltPackages:
175 172
                     canBuild = False
176
-                    Scheduler.logger.info(reqPkg + " is not available. So we cannot build " +
177
-                                          pkg + " at this moment.")
178 173
                     break
179 174
             if canBuild:
180
-                listOfPackagesNextToBuild.put((-Scheduler.priorityMap[pkg], pkg))
175
+                Scheduler.listOfPackagesNextToBuild.put((-Scheduler._getWeight(pkg), pkg))
181 176
                 Scheduler.logger.info("Adding " + pkg + " to the schedule list")
182
-        return listOfPackagesNextToBuild
183
-
184
-    @staticmethod
185
-    def getNextPackageToBuild():
186
-        Scheduler.logger.info("Waiting to acquire scheduler lock")
187
-        with Scheduler.lock:
188
-
189
-            if Scheduler.stopScheduling:
190
-                Scheduler.logger.info("Released scheduler lock")
191
-                return None
192
-
193
-            if len(Scheduler.listOfPackagesToBuild) == 0:
194
-                if Scheduler.event is not None:
195
-                    Scheduler.event.set()
196
-
197
-            try:
198
-                if Scheduler.listOfPackagesNextToBuild.qsize() == 0:
199
-                    listOfPackagesNextToBuild = Scheduler.__getListNextPackagesReadyToBuild()
200
-                    Scheduler.listOfPackagesNextToBuild = listOfPackagesNextToBuild
201
-            except:
202
-                if len(Scheduler.listOfPackagesNextToBuild) == 0:
203
-                    listOfPackagesNextToBuild = Scheduler.__getListNextPackagesReadyToBuild()
204
-                    Scheduler.listOfPackagesNextToBuild = listOfPackagesNextToBuild
205
-
206
-            if Scheduler.listOfPackagesNextToBuild.qsize() == 0:
207
-                return None
208
-
209
-            packageTup = Scheduler.listOfPackagesNextToBuild.get()
210
-
211
-            if packageTup[0] == 0 and Scheduler.isPriorityScheduler == 1:
212
-                listOfPackagesNextToBuild = Scheduler.__getListNextPackagesReadyToBuild()
213
-                Scheduler.listOfPackagesNextToBuild = listOfPackagesNextToBuild
214
-                if Scheduler.listOfPackagesNextToBuild.qsize() == 0:
215
-                    return None
216
-                packageTup = Scheduler.listOfPackagesNextToBuild.get()
217
-
218
-            package = packageTup[1]
219
-            Scheduler.logger.info("PackagesNextToBuild " + str(packageTup))
220
-            if Scheduler.listOfPackagesNextToBuild.qsize() > 0:
221
-                ThreadPool.ThreadPool.activateWorkerThreads(
222
-                    Scheduler.listOfPackagesNextToBuild.qsize())
223
-            Scheduler.listOfPackagesCurrentlyBuilding.append(package)
224
-            Scheduler.listOfPackagesToBuild.remove(package)
225
-            return package
226
-
227
-    #can be synchronized TODO
228
-    @staticmethod
229
-    def notifyPackageBuildCompleted(package):
230
-        if package in Scheduler.listOfPackagesCurrentlyBuilding:
231
-            Scheduler.listOfPackagesCurrentlyBuilding.remove(package)
232
-            Scheduler.listOfAlreadyBuiltPackages.append(package)
233
-
234
-    #can be synchronized TODO
235
-    @staticmethod
236
-    def notifyPackageBuildFailed(package):
237
-        if package in Scheduler.listOfPackagesCurrentlyBuilding:
238
-            Scheduler.listOfPackagesCurrentlyBuilding.remove(package)
239
-            Scheduler.listOfFailedPackages.append(package)
240
-
241
-    @staticmethod
242
-    def isAllPackagesBuilt():
243
-        if len(Scheduler.listOfPackagesToBuild) == 0:
244
-            return True
245
-        return False
246
-
247
-    @staticmethod
248
-    def isAnyPackagesFailedToBuild():
249
-        if len(Scheduler.listOfFailedPackages) != 0:
250
-            return True
251
-        return False
... ...
@@ -319,11 +319,10 @@ class SpecDependencyGenerator(object):
319 319
                 self.printTree(children, child, depth + 1)
320 320
 
321 321
     def getAllPackageNames(self, jsonFilePath):
322
-        jsonData = open(jsonFilePath)
323
-        option_list_json = json.load(jsonData)
324
-        jsonData.close()
325
-        packages = option_list_json["packages"]
326
-        return packages
322
+        with open(jsonFilePath) as jsonData:
323
+            option_list_json = json.load(jsonData)
324
+            packages = option_list_json["packages"]
325
+            return packages
327 326
 
328 327
     def updateLevels(self, mapDependencies, inPkg, parent, level):
329 328
         listPackages = SPECS.getData().getPackages(inPkg)
... ...
@@ -1,7 +1,8 @@
1
+# pylint: disable=invalid-name,missing-docstring
1 2
 import re
2 3
 import platform
3 4
 from StringUtils import StringUtils
4
-from SpecStructures import *
5
+from SpecStructures import rpmMacro, dependentPackageData, Package
5 6
 from constants import constants
6 7
 
7 8
 class SpecParser(object):
... ...
@@ -20,8 +21,77 @@ class SpecParser(object):
20 20
         self.conditionalCheckMacroEnabled = False
21 21
         self.macro_pattern = re.compile(r'%{(\S+?)\}')
22 22
 
23
+    def parseSpecFile(self, specfile):
24
+        self._createDefaultPackage()
25
+        currentPkg = "default"
26
+        with open(specfile) as specFile:
27
+            lines = specFile.readlines()
28
+            totalLines = len(lines)
29
+            i = 0
30
+            while i < totalLines:
31
+                line = lines[i].strip()
32
+                if self._isConditionalArch(line):
33
+                    if platform.machine() != self._readConditionalArch(line):
34
+                        # skip conditional body
35
+                        deep = 1
36
+                        while i < totalLines and deep != 0:
37
+                            i = i + 1
38
+                            line = lines[i].strip()
39
+                            if self._isConditionalMacroStart(line):
40
+                                deep = deep + 1
41
+                            elif self._isConditionalMacroEnd(line):
42
+                                deep = deep - 1
43
+                elif self._isIfCondition(line):
44
+                    if not self._isConditionTrue(line):
45
+                        # skip conditional body
46
+                        deep = 1
47
+                        while i < totalLines and deep != 0:
48
+                            i = i + 1
49
+                            line = lines[i].strip()
50
+                            if self._isConditionalMacroStart(line):
51
+                                deep = deep + 1
52
+                            elif self._isConditionalMacroEnd(line):
53
+                                deep = deep - 1
54
+                elif self._isSpecMacro(line):
55
+                    macro, i = self._readMacroFromFile(i, lines)
56
+                    self._updateSpecMacro(macro)
57
+                elif self._isPackageMacro(line):
58
+                    defaultpkg = self.packages.get('default')
59
+                    returnVal, packageName = self._readPkgNameFromPackageMacro(line,
60
+                                                                               defaultpkg.name)
61
+                    packageName = self._replaceMacros(packageName)
62
+                    if not returnVal:
63
+                        return False
64
+                    if line.startswith('%package'):
65
+                        pkg = Package(defaultpkg)
66
+                        pkg.name = packageName
67
+                        currentPkg = packageName
68
+                        self.packages[pkg.name] = pkg
69
+                    else:
70
+                        if defaultpkg.name == packageName:
71
+                            packageName = 'default'
72
+                        macro, i = self._readMacroFromFile(i, lines)
73
+                        if packageName not in self.packages:
74
+                            i = i + 1
75
+                            continue
76
+                        self.packages[packageName].updatePackageMacro(macro)
77
+                elif self._isPackageHeaders(line):
78
+                    self._readPackageHeaders(line, self.packages[currentPkg])
79
+                elif self._isGlobalSecurityHardening(line):
80
+                    self._readSecurityHardening(line)
81
+                elif self._isChecksum(line):
82
+                    self._readChecksum(line, self.packages[currentPkg])
83
+                elif self._isDefinition(line):
84
+                    self._readDefinition(line)
85
+                elif self._isConditionalCheckMacro(line):
86
+                    self.conditionalCheckMacroEnabled = True
87
+                elif self.conditionalCheckMacroEnabled and self._isConditionalMacroEnd(line):
88
+                    self.conditionalCheckMacroEnabled = False
89
+                else:
90
+                    self.specAdditionalContent += line + "\n"
91
+                i = i + 1
23 92
 
24
-    def readPkgNameFromPackageMacro(self, data, basePkgName=None):
93
+    def _readPkgNameFromPackageMacro(self, data, basePkgName=None):
25 94
         data = " ".join(data.split())
26 95
         pkgHeaderName = data.split(" ")
27 96
         lenpkgHeaderName = len(pkgHeaderName)
... ...
@@ -40,7 +110,7 @@ class SpecParser(object):
40 40
             return True, basePkgName
41 41
         return True, pkgName
42 42
 
43
-    def replaceMacros(self, string):
43
+    def _replaceMacros(self, string):
44 44
         """Replace all macros in given string with corresponding values.
45 45
 
46 46
         For example: a string '%{name}-%{version}.tar.gz' will be transformed to 'foo-2.0.tar.gz'.
... ...
@@ -72,114 +142,40 @@ class SpecParser(object):
72 72
             macro_name = match.group(1)
73 73
             if _is_conditional(macro_name):
74 74
                 parts = macro_name[1:].split(":")
75
-                assert len(parts) > 0
75
+                assert parts
76
+                retv = ""
76 77
                 if _test_conditional(macro_name):  # ?
77 78
                     if _is_macro_defined(parts[0]):
78 79
                         if len(parts) == 2:
79
-                            return parts[1]
80
+                            retv = parts[1]
80 81
                         else:
81
-                            return _get_macro(parts[0])
82
-                    else:
83
-                        return ""
82
+                            retv = _get_macro(parts[0])
84 83
                 else:  # !
85 84
                     if not _is_macro_defined(parts[0]):
86 85
                         if len(parts) == 2:
87
-                            return parts[1]
88
-                    return ""
86
+                            retv = parts[1]
87
+                return retv
89 88
 
90 89
             if _is_macro_defined(macro_name):
91 90
                 return _get_macro(macro_name)
92 91
             return match.string[match.start():match.end()]
93 92
 
94 93
         #User macros
95
-        for macroName in constants.userDefinedMacros.keys():
96
-            value = constants.userDefinedMacros[macroName]
94
+        for macroName, value in constants.userDefinedMacros.items():
97 95
             macro = "%" + macroName
98 96
             if string.find(macro) != -1:
99 97
                 string = string.replace(macro, value)
100 98
         #Spec definitions
101
-        for macroName in self.defs.keys():
102
-            value = self.defs[macroName]
99
+        for macroName, value in self.defs.items():
103 100
             macro = "%" + macroName
104 101
             if string.find(macro) != -1:
105 102
                 string = string.replace(macro, value)
106 103
         return re.sub(self.macro_pattern, _macro_repl, string)
107 104
 
108
-    def parseSpecFile(self, specfile):
109
-        self.createDefaultPackage()
110
-        currentPkg = "default"
111
-        specFile = open(specfile)
112
-        lines = specFile.readlines()
113
-        totalLines = len(lines)
114
-        i = 0
115
-        while i < totalLines:
116
-            line = lines[i].strip()
117
-            if self.isConditionalArch(line):
118
-                if platform.machine() != self.readConditionalArch(line):
119
-                    # skip conditional body
120
-                    deep = 1
121
-                    while i < totalLines and deep != 0:
122
-                        i = i + 1
123
-                        line = lines[i].strip()
124
-                        if self.isConditionalMacroStart(line):
125
-                            deep = deep + 1
126
-                        elif self.isConditionalMacroEnd(line):
127
-                            deep = deep - 1
128
-            elif self.isIfCondition(line):
129
-                if not self.isConditionTrue(line):
130
-                    # skip conditional body
131
-                    deep = 1
132
-                    while i < totalLines and deep != 0:
133
-                        i = i + 1
134
-                        line = lines[i].strip()
135
-                        if self.isConditionalMacroStart(line):
136
-                            deep = deep + 1
137
-                        elif self.isConditionalMacroEnd(line):
138
-                            deep = deep - 1
139
-            elif self.isSpecMacro(line):
140
-                macro, i = self.readMacroFromFile(i, lines)
141
-                self.updateMacro(macro)
142
-            elif self.isPackageMacro(line):
143
-                defaultpkg = self.packages.get('default')
144
-                returnVal, packageName = self.readPkgNameFromPackageMacro(line, defaultpkg.name)
145
-                packageName = self.replaceMacros(packageName)
146
-                if not returnVal:
147
-                    return False
148
-                if line.startswith('%package'):
149
-                    pkg = Package(defaultpkg)
150
-                    pkg.name = packageName
151
-                    currentPkg = packageName
152
-                    self.packages[pkg.name] = pkg
153
-                else:
154
-                    if defaultpkg.name == packageName:
155
-                        packageName = 'default'
156
-                    macro, i = self.readMacroFromFile(i, lines)
157
-                    if packageName not in self.packages:
158
-                        i = i + 1
159
-                        continue
160
-                    self.packages[packageName].updatePackageMacro(macro)
161
-            elif self.isPackageHeaders(line):
162
-                self.readPackageHeaders(line, self.packages[currentPkg])
163
-            elif self.isGlobalSecurityHardening(line):
164
-                self.readSecurityHardening(line)
165
-            elif self.isChecksum(line):
166
-                self.readChecksum(line, self.packages[currentPkg])
167
-            elif self.isDefinition(line):
168
-                self.readDefinition(line)
169
-            elif self.isConditionalCheckMacro(line):
170
-                self.conditionalCheckMacroEnabled = True
171
-            elif self.conditionalCheckMacroEnabled and self.isConditionalMacroEnd(line):
172
-                self.conditionalCheckMacroEnabled = False
173
-            else:
174
-                self.specAdditionalContent += line + "\n"
175
-            i = i + 1
176
-        specFile.close()
177
-
178
-    def createDefaultPackage(self):
179
-        pkg = Package()
180
-        self.packages["default"] = pkg
105
+    def _createDefaultPackage(self):
106
+        self.packages["default"] = Package()
181 107
 
182
-    def readMacroFromFile(self, currentPos, lines):
108
+    def _readMacroFromFile(self, currentPos, lines):
183 109
         macro = rpmMacro()
184 110
         line = lines[currentPos]
185 111
         macro.position = currentPos
... ...
@@ -193,18 +189,18 @@ class SpecParser(object):
193 193
         else:
194 194
             macro.macroName = line
195 195
 
196
-        if currentPos + 1 < len(lines) and self.isMacro(lines[currentPos+1]):
196
+        if currentPos + 1 < len(lines) and self._isMacro(lines[currentPos+1]):
197 197
             return macro, currentPos
198 198
 
199 199
         for j in range(currentPos + 1, endPos):
200 200
             content = lines[j]
201
-            if j+1 < endPos and self.isMacro(lines[j+1]):
201
+            if j+1 < endPos and self._isMacro(lines[j+1]):
202 202
                 return macro, j
203 203
             macro.content += content +'\n'
204 204
             macro.endposition = j
205 205
         return macro, endPos
206 206
 
207
-    def updateMacro(self, macro):
207
+    def _updateSpecMacro(self, macro):
208 208
         if macro.macroName == "%clean":
209 209
             self.cleanMacro = macro
210 210
             return True
... ...
@@ -224,34 +220,33 @@ class SpecParser(object):
224 224
             self.checkMacro = macro
225 225
             return True
226 226
         return False
227
+    def _isMacro(self, line):
228
+        return (self._isPackageMacro(line) or
229
+                self._isSpecMacro(line) or
230
+                self._isConditionalMacroStart(line) or
231
+                self._isConditionalMacroEnd(line))
227 232
 
228
-    def isMacro(self, line):
229
-        return (self.isPackageMacro(line) or
230
-                self.isSpecMacro(line) or
231
-                self.isConditionalMacroStart(line) or
232
-                self.isConditionalMacroEnd(line))
233
-
234
-    def isConditionalArch(self, line):
233
+    def _isConditionalArch(self, line):
235 234
         if re.search('^'+'%ifarch', line):
236 235
             return True
237 236
         return False
238 237
 
239
-    def isSpecMacro(self, line):
238
+    def _isSpecMacro(self, line):
240 239
         if line.startswith(('%clean', '%prep', '%build', '%install', '%changelog', '%check')):
241 240
             return True
242 241
         return False
243 242
 
244
-    def isPackageMacro(self, line):
243
+    def _isPackageMacro(self, line):
245 244
         line = line.strip()
246 245
         if line.startswith(('%post', '%postun', '%files', '%description', '%package')):
247 246
             return True
248 247
         return False
249 248
 
250
-    def isPackageHeaders(self, line):
249
+    def _isPackageHeaders(self, line):
251 250
         headersPatterns = ['^summary:', '^name:', '^group:',
252 251
                            '^license:', '^version:', '^release:',
253 252
                            '^distribution:', '^requires:',
254
-                           '^requires\((pre|post|preun|postun)\):',
253
+                           r'^requires\((pre|post|preun|postun)\):',
255 254
                            '^provides:', '^obsoletes:', '^conflicts:',
256 255
                            '^url:', '^source[0-9]*:', '^patch[0-9]*:',
257 256
                            '^buildrequires:', '^buildprovides:',
... ...
@@ -260,35 +255,35 @@ class SpecParser(object):
260 260
             return True
261 261
         return False
262 262
 
263
-    def isGlobalSecurityHardening(self, line):
263
+    def _isGlobalSecurityHardening(self, line):
264 264
         if re.search('^%global *security_hardening', line, flags=re.IGNORECASE):
265 265
             return True
266 266
         return False
267 267
 
268
-    def isChecksum(self, line):
268
+    def _isChecksum(self, line):
269 269
         if re.search('^%define *sha1', line, flags=re.IGNORECASE):
270 270
             return True
271 271
         return False
272 272
 
273
-    def isDefinition(self, line):
273
+    def _isDefinition(self, line):
274 274
         if line.startswith(('%define', '%global')):
275 275
             return True
276 276
         return False
277 277
 
278
-    def readConditionalArch(self, line):
278
+    def _readConditionalArch(self, line):
279 279
         w = line.split()
280 280
         if len(w) == 2:
281 281
             return w[1]
282 282
         return None
283 283
 
284
-    def readDefinition(self, line):
284
+    def _readDefinition(self, line):
285 285
         listDefines = line.split()
286 286
         if len(listDefines) == 3:
287
-            self.defs[listDefines[1]] = self.replaceMacros(listDefines[2])
287
+            self.defs[listDefines[1]] = self._replaceMacros(listDefines[2])
288 288
             return True
289 289
         return False
290 290
 
291
-    def readHeader(self, line):
291
+    def _readHeader(self, line):
292 292
         headerSplitIndex = line.find(":")
293 293
         if headerSplitIndex + 1 == len(line):
294 294
             print(line)
... ...
@@ -298,7 +293,7 @@ class SpecParser(object):
298 298
         headerContent = line[headerSplitIndex + 1:].strip()
299 299
         return True, headerName, headerContent
300 300
 
301
-    def readDependentPackageData(self, line):
301
+    def _readDependentPackageData(self, line):
302 302
         strUtils = StringUtils()
303 303
         listPackages = line.split(",")
304 304
         listdependentpkgs = []
... ...
@@ -318,7 +313,7 @@ class SpecParser(object):
318 318
                         packageName = provider
319 319
                     else:
320 320
                         continue
321
-                if i+2 < len(listContents):
321
+                if i + 2 < len(listContents):
322 322
                     if listContents[i+1] == ">=":
323 323
                         compare = "gte"
324 324
                     elif listContents[i+1] == "<=":
... ...
@@ -343,12 +338,12 @@ class SpecParser(object):
343 343
                 listdependentpkgs.append(dpkg)
344 344
         return listdependentpkgs
345 345
 
346
-    def readPackageHeaders(self, line, pkg):
347
-        returnVal, headerName, headerContent = self.readHeader(line)
346
+    def _readPackageHeaders(self, line, pkg):
347
+        returnVal, headerName, headerContent = self._readHeader(line)
348 348
         if not returnVal:
349 349
             return False
350 350
 
351
-        headerContent = self.replaceMacros(headerContent)
351
+        headerContent = self._replaceMacros(headerContent)
352 352
         if headerName == 'summary':
353 353
             pkg.summary = headerContent
354 354
             return True
... ...
@@ -382,10 +377,10 @@ class SpecParser(object):
382 382
         if headerName == 'url':
383 383
             pkg.URL = headerContent
384 384
             return True
385
-        if headerName.find('source') != -1:
385
+        if 'source' in headerName:
386 386
             pkg.sources.append(headerContent)
387 387
             return True
388
-        if headerName.find('patch') != -1:
388
+        if 'patch' in headerName:
389 389
             pkg.patches.append(headerContent)
390 390
             return True
391 391
         if (headerName.startswith('requires') or
... ...
@@ -394,7 +389,7 @@ class SpecParser(object):
394 394
                 headerName == 'conflicts' or
395 395
                 headerName == 'buildrequires' or
396 396
                 headerName == 'buildprovides'):
397
-            dpkg = self.readDependentPackageData(headerContent)
397
+            dpkg = self._readDependentPackageData(headerContent)
398 398
             if dpkg is None:
399 399
                 return False
400 400
             if headerName.startswith('requires'):
... ...
@@ -416,7 +411,7 @@ class SpecParser(object):
416 416
             return True
417 417
         return False
418 418
 
419
-    def readSecurityHardening(self, line):
419
+    def _readSecurityHardening(self, line):
420 420
         data = line.lower().strip()
421 421
         words = data.split(" ")
422 422
         nrWords = len(words)
... ...
@@ -429,9 +424,9 @@ class SpecParser(object):
429 429
         self.globalSecurityHardening = words[2]
430 430
         return True
431 431
 
432
-    def readChecksum(self, line, pkg):
432
+    def _readChecksum(self, line, pkg):
433 433
         strUtils = StringUtils()
434
-        line = self.replaceMacros(line)
434
+        line = self._replaceMacros(line)
435 435
         data = line.strip()
436 436
         words = data.split()
437 437
         nrWords = len(words)
... ...
@@ -445,45 +440,45 @@ class SpecParser(object):
445 445
         matchedSources = []
446 446
         for source in pkg.sources:
447 447
             sourceName = strUtils.getFileNameFromURL(source)
448
-            if (sourceName.startswith(value[0])):
448
+            if sourceName.startswith(value[0]):
449 449
                 matchedSources.append(sourceName)
450
-        if (len(matchedSources) == 0):
450
+        if not matchedSources:
451 451
             print("Error: Can not find match for sha1 " + value[0])
452 452
             return False
453
-        if (len(matchedSources) > 1):
453
+        if len(matchedSources) > 1:
454 454
             print("Error: Too many matched Sources:" +
455 455
                   ' '.join(matchedSources) + " for sha1 " + value[0])
456 456
             return False
457 457
         pkg.checksums[sourceName] = value[1]
458
-        return True;
458
+        return True
459 459
 
460
-    def isConditionalCheckMacro(self, line):
460
+    def _isConditionalCheckMacro(self, line):
461 461
         data = line.strip()
462 462
         words = data.split()
463 463
         nrWords = len(words)
464
-        if(nrWords != 2):
464
+        if nrWords != 2:
465 465
             return False
466
-        if(words[0] != "%if" or words[1] != "%{with_check}"):
466
+        if words[0] != "%if" or words[1] != "%{with_check}":
467 467
             return False
468 468
         return True
469 469
 
470
-    def isIfCondition(self,line):
470
+    def _isIfCondition(self, line):
471 471
         return line.startswith("%if ")
472 472
 
473 473
     # Supports only %if %{}
474
-    def isConditionTrue(self,line):
474
+    def _isConditionTrue(self, line):
475 475
         data = line.strip()
476 476
         words = data.split()
477 477
         nrWords = len(words)
478 478
         # condition like %if a > b is not supported
479
-        if(nrWords != 2):
479
+        if nrWords != 2:
480 480
             return True
481
-        if (self.replaceMacros(words[1]) == "0"):
481
+        if self._replaceMacros(words[1]) == "0":
482 482
             return False
483 483
         return True
484 484
 
485
-    def isConditionalMacroStart(self, line):
485
+    def _isConditionalMacroStart(self, line):
486 486
         return line.startswith("%if")
487 487
 
488
-    def isConditionalMacroEnd(self, line):
489
-        return (line.strip() == "%endif")
488
+    def _isConditionalMacroEnd(self, line):
489
+        return line.strip() == "%endif"
... ...
@@ -1,4 +1,4 @@
1
-import platform
1
+# pylint: disable=invalid-name,missing-docstring
2 2
 import os
3 3
 from SpecParser import SpecParser
4 4
 from StringUtils import StringUtils
... ...
@@ -8,11 +8,12 @@ class Specutils(object):
8 8
     def __init__(self, specfile):
9 9
         self.specfile = ""
10 10
         self.spec = SpecParser()
11
-        if self.isSpecFile(specfile):
11
+        if Specutils._isSpecFile(specfile):
12 12
             self.specfile = specfile
13 13
             self.spec.parseSpecFile(self.specfile)
14 14
 
15
-    def isSpecFile(self, specfile):
15
+    @staticmethod
16
+    def _isSpecFile(specfile):
16 17
         if os.path.isfile(specfile) and specfile.endswith(".spec"):
17 18
             return True
18 19
         return False
... ...
@@ -32,20 +33,6 @@ class Specutils(object):
32 32
         pkg = self.spec.packages.get('default')
33 33
         return pkg.checksums
34 34
 
35
-    def getChecksumForSource(self, source):
36
-        pkg = self.spec.packages.get('default')
37
-        return pkg.checksums.get(source)
38
-
39
-    def getSourceURLs(self):
40
-        sourceNames = []
41
-        strUtils = StringUtils()
42
-        pkg = self.spec.packages.get('default')
43
-        if pkg is None:
44
-            return None
45
-        for source in pkg.sources:
46
-            sourceNames.append(source)
47
-        return sourceNames
48
-
49 35
     def getPatchNames(self):
50 36
         patchNames = []
51 37
         strUtils = StringUtils()
... ...
@@ -80,32 +67,7 @@ class Specutils(object):
80 80
             rpmNames.append(rpmName)
81 81
         return rpmNames
82 82
 
83
-    def getRPMName(self, pkgName):
84
-        rpmName = None
85
-        for pkg in self.spec.packages.values():
86
-            if pkg.name == pkgName:
87
-                rpmName = pkg.name + "-" + pkg.version + "-" + pkg.release
88
-                break
89
-        return rpmName
90
-
91
-    def getRPMVersion(self, pkgName):
92
-        version = None
93
-        for pkg in self.spec.packages.values():
94
-            if pkg.name == pkgName:
95
-                version = pkg.version
96
-                break
97
-        return version
98
-
99
-    def getRPMRelease(self, pkgName):
100
-        release = None
101
-        for pkg in self.spec.packages.values():
102
-            if pkg.name == pkgName:
103
-                release = pkg.release
104
-                break
105
-        return release
106
-
107 83
     def getLicense(self):
108
-        licenseInfo = None
109 84
         pkg = self.spec.packages.get('default')
110 85
         if pkg is None:
111 86
             return None
... ...
@@ -121,21 +83,13 @@ class Specutils(object):
121 121
         pkg = self.spec.packages.get('default')
122 122
         if pkg is None:
123 123
             return None
124
-        if len(pkg.sources) == 0:
124
+        if not pkg.sources:
125 125
             return None
126 126
         sourceURL = pkg.sources[0]
127 127
         if sourceURL.startswith("http") or sourceURL.startswith("ftp"):
128 128
             return sourceURL
129 129
         return None
130 130
 
131
-    def getBuildArch(self, pkgName):
132
-        buildArch = platform.machine()
133
-        for pkg in self.spec.packages.values():
134
-            if pkg.name == pkgName:
135
-                buildArch = pkg.buildarch
136
-                break
137
-        return buildArch
138
-
139 131
     def getRequiresAllPackages(self):
140 132
         dependentPackages = []
141 133
         for pkg in self.spec.packages.values():
... ...
@@ -176,14 +130,6 @@ class Specutils(object):
176 176
                     dependentPackages.append(dpkg.package)
177 177
         return dependentPackages
178 178
 
179
-    def getBuildRequires(self, pkgName):
180
-        dependentPackages = []
181
-        for pkg in self.spec.packages.values():
182
-            if pkg.name == pkgName:
183
-                for dpkg in pkg.buildrequires:
184
-                    dependentPackages.append(dpkg.package)
185
-        return dependentPackages
186
-
187 179
     def getProvides(self, packageName):
188 180
         dependentPackages = []
189 181
         defaultPkgName = self.spec.packages['default'].name
... ...
@@ -6,7 +6,6 @@ class ThreadPool(object):
6 6
     activeWorkerThreads = []
7 7
     inactiveWorkerThreads = []
8 8
     mapPackageToCycle = {}
9
-    listAvailableCyclicPackages = []
10 9
     pkgBuildType = "chroot"
11 10
     logger = None
12 11
     statusEvent = None
... ...
@@ -18,21 +17,11 @@ class ThreadPool(object):
18 18
         ThreadPool.inactiveWorkerThreads = []
19 19
 
20 20
     @staticmethod
21
-    def getAllWorkerObjects():
22
-        listWorkerObjs = []
23
-        listWorkerKeys = ThreadPool.mapWorkerThreads.keys()
24
-        for x in listWorkerKeys:
25
-            xobj = ThreadPool.mapWorkerThreads[x]
26
-            listWorkerObjs.append(xobj)
27
-        return listWorkerObjs
28
-
29
-    @staticmethod
30 21
     def addWorkerThread(workerThreadName):
31 22
         workerThread = WorkerThread.WorkerThread(
32 23
             ThreadPool.statusEvent,
33 24
             workerThreadName,
34 25
             ThreadPool.mapPackageToCycle,
35
-            ThreadPool.listAvailableCyclicPackages,
36 26
             ThreadPool.logger,
37 27
             ThreadPool.pkgBuildType)
38 28
         ThreadPool.mapWorkerThreads[workerThreadName] = workerThread
... ...
@@ -59,9 +48,14 @@ class ThreadPool(object):
59 59
 
60 60
     @staticmethod
61 61
     def activateWorkerThreads(numOfThreadsToActivate):
62
-        while len(ThreadPool.inactiveWorkerThreads) > 0 and numOfThreadsToActivate > 0:
62
+        while ThreadPool.inactiveWorkerThreads and numOfThreadsToActivate > 0:
63 63
             threadName = ThreadPool.inactiveWorkerThreads.pop()
64 64
             ThreadPool.addWorkerThread(threadName)
65 65
             ThreadPool.startWorkerThread(threadName)
66 66
             ThreadPool.makeWorkerThreadActive(threadName)
67 67
             numOfThreadsToActivate = numOfThreadsToActivate -1
68
+
69
+    @staticmethod
70
+    def join_all():
71
+        for p in ThreadPool.mapWorkerThreads.values():
72
+            p.join()
... ...
@@ -6,13 +6,12 @@ import ThreadPool
6 6
 
7 7
 class WorkerThread(threading.Thread):
8 8
 
9
-    def __init__(self, event, name, mapPackageToCycle, listAvailableCyclicPackages, logger,
9
+    def __init__(self, event, name, mapPackageToCycle, logger,
10 10
                  pkgBuildType):
11 11
         threading.Thread.__init__(self)
12 12
         self.statusEvent = event
13 13
         self.name = name
14 14
         self.mapPackageToCycle = mapPackageToCycle
15
-        self.listAvailableCyclicPackages = listAvailableCyclicPackages
16 15
         self.logger = logger
17 16
         self.pkgBuildType = pkgBuildType
18 17
 
... ...
@@ -21,30 +20,27 @@ class WorkerThread(threading.Thread):
21 21
         ThreadPool.ThreadPool.makeWorkerThreadActive(self.name)
22 22
         self.logger.info("Thread " + self.name + " is starting now")
23 23
         while True:
24
-            outputMap = {}
25 24
             pkg = Scheduler.Scheduler.getNextPackageToBuild()
26 25
             if pkg is None:
27 26
                 break
28 27
             self.logger.info("Thread " + self.name + " is building package:" + pkg)
29 28
             if self.pkgBuildType == "chroot":
30 29
                 pkgBuilder = PackageBuilderChroot(self.mapPackageToCycle,
31
-                                                  self.listAvailableCyclicPackages,
32 30
                                                   self.pkgBuildType)
33 31
             elif self.pkgBuildType == "container":
34 32
                 pkgBuilder = PackageBuilderContainer(self.mapPackageToCycle,
35
-                                                     self.listAvailableCyclicPackages,
36 33
                                                      self.pkgBuildType)
37
-            pkgBuilder.buildPackageFunction(pkg, outputMap, pkg)
38
-            if pkg not in outputMap or outputMap[pkg] == False:
34
+            try:
35
+                pkgBuilder.buildPackageFunction(pkg)
36
+            except Exception as e:
37
+                self.logger.exception(e)
39 38
                 buildThreadFailed = True
40 39
                 Scheduler.Scheduler.notifyPackageBuildFailed(pkg)
41
-                self.logger.info("Thread "+self.name +" stopped building package:" + pkg)
40
+                self.logger.info("Thread " + self.name + " stopped building package:" + pkg)
41
+                self.statusEvent.set()
42 42
                 break
43
-            self.logger.info("Thread "+ self.name + " finished building package:" + pkg)
43
+            self.logger.info("Thread " + self.name + " finished building package:" + pkg)
44 44
             Scheduler.Scheduler.notifyPackageBuildCompleted(pkg)
45 45
 
46
-        if buildThreadFailed:
47
-            self.statusEvent.set()
48
-
49 46
         ThreadPool.ThreadPool.makeWorkerThreadInActive(self.name)
50
-        self.logger.info("Thread "+self.name +" is going to rest")
47
+        self.logger.info("Thread " + self.name + " is going to rest")
... ...
@@ -7,6 +7,7 @@ import collections
7 7
 import traceback
8 8
 import sys
9 9
 import json
10
+import copy
10 11
 from CommandUtils import CommandUtils
11 12
 from Logger import Logger
12 13
 from constants import constants
... ...
@@ -187,7 +188,7 @@ def buildAPackage(package, buildThreads, pkgBuildType):
187 187
     listPackages = [package]
188 188
     pkgManager = PackageManager(pkgBuildType=pkgBuildType)
189 189
     if constants.rpmCheck:
190
-        constants.setTestForceRPMS(listPackages[:])
190
+        constants.setTestForceRPMS(copy.copy(listPackages))
191 191
     pkgManager.buildPackages(listPackages, buildThreads, pkgBuildType)
192 192
 
193 193
 
... ...
@@ -197,7 +198,7 @@ def buildPackagesForAllSpecs(logger, buildThreads, pkgInfoJsonFile, pkgBuildType
197 197
     logger.info("List of packages to build:")
198 198
     logger.info(listPackages)
199 199
     if constants.rpmCheck:
200
-        constants.setTestForceRPMS(listPackages[:])
200
+        constants.setTestForceRPMS(copy.copy(listPackages))
201 201
     pkgManager = PackageManager(pkgBuildType=pkgBuildType)
202 202
     pkgManager.buildPackages(listPackages, buildThreads, pkgBuildType)
203 203
 
... ...
@@ -216,18 +217,17 @@ def get_packages_with_build_options(pkg_build_options_file):
216 216
 
217 217
 def get_all_package_names(build_install_option):
218 218
     base_path = os.path.dirname(build_install_option)
219
-    jsonData = open(build_install_option)
220
-    option_list_json = json.load(jsonData, object_pairs_hook=collections.OrderedDict)
221
-    jsonData.close()
222
-    options_sorted = option_list_json.items()
223 219
     packages = []
224 220
 
225
-    for install_option in options_sorted:
226
-        filename = os.path.join(base_path, install_option[1]["file"])
227
-        jsonData = open(filename)
228
-        package_list_json = json.load(jsonData)
229
-        jsonData.close()
230
-        packages = packages + package_list_json["packages"]
221
+    with open(build_install_option) as jsonData:
222
+        option_list_json = json.load(jsonData, object_pairs_hook=collections.OrderedDict)
223
+        options_sorted = option_list_json.items()
224
+
225
+        for install_option in options_sorted:
226
+            filename = os.path.join(base_path, install_option[1]["file"])
227
+            with open(filename) as pkgJsonData:
228
+                package_list_json = json.load(pkgJsonData)
229
+            packages = packages + package_list_json["packages"]
231 230
 
232 231
     return packages
233 232