Use session_index to find session to logout

* larpe/session.py:
   add two dictionnaries larpe_session_indexes and
   larpe_session_name_identifiers to cache sessionIndex and
   nameIdentifier received from authentication assertion, and use them
   to find session to logout when receiving logout request.
 * larpes/saml2.ptl:
   implement logout using the new dictionnaries to find sessions.

git-svn-id: svn+ssh://labs.libre-entreprise.org/svnroot/larpe@478 3ed937ae-f919-0410-9a43-8e6f19e4ba6e
This commit is contained in:
bdauvergne 2009-09-28 13:19:50 +00:00
parent 319d6d64e9
commit b54fb9e091
2 changed files with 31 additions and 9 deletions

View File

@ -77,6 +77,7 @@ class Saml2(Saml2Directory):
return self.sso_after_response(login)
def sso_after_response(self, login):
providerId = login.server.providerId
try:
assertion = login.response.assertion[0]
if assertion.subject.subjectConfirmation.subjectConfirmationData.recipient != \
@ -103,7 +104,7 @@ class Saml2(Saml2Directory):
try:
audience_ok = False
for audience_restriction in assertion.conditions.audienceRestriction:
if audience_restriction.audience != login.server.providerId:
if audience_restriction.audience != providerId:
return template.error_page('Incorrect AudienceRestriction')
audience_ok = True
if not audience_ok:
@ -129,12 +130,14 @@ class Saml2(Saml2Directory):
session = get_session()
if login.isSessionDirty:
if login.session:
session.lasso_session_dumps[login.server.providerId] = login.session.dump()
session.lasso_session_dumps[providerId] = login.session.dump()
session.lasso_session_indexes[providerId] = assertion.authnStatement[0].sessionIndex
session.lasso_session_name_identifiers[providerId] = login.nameIdentifier.content
else:
session.lasso_session_dumps[login.server.providerId] = None
if assertion.authnStatement[0].sessionIndex:
session.lasso_session_index = assertion.authnStatement[0].sessionIndex
session.lasso_session_indexes = assertion.authnStatement[0].sessionIndex
user = self.lookup_user(session, login)
@ -301,11 +304,17 @@ class Saml2(Saml2Directory):
return
logout = lasso.Logout(misc.get_lasso_server(protocol = 'saml2'))
providerId = logout.server.providerId
logout.processRequestMsg(soap_message)
name_identifier = logout.nameIdentifier.content
# find one session matching the name identifier, and eventually the request
for session in get_session_manager().values():
user = session.get_user(logout.server.providerId)
if user and logout.nameIdentifier.content in user.name_identifiers:
session_index = session.lasso_session_indexes.get(providerId)
name_identifier = session.lasso_session_name_identifiers.get(providerId)
request_name_identifier = logout.nameIdentifier.content
request_session_index = logout.request.sessionIndex
if request_name_identifier == name_identifier and \
(not session_index or request_session_index == session_index):
get_logger().info('SLO/SOAP from %s' % logout.remoteProviderId)
break
else:
@ -375,10 +384,15 @@ class Saml2(Saml2Directory):
get_session_manager().expire_session(logout.server.providerId)
try:
if not logout.request.sessionIndex:
for session2 in get_session_manager().values():
if name_identifier == session2.name_identifier:
del get_session_manager()[session2.id]
providerId = logout.server.providerId
session_index = logout.request.sessionIndex
name_identifier = logout.nameIdentifier.content
# Remove all session for this name_identifier and if present for this session index
for session2 in get_session_manager().values():
if session2.lasso_session_name_identifiers.get(providerId) == name_identifier \
and ( not session_index
or session2.lasso_session_indexes.get(providerId) == session_index):
del get_session_manager()[session2.id]
except:
# killing all session failed, ignoring silently
pass

View File

@ -16,9 +16,17 @@ class BasicSession(Session):
def __init__(self, id):
self.users = {}
self.lasso_session_dumps = {}
self.lasso_session_indexes = {}
self.lasso_session_name_identifiers = {}
self.provider_id = None
Session.__init__(self, id)
# lasso_session_indexes newly introduced
def __setstate__(self, dict):
self.lasso_session_indexes = {}
self.lasso_session_name_identifiers = {}
self.__dict__.update(dict)
def has_info(self):
return self.users or self.lasso_session_dumps or self.provider_id or Session.has_info(self)
is_dirty = has_info