testtools-dev team mailing list archive
-
testtools-dev team
-
Mailing list archive
-
Message #00343
[Merge] lp:~lifeless/testtools/load-list into lp:testtools
Robert Collins has proposed merging lp:~lifeless/testtools/load-list into lp:testtools.
Requested reviews:
testtools developers (testtools-dev)
* ``testtools.run`` now supports ``--load-list``, which takes a file containing
test ids, one per line, and intersects those ids with the tests found. This
allows fine grained control of what tests are run even when the tests cannot
be named as objects to import (e.g. due to test parameterisation via
testscenarios). (Robert Collins)
--
https://code.launchpad.net/~lifeless/testtools/load-list/+merge/42196
Your team testtools developers is requested to review the proposed merge of lp:~lifeless/testtools/load-list into lp:testtools.
=== modified file 'NEWS'
--- NEWS 2010-11-29 20:32:00 +0000
+++ NEWS 2010-11-29 23:47:53 +0000
@@ -62,6 +62,12 @@
them. This is useful for integration with external test analysis/processing
tools like subunit and testrepository. (Robert Collins)
+* ``testtools.run`` now supports ``--load-list``, which takes a file containing
+ test ids, one per line, and intersects those ids with the tests found. This
+ allows fine grained control of what tests are run even when the tests cannot
+ be named as objects to import (e.g. due to test parameterisation via
+ testscenarios). (Robert Collins)
+
* Update documentation to say how to use testtools.run() on Python 2.4.
(Jonathan Lange, #501174)
=== modified file 'testtools/run.py'
--- testtools/run.py 2010-11-29 20:32:00 +0000
+++ testtools/run.py 2010-11-29 23:47:53 +0000
@@ -62,6 +62,12 @@
# removed.
# - A tweak has been added to detect 'python -m *.run' and use a
# better progName in that case.
+# - self.module is more comprehensively set to None when being invoked from
+# the commandline - __name__ is used as a sentinel value.
+# - --list has been added which can list tests (should be upstreamed).
+# - --load-list has been added which can reduce the tests used (should be
+# upstreamed).
+# - The limitation of using getopt is declared to the user.
FAILFAST = " -f, --failfast Stop on first failure\n"
CATCHBREAK = " -c, --catch Catch control-C and display results\n"
@@ -75,14 +81,16 @@
-v, --verbose Verbose output
-q, --quiet Minimal output
-l, --list List tests rather than executing them.
+ --load-list Specifies a file containing test ids, only tests matching
+ those ids are executed.
%(failfast)s%(catchbreak)s%(buffer)s
Examples:
%(progName)s test_module - run tests from test_module
%(progName)s module.TestClass - run tests from module.TestClass
%(progName)s module.Class.test_method - run specified test method
-[tests] can be a list of any number of test modules, classes and test
-methods.
+All options must come before [tests]. [tests] can be a list of any number of
+test modules, classes and test methods.
Alternative Usage: %(progName)s discover [options]
@@ -93,6 +101,8 @@
-t directory Top level directory of project (default to
start directory)
-l, --list List tests rather than executing them.
+ --load-list Specifies a file containing test ids, only tests matching
+ those ids are executed.
For test discovery all test modules must be importable from the top
level directory of the project.
@@ -130,6 +140,7 @@
self.buffer = buffer
self.defaultTest = defaultTest
self.listtests = False
+ self.load_list = None
self.testRunner = testRunner
self.testLoader = testLoader
progName = argv[0]
@@ -140,6 +151,22 @@
progName = os.path.basename(argv[0])
self.progName = progName
self.parseArgs(argv)
+ if self.load_list:
+ # TODO: preserve existing suites (like testresources does in
+ # OptimisingTestSuite.add, but with a standard protocol).
+ # This is needed because the load_tests hook allows arbitrary
+ # suites, even if that is rarely used.
+ source = file(self.load_list, 'rb')
+ try:
+ lines = source.readlines()
+ finally:
+ source.close()
+ test_ids = set(line.strip() for line in lines)
+ filtered = unittest.TestSuite()
+ for test in iterate_tests(self.test):
+ if test.id() in test_ids:
+ filtered.addTest(test)
+ self.test = filtered
if not self.listtests:
self.runTests()
else:
@@ -167,7 +194,7 @@
import getopt
long_opts = ['help', 'verbose', 'quiet', 'failfast', 'catch', 'buffer',
- 'list']
+ 'list', 'load-list=']
try:
options, args = getopt.getopt(argv[1:], 'hHvqfcbl', long_opts)
for opt, value in options:
@@ -191,6 +218,8 @@
# Should this raise an exception if -b is not valid?
if opt in ('-l', '--list'):
self.listtests = True
+ if opt == '--load-list':
+ self.load_list = value
if len(args) == 0 and self.defaultTest is None:
# createTests will load tests from self.module
self.testNames = None
@@ -240,6 +269,8 @@
help='Top level directory of project (defaults to start directory)')
parser.add_option('-l', '--list', dest='listtests', default=False,
help='List tests rather than running them.')
+ parser.add_option('--load-list', dest='load_list', default=None,
+ help='Specify a filename containing the test ids to use.')
options, args = parser.parse_args(argv)
if len(args) > 3:
@@ -257,6 +288,7 @@
if self.buffer is None:
self.buffer = options.buffer
self.listtests = options.listtests
+ self.load_list = options.load_list
if options.verbose:
self.verbosity = 2
=== modified file 'testtools/tests/test_run.py'
--- testtools/tests/test_run.py 2010-11-29 23:09:22 +0000
+++ testtools/tests/test_run.py 2010-11-29 23:47:53 +0000
@@ -49,6 +49,29 @@
testtools.runexample.TestFoo.test_quux
""", out.getvalue())
+ def test_run_load_list(self):
+ if fixtures is None:
+ self.skipTest("Need fixtures")
+ package = self.useFixture(SampleTestFixture())
+ out = StringIO.StringIO()
+ # We load two tests - one that exists and one that doesn't, and we
+ # should get the one that exists and neither the one that doesn't nor
+ # the unmentioned one that does.
+ tempdir = self.useFixture(fixtures.TempDir())
+ tempname = tempdir.path + '/tests.list'
+ f = open(tempname, 'wb')
+ try:
+ f.write("""
+testtools.runexample.TestFoo.test_bar
+testtools.runexample.missingtest
+""")
+ finally:
+ f.close()
+ run.main(['prog', '-l', '--load-list', tempname,
+ 'testtools.runexample.test_suite'], out)
+ self.assertEqual("""testtools.runexample.TestFoo.test_bar
+""", out.getvalue())
+
def test_suite():
from unittest import TestLoader
return TestLoader().loadTestsFromName(__name__)
Follow ups