optimisation empreinte mémoire.
[Plinn.git] / GroupDataTool.py
1 # -*- coding: utf-8 -*-
2 #######################################################################################
3 # Plinn - http://plinn.org #
4 # Copyright (C) 2005-2007 Benoît PIN <benoit.pin@ensmp.fr> #
5 # #
6 # This program is free software; you can redistribute it and/or #
7 # modify it under the terms of the GNU General Public License #
8 # as published by the Free Software Foundation; either version 2 #
9 # of the License, or (at your option) any later version. #
10 # #
11 # This program is distributed in the hope that it will be useful, #
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of #
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the #
14 # GNU General Public License for more details. #
15 # #
16 # You should have received a copy of the GNU General Public License #
17 # along with this program; if not, write to the Free Software #
18 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. #
19 #######################################################################################
20 """
21
22
23 """
24
25 from Globals import InitializeClass
26 from AccessControl import ClassSecurityInfo
27 from Acquisition import aq_inner, aq_parent, aq_base
28
29 from Products.GroupUserFolder.GroupDataTool import GroupDataTool as BaseTool
30 from Products.GroupUserFolder.GroupDataTool import GroupData as BaseGroupData
31 from Products.GroupUserFolder.GroupsToolPermissions import ManageGroups, ViewGroups
32 from Products.CMFCore.utils import getToolByName
33 from ZPublisher.Converters import type_converters
34
35 from GroupsTool import CACHE_ROOT_GROUPS, CACHE_GROUPS_OF_GROUP, CACHE_USER_NAMES_OF_GROUP
36
37 try:
38 from Products.CMFCore.MemberDataTool import CleanupTemp
39 _have_cleanup_temp = 1
40 except:
41 _have_cleanup_temp = None
42
43
44 class GroupDataTool(BaseTool) :
45 """ Group Data Tool """
46
47 meta_type = 'Plinn Group Data Tool'
48
49 security = ClassSecurityInfo()
50
51 security.declarePrivate('wrapGroup')
52 def wrapGroup(self, g):
53 """Returns an object implementing the GroupData interface"""
54 id = g.getId()
55 members = self._members
56 if not members.has_key(id):
57 # Get a temporary member that might be
58 # registered later via registerMemberData().
59 temps = self._v_temps
60 if temps is not None and temps.has_key(id):
61 portal_group = temps[id]
62 else:
63 base = aq_base(self)
64 portal_group = GroupData(base, id)
65 if temps is None:
66 self._v_temps = {id:portal_group}
67 if hasattr(self, 'REQUEST'):
68 # No REQUEST during tests.
69 # XXX jcc => CleanupTemp doesn't seem to work on Plone 1.0.3.
70 # Have to find a way to pass around...
71 if _have_cleanup_temp:
72 self.REQUEST._hold(CleanupTemp(self))
73 else:
74 temps[id] = portal_group
75 else:
76 portal_group = members[id]
77 # Return a wrapper with self as containment and
78 # the user as context.
79 return portal_group.__of__(self).__of__(g)
80
81 class GroupData(BaseGroupData) :
82 """ """
83
84 security = ClassSecurityInfo()
85
86 security.declareProtected(ViewGroups, 'getGroups')
87 security.declareProtected(ManageGroups, 'setGroupProperties')
88 def setGroupProperties(self, mapping):
89 '''Sets the properties of the group.
90 '''
91 # Sets the properties given in the MemberDataTool.
92 tool = self.getTool()
93 self = self.aq_inner.aq_self
94 for id in tool.propertyIds():
95 if mapping.has_key(id):
96 if not self.__class__.__dict__.has_key(id):
97 value = mapping[id]
98 if type(value)==type(''):
99 proptype = tool.getPropertyType(id) or 'string'
100 if type_converters.has_key(proptype):
101 value = type_converters[proptype](value)
102 setattr(self, id, value)
103 # Hopefully we can later make notifyModified() implicit.
104 self.notifyModified()
105
106 security.declareProtected(ManageGroups, 'removeMember')
107 def removeMember(self, id):
108 """ Remove the member with the provided id from the group """
109
110 user = self.acl_users.getUser(id)
111
112 groups = list(user.getGroups(no_recurse=1))
113 prefix = self.acl_users.getGroupPrefix()
114 try : groups.remove(prefix + self.getGroupName())
115 except ValueError : return # the user (id) is an implicit member of this group (self)
116
117 roles_no_recurse = tuple(filter(lambda x: x not in ('Authenticated', 'Shared'), user.getUserRoles()))
118
119 if user.isGroup() :
120 self.acl_users._doChangeGroup(id, roles_no_recurse, groups = groups)
121 else :
122 self.acl_users._doChangeUser(id,
123 None,
124 roles_no_recurse,
125 user.getDomains(),
126 groups=tuple(groups))
127
128 gtool = getToolByName(self, "portal_groups")
129 if gtool.ZCacheable_isCachingEnabled() :
130 # humm... there's a bug on Cacheable / RamCacheManger
131 #gtool.ZCacheable_invalidate(view_name=CACHE_USER_NAMES_OF_GROUP)
132 gtool.ZCacheable_set(None, view_name=CACHE_USER_NAMES_OF_GROUP, keywords={'no_recurse' : 0})
133 gtool.ZCacheable_set(None, view_name=CACHE_USER_NAMES_OF_GROUP, keywords={'no_recurse' : 1})
134
135
136
137 security.declareProtected(ManageGroups, 'addMember')
138 def addMember(self, id):
139 """ Add the existing member with the given id to the group"""
140 aclu = self.aq_inner.acl_users
141 user = aclu.getUser(id)
142 prefix = aclu.getGroupPrefix()
143
144 userRoles = tuple(filter(lambda x: x not in ('Authenticated', 'Shared'), user.getUserRoles()))
145 groups = user.getGroups(no_recurse = 1)
146 groups += (self.id, )
147
148 aclu.changeUser(user.id, groups = groups, roles = userRoles)
149 gtool = getToolByName(self, 'portal_groups')
150 if gtool.ZCacheable_isCachingEnabled() :
151 # humm... there's a bug on Cacheable / RamCacheManger
152 #gtool.ZCacheable_invalidate(view_name=CACHE_USER_NAMES_OF_GROUP)
153 gtool.ZCacheable_set(None, view_name=CACHE_USER_NAMES_OF_GROUP, keywords={'no_recurse' : 0})
154 gtool.ZCacheable_set(None, view_name=CACHE_USER_NAMES_OF_GROUP, keywords={'no_recurse' : 1})
155
156
157
158 security.declareProtected(ManageGroups, 'removeGroup')
159 def removeGroup(self, id) :
160 """ Remove the existing group with the given id to the group"""
161 aclu = self.aq_inner.acl_users
162 groupPrefix = aclu.getGroupPrefix()
163 group = aclu.getGroup(id)
164
165 # get group roles
166 groupRoles = tuple(filter(lambda x: x not in ('Authenticated', 'Shared'), group.getUserRoles()))
167 superGroupIds = list(group.getGroups(no_recurse = 1))
168 superGroupIds.remove(self.id)
169
170 aclu.changeUser(groupPrefix + group.id, groups = superGroupIds, roles = groupRoles)
171
172 gtool = getToolByName(self, "portal_groups")
173 if gtool.ZCacheable_isCachingEnabled() :
174 gtool.ZCacheable_set(None, view_name=CACHE_GROUPS_OF_GROUP)
175 if not superGroupIds :
176 gtool.ZCacheable_set(None, view_name=CACHE_ROOT_GROUPS)
177
178
179 security.declareProtected(ManageGroups, 'addGroup')
180 def addGroup(self, id) :
181 """ Add the existing group with the given id to the group"""
182 aclu = self.aq_inner.acl_users
183 groupPrefix = aclu.getGroupPrefix()
184 group = aclu.getGroup(id)
185
186 # get group roles
187 groupRoles = tuple(filter(lambda x: x not in ('Authenticated', 'Shared'), group.getUserRoles()))
188 superGroupIds = list(group.getGroups(no_recurse = 1))
189 newSuperGroupIds = superGroupIds[:]
190 newSuperGroupIds.append(self.id)
191
192 aclu.changeUser(groupPrefix + group.id, groups = newSuperGroupIds, roles = groupRoles)
193
194 gtool = getToolByName(self, "portal_groups")
195 if gtool.ZCacheable_isCachingEnabled() :
196 gtool.ZCacheable_set(None, view_name=CACHE_GROUPS_OF_GROUP)
197 if not superGroupIds :
198 gtool.ZCacheable_set(None, view_name=CACHE_ROOT_GROUPS)
199
200
201
202 InitializeClass(GroupDataTool)