diff options
| -rw-r--r-- | src/pyramid/request.py | 7 | ||||
| -rw-r--r-- | src/pyramid/security.py | 67 | ||||
| -rw-r--r-- | src/pyramid/testing.py | 2 | ||||
| -rw-r--r-- | tests/test_config/test_testing.py | 4 | ||||
| -rw-r--r-- | tests/test_request.py | 4 | ||||
| -rw-r--r-- | tests/test_security.py | 30 |
6 files changed, 39 insertions, 75 deletions
diff --git a/src/pyramid/request.py b/src/pyramid/request.py index bb0dcaa2b..5c68abe69 100644 --- a/src/pyramid/request.py +++ b/src/pyramid/request.py @@ -15,11 +15,7 @@ from pyramid.interfaces import ( from pyramid.decorator import reify from pyramid.i18n import LocalizerRequestMixin from pyramid.response import Response, _get_response_factory -from pyramid.security import ( - SecurityAPIMixin, - AuthenticationAPIMixin, - AuthorizationAPIMixin, -) +from pyramid.security import SecurityAPIMixin, AuthenticationAPIMixin from pyramid.url import URLMethodsMixin from pyramid.util import ( InstancePropertyHelper, @@ -153,7 +149,6 @@ class Request( LocalizerRequestMixin, SecurityAPIMixin, AuthenticationAPIMixin, - AuthorizationAPIMixin, ViewMethodsMixin, ): """ diff --git a/src/pyramid/security.py b/src/pyramid/security.py index 66e314f79..4881d94a6 100644 --- a/src/pyramid/security.py +++ b/src/pyramid/security.py @@ -299,6 +299,34 @@ class SecurityAPIMixin(object): return None return policy.identify(self) + def has_permission(self, permission, context=None): + """ Given a permission and an optional context, returns an instance of + :data:`pyramid.security.Allowed` if the permission is granted to this + request with the provided context, or the context already associated + with the request. Otherwise, returns an instance of + :data:`pyramid.security.Denied`. This method delegates to the current + security policy. Returns + :data:`pyramid.security.Allowed` unconditionally if no security + policy has been registered for this request. If ``context`` is not + supplied or is supplied as ``None``, the context used is the + ``request.context`` attribute. + + :param permission: Does this request have the given permission? + :type permission: str + :param context: A resource object or ``None`` + :type context: object + :returns: Either :class:`pyramid.security.Allowed` or + :class:`pyramid.security.Denied`. + + """ + if context is None: + context = self.context + policy = _get_security_policy(self) + if policy is None: + return Allowed('No security policy in use.') + identity = policy.identify(self) + return policy.permits(self, context, identity, permission) + class AuthenticationAPIMixin(object): @property @@ -361,45 +389,6 @@ class AuthenticationAPIMixin(object): return policy.effective_principals(self) -class AuthorizationAPIMixin(object): - def has_permission(self, permission, context=None): - """ Given a permission and an optional context, returns an instance of - :data:`pyramid.security.Allowed` if the permission is granted to this - request with the provided context, or the context already associated - with the request. Otherwise, returns an instance of - :data:`pyramid.security.Denied`. This method delegates to the current - authentication and authorization policies. Returns - :data:`pyramid.security.Allowed` unconditionally if no authentication - policy has been registered for this request. If ``context`` is not - supplied or is supplied as ``None``, the context used is the - ``request.context`` attribute. - - :param permission: Does this request have the given permission? - :type permission: str - :param context: A resource object or ``None`` - :type context: object - :returns: Either :class:`pyramid.security.Allowed` or - :class:`pyramid.security.Denied`. - - .. versionadded:: 1.5 - - """ - if context is None: - context = self.context - reg = _get_registry(self) - authn_policy = reg.queryUtility(IAuthenticationPolicy) - if authn_policy is None: - return Allowed('No authentication policy in use.') - authz_policy = reg.queryUtility(IAuthorizationPolicy) - if authz_policy is None: - raise ValueError( - 'Authentication policy registered without ' - 'authorization policy' - ) # should never happen - principals = authn_policy.effective_principals(self) - return authz_policy.permits(context, principals, permission) - - @implementer(ISecurityPolicy) class LegacySecurityPolicy: """ diff --git a/src/pyramid/testing.py b/src/pyramid/testing.py index 7a85aff85..90a49c04a 100644 --- a/src/pyramid/testing.py +++ b/src/pyramid/testing.py @@ -19,7 +19,6 @@ from pyramid.security import ( Everyone, SecurityAPIMixin, AuthenticationAPIMixin, - AuthorizationAPIMixin, ) from pyramid.threadlocal import get_current_registry, manager @@ -306,7 +305,6 @@ class DummyRequest( LocalizerRequestMixin, SecurityAPIMixin, AuthenticationAPIMixin, - AuthorizationAPIMixin, ViewMethodsMixin, ): """ A DummyRequest object (incompletely) imitates a :term:`request` object. diff --git a/tests/test_config/test_testing.py b/tests/test_config/test_testing.py index 0fb73d268..822eeac8f 100644 --- a/tests/test_config/test_testing.py +++ b/tests/test_config/test_testing.py @@ -1,7 +1,7 @@ import unittest from zope.interface import implementer -from pyramid.security import AuthenticationAPIMixin, AuthorizationAPIMixin +from pyramid.security import SecurityAPIMixin, AuthenticationAPIMixin from pyramid.util import text_ from . import IDummy @@ -232,7 +232,7 @@ class DummyEvent: pass -class DummyRequest(AuthenticationAPIMixin, AuthorizationAPIMixin): +class DummyRequest(SecurityAPIMixin, AuthenticationAPIMixin): def __init__(self, environ=None): if environ is None: environ = {} diff --git a/tests/test_request.py b/tests/test_request.py index 484d86e01..1a10a8509 100644 --- a/tests/test_request.py +++ b/tests/test_request.py @@ -1,7 +1,7 @@ import unittest from pyramid import testing -from pyramid.security import AuthenticationAPIMixin, AuthorizationAPIMixin +from pyramid.security import SecurityAPIMixin, AuthenticationAPIMixin from pyramid.util import text_, bytes_ @@ -54,7 +54,7 @@ class TestRequest(unittest.TestCase): self.assertEqual(cls.ResponseClass, Response) def test_implements_security_apis(self): - apis = (AuthenticationAPIMixin, AuthorizationAPIMixin) + apis = (SecurityAPIMixin, AuthenticationAPIMixin) r = self._makeOne() self.assertTrue(isinstance(r, apis)) diff --git a/tests/test_security.py b/tests/test_security.py index dd2c225d3..40b5cd061 100644 --- a/tests/test_security.py +++ b/tests/test_security.py @@ -455,43 +455,25 @@ class TestHasPermission(unittest.TestCase): testing.tearDown() def _makeOne(self): - from pyramid.security import AuthorizationAPIMixin + from pyramid.security import SecurityAPIMixin from pyramid.registry import Registry - mixin = AuthorizationAPIMixin() + mixin = SecurityAPIMixin() mixin.registry = Registry() mixin.context = object() return mixin - def test_no_authentication_policy(self): + def test_no_security_policy(self): request = self._makeOne() result = request.has_permission('view') self.assertTrue(result) - self.assertEqual(result.msg, 'No authentication policy in use.') + self.assertEqual(result.msg, 'No security policy in use.') - def test_with_no_authorization_policy(self): + def test_with_security_registered(self): request = self._makeOne() - _registerAuthenticationPolicy(request.registry, None) - self.assertRaises( - ValueError, request.has_permission, 'view', context=None - ) - - def test_with_authn_and_authz_policies_registered(self): - request = self._makeOne() - _registerAuthenticationPolicy(request.registry, None) - _registerAuthorizationPolicy(request.registry, 'yo') + _registerSecurityPolicy(request.registry, 'yo') self.assertEqual(request.has_permission('view', context=None), 'yo') - def test_with_no_reg_on_request(self): - from pyramid.threadlocal import get_current_registry - - registry = get_current_registry() - request = self._makeOne() - del request.registry - _registerAuthenticationPolicy(registry, None) - _registerAuthorizationPolicy(registry, 'yo') - self.assertEqual(request.has_permission('view'), 'yo') - def test_with_no_context_passed(self): request = self._makeOne() self.assertTrue(request.has_permission('view')) |
