diff --git a/django/test/runner.py b/django/test/runner.py
index 84fe249..5ff3f15 100644
a
|
b
|
class DiscoverRunner(object):
|
14 | 14 | A Django test runner that uses unittest2 test discovery. |
15 | 15 | """ |
16 | 16 | |
| 17 | test_suite = TestSuite |
| 18 | test_runner = unittest.TextTestRunner |
17 | 19 | test_loader = defaultTestLoader |
18 | 20 | reorder_by = (TestCase, ) |
19 | 21 | option_list = ( |
… |
… |
class DiscoverRunner(object):
|
42 | 44 | unittest.installHandler() |
43 | 45 | |
44 | 46 | def build_suite(self, test_labels=None, extra_tests=None, **kwargs): |
45 | | suite = TestSuite() |
| 47 | suite = self.test_suite() |
46 | 48 | test_labels = test_labels or ['.'] |
47 | 49 | extra_tests = extra_tests or [] |
48 | 50 | |
… |
… |
class DiscoverRunner(object):
|
107 | 109 | return setup_databases(self.verbosity, self.interactive, **kwargs) |
108 | 110 | |
109 | 111 | def run_suite(self, suite, **kwargs): |
110 | | return unittest.TextTestRunner( |
| 112 | return self.test_runner( |
111 | 113 | verbosity=self.verbosity, |
112 | 114 | failfast=self.failfast, |
113 | 115 | ).run(suite) |
… |
… |
def reorder_suite(suite, classes):
|
201 | 203 | classes[1], etc. Tests with no match in classes are placed last. |
202 | 204 | """ |
203 | 205 | class_count = len(classes) |
204 | | bins = [unittest.TestSuite() for i in range(class_count+1)] |
| 206 | suite_class = type(suite) |
| 207 | bins = [suite_class() for i in range(class_count+1)] |
205 | 208 | partition_suite(suite, classes, bins) |
206 | 209 | for i in range(class_count): |
207 | 210 | bins[0].addTests(bins[i+1]) |
diff --git a/docs/releases/1.7.txt b/docs/releases/1.7.txt
index 4177b46..cffca16 100644
a
|
b
|
Templates
|
282 | 282 | :setting:`TEMPLATE_DEBUG` is ``True``. This allows template origins to be |
283 | 283 | inspected and logged outside of the ``django.template`` infrastructure. |
284 | 284 | |
| 285 | Tests |
| 286 | ^^^^^ |
| 287 | |
| 288 | * :class:`~django.test.runner.DiscoverRunner` has two new attributes, |
| 289 | :attr:`test_suite` and :attr:`test_runner`, which facilitate |
| 290 | overriding the way tests are collected and run. Documentation has been |
| 291 | added for the similar :attr:`test_loader` attribute |
| 292 | which has been in place since 1.6. |
| 293 | |
| 294 | |
285 | 295 | Backwards incompatible changes in 1.7 |
286 | 296 | ===================================== |
287 | 297 | |
diff --git a/docs/topics/testing/advanced.txt b/docs/topics/testing/advanced.txt
index d8d59c6..7f9ac84 100644
a
|
b
|
Defining a test runner
|
299 | 299 | .. currentmodule:: django.test.runner |
300 | 300 | |
301 | 301 | A test runner is a class defining a ``run_tests()`` method. Django ships |
302 | | with a ``DiscoverRunner`` class that defines the default Django |
303 | | testing behavior. This class defines the ``run_tests()`` entry point, |
304 | | plus a selection of other methods that are used to by ``run_tests()`` to |
305 | | set up, execute and tear down the test suite. |
| 302 | with a ``DiscoverRunner`` class that defines the default Django testing |
| 303 | behavior. This class defines the ``run_tests()`` entry point, plus a |
| 304 | selection of other methods that are used to by ``run_tests()`` to set up, |
| 305 | execute and tear down the test suite. |
306 | 306 | |
307 | 307 | .. class:: DiscoverRunner(pattern='test*.py', top_level=None, verbosity=1, interactive=True, failfast=True, **kwargs) |
308 | 308 | |
| 309 | .. versionadded:: 1.6 |
| 310 | |
309 | 311 | ``DiscoverRunner`` will search for tests in any file matching ``pattern``. |
310 | 312 | |
311 | 313 | ``top_level`` can be used to specify the directory containing your |
… |
… |
set up, execute and tear down the test suite.
|
339 | 341 | Attributes |
340 | 342 | ~~~~~~~~~~ |
341 | 343 | |
| 344 | .. attribute:: DiscoverRunner.test_suite |
| 345 | |
| 346 | .. versionadded:: 1.7 |
| 347 | |
| 348 | The class used to build the test suite. By default it is set to |
| 349 | ``unittest.TestSuite``. This can be overridden if you wish to implement |
| 350 | different logic for collecting tests into a test suite. |
| 351 | |
| 352 | .. attribute:: DiscoverRunner.test_runner |
| 353 | |
| 354 | .. versionadded:: 1.7 |
| 355 | |
| 356 | This is the class of the low-level test runner which is used to execute |
| 357 | the individual tests and format the results. By default it is set to |
| 358 | ``unittest.TextTestRunner``. Despite the unfortunate similarity in |
| 359 | naming conventions, this is not the same type of class as |
| 360 | ``DiscoverRunner``, which covers a broader set of responsibilites. You |
| 361 | can override this attribute to modify the way tests are run and reported. |
| 362 | |
| 363 | .. attribute:: DiscoverRunner.test_loader |
| 364 | |
| 365 | .. versionadded:: 1.6 |
| 366 | |
| 367 | This is the class that loads tests, whether from TestCases or modules or |
| 368 | otherwise and bundles them into test suites for the runner to execute. |
| 369 | By default it is set to ``unittest.defaultTestLoader``. You can override |
| 370 | this attribute if your tests are going to be loaded in unusual ways. |
| 371 | |
342 | 372 | .. attribute:: DiscoverRunner.option_list |
343 | 373 | |
344 | 374 | This is the tuple of ``optparse`` options which will be fed into the |
diff --git a/tests/test_runner/test_discover_runner.py b/tests/test_runner/test_discover_runner.py
index 4494b2b..bd26e2e 100644
a
|
b
|
|
1 | 1 | from contextlib import contextmanager |
2 | 2 | import os |
3 | 3 | import sys |
4 | | from unittest import expectedFailure |
| 4 | from unittest import expectedFailure, TestSuite, TextTestRunner, defaultTestLoader |
5 | 5 | |
6 | 6 | from django.test import TestCase |
7 | 7 | from django.test.runner import DiscoverRunner |
… |
… |
class DiscoverRunnerTest(TestCase):
|
68 | 68 | ).countTestCases() |
69 | 69 | |
70 | 70 | self.assertEqual(count, 3) |
| 71 | |
| 72 | def test_overrideable_test_suite(self): |
| 73 | self.assertEqual(DiscoverRunner().test_suite, TestSuite) |
| 74 | |
| 75 | def test_overrideable_test_runner(self): |
| 76 | self.assertEqual(DiscoverRunner().test_runner, TextTestRunner) |
| 77 | |
| 78 | def test_overrideable_test_loader(self): |
| 79 | self.assertEqual(DiscoverRunner().test_loader, defaultTestLoader) |