~launchpad-pqm/launchpad/devel

« back to all changes in this revision

Viewing changes to lib/lp/archivepublisher/domination.py

  • Committer: Launchpad Patch Queue Manager
  • Date: 2011-10-18 05:47:37 UTC
  • mfrom: (14157.2.5 bug-876171)
  • Revision ID: launchpad@pqm.canonical.com-20111018054737-s0b72mtu8grdpwfy
[r=stevenk][bug=876171] obsolete-distroseries.py will now schedule
        deletion of any publications that remain uncondemned.

Show diffs side-by-side

added added

removed removed

Lines of Context:
153
153
    class.
154
154
    """
155
155
    def __init__(self, is_source=True):
156
 
        self.is_source = is_source
157
156
        if is_source:
158
157
            self.traits = SourcePublicationTraits
159
158
        else:
205
204
        self.logger = logger
206
205
        self.archive = archive
207
206
 
208
 
    def _checkArchIndep(self, publication):
209
 
        """Return True if the binary publication can be superseded.
210
 
 
211
 
        If the publication is an arch-indep binary, we can only supersede
212
 
        it if all the binaries from the same source are also superseded,
213
 
        else those binaries may become uninstallable.
214
 
        See bug 34086.
215
 
        """
216
 
        binary = publication.binarypackagerelease
217
 
        if not binary.architecturespecific:
218
 
            # getOtherPublicationsForSameSource returns PENDING in
219
 
            # addition to PUBLISHED binaries, and we rely on this since
220
 
            # they must also block domination.
221
 
            others = publication.getOtherPublicationsForSameSource()
222
 
            if others.any():
223
 
                # Don't dominate this arch:all binary as there are
224
 
                # other arch-specific binaries from the same build
225
 
                # that are still active.
226
 
                return False
227
 
        return True
228
 
 
229
207
    def dominatePackage(self, publications, live_versions, generalization):
230
208
        """Dominate publications for a single package.
231
209
 
282
260
                pub.supersede(current_dominant, logger=self.logger)
283
261
                self.logger.debug2(
284
262
                    "Superseding older publication for version %s.", version)
285
 
            elif (version in live_versions or
286
 
                  (not generalization.is_source and
287
 
                   not self._checkArchIndep(pub))):
 
263
            elif version in live_versions:
288
264
                # This publication stays active; if any publications
289
265
                # that follow right after this are to be superseded,
290
266
                # this is the release that they are superseded by.
322
298
            # one, this dominatePackage call will never result in a
323
299
            # deletion.
324
300
            latest_version = generalization.getPackageVersion(publications[0])
325
 
            self.logger.debug2("Dominating %s" % name)
326
301
            self.dominatePackage(
327
302
                publications, [latest_version], generalization)
328
303
 
384
359
 
385
360
        self.logger.debug("Beginning superseded processing...")
386
361
 
 
362
        # XXX: dsilvers 2005-09-22 bug=55030:
 
363
        # Need to make binaries go in groups but for now this'll do.
 
364
        # An example of the concrete problem here is:
 
365
        # - Upload foo-1.0, which builds foo and foo-common (arch all).
 
366
        # - Upload foo-1.1, ditto.
 
367
        # - foo-common-1.1 is built (along with the i386 binary for foo)
 
368
        # - foo-common-1.0 is superseded
 
369
        # Foo is now uninstallable on any architectures which don't yet
 
370
        # have a build of foo-1.1, as the foo-common for foo-1.0 is gone.
 
371
 
 
372
        # Essentially we ideally don't want to lose superseded binaries
 
373
        # unless the entire group is ready to be made pending removal.
 
374
        # In this instance a group is defined as all the binaries from a
 
375
        # given build. This assumes we've copied the arch_all binaries
 
376
        # from whichever build provided them into each arch-specific build
 
377
        # which we publish. If instead we simply publish the arch-all
 
378
        # binaries from another build then instead we should scan up from
 
379
        # the binary to its source, and then back from the source to each
 
380
        # binary published in *this* distroarchseries for that source.
 
381
        # if the binaries as a group (in that definition) are all superseded
 
382
        # then we can consider them eligible for removal.
387
383
        for pub_record in binary_records:
388
384
            binpkg_release = pub_record.binarypackagerelease
389
385
            self.logger.debug(
454
450
        generalization = GeneralizedPublication(is_source=False)
455
451
 
456
452
        for distroarchseries in distroseries.architectures:
457
 
            self.logger.info(
 
453
            self.logger.debug(
458
454
                "Performing domination across %s/%s (%s)",
459
455
                distroseries.name, pocket.title,
460
456
                distroarchseries.architecturetag)
461
457
 
462
 
            bpph_location_clauses = [
 
458
            bpph_location_clauses = And(
463
459
                BinaryPackagePublishingHistory.status ==
464
460
                    PackagePublishingStatus.PUBLISHED,
465
461
                BinaryPackagePublishingHistory.distroarchseries ==
466
462
                    distroarchseries,
467
463
                BinaryPackagePublishingHistory.archive == self.archive,
468
464
                BinaryPackagePublishingHistory.pocket == pocket,
469
 
                ]
 
465
                )
470
466
            candidate_binary_names = Select(
471
467
                BinaryPackageName.id,
472
468
                And(
478
474
                ),
479
475
                group_by=BinaryPackageName.id,
480
476
                having=Count(BinaryPackagePublishingHistory.id) > 1)
481
 
            main_clauses = [
 
477
            binaries = IStore(BinaryPackagePublishingHistory).find(
482
478
                BinaryPackagePublishingHistory,
483
479
                BinaryPackageRelease.id ==
484
480
                    BinaryPackagePublishingHistory.binarypackagereleaseID,
486
482
                    candidate_binary_names),
487
483
                BinaryPackageRelease.binpackageformat !=
488
484
                    BinaryPackageFormat.DDEB,
489
 
                ]
490
 
            main_clauses.extend(bpph_location_clauses)
491
 
 
492
 
            def do_domination(pass2_msg=""):
493
 
                msg = "binaries..." + pass2_msg
494
 
                self.logger.info("Finding %s" % msg)
495
 
                bins = IStore(
496
 
                    BinaryPackagePublishingHistory).find(*main_clauses)
497
 
                self.logger.info("Dominating %s" % msg)
498
 
                sorted_packages = self._sortPackages(bins, generalization)
499
 
                self._dominatePublications(sorted_packages, generalization)
500
 
 
501
 
            do_domination()
502
 
 
503
 
            # We need to make a second pass to cover the cases where:
504
 
            #  * arch-specific binaries were not all dominated before arch-all
505
 
            #    ones that depend on them
506
 
            #  * An arch-all turned into an arch-specific, or vice-versa
507
 
            #  * A package is completely schizophrenic and changes all of
508
 
            #    its binaries between arch-all and arch-any (apparently
509
 
            #    occurs sometimes!)
510
 
            do_domination("(2nd pass)")
 
485
                bpph_location_clauses)
 
486
            self.logger.debug("Dominating binaries...")
 
487
            self._dominatePublications(
 
488
                self._sortPackages(binaries, generalization), generalization)
511
489
 
512
490
    def _composeActiveSourcePubsCondition(self, distroseries, pocket):
513
491
        """Compose ORM condition for restricting relevant source pubs."""