View -> APIView

This commit is contained in:
Tom Christie 2012-09-03 16:54:17 +01:00
parent 1a1ccf94c2
commit a092a72844
12 changed files with 53 additions and 47 deletions

View File

@ -2,7 +2,7 @@ from django.conf.urls.defaults import patterns, url, include
from django.test import TestCase from django.test import TestCase
from djangorestframework.compat import RequestFactory from djangorestframework.compat import RequestFactory
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework.response import Response from djangorestframework.response import Response
@ -32,12 +32,12 @@ class UserAgentMungingTest(TestCase):
def setUp(self): def setUp(self):
class MockView(View): class MockView(APIView):
permissions = () permissions = ()
response_class = Response response_class = Response
def get(self, request): def get(self, request):
return self.response_class({'a':1, 'b':2, 'c':3}) return self.response_class({'a': 1, 'b': 2, 'c': 3})
self.req = RequestFactory() self.req = RequestFactory()
self.MockView = MockView self.MockView = MockView
@ -58,7 +58,7 @@ class UserAgentMungingTest(TestCase):
"""Turn off _IGNORE_IE_ACCEPT_HEADER, send MSIE user agent strings and ensure """Turn off _IGNORE_IE_ACCEPT_HEADER, send MSIE user agent strings and ensure
that we get a JSON response if we set a */* accept header.""" that we get a JSON response if we set a */* accept header."""
class IgnoreIEAcceptResponse(Response): class IgnoreIEAcceptResponse(Response):
_IGNORE_IE_ACCEPT_HEADER=False _IGNORE_IE_ACCEPT_HEADER = False
view = self.MockView.as_view(response_class=IgnoreIEAcceptResponse) view = self.MockView.as_view(response_class=IgnoreIEAcceptResponse)
for user_agent in (MSIE_9_USER_AGENT, for user_agent in (MSIE_9_USER_AGENT,
@ -81,4 +81,3 @@ class UserAgentMungingTest(TestCase):
resp = self.view(req) resp = self.view(req)
resp.render() resp.render()
self.assertEqual(resp['Content-Type'], 'application/json') self.assertEqual(resp['Content-Type'], 'application/json')

View File

@ -5,13 +5,13 @@ from django.test import Client, TestCase
from django.utils import simplejson as json from django.utils import simplejson as json
from django.http import HttpResponse from django.http import HttpResponse
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework import permissions from djangorestframework import permissions
import base64 import base64
class MockView(View): class MockView(APIView):
permission_classes = (permissions.IsAuthenticated,) permission_classes = (permissions.IsAuthenticated,)
def post(self, request): def post(self, request):

View File

@ -1,21 +1,26 @@
from django.conf.urls.defaults import patterns, url from django.conf.urls.defaults import patterns, url
from django.test import TestCase from django.test import TestCase
from djangorestframework.utils.breadcrumbs import get_breadcrumbs from djangorestframework.utils.breadcrumbs import get_breadcrumbs
from djangorestframework.views import View from djangorestframework.views import APIView
class Root(View):
class Root(APIView):
pass pass
class ResourceRoot(View):
class ResourceRoot(APIView):
pass pass
class ResourceInstance(View):
class ResourceInstance(APIView):
pass pass
class NestedResourceRoot(View):
class NestedResourceRoot(APIView):
pass pass
class NestedResourceInstance(View):
class NestedResourceInstance(APIView):
pass pass
urlpatterns = patterns('', urlpatterns = patterns('',

View File

@ -1,5 +1,5 @@
from django.test import TestCase from django.test import TestCase
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework.compat import apply_markdown from djangorestframework.compat import apply_markdown
# We check that docstrings get nicely un-indented. # We check that docstrings get nicely un-indented.
@ -48,21 +48,21 @@ MARKED_DOWN_gte_21 = """<h2 id="an-example-docstring">an example docstring</h2>
class TestViewNamesAndDescriptions(TestCase): class TestViewNamesAndDescriptions(TestCase):
def test_resource_name_uses_classname_by_default(self): def test_resource_name_uses_classname_by_default(self):
"""Ensure Resource names are based on the classname by default.""" """Ensure Resource names are based on the classname by default."""
class MockView(View): class MockView(APIView):
pass pass
self.assertEquals(MockView().get_name(), 'Mock') self.assertEquals(MockView().get_name(), 'Mock')
def test_resource_name_can_be_set_explicitly(self): def test_resource_name_can_be_set_explicitly(self):
"""Ensure Resource names can be set using the 'get_name' method.""" """Ensure Resource names can be set using the 'get_name' method."""
example = 'Some Other Name' example = 'Some Other Name'
class MockView(View): class MockView(APIView):
def get_name(self): def get_name(self):
return example return example
self.assertEquals(MockView().get_name(), example) self.assertEquals(MockView().get_name(), example)
def test_resource_description_uses_docstring_by_default(self): def test_resource_description_uses_docstring_by_default(self):
"""Ensure Resource names are based on the docstring by default.""" """Ensure Resource names are based on the docstring by default."""
class MockView(View): class MockView(APIView):
"""an example docstring """an example docstring
==================== ====================
@ -83,7 +83,8 @@ class TestViewNamesAndDescriptions(TestCase):
def test_resource_description_can_be_set_explicitly(self): def test_resource_description_can_be_set_explicitly(self):
"""Ensure Resource descriptions can be set using the 'get_description' method.""" """Ensure Resource descriptions can be set using the 'get_description' method."""
example = 'Some other description' example = 'Some other description'
class MockView(View):
class MockView(APIView):
"""docstring""" """docstring"""
def get_description(self): def get_description(self):
return example return example
@ -92,14 +93,15 @@ class TestViewNamesAndDescriptions(TestCase):
def test_resource_description_does_not_require_docstring(self): def test_resource_description_does_not_require_docstring(self):
"""Ensure that empty docstrings do not affect the Resource's description if it has been set using the 'get_description' method.""" """Ensure that empty docstrings do not affect the Resource's description if it has been set using the 'get_description' method."""
example = 'Some other description' example = 'Some other description'
class MockView(View):
class MockView(APIView):
def get_description(self): def get_description(self):
return example return example
self.assertEquals(MockView().get_description(), example) self.assertEquals(MockView().get_description(), example)
def test_resource_description_can_be_empty(self): def test_resource_description_can_be_empty(self):
"""Ensure that if a resource has no doctring or 'description' class attribute, then it's description is the empty string.""" """Ensure that if a resource has no doctring or 'description' class attribute, then it's description is the empty string."""
class MockView(View): class MockView(APIView):
pass pass
self.assertEquals(MockView().get_description(), '') self.assertEquals(MockView().get_description(), '')

View File

@ -4,7 +4,7 @@ from django.conf.urls.defaults import patterns, url, include
from django.contrib.auth.models import User from django.contrib.auth.models import User
from django.test import Client, TestCase from django.test import Client, TestCase
from djangorestframework.views import View from djangorestframework.views import APIView
# Since oauth2 / django-oauth-plus are optional dependancies, we don't want to # Since oauth2 / django-oauth-plus are optional dependancies, we don't want to
# always run these tests. # always run these tests.
@ -20,7 +20,7 @@ except ImportError:
else: else:
# Alrighty, we're good to go here. # Alrighty, we're good to go here.
class ClientView(View): class ClientView(APIView):
def get(self, request): def get(self, request):
return {'resource': 'Protected!'} return {'resource': 'Protected!'}
@ -30,7 +30,6 @@ else:
url(r'^restframework/', include('djangorestframework.urls', namespace='djangorestframework')), url(r'^restframework/', include('djangorestframework.urls', namespace='djangorestframework')),
) )
class OAuthTests(TestCase): class OAuthTests(TestCase):
""" """
OAuth authentication: OAuth authentication:
@ -117,7 +116,7 @@ else:
# Starting the test here # Starting the test here
self.client.login(username=self.username, password=self.password) self.client.login(username=self.username, password=self.password)
parameters = {'oauth_token': token.key,} parameters = {'oauth_token': token.key}
response = self.client.get("/oauth/authorize/", parameters) response = self.client.get("/oauth/authorize/", parameters)
self.assertEqual(response.status_code, 200) self.assertEqual(response.status_code, 200)
self.failIf(not response.content.startswith('Fake authorize view for api.example.com with params: oauth_token=')) self.failIf(not response.content.startswith('Fake authorize view for api.example.com with params: oauth_token='))

View File

@ -5,7 +5,7 @@ from django.test import TestCase
from djangorestframework import status from djangorestframework import status
from djangorestframework.response import Response from djangorestframework.response import Response
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework.renderers import BaseRenderer, JSONRenderer, YAMLRenderer, \ from djangorestframework.renderers import BaseRenderer, JSONRenderer, YAMLRenderer, \
XMLRenderer, JSONPRenderer, DocumentingHTMLRenderer XMLRenderer, JSONPRenderer, DocumentingHTMLRenderer
from djangorestframework.parsers import YAMLParser, XMLParser from djangorestframework.parsers import YAMLParser, XMLParser
@ -50,7 +50,7 @@ class RendererB(BaseRenderer):
return RENDERER_B_SERIALIZER(obj) return RENDERER_B_SERIALIZER(obj)
class MockView(View): class MockView(APIView):
renderers = (RendererA, RendererB) renderers = (RendererA, RendererB)
def get(self, request, **kwargs): def get(self, request, **kwargs):
@ -58,20 +58,20 @@ class MockView(View):
return self.render(response) return self.render(response)
class MockGETView(View): class MockGETView(APIView):
def get(self, request, **kwargs): def get(self, request, **kwargs):
return {'foo': ['bar', 'baz']} return {'foo': ['bar', 'baz']}
class HTMLView(View): class HTMLView(APIView):
renderers = (DocumentingHTMLRenderer, ) renderers = (DocumentingHTMLRenderer, )
def get(self, request, **kwargs): def get(self, request, **kwargs):
return 'text' return 'text'
class HTMLView1(View): class HTMLView1(APIView):
renderers = (DocumentingHTMLRenderer, JSONRenderer) renderers = (DocumentingHTMLRenderer, JSONRenderer)
def get(self, request, **kwargs): def get(self, request, **kwargs):
@ -222,7 +222,7 @@ class JSONRendererTests(TestCase):
self.assertEquals(strip_trailing_whitespace(content), _indented_repr) self.assertEquals(strip_trailing_whitespace(content), _indented_repr)
class MockGETView(View): class MockGETView(APIView):
def get(self, request, *args, **kwargs): def get(self, request, *args, **kwargs):
return Response({'foo': ['bar', 'baz']}) return Response({'foo': ['bar', 'baz']})

View File

@ -15,7 +15,7 @@ from djangorestframework.parsers import (
) )
from djangorestframework.request import Request from djangorestframework.request import Request
from djangorestframework.response import Response from djangorestframework.response import Response
from djangorestframework.views import View from djangorestframework.views import APIView
factory = RequestFactory() factory = RequestFactory()
@ -207,7 +207,7 @@ class TestContentParsing(TestCase):
# self.assertEqual(request.DATA.items(), data.items()) # self.assertEqual(request.DATA.items(), data.items())
class MockView(View): class MockView(APIView):
authentication = (UserLoggedInAuthentication,) authentication = (UserLoggedInAuthentication,)
def post(self, request): def post(self, request):

View File

@ -5,7 +5,7 @@ from django.conf.urls.defaults import patterns, url, include
from django.test import TestCase from django.test import TestCase
from djangorestframework.response import Response, NotAcceptable from djangorestframework.response import Response, NotAcceptable
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework.compat import RequestFactory from djangorestframework.compat import RequestFactory
from djangorestframework import status from djangorestframework import status
from djangorestframework.renderers import ( from djangorestframework.renderers import (
@ -167,21 +167,21 @@ class RendererB(BaseRenderer):
return RENDERER_B_SERIALIZER(obj) return RENDERER_B_SERIALIZER(obj)
class MockView(View): class MockView(APIView):
renderers = (RendererA, RendererB) renderers = (RendererA, RendererB)
def get(self, request, **kwargs): def get(self, request, **kwargs):
return Response(DUMMYCONTENT, status=DUMMYSTATUS) return Response(DUMMYCONTENT, status=DUMMYSTATUS)
class HTMLView(View): class HTMLView(APIView):
renderers = (DocumentingHTMLRenderer, ) renderers = (DocumentingHTMLRenderer, )
def get(self, request, **kwargs): def get(self, request, **kwargs):
return Response('text') return Response('text')
class HTMLView1(View): class HTMLView1(APIView):
renderers = (DocumentingHTMLRenderer, JSONRenderer) renderers = (DocumentingHTMLRenderer, JSONRenderer)
def get(self, request, **kwargs): def get(self, request, **kwargs):

View File

@ -4,11 +4,11 @@ from django.utils import simplejson as json
from djangorestframework.renderers import JSONRenderer from djangorestframework.renderers import JSONRenderer
from djangorestframework.reverse import reverse from djangorestframework.reverse import reverse
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework.response import Response from djangorestframework.response import Response
class MyView(View): class MyView(APIView):
""" """
Mock resource which simply returns a URL, so that we can ensure Mock resource which simply returns a URL, so that we can ensure
that reversed URLs are fully qualified. that reversed URLs are fully qualified.

View File

@ -7,12 +7,12 @@ from django.contrib.auth.models import User
from django.core.cache import cache from django.core.cache import cache
from djangorestframework.compat import RequestFactory from djangorestframework.compat import RequestFactory
from djangorestframework.views import View from djangorestframework.views import APIView
from djangorestframework.permissions import PerUserThrottling, PerViewThrottling from djangorestframework.permissions import PerUserThrottling, PerViewThrottling
from djangorestframework.response import Response from djangorestframework.response import Response
class MockView(View): class MockView(APIView):
permission_classes = (PerUserThrottling,) permission_classes = (PerUserThrottling,)
throttle = '3/sec' throttle = '3/sec'

View File

@ -1,9 +1,10 @@
from django.core.urlresolvers import resolve from django.core.urlresolvers import resolve
def get_breadcrumbs(url): def get_breadcrumbs(url):
"""Given a url returns a list of breadcrumbs, which are each a tuple of (name, url).""" """Given a url returns a list of breadcrumbs, which are each a tuple of (name, url)."""
from djangorestframework.views import View from djangorestframework.views import APIView
def breadcrumbs_recursive(url, breadcrumbs_list): def breadcrumbs_recursive(url, breadcrumbs_list):
"""Add tuples of (name, url) to the breadcrumbs list, progressively chomping off parts of the url.""" """Add tuples of (name, url) to the breadcrumbs list, progressively chomping off parts of the url."""
@ -14,7 +15,7 @@ def get_breadcrumbs(url):
pass pass
else: else:
# Check if this is a REST framework view, and if so add it to the breadcrumbs # Check if this is a REST framework view, and if so add it to the breadcrumbs
if isinstance(getattr(view, 'cls_instance', None), View): if isinstance(getattr(view, 'cls_instance', None), APIView):
breadcrumbs_list.insert(0, (view.cls_instance.get_name(), url)) breadcrumbs_list.insert(0, (view.cls_instance.get_name(), url))
if url == '': if url == '':

View File

@ -12,7 +12,7 @@ from django.utils.html import escape
from django.utils.safestring import mark_safe from django.utils.safestring import mark_safe
from django.views.decorators.csrf import csrf_exempt from django.views.decorators.csrf import csrf_exempt
from djangorestframework.compat import View, apply_markdown from djangorestframework.compat import View as _View, apply_markdown
from djangorestframework.response import Response from djangorestframework.response import Response
from djangorestframework.request import Request from djangorestframework.request import Request
from djangorestframework.settings import api_settings from djangorestframework.settings import api_settings
@ -62,7 +62,7 @@ def _camelcase_to_spaces(content):
return re.sub(camelcase_boundry, ' \\1', content).strip() return re.sub(camelcase_boundry, ' \\1', content).strip()
class APIView(View): class APIView(_View):
""" """
Handles incoming requests and maps them to REST operations. Handles incoming requests and maps them to REST operations.
Performs request deserialization, response serialization, authentication and input validation. Performs request deserialization, response serialization, authentication and input validation.
@ -96,7 +96,7 @@ class APIView(View):
as an attribute on the callable function. This allows us to discover as an attribute on the callable function. This allows us to discover
information about the view when we do URL reverse lookups. information about the view when we do URL reverse lookups.
""" """
view = super(View, cls).as_view(**initkwargs) view = super(APIView, cls).as_view(**initkwargs)
view.cls_instance = cls(**initkwargs) view.cls_instance = cls(**initkwargs)
return view return view