Commit 63cbf5ee authored by David Glick's avatar David Glick

make sure that the browser:view directive doesn't clobber security...

make sure that the browser:view directive doesn't clobber security declarations for attributes which are not included in allowed_attributes or allowed_interface but which already have security declarations in a base class's security info. This is needed to provide access to, e.g., restrictedTraverse on views that subclass Traversable
parent b7d8e8d9
...@@ -11,6 +11,12 @@ http://docs.zope.org/zope2/releases/. ...@@ -11,6 +11,12 @@ http://docs.zope.org/zope2/releases/.
Bugs Fixed Bugs Fixed
++++++++++ ++++++++++
- Fix support for non-public permission attributes in the
browser:view directive so that attributes which are not included in
allowed_interface or allowed_attributes but which have declarations from a
base class's security info don't get their security overwritten to be
private.
- LP #143755: Also catch TypeError when trying to determine an - LP #143755: Also catch TypeError when trying to determine an
indexable value for an object in PluginIndexes.common.UnIndex indexable value for an object in PluginIndexes.common.UnIndex
......
...@@ -315,7 +315,7 @@ class view(zope.app.publisher.browser.viewmeta.view): ...@@ -315,7 +315,7 @@ class view(zope.app.publisher.browser.viewmeta.view):
_context.action( _context.action(
discriminator = ('five:protectName', newclass, attr), discriminator = ('five:protectName', newclass, attr),
callable = protectName, callable = protectName,
args = (newclass, attr, CheckerPrivateId) args = (newclass, attr, CheckerPrivateId, False)
) )
# Protect the class # Protect the class
......
...@@ -17,6 +17,7 @@ $Id$ ...@@ -17,6 +17,7 @@ $Id$
""" """
from Products.Five import BrowserView from Products.Five import BrowserView
from Products.Five.browser.pagetemplatefile import ViewPageTemplateFile from Products.Five.browser.pagetemplatefile import ViewPageTemplateFile
from OFS.SimpleItem import SimpleItem
class SimpleView(BrowserView): class SimpleView(BrowserView):
"""More docstring. Please Zope""" """More docstring. Please Zope"""
...@@ -40,6 +41,11 @@ class CallView(BrowserView): ...@@ -40,6 +41,11 @@ class CallView(BrowserView):
def __call__(self): def __call__(self):
return u"I was __call__()'ed" return u"I was __call__()'ed"
class PermissionView(BrowserView, SimpleItem):
def __call__(self):
return u"I was __call__()'ed"
class CallTemplate(BrowserView): class CallTemplate(BrowserView):
__call__ = ViewPageTemplateFile('falcon.pt') __call__ = ViewPageTemplateFile('falcon.pt')
......
...@@ -275,6 +275,13 @@ The same applies to a view registered with <browser:view /> instead of ...@@ -275,6 +275,13 @@ The same applies to a view registered with <browser:view /> instead of
>>> aq_parent(aq_inner(context)) >>> aq_parent(aq_inner(context))
<Folder at /test_folder_1_> <Folder at /test_folder_1_>
Make sure that methods which are not included in the allowed interface or
attributes, but which already had security declarations from a base class,
don't get those declarations overridden to be private. (The roles for
restrictedTraverse should be None, indicating it is public.)
>>> view.restrictedTraverse__roles__
High-level security High-level security
------------------- -------------------
......
...@@ -237,7 +237,7 @@ ...@@ -237,7 +237,7 @@
<browser:view <browser:view
name="permission_view" name="permission_view"
for="Products.Five.tests.testing.simplecontent.ISimpleContent" for="Products.Five.tests.testing.simplecontent.ISimpleContent"
class=".pages.CallView" class=".pages.PermissionView"
permission="zope2.ViewManagementScreens" permission="zope2.ViewManagementScreens"
/> />
......
...@@ -127,12 +127,15 @@ def _getSecurity(klass): ...@@ -127,12 +127,15 @@ def _getSecurity(klass):
setattr(klass, '__security__', security) setattr(klass, '__security__', security)
return security return security
def protectName(klass, name, permission_id): def protectName(klass, name, permission_id, override_existing_protection=True):
"""Protect the attribute 'name' on 'klass' using the given """Protect the attribute 'name' on 'klass' using the given
permission""" permission"""
security = _getSecurity(klass) security = _getSecurity(klass)
# Zope 2 uses string, not unicode yet # Zope 2 uses string, not unicode yet
name = str(name) name = str(name)
if not override_existing_protection and ('%s__roles__' % name) in dir(klass):
# There is already a declaration for this name from a base class.
return
if permission_id == CheckerPublicId or permission_id is CheckerPublic: if permission_id == CheckerPublicId or permission_id is CheckerPublic:
# Sometimes, we already get a processed permission id, which # Sometimes, we already get a processed permission id, which
# can mean that 'zope.Public' has been interchanged for the # can mean that 'zope.Public' has been interchanged for the
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment