launchpad-reviewers team mailing list archive
-
launchpad-reviewers team
-
Mailing list archive
-
Message #09411
[Merge] lp:~cjwatson/launchpad/fix-check-copy-permissions into lp:launchpad
Colin Watson has proposed merging lp:~cjwatson/launchpad/fix-check-copy-permissions into lp:launchpad.
Requested reviews:
Launchpad code reviewers (launchpad-reviewers)
Related bugs:
Bug #795005 in Launchpad itself: "Asynchronous PPA copying with default series OOPSes"
https://bugs.launchpad.net/launchpad/+bug/795005
For more details, see:
https://code.launchpad.net/~cjwatson/launchpad/fix-check-copy-permissions/+merge/112832
== Summary ==
William Grant pointed out that my change in https://code.launchpad.net/~cjwatson/launchpad/copy-packages-with-default-series/+merge/112557 has incorrect semantics, because it checks the component of the source rather than of the target in the "series is None" (i.e. copy to same series as source) case.
== Proposed fix ==
Check the target component instead. This requires using archive.getPublishedSources; with some care, we can consolidate duplicate code again.
== LOC Rationale ==
+32. Same rationale as https://code.launchpad.net/~cjwatson/launchpad/copy-packages-with-default-series/+merge/112557 - removing delayed copies, which this is part of the road to, is worth at least 1100 lines.
== Tests ==
bin/test -vvct test_archive.TestSyncSource
== Demo and Q/A ==
As https://code.launchpad.net/~cjwatson/launchpad/copy-packages-with-default-series/+merge/112557, but copy into a distribution archive with various permissions. PPA publications are always in main, so the ability to copy a new version of a package in universe with only universe component upload permissions is a good indicator that this is working.
== Lint ==
''Paste output from `make lint` here - if there's lint related to your code, fix it so that you don't have to paste it here!''
--
https://code.launchpad.net/~cjwatson/launchpad/fix-check-copy-permissions/+merge/112832
Your team Launchpad code reviewers is requested to review the proposed merge of lp:~cjwatson/launchpad/fix-check-copy-permissions into lp:launchpad.
=== modified file 'lib/lp/soyuz/scripts/packagecopier.py'
--- lib/lp/soyuz/scripts/packagecopier.py 2012-06-29 01:03:10 +0000
+++ lib/lp/soyuz/scripts/packagecopier.py 2012-06-29 18:46:21 +0000
@@ -16,6 +16,7 @@
'update_files_privacy',
]
+from itertools import repeat
from operator import attrgetter
import os
import tempfile
@@ -231,34 +232,32 @@
# the destination (archive, component, pocket). This check is done
# here rather than in the security adapter because it requires more
# info than is available in the security adapter.
+ sourcepackagenames = [
+ source.sourcepackagerelease.sourcepackagename for source in sources]
if series is None:
# Use each source's series as the destination for that source.
- for source in sources:
- reason = archive.checkUpload(
- person, source.distroseries,
- source.sourcepackagerelease.sourcepackagename,
- source.component, pocket, strict_component=True)
-
- if reason is not None:
- raise CannotCopy(reason)
+ series_iter = map(attrgetter("distroseries"), sources)
else:
- sourcepackagenames = [
- source.sourcepackagerelease.sourcepackagename
- for source in sources]
- for spn in set(sourcepackagenames):
- package = series.getSourcePackage(spn)
- destination_component = package.latest_published_component
-
- # If destination_component is not None, make sure the person
- # has upload permission for this component. Otherwise, any
- # upload permission on this archive will do.
- strict_component = destination_component is not None
- reason = archive.checkUpload(
- person, series, spn, destination_component, pocket,
- strict_component=strict_component)
-
- if reason is not None:
- raise CannotCopy(reason)
+ series_iter = repeat(series)
+ for spn, dest_series in set(zip(sourcepackagenames, series_iter)):
+ ancestries = archive.getPublishedSources(
+ name=spn.name, exact_match=True, status=active_publishing_status,
+ distroseries=dest_series, pocket=pocket)
+ try:
+ destination_component = ancestries[0].component
+ except IndexError:
+ destination_component = None
+
+ # If destination_component is not None, make sure the person
+ # has upload permission for this component. Otherwise, any
+ # upload permission on this archive will do.
+ strict_component = destination_component is not None
+ reason = archive.checkUpload(
+ person, dest_series, spn, destination_component, pocket,
+ strict_component=strict_component)
+
+ if reason is not None:
+ raise CannotCopy(reason)
class CopyChecker:
=== modified file 'lib/lp/soyuz/tests/test_archive.py'
--- lib/lp/soyuz/tests/test_archive.py 2012-06-28 12:21:01 +0000
+++ lib/lp/soyuz/tests/test_archive.py 2012-06-29 18:46:21 +0000
@@ -2548,6 +2548,39 @@
[source.distroseries for source in sources],
[copy_job.target_distroseries for copy_job in copy_jobs])
+ def test_copyPackages_with_default_distroseries_and_override(self):
+ # If to_series is None, copyPackages checks permissions based on the
+ # component in the target archive, not the component in the source
+ # archive.
+ (source, source_archive, source_name, target_archive, to_pocket,
+ to_series, version) = self._setup_copy_data(
+ target_purpose=ArchivePurpose.PRIMARY)
+ sources = [source]
+ uploader = self.factory.makePerson()
+ main = self.factory.makeComponent(name="main")
+ universe = self.factory.makeComponent(name="universe")
+ ComponentSelection(distroseries=to_series, component=main)
+ ComponentSelection(distroseries=to_series, component=universe)
+ with person_logged_in(target_archive.owner):
+ target_archive.newComponentUploader(uploader, universe)
+ self.factory.makeSourcePackagePublishingHistory(
+ distroseries=source.distroseries, archive=target_archive,
+ pocket=to_pocket, status=PackagePublishingStatus.PUBLISHED,
+ sourcepackagename=source_name, version="%s~1" % version,
+ component=universe)
+ names = [source.sourcepackagerelease.sourcepackagename.name
+ for source in sources]
+
+ with person_logged_in(uploader):
+ target_archive.copyPackages(
+ names, source_archive, to_pocket.name, include_binaries=False,
+ person=uploader)
+
+ # There should be a copy job with the correct target series.
+ job_source = getUtility(IPlainPackageCopyJobSource)
+ copy_job = job_source.getActiveJobs(target_archive).one()
+ self.assertEqual(source.distroseries, copy_job.target_distroseries)
+
class TestgetAllPublishedBinaries(TestCaseWithFactory):
Follow ups