Reputation: 1363
I have replaced project/app/tests.py
with a project/app/tests/
directory. The directory contains several Python files (call them apples.py
, bananas.py
, etc.), each of which defines one or more classes derived from TestCase
(call them TestApples
, TestBananas
, etc.). The file project/app/tests/__init__.py
contains
from apples import TestApples
from bananas import TestBananas
The command manage.py test app
still works, but manage.py test app.bananas
and manage.py test app.tests.bananas
do not, e.g.:
ValueError: Test label 'app.bananas' does not refer to a test
manage.py test app.tests.bananas
fails with the same error, but manage.py test app.tests.bananas.TestBananas
is more hopeful:
ValueError: Test label 'store.tests.bananas.TestBananas' should be of the form app.TestCase or app.TestCase.test_method
The Django docs and Python docs suggest that the solution is to write a custom test runner or test collector and plug it in; this StackOverflow question goes down the same route, then seems to recommend switching to django-nose. I'd rather not unless I have to, and I'm curious to see how to make this work with Django's standard tools. Anyone have a simple(ish) solution?
Upvotes: 3
Views: 2759
Reputation: 1523
I just do this tutorial.
Edit: after django 1.6, the test discovery mechanism changed. You just have to create a folder tests
with an __init__.py
file inside, and put your test files there.
Your test files should match test*.py
pattern.
Upvotes: 2
Reputation: 709
In your example, if you run manage.py test app.TestBananas
then you can run that specific test.
You can get everything working by making sure all your tests are imported into __init__.py
but when you have lots of tests this becomes difficult to manage. If you want to run the tests in PyCharm then django-nose isn't an option.
To make this easier we can have the test suite automatically find all tests in the tests package. Just put this in __init__.py
(Be sure to replace "appname"):
def suite():
return unittest.TestLoader().discover("appname.tests", pattern="*.py")
This still won't allow us to run specific tests. To do that you'll need to add this code at the top of __init__.py
:
import pkgutil
import unittest
for loader, module_name, is_pkg in pkgutil.walk_packages(__path__):
module = loader.find_module(module_name).load_module(module_name)
for name in dir(module):
obj = getattr(module, name)
if isinstance(obj, type) and issubclass(obj, unittest.case.TestCase):
exec ('%s = obj' % obj.__name__)
Now you can run all your tests via manage.py test app
or specific ones via manage.py test app.TestApples
Upvotes: 2
Reputation: 481
Did you try renaming your test files to "test_foo.py", instead of "foo.py", for example?
Upvotes: 0