[Checkins] SVN: bluebream/website/docs/v1.0/tutorial4.rst Added PAU

Baiju M baiju.m.mail at gmail.com
Thu Aug 19 02:07:37 EDT 2010


Log message for revision 115767:
  Added PAU
  

Changed:
  U   bluebream/website/docs/v1.0/tutorial4.rst

-=-
Modified: bluebream/website/docs/v1.0/tutorial4.rst
===================================================================
--- bluebream/website/docs/v1.0/tutorial4.rst	2010-08-19 02:38:46 UTC (rev 115766)
+++ bluebream/website/docs/v1.0/tutorial4.rst	2010-08-19 06:07:36 UTC (rev 115767)
@@ -139,7 +139,7 @@
        interface="zope.annotation.interfaces.IAttributeAnnotatable"
        />
     <implements
-       interface="zope.container.interfaces.IContentContainer" 
+       interface="zope.container.interfaces.IContentContainer"
        />
     <require
        permission="tc.View"
@@ -230,7 +230,7 @@
       id="tc.Member"
       title="Ticket collector member"
       description="Users that actually use the ticket collector."/>
-  
+
   <role
       id="tc.Admin"
       title="Ticket collector administrator"
@@ -297,7 +297,7 @@
       role="tc.Member"
       principal="tc.jack"
       />
-   
+
   <principal
       id="tc.jill"
       title="Ticket collector admin"
@@ -332,7 +332,8 @@
 
 You also need to register a default view for ``IUnauthorized`` exception as
 given below.  Here the and implementation available in ``zope.app.http``
-package is included: ``zope.app.http.exception.unauthorized.Unauthorized``::
+package is included: ``zope.app.http.exception.unauthorized.Unauthorized``.
+Add these registrations to ``src/tc/main/configure.zcml``::
 
   <view
       for="zope.security.interfaces.IUnauthorized"
@@ -355,7 +356,192 @@
 Important Note: While testing security related things use ``deploy.ini``.
 Otherwise you can remove ``z3c.evalexception`` middleware from ``debug.ini``.
 
+Persistent principals
+---------------------
 
+In the example given above, principals are stored in ZCML.  You can store
+principals in ZODB using some plugins mechanism provided by the pluggable
+authentication utility using `zope.pluggableauth` package.
+
+While adding ticket collector, it is registered as a site.  A site provides
+a persistent component registry.  To add site to the collector object, you
+are doing like this in ``src/tc/collector/views.py`` file (class:
+``AddTicketCollector``)::
+
+         collector.setSiteManager(LocalSiteManager(collector))
+
+Repplace this line with this function call::
+
+         setup_site_manager(context)
+
+Here is the definition of this function, you can write this function in the
+same file, ``src/tc/collector/views.py``::
+
+  from zope.site import LocalSiteManager
+  from zope.pluggableauth.authentication import PluggableAuthentication
+  from zope.authentication.interfaces import IAuthentication
+  from zope.app.authentication.principalfolder import PrincipalFolder
+  from zope.pluggableauth.interfaces import IAuthenticatorPlugin
+
+  from zope.securitypolicy.interfaces import (IPrincipalRoleManager,
+                                              IPrincipalPermissionManager)
+  from zope.principalannotation.interfaces import IPrincipalAnnotationUtility
+  from zope.principalannotation.utility import PrincipalAnnotationUtility
+  from zope.session.interfaces import ISessionDataContainer
+  from zope.session.session import PersistentSessionDataContainer
+
+  from zope.event import notify
+  from zope.lifecycleevent import ObjectCreatedEvent, ObjectModifiedEvent
+  from zope.session.http import CookieClientIdManager
+  from zope.session.http import ICookieClientIdManager
+  from zope.app.authentication.principalfolder import InternalPrincipal
+
+  def setup_site_manager(context):
+      context.setSiteManager(LocalSiteManager(context))
+      sm = context.getSiteManager()
+      pau = PluggableAuthentication(prefix='hello.pau.')
+      notify(ObjectCreatedEvent(pau))
+      sm[u'authentication'] = pau
+      sm.registerUtility(pau, IAuthentication)
+
+      annotation_utility = PrincipalAnnotationUtility()
+      sm.registerUtility(annotation_utility, IPrincipalAnnotationUtility)
+      session_data = PersistentSessionDataContainer()
+      sm.registerUtility(session_data, ISessionDataContainer)
+
+      client_id_manager = CookieClientIdManager()
+      notify(ObjectCreatedEvent(client_id_manager))
+      sm[u'CookieClientIdManager'] = client_id_manager
+      sm.registerUtility(client_id_manager, ICookieClientIdManager)
+
+      principals = PrincipalFolder(prefix='pf.')
+      notify(ObjectCreatedEvent(principals))
+      pau[u'pf'] = principals
+      pau.authenticatorPlugins += (u"pf", )
+      notify(ObjectModifiedEvent(pau))
+
+      pau.credentialsPlugins += (u'Session Credentials',)
+
+      p1 = InternalPrincipal('admin1', 'admin1', "Admin 1",
+                             passwordManagerName="Plain Text")
+      principals['p1'] = p1
+
+      role_manager = IPrincipalRoleManager(context)
+      login_name = principals.getIdByLogin(p1.login)
+      pid = unicode('hello.pau.' + login_name)
+      role_manager.assignRoleToPrincipal('tc.Admin', pid)
+
+Now you need to create a new factory class for
+``zope.security.interfaces.IUnauthorized`` exception.  Create a file
+``src/tc/main/unauthorized.py`` with this content::
+
+  from zope.authentication.interfaces import IAuthentication
+  from zope.publisher.browser import BrowserPage
+  from zope.component import getUtility
+  from zope.browserpage import ViewPageTemplateFile
+
+  class Unauthorized(BrowserPage):
+
+      template = ViewPageTemplateFile('unauthorized.pt')
+
+      def __call__(self):
+          # Set the error status to 403 (Forbidden) in the case when we don't
+          # challenge the user
+          self.request.response.setStatus(403)
+
+          # make sure that squid does not keep the response in the cache
+          self.request.response.setHeader('Expires', 'Mon, 26 Jul 1997 05:00:00 GMT')
+          self.request.response.setHeader('Cache-Control', 'no-store, no-cache, must-revalidate')
+          self.request.response.setHeader('Pragma', 'no-cache')
+
+          principal = self.request.principal
+          auth = getUtility(IAuthentication)
+          auth.unauthorized(principal.id, self.request)
+          if self.request.response.getStatus() not in (302, 303):
+              return self.template()
+
+Create the ``src/tc/main/unauthorized.pt`` with this content::
+
+  <html>
+  <body>
+
+  <h1>Unauthorized</h1>
+
+  <p>You are not authorized</p>
+
+  </body>
+  </html>
+
+You can change the ``zope.security.interfaces.IUnauthorized`` exception view
+registration like this in the file: ``src/tc/main/configure.zcml``::
+
+  <view
+     for="zope.security.interfaces.IUnauthorized"
+     type="zope.publisher.interfaces.http.IHTTPRequest"
+     name="index"
+     permission="zope.Public"
+     factory=".unauthorized.Unauthorized"
+     />
+
+Finally you need a login form, create a template file in
+``src/tc/main/loginform.html``::
+
+  <html>
+    <head><title>Sign in</title></head>
+  <body>
+  
+    <div tal:define="principal python:request.principal.id">
+      <p tal:condition="python: principal == 'zope.anybody'">
+        Please provide Login Information</p>
+      <p tal:condition="python: principal != 'zope.anybody'">
+        You are not authorized to perform this action. However, you may login
+        as a different user who is authorized.</p>
+      <form action="" method="post">
+        <div tal:omit-tag=""
+             tal:condition="python:principal != 'zope.anybody' and 'SUBMIT' in request">
+          <span
+             tal:define="dummy python:request.response.redirect(request.get('camefrom', ''))" />
+        </div>
+  
+        <div class="row">
+          <div class="label">
+            <label for="login" i18n:translate="">User Name</label></div>
+          <div class="field">
+            <input type="text" name="login" id="login" />
+          </div>
+        </div>
+  
+        <div class="row">
+          <div class="label">
+            <label for="password" i18n:translate="">Password</label></div>
+          <div class="field">
+            <input type="password" name="password" id="password" />
+          </div>
+        </div>
+      
+        <div class="row">
+          <input class="form-element" type="submit" 
+                 name="SUBMIT" value="Log in" i18n:attributes="value login-button" />
+        </div>
+        <input type="hidden" name="camefrom" tal:attributes="value request/camefrom | nothing" />
+      </form>
+    </div>
+  </body>
+  </html>
+
+And register a browser page with the above template::
+
+  <browser:page
+     name="loginForm.html"
+     for="*"
+     template="loginform.pt"
+     permission="zope.Public"
+     layer="tc.skin.interfaces.ITCSkin"
+     />
+
+Now you should be able access the site with new authentication details.  The
+``admin1`` user has the Admin role.
+
 Conclusion
 ----------
 



More information about the checkins mailing list