← Back to team overview

launchpad-reviewers team mailing list archive

[Merge] lp:~laney/launchpad/proposed-notautomatic into lp:launchpad

 

Iain Lane has proposed merging lp:~laney/launchpad/proposed-notautomatic into lp:launchpad.

Requested reviews:
  Launchpad code reviewers (launchpad-reviewers)
Related bugs:
  Bug #1016776 in Launchpad itself: "Users are offered updates to packages in -proposed"
  https://bugs.launchpad.net/launchpad/+bug/1016776

For more details, see:
https://code.launchpad.net/~laney/launchpad/proposed-notautomatic/+merge/113921

Summary
=======

Users are offered upgrades to packages in -proposed, which is often used as a staging/test area. It would be better if they were able to opt in on a per-package basis.

Proposed Fix
============

Add a flag which causes the -proposed Eelease files for a series to contain the NotAutomatic and ButAutomaticUpgrade flags, so that users are not offered updates by apt to packages in -propoed, but are offered upgrades within it.

QA Plans
========

Upload (or copy) a package into quantal-proposed with proposed_not_automatic = False. Confirm that the Release file for quantal-proposed does not contain NotAutomatic or ButAutomaticUpgrades. Set the flag to True and upload another package (to cause the Release files to be re-written) and check that the Release file contains NotAutomatic: yes and ButAutomaticUpgrades: yes.
-- 
https://code.launchpad.net/~laney/launchpad/proposed-notautomatic/+merge/113921
Your team Launchpad code reviewers is requested to review the proposed merge of lp:~laney/launchpad/proposed-notautomatic into lp:launchpad.
=== modified file 'lib/lp/archivepublisher/publishing.py'
--- lib/lp/archivepublisher/publishing.py	2012-06-29 08:40:05 +0000
+++ lib/lp/archivepublisher/publishing.py	2012-07-09 08:16:26 +0000
@@ -569,8 +569,10 @@
         release_file["Components"] = " ".join(
             reorder_components(all_components))
         release_file["Description"] = drsummary
-        if (pocket == PackagePublishingPocket.BACKPORTS and
-            distroseries.backports_not_automatic):
+        if ((pocket == PackagePublishingPocket.BACKPORTS and
+            distroseries.backports_not_automatic) or
+           (pocket == PackagePublishingPocket.PROPOSED and
+            distroseries.proposed_not_automatic)):
             release_file["NotAutomatic"] = "yes"
             release_file["ButAutomaticUpgrades"] = "yes"
 

=== modified file 'lib/lp/archivepublisher/tests/test_publisher.py'
--- lib/lp/archivepublisher/tests/test_publisher.py	2012-01-03 01:02:12 +0000
+++ lib/lp/archivepublisher/tests/test_publisher.py	2012-07-09 08:16:26 +0000
@@ -64,6 +64,7 @@
 
 RELEASE = PackagePublishingPocket.RELEASE
 BACKPORTS = PackagePublishingPocket.BACKPORTS
+PROPOSED = PackagePublishingPocket.PROPOSED
 
 
 class TestPublisherBase(TestNativePublishingBase):
@@ -1021,13 +1022,14 @@
         # The Label: field should be set to the archive displayname
         self.assertEqual('Partner archive', release['label'])
 
-    def testReleaseFileForNotAutomaticBackports(self):
-        # Test Release file writing for series with NotAutomatic backports.
+    def releaseFileNotAutomatic(self, pocket, flag_value, set_flag):
+        # Set up Release file writing for series/pocket with NotAutomatic
+        # ButAutomaticUpgrades.
         publisher = Publisher(
             self.logger, self.config, self.disk_pool,
             self.ubuntutest.main_archive)
         self.getPubSource(filecontent='Hello world', pocket=RELEASE)
-        self.getPubSource(filecontent='Hello world', pocket=BACKPORTS)
+        self.getPubSource(filecontent='Hello world', pocket=pocket)
 
         publisher.A_publish(True)
         publisher.C_writeIndexes(False)
@@ -1039,20 +1041,34 @@
             with open(release_path) as release_file:
                 return release_file.read().splitlines()
 
-        # When backports_not_automatic is unset, no Release files have
+        # When flag is unset, no Release files have
         # NotAutomatic: yes.
-        self.assertEqual(False, self.breezy_autotest.backports_not_automatic)
-        publisher.D_writeReleaseFiles(False)
-        self.assertNotIn("NotAutomatic: yes", get_release(RELEASE))
-        self.assertNotIn("NotAutomatic: yes", get_release(BACKPORTS))
-
-        # But with the flag set, -backports Release files gain
-        # NotAutomatic: yes and ButAutomaticUpgrades: yes.
-        self.breezy_autotest.backports_not_automatic = True
-        publisher.D_writeReleaseFiles(False)
-        self.assertNotIn("NotAutomatic: yes", get_release(RELEASE))
-        self.assertIn("NotAutomatic: yes", get_release(BACKPORTS))
-        self.assertIn("ButAutomaticUpgrades: yes", get_release(BACKPORTS))
+        self.assertEqual(False, flag_value)
+        publisher.D_writeReleaseFiles(False)
+        self.assertNotIn("NotAutomatic: yes", get_release(RELEASE))
+        self.assertNotIn("NotAutomatic: yes", get_release(pocket))
+
+        # But with the flag set, the pocket's Release files gain NotAutomatic:
+        # yes and ButAutomaticUpgrades: yes.
+        set_flag(True)
+        publisher.D_writeReleaseFiles(False)
+        self.assertNotIn("NotAutomatic: yes", get_release(RELEASE))
+        self.assertIn("NotAutomatic: yes", get_release(pocket))
+        self.assertIn("ButAutomaticUpgrades: yes", get_release(pocket))
+
+    def testReleaseFileForNotAutomaticBackports(self):
+        def set_flag(value):
+            self.breezy_autotest.backports_not_automatic = value
+        self.releaseFileNotAutomatic(BACKPORTS,
+                self.breezy_autotest.backports_not_automatic,
+                set_flag)
+
+    def testReleaseFileForNotAutomaticProposed(self):
+        def set_flag(value):
+            self.breezy_autotest.proposed_not_automatic = value
+        self.releaseFileNotAutomatic(PROPOSED,
+                self.breezy_autotest.proposed_not_automatic,
+                set_flag)
 
     def testReleaseFileForI18n(self):
         """Test Release file writing for translated package descriptions."""

=== modified file 'lib/lp/registry/configure.zcml'
--- lib/lp/registry/configure.zcml	2012-06-29 02:15:05 +0000
+++ lib/lp/registry/configure.zcml	2012-07-09 08:16:26 +0000
@@ -263,6 +263,7 @@
             permission="launchpad.Edit"
             set_attributes="displayname title summary description driver
                             backports_not_automatic
+                            proposed_not_automatic
                             include_long_descriptions"/>
 
         <!-- NB: check with SABDFL before modifying these, there is potential to

=== modified file 'lib/lp/registry/interfaces/distroseries.py'
--- lib/lp/registry/interfaces/distroseries.py	2012-07-03 08:04:35 +0000
+++ lib/lp/registry/interfaces/distroseries.py	2012-07-09 08:16:26 +0000
@@ -365,6 +365,18 @@
             automatically upgrade within backports, but not into it.
             """))
 
+    proposed_not_automatic = Bool(
+        title=_("Don't upgrade to packages in proposed automatically"),
+        required=True,
+        description=_("""
+            Set NotAutomatic: yes and ButAutomaticUpgrades: yes in Release
+            files generated for the proposed pocket pre-release. This tells apt
+            to automatically upgrade within proposed, but not into it.
+            Pre-release, this pocket is used as a package staging area for
+            archive consistency purposes. Post-release, users would like to be
+            able to opt-in to testing proposed updates on a per-package basis.
+            """))
+
     include_long_descriptions = exported(
         Bool(
             title=_(

=== modified file 'lib/lp/registry/model/distroseries.py'
--- lib/lp/registry/model/distroseries.py	2012-07-05 09:43:58 +0000
+++ lib/lp/registry/model/distroseries.py	2012-07-09 08:16:26 +0000
@@ -244,6 +244,7 @@
         notNull=False, default=None)
     language_pack_full_export_requested = BoolCol(notNull=True, default=False)
     backports_not_automatic = BoolCol(notNull=True, default=False)
+    proposed_not_automatic = BoolCol(notNull=True, default=False)
     include_long_descriptions = BoolCol(notNull=True, default=True)
 
     language_packs = SQLMultipleJoin(

=== modified file 'lib/lp/soyuz/scripts/initialize_distroseries.py'
--- lib/lp/soyuz/scripts/initialize_distroseries.py	2012-07-05 09:43:58 +0000
+++ lib/lp/soyuz/scripts/initialize_distroseries.py	2012-07-09 08:16:26 +0000
@@ -367,6 +367,9 @@
         self.distroseries.backports_not_automatic = any(
             parent.backports_not_automatic
                 for parent in self.derivation_parents)
+        self.distroseries.proposed_not_automatic = any(
+            parent.proposed_not_automatic
+                for parent in self.derivation_parents)
         self.distroseries.include_long_descriptions = any(
             parent.include_long_descriptions
                 for parent in self.derivation_parents)

=== modified file 'lib/lp/soyuz/scripts/tests/test_initialize_distroseries.py'
--- lib/lp/soyuz/scripts/tests/test_initialize_distroseries.py	2012-04-23 22:18:46 +0000
+++ lib/lp/soyuz/scripts/tests/test_initialize_distroseries.py	2012-07-09 08:16:26 +0000
@@ -5,12 +5,6 @@
 
 __metaclass__ = type
 
-import os
-import subprocess
-import sys
-
-from testtools.content import Content
-from testtools.content_type import UTF8_TEXT
 import transaction
 from zope.component import getUtility
 
@@ -21,7 +15,6 @@
     )
 from lp.registry.interfaces.distroseriesparent import IDistroSeriesParentSet
 from lp.registry.interfaces.pocket import PackagePublishingPocket
-from lp.services.config import config
 from lp.services.database.lpstorm import IStore
 from lp.services.features.testing import FeatureFixture
 from lp.soyuz.enums import (
@@ -89,6 +82,7 @@
         if existing_format_selection is None:
             spfss_utility.add(parent, format_selection)
         parent.backports_not_automatic = True
+        parent.proposed_not_automatic = True
         parent.include_long_descriptions = False
         self._populate_parent(parent, parent_das, packages, pocket)
         return parent, parent_das
@@ -593,6 +587,7 @@
             SourcePackageFormat.FORMAT_1_0))
         # Other configuration bits are copied too.
         self.assertTrue(child.backports_not_automatic)
+        self.assertTrue(child.proposed_not_automatic)
         self.assertFalse(child.include_long_descriptions)
 
     def test_initialize(self):


Follow ups