[Zope-CMF] Re: Inconstancy with CA traversal
Laurence Rowe
l at lrowe.co.uk
Mon Jun 30 08:13:25 EDT 2008
Tres Seaver wrote:
>
> I don't get it: why isn't OFS.Traversable's check sufficient?
> __bobo_traverse__ has a bad enough (insane, actually) contract, without
> adding security checking to it.
Tres: You're quite right, the security check happens outside of
bobo_traverse.
Dylan: Could you try this patch and see if it works for you. It really
needs some tests writing for it too.
Laurence
-------------- next part --------------
Index: Products/CMFCore/Skinnable.py
===================================================================
--- Products/CMFCore/Skinnable.py (revision 87827)
+++ Products/CMFCore/Skinnable.py (working copy)
@@ -27,6 +27,10 @@
from Globals import InitializeClass
from OFS.ObjectManager import ObjectManager
from ZODB.POSException import ConflictError
+from zExceptions import NotFound
+import webdav
+from zope.interface import implements, Interface
+from zope.component import queryMultiAdapter
logger = logging.getLogger('CMFCore.Skinnable')
@@ -94,6 +98,56 @@
if superGetAttr is None:
raise AttributeError, name
return superGetAttr(self, name)
+
+ def __bobo_traverse__(self, REQUEST, name):
+ '''
+ Ensures that views are traversed before skin objects
+ '''
+ resource = _marker = _MARKER
+
+ # Look up unskinned objects
+ unskinned = super(SkinnableObjectManager, aq_base(self))
+ next = getattr(unskinned, name, _marker)
+ if next is _marker:
+ try:
+ try:
+ next = self[name]
+ # The item lookup may return a NullResource,
+ # if this is the case we save it and return it
+ # if all other lookups fail.
+ if isinstance(next,
+ webdav.NullResource.NullResource):
+ resource = next
+ raise KeyError(name)
+ except (TypeError, AttributeError):
+ # Raise NotFound for easier debugging
+ # instead of AttributeError: __getitem__
+ raise NotFound(name)
+
+ except (AttributeError, NotFound, KeyError), e:
+ # Try to look for a view
+ next = queryMultiAdapter((self, self.REQUEST),
+ Interface, name)
+ if next is not None:
+ return next.__of__(self)
+
+ # Lookup skin objects
+ next = getattr(aq_base(self), name, _marker)
+ if next is not _marker:
+ return next
+
+ # Try acquired attributes
+ next = getattr(self, name, _marker)
+ if next is not _marker:
+ return next
+
+ if next is _marker:
+ # If we have a NullResource from earlier use it.
+ next = resource
+ if next is _marker:
+ # Nothing found re-raise error
+ raise e
+ return next
security.declarePrivate('getSkin')
def getSkin(self, name=None):
More information about the Zope-CMF
mailing list