36 |
36 |
details = None
|
37 |
37 |
|
38 |
38 |
def __init__(self, message, details=None):
|
39 |
|
if details:
|
40 |
|
self.details = details
|
|
39 |
self.details = details or {}
|
41 |
40 |
super(MappingError, self).__init__(message)
|
42 |
41 |
|
43 |
42 |
def __str__(self):
|
... | ... | |
104 |
103 |
if not isinstance(attribute_mapping, list):
|
105 |
104 |
raise MappingError('invalid A2_ATTRIBUTE_MAPPING')
|
106 |
105 |
|
|
106 |
if self.apply_attribute_mapping(user, idp, saml_attributes, attribute_mapping):
|
|
107 |
user.save()
|
|
108 |
|
|
109 |
def apply_attribute_mapping(self, user, idp, saml_attributes, attribute_mapping):
|
107 |
110 |
user_modified = False
|
108 |
111 |
for mapping in attribute_mapping:
|
109 |
112 |
if not isinstance(mapping, dict):
|
... | ... | |
116 |
119 |
method = getattr(self, 'action_' + action.replace('-', '_'))
|
117 |
120 |
except AttributeError:
|
118 |
121 |
pass
|
119 |
|
if not method:
|
120 |
|
raise MappingError('invalid action %r' % action)
|
121 |
122 |
try:
|
|
123 |
if not method:
|
|
124 |
raise MappingError('invalid action')
|
122 |
125 |
logger.debug('auth_saml: applying provisionning mapping %s', mapping)
|
123 |
126 |
if method(user, idp, saml_attributes, mapping):
|
124 |
127 |
user_modified = True
|
125 |
128 |
except MappingError as e:
|
|
129 |
e.details['mapping'] = mapping
|
126 |
130 |
if mandatory:
|
127 |
131 |
# it's mandatory, provisionning should fail completely
|
128 |
132 |
raise e
|
129 |
133 |
else:
|
130 |
|
logger.debug('auth_saml: action mapping %r failed: %s', mapping, e)
|
131 |
|
|
132 |
|
if user_modified:
|
133 |
|
user.save()
|
|
134 |
logger.warning('auth_saml: mapping action failed: %s', e)
|
|
135 |
return user_modified
|
134 |
136 |
|
135 |
137 |
def action_rename(self, user, idp, saml_attributes, mapping):
|
136 |
138 |
from_name = mapping.get('from')
|
... | ... | |
152 |
154 |
raise MappingError('missing saml_attribute key')
|
153 |
155 |
|
154 |
156 |
if saml_attribute not in saml_attributes:
|
155 |
|
raise MappingError('unknown saml_attribute', details={'saml_attribute': saml_attribute})
|
|
157 |
raise MappingError('unknown saml_attribute')
|
156 |
158 |
value = saml_attributes[saml_attribute]
|
157 |
159 |
return self.set_user_attribute(user, attribute, value)
|
158 |
160 |
|
159 |
161 |
def set_user_attribute(self, user, attribute, value):
|
160 |
162 |
if isinstance(value, list):
|
161 |
163 |
if len(value) == 0:
|
162 |
|
raise MappingError('no value for %s' % attribute, details={'attribute': attribute})
|
|
164 |
raise MappingError('no value')
|
163 |
165 |
if len(value) > 1:
|
164 |
|
raise MappingError('too many values for %s' % attribute, details={'attribute': attribute})
|
|
166 |
raise MappingError('too many values', details={'value': value})
|
165 |
167 |
value = value[0]
|
166 |
168 |
if attribute in ('first_name', 'last_name', 'email', 'username'):
|
167 |
169 |
if getattr(user, attribute) != value:
|