diff --git a/src/zope/security/_compat.py b/src/zope/security/_compat.py index 6de4758..f3e441f 100644 --- a/src/zope/security/_compat.py +++ b/src/zope/security/_compat.py @@ -14,11 +14,13 @@ """ Python 2 / 3 compatibility """ import platform +import os import sys import types py_impl = getattr(platform, 'python_implementation', lambda: None) PYPY = py_impl() == 'PyPy' +PURE_PYTHON = os.environ.get('PURE_PYTHON', False) if sys.version_info[0] < 3: #pragma NO COVER diff --git a/src/zope/security/checker.py b/src/zope/security/checker.py index 061cc44..89ae214 100644 --- a/src/zope/security/checker.py +++ b/src/zope/security/checker.py @@ -177,6 +177,8 @@ def __init__(self, get_permissions, set_permissions=None): if set_permissions is not None: if not isinstance(set_permissions, dict): raise TypeError('set_permissions must be a dict') + else: + set_permissions = {} self.set_permissions = set_permissions def permission_id(self, name): diff --git a/src/zope/security/protectclass.py b/src/zope/security/protectclass.py index 57effb3..7e91f22 100644 --- a/src/zope/security/protectclass.py +++ b/src/zope/security/protectclass.py @@ -38,7 +38,6 @@ def protectName(class_, name, permission): def protectSetAttribute(class_, name, permission): """Set a permission on a particular name.""" - checker = getCheckerForInstancesOf(class_) if checker is None: checker = Checker({}, {}) diff --git a/src/zope/security/proxy.py b/src/zope/security/proxy.py index 974b923..7f7d626 100644 --- a/src/zope/security/proxy.py +++ b/src/zope/security/proxy.py @@ -114,13 +114,19 @@ def __delattr__(self, name): @_check_name def __getslice__(self, start, end): - getitem = PyProxyBase.__getattribute__(self, '__getitem__') - return getitem(slice(start, end)) + try: + return self._wrapped.__getslice__(start, end) + except: + getitem = PyProxyBase.__getattribute__(self, '__getitem__') + return getitem(slice(start, end)) @_check_name def __setslice__(self, i, j, value): - setitem = PyProxyBase.__getattribute__(self, '__setitem__') - return setitem(slice(i, j), value) + try: + return self._wrapped.__setslice__(i, j, value) + except: + setitem = PyProxyBase.__getattribute__(self, '__setitem__') + return setitem(slice(i, j), value) def __cmp__(self, other): # no check @@ -172,17 +178,14 @@ def __coerce__(self, other): # For some reason _check_name does not work for coerce() wrapped = super(PyProxyBase, self).__getattribute__('_wrapped') checker = super(PyProxyBase, self).__getattribute__('_checker') - checker.check_getattr(wrapped, '__coerce__') - # Re-implement __coerce__(), so we do not depend on self._wrapped - left, right = coerce(wrapped, other) - if left == wrapped and type(left) is type(wrapped): - left = self - return left, right + checker.check(wrapped, '__coerce__') + return super(ProxyPy, self).__coerce__(other) def __str__(self): try: return _check_name(PyProxyBase.__str__)(self) - except ForbiddenAttribute: + except: + # The C implementation catches all exceptions. wrapped = super(PyProxyBase, self).__getattribute__('_wrapped') return '' %( wrapped.__class__.__module__, wrapped.__class__.__name__, @@ -191,7 +194,8 @@ def __str__(self): def __repr__(self): try: return _check_name(PyProxyBase.__repr__)(self) - except ForbiddenAttribute: + except: + # The C implementation catches all exceptions. wrapped = super(PyProxyBase, self).__getattribute__('_wrapped') return '' %( wrapped.__class__.__module__, wrapped.__class__.__name__, diff --git a/src/zope/security/tests/test_proxy.py b/src/zope/security/tests/test_proxy.py index 974c26f..f73990d 100644 --- a/src/zope/security/tests/test_proxy.py +++ b/src/zope/security/tests/test_proxy.py @@ -16,7 +16,7 @@ import unittest import sys -from zope.security._compat import PYTHON2, PYPY +from zope.security._compat import PYTHON2, PYPY, PURE_PYTHON def _skip_if_not_Py2(testfunc): from functools import update_wrapper @@ -1946,6 +1946,6 @@ def test_suite(): unittest.makeSuite(ProxyTests), unittest.makeSuite(LocationProxySecurityCheckerTests), )) - if not PYPY: + if not (PYPY or PURE_PYTHON): suite.addTest(unittest.makeSuite(ProxyCTests)) return suite