diff options
| author | Pierre Dulac | 2013-03-10 14:40:20 +0100 |
|---|---|---|
| committer | Pierre Dulac | 2013-03-10 14:40:20 +0100 |
| commit | eec8efafc3eeacf00696208d2e1e55a11821257b (patch) | |
| tree | 9f16aba8b91aece7480ada162d768230c24b3204 | |
| parent | e03906a5c4101853b709403266b738911680c4b5 (diff) | |
| download | django-rest-framework-eec8efafc3eeacf00696208d2e1e55a11821257b.tar.bz2 | |
Add the implementation for TokenHasReadWriteScope permissions w/ oauth 1
| -rw-r--r-- | rest_framework/permissions.py | 8 | ||||
| -rw-r--r-- | rest_framework/tests/authentication.py | 37 |
2 files changed, 42 insertions, 3 deletions
diff --git a/rest_framework/permissions.py b/rest_framework/permissions.py index 519a3691..c477474c 100644 --- a/rest_framework/permissions.py +++ b/rest_framework/permissions.py @@ -140,12 +140,16 @@ class TokenHasReadWriteScope(BasePermission): read_only = request.method in SAFE_METHODS if hasattr(request.auth, 'resource'): # oauth 1 - pass + if read_only: + return True + elif request.auth.resource.is_readonly is False: + return True + return False elif hasattr(request.auth, 'scope'): # oauth 2 scope_valid = lambda scope_wanted_key, scope_had: oauth2_provider_scope.check( oauth2_provider_scope.SCOPE_NAME_DICT[scope_wanted_key], scope_had) - if (read_only and scope_valid('read', request.auth.scope)): + if read_only and scope_valid('read', request.auth.scope): return True elif scope_valid('write', request.auth.scope): return True diff --git a/rest_framework/tests/authentication.py b/rest_framework/tests/authentication.py index 693dbb4d..b663ca48 100644 --- a/rest_framework/tests/authentication.py +++ b/rest_framework/tests/authentication.py @@ -47,7 +47,9 @@ urlpatterns = patterns('', (r'^basic/$', MockView.as_view(authentication_classes=[BasicAuthentication])), (r'^token/$', MockView.as_view(authentication_classes=[TokenAuthentication])), (r'^auth-token/$', 'rest_framework.authtoken.views.obtain_auth_token'), - (r'^oauth/$', MockView.as_view(authentication_classes=[OAuthAuthentication])) + (r'^oauth/$', MockView.as_view(authentication_classes=[OAuthAuthentication])), + (r'^oauth-with-scope/$', MockView.as_view(authentication_classes=[OAuthAuthentication], + permission_classes=[permissions.TokenHasReadWriteScope])) ) if oauth2_provider is not None: @@ -391,6 +393,39 @@ class OAuthTests(TestCase): response = self.csrf_client.post('/oauth/', HTTP_AUTHORIZATION=auth) self.assertEqual(response.status_code, 200) + @unittest.skipUnless(oauth_provider, 'django-oauth-plus not installed') + @unittest.skipUnless(oauth, 'oauth2 not installed') + def test_get_form_with_readonly_resource_passing_auth(self): + """Ensure POSTing with a readonly resource instead of a write scope fails""" + read_only_access_token = self.token + read_only_access_token.resource.is_readonly = True + read_only_access_token.resource.save() + params = self._create_authorization_url_parameters() + response = self.csrf_client.get('/oauth-with-scope/', params) + self.assertEqual(response.status_code, 200) + + @unittest.skipUnless(oauth_provider, 'django-oauth-plus not installed') + @unittest.skipUnless(oauth, 'oauth2 not installed') + def test_post_form_with_readonly_resource_failing_auth(self): + """Ensure POSTing with a readonly resource instead of a write scope fails""" + read_only_access_token = self.token + read_only_access_token.resource.is_readonly = True + read_only_access_token.resource.save() + params = self._create_authorization_url_parameters() + response = self.csrf_client.post('/oauth-with-scope/', params) + self.assertIn(response.status_code, (status.HTTP_401_UNAUTHORIZED, status.HTTP_403_FORBIDDEN)) + + @unittest.skipUnless(oauth_provider, 'django-oauth-plus not installed') + @unittest.skipUnless(oauth, 'oauth2 not installed') + def test_post_form_with_write_resource_passing_auth(self): + """Ensure POSTing with a write resource succeed""" + read_write_access_token = self.token + read_write_access_token.resource.is_readonly = False + read_write_access_token.resource.save() + params = self._create_authorization_url_parameters() + response = self.csrf_client.post('/oauth-with-scope/', params) + self.assertEqual(response.status_code, 200) + class OAuth2Tests(TestCase): """OAuth 2.0 authentication""" |
