Skip to content

Commit

Permalink
Implement traversal to attributes of a view via an adapter.
Browse files Browse the repository at this point in the history
  • Loading branch information
Michael Howitz committed May 20, 2019
1 parent ae3b3d2 commit 64fc2ab
Show file tree
Hide file tree
Showing 4 changed files with 24 additions and 17 deletions.
2 changes: 2 additions & 0 deletions src/Products/Five/browser/configure.zcml
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@
provides="zope.container.interfaces.INameChooser"
/>

<adapter factory=".metaconfigure.SimplePublishTraverse" />

<!-- Menu access -->
<browser:page
for="*"
Expand Down
25 changes: 17 additions & 8 deletions src/Products/Five/browser/metaconfigure.py
Original file line number Diff line number Diff line change
Expand Up @@ -444,16 +444,8 @@ class ViewNotCallableError(AttributeError, NotImplementedError):
pass


@zope.interface.implementer(IPublishTraverse)
class simple(zope.publisher.browser.BrowserView):

def publishTraverse(self, request, name):
try:
return guarded_getattr(self, name)
except Unauthorized:
# attribute exists but is not published, so hide it from access:
raise AttributeError(name)

# __call__ should have the same signature as the original method
@property
def __call__(self):
Expand All @@ -467,6 +459,23 @@ def __call__(self):
return getattr(self, attr)


@zope.interface.implementer(IPublishTraverse)
@zope.component.adapter(simple, IBrowserRequest)
class SimplePublishTraverse(object):
"""Default PublishTraverse implementation attributes of class `simple`."""

def __init__(self, context, request):
self.context = context
self.request = request

def publishTraverse(self, request, name):
try:
return guarded_getattr(self.context, name)
except Unauthorized:
# attribute exists but is not published, so hide it from access:
raise AttributeError(name)


class ViewMixinForTemplates(zope.browserpage.simpleviewclass.simple):

def __getitem__(self, name):
Expand Down
9 changes: 5 additions & 4 deletions src/Products/Five/browser/tests/pages.txt
Original file line number Diff line number Diff line change
Expand Up @@ -234,11 +234,12 @@ Other attributes are private:
>>> aq_acquire(view, 'mouse__roles__') is ACCESS_PRIVATE
True

In zope.browserpage this is just protected with the specified permission. Not
sure if this has to be private in Zope 2:
A view does not have a ``publishTraverse`` method, traversal to attributes
of the view is done via an adapter.

>>> aq_acquire(view, 'publishTraverse__roles__') is ACCESS_PRIVATE
True
>>> aq_acquire(view, 'publishTraverse')
Traceback (most recent call last):
AttributeError: 'RequestContainer' object has no attribute 'publishTraverse'

Check to see if view's context properly acquires its true
parent
Expand Down
5 changes: 0 additions & 5 deletions src/Products/Five/browser/tests/test_pages.py
Original file line number Diff line number Diff line change
Expand Up @@ -92,11 +92,6 @@ def test_publishTraverse_to_allowed_name():
>>> 'The eagle has landed' in result
True
Publishing traversal also works directly:
>>> view.publishTraverse(request, 'eagle')() == 'The eagle has landed'
True
Clean up:
>>> from zope.component.testing import tearDown
Expand Down

0 comments on commit 64fc2ab

Please sign in to comment.