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>
... | ... |
@@ -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 |
|