← Back to team overview

launchpad-reviewers team mailing list archive

[Merge] lp:~flacoste/launchpad/bug-365098 into lp:launchpad

 

Francis J. Lacoste has proposed merging lp:~flacoste/launchpad/bug-365098 into lp:launchpad.

Requested reviews:
  Launchpad code reviewers (launchpad-reviewers)

For more details, see:
https://code.launchpad.net/~flacoste/launchpad/bug-365098/+merge/63301

Allow distribution and archive owners as well as package uploader to set the
official package branch link. Remove the ubuntu-branches celebrity.
-- 
https://code.launchpad.net/~flacoste/launchpad/bug-365098/+merge/63301
Your team Launchpad code reviewers is requested to review the proposed merge of lp:~flacoste/launchpad/bug-365098 into lp:launchpad.
=== modified file 'database/sampledata/current-dev.sql'
--- database/sampledata/current-dev.sql	2011-05-04 16:46:43 +0000
+++ database/sampledata/current-dev.sql	2011-06-02 21:27:44 +0000
@@ -843,6 +843,9 @@
 
 
 
+
+
+
 SET SESSION AUTHORIZATION DEFAULT;
 
 ALTER TABLE account DISABLE TRIGGER ALL;
@@ -1828,8 +1831,6 @@
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243624, 'Commercial Subscription Approvers', 243623, NULL, 'commercial-approvers', NULL, NULL, NULL, NULL, 1, NULL, '2008-06-27 14:49:38.676264', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243625, 'PPA key guard', NULL, NULL, 'ppa-key-guard', NULL, NULL, NULL, NULL, 1, NULL, '2008-11-04 12:59:26.965843', NULL, NULL, NULL, true, 1, '', NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436241);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243626, 'Launchpad Users', 12, NULL, 'launchpad-users', NULL, NULL, NULL, NULL, 2, NULL, '2008-11-26 18:19:53.547918', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
-INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243627, 'Ubuntu-branches-owner', NULL, NULL, 'ubuntu-branches-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-03-17 07:26:14.024613', NULL, NULL, NULL, false, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436242);
-INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243628, 'Ubuntu branches', 243627, 'Celebrity team that controls official source package branches.', 'ubuntu-branches', NULL, NULL, NULL, NULL, 3, NULL, '2009-03-17 07:27:39.306182', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243629, 'Ubuntu Security Team', 4, NULL, 'ubuntu-security', NULL, NULL, NULL, NULL, 2, NULL, '2009-07-14 20:23:59.698654', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243630, 'HWDB Team', 16, NULL, 'hwdb-team', NULL, NULL, NULL, NULL, 3, NULL, '2009-07-09 09:12:39.400351', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243631, 'Techboard Owner', NULL, NULL, 'techboard-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-08-04 10:50:39.370018', NULL, NULL, NULL, true, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436243);
@@ -3800,6 +3801,13 @@
 ALTER TABLE bugsubscriptionfilterimportance ENABLE TRIGGER ALL;
 
 
+ALTER TABLE bugsubscriptionfiltermute DISABLE TRIGGER ALL;
+
+
+
+ALTER TABLE bugsubscriptionfiltermute ENABLE TRIGGER ALL;
+
+
 ALTER TABLE bugsubscriptionfilterstatus DISABLE TRIGGER ALL;
 
 
@@ -4236,6 +4244,13 @@
 ALTER TABLE distroseriespackagecache ENABLE TRIGGER ALL;
 
 
+ALTER TABLE distroseriesparent DISABLE TRIGGER ALL;
+
+
+
+ALTER TABLE distroseriesparent ENABLE TRIGGER ALL;
+
+
 ALTER TABLE emailaddress DISABLE TRIGGER ALL;
 
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (1, 'mark@xxxxxxxxxxx', 1, 4, '2006-10-16 18:31:43.540582', 11);
@@ -4316,7 +4331,6 @@
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (78, 'bac@xxxxxxxxxxxxx', 243623, 4, '2008-06-27 14:49:11.149508', 2436231);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (79, 'admin@xxxxxxxxxxxxx', 16, 2, '2008-08-05 12:01:32.086327', 161);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (80, 'ppa-key-guard@xxxxxxxxxxxxx', 243625, 4, '2008-11-04 12:59:26.965843', 2436241);
-INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (81, 'ubuntu-branches-owner@xxxxxxxxxxx', 243627, 4, '2009-03-17 07:26:14.024613', 2436242);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (82, 'techboard-owner@xxxxxxxxxxx', 243631, 4, '2009-08-04 10:50:39.383407', 2436243);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (93, 'software-center-agent@xxxxxxxxxxx', 243651, 4, '2010-07-12 09:48:27.198885', 243637);
 
@@ -5271,8 +5285,6 @@
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243624, 'Commercial Subscription Approvers', 243623, NULL, 'commercial-approvers', NULL, NULL, NULL, NULL, 1, NULL, '2008-06-27 14:49:38.676264', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243625, 'PPA key guard', NULL, NULL, 'ppa-key-guard', NULL, NULL, NULL, NULL, 1, NULL, '2008-11-04 12:59:26.965843', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, true, 1, '', NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436241);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243626, 'Launchpad Users', 12, NULL, 'launchpad-users', NULL, NULL, NULL, NULL, 2, NULL, '2008-11-26 18:19:53.547918', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
-INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243627, 'Ubuntu-branches-owner', NULL, NULL, 'ubuntu-branches-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-03-17 07:26:14.024613', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436242);
-INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243628, 'Ubuntu branches', 243627, 'Celebrity team that controls official source package branches.', 'ubuntu-branches', NULL, NULL, NULL, NULL, 3, NULL, '2009-03-17 07:27:39.306182', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243629, 'Ubuntu Security Team', 4, NULL, 'ubuntu-security', NULL, NULL, NULL, NULL, 2, NULL, '2009-07-14 20:23:59.698654', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243630, 'HWDB Team', 16, NULL, 'hwdb-team', NULL, NULL, NULL, NULL, 3, NULL, '2009-07-09 09:12:39.400351', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243631, 'Techboard Owner', NULL, NULL, 'techboard-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-08-04 10:50:39.370018', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, true, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436243);

=== modified file 'database/sampledata/current.sql'
--- database/sampledata/current.sql	2011-05-04 16:46:43 +0000
+++ database/sampledata/current.sql	2011-06-02 21:27:44 +0000
@@ -843,6 +843,9 @@
 
 
 
+
+
+
 SET SESSION AUTHORIZATION DEFAULT;
 
 ALTER TABLE account DISABLE TRIGGER ALL;
@@ -1828,8 +1831,6 @@
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243624, 'Commercial Subscription Approvers', 243623, NULL, 'commercial-approvers', NULL, NULL, NULL, NULL, 1, NULL, '2008-06-27 14:49:38.676264', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243625, 'PPA key guard', NULL, NULL, 'ppa-key-guard', NULL, NULL, NULL, NULL, 1, NULL, '2008-11-04 12:59:26.965843', NULL, NULL, NULL, true, 1, '', NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436241);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243626, 'Launchpad Users', 12, NULL, 'launchpad-users', NULL, NULL, NULL, NULL, 2, NULL, '2008-11-26 18:19:53.547918', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
-INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243627, 'Ubuntu-branches-owner', NULL, NULL, 'ubuntu-branches-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-03-17 07:26:14.024613', NULL, NULL, NULL, false, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436242);
-INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243628, 'Ubuntu branches', 243627, 'Celebrity team that controls official source package branches.', 'ubuntu-branches', NULL, NULL, NULL, NULL, 3, NULL, '2009-03-17 07:27:39.306182', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243629, 'Ubuntu Security Team', 4, NULL, 'ubuntu-security', NULL, NULL, NULL, NULL, 2, NULL, '2009-07-14 20:23:59.698654', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243630, 'HWDB Team', 16, NULL, 'hwdb-team', NULL, NULL, NULL, NULL, 3, NULL, '2009-07-09 09:12:39.400351', NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243631, 'Techboard Owner', NULL, NULL, 'techboard-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-08-04 10:50:39.370018', NULL, NULL, NULL, true, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436243);
@@ -3736,6 +3737,13 @@
 ALTER TABLE bugsubscriptionfilterimportance ENABLE TRIGGER ALL;
 
 
+ALTER TABLE bugsubscriptionfiltermute DISABLE TRIGGER ALL;
+
+
+
+ALTER TABLE bugsubscriptionfiltermute ENABLE TRIGGER ALL;
+
+
 ALTER TABLE bugsubscriptionfilterstatus DISABLE TRIGGER ALL;
 
 
@@ -4169,6 +4177,13 @@
 ALTER TABLE distroseriespackagecache ENABLE TRIGGER ALL;
 
 
+ALTER TABLE distroseriesparent DISABLE TRIGGER ALL;
+
+
+
+ALTER TABLE distroseriesparent ENABLE TRIGGER ALL;
+
+
 ALTER TABLE emailaddress DISABLE TRIGGER ALL;
 
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (1, 'mark@xxxxxxxxxxx', 1, 4, '2006-10-16 18:31:43.540582', 11);
@@ -4249,7 +4264,6 @@
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (78, 'bac@xxxxxxxxxxxxx', 243623, 4, '2008-06-27 14:49:11.149508', 2436231);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (79, 'admin@xxxxxxxxxxxxx', 16, 2, '2008-08-05 12:01:32.086327', 161);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (80, 'ppa-key-guard@xxxxxxxxxxxxx', 243625, 4, '2008-11-04 12:59:26.965843', 2436241);
-INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (81, 'ubuntu-branches-owner@xxxxxxxxxxx', 243627, 4, '2009-03-17 07:26:14.024613', 2436242);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (82, 'techboard-owner@xxxxxxxxxxx', 243631, 4, '2009-08-04 10:50:39.383407', 2436243);
 INSERT INTO emailaddress (id, email, person, status, date_created, account) VALUES (93, 'software-center-agent@xxxxxxxxxxx', 243651, 4, '2010-07-12 09:48:27.198885', 243637);
 
@@ -5203,8 +5217,6 @@
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243624, 'Commercial Subscription Approvers', 243623, NULL, 'commercial-approvers', NULL, NULL, NULL, NULL, 1, NULL, '2008-06-27 14:49:38.676264', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243625, 'PPA key guard', NULL, NULL, 'ppa-key-guard', NULL, NULL, NULL, NULL, 1, NULL, '2008-11-04 12:59:26.965843', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, true, 1, '', NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436241);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243626, 'Launchpad Users', 12, NULL, 'launchpad-users', NULL, NULL, NULL, NULL, 2, NULL, '2008-11-26 18:19:53.547918', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
-INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243627, 'Ubuntu-branches-owner', NULL, NULL, 'ubuntu-branches-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-03-17 07:26:14.024613', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436242);
-INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243628, 'Ubuntu branches', 243627, 'Celebrity team that controls official source package branches.', 'ubuntu-branches', NULL, NULL, NULL, NULL, 3, NULL, '2009-03-17 07:27:39.306182', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243629, 'Ubuntu Security Team', 4, NULL, 'ubuntu-security', NULL, NULL, NULL, NULL, 2, NULL, '2009-07-14 20:23:59.698654', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243630, 'HWDB Team', 16, NULL, 'hwdb-team', NULL, NULL, NULL, NULL, 3, NULL, '2009-07-09 09:12:39.400351', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, false, NULL, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, NULL);
 INSERT INTO lp_person (id, displayname, teamowner, teamdescription, name, language, fti, defaultmembershipperiod, defaultrenewalperiod, subscriptionpolicy, merged, datecreated, addressline1, addressline2, organization, city, province, country, postcode, phone, homepage_content, icon, mugshot, hide_email_addresses, creation_rationale, creation_comment, registrant, logo, renewal_policy, personal_standing, personal_standing_reason, mail_resumption_date, mailing_list_auto_subscribe_policy, mailing_list_receive_duplicates, visibility, verbose_bugnotifications, account) VALUES (243631, 'Techboard Owner', NULL, NULL, 'techboard-owner', NULL, NULL, NULL, NULL, 1, NULL, '2009-08-04 10:50:39.370018', NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, true, 1, NULL, NULL, NULL, 10, 0, NULL, NULL, 1, true, 1, true, 2436243);

=== modified file 'lib/canonical/launchpad/interfaces/_schema_circular_imports.py'
--- lib/canonical/launchpad/interfaces/_schema_circular_imports.py	2011-05-17 14:27:34 +0000
+++ lib/canonical/launchpad/interfaces/_schema_circular_imports.py	2011-06-02 21:27:44 +0000
@@ -160,7 +160,11 @@
     IProjectGroup,
     IProjectGroupSet,
     )
-from lp.registry.interfaces.sourcepackage import ISourcePackage
+from lp.registry.interfaces.sourcepackage import (
+    ISourcePackage,
+    ISourcePackageEdit,
+    ISourcePackagePublic,
+    )
 from lp.registry.interfaces.ssh import ISSHKey
 from lp.registry.interfaces.teammembership import ITeamMembership
 from lp.registry.interfaces.wikiname import IWikiName
@@ -226,9 +230,9 @@
 IBranch['landing_candidates'].value_type.schema = IBranchMergeProposal
 IBranch['landing_targets'].value_type.schema = IBranchMergeProposal
 IBranch['linkBug'].queryTaggedValue(
-    LAZR_WEBSERVICE_EXPORTED)['params']['bug'].schema= IBug
+    LAZR_WEBSERVICE_EXPORTED)['params']['bug'].schema = IBug
 IBranch['linkSpecification'].queryTaggedValue(
-    LAZR_WEBSERVICE_EXPORTED)['params']['spec'].schema= ISpecification
+    LAZR_WEBSERVICE_EXPORTED)['params']['spec'].schema = ISpecification
 IBranch['product'].schema = IProduct
 
 patch_plain_parameter_type(
@@ -243,9 +247,9 @@
     LAZR_WEBSERVICE_EXPORTED)['return_type'].schema = IBranchSubscription
 IBranch['subscriptions'].value_type.schema = IBranchSubscription
 IBranch['unlinkBug'].queryTaggedValue(
-    LAZR_WEBSERVICE_EXPORTED)['params']['bug'].schema= IBug
+    LAZR_WEBSERVICE_EXPORTED)['params']['bug'].schema = IBug
 IBranch['unlinkSpecification'].queryTaggedValue(
-    LAZR_WEBSERVICE_EXPORTED)['params']['spec'].schema= ISpecification
+    LAZR_WEBSERVICE_EXPORTED)['params']['spec'].schema = ISpecification
 
 patch_entry_return_type(IBranch, '_createMergeProposal', IBranchMergeProposal)
 patch_plain_parameter_type(
@@ -316,17 +320,17 @@
     LAZR_WEBSERVICE_EXPORTED)[
         'return_type'].value_type.schema = IBinaryPackageBuild
 
-ISourcePackage['distroseries'].schema = IDistroSeries
-ISourcePackage['productseries'].schema = IProductSeries
-ISourcePackage['getBranch'].queryTaggedValue(
+ISourcePackagePublic['distroseries'].schema = IDistroSeries
+ISourcePackagePublic['productseries'].schema = IProductSeries
+ISourcePackagePublic['getBranch'].queryTaggedValue(
     LAZR_WEBSERVICE_EXPORTED)[
         'params']['pocket'].vocabulary = PackagePublishingPocket
-ISourcePackage['getBranch'].queryTaggedValue(
+ISourcePackagePublic['getBranch'].queryTaggedValue(
     LAZR_WEBSERVICE_EXPORTED)['return_type'].schema = IBranch
-ISourcePackage['setBranch'].queryTaggedValue(
+ISourcePackageEdit['setBranch'].queryTaggedValue(
     LAZR_WEBSERVICE_EXPORTED)[
         'params']['pocket'].vocabulary = PackagePublishingPocket
-ISourcePackage['setBranch'].queryTaggedValue(
+ISourcePackageEdit['setBranch'].queryTaggedValue(
     LAZR_WEBSERVICE_EXPORTED)['params']['branch'].schema = IBranch
 patch_reference_property(ISourcePackage, 'distribution', IDistribution)
 

=== modified file 'lib/canonical/launchpad/security.py'
--- lib/canonical/launchpad/security.py	2011-05-27 21:12:25 +0000
+++ lib/canonical/launchpad/security.py	2011-06-02 21:27:44 +0000
@@ -79,10 +79,6 @@
     )
 from lp.code.interfaces.codereviewvote import ICodeReviewVoteReference
 from lp.code.interfaces.diff import IPreviewDiff
-from lp.code.interfaces.seriessourcepackagebranch import (
-    IMakeOfficialBranchLinks,
-    ISeriesSourcePackageBranch,
-    )
 from lp.code.interfaces.sourcepackagerecipe import ISourcePackageRecipe
 from lp.code.interfaces.sourcepackagerecipebuild import (
     ISourcePackageRecipeBuild,
@@ -122,6 +118,7 @@
     INameBlacklistSet,
     )
 from lp.registry.interfaces.packaging import IPackaging
+from lp.registry.interfaces.pocket import PackagePublishingPocket
 from lp.registry.interfaces.person import (
     IPerson,
     IPersonSet,
@@ -2505,38 +2502,6 @@
         return user.in_admin or user.in_ubuntu_techboard
 
 
-class LinkOfficialSourcePackageBranches(AuthorizationBase):
-    """Who can source packages to their official branches?
-
-    Only members of the ~ubuntu-branches celebrity team! Or admins.
-    """
-
-    permission = 'launchpad.Edit'
-    usedfor = IMakeOfficialBranchLinks
-
-    def checkUnauthenticated(self):
-        return False
-
-    def checkAuthenticated(self, user):
-        return user.in_ubuntu_branches or user.in_admin
-
-
-class ChangeOfficialSourcePackageBranchLinks(AuthorizationBase):
-    """Who can change the links from source packages to their branches?
-
-    Only members of the ~ubuntu-branches celebrity team! Or admins.
-    """
-
-    permission = 'launchpad.Edit'
-    usedfor = ISeriesSourcePackageBranch
-
-    def checkUnauthenticated(self):
-        return False
-
-    def checkAuthenticated(self, user):
-        return user.in_ubuntu_branches or user.in_admin
-
-
 class ViewPackageset(AnonymousAuthorization):
     """Anyone can view an IPackageset."""
     usedfor = IPackageset
@@ -2611,3 +2576,25 @@
 
 class ViewPublisherConfig(AdminByAdminsTeam):
     usedfor = IPublisherConfig
+
+
+class EditSourcePackage(AuthorizationBase):
+    permission = 'launchpad.Edit'
+    usedfor = ISourcePackage
+
+    def checkAuthenticated(self, user):
+        """Anyone who can upload a package can edit it."""
+        if user.in_admin:
+            return True
+
+        distribution = self.obj.distribution
+        if user.inTeam(distribution.owner):
+            return True
+
+        # checkUpload() returns the reason the user can't upload
+        # or None if they are allowed.
+        reason = distribution.main_archive.checkUpload(
+            user.person, self.obj.distroseries, self.obj.sourcepackagename,
+            component=None, pocket=PackagePublishingPocket.RELEASE,
+            strict_component=False)
+        return reason is None

=== modified file 'lib/lp/app/utilities/celebrities.py'
--- lib/lp/app/utilities/celebrities.py	2011-05-27 21:12:25 +0000
+++ lib/lp/app/utilities/celebrities.py	2011-06-02 21:27:44 +0000
@@ -101,7 +101,7 @@
     This descriptor maintains a list of names so code can detect
     if a given person is a celebrity for special handling.
     """
-    names = set() # Populated by the constructor.
+    names = set()  # Populated by the constructor.
 
     def __init__(self, name):
         PersonCelebrityDescriptor.names.add(name)
@@ -153,7 +153,6 @@
     savannah_tracker = CelebrityDescriptor(IBugTrackerSet, 'savannah')
     sourceforge_tracker = CelebrityDescriptor(IBugTrackerSet, 'sf')
     ubuntu = CelebrityDescriptor(IDistributionSet, 'ubuntu')
-    ubuntu_branches = PersonCelebrityDescriptor('ubuntu-branches')
     ubuntu_bugzilla = CelebrityDescriptor(IBugTrackerSet, 'ubuntu-bugzilla')
     ubuntu_security = PersonCelebrityDescriptor('ubuntu-security')
     ubuntu_techboard = PersonCelebrityDescriptor('techboard')

=== modified file 'lib/lp/code/browser/tests/test_branchlisting.py'
--- lib/lp/code/browser/tests/test_branchlisting.py	2010-10-26 15:47:24 +0000
+++ lib/lp/code/browser/tests/test_branchlisting.py	2011-06-02 21:27:44 +0000
@@ -16,7 +16,6 @@
     Desc,
     )
 from zope.component import getUtility
-from zope.security.proxy import removeSecurityProxy
 
 from canonical.launchpad.testing.pages import (
     extract_text,
@@ -32,8 +31,8 @@
     SourcePackageBranchesView,
     )
 from lp.code.enums import BranchVisibilityRule
-from lp.code.interfaces.seriessourcepackagebranch import (
-    IMakeOfficialBranchLinks,
+from lp.code.model.seriessourcepackagebranch import (
+    SeriesSourcePackageBranchSet,
     )
 from lp.code.model.branch import Branch
 from lp.registry.interfaces.person import (
@@ -270,15 +269,12 @@
             for i in range(branch_count)]
 
         official = []
-        # We don't care about who can make things official, so get rid of the
-        # security proxy.
-        series_set = removeSecurityProxy(getUtility(IMakeOfficialBranchLinks))
         # Sort the pocket items so RELEASE is last, and thus first popped.
         pockets = sorted(PackagePublishingPocket.items, reverse=True)
         for i in range(official_count):
             branch = branches.pop()
             pocket = pockets.pop()
-            sspb = series_set.new(
+            SeriesSourcePackageBranchSet.new(
                 distroseries, pocket, self.sourcepackagename,
                 branch, branch.owner)
             official.append(branch)
@@ -354,8 +350,7 @@
     def test_package_development_focus(self):
         # Check the bzr_identity of a development focus package branch.
         branch = self.factory.makePackageBranch()
-        series_set = removeSecurityProxy(getUtility(IMakeOfficialBranchLinks))
-        sspb = series_set.new(
+        SeriesSourcePackageBranchSet.new(
             branch.distroseries, PackagePublishingPocket.RELEASE,
             branch.sourcepackagename, branch, branch.owner)
         identity = "lp://dev/%s/%s" % (

=== modified file 'lib/lp/code/configure.zcml'
--- lib/lp/code/configure.zcml	2011-05-13 16:08:03 +0000
+++ lib/lp/code/configure.zcml	2011-06-02 21:27:44 +0000
@@ -398,21 +398,10 @@
   <class
       class="lp.code.model.seriessourcepackagebranch.SeriesSourcePackageBranch">
     <allow interface="lp.code.interfaces.seriessourcepackagebranch.ISeriesSourcePackageBranch"/>
-    <require
-        permission="launchpad.Edit"
-        set_schema="lp.code.interfaces.seriessourcepackagebranch.ISeriesSourcePackageBranch"/>
   </class>
 
   <securedutility
      class="lp.code.model.seriessourcepackagebranch.SeriesSourcePackageBranchSet"
-     provides="lp.code.interfaces.seriessourcepackagebranch.IMakeOfficialBranchLinks">
-    <allow interface="lp.code.interfaces.seriessourcepackagebranch.IMakeOfficialBranchLinks"/>
-    <require
-       permission="launchpad.Edit"
-       interface="lp.code.interfaces.seriessourcepackagebranch.IMakeOfficialBranchLinks"/>
-  </securedutility>
-  <securedutility
-     class="lp.code.model.seriessourcepackagebranch.SeriesSourcePackageBranchSet"
      provides="lp.code.interfaces.seriessourcepackagebranch.IFindOfficialBranchLinks">
     <allow interface="lp.code.interfaces.seriessourcepackagebranch.IFindOfficialBranchLinks"/>
   </securedutility>

=== modified file 'lib/lp/code/interfaces/seriessourcepackagebranch.py'
--- lib/lp/code/interfaces/seriessourcepackagebranch.py	2011-03-03 01:13:47 +0000
+++ lib/lp/code/interfaces/seriessourcepackagebranch.py	2011-06-02 21:27:44 +0000
@@ -9,7 +9,6 @@
 __all__ = [
     'IFindOfficialBranchLinks',
     'ISeriesSourcePackageBranch',
-    'IMakeOfficialBranchLinks',
     ]
 
 
@@ -33,17 +32,20 @@
     id = Int()
 
     distroseries = Choice(
-        title=_("Series"), required=True, vocabulary='DistroSeries')
+        title=_("Series"), required=True, readonly=True,
+        vocabulary='DistroSeries')
 
     pocket = Choice(
-        title=_("Pocket"), required=True, vocabulary=PackagePublishingPocket)
+        title=_("Pocket"), required=True, readonly=True,
+        vocabulary=PackagePublishingPocket)
 
     sourcepackage = Attribute('The source package')
 
     suite_sourcepackage = Attribute('The suite source package')
 
     sourcepackagename = Choice(
-        title=_("Package"), required=True, vocabulary='SourcePackageName')
+        title=_("Package"), required=True,
+        readonly=True, vocabulary='SourcePackageName')
 
     branchID = Attribute('The ID of the branch.')
     branch = Choice(
@@ -52,7 +54,8 @@
     registrant = Attribute("The person who registered this link.")
 
     date_created = Datetime(
-        title=_("When the branch was linked to the distribution suite."))
+        title=_("When the branch was linked to the distribution suite."),
+        readonly=True)
 
 
 class IFindOfficialBranchLinks(Interface):
@@ -86,22 +89,3 @@
         :param distrosourcepackage: An `IDistributionSourcePackage`.
         :return: An `IResultSet` of `ISeriesSourcePackageBranch` objects.
         """
-
-
-class IMakeOfficialBranchLinks(Interface):
-    """A set of links from source packages in distribution suites to branches.
-
-    This doesn't really make sense as an interface, but is provided to match
-    the rest of Launchpad.
-    """
-
-    def delete(sourcepackage, pocket):
-        """Remove the SeriesSourcePackageBranch for sourcepackage and pocket.
-
-        :param sourcepackage: An `ISourcePackage`.
-        :param pocket: A `PackagePublishingPocket` enum item.
-        """
-
-    def new(distroseries, pocket, sourcepackagename, branch, registrant,
-            date_created=None):
-        """Link a source package in a distribution suite to a branch."""

=== modified file 'lib/lp/code/model/seriessourcepackagebranch.py'
--- lib/lp/code/model/seriessourcepackagebranch.py	2011-03-03 01:13:47 +0000
+++ lib/lp/code/model/seriessourcepackagebranch.py	2011-06-02 21:27:44 +0000
@@ -32,7 +32,6 @@
     )
 from lp.code.interfaces.seriessourcepackagebranch import (
     IFindOfficialBranchLinks,
-    IMakeOfficialBranchLinks,
     ISeriesSourcePackageBranch,
     )
 from lp.registry.interfaces.pocket import PackagePublishingPocket
@@ -44,7 +43,6 @@
     __storm_table__ = 'SeriesSourcePackageBranch'
     implements(ISeriesSourcePackageBranch)
 
-
     id = Int(primary=True)
     distroseriesID = Int('distroseries')
     distroseries = Reference(distroseriesID, 'DistroSeries.id')
@@ -85,11 +83,12 @@
 class SeriesSourcePackageBranchSet:
     """See `ISeriesSourcePackageBranchSet`."""
 
-    implements(IFindOfficialBranchLinks, IMakeOfficialBranchLinks)
+    implements(IFindOfficialBranchLinks)
 
-    def new(self, distroseries, pocket, sourcepackagename, branch, registrant,
+    @staticmethod
+    def new(distroseries, pocket, sourcepackagename, branch, registrant,
             date_created=None):
-        """See `IMakeOfficialBranchLinks`."""
+        """Link a source package in a distribution suite to a branch."""
         if date_created is None:
             date_created = datetime.now(pytz.UTC)
         sspb = SeriesSourcePackageBranch(
@@ -136,8 +135,13 @@
             SeriesSourcePackageBranch.sourcepackagename ==
             sourcepackagename.id)
 
-    def delete(self, sourcepackage, pocket):
-        """See `IMakeOfficialBranchLinks`."""
+    @staticmethod
+    def delete(sourcepackage, pocket):
+        """Remove the SeriesSourcePackageBranch for sourcepackage and pocket.
+
+        :param sourcepackage: An `ISourcePackage`.
+        :param pocket: A `PackagePublishingPocket` enum item.
+        """
         store = getUtility(IStoreSelector).get(MAIN_STORE, MASTER_FLAVOR)
         distroseries = sourcepackage.distroseries
         sourcepackagename = sourcepackage.sourcepackagename

=== modified file 'lib/lp/code/tests/helpers.py'
--- lib/lp/code/tests/helpers.py	2011-05-27 19:53:20 +0000
+++ lib/lp/code/tests/helpers.py	2011-06-02 21:27:44 +0000
@@ -34,8 +34,8 @@
     )
 from lp.code.interfaces.linkedbranch import ICanHasLinkedBranch
 from lp.code.interfaces.revision import IRevisionSet
-from lp.code.interfaces.seriessourcepackagebranch import (
-    IMakeOfficialBranchLinks,
+from lp.code.model.seriessourcepackagebranch import (
+    SeriesSourcePackageBranchSet
     )
 from lp.registry.interfaces.pocket import PackagePublishingPocket
 from lp.registry.interfaces.series import SeriesStatus
@@ -89,7 +89,6 @@
 
     :return: a dict of objects to put into local scope.
     """
-    result = {}
     eric = factory.makePerson(
         name='eric', displayname='Eric the Viking',
         email='eric@xxxxxxxxxxx', password='test')
@@ -135,10 +134,7 @@
     # It is possible for the param to be None, so reset to the factory
     # generated one.
     sourcepackagename = source_package.sourcepackagename
-    # We don't care about who can make things official, so get rid of the
-    # security proxy.
-    series_set = removeSecurityProxy(getUtility(IMakeOfficialBranchLinks))
-    series_set.new(
+    SeriesSourcePackageBranchSet.new(
         distro_series, pocket, sourcepackagename, branch, branch.owner)
     return branch
 
@@ -177,9 +173,6 @@
         for i in range(branch_count)]
 
     official = []
-    # We don't care about who can make things official, so get rid of the
-    # security proxy.
-    series_set = removeSecurityProxy(getUtility(IMakeOfficialBranchLinks))
     # Sort the pocket items so RELEASE is last, and thus first popped.
     pockets = sorted(PackagePublishingPocket.items, reverse=True)
     # Since there can be only one link per pocket, max out the number of
@@ -187,7 +180,7 @@
     for i in range(min(official_count, len(pockets))):
         branch = branches.pop()
         pocket = pockets.pop()
-        sspb = series_set.new(
+        SeriesSourcePackageBranchSet.new(
             series, pocket, sourcepackagename, branch, branch.owner)
         official.append(branch)
 

=== modified file 'lib/lp/code/tests/test_seriessourcepackagebranch.py'
--- lib/lp/code/tests/test_seriessourcepackagebranch.py	2011-05-27 21:12:25 +0000
+++ lib/lp/code/tests/test_seriessourcepackagebranch.py	2011-06-02 21:27:44 +0000
@@ -11,22 +11,15 @@
 import pytz
 import transaction
 from zope.component import getUtility
-from zope.security.interfaces import Unauthorized
-from zope.security.proxy import removeSecurityProxy
 
-from canonical.launchpad.ftests import (
-    ANONYMOUS,
-    login,
-    login_person,
-    logout,
-    )
 from canonical.testing.layers import DatabaseFunctionalLayer
-from lp.app.interfaces.launchpad import ILaunchpadCelebrities
 from lp.code.interfaces.seriessourcepackagebranch import (
     IFindOfficialBranchLinks,
-    IMakeOfficialBranchLinks,
     ISeriesSourcePackageBranch,
     )
+from lp.code.model.seriessourcepackagebranch import (
+    SeriesSourcePackageBranchSet,
+    )
 from lp.registry.interfaces.pocket import PackagePublishingPocket
 from lp.testing import TestCaseWithFactory
 
@@ -36,25 +29,15 @@
 
     layer = DatabaseFunctionalLayer
 
-    def setUp(self):
-        TestCaseWithFactory.setUp(self)
-        person = self.factory.makePerson()
-        ubuntu_branches = getUtility(ILaunchpadCelebrities).ubuntu_branches
-        removeSecurityProxy(ubuntu_branches).addMember(
-            person, ubuntu_branches.teamowner)
-        login_person(person)
-        self.addCleanup(logout)
-
     def test_new_sets_attributes(self):
-        # ISeriesSourcePackageBranchSet.new sets all the defined attributes on
+        # SeriesSourcePackageBranchSet.new sets all the defined attributes on
         # the interface.
-        series_set = getUtility(IMakeOfficialBranchLinks)
         distroseries = self.factory.makeDistroRelease()
         sourcepackagename = self.factory.makeSourcePackageName()
         registrant = self.factory.makePerson()
         branch = self.factory.makeAnyBranch()
         now = datetime.now(pytz.UTC)
-        sspb = series_set.new(
+        sspb = SeriesSourcePackageBranchSet.new(
             distroseries, PackagePublishingPocket.RELEASE, sourcepackagename,
             branch, registrant, now)
         self.assertEqual(distroseries, sspb.distroseries)
@@ -65,28 +48,26 @@
         self.assertEqual(now, sspb.date_created)
 
     def test_new_inserts_into_db(self):
-        # IMakeOfficialBranchLinks.new inserts the new object into the
+        # SeriesSourcePackageBranchSet.new inserts the new object into the
         # database, giving it an ID.
-        series_set = getUtility(IMakeOfficialBranchLinks)
         distroseries = self.factory.makeDistroRelease()
         sourcepackagename = self.factory.makeSourcePackageName()
         registrant = self.factory.makePerson()
         branch = self.factory.makeAnyBranch()
-        sspb = series_set.new(
+        sspb = SeriesSourcePackageBranchSet.new(
             distroseries, PackagePublishingPocket.RELEASE, sourcepackagename,
             branch, registrant)
         transaction.commit()
         self.assertIsNot(sspb.id, None)
 
     def test_new_returns_ISeriesSourcePackageBranch(self):
-        # IMakeOfficialBranchLinks.new returns an
+        # SeriesSourcePackageBranchSet.new returns an
         # ISeriesSourcePackageBranch, know what I mean?
-        series_set = getUtility(IMakeOfficialBranchLinks)
         distroseries = self.factory.makeDistroRelease()
         sourcepackagename = self.factory.makeSourcePackageName()
         registrant = self.factory.makePerson()
         branch = self.factory.makeAnyBranch()
-        sspb = series_set.new(
+        sspb = SeriesSourcePackageBranchSet.new(
             distroseries, PackagePublishingPocket.RELEASE, sourcepackagename,
             branch, registrant)
         self.assertProvides(sspb, ISeriesSourcePackageBranch)
@@ -102,10 +83,9 @@
         # IFindOfficialBranchLinks.findForSourcePackage returns a result
         # set of links from the source package. Each link is an
         # ISeriesSourcePackageBranch.
-        make_branch_links = getUtility(IMakeOfficialBranchLinks)
         branch = self.factory.makePackageBranch()
         package = branch.sourcepackage
-        make_branch_links.new(
+        SeriesSourcePackageBranchSet.new(
             package.distroseries, PackagePublishingPocket.RELEASE,
             package.sourcepackagename, branch, self.factory.makePerson())
         find_branch_links = getUtility(IFindOfficialBranchLinks)
@@ -119,10 +99,9 @@
         # IFindOfficialBranchLinks.findForBranch returns a result set of
         # links from the branch to source packages & pockets. Each link is an
         # ISeriesSourcePackageBranch.
-        make_branch_links = getUtility(IMakeOfficialBranchLinks)
         branch = self.factory.makePackageBranch()
         package = branch.sourcepackage
-        make_branch_links.new(
+        SeriesSourcePackageBranchSet.new(
             package.distroseries, PackagePublishingPocket.RELEASE,
             package.sourcepackagename, branch, self.factory.makePerson())
         find_branch_links = getUtility(IFindOfficialBranchLinks)
@@ -135,35 +114,17 @@
     def test_delete(self):
         # `delete` ensures that there is no branch associated with that
         # sourcepackage and pocket.
-        make_branch_links = getUtility(IMakeOfficialBranchLinks)
         branch = self.factory.makePackageBranch()
         package = branch.sourcepackage
-        make_branch_links.new(
+        SeriesSourcePackageBranchSet.new(
             package.distroseries, PackagePublishingPocket.RELEASE,
             package.sourcepackagename, branch, self.factory.makePerson())
-        make_branch_links.delete(package, PackagePublishingPocket.RELEASE)
+        SeriesSourcePackageBranchSet.delete(
+            package, PackagePublishingPocket.RELEASE)
         find_branch_links = getUtility(IFindOfficialBranchLinks)
         self.assertEqual(
             [], list(find_branch_links.findForSourcePackage(package)))
 
-    def test_cannot_edit_branch_link(self):
-        # You can only edit an ISeriesSourcePackageBranch if you have edit
-        # permissions, which almost no one has.
-        series_set = getUtility(IMakeOfficialBranchLinks)
-        distroseries = self.factory.makeDistroRelease()
-        sourcepackagename = self.factory.makeSourcePackageName()
-        registrant = self.factory.makePerson()
-        branch = self.factory.makeAnyBranch()
-        sspb = series_set.new(
-            distroseries, PackagePublishingPocket.RELEASE, sourcepackagename,
-            branch, registrant)
-        logout()
-        login(ANONYMOUS)
-        self.assertRaises(
-            Unauthorized, setattr, sspb, 'pocket',
-            PackagePublishingPocket.BACKPORTS)
-
 
 def test_suite():
     return unittest.TestLoader().loadTestsFromName(__name__)
-

=== modified file 'lib/lp/registry/configure.zcml'
--- lib/lp/registry/configure.zcml	2011-05-31 07:11:18 +0000
+++ lib/lp/registry/configure.zcml	2011-06-02 21:27:44 +0000
@@ -1585,15 +1585,17 @@
     </securedutility>
 
     <!-- SourcePackage -->
-
     <class
         class="lp.registry.model.sourcepackage.SourcePackage">
         <allow
-            interface="lp.registry.interfaces.sourcepackage.ISourcePackage"/>
+            interface="lp.registry.interfaces.sourcepackage.ISourcePackagePublic"/>
         <allow
             interface="lp.bugs.interfaces.bugtarget.IHasBugHeat"/>
         <allow
             interface="lp.soyuz.interfaces.buildrecords.IHasBuildRecords"/>
+        <require
+            permission="launchpad.Edit"
+            interface="lp.registry.interfaces.sourcepackage.ISourcePackageEdit"/>
     </class>
     <securedutility
         component="lp.registry.model.sourcepackage.SourcePackage"

=== modified file 'lib/lp/registry/interfaces/role.py'
--- lib/lp/registry/interfaces/role.py	2011-05-27 21:25:58 +0000
+++ lib/lp/registry/interfaces/role.py	2011-06-02 21:27:44 +0000
@@ -112,9 +112,6 @@
     in_rosetta_experts = Bool(
         title=_("True if this person is a rosetta expert."),
         required=True, readonly=True)
-    in_ubuntu_branches = Bool(
-        title=_("True if this person is on the Ubuntu branches team."),
-        required=True, readonly=True)
     in_ubuntu_security = Bool(
         title=_("True if this person is on the Ubuntu security team."),
         required=True, readonly=True)

=== modified file 'lib/lp/registry/interfaces/sourcepackage.py'
--- lib/lp/registry/interfaces/sourcepackage.py	2011-05-12 14:55:54 +0000
+++ lib/lp/registry/interfaces/sourcepackage.py	2011-06-02 21:27:44 +0000
@@ -9,6 +9,8 @@
 
 __all__ = [
     'ISourcePackage',
+    'ISourcePackagePublic',
+    'ISourcePackageEdit',
     'ISourcePackageFactory',
     'SourcePackageFileType',
     'SourcePackageType',
@@ -65,26 +67,21 @@
     )
 
 
-class ISourcePackage(IBugTarget, IHasBranches, IHasMergeProposals,
-                     IHasOfficialBugTags, IHasCodeImports,
-                     IHasTranslationImports, IHasTranslationTemplates):
-    """A SourcePackage. See the MagicSourcePackage specification. This
-    interface preserves as much as possible of the old SourcePackage
-    interface from the SourcePackage table, with the new table-less
-    implementation."""
-
-    export_as_webservice_entry()
+class ISourcePackagePublic(IBugTarget, IHasBranches, IHasMergeProposals,
+                           IHasOfficialBugTags, IHasCodeImports,
+                           IHasTranslationImports, IHasTranslationTemplates):
+    """Public attributes for SourcePackage."""
 
     id = Attribute("ID")
 
     name = exported(
         TextLine(
-            title=_("Name"), required=True,
+            title=_("Name"), required=True, readonly=True,
             description=_("The text name of this source package.")))
 
     displayname = exported(
         TextLine(
-            title=_("Display name"), required=True,
+            title=_("Display name"), required=True, readonly=True,
             description=_("A displayname, constructed, for this package")))
 
     path = Attribute("A path to this package, <distro>/<series>/<package>")
@@ -107,7 +104,7 @@
             Interface,
             # Really IDistribution, circular import fixed in
             # _schema_circular_imports.
-            title=_("Distribution"), required=True,
+            title=_("Distribution"), required=True, readonly=True,
             description=_("The distribution for this source package.")))
 
     # The interface for this is really IDistroSeries, but importing that would
@@ -115,6 +112,7 @@
     distroseries = exported(
         Reference(
             Interface, title=_("Distribution Series"), required=True,
+            readonly=True,
             description=_("The DistroSeries for this SourcePackage")))
 
     sourcepackagename = Attribute("SourcePackageName")
@@ -130,7 +128,7 @@
     productseries = exported(
         ReferenceChoice(
             title=_("Project series"), required=False,
-            vocabulary="ProductSeries",
+            vocabulary="ProductSeries", readonly=True,
             schema=Interface,
             description=_(
                 "The registered project series that this source package "
@@ -265,25 +263,6 @@
         :return: An `IBranch`.
         """
 
-    # 'pocket' should actually be a PackagePublishingPocket, and 'branch'
-    # should be IBranch, but we use the base classes to avoid circular
-    # imports. Correct interface specific in _schema_circular_imports.
-    @operation_parameters(
-        pocket=Choice(
-            title=_("Pocket"), required=True,
-            vocabulary=DBEnumeratedType),
-        branch=Reference(Interface, title=_("Branch"), required=False))
-    @call_with(registrant=REQUEST_USER)
-    @export_write_operation()
-    def setBranch(pocket, branch, registrant):
-        """Set the official branch for the given pocket of this package.
-
-        :param pocket: A `PackagePublishingPocket`.
-        :param branch: The branch to set as the official branch.
-        :param registrant: The individual who created this link.
-        :return: None
-        """
-
     shouldimport = Attribute("""Whether we should import this or not.
         By 'import' we mean sourcerer analysis resulting in a manifest and a
         set of Bazaar branches which describe the source package release.
@@ -329,6 +308,34 @@
         """
 
 
+class ISourcePackageEdit(Interface):
+    """SourcePackage attributes requiring launchpad.Edit."""
+
+    # 'pocket' should actually be a PackagePublishingPocket, and 'branch'
+    # should be IBranch, but we use the base classes to avoid circular
+    # imports. Correct interface specific in _schema_circular_imports.
+    @operation_parameters(
+        pocket=Choice(
+            title=_("Pocket"), required=True,
+            vocabulary=DBEnumeratedType),
+        branch=Reference(Interface, title=_("Branch"), required=False))
+    @call_with(registrant=REQUEST_USER)
+    @export_write_operation()
+    def setBranch(pocket, branch, registrant):
+        """Set the official branch for the given pocket of this package.
+
+        :param pocket: A `PackagePublishingPocket`.
+        :param branch: The branch to set as the official branch.
+        :param registrant: The individual who created this link.
+        :return: None
+        """
+
+
+class ISourcePackage(ISourcePackagePublic, ISourcePackageEdit):
+    """A source package associated to a particular distribution series."""
+    export_as_webservice_entry()
+
+
 class ISourcePackageFactory(Interface):
     """A creator of source packages."""
 

=== modified file 'lib/lp/registry/model/sourcepackage.py'
--- lib/lp/registry/model/sourcepackage.py	2011-05-14 15:03:04 +0000
+++ lib/lp/registry/model/sourcepackage.py	2011-06-02 21:27:44 +0000
@@ -46,8 +46,8 @@
     )
 from lp.bugs.model.bugtask import BugTask
 from lp.buildmaster.enums import BuildStatus
-from lp.code.interfaces.seriessourcepackagebranch import (
-    IMakeOfficialBranchLinks,
+from lp.code.model.seriessourcepackagebranch import (
+    SeriesSourcePackageBranchSet,
     )
 from lp.code.model.branch import Branch
 from lp.code.model.hasbranches import (
@@ -202,8 +202,14 @@
     classProvides(ISourcePackageFactory)
 
     def __init__(self, sourcepackagename, distroseries):
+        # We store the ID of the sourcepackagename and distroseries
+        # simply because Storm can break when accessing them
+        # with implicit flush is blocked (like in a permission check when
+        # storing the object in the permission cache).
+        self.sourcepackagenameID = sourcepackagename.id
         self.sourcepackagename = sourcepackagename
         self.distroseries = distroseries
+        self.distroseriesID = distroseries.id
 
     @classmethod
     def new(cls, sourcepackagename, distroseries):
@@ -585,7 +591,7 @@
 
     def __hash__(self):
         """See `ISourcePackage`."""
-        return hash(self.distroseries.id) ^ hash(self.sourcepackagename.id)
+        return hash(self.distroseriesID) ^ hash(self.sourcepackagenameID)
 
     def __eq__(self, other):
         """See `ISourcePackage`."""
@@ -725,10 +731,9 @@
 
     def setBranch(self, pocket, branch, registrant):
         """See `ISourcePackage`."""
-        series_set = getUtility(IMakeOfficialBranchLinks)
-        series_set.delete(self, pocket)
+        SeriesSourcePackageBranchSet.delete(self, pocket)
         if branch is not None:
-            series_set.new(
+            SeriesSourcePackageBranchSet.new(
                 self.distroseries, pocket, self.sourcepackagename, branch,
                 registrant)
 

=== modified file 'lib/lp/registry/tests/test_sourcepackage.py'
--- lib/lp/registry/tests/test_sourcepackage.py	2011-05-27 21:12:25 +0000
+++ lib/lp/registry/tests/test_sourcepackage.py	2011-06-02 21:27:44 +0000
@@ -14,17 +14,14 @@
 from storm.locals import Store
 import transaction
 from zope.component import getUtility
+from zope.security.checker import canAccess
 from zope.security.interfaces import Unauthorized
-from zope.security.proxy import removeSecurityProxy
+from zope.security.management import checkPermission
 
-from canonical.launchpad.ftests import (
-    login_person,
-    logout,
-    )
 from canonical.testing.layers import DatabaseFunctionalLayer
 from lp.app.interfaces.launchpad import ILaunchpadCelebrities
-from lp.code.interfaces.seriessourcepackagebranch import (
-    IMakeOfficialBranchLinks,
+from lp.code.model.seriessourcepackagebranch import (
+    SeriesSourcePackageBranchSet,
     )
 from lp.registry.interfaces.distribution import NoPartnerArchive
 from lp.registry.interfaces.pocket import PackagePublishingPocket
@@ -48,15 +45,6 @@
 
     layer = DatabaseFunctionalLayer
 
-    def setUp(self):
-        TestCaseWithFactory.setUp(self)
-        person = self.factory.makePerson()
-        ubuntu_branches = getUtility(ILaunchpadCelebrities).ubuntu_branches
-        removeSecurityProxy(ubuntu_branches).addMember(
-            person, ubuntu_branches.teamowner)
-        login_person(person)
-        self.addCleanup(logout)
-
     def test_path(self):
         sourcepackage = self.factory.makeSourcePackage()
         self.assertEqual(
@@ -79,7 +67,7 @@
         sourcepackage = self.factory.makeSourcePackage()
         registrant = self.factory.makePerson()
         branch = self.factory.makePackageBranch(sourcepackage=sourcepackage)
-        getUtility(IMakeOfficialBranchLinks).new(
+        SeriesSourcePackageBranchSet.new(
             sourcepackage.distroseries, PackagePublishingPocket.RELEASE,
             sourcepackage.sourcepackagename, branch, registrant)
         official_branch = sourcepackage.getBranch(
@@ -92,7 +80,8 @@
         pocket = PackagePublishingPocket.RELEASE
         registrant = self.factory.makePerson()
         branch = self.factory.makePackageBranch(sourcepackage=sourcepackage)
-        sourcepackage.setBranch(pocket, branch, registrant)
+        with person_logged_in(sourcepackage.distribution.owner):
+            sourcepackage.setBranch(pocket, branch, registrant)
         self.assertEqual(branch, sourcepackage.getBranch(pocket))
 
     def test_change_branch_once_set(self):
@@ -104,8 +93,9 @@
         branch = self.factory.makePackageBranch(sourcepackage=sourcepackage)
         new_branch = self.factory.makePackageBranch(
             sourcepackage=sourcepackage)
-        sourcepackage.setBranch(pocket, branch, registrant)
-        sourcepackage.setBranch(pocket, new_branch, registrant)
+        with person_logged_in(sourcepackage.distribution.owner):
+            sourcepackage.setBranch(pocket, branch, registrant)
+            sourcepackage.setBranch(pocket, new_branch, registrant)
         self.assertEqual(new_branch, sourcepackage.getBranch(pocket))
 
     def test_unsetBranch(self):
@@ -115,8 +105,9 @@
         pocket = PackagePublishingPocket.RELEASE
         registrant = self.factory.makePerson()
         branch = self.factory.makePackageBranch(sourcepackage=sourcepackage)
-        sourcepackage.setBranch(pocket, branch, registrant)
-        sourcepackage.setBranch(pocket, None, registrant)
+        with person_logged_in(sourcepackage.distribution.owner):
+            sourcepackage.setBranch(pocket, branch, registrant)
+            sourcepackage.setBranch(pocket, None, registrant)
         self.assertIs(None, sourcepackage.getBranch(pocket))
 
     def test_linked_branches(self):
@@ -125,7 +116,8 @@
         pocket = PackagePublishingPocket.RELEASE
         registrant = self.factory.makePerson()
         branch = self.factory.makePackageBranch(sourcepackage=sourcepackage)
-        sourcepackage.setBranch(pocket, branch, registrant)
+        with person_logged_in(sourcepackage.distribution.owner):
+            sourcepackage.setBranch(pocket, branch, registrant)
         self.assertEqual(
             [(pocket, branch)], list(sourcepackage.linked_branches))
 
@@ -270,7 +262,7 @@
         store = Store.of(packaging)
         with person_logged_in(packaging.owner):
             packaging.sourcepackage.deletePackaging()
-        result = store.find(Packaging, Packaging.id==packaging_id)
+        result = store.find(Packaging, Packaging.id == packaging_id)
         self.assertIs(None, result.one())
 
     def test_setPackaging__new(self):
@@ -469,8 +461,9 @@
             'user_can_change_branch': False,
             'user_can_change_translation_usage': False,
             'user_can_change_translations_autoimport_mode': False}
-        self.assertEqual(
-            expected, sourcepackage.getSharingDetailPermissions())
+        with person_logged_in(self.factory.makePerson()):
+            self.assertEqual(
+                expected, sourcepackage.getSharingDetailPermissions())
 
     def test_getSharingDetailPermissions_no_user(self):
         sourcepackage = self.factory.makeSourcePackage()
@@ -479,7 +472,6 @@
             'user_can_change_branch': False,
             'user_can_change_translation_usage': False,
             'user_can_change_translations_autoimport_mode': False}
-        logout()
         self.assertEqual(
             expected, sourcepackage.getSharingDetailPermissions())
 
@@ -518,17 +510,53 @@
 
 
 class TestSourcePackageSecurity(TestCaseWithFactory):
-    """Tests for source package branch linking security."""
+    """Tests for source package security."""
 
     layer = DatabaseFunctionalLayer
 
+    def test_admins_have_launchpad_Edit(self):
+        admin = self.factory.makeAdministrator()
+        sourcepackage = self.factory.makeSourcePackage()
+        with person_logged_in(admin):
+            self.failUnless(
+                checkPermission('launchpad.Edit', sourcepackage),
+                "Administrators should have launchpad.Edit on source "
+                "packages.")
+
+    def test_distro_owner_have_launchpad_Edit(self):
+        sourcepackage = self.factory.makeSourcePackage()
+        with person_logged_in(sourcepackage.distribution.owner):
+            self.failUnless(
+                checkPermission('launchpad.Edit', sourcepackage),
+                "Distribution owner should have launchpad.Edit on source "
+                "packages.")
+
+    def test_uploader_have_launchpad_edit(self):
+        sourcepackage = self.factory.makeSourcePackage()
+        uploader = self.factory.makePerson()
+        archive = sourcepackage.get_default_archive()
+        with person_logged_in(sourcepackage.distribution.main_archive.owner):
+            archive.newPackageUploader(uploader, sourcepackage.name)
+        with person_logged_in(uploader):
+            self.failUnless(
+                checkPermission('launchpad.Edit', sourcepackage),
+                "Uploader to the package should have launchpad.Edit on "
+                "source packages.")
+
+    def test_john_doe_can_t_edit(self):
+        sourcepackage = self.factory.makeSourcePackage()
+        john_doe = self.factory.makePerson()
+        with person_logged_in(john_doe):
+            self.failIf(
+                checkPermission('launchpad.Edit', sourcepackage),
+                "Random user shouldn't have launchpad.Edit on source "
+                "packages.")
+
     def test_cannot_setBranch(self):
         sourcepackage = self.factory.makeSourcePackage()
-        pocket = PackagePublishingPocket.RELEASE
-        registrant = self.factory.makePerson()
-        branch = self.factory.makePackageBranch(sourcepackage=sourcepackage)
-        self.assertRaises(
-            Unauthorized, sourcepackage.setBranch, pocket, branch, registrant)
+        self.failIf(
+            canAccess(sourcepackage, 'setBranch'),
+            "setBranch should only be available to admins and uploaders")
 
 
 class TestSourcePackageViews(TestCaseWithFactory):


Follow ups