Viewing file: rpmmdRepo.py (15.88 KB) -rwxr-xr-x Select action/file-type: (+) | (+) | (+) | Code (+) | Session (+) | (+) | SDB (+) | (+) | (+) | (+) | (+) | (+) |
#!/usr/bin/python
import os import sys import time import glob import gzip import string import urllib import xmlrpclib import cStringIO import time
import rpm
sys.path.append("/usr/share/rhn/") from up2date_client import rpmSource from up2date_client import rpmSourceUtils from up2date_client import rhnChannel from up2date_client import repoDirector from up2date_client import rpmUtils from up2date_client import config from up2date_client import rpcServer from up2date_client import up2dateUtils
import genericRepo import urlUtils import genericSolveDep import repoMDObject import packageSack import packageObject
class RpmmdSolveDep(genericSolveDep.GenericSolveDep): def __init__(self): genericSolveDep.GenericSolveDep.__init__(self) self.type = "rpmmd"
# insert code to actually solve the dep by looking # though the package sack code to see what packags # solve a given dep def getSolutions(self, unknowns, msgCallback=None, progressCallback=None): channels = rhnChannel.getChannels() repoChannels = channels.getByType(self.type) channelNames = [] repoPackages = [] for channel in repoChannels: channelNames.append(channel['label']) for pkg in self.availList: if pkg[6] in channelNames: repoPackages.append(pkg) for channel in repoChannels: self.pkgSack = initPkgSack(label=channel['label'])
solutions = {} unknownsCopy = unknowns[:] for unknown in unknowns: provs = self.pkgSack.searchProvides(unknown) for prov in provs: if not solutions.has_key(unknown): solutions[unknown] = [] nevra = prov.returnNevraTuple() epoch = nevra[1] if epoch == '0': epoch = "" solutions[unknown] = [ [nevra[0], nevra[2], nevra[3], epoch, nevra[4]] ]
try: unknownsCopy.remove(unknown) except ValueError: # already removed from list pass if len(unknownsCopy) == 0: break
print "rpmmdSolvedep.getSolutions: %s" % solutions self.retList = solutions
def initPkgSack(label=None): cfg = config.initUp2dateConfig() global pkgSack try: pkgSack = pkgSack except NameError: pkgSack = None
if pkgSack == None: pkgSack = packageSack.XMLPackageSack(packageObject.RpmXMLPackageObject)
# just initilizing pkgSack not populating it if label == None: return pkgSack if not pkgSack._checkRepoStatus(label): xmlPrimaryPath = "%s/rpmmd-%s.primary.xml" % (cfg["storageDir"],label) #print "\n\nxmlPrimaryPath: %s" % xmlPrimaryPath # print os.access(xmlPrimaryPath) print "gh122" pkgSack.addFile(label, xmlPrimaryPath) else: print "already got %s" % label
return pkgSack
class RpmmdRepoSource(rpmSource.PackageSource): def __init__(self, proxyHost=None, loginInfo=None, cacheObject=None, register=None): self.cfg = config.initUp2dateConfig() rpmSource.PackageSource.__init__(self, cacheObject = cacheObject) self._loginInfo=loginInfo self.headerCache = cacheObject self.pkglists = {} self.pkgSack = initPkgSack()
def listPackages(self, channel, msgCallback = None, progressCallback = None):
globPattern = "%s/%s.*" % (self.cfg["storageDir"], channel['label']) oldLists = glob.glob(globPattern) channelTimeStamp = None if oldLists: filename = oldLists[0] filename = os.path.basename(filename) oldVersion = string.split(filename, '.')[-1] channelTimeStamp = time.strptime(oldVersion,"%Y%m%d%H%M%S")
url = "%s/repodata/repomd.xml" % (channel['url']) if msgCallback: msgCallback("Fetching %s" % url)
#print "url1: %s" % url ret = urlUtils.fetchUrl(url, lastModified=channelTimeStamp, progressCallback = progressCallback, agent = "Up2date %s/Yum" % up2dateUtils.version())
#print "gh2, ret: %s" % (ret, ) # time stamp bookkeeping if ret: (buffer, lmtime) = ret del ret else: return None
if not lmtime: lmtime = time.gmtime(time.time()) version = time.strftime("%Y%m%d%H%M%S", lmtime)
# print "buffer: %s" % buffer # print "lmtime: %s" % lmtime # use the time stamp on the headerlist as the channel "version" xmlFilePath = "%s/rpmmd-%s.repomd.%s" % (self.cfg["storageDir"], channel['label'], version) filePath = "%s/%s.%s" % (self.cfg["storageDir"], channel['label'], version) f = open(xmlFilePath, "w") f.write(buffer) f.close()
repodata = repoMDObject.RepoMD(channel['label'], xmlFilePath)
(pbase, phref) = repodata.primaryLocation()
xmlPrimaryPath = "%s/rpmmd-%s.primary.xml" % (self.cfg["storageDir"], channel['label']) xmlPrimaryUrl = "%s/%s" % (channel['url'], phref)
# msg callback here? #print "xmlPrimaryUrl: %s" % xmlPrimaryUrl # time1 = time.time() ret = urlUtils.fetchUrl(xmlPrimaryUrl, lastModified=channelTimeStamp, progressCallback = progressCallback, agent = "Up2date %s/Yum" % up2dateUtils.version())
# time stamp bookkeeping # FIXME, probabaly dont want to bail here if the file isnt new... if ret: (buffer, lmtime) = ret del ret else: return None
f = open(xmlPrimaryPath, "w") f.write(buffer) f.close()
# class scope since we want this to stick around, so we dont reparse # the big xml file time1 = time.time() self.pkgSack.addFile(channel['label'], xmlPrimaryPath) #print "import: %s" % (time.time() - time1)
pkglist = [] for key in self.pkgSack.nevra.keys(): #print key pkgs = self.pkgSack.nevra[key] for pkg in pkgs: info = pkg.simple epoch = info['epoch'] if epoch == "0" or epoch == 0: epoch = ""
# skip incompitable arches arch = info['arch'] if rpm.archscore(arch) == 0: continue
pkglist.append( (info['name'], info['version'], info['release'], epoch, info['arch'], info['packagesize'], channel['label']) )
pkglist.sort(lambda a, b: cmp(a[0], b[0])) rpmSourceUtils.saveListToDisk(pkglist, filePath, globPattern) self.pkglists[channel['label']] = pkglist return pkglist
def genObsoleteTupleFromPackageObject(self, packageObject): pkg = packageObject
epoch = pkg.epoch or "" name = pkg.name version = pkg.name release = pkg.release arch = pkg.arch
obs = [] for obsTup in pkg.prco['obsoletes']: obsName = obsTup[0] obsVers = obsTup[2] obsFlags = obsTup[1] obs.append([name, version, release, epoch, arch, obsName, obsVers, obsFlags])
# print "obs: %s" % obs return obs
def getObsoletes(self, channel, msgCallback = None, progressCallback = None): filePath = "%s/%s-obsoletes.%s" % (self.cfg["storageDir"], channel['label'], channel['version']) globPattern = "%s/%s-obsoletes.*" % (self.cfg["storageDir"], channel['label'])
if msgCallback: msgCallback("Fetching obsoletes list for %s" % channel['url'])
obsList = [] total = len(self.pkgSack.nevra) count = 0
for key in self.pkgSack.obsoletes.keys(): pkgs = self.pkgSack.obsoletes[key] for pkg in pkgs: obs = self.genObsoleteTupleFromPackageObject(pkg) if obs: obsList = obsList + obs
return []
def getHeader(self, package, msgCallback = None, progressCallback = None):
print "package: %s" % (package,) remoteFilename = "%s-%s-%s.%s.rpm" % (package[0], package[1], package[2], package[4])
if msgCallback: msgCallback(filename)
channels = rhnChannel.getChannels() channel = channels.getByLabel(package[6]) #url = "%s/RPMS/%s" % (channel['url'],remoteFilename ) if msgCallback: msgCallback("Fetching %s" % url)
#print package[0], package[3], package[1], package[2], package[4] epoch = "%s" % package[3] if package[3] == '': epoch = '0'
# if __debug__: # foo = self.pkgSack.nevra.keys() # foo.sort() # print foo # print self.pkgSack pkgs = self.pkgSack.nevra[package[0], epoch, package[1], package[2], package[4]]
# er...? pkg = pkgs[0] start = pkg.simple['hdrstart'] end = pkg.simple['hdrend'] relPath = pkg.simple['relativepath'] url = "%s/%s" % (channel['url'], relPath) # print "hdr start: %s end: %s" % (start, end)
# print "url: %s" % url (buffer, lmtime) = urlUtils.fetchUrl(url, progressCallback = progressCallback, agent = "Up2date %s/Yum" % up2dateUtils.version(), start=start, end=end)
# print buffer #tmp name to write out the raw header localFilename = "%s-%s-%s.%s.hdr" % (package[0], package[1], package[2], package[4]) tmpfilename = "%s/%s" % (self.cfg['storageDir'], localFilename) fd = open(tmpfilename, "w+") fd.write(buffer) fd.close() hdr = rpm.readHeaderListFromFile(tmpfilename)[0] rpmSourceUtils.saveHeader(hdr) self.headerCache["%s-%s-%s" % (hdr['name'], hdr['version'], hdr['release'])] = hdr return hdr
def getPackage(self, pkg, msgCallback = None, progressCallback = None): filename = "%s-%s-%s.%s.rpm" % (pkg[0], pkg[1], pkg[2], pkg[4]) channels = rhnChannel.getChannels() channel = channels.getByLabel(pkg[6]) #print "stored rpmpath: %s" % self.pkgNamePath[(pkg[0], pkg[1], pkg[2], pkg[3], pkg[4])] filePath = "%s/%s" % (self.cfg["storageDir"], filename) #rpmPath = self.pkgNamePath[(pkg[0], pkg[1], pkg[2], pkg[3], pkg[4])]
epoch = "%s" % pkg[3] if epoch == '': epoch = '0' label = channel['label'] if not pkgSack._checkRepoStatus(label): xmlPrimaryPath = "%s/rpmmd-%s.primary.xml" % (self.cfg["storageDir"],label) #print "\n\nxmlPrimaryPath: %s" % xmlPrimaryPath # print os.access(xmlPrimaryPath) pkgSack.addFile(label, xmlPrimaryPath) pkgs = self.pkgSack.nevra[pkg[0], epoch, pkg[1], pkg[2], pkg[4]] # er...? pkg = pkgs[0] relPath = pkg.simple['relativepath'] url = "%s/%s" % (channel['url'], relPath) #print "url: %s" % url
if msgCallback: # for now, makes it easier to debug #msgCallback(url) msgCallback(filename)
fd = open(filePath, "w+") (lmtime) = urlUtils.fetchUrlAndWriteFD(url, fd, progressCallback = progressCallback, agent = "Up2date %s/Yum" % up2dateUtils.version()) fd.close() buffer = open(filePath, "r").read() return buffer
# for key in self.pkgSack.nevra.keys(): # pkgs # since we use the diskcache secondary in yum/apt, and # we dont know the version till after we look at the # file, we glob for it, and use it class RpmmdDiskCache(rpmSource.PackageSource): def __init__(self, cacheObject = None): self.cfg = config.initUp2dateConfig() rpmSource.PackageSource.__init__(self, cacheObject = cacheObject)
def listAllPackages(self): pass def getObsoletes(self): pass def getHeader(self): pass def getPackage(self): pass def getPackageSource(self): pass
def listPackages(self, channel, msgCallback = None, progressCallback = None): globPattern = "%s/%s.*" % (self.cfg["storageDir"], channel['label']) lists = glob.glob(globPattern)
# FIXME? # we could sort and find the oldest, but there should # only be one if len(lists): localFilename = lists[0] else: # for now, fix PackageSourceChain to not freak # when everything returns None return 0
# FIXME error handling and what not f = open(localFilename, "r") filecontents = f.read() # bump it full if progressCallback: progressCallback(100,100)
tmp_args, tmp_method = xmlrpclib.loads(filecontents) # tmp_args[0] is the list of packages return tmp_args[0]
class RpmmdRepo(genericRepo.GenericRepo): def __init__(self): self.login = None genericRepo.GenericRepo.__init__(self) self.rmdrs = RpmmdRepoSource() self.rmdss = RpmmdDiskCache() localHeaderCache = rpmSource.HeaderCache() self.hcs = rpmSource.HeaderMemoryCache(cacheObject = localHeaderCache)
self.hds = rpmSource.DiskCache() self.hldc = rpmSource.LocalDisk()
self.psc.headerCache = localHeaderCache
self.sources = {'listPackages':[{'name':'rpmmd', 'object': self.rmdrs}, {'name':'rpmmddiskcache', 'object':self.rmdss}], 'listAllPackages':[{'name':'diskcache', 'object':self.hds}, {'name':'rpmmd', 'object': self.rmdss}], 'getObsoletes':[{'name':'diskcache', 'object':self.hds}, {'name':'rpmmd', 'object': self.rmdrs}], 'getHeader':[{'name':'memcache', 'object': self.hcs}, {'name':'rpmmd-diskcache', 'object':self.hds}, {'name':'rpmmd-localdisk', 'object':self.hldc}, {'name':'rpmmd', 'object': self.rmdrs}], 'getPackage':[{'name':'localdisk','object':self.hldc}, {'name':'diskcache', 'object':self.hds}, {'name':'rpmmd', 'object': self.rmdrs} ], # 'getPackageSource':[{'name':'localdisk','object':self.hldc}, # {'name':'diskcache', 'object':self.hds}, # {'name':'rpmmd', 'object': self.rmdrs} # ] }
# print "self.sources: %s" % self.sources
def updateAuthInfo(self): pass
def register(rd): rpmmdRepo = RpmmdRepo() rd.handlers['rpmmd'] = rpmmdRepo rpmmdSolveDep = RpmmdSolveDep() rd.depSolveHandlers['rpmmd'] = rpmmdSolveDep
|