pythondjangounit-testingtestingdoctest

How to get django's unittest TestLoader to find and run my doctests?


In Django, my tests are a set of test_foo.py files inside my_django_app/tests/, which each contain a TestCase subclass, and which django automatically finds and runs.

I have a bunch of utility modules with simple doctests that I would like to be included with my test suite. I tried using doctest.DocTestSuite() to define test suites in my_django_app/tests/test_doctests.py, but django's test runner does not find the new tests in that module.

Is there a way I can create a TestCase class that calls my doctests, or somehow otherwise define a new tests/test_foo.py module that would run these tests?


Solution

  • I solved this by creating a new module, my_django_app/tests/test_doctests.py, that looks like:

    import doctest
    import unittest
    
    # These are my modules that contain doctests:
    from util import bitwise
    from util import text
    from util import urlutil
    DOCTEST_MODULES = (
      bitwise,
      text,
      urlutil,
    )
    
    # unittest.TestLoader will call this when it finds this module:
    def load_tests(*args, **kwargs):
      test_all_doctests = unittest.TestSuite()
      for m in DOCTEST_MODULES:
        test_all_doctests.addTest(doctest.DocTestSuite(m))
      return test_all_doctests
    

    Django uses the builtin unittest TestLoader, which, during test discovery, will call load_tests() on your test module. So we define load_tests which creates a test suite out of all of the doctests.