Merge lp:~lifeless/launchpad/bug-227494 into lp:launchpad

Proposed by Robert Collins
Status: Merged
Approved by: Robert Collins
Approved revision: no longer in the source branch.
Merged at revision: 13141
Proposed branch: lp:~lifeless/launchpad/bug-227494
Merge into: lp:launchpad
Diff against target: 99 lines (+25/-18)
4 files modified
lib/lp/registry/doc/teammembership-email-notification.txt (+5/-2)
lib/lp/registry/doc/teammembership.txt (+18/-3)
lib/lp/registry/interfaces/person.py (+1/-1)
lib/lp/registry/model/person.py (+1/-12)
To merge this branch: bzr merge lp:~lifeless/launchpad/bug-227494
Reviewer Review Type Date Requested Status
William Grant code Approve
Review via email: mp+62943@code.launchpad.net

Commit message

Make perosn.inTeam(foo) and foo.members agree even for team owners.

Description of the change

Per the attached bug we currently have an awkward situation where if you ask 'is teamX.owner in the list of members of team X' and 'is teamX.owner a member of team X' you get different answers.

This exhibits itself as team owners being able to do anything the team can do even if they are not in the team and not shown as the team in the web UI.

This small patch corrects that. It leaves team owners as *administrators* of the team they own, because thats much less confusing.

To post a comment you must log in.
Revision history for this message
William Grant (wgrant) wrote :

login_person in the middle of the test seems a bit arbitrary. Could you do it earlier? I also worry that it may invalidate more tests, as you only changed it because one case depended on the logged in user.

review: Approve (code*)
Revision history for this message
Robert Collins (lifeless) wrote :

On Tue, May 31, 2011 at 5:35 PM, William Grant <email address hidden> wrote:
> Review: Approve code*
> login_person in the middle of the test seems a bit arbitrary. Could you do it earlier? I also worry that it may invalidate more tests, as you only changed it because one case depended on the logged in user.

Earlier scenarios use a different user. Or is that different to what you mean?

The test script in question passes, and I found the two failing
scripts via an ec2 test run.

Revision history for this message
Robert Collins (lifeless) wrote :

18:47 < lifeless> wgrant: follow up on https://code.launchpad.net/~lifeless/launchpad/bug-227494/+merge/62943 ?
18:49 < wgrant> lifeless: You are arbitrarily changing the user to an admin half-way through because the owner has no privs.
18:49 < wgrant> That may be invalidating subsequent tests.
18:49 < wgrant> Even if it isn't, it's rather confusing to change it partially globally when only that one block needs it.
18:50 < lifeless> wgrant: have you looked through that doctest ?
18:50 < lifeless> hint: it does this a lot already
18:50 < wgrant> It's a doctest. No.
18:50 < lifeless> and the previous user was one it thought was an admin.
18:50 < wgrant> Ah, I see.
18:50 < wgrant> OK.
18:50 < wgrant> An admin, but not an Admin.
18:50 < wgrant> Not an ~admin, sorry.
18:50 < lifeless> yes, a ~admin
18:51 < wgrant> How did it stop being an admin?
18:51 < lifeless> because it was mark
18:51 < wgrant> Because it was the owner of ~admins?
18:51 < lifeless> yes
18:51 < wgrant> But the test removed that membership?
18:51 < lifeless> yes
18:51 < wgrant> ahhhhhhhh
18:51 < lifeless> it was BROKEN
18:51 < wgrant> Carry on, then.
18:51 < wgrant> Preferably beating that test to death on the way.

Revision history for this message
William Grant (wgrant) wrote :

Yay

review: Approve (code)

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'lib/lp/registry/doc/teammembership-email-notification.txt'
2--- lib/lp/registry/doc/teammembership-email-notification.txt 2011-05-27 19:53:20 +0000
3+++ lib/lp/registry/doc/teammembership-email-notification.txt 2011-05-31 05:29:26 +0000
4@@ -41,6 +41,8 @@
5 >>> kamion = personset.getByName('kamion')
6 >>> sampleperson = personset.getByName('name12')
7 >>> ubuntu_team = personset.getByName('ubuntu-team')
8+ >>> from lp.testing.sampledata import ADMIN_EMAIL
9+ >>> admin_person = personset.getByEmail(ADMIN_EMAIL)
10
11
12 Now Robert Collins proposes himself as a member of the Ubuntu Team. This
13@@ -826,8 +828,9 @@
14 ... hwdb_admins)
15 >>> print dumper_hwdb_membership.status.title
16 Approved
17- >>> setStatus(dumper_hwdb_membership,
18- ... TeamMembershipStatus.DEACTIVATED, reviewer=mark, silent=True)
19+ >>> login_person(admin_person)
20+ >>> setStatus(dumper_hwdb_membership, TeamMembershipStatus.DEACTIVATED,
21+ ... reviewer=admin_person, silent=True)
22 >>> run_mail_jobs()
23 >>> len(stub.test_emails)
24 0
25
26=== modified file 'lib/lp/registry/doc/teammembership.txt'
27--- lib/lp/registry/doc/teammembership.txt 2011-04-21 05:18:26 +0000
28+++ lib/lp/registry/doc/teammembership.txt 2011-05-31 05:29:26 +0000
29@@ -410,7 +410,7 @@
30 It's important to note that even if the owner leaves the team, which
31 removes his membership, he will still be the team's owner and retain his
32 rights over it. This ensures we'll never have teams which can't be
33-managed.
34+managed. This does not imply that the owner will be a member of the team.
35
36 >>> login_person(t5.teamowner)
37 >>> t5.teamowner.leave(t5)
38@@ -418,8 +418,23 @@
39 >>> [m.displayname for m in t5.allmembers]
40 []
41 >>> t5.teamowner.inTeam(t5)
42- True
43-
44+ False
45+
46+The team owner can make themselves a member again even if the team is
47+restricted:
48+
49+ >>> t5.teamowner.join(t5, requester=t5.teamowner)
50+ >>> flush_database_updates()
51+ >>> t5.teamowner in t5.allmembers
52+ True
53+ >>> t5.teamowner.inTeam(t5)
54+ True
55+
56+And escalate their privileges back to administrator:
57+
58+ >>> membership = membershipset.getByPersonAndTeam(t5.teamowner, t5)
59+ >>> membership.setStatus(TeamMembershipStatus.ADMIN, t5.teamowner)
60+ True
61
62 Changing membership data
63 ------------------------
64
65=== modified file 'lib/lp/registry/interfaces/person.py'
66--- lib/lp/registry/interfaces/person.py 2011-05-18 03:36:29 +0000
67+++ lib/lp/registry/interfaces/person.py 2011-05-31 05:29:26 +0000
68@@ -1214,7 +1214,7 @@
69 # @operation_parameters(team=copy_field(ITeamMembership['team']))
70 # @export_read_operation()
71 def inTeam(team):
72- """Is this person is a member or the owner of `team`?
73+ """Is this person is a member of `team`?
74
75 Returns `True` when you ask if an `IPerson` (or an `ITeam`,
76 since it inherits from `IPerson`) is a member of himself
77
78=== modified file 'lib/lp/registry/model/person.py'
79--- lib/lp/registry/model/person.py 2011-05-27 21:53:34 +0000
80+++ lib/lp/registry/model/person.py 2011-05-31 05:29:26 +0000
81@@ -1336,18 +1336,7 @@
82 pass
83
84 tp = TeamParticipation.selectOneBy(team=team, person=self)
85- if tp is not None or self.id == team.teamownerID:
86- in_team = True
87- elif not team.teamowner.inTeam(team):
88- # The owner is not a member but must retain his rights over
89- # this team. This person may be a member of the owner, and in this
90- # case it'll also have rights over this team.
91- # Note that this query and the tp query above can be consolidated
92- # when we get to a finer grained level of optimisations.
93- in_team = self.inTeam(team.teamowner)
94- else:
95- in_team = False
96-
97+ in_team = tp is not None
98 self._inTeam_cache[team.id] = in_team
99 return in_team
100