new authenticator plug-in: virtual principals, based on person objects (work in progress)
git-svn-id: svn://svn.cy55.de/Zope3/src/loops/trunk@3270 fd906abe-77d9-0310-91a1-e0d9ade77398
This commit is contained in:
parent
498a099759
commit
cc3652db1c
4 changed files with 99 additions and 23 deletions
|
@ -33,8 +33,9 @@ ZCML setup):
|
||||||
>>> person = concepts['person']
|
>>> person = concepts['person']
|
||||||
|
|
||||||
>>> from loops.concept import Concept
|
>>> from loops.concept import Concept
|
||||||
>>> johnC = concepts['john'] = Concept(u'John')
|
>>> from loops.setup import addAndConfigureObject
|
||||||
>>> johnC.conceptType = person
|
>>> johnC = addAndConfigureObject(concepts, Concept, 'john', title=u'John',
|
||||||
|
... conceptType=person)
|
||||||
|
|
||||||
|
|
||||||
Organizations: Persons (and Users), Institutions, Addresses...
|
Organizations: Persons (and Users), Institutions, Addresses...
|
||||||
|
@ -237,6 +238,18 @@ The person-based authenticator provides authentication without having to
|
||||||
store a persistent (internal) principal object.
|
store a persistent (internal) principal object.
|
||||||
|
|
||||||
>>> from loops.organize.auth import PersonBasedAuthenticator
|
>>> from loops.organize.auth import PersonBasedAuthenticator
|
||||||
|
>>> pbAuth = PersonBasedAuthenticator('persons.')
|
||||||
|
>>> pau['persons'] = pbAuth
|
||||||
|
>>> pau.authenticatorPlugins = ('loops', 'persons',)
|
||||||
|
|
||||||
|
>>> eddieC = addAndConfigureObject(concepts, Concept, 'eddie', title=u'Eddie',
|
||||||
|
... conceptType=person)
|
||||||
|
>>> eddie = adapted(eddieC)
|
||||||
|
>>> eddie.userId = 'persons.eddie'
|
||||||
|
|
||||||
|
>>> pbAuth.setPassword('eddie', 'secret')
|
||||||
|
>>> pbAuth.authenticateCredentials(dict(login='eddie', password='secret'))
|
||||||
|
PrincipalInfo(u'persons.eddie')
|
||||||
|
|
||||||
|
|
||||||
Security
|
Security
|
||||||
|
@ -332,7 +345,6 @@ Tasks and Events
|
||||||
Task view with edit action
|
Task view with edit action
|
||||||
--------------------------
|
--------------------------
|
||||||
|
|
||||||
>>> from loops.setup import addAndConfigureObject
|
|
||||||
>>> from loops.organize.interfaces import ITask
|
>>> from loops.organize.interfaces import ITask
|
||||||
>>> task = addAndConfigureObject(concepts, Concept, 'task', title=u'Task',
|
>>> task = addAndConfigureObject(concepts, Concept, 'task', title=u'Task',
|
||||||
... conceptType=type, typeInterface=ITask)
|
... conceptType=type, typeInterface=ITask)
|
||||||
|
@ -399,7 +411,7 @@ Send Email to Members
|
||||||
>>> form.subject
|
>>> form.subject
|
||||||
u"loops Notification from '$site'"
|
u"loops Notification from '$site'"
|
||||||
>>> form.mailBody
|
>>> form.mailBody
|
||||||
u'\n\nEvent #1\nhttp://127.0.0.1/loops/views/menu/.target95\n\n'
|
u'\n\nEvent #1\nhttp://127.0.0.1/loops/views/menu/.target97\n\n'
|
||||||
|
|
||||||
|
|
||||||
Fin de partie
|
Fin de partie
|
||||||
|
|
|
@ -25,17 +25,34 @@ $Id$
|
||||||
from persistent import Persistent
|
from persistent import Persistent
|
||||||
from zope.app.container.contained import Contained
|
from zope.app.container.contained import Contained
|
||||||
from zope import component
|
from zope import component
|
||||||
from zope.interface import implements
|
from zope.interface import Interface, implements
|
||||||
from zope.app.authentication.interfaces import IAuthenticatorPlugin
|
from zope.app.authentication.interfaces import IAuthenticatorPlugin
|
||||||
from zope.app.authentication.principalfolder import PrincipalInfo
|
from zope.app.authentication.principalfolder import PrincipalInfo
|
||||||
from zope.app.principalannotation.interfaces import IPrincipalAnnotationUtility
|
from zope.app.principalannotation.interfaces import IPrincipalAnnotationUtility
|
||||||
from zope.app.security.interfaces import IAuthentication
|
from zope.app.security.interfaces import IAuthentication
|
||||||
from zope.cachedescriptors.property import Lazy
|
from zope import schema
|
||||||
|
from zope.traversing.api import getParent
|
||||||
|
|
||||||
|
from loops.util import _
|
||||||
|
|
||||||
|
|
||||||
|
class IPersonBasedAuthenticator(Interface):
|
||||||
|
|
||||||
|
prefix = schema.TextLine(
|
||||||
|
title=_("Prefix"),
|
||||||
|
description=_(
|
||||||
|
"Prefix to be added to all principal ids to assure "
|
||||||
|
"that all ids are unique within the authentication service"),
|
||||||
|
missing_value=u"",
|
||||||
|
default=u'',
|
||||||
|
readonly=True)
|
||||||
|
|
||||||
|
|
||||||
class PersonBasedAuthenticator(Persistent, Contained):
|
class PersonBasedAuthenticator(Persistent, Contained):
|
||||||
|
|
||||||
implements(IAuthenticatorPlugin)
|
implements(IAuthenticatorPlugin, IPersonBasedAuthenticator)
|
||||||
|
|
||||||
|
passwordKey = 'loops.organize.password'
|
||||||
|
|
||||||
def __init__(self, prefix=''):
|
def __init__(self, prefix=''):
|
||||||
self.prefix = unicode(prefix)
|
self.prefix = unicode(prefix)
|
||||||
|
@ -45,11 +62,8 @@ class PersonBasedAuthenticator(Persistent, Contained):
|
||||||
return None
|
return None
|
||||||
login = credentials.get('login')
|
login = credentials.get('login')
|
||||||
password = credentials.get('password')
|
password = credentials.get('password')
|
||||||
if not login or not password :
|
if self.checkPassword(login, password):
|
||||||
return None
|
return PrincipalInfo(self.prefix + login, login, login, u'')
|
||||||
id = self.prefix + login
|
|
||||||
if self._checkPassword(id, password):
|
|
||||||
return PrincipalInfo(id, login, login, u'')
|
|
||||||
return None
|
return None
|
||||||
|
|
||||||
def principalInfo(self, id):
|
def principalInfo(self, id):
|
||||||
|
@ -58,19 +72,35 @@ class PersonBasedAuthenticator(Persistent, Contained):
|
||||||
if login:
|
if login:
|
||||||
return PrincipalInfo(id, login, login, u'')
|
return PrincipalInfo(id, login, login, u'')
|
||||||
|
|
||||||
|
def checkPassword(self, login, password):
|
||||||
|
if login and password:
|
||||||
|
pa = self.getPrincipalAnnotations(
|
||||||
|
getParent(self).prefix + self.prefix + login)
|
||||||
|
return pa.get(self.passwordKey) == password
|
||||||
|
return None
|
||||||
|
|
||||||
def setPassword(self, login, password):
|
def setPassword(self, login, password):
|
||||||
id = self.prefix + login
|
pa = self.getPrincipalAnnotations(
|
||||||
pa = self.getPrincipalAnnotations(id)
|
getParent(self).prefix + self.prefix + login)
|
||||||
pa['loops.organize.password'] = password
|
pa[self.passwordKey] = password
|
||||||
|
|
||||||
@Lazy
|
def getPrincipalAnnotations(self, id):
|
||||||
def principalAnnotations(self):
|
utility = component.getUtility(IPrincipalAnnotationUtility)
|
||||||
return component.getUtility(IPrincipalAnnotationUtility)
|
return utility.getAnnotationsById(id)
|
||||||
|
|
||||||
def getPrincipalAnnotations(id):
|
def get(self, login):
|
||||||
return self.principalAnnotations.getAnnotationsById(id)
|
return InternalPrincipal(self, login)
|
||||||
|
|
||||||
def _checkPassword(self, id, password):
|
|
||||||
pa = self.getPrincipalAnnotations(id)
|
class InternalPrincipal(object):
|
||||||
return pa.get('loops.organize.password') == password
|
|
||||||
|
def __init__(self, auth, login):
|
||||||
|
self.auth = auth
|
||||||
|
self.login = login
|
||||||
|
|
||||||
|
def checkPassword(self, password):
|
||||||
|
return self.auth.checkPassword(self.login, password)
|
||||||
|
|
||||||
|
def setPassword(self, passowrd):
|
||||||
|
self.auth.setPassword(self.login, password)
|
||||||
|
|
||||||
|
|
|
@ -62,4 +62,30 @@
|
||||||
class="loops.organize.browser.party.SendEmailForm"
|
class="loops.organize.browser.party.SendEmailForm"
|
||||||
permission="zope.View" />
|
permission="zope.View" />
|
||||||
|
|
||||||
|
<!-- authentication -->
|
||||||
|
|
||||||
|
<browser:addform
|
||||||
|
schema="loops.organize.auth.IPersonBasedAuthenticator"
|
||||||
|
label="Add Person-based Authenticator"
|
||||||
|
content_factory="loops.organize.auth.PersonBasedAuthenticator"
|
||||||
|
keyword_arguments="prefix"
|
||||||
|
name="AddPersonBasedAuthenticator.html"
|
||||||
|
permission="zope.ManageServices"
|
||||||
|
/>
|
||||||
|
|
||||||
|
<browser:addMenuItem
|
||||||
|
title="Person-based Authenticator"
|
||||||
|
description="An authentication plugin for loops Persons"
|
||||||
|
class="loops.organize.auth.PersonBasedAuthenticator"
|
||||||
|
permission="zope.ManageServices"
|
||||||
|
view="AddPersonBasedAuthenticator.html" />
|
||||||
|
|
||||||
|
<browser:schemadisplay
|
||||||
|
schema="loops.organize.auth.IPersonBasedAuthenticator"
|
||||||
|
label="Authenticator Prefix"
|
||||||
|
name="prefix.html"
|
||||||
|
fields="prefix"
|
||||||
|
permission="zope.ManageServices"
|
||||||
|
menu="zmi_views" title="Prefix" />
|
||||||
|
|
||||||
</configure>
|
</configure>
|
||||||
|
|
|
@ -48,6 +48,14 @@
|
||||||
interface="loops.organize.interfaces.IMemberRegistrationManager" />
|
interface="loops.organize.interfaces.IMemberRegistrationManager" />
|
||||||
</zope:class>
|
</zope:class>
|
||||||
|
|
||||||
|
<!-- authentication -->
|
||||||
|
|
||||||
|
<zope:localUtility class="loops.organize.auth.PersonBasedAuthenticator">
|
||||||
|
<require
|
||||||
|
permission="zope.ManageServices"
|
||||||
|
attributes="prefix" />
|
||||||
|
</zope:localUtility>
|
||||||
|
|
||||||
<!-- other adapters -->
|
<!-- other adapters -->
|
||||||
|
|
||||||
<zope:adapter factory="loops.organize.schema.PersonSchemaFactory" />
|
<zope:adapter factory="loops.organize.schema.PersonSchemaFactory" />
|
||||||
|
|
Loading…
Add table
Reference in a new issue