CVS: Products/PluggableAuthService - PluggableAuthService.py:1.32 UserPropertySheet.py:1.4 __init__.py:1.7 utils.py:1.7

Sidnei da Silva <[email protected]>
Newsgroups gmane.comp.web.zope.public-cvs
Message-ID <[email protected]>
Update of /cvs-repository/Products/PluggableAuthService
In directory cvs.zope.org:/tmp/cvs-serv13697

Modified Files:
	PluggableAuthService.py UserPropertySheet.py __init__.py 
	utils.py 
Log Message:

Merge changes from sidnei-challenge-protocol-chooser:

    - Added two new interfaces, IChallengeProtocolChooser and
      IRequestTypeSniffer. Those are used to select the 'authorization
      protocol' or 'challenger protocol' to be used for challenging
      according to the incoming request type.

    - Fixed a couple more places where Zope 2-style __implements__
      where being used to standardize on using classImplements.

    - Fixed fallback implementations of providedBy and
      implementedBy to always return a tuple.

    - Make sure challenge doesn't break if existing instances of the
      PluginRegistry don't yet have IChallengeProtocolChooser as a
      registered interface. (Would be nice to have some sort of
      migration for the PluginRegistry between PAS releases)

    - Don't assume that just because zope.interface can be imported
      that Five is present.


=== Products/PluggableAuthService/PluggableAuthService.py 1.31 => 1.32 ===
--- Products/PluggableAuthService/PluggableAuthService.py:1.31	Fri May 27 15:10:45 2005
+++ Products/PluggableAuthService/PluggableAuthService.py	Wed Aug 17 16:53:13 2005
@@ -65,13 +65,15 @@
 from interfaces.plugins import IGroupEnumerationPlugin
 from interfaces.plugins import IRoleEnumerationPlugin
 from interfaces.plugins import IRoleAssignerPlugin
+from interfaces.plugins import IChallengeProtocolChooser
+from interfaces.plugins import IRequestTypeSniffer
 
 from permissions import SearchPrincipals
 
 from PropertiedUser import PropertiedUser
 from utils import _wwwdir
 from utils import createViewName
-
+from utils import classImplements
 
 security = ModuleSecurityInfo(
     'Products.PluggableAuthService.PluggableAuthService' )
@@ -95,8 +97,6 @@
 
 class DumbHTTPExtractor( Implicit ):
 
-    __implements__ = ( ILoginPasswordHostExtractionPlugin, )
-
     security = ClassSecurityInfo()
 
     security.declarePrivate( 'extractCredentials' )
@@ -121,13 +121,15 @@
 
         return creds
 
+classImplements( DumbHTTPExtractor
+               , ILoginPasswordHostExtractionPlugin
+               )
+
 InitializeClass( DumbHTTPExtractor )
 
 
 class EmergencyUserAuthenticator( Implicit ):
 
-    __implements__ = ( IAuthenticationPlugin, )
-
     security = ClassSecurityInfo()
 
     security.declarePrivate( 'authenticateCredentials' )
@@ -149,6 +151,10 @@
 
         return (None, None)
 
+classImplements( EmergencyUserAuthenticator
+               , IAuthenticationPlugin
+               )
+
 InitializeClass( EmergencyUserAuthenticator )
 
 
@@ -156,8 +162,6 @@
 
     """ All-singing, all-dancing user folder.
     """
-    __implements__ = ( IPluggableAuthService, )
-
     security = ClassSecurityInfo()
 
     meta_type = 'Pluggable Auth Service'
@@ -986,8 +990,26 @@
             resp._has_challenged = True
 
     def challenge(self, request, response):
-        # Go through all challenge plugins
         plugins = self._getOb('plugins')
+
+        # Find valid protocols for this request type
+        valid_protocols = []
+        choosers = []
+        try:
+            choosers = plugins.listPlugins( IChallengeProtocolChooser )
+        except KeyError:
+            # Work around the fact that old instances might not have
+            # IChallengeProtocolChooser registered with the
+            # PluginRegistry.
+            pass
+
+        for chooser_id, chooser in choosers:
+            choosen = chooser.chooseProtocols(request)
+            if choosen is None:
+                continue
+            valid_protocols.extend(choosen)
+
+        # Go through all challenge plugins
         challengers = plugins.listPlugins( IChallengePlugin )
 
         protocol = None
@@ -995,6 +1017,9 @@
         for challenger_id, challenger in challengers:
             challenger_protocol = getattr(challenger, 'protocol',
                                           challenger_id)
+            if valid_protocols and challenger_protocol not in valid_protocols:
+                # Skip invalid protocol for this request type.
+                continue
             if protocol is None or protocol == challenger_protocol:
                 if challenger.challenge(request, response):
                     protocol = challenger_protocol
@@ -1072,6 +1097,9 @@
             for resetter_id, resetter in cred_resetters:
                 resetter.resetCredentials(request, response)
 
+classImplements( PluggableAuthService
+               , IPluggableAuthService
+               )
 
 InitializeClass( PluggableAuthService )
 
@@ -1168,6 +1196,17 @@
     , 'role_assigner'
     , "Role Assigner plugins allow the Pluggable Auth Service to assign"
       " roles to principals."
+    )
+  , ( IChallengeProtocolChooser
+    , 'IChallengeProtocolChooser'
+    , 'challenge_protocol_chooser'
+    , "Challenge Protocol Chooser plugins decide what authorization"
+      "protocol to use for a given request type."
+    )
+  , ( IRequestTypeSniffer
+    , 'IRequestTypeSniffer'
+    , 'request_type_sniffer'
+    , "Request Type Sniffer plugins detect the type of an incoming request."
     )
   )
 


=== Products/PluggableAuthService/UserPropertySheet.py 1.3 => 1.4 ===
--- Products/PluggableAuthService/UserPropertySheet.py:1.3	Thu Aug 12 11:15:53 2004
+++ Products/PluggableAuthService/UserPropertySheet.py	Wed Aug 17 16:53:13 2005
@@ -34,9 +34,11 @@
 
 from DateTime.DateTime import DateTime
 
+from Products.PluggableAuthService.utils import classImplements
 from Products.PluggableAuthService.interfaces.propertysheets \
     import IPropertySheet
 
+
 def _guessSchema( kw ):
 
     schema = []
@@ -85,8 +87,6 @@
       guess the schema from the keyword args.
     """
 
-    __implements__ = ( IPropertySheet, )
-
     def __init__( self, id, schema=None, **kw ):
 
         self._id = id
@@ -173,3 +173,7 @@
         """ See IPropertySheet.
         """
         return [ ( x, self._properties.get( x ) ) for x in self.propertyIds() ]
+
+classImplements( UserPropertySheet
+               , IPropertySheet
+               )


=== Products/PluggableAuthService/__init__.py 1.6 => 1.7 ===
--- Products/PluggableAuthService/__init__.py:1.6	Thu Jan 27 14:00:22 2005
+++ Products/PluggableAuthService/__init__.py	Wed Aug 17 16:53:13 2005
@@ -43,6 +43,8 @@
 from plugins import SearchPrincipalsPlugin as SPP
 from plugins import RecursiveGroupsPlugin as RGP
 from plugins import DynamicGroupsPlugin as DGP
+from plugins import ChallengeProtocolChooser as CPC
+from plugins import RequestTypeSniffer as RTS
 
 registerMultiPlugin(HBAH.HTTPBasicAuthHelper.meta_type)
 registerMultiPlugin(IAH.InlineAuthHelper.meta_type)
@@ -58,6 +60,8 @@
 registerMultiPlugin(SPP.SearchPrincipalsPlugin.meta_type)
 registerMultiPlugin(RGP.RecursiveGroupsPlugin.meta_type)
 registerMultiPlugin(DGP.DynamicGroupsPlugin.meta_type)
+registerMultiPlugin(CPC.ChallengeProtocolChooser.meta_type)
+registerMultiPlugin(RTS.RequestTypeSniffer.meta_type)
 
 # monkey patch Zope to cause zmi logout to be PAS-aware
 from App.Management import Navigation
@@ -224,4 +228,22 @@
                             DGP.addDynamicGroupsPlugin, )
                          , visibility=None
                          , icon='plugins/www/DynamicGroupsPlugin.png'
+                         )
+
+    context.registerClass( CPC.ChallengeProtocolChooser
+                         , permission=ManageUsers
+                         , constructors=(
+                            CPC.manage_addChallengeProtocolChooserForm,
+                            CPC.addChallengeProtocolChooserPlugin, )
+                         , visibility=None
+                         , icon='plugins/www/DelegatingMultiPlugin.png'
+                         )
+
+    context.registerClass( RTS.RequestTypeSniffer
+                         , permission=ManageUsers
+                         , constructors=(
+                            RTS.manage_addRequestTypeSnifferForm,
+                            RTS.addRequestTypeSnifferPlugin, )
+                         , visibility=None
+                         , icon='plugins/www/DelegatingMultiPlugin.png'
                          )


=== Products/PluggableAuthService/utils.py 1.6 => 1.7 ===
--- Products/PluggableAuthService/utils.py:1.6	Wed Jul  6 14:47:07 2005
+++ Products/PluggableAuthService/utils.py	Wed Aug 17 16:53:13 2005
@@ -14,20 +14,36 @@
 ##############################################################################
 import os
 import unittest
+from types import TupleType, ListType
 
 from Globals import package_home
 
+def tuplize(value):
+    if isinstance(value, TupleType):
+        return value
+    if isinstance(value, ListType):
+        return tuple(value)
+    return (value,)
+
 try:
     from zope.interface import providedBy
 except ImportError:
     def providedBy(obj):
-        return obj.__implements__
+        return tuplize(obj.__implements__)
 
 try:
     from zope.interface import implementedBy
 except ImportError:
     def implementedBy(klass):
-        return klass.__implements__
+        return tuplize(klass.__implements__)
+
+try:
+    from Products.Five.bridge import fromZ2Interface
+except ImportError:
+    def fromZ2Interface(i):
+        # Raise ValueError to work around a cornerish case where
+        # zope.interface is available but Five is not.
+        raise ValueError, i
 
 try:
     from zope import interface
@@ -40,7 +56,6 @@
 
 else:
     def directlyProvides(obj, *interfaces):
-        from Products.Five.bridge import fromZ2Interface
         # convert any Zope 2 interfaces to Zope 3 using fromZ2Interface
         normalized_interfaces = []
         for i in interfaces:
@@ -52,7 +67,6 @@
         return interface.directlyProvides(obj, *normalized_interfaces)
 
     def classImplements(class_, *interfaces):
-        from Products.Five.bridge import fromZ2Interface
         # convert any Zope 2 interfaces to Zope 3 using fromZ2Interface
         normalized_interfaces = []
         for i in interfaces:

_______________________________________________
Zope-CVS maillist  -  [email protected]
http://mail.zope.org/mailman/listinfo/zope-cvs

Zope CVS instructions: http://dev.zope.org/CVS
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.