+++ /dev/null
-# -*- coding: utf-8 -*-
-## GroupUserFolder
-## Copyright (C)2006 Ingeniweb
-
-## This program is free software; you can redistribute it and/or modify
-## it under the terms of the GNU General Public License as published by
-## the Free Software Foundation; either version 2 of the License, or
-## (at your option) any later version.
-
-## This program is distributed in the hope that it will be useful,
-## but WITHOUT ANY WARRANTY; without even the implied warranty of
-## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-## GNU General Public License for more details.
-
-## You should have received a copy of the GNU General Public License
-## along with this program; see the file COPYING. If not, write to the
-## Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-"""
-
-"""
-__version__ = "$Revision: $"
-# $Source: $
-# $Id: LDAPUserFolderAdapter.py 587 2008-07-31 09:20:06Z pin $
-__docformat__ = 'restructuredtext'
-
-
-from global_symbols import *
-from Products.GroupUserFolder import postonly
-
-
-# These mandatory attributes are required by LDAP schema.
-# They will be filled with user name as a default value.
-# You have to provide a gruf_ldap_required_fields python script
-# in your Plone's skins if you want to override this.
-MANDATORY_ATTRIBUTES = ("sn", "cn", )
-
-
-def _doAddUser(self, name, password, roles, domains, **kw):
- """
- Special user adding method for use with LDAPUserFolder.
- This will ensure parameters are correct for LDAP management
- """
- kwargs = {} # We will pass this dict
- attrs = {}
-
- # Get gruf_ldap_required_fields result and fill in mandatory stuff
- if hasattr(self, "gruf_ldap_required_fields"):
- attrs = self.gruf_ldap_required_fields(login = name)
- else:
- for attr in MANDATORY_ATTRIBUTES:
- attrs[attr] = name
- kwargs.update(attrs)
-
- # We assume that name is rdn attribute
- rdn_attr = self._rdnattr
- kwargs[rdn_attr] = name
-
- # Manage password(s)
- kwargs['user_pw'] = password
- kwargs['confirm_pw'] = password
-
- # Mangle roles
- kwargs['user_roles'] = self._mangleRoles(name, roles)
-
- # Delegate to LDAPUF default method
- msg = self.manage_addUser(kwargs = kwargs)
- if msg:
- raise RuntimeError, msg
-
-
-def _doDelUsers(self, names):
- """
- Remove a bunch of users from LDAP.
- We have to call manage_deleteUsers but, before, we need to find their dn.
- """
- dns = []
- for name in names:
- dns.append(self._find_user_dn(name))
-
- self.manage_deleteUsers(dns)
-
-
-def _find_user_dn(self, name):
- """
- Convert a name to an LDAP dn
- """
- # Search records matching name
- login_attr = self._login_attr
- v = self.findUser(search_param = login_attr, search_term = name)
-
- # Filter to keep exact matches only
- v = filter(lambda x: x[login_attr] == name, v)
-
- # Now, decide what to do
- l = len(v)
- if not l:
- # Invalid name
- raise "Invalid user name: '%s'" % (name, )
- elif l > 1:
- # Several records... don't know how to handle
- raise "Duplicate user name for '%s'" % (name, )
- return v[0]['dn']
-
-
-def _mangleRoles(self, name, roles):
- """
- Return role_dns for this user
- """
- # Local groups => the easiest part
- if self._local_groups:
- return roles
-
- # We have to transform roles into group dns: transform them as a dict
- role_dns = []
- all_groups = self.getGroups()
- all_roles = self.valid_roles()
- groups = {}
- for g in all_groups:
- groups[g[0]] = g[1]
-
- # LDAPUF does the mistake of adding possibly invalid roles to the user roles
- # (for example, adding the cn of a group additionnaly to the mapped zope role).
- # So we must remove from our 'roles' list all roles which are prefixed by group prefix
- # but are not actually groups.
- # See http://www.dataflake.org/tracker/issue_00376 for more information on that
- # particular issue.
- # If a group has the same name as a role, we assume that it should be a _role_.
- # We should check against group/role mapping here, but... well... XXX TODO !
- # See "HERE IT IS" comment below.
-
- # Scan roles we are asking for to manage groups correctly
- for role in roles:
- if not role in all_roles:
- continue # Do not allow propagation of invalid roles
- if role.startswith(GROUP_PREFIX):
- role = role[GROUP_PREFIX_LEN:] # Remove group prefix : groups are stored WITHOUT prefix in LDAP
- if role in all_roles:
- continue # HERE IT IS
- r = groups.get(role, None)
- if not r:
- Log(LOG_WARNING, "LDAP Server doesn't provide a '%s' group (required for user '%s')." % (role, name, ))
- else:
- role_dns.append(r)
-
- return role_dns
-
-
-def _doChangeUser(self, name, password, roles, domains, **kw):
- """
- Update a user
- """
- # Find the dn at first
- dn = self._find_user_dn(name)
-
- # Change password
- if password is not None:
- if password == '':
- raise ValueError, "Password must not be empty for LDAP users."
- self.manage_editUserPassword(dn, password)
-
- # Perform role change
- self.manage_editUserRoles(dn, self._mangleRoles(name, roles))
-
- # (No domain management with LDAP.)
-
-
-def manage_editGroupRoles(self, user_dn, role_dns=[], REQUEST=None):
- """ Edit the roles (groups) of a group """
- from Products.LDAPUserFolder.utils import GROUP_MEMBER_MAP
- try:
- from Products.LDAPUserFolder.LDAPDelegate import ADD, DELETE
- except ImportError:
- # Support for LDAPUserFolder >= 2.6
- ADD = self._delegate.ADD
- DELETE = self._delegate.DELETE
-
- msg = ""
-
-## Log(LOG_DEBUG, "assigning", role_dns, "to", user_dn)
- all_groups = self.getGroups(attr='dn')
- cur_groups = self.getGroups(dn=user_dn, attr='dn')
- group_dns = []
- for group in role_dns:
- if group.find('=') == -1:
- group_dns.append('cn=%s,%s' % (group, self.groups_base))
- else:
- group_dns.append(group)
-
- if self._local_groups:
- if len(role_dns) == 0:
- del self._groups_store[user_dn]
- else:
- self._groups_store[user_dn] = role_dns
-
- else:
- for group in all_groups:
- member_attr = GROUP_MEMBER_MAP.get(self.getGroupType(group))
-
- if group in cur_groups and group not in group_dns:
- action = DELETE
- elif group in group_dns and group not in cur_groups:
- action = ADD
- else:
- action = None
- if action is not None:
- msg = self._delegate.modify(
- group
- , action
- , {member_attr : [user_dn]}
- )
-## Log(LOG_DEBUG, "group", group, "subgroup", user_dn, "result", msg)
-
- if msg:
- raise RuntimeError, msg
-manage_editGroupRoles = postonly(manage_editGroupRoles)