Merge lp:~gmb/launchpad/rollback-13050 into lp:launchpad

Proposed by Graham Binns
Status: Merged
Merged at revision: 13065
Proposed branch: lp:~gmb/launchpad/rollback-13050
Merge into: lp:launchpad
Diff against target: 257 lines (+9/-149)
5 files modified
lib/lp/bugs/browser/bug.py (+3/-2)
lib/lp/bugs/browser/tests/test_bug_views.py (+0/-61)
lib/lp/bugs/doc/bugsubscription.txt (+1/-1)
lib/lp/bugs/model/bug.py (+5/-62)
lib/lp/bugs/tests/test_bugsubscription.py (+0/-23)
To merge this branch: bzr merge lp:~gmb/launchpad/rollback-13050
Reviewer Review Type Date Requested Status
Graham Binns (community) Approve
Review via email: mp+61265@code.launchpad.net

Commit message

[r=gmb][ui=none][bug=783948] [rollback=13050] Revert bad revision r13050, which may have caused bug 783948.

Description of the change

This branch reverts devel r13050, which may have resulted in bug 783948 manifesting.

To post a comment you must log in.
Revision history for this message
Graham Binns (gmb) wrote :

Self-approving after checking that rolling back fixed the problem.

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'lib/lp/bugs/browser/bug.py'
2--- lib/lp/bugs/browser/bug.py 2011-05-16 17:43:29 +0000
3+++ lib/lp/bugs/browser/bug.py 2011-05-17 15:03:32 +0000
4@@ -536,7 +536,6 @@
5 @cachedproperty
6 def user_should_see_mute_link(self):
7 """Return True if the user should see the Mute link."""
8- user_is_subscribed = False
9 if features.getFeatureFlag('malone.advanced-subscriptions.enabled'):
10 user_is_subscribed = (
11 # Note that we don't have to check for isMuted(), since
12@@ -545,7 +544,9 @@
13 self.context.isSubscribed(self.user) or
14 self.context.isSubscribedToDupes(self.user) or
15 self.context.personIsAlsoNotifiedSubscriber(self.user))
16- return user_is_subscribed
17+ return user_is_subscribed
18+ else:
19+ return False
20
21 @cachedproperty
22 def _bug_attachments(self):
23
24=== modified file 'lib/lp/bugs/browser/tests/test_bug_views.py'
25--- lib/lp/bugs/browser/tests/test_bug_views.py 2011-05-12 10:36:43 +0000
26+++ lib/lp/bugs/browser/tests/test_bug_views.py 2011-05-17 15:03:32 +0000
27@@ -177,64 +177,3 @@
28 self.assertTrue(
29 self._hasCSSClass(html, 'mute-link-container', 'hidden'),
30 'No "hidden" CSS class in mute-link-container.')
31-
32- def test_mute_link_shown_for_team_subscription_to_duplicate(self):
33- # If the person belongs to a team with a structural subscription to a
34- # duplicate of this bug, then the mute link will be displayed to them.
35- person = self.factory.makePerson(name="a-person")
36- team_owner = self.factory.makePerson(name="team-owner")
37- team = self.factory.makeTeam(owner=team_owner, name="subscribed-team")
38- dupe = self.factory.makeBug()
39- with person_logged_in(self.bug.owner):
40- dupe.markAsDuplicate(self.bug)
41- with FeatureFixture({self.feature_flag_1: 'on'}):
42- with person_logged_in(team_owner):
43- team.addMember(person, team_owner)
44- dupe_target = dupe.default_bugtask.target
45- dupe_target.addBugSubscription(team, team_owner)
46- with person_logged_in(person):
47- self.assertFalse(self.bug.isMuted(person))
48- # This is a sanity check for the test.
49- self.assertFalse(self.bug.duplicates.is_empty())
50- self.assertEqual(self.bug, dupe.duplicateof)
51- self.assertTrue(
52- self.bug.personIsAlsoNotifiedSubscriber(
53- person), "Person should be a notified subscriber")
54- view = create_initialized_view(
55- self.bug, name="+portlet-subscribers")
56- self.assertTrue(view.user_should_see_mute_link,
57- "User should see mute link.")
58- contents = view.render()
59- self.assertTrue('mute_subscription' in contents,
60- "'mute_subscription' not in contents.")
61- create_initialized_view(
62- self.bug.default_bugtask, name="+mute",
63- form={'field.actions.mute': 'Mute bug mail'})
64- self.assertTrue(self.bug.isMuted(person))
65-
66- def test_mute_subscription_link_shown_for_team_direct_subscription(self):
67- # If the person belongs to a team with a direct subscription,
68- # then the mute link will be displayed to them.
69- person = self.factory.makePerson(name="a-person")
70- team_owner = self.factory.makePerson(name="team-owner")
71- team = self.factory.makeTeam(owner=team_owner, name="subscribed-team")
72- with FeatureFixture({self.feature_flag_1: 'on'}):
73- with person_logged_in(team_owner):
74- team.addMember(person, team_owner)
75- self.bug.subscribe(team, team_owner)
76- with person_logged_in(person):
77- self.assertFalse(self.bug.isMuted(person))
78- self.assertTrue(
79- self.bug.personIsAlsoNotifiedSubscriber(person),
80- "Person should be a notified subscriber")
81- view = create_initialized_view(
82- self.bug, name="+portlet-subscribers")
83- self.assertTrue(view.user_should_see_mute_link,
84- "User should see mute link.")
85- contents = view.render()
86- self.assertTrue('mute_subscription' in contents,
87- "'mute_subscription' not in contents.")
88- create_initialized_view(
89- self.bug.default_bugtask, name="+mute",
90- form={'field.actions.mute': 'Mute bug mail'})
91- self.assertTrue(self.bug.isMuted(person))
92
93=== modified file 'lib/lp/bugs/doc/bugsubscription.txt'
94--- lib/lp/bugs/doc/bugsubscription.txt 2011-05-16 17:40:00 +0000
95+++ lib/lp/bugs/doc/bugsubscription.txt 2011-05-17 15:03:32 +0000
96@@ -423,7 +423,7 @@
97 []
98
99 >>> linux_source_bug.getSubscribersFromDuplicates()
100- []
101+ ()
102
103 Direct subscriptions always take precedence over indirect
104 subscriptions. So, if we unmark the above bug as private,
105
106=== modified file 'lib/lp/bugs/model/bug.py'
107--- lib/lp/bugs/model/bug.py 2011-05-17 05:43:19 +0000
108+++ lib/lp/bugs/model/bug.py 2011-05-17 15:03:32 +0000
109@@ -953,30 +953,18 @@
110 See the comment in getDirectSubscribers for a description of the
111 recipients argument.
112 """
113- if self.private:
114- # We short-circuit for private bugs, since actually
115- # returning something non-empty here causes things to break
116- # in fun and interesting ways (see bug 780248).
117- return []
118-
119 if level is None:
120 level = BugNotificationLevel.NOTHING
121 info = self.getSubscriptionInfo(level)
122
123 if recipients is not None:
124- # Pre-load duplicates
125+ # Pre-load duplicate bugs.
126 list(self.duplicates)
127 for subscription in info.duplicate_only_subscriptions:
128 recipients.addDupeSubscriber(
129 subscription.person, subscription.bug)
130- for subscription in info.structural_subscriptions_from_duplicates:
131- recipients.addDupeSubscriber(
132- subscription.subscriber)
133
134- unified_subscribers = (
135- info.duplicate_only_subscriptions.subscribers.union(
136- info.structural_subscriptions_from_duplicates.subscribers))
137- return unified_subscribers.sorted
138+ return info.duplicate_only_subscriptions.subscribers.sorted
139
140 def getSubscribersForPerson(self, person):
141 """See `IBug."""
142@@ -1041,16 +1029,12 @@
143 include_master_dupe_subscribers=False):
144 """See `IBug`."""
145 recipients = BugNotificationRecipients(duplicateof=duplicateof)
146- # Call getDirectSubscribers to update the recipients list with direct
147- # subscribers. The results of the method call are not used.
148 self.getDirectSubscribers(recipients, level=level)
149 if self.private:
150 assert self.getIndirectSubscribers() == [], (
151 "Indirect subscribers found on private bug. "
152 "A private bug should never have implicit subscribers!")
153 else:
154- # Call getIndirectSubscribers to update the recipients list with direct
155- # subscribers. The results of the method call are not used.
156 self.getIndirectSubscribers(recipients, level=level)
157 if include_master_dupe_subscribers and self.duplicateof:
158 # This bug is a public duplicate of another bug, so include
159@@ -1917,22 +1901,6 @@
160
161 def personIsAlsoNotifiedSubscriber(self, person):
162 """See `IBug`."""
163- # This is here to avoid circular imports.
164- from lp.bugs.mail.bugnotificationrecipients import (
165- BugNotificationRecipients,
166- )
167-
168- def check_person_in_team(person, list_of_people):
169- """Is the person in one of the teams?
170-
171- Given a person and a list of people/teams, see if the person
172- belongs to one of the teams.
173- """
174- for subscriber in list_of_people:
175- if subscriber.is_team and person.inTeam(subscriber):
176- return True
177- return False
178-
179 # We have to use getAlsoNotifiedSubscribers() here and iterate
180 # over what it returns because "also notified subscribers" is
181 # actually a composite of bug contacts, structural subscribers
182@@ -1943,16 +1911,9 @@
183 return True
184 # Otherwise check to see if the person is a member of any of the
185 # subscribed teams.
186- if check_person_in_team(person, also_notified_subscribers):
187- return True
188-
189- direct_subscribers = self.getDirectSubscribers()
190- if check_person_in_team(person, direct_subscribers):
191- return True
192- duplicate_subscribers = self.getSubscribersFromDuplicates(
193- recipients=BugNotificationRecipients())
194- if check_person_in_team(person, duplicate_subscribers):
195- return True
196+ for subscriber in also_notified_subscribers:
197+ if subscriber.is_team and person.inTeam(subscriber):
198+ return True
199 return False
200
201 def personIsSubscribedToDuplicate(self, person):
202@@ -2312,24 +2273,6 @@
203 return get_structural_subscriptions_for_bug(self.bug)
204
205 @cachedproperty
206- @freeze(StructuralSubscriptionSet)
207- def structural_subscriptions_from_duplicates(self):
208- """Structural subscriptions from the bug's duplicates."""
209- self.duplicate_subscriptions.subscribers # Pre-load subscribers.
210- higher_precedence = (
211- self.direct_subscriptions.subscribers.union(
212- self.also_notified_subscribers))
213- all_duplicate_structural_subscriptions = list()
214- for duplicate in self.bug.duplicates:
215- duplicate_struct_subs = get_structural_subscriptions_for_bug(
216- duplicate)
217- all_duplicate_structural_subscriptions += duplicate_struct_subs
218- return (
219- subscription for subscription in
220- all_duplicate_structural_subscriptions
221- if subscription.subscriber not in higher_precedence)
222-
223- @cachedproperty
224 @freeze(BugSubscriberSet)
225 def all_assignees(self):
226 """Assignees of the bug's tasks."""
227
228=== modified file 'lib/lp/bugs/tests/test_bugsubscription.py'
229--- lib/lp/bugs/tests/test_bugsubscription.py 2011-05-10 14:13:24 +0000
230+++ lib/lp/bugs/tests/test_bugsubscription.py 2011-05-17 15:03:32 +0000
231@@ -146,26 +146,3 @@
232 self.bug.id, team_2.name, self.subscriber)
233 self.assertThat(
234 collector, HasQueryCount(LessThan(25)))
235-
236-
237-class TestBugSubscriptionMethods(TestCaseWithFactory):
238- """A TestCase for the subscription-related methods of `Bug`."""
239-
240- layer = DatabaseFunctionalLayer
241-
242- def test_getSubscribersFromDuplicates_returns_empty_when_private(self):
243- # If a private bug has duplicates its
244- # getSubscribersFromDuplicates() method should return an empty
245- # set.
246- # This is a regression test for bug 780248.
247- bug = self.factory.makeBug()
248- duplicate = self.factory.makeBug()
249- team = self.factory.makeTeam()
250- with person_logged_in(team.teamowner):
251- duplicate.default_bugtask.product.addSubscription(
252- team, team.teamowner)
253- with person_logged_in(bug.owner):
254- bug.setPrivate(True, bug.owner)
255- duplicate.markAsDuplicate(bug)
256- duplicate_subscribers = bug.getSubscribersFromDuplicates()
257- self.assertEqual(0, len(duplicate_subscribers))