Beispiel #1
0
    def test_process_build(self):
        old_build = self.prepare_old_build()
        build = self.prepare_foo_build(repo_id=123, version='4')

        with self.mocks():
            self.build_resolver.main()
            self.db.rollback()

        self.assertIs(True, build.deps_resolved)

        expected_changes = [
            (build.id, 'C', 2, RpmEVR(1, '2',
                                      '1.fc22'), RpmEVR(1, '3', '1.fc22')),
            (build.id, 'E', 2, None, RpmEVR(0, '0.1', '1.fc22.1')),
        ]
        actual_changes = [(c.build_id, c.dep_name, c.distance, c.prev_evr,
                           c.curr_evr) for c in build.dependency_changes]
        self.assertCountEqual(expected_changes, actual_changes)

        actual_deps = (self.db.query(
            Dependency.name,
            Dependency.epoch,
            Dependency.version,
            Dependency.release,
            Dependency.arch,
        ).filter(Dependency.id.in_(build.dependency_keys)).all())
        self.assertCountEqual(FOO_DEPS, actual_deps)

        self.assertIsNone(old_build.dependency_keys)
Beispiel #2
0
 def test_repo_generation(self):
     self.prepare_old_build()
     self.collection.latest_repo_resolved = None
     self.collection.latest_repo_id = None
     self.db.commit()
     with self.mocks(requires=[['F', 'A'], ['nonexistent']]) as fedmsg_mock:
         self.repo_resolver.main()
         self.assertTrue(self.collection.latest_repo_resolved)
         self.assert_collection_fedmsg_emitted(fedmsg_mock, 'unknown', 'ok')
     self.db.expire_all()
     foo = self.db.query(Package).filter_by(name='foo').first()
     self.assertTrue(foo.resolved)
     self.assertEqual(20, foo.dependency_priority)
     expected_changes = [
         ('C', 2, RpmEVR(1, '2', '1.fc22'), RpmEVR(1, '3', '1.fc22')),
         ('E', 2, None, RpmEVR(0, '0.1', '1.fc22.1')),
     ]
     actual_changes = [(c.dep_name, c.distance, c.prev_evr, c.curr_evr)
                       for c in foo.unapplied_changes]
     self.assertCountEqual(expected_changes, actual_changes)
     resolution_change = self.db.query(ResolutionChange)\
         .filter_by(package_id=foo.id)\
         .one()
     self.assertFalse(
         self.db.query(ResolutionProblem).filter_by(
             resolution_id=resolution_change.id).count())
     self.assertTrue(self.collection.latest_repo_resolved)
     self.assertEqual(123, self.collection.latest_repo_id)
Beispiel #3
0
 def test_rpmevr_db_comparison(self):
     dep = Dependency(name='foo',
                      version='1.1',
                      release='8.fc26',
                      arch='x86_64')
     self.db.add(dep)
     evr = RpmEVR(0, '1.1', '11.fc26')
     res = (self.db.query(Dependency).filter(Dependency.evr > evr).first())
     self.assertIsNone(res)
     res = (self.db.query(Dependency).filter(Dependency.evr < evr).first())
     self.assertIs(dep, res)
Beispiel #4
0
 def test_rpmevr_db_comparison(self):
     build = self.prepare_build('rnv')
     change = UnappliedChange(
         package_id=build.package.id, dep_name='foo',
         prev_epoch=None, prev_version='1.1', prev_release='8.fc26',
         curr_epoch=None, curr_version='1.1', curr_release='8.fc26',
     )
     self.db.add(change)
     evr = RpmEVR(0, '1.1', '11.fc26')
     res = self.db.query(UnappliedChange)\
         .filter(UnappliedChange.prev_evr > evr).first()
     self.assertIsNone(res)
     res = self.db.query(UnappliedChange)\
         .filter(UnappliedChange.prev_evr < evr).first()
     self.assertEqual(change, res)
Beispiel #5
0
 def test_rpmevr_comparison(self):
     evr1 = RpmEVR(0, '1.1', '11.fc26')
     evr2 = RpmEVR(None, '1.1', '8.fc26')
     self.assertGreater(evr1, evr2)
Beispiel #6
0
def affected_by(dep_name):
    """
    Display which packages are possibly affected by given dependency change.
    """
    if len(g.current_collections) != 1:
        abort(400)
    collection = g.current_collections[0]
    try:
        evr1 = RpmEVR(int(request.args['epoch1']), request.args['version1'],
                      request.args['release1'])
        evr2 = RpmEVR(int(request.args['epoch2']), request.args['version2'],
                      request.args['release2'])
    except (KeyError, ValueError):
        abort(400)

    # Dependencies in the evr1 to evr2 interval
    # Note that evr comparisons are overloaded custom comparators that invoke RPM-correct
    # comparisons implemented in rpmvercmp.sql
    deps_in = (db.query(Dependency.id).filter(
        Dependency.name == dep_name).filter(Dependency.evr > evr1).filter(
            Dependency.evr < evr2).cte('deps_in'))
    # Dependencies with greater evr than evr2
    deps_higher = (db.query(
        Dependency.id).filter(Dependency.name == dep_name).filter(
            Dependency.evr >= evr2).cte('deps_higher'))
    # Dependencies with lesser evr than evr1
    deps_lower = (db.query(
        Dependency.id).filter(Dependency.name == dep_name).filter(
            Dependency.evr <= evr1).cte('deps_lower'))
    # Get only changes where the prev_evr to curr_evr interval overlaps with evr1 to evr2
    filtered_changes = union(
        # Changes with previous evr in the evr1 to evr2 interval
        db.query(AppliedChange).filter(
            AppliedChange.prev_dep_id.in_(db.query(deps_in))),
        # Changes with current evr in the evr1 to evr2 interval
        db.query(AppliedChange).filter(
            AppliedChange.curr_dep_id.in_(db.query(deps_in))),
        # Changes with both evrs "around" the evr1 to evr2 interval
        db.query(AppliedChange).filter(
            (AppliedChange.prev_dep_id.in_(db.query(deps_lower)))
            & (AppliedChange.curr_dep_id.in_(db.query(deps_higher)))),
    ).alias('filtered_changes')

    prev_build = aliased(Build)
    # Get a subquery for previous build state
    subq = db.query(prev_build.state.label('prev_state'))\
        .order_by(prev_build.started.desc())\
        .filter(prev_build.started < Build.started)\
        .filter(prev_build.package_id == Build.package_id)\
        .limit(1)\
        .correlate().as_scalar()
    prev_dep = aliased(Dependency)
    curr_dep = aliased(Dependency)
    failed = (
        db.query(
            prev_dep.name.label('dep_name'),
            prev_dep.evr.label('prev_evr'),
            curr_dep.evr.label('curr_evr'),
            AppliedChange.distance,
            Build.id.label('build_id'),
            Build.state.label('build_state'),
            Build.started.label('build_started'),
            Package.name.label('package_name'),
            Package.resolved.label('package_resolved'),
            Package.last_complete_build_state.label('package_lb_state'),
            subq.label('prev_build_state'),
        ).select_entity_from(filtered_changes).join(
            prev_dep, AppliedChange.prev_dep).join(
                curr_dep,
                AppliedChange.curr_dep).join(AppliedChange.build).join(
                    Build.package).filter_by(blocked=False,
                                             tracked=True,
                                             collection_id=collection.id)
        # Show only packages where the build after failed, but the previous one was ok
        .filter(Build.state == Build.FAILED).filter(
            subq != Build.FAILED).order_by(AppliedChange.distance,
                                           Build.started.desc()).all())

    # Auxiliary function to compute state string for the query row
    def package_state(row):
        return Package(
            tracked=True,
            blocked=False,
            resolved=row.package_resolved,
            last_complete_build_state=row.package_lb_state,
        ).state_string

    return render_template("affected-by.html",
                           package_state=package_state,
                           dep_name=dep_name,
                           evr1=evr1,
                           evr2=evr2,
                           collection=collection,
                           failed=failed)