← Back to team overview

launchpad-reviewers team mailing list archive

[Merge] lp:~rvb/launchpad/distro-overlay2-bug-758908-dependencies into lp:launchpad/db-devel

 

Raphaël Victor Badin has proposed merging lp:~rvb/launchpad/distro-overlay2-bug-758908-dependencies into lp:launchpad/db-devel with lp:~rvb/launchpad/distro-overlay2-bug-758908 as a prerequisite.

Requested reviews:
  Launchpad code reviewers (launchpad-reviewers)
Related bugs:
  Bug #758908 in Launchpad itself: "Allow a derived distribution to work as an overlay archive like a PPA works"
  https://bugs.launchpad.net/launchpad/+bug/758908

For more details, see:
https://code.launchpad.net/~rvb/launchpad/distro-overlay2-bug-758908-dependencies/+merge/61110

This branch adds overlay support to DistroSeriesParent. The code that generates sources.list now also traverses the tree of DSPs for an overlay until it hits a non-overlay parent.

= Tests =
./bin/test -cvv test_distroseriesparent test_getFlattenedOverlayTree
./bin/test -cvv test_distroseriesparent test_getFlattenedOverlayTree_empty
./bin/test -cvv test_archive test_searches_overlays

= QA =
On DF:
Create an overlay distribution (manually for now).
Create a build in an overlay distribution and make sure the sources.list includes the parent's details.
-- 
https://code.launchpad.net/~rvb/launchpad/distro-overlay2-bug-758908-dependencies/+merge/61110
Your team Launchpad code reviewers is requested to review the proposed merge of lp:~rvb/launchpad/distro-overlay2-bug-758908-dependencies into lp:launchpad/db-devel.
=== modified file 'lib/lp/registry/interfaces/distroseriesparent.py'
--- lib/lp/registry/interfaces/distroseriesparent.py	2011-05-16 14:01:26 +0000
+++ lib/lp/registry/interfaces/distroseriesparent.py	2011-05-16 14:01:27 +0000
@@ -75,3 +75,20 @@
 
         :param parent_series: An `IDistroseries`
         """
+
+    def getFlattenedOverlayTree(derived_series):
+        """Get the list of DistroSeriesParents corresponding to the
+        flattened overlay tree.
+
+        :param parent_series: An `IDistroseries`
+
+        For instance, given the following structure:
+               /-o- parent11 -o- parent12 --- parent13
+        series
+               \-o- parent21 --- parent22
+                \--- parent 31
+        -o-: overlay
+        ---: not overlay
+        The result would be:
+        [dsp(series, parent11), dsp(series, parent12), dsp(series, parent21)]
+        """

=== modified file 'lib/lp/registry/model/distroseriesparent.py'
--- lib/lp/registry/model/distroseriesparent.py	2011-05-16 14:01:26 +0000
+++ lib/lp/registry/model/distroseriesparent.py	2011-05-16 14:01:27 +0000
@@ -16,6 +16,7 @@
     Reference,
     Storm,
     )
+from zope.component import getUtility
 from zope.interface import implements
 
 from canonical.database.enumcol import EnumCol
@@ -23,6 +24,11 @@
     IMasterStore,
     IStore,
     )
+from canonical.launchpad.webapp.interfaces import (
+    DEFAULT_FLAVOR,
+    IStoreSelector,
+    MAIN_STORE,
+    )
 from lp.registry.interfaces.distroseriesparent import (
     IDistroSeriesParent,
     IDistroSeriesParentSet,
@@ -87,3 +93,26 @@
         return store.find(
             DistroSeriesParent,
             DistroSeriesParent.parent_series_id == parent_series.id)
+
+    def getFlattenedOverlayTree(self, derived_series):
+        """See `IDistroSeriesParentSet`."""
+        self.getByDerivedSeries(derived_series)
+        rec_overlay_query = '''
+        WITH RECURSIVE t_parents(parent_series) AS (
+                SELECT parent_series
+                FROM DistroSeriesParent
+                WHERE derived_series=? AND
+                    is_overlay = True
+            UNION ALL
+                SELECT dsp.parent_series
+                FROM DistroSeriesParent dsp, t_parents p
+                WHERE dsp.derived_series = p.parent_series AND
+                    dsp.is_overlay = True
+        )
+        SELECT * FROM t_parents;
+        '''
+        store = getUtility(IStoreSelector).get(MAIN_STORE, DEFAULT_FLAVOR)
+        res = store.execute(
+            rec_overlay_query, (derived_series.id, )).get_all()
+        return store.find(DistroSeriesParent,
+            DistroSeriesParent.parent_series_id.is_in(r[0] for r in res))

=== modified file 'lib/lp/registry/tests/test_distroseriesparent.py'
--- lib/lp/registry/tests/test_distroseriesparent.py	2011-05-16 14:01:26 +0000
+++ lib/lp/registry/tests/test_distroseriesparent.py	2011-05-16 14:01:27 +0000
@@ -159,3 +159,66 @@
         dsp.derived_series.distribution.owner = person
         with person_logged_in(person):
             self.assertCanEdit(dsp)
+
+
+class TestOverlayTree(TestCaseWithFactory):
+    """Test the overlay tree."""
+
+    layer = DatabaseFunctionalLayer
+
+    def test_getFlattenedOverlayTree(self):
+        #        /-o- parent11 -o- parent12 --- parent13
+        # series
+        #        \-o- parent21 -o- parent22
+        #         \--- parent31
+        #          \-o- parent41
+        # -o-: overlay
+        # ---: not overlay
+        distroseries = self.factory.makeDistroSeries()
+        parent11 = self.factory.makeDistroSeries()
+        parent12 = self.factory.makeDistroSeries()
+        parent21 = self.factory.makeDistroSeries()
+        main_component = getUtility(IComponentSet).ensure('main')
+        # series -> parent11
+        s_p11 = self.factory.makeDistroSeriesParent(
+            derived_series=distroseries, parent_series=parent11,
+            initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        # parent11 -> parent12
+        p11_p12 = self.factory.makeDistroSeriesParent(
+            derived_series=parent11, parent_series=parent12,
+            initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        # parent12 -> parent13
+        self.factory.makeDistroSeriesParent(derived_series=parent12,
+            initialized=True, is_overlay=False)
+        # series -> parent2
+        s_p2 = self.factory.makeDistroSeriesParent(
+            derived_series=distroseries, parent_series=parent21,
+            initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        # parent21 -> parent22
+        p21_p22 = self.factory.makeDistroSeriesParent(
+            derived_series=parent21, initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        # series -> parent31
+        self.factory.makeDistroSeriesParent(derived_series=distroseries,
+            initialized=True, is_overlay=False)
+        # series -> parent41
+        s_p4 = self.factory.makeDistroSeriesParent(
+            derived_series=distroseries, initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        overlays = getUtility(
+            IDistroSeriesParentSet).getFlattenedOverlayTree(distroseries)
+
+        self.assertContentEqual(
+            [s_p11, p11_p12, s_p2, p21_p22, s_p4], overlays)
+
+    def test_getFlattenedOverlayTree_empty(self):
+        distroseries = self.factory.makeDistroSeries()
+        self.factory.makeDistroSeriesParent(derived_series=distroseries,
+            initialized=True, is_overlay=False)
+        overlays = getUtility(
+            IDistroSeriesParentSet).getFlattenedOverlayTree(distroseries)
+
+        self.assertTrue(overlays.is_empty())

=== modified file 'lib/lp/soyuz/adapters/archivedependencies.py'
--- lib/lp/soyuz/adapters/archivedependencies.py	2011-01-12 13:06:21 +0000
+++ lib/lp/soyuz/adapters/archivedependencies.py	2011-05-16 14:01:27 +0000
@@ -42,7 +42,9 @@
 import traceback
 
 from lazr.uri import URI
+from zope.component import getUtility
 
+from lp.registry.interfaces.distroseriesparent import IDistroSeriesParentSet
 from lp.registry.interfaces.pocket import (
     PackagePublishingPocket,
     pocketsuffix,
@@ -51,9 +53,7 @@
     ArchivePurpose,
     PackagePublishingStatus,
     )
-from lp.soyuz.interfaces.archive import (
-    ALLOW_RELEASE_BUILDS,
-    )
+from lp.soyuz.interfaces.archive import ALLOW_RELEASE_BUILDS
 
 
 component_dependencies = {
@@ -61,7 +61,7 @@
     'restricted': ['main', 'restricted'],
     'universe': ['main', 'universe'],
     'multiverse': ['main', 'restricted', 'universe', 'multiverse'],
-    'partner' : ['partner'],
+    'partner': ['partner'],
     }
 
 pocket_dependencies = {
@@ -173,6 +173,12 @@
             archive, component, pocket)
         deps.extend(primary_dependencies)
 
+    # Add dependencies for overlay archives.
+    for dsp in getUtility(
+        IDistroSeriesParentSet).getFlattenedOverlayTree(distro_series):
+        dep_archive = dsp.parent_series.distribution.main_archive
+        deps.append((dep_archive, dsp.pocket, (dsp.component.name, )))
+
     return deps
 
 

=== modified file 'lib/lp/soyuz/tests/test_archive.py'
--- lib/lp/soyuz/tests/test_archive.py	2011-05-10 10:39:53 +0000
+++ lib/lp/soyuz/tests/test_archive.py	2011-05-16 14:01:27 +0000
@@ -1428,6 +1428,26 @@
         self.assertDep('i386', 'foo-main', [main_bins[0]])
         self.assertDep('i386', 'foo-universe', [universe_bins[0]])
 
+    def test_searches_overlays(self):
+        # Dependencies can be found in overlays.
+        # series --overlay--> parent1 --overlay--> parent2
+        main_component = getUtility(IComponentSet)['main']
+        dsp1 = self.factory.makeDistroSeriesParent(
+            derived_series=self.publisher.distroseries,
+            initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        dsp2 = self.factory.makeDistroSeriesParent(
+            derived_series=dsp1.parent_series,
+            initialized=True, is_overlay=True,
+            pocket=PackagePublishingPocket.RELEASE, component=main_component)
+        main_bins = self.publisher.getPubBinaries(
+            binaryname='foo-main',
+            archive=dsp2.parent_series.distribution.main_archive,
+            component='main',
+            status=PackagePublishingStatus.PUBLISHED)
+
+        self.assertDep('i386', 'foo-main', [main_bins[0]])
+
 
 class TestComponents(TestCaseWithFactory):