[Zope-Checkins] SVN: Zope/branches/2.12/ Fix regression in treatment of trusted code in view page templates.
Martin Aspeli
optilude at gmx.net
Sun Dec 13 04:28:24 EST 2009
Log message for revision 106436:
Fix regression in treatment of trusted code in view page templates.
Changed:
U Zope/branches/2.12/doc/CHANGES.rst
U Zope/branches/2.12/src/Products/Five/browser/tests/test_pagetemplatefile.py
U Zope/branches/2.12/src/Products/PageTemplates/Expressions.py
-=-
Modified: Zope/branches/2.12/doc/CHANGES.rst
===================================================================
--- Zope/branches/2.12/doc/CHANGES.rst 2009-12-12 10:58:43 UTC (rev 106435)
+++ Zope/branches/2.12/doc/CHANGES.rst 2009-12-13 09:28:23 UTC (rev 106436)
@@ -27,6 +27,12 @@
Bugs Fixed
++++++++++
+- Fixed a regression in Products.PageTemplates that meant filesystem templates
+ using Products.Five.browser.pagetemplatefile would treat TALES path
+ expressions (but not python expressions) as protected code and so attempt
+ to apply security. See original issue here:
+ http://codespeak.net/pipermail/z3-five/2007q2/002185.html
+
- LP #491249: fix tabindex on ZRDB connection test form.
- LP #490514: preserve tainting when calling into DTML from ZPT.
Modified: Zope/branches/2.12/src/Products/Five/browser/tests/test_pagetemplatefile.py
===================================================================
--- Zope/branches/2.12/src/Products/Five/browser/tests/test_pagetemplatefile.py 2009-12-12 10:58:43 UTC (rev 106435)
+++ Zope/branches/2.12/src/Products/Five/browser/tests/test_pagetemplatefile.py 2009-12-13 09:28:23 UTC (rev 106436)
@@ -42,15 +42,15 @@
from zope.tales.pythonexpr import PythonExpr
from zope.contentprovider.tales import TALESProviderExpression
from Products.PageTemplates.DeferExpr import LazyExpr
- from Products.PageTemplates.Expressions import ZopePathExpr
+ from Products.PageTemplates.Expressions import TrustedZopePathExpr
from Products.PageTemplates.Expressions import SecureModuleImporter
vptf = self._makeOne('seagull.pt')
engine = vptf.pt_getEngine()
- self.assertEqual(engine.types['standard'], ZopePathExpr)
- self.assertEqual(engine.types['path'], ZopePathExpr)
- self.assertEqual(engine.types['exists'], ZopePathExpr)
- self.assertEqual(engine.types['nocall'], ZopePathExpr)
+ self.assertEqual(engine.types['standard'], TrustedZopePathExpr)
+ self.assertEqual(engine.types['path'], TrustedZopePathExpr)
+ self.assertEqual(engine.types['exists'], TrustedZopePathExpr)
+ self.assertEqual(engine.types['nocall'], TrustedZopePathExpr)
self.assertEqual(engine.types['string'], StringExpr)
self.assertEqual(engine.types['python'], PythonExpr)
self.assertEqual(engine.types['not'], NotExpr)
Modified: Zope/branches/2.12/src/Products/PageTemplates/Expressions.py
===================================================================
--- Zope/branches/2.12/src/Products/PageTemplates/Expressions.py 2009-12-12 10:58:43 UTC (rev 106435)
+++ Zope/branches/2.12/src/Products/PageTemplates/Expressions.py 2009-12-13 09:28:23 UTC (rev 106436)
@@ -79,6 +79,26 @@
request=request)
return object
+def trustedBoboAwareZopeTraverse(object, path_items, econtext):
+ """Traverses a sequence of names, first trying attributes then items.
+
+ This uses Zope 3 path traversal where possible and interacts
+ correctly with objects providing OFS.interface.ITraversable when
+ necessary (bobo-awareness).
+ """
+ request = getattr(econtext, 'request', None)
+ path_items = list(path_items)
+ path_items.reverse()
+
+ while path_items:
+ name = path_items.pop()
+ if OFS.interfaces.ITraversable.providedBy(object):
+ object = object.unrestrictedTraverse(name)
+ else:
+ object = traversePathElement(object, name, path_items,
+ request=request)
+ return object
+
def render(ob, ns):
"""Calls the object, possibly a document template, or just returns
it if not callable. (From DT_Util.py)
@@ -104,11 +124,13 @@
class ZopePathExpr(PathExpr):
+ _TRAVERSER = staticmethod(boboAwareZopeTraverse)
+
def __init__(self, name, expr, engine):
if not expr.strip():
expr = 'nothing'
super(ZopePathExpr, self).__init__(name, expr, engine,
- boboAwareZopeTraverse)
+ self._TRAVERSER)
# override this to support different call metrics (see bottom of
# method) and Zope 2's traversal exceptions (ZopeUndefs instead of
@@ -146,6 +168,9 @@
return 1
return 0
+class TrustedZopePathExpr(ZopePathExpr):
+ _TRAVERSER = staticmethod(trustedBoboAwareZopeTraverse)
+
class SafeMapping(MultiMapping):
"""Mapping with security declarations and limited method exposure.
@@ -347,11 +372,11 @@
return False
return ob1 == ob2
-def createZopeEngine():
+def createZopeEngine(zpe=ZopePathExpr):
e = ZopeEngine()
e.iteratorFactory = PathIterator
- for pt in ZopePathExpr._default_type_names:
- e.registerType(pt, ZopePathExpr)
+ for pt in zpe._default_type_names:
+ e.registerType(pt, zpe)
e.registerType('string', StringExpr)
e.registerType('python', ZRPythonExpr.PythonExpr)
e.registerType('not', NotExpr)
@@ -364,7 +389,7 @@
def createTrustedZopeEngine():
# same as createZopeEngine, but use non-restricted Python
# expression evaluator
- e = createZopeEngine()
+ e = createZopeEngine(TrustedZopePathExpr)
e.types['python'] = PythonExpr
return e
More information about the Zope-Checkins
mailing list