[Checkins] SVN: zope.app.authentication/trunk/ Moved the following views from `zope.app.securitypolicy` here, to inverse dependency between these two packages, as `zope.app.securitypolicy` deprecated in ZTK 1.0:

Michael Howitz mh at gocept.com
Sat Sep 25 05:03:26 EDT 2010


Log message for revision 116799:
  Moved the following views from `zope.app.securitypolicy` here, to inverse dependency between these two packages, as `zope.app.securitypolicy` deprecated in ZTK 1.0:
    - ``@@grant.html``
    - ``@@AllRolePermissions.html``
    - ``@@RolePermissions.html``
    - ``@@RolesWithPermission.html``
  

Changed:
  U   zope.app.authentication/trunk/CHANGES.txt
  U   zope.app.authentication/trunk/README.txt
  U   zope.app.authentication/trunk/setup.py
  U   zope.app.authentication/trunk/src/zope/app/authentication/browser/configure.zcml
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/grant.zcml
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.pt
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.py
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.txt
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_access.pt
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_permissionform.pt
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_roleform.pt
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/rolepermissionview.py
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/rolepermissionmanager.py
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_granting.py
  A   zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_rolepermissionview.py
  U   zope.app.authentication/trunk/src/zope/app/authentication/ftesting.zcml

-=-
Modified: zope.app.authentication/trunk/CHANGES.txt
===================================================================
--- zope.app.authentication/trunk/CHANGES.txt	2010-09-25 08:10:36 UTC (rev 116798)
+++ zope.app.authentication/trunk/CHANGES.txt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -2,13 +2,22 @@
 Changes
 =======
 
-3.7.2 (unreleased)
+3.8.0 (unreleased)
 ------------------
 
 * Using python's ``doctest`` module instead of deprecated
   ``zope.testing.doctest[unit]``.
 
+* Moved the following views from `zope.app.securitypolicy` here, to inverse
+  dependency between these two packages, as `zope.app.securitypolicy`
+  deprecated in ZTK 1.0:
 
+  - ``@@grant.html``
+  - ``@@AllRolePermissions.html``
+  - ``@@RolePermissions.html``
+  - ``@@RolesWithPermission.html``
+
+
 3.7.1 (2010-02-11)
 ------------------
 

Modified: zope.app.authentication/trunk/README.txt
===================================================================
--- zope.app.authentication/trunk/README.txt	2010-09-25 08:10:36 UTC (rev 116798)
+++ zope.app.authentication/trunk/README.txt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -1,6 +1,2 @@
-==========================
- Pluggable Authentication
-==========================
-
 This package provides a flexible and pluggable authentication utility for Zope
 3, using `zope.pluggableauth`. Several common plugins are provided.

Modified: zope.app.authentication/trunk/setup.py
===================================================================
--- zope.app.authentication/trunk/setup.py	2010-09-25 08:10:36 UTC (rev 116798)
+++ zope.app.authentication/trunk/setup.py	2010-09-25 09:03:24 UTC (rev 116799)
@@ -27,17 +27,14 @@
     return open(os.path.join(os.path.dirname(__file__), *rnames)).read()
 
 setup(name='zope.app.authentication',
-      version = '3.7.2dev',
+      version = '3.8.0dev',
       author='Zope Corporation and Contributors',
       author_email='zope-dev at zope.org',
       description=('Principals and groups management for '
                    'the pluggable authentication utility'),
       long_description=(
         read('README.txt')
-        + '\n\n' +
-        'Detailed Documentation\n' +
-        '----------------------\n'
-        + '\n' +
+        + '\n\n.. contents::\n\n' +
         read('src', 'zope', 'app', 'authentication', 'README.txt')
         + '\n\n' +
         read('src', 'zope', 'app', 'authentication', 'principalfolder.txt')
@@ -63,7 +60,7 @@
       package_dir = {'': 'src'},
       extras_require=dict(test=[
           'zope.app.testing',
-          'zope.app.securitypolicy', # needed in browser tests
+          'zope.securitypolicy',
           'zope.app.zcmlfiles',
           'zope.securitypolicy',
           'zope.testbrowser',

Modified: zope.app.authentication/trunk/src/zope/app/authentication/browser/configure.zcml
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/configure.zcml	2010-09-25 08:10:36 UTC (rev 116798)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/configure.zcml	2010-09-25 09:03:24 UTC (rev 116799)
@@ -35,7 +35,7 @@
       for="..interfaces.IPluggableAuthentication"
       name="addRegistration.html"
       permission="zope.ManageSite"
-      class=".register.AddAuthenticationRegistration" 
+      class=".register.AddAuthenticationRegistration"
       />
 
   <editform
@@ -88,4 +88,6 @@
       factory=".schemasearch.QuerySchemaSearchView"
       />
 
+  <include file="grant.zcml" />
+
 </configure>

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/grant.zcml (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/configure.zcml)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/grant.zcml	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/grant.zcml	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,66 @@
+<configure
+    xmlns="http://namespaces.zope.org/zope"
+    xmlns:browser="http://namespaces.zope.org/browser"
+    i18n_domain="zope">
+
+<!-- Role Permissions -->
+
+  <!-- Note that we've moved this to the site manager! -->
+  <!-- The role-permission mapping is really the domain of programmers -->
+
+  <browser:pages
+      for="zope.app.component.interfaces.ILocalSiteManager"
+      permission="zope.Security"
+      class=".rolepermissionview.RolePermissionView">
+    <browser:page
+        name="AllRolePermissions.html"
+        template="manage_access.pt"
+        menu="zmi_actions"
+        title="Role-Permissions"
+        />
+    <!-- menu="zmi_actions" title="Role Permissions" / -->
+    <browser:page
+        name="RolePermissions.html"
+        template="manage_roleform.pt"
+        />
+    <browser:page
+        name="RolesWithPermission.html"
+        template="manage_permissionform.pt"
+        />
+  </browser:pages>
+
+  <class class=".rolepermissionview.PermissionRoles">
+    <require
+        permission="zope.Security"
+        attributes="roles rolesInfo id title description" />
+  </class>
+
+  <class class=".rolepermissionview.RolePermissions">
+    <require
+        permission="zope.Security"
+        attributes="permissions permissionsInfo id title description" />
+  </class>
+
+<!-- RadioWidget for build a matrix for granting permissions -->
+  <view
+      type="zope.publisher.interfaces.browser.IBrowserRequest"
+      for="zope.schema.interfaces.IChoice
+           zope.securitypolicy.interfaces.IGrantVocabulary"
+      provides="zope.app.form.interfaces.IInputWidget"
+      factory=".granting.GrantWidget"
+      permission="zope.Public"
+      />
+
+<!-- Granting Roles and Permissions to Principals -->
+
+  <browser:page
+      for="zope.annotation.interfaces.IAnnotatable"
+      name="grant.html"
+      permission="zope.Security"
+      template="granting.pt"
+      class=".granting.Granting"
+      menu="zmi_actions"
+      title="Grant"
+      />
+
+</configure>

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.pt (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/granting.pt)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.pt	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.pt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,85 @@
+<html metal:use-macro="context/@@standard_macros/page"
+    i18n:domain="zope">
+<body>
+<div metal:fill-slot="body" i18n:domain="zope">
+  <h2 i18n:translate="">Granting Roles and Permissions to Principals</h2>
+  <p tal:define="status view/status"
+     tal:condition="status"
+     tal:content="status" i18n:translate=""/>
+  &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
+  &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
+
+  <form action="" method="POST">
+
+    <div tal:content="structure view/principal_widget">...</div>
+
+    <div tal:condition="view/principal">
+
+      <h2 i18n:translate="">Grants for the selected principal</h2>
+      <input type="submit" name="GRANT_SUBMIT" value="Change" 
+             i18n:attributes="value grant-submit" />
+
+      <table width="100%" border="0">
+        <tr>
+          <td valign="top">
+            <table class="matrix">
+              <tr>
+                <td i18n:translate=""><strong>Roles</strong>&nbsp;</td>
+                <td i18n:translate=""><strong>Allow</strong>&nbsp;</td>
+                <td i18n:translate=""><strong>Unset</strong>&nbsp;</td>
+                <td i18n:translate=""><strong>Deny</strong>&nbsp;</td>
+              </tr>
+              <tr tal:repeat="widget view/roles">
+                <td valign="top" nowrap>
+                  <div class="label">
+                    <label for="field.name" title="The widget's hint"
+                           tal:attributes="for widget/name; title widget/hint"
+                           tal:content="widget/label"
+                           i18n:translate="">The Label</label>
+                  </div>
+                </td>
+                <tal:block tal:content="structure widget">
+                  roles widget
+                </tal:block>
+              </tr>
+              <tr>
+                <td colspan="2"><a href="#top" i18n:translate="">^ top</a></td>
+              </tr>
+            </table>
+          </td>
+          <td valign="top">
+            <table class="matrix">
+              <tr>
+                <td i18n:translate=""><strong>Permissions</strong>&nbsp;</td>
+                <td i18n:translate=""><strong>Allow</strong>&nbsp;</td>
+                <td i18n:translate=""><strong>Unset</strong>&nbsp;</td>
+                <td i18n:translate=""><strong>Deny</strong>&nbsp;</td>
+              </tr>
+              <tr tal:repeat="widget view/permissions">
+                <td valign="top" nowrap>
+                  <div class="label">
+                    <label for="field.name" title="The widget's hint"
+                           tal:attributes="for widget/name; title widget/hint"
+                           tal:content="widget/label"
+                           i18n:translate="">The Label</label>
+                  </div>
+                </td>
+                <tal:block tal:content="structure widget">
+                  permission widget
+                </tal:block>
+              </tr>
+              <tr>
+                <td colspan="2"><a href="#top" i18n:translate="">^ top</a></td>
+              </tr>
+            </table>
+          </td>
+        </tr>
+      </table>
+      <input type="submit" name="GRANT_SUBMIT" value="Change" 
+             i18n:attributes="value grant-submit" />
+
+    </div>
+  </form>
+</div>
+</body>
+</html>

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.py (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/granting.py)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.py	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.py	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,241 @@
+##############################################################################
+#
+# Copyright (c) 2004 Zope Corporation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Granting Roles and Permissions to Principals
+
+$Id$
+"""
+__docformat__ = "reStructuredText"
+
+import zope.schema
+from zope.component import getUtilitiesFor
+from zope.schema.vocabulary import SimpleTerm
+from zope.i18nmessageid import ZopeMessageFactory as _
+from zope.securitypolicy.interfaces import Allow, Unset, Deny
+from zope.securitypolicy.interfaces import IPrincipalPermissionManager
+from zope.securitypolicy.interfaces import IPrincipalRoleManager
+from zope.securitypolicy.interfaces import IRole
+from zope.securitypolicy.vocabulary import GrantVocabulary
+
+from zope.authentication.principal import PrincipalSource
+from zope.app.form.utility import setUpWidget
+from zope.app.form.browser import RadioWidget
+from zope.app.form.browser.widget import renderElement
+from zope.app.form.interfaces import MissingInputError
+from zope.app.form.interfaces import IInputWidget
+from zope.security.interfaces import IPermission
+
+
+settings_vocabulary = GrantVocabulary(
+    [SimpleTerm(Allow, token="allow", title=_('Allow')),
+     SimpleTerm(Unset, token="unset", title=_('Unset')),
+     SimpleTerm(Deny,  token='deny',  title=_('Deny')),
+     ])
+
+
+class GrantWidget(RadioWidget):
+    """Grant widget for building a colorized matrix.
+
+    The matrix shows anytime the status if you edit the radio widgets.
+    This special widget shows the radio input field without labels.
+    The labels are added in the header of the table. The order of the radio
+    input fields is 'Allowed', 'Unset', 'Deny'.
+
+    """
+    orientation = "horizontal"
+    _tdTemplate = (
+        u'\n<td class="%s">\n<center>\n<label for="%s" title="%s">\n'
+        u'%s\n</label>\n</center>\n</td>\n'
+        )
+
+    def __call__(self):
+        """See IBrowserWidget."""
+        value = self._getFormValue()
+        contents = []
+        have_results = False
+
+        return self.renderValue(value)
+
+
+    def renderItem(self, index, text, value, name, cssClass):
+        """Render an item of the list. 
+
+        Revert the order of label and text. Added field id to the lable
+        attribute.
+
+        Added tabel td tags for fit in the matrix table.
+
+        """
+
+        tdClass = ''
+        id = '%s.%s' % (name, index)
+        elem = renderElement(u'input',
+                             value=value,
+                             name=name,
+                             id=id,
+                             cssClass=cssClass,
+                             type='radio',
+                             extra = 'onclick="changeMatrix(this);"')
+        return self._tdTemplate % (tdClass, id, text, elem)
+
+    def renderSelectedItem(self, index, text, value, name, cssClass):
+        """Render a selected item of the list. 
+
+        Revert the order of label and text. Added field id to the lable
+        attribute.
+        """
+
+        tdClass = 'default'
+        id = '%s.%s' % (name, index)
+        elem = renderElement(u'input',
+                             value=value,
+                             name=name,
+                             id=id,
+                             cssClass=cssClass,
+                             checked="checked",
+                             type='radio',
+                             extra = 'onclick="changeMatrix(this);"')
+        return self._tdTemplate % (tdClass, id, text, elem)
+
+    def renderItems(self, value):
+        # check if we want to select first item, the previously selected item
+        # or the "no value" item.
+        no_value = None
+        if (value == self.context.missing_value
+            and getattr(self, 'firstItem', False)
+            and len(self.vocabulary) > 0):
+            if self.context.required:
+                # Grab the first item from the iterator:
+                values = [iter(self.vocabulary).next().value]
+            else:
+                # the "no value" option will be checked
+                no_value = 'checked'
+        elif value != self.context.missing_value:
+            values = [value]
+        else:
+            values = []
+
+        items = self.renderItemsWithValues(values)
+        return items
+
+    def renderValue(self, value):
+        rendered_items = self.renderItems(value)
+        return " ".join(rendered_items)
+
+
+
+class Granting(object):
+
+    principal = None
+
+    principal_field = zope.schema.Choice(
+        __name__ = 'principal',
+        source=PrincipalSource(),
+        required=True)
+
+    def __init__(self, context, request):
+        self.context = context
+        self.request = request
+
+    def status(self):
+        setUpWidget(self, 'principal', self.principal_field, IInputWidget)
+        if not self.principal_widget.hasInput():
+            return u''
+        try:
+            principal = self.principal_widget.getInputValue()
+        except MissingInputError:
+            return u''
+
+        self.principal = principal
+
+        # Make sure we can use the principal id in a form by base64ing it
+        principal_token = unicode(principal).encode('base64').strip().replace(
+            '=', '_')
+
+        roles = [role for name, role in getUtilitiesFor(IRole)]
+        roles.sort(lambda x, y: cmp(x.title, y.title))
+        principal_roles = IPrincipalRoleManager(self.context)
+
+        self.roles = []
+        for role in roles:
+            name = principal_token + '.role.'+role.id
+            field = zope.schema.Choice(__name__= name,
+                                       title=role.title,
+                                       vocabulary=settings_vocabulary)
+            setUpWidget(self, name, field, IInputWidget,
+                        principal_roles.getSetting(role.id, principal))
+            self.roles.append(getattr(self, name+'_widget'))
+
+        perms = [perm for name, perm in getUtilitiesFor(IPermission)]
+        perms.sort(lambda x, y: cmp(x.title, y.title))
+        principal_perms = IPrincipalPermissionManager(self.context)
+
+        self.permissions = []
+        for perm in perms:
+            if perm.id == 'zope.Public':
+                continue
+            name = principal_token + '.permission.'+perm.id
+            field = zope.schema.Choice(__name__=name,
+                                       title=perm.title,
+                                       vocabulary=settings_vocabulary)
+            setUpWidget(self, name, field, IInputWidget,
+                        principal_perms.getSetting(perm.id, principal))
+            self.permissions.append(
+                getattr(self, name+'_widget'))
+
+        if 'GRANT_SUBMIT' not in self.request:
+            return u''
+
+        for role in roles:
+            name = principal_token + '.role.'+role.id
+            role_widget = getattr(self, name+'_widget')
+            if role_widget.hasInput():
+                try:
+                    setting = role_widget.getInputValue()
+                except MissingInputError:
+                    pass
+                else:
+                    # Arrgh!
+                    if setting is Allow:
+                        principal_roles.assignRoleToPrincipal(
+                            role.id, principal)
+                    elif setting is Deny:
+                        principal_roles.removeRoleFromPrincipal(
+                            role.id, principal)
+                    else:
+                        principal_roles.unsetRoleForPrincipal(
+                            role.id, principal)
+
+        for perm in perms:
+            if perm.id == 'zope.Public':
+                continue
+            name = principal_token + '.permission.'+perm.id
+            perm_widget = getattr(self, name+'_widget')
+            if perm_widget.hasInput():
+                try:
+                    setting = perm_widget.getInputValue()
+                except MissingInputError:
+                    pass
+                else:
+                    # Arrgh!
+                    if setting is Allow:
+                        principal_perms.grantPermissionToPrincipal(
+                            perm.id, principal)
+                    elif setting is Deny:
+                        principal_perms.denyPermissionToPrincipal(
+                            perm.id, principal)
+                    else:
+                        principal_perms.unsetPermissionForPrincipal(
+                            perm.id, principal)
+
+        return _('Grants updated.')

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.txt (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/granting.txt)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.txt	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/granting.txt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,203 @@
+Granting View
+=============
+
+The granting view allows the user to grant permissions and roles to
+principals. The view unfortunately depends on a lot of other components:
+
+  - Roles
+
+    >>> from zope.app.testing import ztapi
+    >>> from zope.securitypolicy.role import Role
+    >>> from zope.securitypolicy.interfaces import IRole
+    >>> ztapi.provideUtility(IRole, Role(u'role1', u'Role 1'), u'role1')
+    >>> ztapi.provideUtility(IRole, Role(u'role2', u'Role 2'), u'role2')
+    >>> ztapi.provideUtility(IRole, Role(u'role3', u'Role 3'), u'role3')
+
+  - Permissions
+
+    >>> from zope.security.permission import Permission
+    >>> from zope.security.interfaces import IPermission
+    >>> ztapi.provideUtility(IPermission, Permission(u'permission1',
+    ...                      u'Permission 1'), u'permission1')
+    >>> ztapi.provideUtility(IPermission, Permission(u'permission2',
+    ...                      u'Permission 2'), u'permission2')
+    >>> ztapi.provideUtility(IPermission, Permission(u'permission3',
+    ...                      u'Permission 3'), u'permission3')
+
+  - Authentication Utility
+
+    >>> class Principal:
+    ...     def __init__(self, id, title): self.id, self.title = id, title
+
+    >>> from zope.app.security.interfaces import IAuthentication
+    >>> from zope.app.security.interfaces import PrincipalLookupError
+    >>> from zope.interface import implements
+    >>> class AuthUtility:
+    ...     implements(IAuthentication)
+    ...     data = {'jim': Principal('jim', 'Jim Fulton'),
+    ...             'stephan': Principal('stephan', 'Stephan Richter')}
+    ...
+    ...     def getPrincipal(self, id):
+    ...         try:
+    ...             return self.data.get(id)
+    ...         except KeyError:
+    ...             raise PrincipalLookupError(id)
+    ...
+    ...     def getPrincipals(self, search):
+    ...         return [principal
+    ...                 for principal in self.data.values()
+    ...                 if search in principal.title]
+
+    >>> ztapi.provideUtility(IAuthentication, AuthUtility())
+
+  - Security-related Adapters
+
+    >>> from zope.annotation.interfaces import IAnnotatable
+    >>> from zope.securitypolicy.interfaces import IPrincipalRoleManager
+    >>> from zope.securitypolicy.principalrole import \
+    ...     AnnotationPrincipalRoleManager
+
+    >>> ztapi.provideAdapter(IAnnotatable, IPrincipalRoleManager,
+    ...                      AnnotationPrincipalRoleManager)
+
+    >>> from zope.securitypolicy.interfaces import \
+    ...     IPrincipalPermissionManager
+    >>> from zope.securitypolicy.principalpermission import \
+    ...     AnnotationPrincipalPermissionManager
+
+    >>> ztapi.provideAdapter(IAnnotatable, IPrincipalPermissionManager,
+    ...                      AnnotationPrincipalPermissionManager)
+
+  - Vocabulary Choice Widgets
+
+    >>> from zope.schema.interfaces import IChoice
+    >>> from zope.app.form.browser import ChoiceInputWidget
+    >>> from zope.app.form.interfaces import IInputWidget
+    >>> ztapi.browserViewProviding(IChoice, ChoiceInputWidget, IInputWidget)
+
+    >>> from zope.schema.interfaces import IVocabularyTokenized
+    >>> from zope.publisher.interfaces.browser import IBrowserRequest
+    >>> from zope.app.form.browser import DropdownWidget
+    >>> ztapi.provideMultiView((IChoice, IVocabularyTokenized),
+    ...                        IBrowserRequest, IInputWidget, '',
+    ...                        DropdownWidget)
+
+  - Support Views for the Principal Source Widget
+
+    >>> from zope.app.security.interfaces import IPrincipalSource
+    >>> from zope.app.security.browser.principalterms import PrincipalTerms
+    >>> from zope.browser.interfaces import ITerms
+    >>> ztapi.browserViewProviding(IPrincipalSource, PrincipalTerms, ITerms)
+
+    >>> from zope.app.security.browser.auth import AuthUtilitySearchView
+    >>> from zope.app.form.browser.interfaces import ISourceQueryView
+    >>> ztapi.browserViewProviding(IAuthentication,
+    ...                            AuthUtilitySearchView,
+    ...                            ISourceQueryView)
+
+
+    >>> from zope.schema.interfaces import ISource
+    >>> from zope.app.form.browser.source import SourceInputWidget
+    >>> ztapi.provideMultiView((IChoice, ISource), IBrowserRequest,
+    ...                        IInputWidget, '', SourceInputWidget)
+
+  - Attribute Annotatable Adapter
+
+    >>> from zope.app.testing import setup
+    >>> setup.setUpAnnotations()
+    >>> setup.setUpSiteManagerLookup()
+
+  - Content Object
+
+    >>> from zope.annotation.interfaces import IAttributeAnnotatable
+    >>> class Content:
+    ...     implements(IAttributeAnnotatable)
+    ...     __annotations__ = {}
+
+  (This is Jim's understanding of a "easy" setup!)
+
+Now that we have all the components we need, let's create *the* view.
+
+  >>> ob = Content()
+  >>> from zope.publisher.browser import TestRequest
+  >>> request = TestRequest()
+
+  >>> from zope.app.authentication.browser.granting import Granting
+  >>> view = Granting(ob, request)
+
+If we call status, we get nothing and the view's principal attribute is `None`:
+
+  >>> view.status()
+  u''
+  >>> view.principal
+
+Since we have not selected a principal, we have no role or permission widgets:
+
+  >>> getattr(view, 'roles', None)
+  >>> getattr(view, 'permissions', None)
+
+Now that we have a selected principal, then
+
+
+  >>> view.request.form['field.principal.displayed'] = 'y'
+  >>> view.request.form['field.principal'] = 'amlt'
+
+(Yes, 'amlt' is the base 64 code for 'jim'.)
+
+  >>> view.status()
+  u''
+
+and now the `view.principal` is set:
+
+  >>> view.principal
+  'jim'
+
+Now we should have a list of role and permission widgets, and all of them
+should be unset, because do not have any settings for 'jim'.
+
+  >>> [role.context.title for role in view.roles]
+  [u'Role 1', u'Role 2', u'Role 3']
+  >>> [perm.context.title for perm in view.permissions]
+  [u'Permission 1', u'Permission 2', u'Permission 3']
+
+Now we change some settings and submit the form:
+
+  >>> from zope.securitypolicy.interfaces import Allow, Deny, Unset
+
+  >>> view.request.form['field.amlt.role.role1'] = 'unset'
+  >>> view.request.form['field.amlt.role.role1-empty-makrer'] = 1
+  >>> view.request.form['field.amlt.role.role2'] = 'allow'
+  >>> view.request.form['field.amlt.role.role2-empty-makrer'] = 1
+  >>> view.request.form['field.amlt.role.role3'] = 'deny'
+  >>> view.request.form['field.amlt.role.role3-empty-makrer'] = 1
+
+  >>> view.request.form['field.amlt.permission.permission1'] = 'unset'
+  >>> view.request.form['field.amlt.permission.permission1-empty-makrer'] = 1
+  >>> view.request.form['field.amlt.permission.permission2'] = 'allow'
+  >>> view.request.form['field.amlt.permission.permission2-empty-makrer'] = 1
+  >>> view.request.form['field.amlt.permission.permission3'] = 'deny'
+  >>> view.request.form['field.amlt.permission.permission3-empty-makrer'] = 1
+
+  >>> view.request.form['GRANT_SUBMIT'] = 'Submit'
+
+If we get the status now, the data should be written and a status message
+should be returned:
+
+  >>> view.status()
+  u'Grants updated.'
+
+  >>> roles = IPrincipalRoleManager(ob)
+  >>> roles.getSetting('role1', 'jim') is Unset
+  True
+  >>> roles.getSetting('role2', 'jim') is Allow
+  True
+  >>> roles.getSetting('role3', 'jim') is Deny
+  True
+
+  >>> roles = IPrincipalPermissionManager(ob)
+  >>> roles.getSetting('permission1', 'jim') is Unset
+  True
+  >>> roles.getSetting('permission2', 'jim') is Allow
+  True
+  >>> roles.getSetting('permission3', 'jim') is Deny
+  True

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_access.pt (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/manage_access.pt)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_access.pt	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_access.pt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,94 @@
+<html metal:use-macro="context/@@standard_macros/dialog" i18n:domain="zope">
+<head>
+  <tal:block
+      metal:fill-slot="headers"
+      tal:define="global pagetip view/pagetip"
+      />
+</head>
+<body>
+<div metal:fill-slot="body">
+
+   <p tal:define="status view/update"
+      tal:condition="status"
+      tal:content="status" i18n:translate=""/>
+
+  <form action="AllRolePermissions.html" method="POST">
+
+    <table width="100%" cellspacing="0" cellpadding="2" border="0"
+           nowrap="nowrap">
+
+      <tr class="list-header">
+        <td align="left" valign="top">
+          <div class="form-label">
+            <strong i18n:translate="">Permission</strong>
+          </div>
+        </td>
+        <td align="left">
+          <div class="form-label">
+            <strong i18n:translate="">Roles</strong>
+          </div>
+        </td>
+      </tr>
+
+      <tr class="row-normal">
+        <td></td>
+        <td align="center" tal:repeat="role view/roles">
+          <div class="list-item">
+            <a href="RolePermissions.html"
+              tal:attributes="
+              href string:RolePermissions.html?role_to_manage=${role/id}"
+              tal:content="role/title" i18n:translate="">Anonymous</a>
+            <input type="hidden" name="r0" value=""
+              tal:attributes="
+              name string:r${repeat/role/index};
+              value  string:${role/id}" />
+
+          </div>
+        </td>
+      </tr>
+
+      <tbody tal:repeat="perm view/permissionRoles">
+      <tr class="row-normal"
+          tal:attributes="class 
+             python:path('repeat/perm/even') and 'row-normal' or 'row-hilite'">
+        <td align="left" nowrap="nowrap">
+          <div class="list-item">
+             <a href="RolesWithPermission.html"
+                tal:attributes="href
+           string:RolesWithPermission.html?permission_to_manage=${perm/id}"
+                tal:content="perm/title"
+                i18n:translate="">Access Transient Objects</a>
+             <input type="hidden" name="r0" value=""
+                 tal:attributes="
+                 name string:p${repeat/perm/index};
+                 value  string:${perm/id}" />
+          </div>
+        </td>
+        <td align="center" tal:repeat="setting perm/roleSettings">
+          <select name="p0r0"
+              tal:attributes="name
+                  string:p${repeat/perm/index}r${repeat/setting/index}">
+            <option value="Unset"
+                tal:repeat="option view/availableSettings"
+                tal:attributes="value option/id;
+                                selected python:setting == option['id']"
+                tal:content="option/shorttitle">+</option>
+          </select>
+        </td>
+      </tr>
+      </tbody>
+
+      <tr>
+        <td colspan="5" align="left">
+          <div class="form-element">
+            <input class="form-element" type="submit" name="SUBMIT"
+                   value="Save Changes" i18n:attributes="value" />
+          </div>
+        </td>
+      </tr>
+    </table>
+  </form>
+
+</div>
+</body>
+</html>

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_permissionform.pt (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/manage_permissionform.pt)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_permissionform.pt	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_permissionform.pt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,92 @@
+<html metal:use-macro="context/@@standard_macros/page"
+    i18n:domain="zope">
+<head>
+  <style metal:fill-slot="headers" type="text/css">
+    <!--
+    .row-normal {
+      background-color: #ffffff;
+      border: none;
+    }
+
+    .row-hilite {
+      background-color: #efefef;
+      border: none;
+    }
+    -->
+  </style>
+</head>
+<body>
+<div metal:fill-slot="body">
+
+  <p tal:define="status view/update"
+     tal:condition="status"
+     tal:content="status" />
+
+  <div tal:define="perm 
+      python:view.permissionForID(request.get('permission_to_manage'))">
+
+    <p class="form-text" i18n:translate="">
+      Roles which are granted the permission
+      <strong tal:content="perm/title" 
+          i18n:name="perm_title" i18n:translate="">Change DTML Methods</strong>
+      (id: <strong tal:content="perm/id"
+          i18n:name="perm_id">Zope.Some.Permission</strong>)
+    </p>
+
+    <form action="AllRolePermissions.html" method="post">
+
+      <input type="hidden" name="permission_id" value="Permission Name"
+          tal:attributes="value perm/id" />
+
+        <div class="form-element">
+
+          <table width="100%" cellspacing="0" cellpadding="2" border="0" 
+              nowrap="nowrap">
+
+            <tr class="list-header">
+              <td align="left" valign="top">
+                <div class="form-label">
+                  <strong i18n:translate="">Role</strong>
+                </div>
+              </td>
+              <td align="left">
+                <div class="form-label">
+                  <strong i18n:translate="">Setting</strong>
+                </div>
+              </td>
+            </tr>
+
+            <tr class="row-normal"
+                tal:repeat="setting perm/roleSettings"
+                tal:attributes="class
+          python:path('repeat/setting/even') and 'row-normal' or 'row-hilite'">
+              <td align="left" valign="top"
+                  tal:define="ir repeat/setting/index"
+                  tal:content="python:path('view/roles')[ir].id">
+                Manager
+              </td>
+              <td>
+                <select name="settings:list">
+                    <option value="Unset"
+                       tal:repeat="option view/availableSettings"
+                       tal:attributes="value option/id;
+                                       selected python:setting == option['id']"
+                       tal:content="option/shorttitle"
+                       i18n:translate="">+</option>
+                </select>
+              </td>
+            </tr>
+        </table>
+
+      </div>
+
+      <div class="form-element">
+        <input class="form-element" type="submit" name="SUBMIT_PERMS" 
+            value="Save Changes" i18n:attributes="value save-changes-button"/>
+      </div>
+    </form>
+
+  </div>
+</div>
+</body>
+</html>

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_roleform.pt (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/manage_roleform.pt)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_roleform.pt	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/manage_roleform.pt	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,76 @@
+<html metal:use-macro="context/@@standard_macros/page"
+    i18n:domain="zope">
+<body>
+<div metal:fill-slot="body">
+
+  <p tal:define="status view/update"
+     tal:condition="status"
+     tal:content="status" i18n:translate=""/>
+
+
+  <div tal:define="role 
+          python:view.roleForID(request.get('role_to_manage'))" tal:omit-tag="">
+
+    <p class="form-help" i18n:translate="">
+      This page shows the permissions allowed and denied the role
+        <strong tal:content="role/title"
+                i18n:name="role_title"
+                i18n:translate="">Great Master Guru</strong>
+        (id: <strong tal:content="role/id"
+                i18n:name="role_id">Zope.Some.Role</strong>).
+      To change settings, simply select different permissions in the
+      Allow or Deny lists. Make sure you don't select the same
+        permission in both lists though.
+    </p>
+
+
+    <form action="AllRolePermissions.html" method="POST">
+      <input type="hidden" name="role_id" value="Role ID"
+             tal:attributes="value role/id" />
+
+      <table width="100%" cellspacing="0" cellpadding="2" border="0" 
+             nowrap="nowrap"
+             tal:define="availableSettings 
+                python:view.availableSettings(noacquire=True)">
+
+        <tr class="list-header">
+          <td align="left" valign="top"
+              tal:repeat="setting availableSettings">
+            <div class="form-label">
+              <strong tal:content="setting/title"
+                    i18n:translate="">Allow</strong>
+            </div>
+          </td>
+        </tr>
+
+        <tr>
+          <td align="left" valign="top"
+              tal:repeat="settinginfo availableSettings">
+            <div class="form-element">
+              <select name="Unset:list" multiple="multiple" size="20"
+                      tal:define="setting settinginfo/id"
+                      tal:attributes="name string:${setting}:list">
+              <option tal:repeat="permissioninfo role/permissionsInfo"
+                      tal:content="permissioninfo/title"
+                      i18n:translate=""
+                      tal:attributes="selected
+                         python:path('permissioninfo/setting') == setting;
+                                      value permissioninfo/id"
+                      >Sample Permission</option>
+              </select>
+            </div>
+          </td>
+        </tr>
+      </table>
+
+      <div class="form-element">
+        <input class="form-element" type="submit" name="SUBMIT_ROLE" 
+            value="Save Changes" i18n:attributes="value save-changes-button"/>
+      </div>
+    </form>
+
+  </div>
+
+</div>
+</body>
+</html>

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/rolepermissionview.py (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/rolepermissionview.py)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/rolepermissionview.py	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/rolepermissionview.py	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,240 @@
+##############################################################################
+#
+# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Role Permission View Classes
+
+$Id$
+"""
+from datetime import datetime
+
+from zope.component import getUtilitiesFor, getUtility
+from zope.i18n import translate
+from zope.interface import implements
+from zope.exceptions.interfaces import UserError
+from zope.i18nmessageid import ZopeMessageFactory as _
+
+from zope.security.interfaces import IPermission
+from zope.securitypolicy.interfaces import Unset, Allow, Deny
+from zope.securitypolicy.interfaces import IRole, IRolePermissionManager
+
+class RolePermissionView(object):
+
+    _pagetip = _("""For each permission you want to grant (or deny) to a role,
+        set the entry for that permission and role to a '+' (or '-').
+        Permissions are shown on the left side, going down.
+        Roles are shown accross the top.
+        """)
+
+    def pagetip(self):
+        return translate(self._pagetip, context=self.request)
+
+    def roles(self):
+        roles = getattr(self, '_roles', None)
+        if roles is None:
+            roles = [
+                (translate(role.title, context=self.request).strip(), role)
+                for name, role in getUtilitiesFor(IRole)]
+            roles.sort()
+            roles = self._roles = [role for name, role in roles]
+        return roles
+
+    def permissions(self):
+        permissions = getattr(self, '_permissions', None)
+        if permissions is None:
+            permissions = [
+                (translate(perm.title, context=self.request).strip(), perm)
+                for name, perm in getUtilitiesFor(IPermission)
+                if name != 'zope.Public']
+            permissions.sort()
+            permissions = self._permissions = [perm
+                                               for name, perm in permissions]
+
+        return permissions
+
+    def availableSettings(self, noacquire=False):
+        aq = {'id': Unset.getName(), 'shorttitle': ' ',
+              'title': _('permission-acquire', 'Acquire')}
+        rest = [{'id': Allow.getName(), 'shorttitle': '+',
+                 'title': _('permission-allow', 'Allow')},
+                {'id': Deny.getName(), 'shorttitle': '-',
+                 'title': _('permission-deny', 'Deny')},
+                ]
+        if noacquire:
+            return rest
+        else:
+            return [aq]+rest
+
+    def permissionRoles(self):
+        context = self.context.__parent__
+        roles = self.roles()
+        return [PermissionRoles(permission, context, roles)
+                for permission in self.permissions()]
+
+    def permissionForID(self, pid):
+        roles = self.roles()
+        perm = getUtility(IPermission, pid)
+        return PermissionRoles(perm, self.context.__parent__, roles)
+
+    def roleForID(self, rid):
+        permissions = self.permissions()
+        role = getUtility(IRole, rid)
+        return RolePermissions(role, self.context.__parent__, permissions)
+
+
+    def update(self, testing=None):
+        status = ''
+        changed = False
+
+        if 'SUBMIT' in self.request:
+            roles       = [r.id for r in self.roles()]
+            permissions = [p.id for p in self.permissions()]
+            prm         = IRolePermissionManager(self.context.__parent__)
+            for ip in range(len(permissions)):
+                rperm = self.request.get("p%s" % ip)
+                if rperm not in permissions: continue
+                for ir in range(len(roles)):
+                    rrole = self.request.get("r%s" % ir)
+                    if rrole not in roles: continue
+                    setting = self.request.get("p%sr%s" % (ip, ir), None)
+                    if setting is not None:
+                        if setting == Unset.getName():
+                            prm.unsetPermissionFromRole(rperm, rrole)
+                        elif setting == Allow.getName():
+                            prm.grantPermissionToRole(rperm, rrole)
+                        elif setting == Deny.getName():
+                            prm.denyPermissionToRole(rperm, rrole)
+                        else:
+                            raise ValueError("Incorrect setting: %s" % setting)
+            changed = True
+
+        if 'SUBMIT_PERMS' in self.request:
+            prm = IRolePermissionManager(self.context.__parent__)
+            roles = self.roles()
+            rperm = self.request.get('permission_id')
+            settings = self.request.get('settings', ())
+            for ir in range(len(roles)):
+                rrole = roles[ir].id
+                setting = settings[ir]
+                if setting == Unset.getName():
+                    prm.unsetPermissionFromRole(rperm, rrole)
+                elif setting == Allow.getName():
+                    prm.grantPermissionToRole(rperm, rrole)
+                elif setting == Deny.getName():
+                    prm.denyPermissionToRole(rperm, rrole)
+                else:
+                    raise ValueError("Incorrect setting: %s" % setting)
+            changed = True
+
+        if 'SUBMIT_ROLE' in self.request:
+            role_id = self.request.get('role_id')
+            prm = IRolePermissionManager(self.context.__parent__)
+            allowed = self.request.get(Allow.getName(), ())
+            denied = self.request.get(Deny.getName(), ())
+            for permission in self.permissions():
+                rperm = permission.id
+                if rperm in allowed and rperm in denied:
+                    permission_translated = translate(
+                        permission.title, context=self.request)
+                    msg = _('You choose both allow and deny for permission'
+                            ' "${permission}". This is not allowed.',
+                            mapping = {'permission': permission_translated})
+                    raise UserError(msg)
+                if rperm in allowed:
+                    prm.grantPermissionToRole(rperm, role_id)
+                elif rperm in denied:
+                    prm.denyPermissionToRole(rperm, role_id)
+                else:
+                    prm.unsetPermissionFromRole(rperm, role_id)
+            changed = True
+
+        if changed:
+            formatter = self.request.locale.dates.getFormatter(
+                'dateTime', 'medium')
+            status = _("Settings changed at ${date_time}",
+                       mapping={'date_time':
+                                formatter.format(datetime.utcnow())})
+
+        return status
+
+
+class PermissionRoles(object):
+
+    implements(IPermission)
+
+    def __init__(self, permission, context, roles):
+        self._permission = permission
+        self._context    = context
+        self._roles      = roles
+
+    def _getId(self):
+        return self._permission.id
+
+    id = property(_getId)
+
+    def _getTitle(self):
+        return self._permission.title
+
+    title = property(_getTitle)
+
+    def _getDescription(self):
+        return self._permission.description
+
+    description = property(_getDescription)
+
+    def roleSettings(self):
+        """
+        Returns the list of setting names of each role for this permission.
+        """
+        prm = IRolePermissionManager(self._context)
+        proles = prm.getRolesForPermission(self._permission.id)
+        settings = {}
+        for role, setting in proles:
+            settings[role] = setting.getName()
+        nosetting = Unset.getName()
+        return [settings.get(role.id, nosetting) for role in self._roles]
+
+class RolePermissions(object):
+
+    implements(IRole)
+
+    def __init__(self, role, context, permissions):
+        self._role = role
+        self._context = context
+        self._permissions = permissions
+
+    def _getId(self):
+        return self._role.id
+
+    id = property(_getId)
+
+    def _getTitle(self):
+        return self._role.title
+
+    title = property(_getTitle)
+
+    def _getDescription(self):
+        return self._role.description
+
+    description = property(_getDescription)
+
+    def permissionsInfo(self):
+        prm = IRolePermissionManager(self._context)
+        rperms = prm.getPermissionsForRole(self._role.id)
+        settings = {}
+        for permission, setting in rperms:
+            settings[permission] = setting.getName()
+        nosetting = Unset.getName()
+        return [{'id': permission.id,
+                 'title': permission.title,
+                 'setting': settings.get(permission.id, nosetting)}
+                for permission in self._permissions]

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/rolepermissionmanager.py (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/tests/rolepermissionmanager.py)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/rolepermissionmanager.py	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/rolepermissionmanager.py	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,87 @@
+##############################################################################
+#
+# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Test IRolePermissionManager class that has no context.
+
+$Id$
+"""
+
+from zope.interface import implements
+from zope.securitypolicy.interfaces import Allow, Deny, Unset
+from zope.securitypolicy.interfaces import IRolePermissionManager
+from zope.securitypolicy.interfaces import IRolePermissionMap
+from zope.securitypolicy.securitymap import SecurityMap
+
+class RolePermissionManager(object):
+    """
+    provide adapter that manages role permission data in an object attribute
+    """
+
+    implements(IRolePermissionManager, IRolePermissionMap)
+
+    def __init__(self):
+        self._rp = SecurityMap()
+
+    def grantPermissionToRole(self, permission_id, role_id):
+        ''' See the interface IRolePermissionManager '''
+        rp = self._getRolePermissions(create=1)
+        rp.addCell(permission_id, role_id, Allow)
+
+    def denyPermissionToRole(self, permission_id, role_id):
+        ''' See the interface IRolePermissionManager '''
+        rp = self._getRolePermissions(create=1)
+        rp.addCell(permission_id, role_id, Deny)
+
+    def unsetPermissionFromRole(self, permission_id, role_id):
+        ''' See the interface IRolePermissionManager '''
+        rp = self._getRolePermissions()
+        # Only unset if there is a security map, otherwise, we're done
+        if rp:
+            rp.delCell(permission_id, role_id)
+
+    def getRolesForPermission(self, permission_id):
+        '''See interface IRolePermissionMap'''
+        rp = self._getRolePermissions()
+        if rp:
+            return rp.getRow(permission_id)
+        else:
+            return []
+
+    def getPermissionsForRole(self, role_id):
+        '''See interface IRolePermissionMap'''
+        rp = self._getRolePermissions()
+        if rp:
+            return rp.getCol(role_id)
+        else:
+            return []
+
+    def getRolesAndPermissions(self):
+        '''See interface IRolePermissionMap'''
+        rp = self._getRolePermissions()
+        if rp:
+            return rp.getAllCells()
+        else:
+            return []
+
+    def getSetting(self, permission_id, role_id):
+        '''See interface IRolePermissionMap'''
+        rp = self._getRolePermissions()
+        if rp:
+            return rp.queryCell(permission_id, role_id)
+        else:
+            return Unset
+
+    def _getRolePermissions(self, create=0):
+        """Get the role permission map stored in the context, optionally
+           creating one if necessary"""
+        return self._rp

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_granting.py (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/tests/test_granting.py)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_granting.py	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_granting.py	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,23 @@
+##############################################################################
+#
+# Copyright (c) 2004 Zope Corporation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Security Policy Granting Views Tests"""
+
+from zope.app.testing import placelesssetup
+import doctest
+import unittest
+
+def test_suite():
+    return doctest.DocFileSuite('../granting.txt',
+                                setUp=placelesssetup.setUp,
+                                tearDown=placelesssetup.tearDown)

Copied: zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_rolepermissionview.py (from rev 116784, zope.app.securitypolicy/trunk/src/zope/app/securitypolicy/browser/tests/test_rolepermissionview.py)
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_rolepermissionview.py	                        (rev 0)
+++ zope.app.authentication/trunk/src/zope/app/authentication/browser/tests/test_rolepermissionview.py	2010-09-25 09:03:24 UTC (rev 116799)
@@ -0,0 +1,221 @@
+##############################################################################
+#
+# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Role-Permission View Tests
+
+$Id$
+"""
+import unittest
+
+import zope.interface
+from zope.i18n.interfaces import ITranslationDomain
+from zope.i18nmessageid import Message
+from zope.publisher.browser import TestRequest, BrowserView
+from zope.exceptions.interfaces import UserError
+from zope.security.permission import Permission
+from zope.security.interfaces import IPermission
+
+from zope.app.testing import ztapi
+from zope.app.component.testing import PlacefulSetup
+
+from zope.securitypolicy.role import Role
+from zope.securitypolicy.interfaces import IRole
+
+from zope.app.authentication.browser.tests.rolepermissionmanager import \
+     RolePermissionManager
+from zope.app.authentication.browser.rolepermissionview import \
+     RolePermissionView
+
+class RolePermissionView(RolePermissionView, BrowserView):
+    """Adding BrowserView to Utilities; this is usually done by ZCML."""
+
+class TranslationDomain:
+    zope.interface.implements(ITranslationDomain)
+
+    def __init__(self, **translations):
+        self.translations = translations
+
+    def translate(self, msgid, *ignored, **also_ignored):
+        return self.translations.get(msgid, msgid)
+
+
+def defineRole(id, title=None, description=None):
+    role = Role(id, title, description)
+    ztapi.provideUtility(IRole, role, name=role.id)
+    return role
+
+def definePermission(id, title=None, description=None):
+    permission = Permission(id, title, description)
+    ztapi.provideUtility(IPermission, permission, name=permission.id)
+    return permission
+
+class FakeSiteManager:
+
+    def __init__(self, site):
+        self.__parent__ = site
+
+class Test(PlacefulSetup, unittest.TestCase):
+
+    def setUp(self):
+        PlacefulSetup.setUp(self)
+        defineRole('manager', Message('Manager', 'testdomain'))
+        defineRole('member',  Message('Member', 'testdomain'))
+        definePermission('read', Message('Read', 'testdomain'))
+        definePermission('write', Message('Write', 'testdomain'))
+        site = RolePermissionManager()
+        self.view = RolePermissionView(FakeSiteManager(site), None)
+        ztapi.provideUtility(ITranslationDomain,
+                             TranslationDomain(Member="A Member",
+                                               Write="A Write",
+                                               ),
+                             'testdomain')
+
+    def testRoles(self):
+        self.assertEqual([role.title for role in self.view.roles()],
+                         ["Member", "Manager"])
+
+    def testPermisssions(self):
+        self.assertEqual([role.title for role in self.view.permissions()],
+                         ["Write", "Read"])
+
+    def testMatrix(self):
+        roles = self.view.roles()
+        permissions = self.view.permissions()
+
+        #         manager  member
+        # read       +
+        # write      .       -
+        env = {
+            'p0': 'read', 'p1': 'write',
+            'r0': 'manager', 'r1': 'member',
+            'p0r0': 'Allow',
+            'p1r0': 'Unset', 'p1r1': 'Deny',
+            'SUBMIT': 1
+            }
+        self.view.request = TestRequest(environ=env)
+        self.view.update()
+        permissionRoles = self.view.permissionRoles()
+        for ip in range(len(permissionRoles)):
+            permissionRole = permissionRoles[ip]
+            rset = permissionRole.roleSettings()
+            for ir in range(len(rset)):
+                setting = rset[ir]
+                r = roles[ir].id
+                p = permissions[ip].id
+                if setting == 'Allow':
+                    self.failUnless(r == 'manager' and p == 'read')
+                elif setting == 'Deny':
+                    self.failUnless(r == 'member' and p == 'write')
+                else:
+                    self.failUnless(setting == 'Unset')
+
+        #         manager  member
+        # read       -
+        # write      +
+        env = {
+            'p0': 'read', 'p1': 'write',
+            'r0': 'manager', 'r1': 'member',
+            'p0r0': 'Deny',
+            'p1r0': 'Allow', 'p1r1': 'Unset',
+            'SUBMIT': 1
+            }
+        self.view.request = TestRequest(environ=env)
+        self.view.update()
+        permissionRoles = self.view.permissionRoles()
+        for ip in range(len(permissionRoles)):
+            permissionRole = permissionRoles[ip]
+            rset = permissionRole.roleSettings()
+            for ir in range(len(rset)):
+                setting = rset[ir]
+                r = roles[ir].id
+                p = permissions[ip].id
+                if setting == 'Allow':
+                    self.failUnless(r == 'manager' and p == 'write')
+                elif setting == 'Deny':
+                    self.failUnless(r == 'manager' and p == 'read')
+                else:
+                    self.failUnless(setting == 'Unset')
+
+    def testPermissionRoles(self):
+        env={'permission_id': 'write',
+             'settings': ['Allow', 'Unset'],
+             'SUBMIT_PERMS': 1}
+        self.view.request = TestRequest(environ=env)
+        self.view.update()
+        permission = self.view.permissionForID('write')
+        settings = permission.roleSettings()
+        self.assertEquals(settings, ['Allow', 'Unset'])
+
+
+        env={'permission_id': 'write',
+             'settings': ['Unset', 'Deny'],
+             'SUBMIT_PERMS': 1}
+        self.view.request = TestRequest(environ=env)
+        self.view.update()
+        permission = self.view.permissionForID('write')
+        settings = permission.roleSettings()
+        self.assertEquals(settings, ['Unset', 'Deny'])
+
+        env={'permission_id': 'write',
+             'settings': ['Unset', 'foo'],
+             'SUBMIT_PERMS': 1}
+        self.view.request = TestRequest(environ=env)
+        self.assertRaises(ValueError, self.view.update)
+
+    def testRolePermissions(self):
+        env={'Allow': ['read'],
+             'Deny': ['write'],
+             'SUBMIT_ROLE': 1,
+             'role_id': 'member'}
+        self.view.request = TestRequest(environ=env)
+        self.view.update(1)
+        role = self.view.roleForID('member')
+        pinfos = role.permissionsInfo()
+        for pinfo in pinfos:
+            pid = pinfo['id']
+            if pid == 'read':
+                self.assertEquals(pinfo['setting'], 'Allow')
+            if pid == 'write':
+                self.assertEquals(pinfo['setting'], 'Deny')
+
+        env={'Allow': [],
+             'Deny': ['read'],
+             'SUBMIT_ROLE': 1,
+             'role_id': 'member'}
+        self.view.request = TestRequest(environ=env)
+        self.view.update()
+        role = self.view.roleForID('member')
+        pinfos = role.permissionsInfo()
+        for pinfo in pinfos:
+            pid = pinfo['id']
+            if pid == 'read':
+                self.assertEquals(pinfo['setting'], 'Deny')
+            if pid == 'write':
+                self.assertEquals(pinfo['setting'], 'Unset')
+
+
+    def testRolePermissions_UserError(self):
+        env={'Allow': ['read'],
+             'Deny': ['read'],
+             'SUBMIT_ROLE': 1,
+             'role_id': 'member'}
+        self.view.request = TestRequest(environ=env)
+        self.assertRaises(UserError, self.view.update, 1)
+
+
+def test_suite():
+    loader=unittest.TestLoader()
+    return loader.loadTestsFromTestCase(Test)
+
+if __name__=='__main__':
+    unittest.TextTestRunner().run(test_suite())

Modified: zope.app.authentication/trunk/src/zope/app/authentication/ftesting.zcml
===================================================================
--- zope.app.authentication/trunk/src/zope/app/authentication/ftesting.zcml	2010-09-25 08:10:36 UTC (rev 116798)
+++ zope.app.authentication/trunk/src/zope/app/authentication/ftesting.zcml	2010-09-25 09:03:24 UTC (rev 116799)
@@ -13,7 +13,7 @@
   <include package="zope.formlib" />
   <include package="zope.session" />
   <include package="zope.app.authentication" />
-  <include package="zope.app.securitypolicy" />
+  <include package="zope.securitypolicy" />
   <include package="zope.login" />
 
   <securityPolicy
@@ -29,10 +29,6 @@
 
   <grantAll role="zope.Manager" />
 
-  <include
-      package="zope.app.securitypolicy.browser.tests"
-      file="functional.zcml" />
-
   <!-- Principals -->
 
   <unauthenticatedPrincipal
@@ -61,13 +57,6 @@
       login="mgr"
       password="mgrpw" />
 
-  <!-- Bootstrap principal used to make local grant to the principal above -->
-  <principal
-      id="zope.globalmgr"
-      title="Manager"
-      login="globalmgr"
-      password="globalmgrpw" />
+  <grant role="zope.Manager" principal="zope.mgr" />
 
-  <grant role="zope.Manager" principal="zope.globalmgr" />
-
 </configure>



More information about the checkins mailing list