Getting Started with Django Testing
I have been programming for a while and have only recently begun to implement testing into my development process. Needless to say, this guide is intended for someone who is starting at ground zero. If you’re the type of person who can soak up documentation, I’d skip straight to that. But for everyone else, this is the overview I wish I would’ve read before I started.
An overview of testing
Automated testing is useful for ensuring code quality. If you’ve been coding for a while, it’s inevitable that you’ve released some new feature that broke an existing feature. The tests you write will be run before you push any code, and over time you will accumulate many tests. So when you’re working on a new feature in a few months, you’ll run your automated tests ensuring that the code you’re writing today still works as expected. This process requires an initial investment of time and energy, but it pays off in the end. With automated software testing in place, you’ll save a lot of time on manual testing, and you’ll be much more confident in the code you push.
TL;DR discover bug, write test that fails because of the bug, fix bug, don’t worry about it again.
If you’re not sure how to get started or if you’re looking for a way to ease into testing, antifragility testing is a great. Antifragility is based on the idea that some things get stronger when subjected to shock. As your application grows, bugs will pop up here and there, and you’ll be tasked to fix them.
However, before fixing the bug, you can write a test that fails because of the bug. For instance, if you have a form that creates a user and isn’t validating the username properly, you can write a test that specifically checks validation for that field. You might call the test username_validation_should_fail_when_length_is_less_than_8. It may seem comical to have such a long name (and perhaps you could shorten it), but it’s important to write very specific tests. You could then test validation by passing in values that you know should fail. Before fixing the bug, you can run the test and cause the test to fail. Then after fixing the bug, you can be confident that it won’t fail again.
In this way, bugs are still a nuisance, but at least they will make your application stronger over time. After all, you should never have to fix the same bug twice.
Testing in Django
The later versions of Django ship with a testing framework. It’s actually just a wrapper for Python’s built in unit testing framework. You’ll want to put your tests in the app folder that they belong to, and you’ll call the file tests.py. As of Django 1.6, Django will look for tests in any file that begins with test. This way you can better organize your tests rather than writing a few thousand lines of tests in a single file.
Writing your first test
This step assumes that you’ve already setup a Django application. Open up a file called tests.py in the app of our choice (in Django the main application is called a project and it is often composed of many apps). At the top of the file, you’ll import Django’s testing framework:
from django import test
And any tests that you write will extend the test.TestCase class. So for our first test we will assume you want to check whether the homepage returns a 200 response status. If you haven’t setup your urls file or your views that’s OK. We can start by writing the test. When you write tests it’s good to force the test to fail so you know it works.
class URLTests(test.TestCase): def test_homepage(self): response = self.client.get('/') self.assertEqual (response.status_code, 200)
Django will run the test suite URLTests and execute any methods that begin with test. So in this case, test_homepage will be run automatically. So the first line of the test simply runs an HTTP GET request to fetch the home page. The response is stored in the response variable and we use the TestCase’s assertEqual method to ensure that the status code is 200.
TestCase.assertEqual will throw an exception if the assertion fails, and it will stop the test so you can fix the issue. At this point, since you haven’t built the home page yet you would go ahead and set up the URL and view and run the test again.
Running your tests
Now that you’ve written your test it’s time to run it. Tests can and should be run frequently as you develop. At the very least they should be run before deployment. With Django, you can run all tests in your project or target the tests for a single app. To run all tests you can simply run the following on the command line:
To run only the tests in a specific app you can run:
./manage.py test app_name
As mentioned previously, these commands will find all applicable tests and run them. A test database will be created before and destroyed after, and as expected you’ll be notified if any tests fail.
Hopefully by now you’ve got a good understanding of why and how you would use testing. Now it’s time to dive into the docs.