예제 #1
0
    def testBlockDevice(self):
        foo = filetypes.BlockDevice(8, 1)
        fileObj = foo.get(pathId)
        self.assertEquals(fileObj.lsTag, 'b')
        self.assertEquals(fileObj.devt.major(), 8)
        self.assertEquals(fileObj.devt.minor(), 1)
        self.assertEquals(foo.getContents(), None)

        requires = deps.ThawDependencySet('4#foo::runtime')
        provides = deps.ThawDependencySet('11#foo')
        foo = filetypes.BlockDevice(8, 1, provides=provides, requires=requires)
        fileObj = foo.get(pathId)
        self.assertEquals(fileObj.provides(), provides)
        self.assertEquals(fileObj.requires(), requires)
예제 #2
0
    def getDepCacheEntry(self, troveTup):
        result = self.depCache.get(troveTup)
        if result is None:
            return None

        origResult = result
        if type(result[0]) is str:
            result = (deps.ThawDependencySet(result[0]), result[1])

        if type(result[1]) is str:
            result = (result[0], deps.ThawDependencySet(result[1]))

        if result != origResult:
            self.depCache[troveTup] = result

        return result
예제 #3
0
    def testRegularFileBasics(self):
        foo = filetypes.RegularFile(contents='foo1')
        fileObj = foo.get(pathId)
        f = foo.getContents()
        self.assertEquals(f.read(), 'foo1')
        self.assertEquals(fileObj.flags(), 0)
        self.assertEquals(fileObj.flavor(), deps.Flavor())
        self.assertEquals(fileObj.provides(), deps.DependencySet())
        self.assertEquals(fileObj.requires(), deps.DependencySet())
        self.assertEquals(fileObj.inode.perms(), 0644)
        self.assertEquals(fileObj.inode.owner(), 'root')
        self.assertEquals(fileObj.inode.group(), 'root')
        self.assertEquals(fileObj.lsTag, '-')
        self.assertEquals(fileObj.linkGroup(), None)
        self.assertEquals(
            fileObj.fileId(),
            '(\x01\x9a\xcbz\xbb\x93\x15\x01c\xcf\xd5\x14\xef\xf7,S\xbb\xf8p')

        requires = deps.ThawDependencySet('4#foo::runtime')
        provides = deps.ThawDependencySet('11#foo')
        flv = deps.parseFlavor('xen,domU is: x86')
        bar = filetypes.RegularFile(contents=StringIO('bar'),
                                    config=True,
                                    provides=provides,
                                    requires=requires,
                                    flavor=flv,
                                    owner='foo',
                                    group='bar',
                                    perms=0700,
                                    mtime=12345,
                                    tags=['tag1', 'tag2'])
        fileObj = bar.get(pathId)
        self.assertEquals(bool(fileObj.flags.isInitialContents()), False)
        self.assertEquals(bool(fileObj.flags.isTransient()), False)
        self.assertEquals(bool(fileObj.flags.isConfig()), True)
        self.assertEquals(fileObj.requires(), requires)
        self.assertEquals(fileObj.provides(), provides)
        self.assertEquals(fileObj.flavor(), flv)
        self.assertEquals(fileObj.inode.perms(), 0700)
        self.assertEquals(fileObj.inode.owner(), 'foo')
        self.assertEquals(fileObj.inode.group(), 'bar')
        self.assertEquals(fileObj.inode.mtime(), 12345)
        self.assertEquals(fileObj.tags(), ['tag1', 'tag2'])
예제 #4
0
 def _loadDepSolutions(self):
     if self.version < (2, 0):
         # Earlier versions were missing timestamps, which interferes with
         # dep solver tie-breaking.
         return
     depSolutionsList = self._loadPickle(self._depSolutionsPathId)
     for (sig, depSet, aResult) in depSolutionsList:
         depSet = deps.ThawDependencySet(depSet)
         allResults = []
         for resultList in aResult:
             allResults.append([(x[0], versions.ThawVersion(x[1]),
                                 deps.ThawFlavor(x[2]))
                                for x in resultList])
         self.addDepSolution(sig, depSet, allResults)
예제 #5
0
 def _loadDepSolutions(self):
     if self.version < (3, 0):
         # Version 1 was missing timestamps, which interferes with dep
         # solver tie-breaking.
         # Version 2 could have bogus unresolved dep solutions due to a bug
         # so the version was bumped to invalidate those.
         return
     depSolutionsList = self._loadPickle(self._depSolutionsPathId)
     for (sig, depSet, aResult) in depSolutionsList:
         depSet = deps.ThawDependencySet(depSet)
         allResults = []
         for resultList in aResult:
             allResults.append([
                 (x[0], versions.ThawVersion(x[1]), deps.ThawFlavor(x[2]))
                 for x in resultList])
         self.addDepSolution(sig, depSet, allResults)
예제 #6
0
    def testRPMCapsuleUserGroup(self):
        recipestr1 = r"""
class TestGroup(CapsuleRecipe):
    name = 'test'
    version = '0'
    clearBuildReqs()

    def setup(r):
        r.addCapsule('ownerships-1.0-1.i386.rpm')
"""
        built, d = self.buildRecipe(recipestr1, "TestGroup")

        nvf = built[0]
        nvf = nvf[0], versions.VersionFromString(nvf[1]), nvf[2]

        repos = self.openRepository()
        trv = repos.getTrove(*nvf)

        self.assertEquals(
            trv.requires(),
            deps.ThawDependencySet(
                '17#CompressedFileNames|17#PayloadFilesHavePrefix|'
                '17#PayloadIsBzip2'))
예제 #7
0
    def testUserInfoGroupInfoSplitting(self):
        """
        We need to create users and groups sepparately to handle dependency
        loops in group memebership. For instance on CentOS 6 the daemon user is
        in the bin, lp, and daemon groups. The lp user is in the daemon and lp
        groups. This means that neither of these users can be installed due to
        the depency loop. The install code does put all of the uesrs into the
        same install job, but then can't deal with the loop. (CNY-3731)
        """

        daemonInfoRecipe = """
class InfoDaemon(UserInfoRecipe):
    name = 'info-daemon'
    version = '1'
    clearBuildReqs()
    def setup(r):
        r.User('daemon', 2, supplemental=['lp', 'bin'])
"""

        lpInfoRecipe = """
class InfoLp(UserInfoRecipe):
    name = 'info-lp'
    version = '1'
    clearBuildReqs()
    def setup(r):
        r.User('lp', 3, supplemental=['daemon', ])
"""

        binInfoRecipe = """
class InfoBin(UserInfoRecipe):
    name = 'info-bin'
    version = '1'
    clearBuildReqs()
    def setup(r):
        r.User('bin', 4, supplemental=['daemon', ])
"""

        comps1, r1 = self.buildRecipe(daemonInfoRecipe, 'InfoDaemon')
        comps2, r2 = self.buildRecipe(lpInfoRecipe, 'InfoLp')
        comps3, r3 = self.buildRecipe(binInfoRecipe, 'InfoBin')

        # Make sure there is a :user and :group component for each package.
        for comps in (comps1, comps2, comps3):
            self.failUnlessEqual(len([ x for x in comps
                if x[0].endswith(':user') or x[0].endswith(':group') ]), 2)

        group1, user1 = sorted(comps1)
        group2, user2 = sorted(comps2)
        group3, user3 = sorted(comps3)

        repos = self.openRepository()
        user1nvf = repos.findTrove(None, user1)
        user2nvf = repos.findTrove(None, user2)
        user3nvf = repos.findTrove(None, user3)

        user1trv = repos.getTrove(*user1nvf[0])
        user2trv = repos.getTrove(*user2nvf[0])
        user3trv = repos.getTrove(*user3nvf[0])

        group1nvf = repos.findTrove(None, group1)
        group2nvf = repos.findTrove(None, group2)
        group3nvf = repos.findTrove(None, group3)

        group1trv = repos.getTrove(*group1nvf[0])
        group2trv = repos.getTrove(*group2nvf[0])
        group3trv = repos.getTrove(*group3nvf[0])

        # info-daemon:user should require info-bin:group, info-daemon:group,
        # and info-lp:group.
        self.failUnlessEqual(user1trv.requires,
            deps.ThawDependencySet('8#bin|8#daemon|8#lp'))
        # info-lp:user should require info-daemon:group and info-lp:group.
        self.failUnlessEqual(user2trv.requires,
            deps.ThawDependencySet('8#daemon|8#lp'))
        # info-bin:user should require info-bin:group and info-dameon:group.
        self.failUnlessEqual(user3trv.requires,
            deps.ThawDependencySet('8#bin|8#daemon'))

        # Make sure the user components don't provide groups.
        self.failUnlessEqual(user1trv.provides,
            deps.ThawDependencySet('4#info-daemon::user|7#daemon'))
        self.failUnlessEqual(user2trv.provides,
            deps.ThawDependencySet('4#info-lp::user|7#lp'))
        self.failUnlessEqual(user3trv.provides,
            deps.ThawDependencySet('4#info-bin::user|7#bin'))

        # Make sure the group components provide the groups
        self.failUnlessEqual(group1trv.provides,
            deps.ThawDependencySet('4#info-daemon::group|8#daemon'))
        self.failUnlessEqual(group2trv.provides,
            deps.ThawDependencySet('4#info-lp::group|8#lp'))
        self.failUnlessEqual(group3trv.provides,
            deps.ThawDependencySet('4#info-bin::group|8#bin'))

        # And that the groups don't require anything
        self.failUnlessEqual(group1trv.requires, deps.ThawDependencySet(''))
        self.failUnlessEqual(group2trv.requires, deps.ThawDependencySet(''))
        self.failUnlessEqual(group3trv.requires, deps.ThawDependencySet(''))

        self.updatePkg('info-daemon:user', resolve=True)
예제 #8
0
    def resolve(self,
                groupIds,
                label,
                depList,
                troveList=[],
                leavesOnly=False):
        """ Determine troves that provide the given dependencies,
            restricting by label and limiting to latest version for
            each (name, flavor) pair.
        """
        cu = self.db.cursor()
        # need to make sure that depList does not contain duplicates
        # for efficiency reasons
        requires = {}
        for depStr in depList:
            depSet = deps.ThawDependencySet(depStr)
            requires[depSet] = depStr
        depSetList = requires.keys()
        depNums = self._setupDepSets(cu, depSetList)

        # 1. look up inmstances whose provides fully satisfy all the
        #    flags of every depName within a depSet (flagCount check)
        # 2. out of those instances, only consider the ones that fully
        #    satisfy all the depName deps within a depSet (depCount
        #    check)
        # 3. filter only the instanceIds the user has access to
        query = """
        select distinct
            tmpDepNum.idx as idx, tmpDepNum.depNum as depNum,
            Items.item, flavor, version, Nodes.timeStamps,
            Nodes.finalTimestamp as finalTimestamp
        from tmpDepNum
        join (
            select
                tmpDeps.idx as idx,
                tmpDeps.depNum as depNum,
                Provides.instanceId as instanceid,
                count(*) as flagCount
            from tmpDeps
            join Dependencies using(class, name, flag)
            join Provides using(depId)
            group by tmpDeps.idx, tmpDeps.depNum, Provides.instanceId
        ) as DepSelect using(idx, depNum, flagCount)
        join Instances on
            Instances.instanceId = DepSelect.instanceId
        join Nodes using(itemId, versionId) """

        where = [
            "ugi.userGroupId in (%s)" % (",".join("%d" % x
                                                  for x in groupIds), )
        ]
        args = []
        if troveList:
            self._setupTroveList(cu, troveList)
            query += """
            join tmpInstances as ti on ti.instanceId = Instances.instanceId
            join UserGroupInstancesCache as ugi on
                ugi.instanceId = ti.instanceId """
        else:
            if leavesOnly:
                query += """
                join LatestCache as ugi using (itemId, versionId, branchId) """
                where.append("ugi.latestType = %d" %
                             trovesource.TROVE_QUERY_NORMAL)
                where.append("ugi.flavorId = Instances.flavorId")
            else:
                query += """
                join UserGroupInstancesCache as ugi on
                    ugi.instanceId = Instances.instanceId """
            # restrict by label
            if label:
                query += """
                join LabelMap on
                    Instances.itemId = LabelMap.itemId and
                    Nodes.branchId = LabelMap.branchId
                join Labels using (labelId) """
                where.append("Labels.label = ?")
                args.append(label)
        # final joins to allow us to extract the query results as strings
        query += """
        join Items on Instances.itemId = Items.itemId
        join Versions on Instances.versionId = Versions.versionId
        join Flavors on Instances.flavorId = Flavors.flavorId
        where %s
        order by idx, depNum, finalTimestamp desc """ % (" and ".join(where))
        cu.execute(query, args)

        # sqlite version 3.2.2 have trouble sorting correctly the
        # results from the previous query. If we're running on sqlite,
        # we take the hit here and resort the results in Python...
        if self.db.driver == "sqlite":
            # order by idx, depNum, finalTimestamp desc
            retList = sorted(cu, key=lambda a: (a[0], a[1], -a[6]))
        else:
            retList = cu

        ret = {}
        for (depId, depNum, troveName, flavorStr, versionStr, timeStamps,
             ft) in retList:
            retd = ret.setdefault(depId, [{} for x in xrange(depNums[depId])])
            # remember the first version of each (n,f) tuple for each query
            retd[depNum].setdefault((troveName, flavorStr),
                                    (versionStr, timeStamps))
        ret2 = {}
        for depId, depDictList in ret.iteritems():
            key = requires[depSetList[depId]]
            retList = ret2.setdefault(key,
                                      [[] for x in xrange(len(depDictList))])
            for i, depDict in enumerate(depDictList):
                retList[i] = [(trv[0],
                               versions.strToFrozen(ver[0],
                                                    ver[1].split(":")), trv[1])
                              for trv, ver in depDict.iteritems()]
        # fill in the result dictionary for the values we have not resolved deps for
        result = {}
        for depId, depSet in enumerate(depSetList):
            result.setdefault(requires[depSet],
                              [[] for x in xrange(depNums[depId])])
        result.update(ret2)
        return result