- Author:
- vaughnkoch
- Posted:
- October 7, 2010
- Language:
- Python
- Version:
- 1.2
- Score:
- 2 (after 2 ratings)
This is an update to Simon Willison's snippet http://djangosnippets.org/snippets/963/, along with one of the comments in that snippet.
This class lets you create a Request object that's gone through all the middleware. Suitable for unit testing when you need to modify something on the request directly, or pass in a mock object. (note: see http://labix.org/mocker for details on how to mock requests for testing)
Example on how to use:
from django.test import TestCase from yourapp import your_view from yourutils import RequestFactory
class YourTestClass(TestCase): def setUp(self): pass def tearDown(self): pass
# Create your own request, which you can modify, instead of using self.client.
def test_your_view(self):
# Create your request object
rf = RequestFactory()
request = rf.get('/your-url-here/')
# ... modify the request to your liking ...
response = your_view(request)
self.assertEqual(response.status_code, 200)
Suggestions/improvements are welcome. :)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | from django.test import Client
from django.core.handlers.wsgi import WSGIRequest
from django.core.handlers.base import BaseHandler
# Adapted from Simon Willison's snippet: http://djangosnippets.org/snippets/963/.
class RequestFactory(Client):
"""
Class that lets you create mock Request objects for use in testing.
Usage:
rf = RequestFactory()
get_request = rf.get('/hello/')
post_request = rf.post('/submit/', {'foo': 'bar'})
This class re-uses the django.test.client.Client interface, docs here:
http://www.djangoproject.com/documentation/testing/#the-test-client
Once you have a request object you can pass it to any view function,
just as if that view had been hooked up using a URLconf.
"""
def request(self, **request):
"""
Similar to parent class, but returns the request object as soon as it
has created it.
"""
environ = {
'HTTP_COOKIE': self.cookies,
'PATH_INFO': '/',
'QUERY_STRING': '',
'REQUEST_METHOD': 'GET',
'SCRIPT_NAME': '',
'SERVER_NAME': 'testserver',
'SERVER_PORT': 80,
'SERVER_PROTOCOL': 'HTTP/1.1',
}
environ.update(self.defaults)
environ.update(request)
request = WSGIRequest(environ)
handler = BaseHandler()
handler.load_middleware()
for middleware_method in handler._request_middleware:
if middleware_method(request):
raise Exception("Couldn't create request object - "
"request middleware returned a response")
return request
|
More like this
- Template tag - list punctuation for a list of items by shapiromatron 11 months, 2 weeks ago
- JSONRequestMiddleware adds a .json() method to your HttpRequests by cdcarter 11 months, 3 weeks ago
- Serializer factory with Django Rest Framework by julio 1 year, 6 months ago
- Image compression before saving the new model / work with JPG, PNG by Schleidens 1 year, 7 months ago
- Help text hyperlinks by sa2812 1 year, 8 months ago
Comments
Nice work on this, btw.
You should note, btw that Simon's original RequestFactory is now part of the django.test.client module. The Test Client actually implements his RequestFactory now to generate the request object and then executes it against the view.
I'm not sure when it was introduced btw, but I'm running the trunk right now. It looks like there have been some additional enhancements since Simon first posted the snippet.
You might want to refactor this to extend the RequestFactory that's now in Django, since they do not appear to have any middleware handling on it as you have created. You can probably achieve your revision in about 5 lines of code I'd imagine.
Cheers.
#
Please login first before commenting.