Merge lp:~julian-edwards/launchpad/delete-ppa-part2 into lp:launchpad/db-devel

Proposed by Julian Edwards
Status: Merged
Approved by: Julian Edwards
Approved revision: no longer in the source branch.
Merged at revision: not available
Proposed branch: lp:~julian-edwards/launchpad/delete-ppa-part2
Merge into: lp:launchpad/db-devel
Diff against target: 264 lines (+44/-51)
2 files modified
lib/lp/archivepublisher/publishing.py (+11/-20)
lib/lp/archivepublisher/tests/test_publisher.py (+33/-31)
To merge this branch: bzr merge lp:~julian-edwards/launchpad/delete-ppa-part2
Reviewer Review Type Date Requested Status
Abel Deuring (community) code Approve
Review via email: mp+23967@code.launchpad.net

Description of the change

This is a quick branch bloated a bit by all the lint I fixed. It is a fix to
delete the right directory when deleting PPAs.

Consider this tree structure:

PPA_ROOT/
  <ppa_owner_name>/
     ppa1_name/
        file1
        file2
     ppa2_name/

If we want to delete "ppa1_name" What happens right now is that only the files
*under* the ppa1_name directory are removed.

I've fixed it so that the "ppa1_name" directory itself gets removed.

The test_publisher.py file had lots of lint, please excuse the noise. The
meat of the change is in the deleteArchive() method which no longer raises
OOPSes (it's pointless and was not tested) if it can't delete the archive.
This is a valid scenario since an admin may have done it manually if the
deletion was time-critical. It just logs the error and continues.

In the test, I also added an extra assertion that the archive gets disabled
(was missing from before), and an extra deletion step to prove that deleting a
missing repo doesn't blow up.

Cheers

To post a comment you must log in.
Revision history for this message
Abel Deuring (adeuring) :
review: Approve (code)

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file 'lib/lp/archivepublisher/publishing.py'
--- lib/lp/archivepublisher/publishing.py 2010-04-15 16:20:04 +0000
+++ lib/lp/archivepublisher/publishing.py 2010-04-23 15:16:27 +0000
@@ -37,8 +37,6 @@
37from lp.soyuz.interfaces.publishing import PackagePublishingStatus37from lp.soyuz.interfaces.publishing import PackagePublishingStatus
3838
39from canonical.librarian.client import LibrarianClient39from canonical.librarian.client import LibrarianClient
40from canonical.launchpad.webapp.errorlog import (
41 ErrorReportingUtility, ScriptRequest)
4240
43suffixpocket = dict((v, k) for (k, v) in pocketsuffix.items())41suffixpocket = dict((v, k) for (k, v) in pocketsuffix.items())
4442
@@ -610,28 +608,21 @@
610 be caught and an OOPS report generated.608 be caught and an OOPS report generated.
611 """609 """
612610
611 root_dir = os.path.join(
612 self._config.distroroot, self.archive.owner.name,
613 self.archive.name)
614
613 self.log.info(615 self.log.info(
614 "Attempting to delete archive '%s/%s' at '%s'." % (616 "Attempting to delete archive '%s/%s' at '%s'." % (
615 self.archive.owner.name, self.archive.name, 617 self.archive.owner.name, self.archive.name, root_dir))
616 self._config.archiveroot))
617618
618 # Attempt to rmdir if the path to the root of the archive exists.619 try:
619 if os.path.exists(self._config.archiveroot):620 shutil.rmtree(root_dir)
620 try:621 except (shutil.Error, OSError), e:
621 shutil.rmtree(self._config.archiveroot)
622 except:
623 message = 'Exception while deleting archive root %s' % (
624 self._config.archiveroot)
625 request = ScriptRequest([('error-explanation', message)])
626 ErrorReportingUtility().raising(sys.exc_info(), request)
627 self.log.error('%s (%s)' % (message, request.oopsid))
628 else:
629 self.log.warning(622 self.log.warning(
630 "Root directory '%s' for archive '%s/%s' does not exist." % (623 "Failed to delete directory '%s' for archive '%s/%s'\n%s" % (
631 self._config.archiveroot, self.archive.owner.name, 624 root_dir, self.archive.owner.name,
632 self.archive.name))625 self.archive.name, e))
633626
634 # Set archive's status to DELETED.
635 self.archive.status = ArchiveStatus.DELETED627 self.archive.status = ArchiveStatus.DELETED
636 # Disable publishing for this archive.
637 self.archive.publish = False628 self.archive.publish = False
638629
=== modified file 'lib/lp/archivepublisher/tests/test_publisher.py'
--- lib/lp/archivepublisher/tests/test_publisher.py 2010-04-15 16:18:09 +0000
+++ lib/lp/archivepublisher/tests/test_publisher.py 2010-04-23 15:16:27 +0000
@@ -8,7 +8,6 @@
88
9import bz29import bz2
10import gzip10import gzip
11import hashlib
12import os11import os
13import shutil12import shutil
14import stat13import stat
@@ -37,7 +36,6 @@
37from lp.soyuz.interfaces.publishing import PackagePublishingStatus36from lp.soyuz.interfaces.publishing import PackagePublishingStatus
38from lp.archivepublisher.interfaces.archivesigningkey import (37from lp.archivepublisher.interfaces.archivesigningkey import (
39 IArchiveSigningKey)38 IArchiveSigningKey)
40from lp.testing import get_lsb_information
41from lp.soyuz.tests.test_publishing import TestNativePublishingBase39from lp.soyuz.tests.test_publishing import TestNativePublishingBase
42from canonical.zeca.ftests.harness import ZecaTestSetup40from canonical.zeca.ftests.harness import ZecaTestSetup
4341
@@ -110,8 +108,16 @@
110 publisher._config.archiveroot, 'test_file'), 'w').close()108 publisher._config.archiveroot, 'test_file'), 'w').close()
111109
112 publisher.deleteArchive()110 publisher.deleteArchive()
113 self.assertFalse(os.path.exists(publisher._config.archiveroot))111 root_dir = os.path.join(
112 publisher._config.distroroot, test_archive.owner.name,
113 test_archive.name)
114 self.assertFalse(os.path.exists(root_dir))
114 self.assertEqual(test_archive.status, ArchiveStatus.DELETED)115 self.assertEqual(test_archive.status, ArchiveStatus.DELETED)
116 self.assertEqual(test_archive.publish, False)
117
118 # Trying to delete it again won't fail, in the corner case where
119 # some admin manually deleted the repo.
120 publisher.deleteArchive()
115121
116 def testPublishPartner(self):122 def testPublishPartner(self):
117 """Test that a partner package is published to the right place."""123 """Test that a partner package is published to the right place."""
@@ -122,8 +128,7 @@
122 pub_config.poolroot, pub_config.temproot, self.logger)128 pub_config.poolroot, pub_config.temproot, self.logger)
123 publisher = Publisher(129 publisher = Publisher(
124 self.logger, pub_config, disk_pool, archive)130 self.logger, pub_config, disk_pool, archive)
125 pub_source = self.getPubSource(archive=archive,131 self.getPubSource(archive=archive, filecontent="I am partner")
126 filecontent="I am partner")
127132
128 publisher.A_publish(False)133 publisher.A_publish(False)
129134
@@ -161,7 +166,7 @@
161 disk_pool = DiskPool(166 disk_pool = DiskPool(
162 pub_config.poolroot, pub_config.temproot, self.logger)167 pub_config.poolroot, pub_config.temproot, self.logger)
163 publisher = Publisher(self.logger, pub_config, disk_pool, archive)168 publisher = Publisher(self.logger, pub_config, disk_pool, archive)
164 pub_source = self.getPubSource(169 self.getPubSource(
165 archive=archive, filecontent="I am partner",170 archive=archive, filecontent="I am partner",
166 status=PackagePublishingStatus.PENDING)171 status=PackagePublishingStatus.PENDING)
167172
@@ -248,8 +253,7 @@
248 self.logger, self.config, self.disk_pool,253 self.logger, self.config, self.disk_pool,
249 self.ubuntutest.main_archive)254 self.ubuntutest.main_archive)
250255
251 pub_source = self.getPubSource(256 self.getPubSource(status=PackagePublishingStatus.PUBLISHED)
252 status=PackagePublishingStatus.PUBLISHED)
253257
254 # a new non-careful publisher won't find anything to publish, thus258 # a new non-careful publisher won't find anything to publish, thus
255 # no pockets will be *dirtied*.259 # no pockets will be *dirtied*.
@@ -269,7 +273,7 @@
269 self.logger, self.config, self.disk_pool,273 self.logger, self.config, self.disk_pool,
270 self.ubuntutest.main_archive)274 self.ubuntutest.main_archive)
271275
272 pub_source = self.getPubSource(276 self.getPubSource(
273 filecontent='Hello world',277 filecontent='Hello world',
274 status=PackagePublishingStatus.PUBLISHED)278 status=PackagePublishingStatus.PUBLISHED)
275279
@@ -412,17 +416,17 @@
412 ubuntu = getUtility(IDistributionSet)['ubuntu']416 ubuntu = getUtility(IDistributionSet)['ubuntu']
413417
414 spiv = person_set.getByName('spiv')418 spiv = person_set.getByName('spiv')
415 spiv_archive = archive_set.new(419 archive_set.new(
416 owner=spiv, distribution=ubuntu, purpose=ArchivePurpose.PPA)420 owner=spiv, distribution=ubuntu, purpose=ArchivePurpose.PPA)
417 name16 = person_set.getByName('name16')421 name16 = person_set.getByName('name16')
418 name16_archive = archive_set.new(422 archive_set.new(
419 owner=name16, distribution=ubuntu, purpose=ArchivePurpose.PPA)423 owner=name16, distribution=ubuntu, purpose=ArchivePurpose.PPA)
420424
421 pub_source = self.getPubSource(425 self.getPubSource(
422 sourcename="foo", filename="foo_1.dsc", filecontent='Hello world',426 sourcename="foo", filename="foo_1.dsc", filecontent='Hello world',
423 status=PackagePublishingStatus.PENDING, archive=spiv.archive)427 status=PackagePublishingStatus.PENDING, archive=spiv.archive)
424428
425 pub_source = self.getPubSource(429 self.getPubSource(
426 sourcename="foo", filename="foo_1.dsc", filecontent='Hello world',430 sourcename="foo", filename="foo_1.dsc", filecontent='Hello world',
427 status=PackagePublishingStatus.PUBLISHED, archive=name16.archive)431 status=PackagePublishingStatus.PUBLISHED, archive=name16.archive)
428432
@@ -485,7 +489,7 @@
485 pub_source = self.getPubSource(489 pub_source = self.getPubSource(
486 sourcename="foo", filename="foo_1.dsc", filecontent='Hello world',490 sourcename="foo", filename="foo_1.dsc", filecontent='Hello world',
487 status=PackagePublishingStatus.PENDING, archive=cprov.archive)491 status=PackagePublishingStatus.PENDING, archive=cprov.archive)
488 pub_bin = self.getPubBinaries(492 self.getPubBinaries(
489 pub_source=pub_source,493 pub_source=pub_source,
490 description=" My leading spaces are normalised to a single "494 description=" My leading spaces are normalised to a single "
491 "space but not trailing. \n It does nothing, "495 "space but not trailing. \n It does nothing, "
@@ -496,7 +500,7 @@
496 ignored_source = self.getPubSource(500 ignored_source = self.getPubSource(
497 status=PackagePublishingStatus.DELETED,501 status=PackagePublishingStatus.DELETED,
498 archive=cprov.archive)502 archive=cprov.archive)
499 pub_udeb = self.getPubBinaries(503 self.getPubBinaries(
500 pub_source=ignored_source, binaryname='bingo',504 pub_source=ignored_source, binaryname='bingo',
501 description='nice udeb', format=BinaryPackageFormat.UDEB)[0]505 description='nice udeb', format=BinaryPackageFormat.UDEB)[0]
502506
@@ -627,27 +631,27 @@
627 # waiting to be deleted, each in different pockets. The deleted631 # waiting to be deleted, each in different pockets. The deleted
628 # source in the release pocket should not be processed. We'll632 # source in the release pocket should not be processed. We'll
629 # also have a binary waiting to be deleted.633 # also have a binary waiting to be deleted.
630 published_source = self.getPubSource(634 self.getPubSource(
631 pocket=PackagePublishingPocket.RELEASE,635 pocket=PackagePublishingPocket.RELEASE,
632 status=PackagePublishingStatus.PUBLISHED)636 status=PackagePublishingStatus.PUBLISHED)
633637
634 deleted_source_in_release_pocket = self.getPubSource(638 self.getPubSource(
635 pocket=PackagePublishingPocket.RELEASE,639 pocket=PackagePublishingPocket.RELEASE,
636 status=PackagePublishingStatus.DELETED)640 status=PackagePublishingStatus.DELETED)
637641
638 removed_source = self.getPubSource(642 self.getPubSource(
639 scheduleddeletiondate=UTC_NOW,643 scheduleddeletiondate=UTC_NOW,
640 dateremoved=UTC_NOW,644 dateremoved=UTC_NOW,
641 pocket=PackagePublishingPocket.UPDATES,645 pocket=PackagePublishingPocket.UPDATES,
642 status=PackagePublishingStatus.DELETED)646 status=PackagePublishingStatus.DELETED)
643647
644 deleted_source = self.getPubSource(648 self.getPubSource(
645 pocket=PackagePublishingPocket.SECURITY,649 pocket=PackagePublishingPocket.SECURITY,
646 status=PackagePublishingStatus.DELETED)650 status=PackagePublishingStatus.DELETED)
647651
648 deleted_binary = self.getPubBinaries(652 self.getPubBinaries(
649 pocket=PackagePublishingPocket.BACKPORTS,653 pocket=PackagePublishingPocket.BACKPORTS,
650 status=PackagePublishingStatus.DELETED)[0]654 status=PackagePublishingStatus.DELETED)
651655
652 # Run the deletion detection.656 # Run the deletion detection.
653 publisher.A2_markPocketsWithDeletionsDirty()657 publisher.A2_markPocketsWithDeletionsDirty()
@@ -699,19 +703,19 @@
699703
700 # Create pending deletions in RELEASE, BACKPORTS, SECURITY and704 # Create pending deletions in RELEASE, BACKPORTS, SECURITY and
701 # UPDATES pockets.705 # UPDATES pockets.
702 deleted_source = self.getPubSource(706 self.getPubSource(
703 pocket=PackagePublishingPocket.RELEASE,707 pocket=PackagePublishingPocket.RELEASE,
704 status=PackagePublishingStatus.DELETED)708 status=PackagePublishingStatus.DELETED)
705709
706 deleted_binary = self.getPubBinaries(710 self.getPubBinaries(
707 pocket=PackagePublishingPocket.BACKPORTS,711 pocket=PackagePublishingPocket.BACKPORTS,
708 status=PackagePublishingStatus.DELETED)[0]712 status=PackagePublishingStatus.DELETED)[0]
709713
710 allowed_source_deletion = self.getPubSource(714 self.getPubSource(
711 pocket=PackagePublishingPocket.SECURITY,715 pocket=PackagePublishingPocket.SECURITY,
712 status=PackagePublishingStatus.DELETED)716 status=PackagePublishingStatus.DELETED)
713717
714 allowed_binary_deletion = self.getPubBinaries(718 self.getPubBinaries(
715 pocket=PackagePublishingPocket.UPDATES,719 pocket=PackagePublishingPocket.UPDATES,
716 status=PackagePublishingStatus.DELETED)[0]720 status=PackagePublishingStatus.DELETED)[0]
717721
@@ -781,7 +785,7 @@
781 self.logger, self.config, self.disk_pool,785 self.logger, self.config, self.disk_pool,
782 self.ubuntutest.main_archive)786 self.ubuntutest.main_archive)
783787
784 pub_source = self.getPubSource(filecontent='Hello world')788 self.getPubSource(filecontent='Hello world')
785789
786 publisher.A_publish(False)790 publisher.A_publish(False)
787 publisher.C_doFTPArchive(False)791 publisher.C_doFTPArchive(False)
@@ -866,8 +870,7 @@
866 archive_publisher = getPublisher(870 archive_publisher = getPublisher(
867 cprov.archive, allowed_suites, self.logger)871 cprov.archive, allowed_suites, self.logger)
868872
869 pub_source = self.getPubSource(873 self.getPubSource(filecontent='Hello world', archive=cprov.archive)
870 filecontent='Hello world', archive=cprov.archive)
871874
872 archive_publisher.A_publish(False)875 archive_publisher.A_publish(False)
873 self.layer.txn.commit()876 self.layer.txn.commit()
@@ -970,8 +973,7 @@
970 allowed_suites = []973 allowed_suites = []
971 archive_publisher = getPublisher(974 archive_publisher = getPublisher(
972 named_ppa, allowed_suites, self.logger)975 named_ppa, allowed_suites, self.logger)
973 pub_source = self.getPubSource(976 self.getPubSource(filecontent='Hello world', archive=named_ppa)
974 filecontent='Hello world', archive=named_ppa)
975977
976 archive_publisher.A_publish(False)978 archive_publisher.A_publish(False)
977 self.layer.txn.commit()979 self.layer.txn.commit()
@@ -1080,7 +1082,7 @@
1080 Publish files in pool, generate archive indexes and release files.1082 Publish files in pool, generate archive indexes and release files.
1081 """1083 """
1082 self.setupPublisher(archive)1084 self.setupPublisher(archive)
1083 pub_source = self.getPubSource(archive=archive)1085 self.getPubSource(archive=archive)
10841086
1085 self.archive_publisher.A_publish(False)1087 self.archive_publisher.A_publish(False)
1086 transaction.commit()1088 transaction.commit()

Subscribers

People subscribed via source and target branches

to status/vote changes: