# copyright 2003-2012 LOGILAB S.A. (Paris, FRANCE), all rights reserved.
# contact http://www.logilab.fr/ -- mailto:contact@logilab.fr
#
# This file is part of logilab-common.
#
# logilab-common is free software: you can redistribute it and/or modify it under
# the terms of the GNU Lesser General Public License as published by the Free
# Software Foundation, either version 2.1 of the License, or (at your option) any
# later version.
#
# logilab-common is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
# details.
#
# You should have received a copy of the GNU Lesser General Public License along
# with logilab-common. If not, see .
"""unittest module for logilab.comon.testlib"""
import os
import sys
from os.path import join, dirname, isdir, isfile, abspath, exists
from cStringIO import StringIO
import tempfile
import shutil
try:
__file__
except NameError:
__file__ = sys.argv[0]
from logilab.common.testlib import (unittest, TestSuite, unittest_main, Tags,
TestCase, mock_object, create_files, InnerTest, with_tempdir, tag,
require_version, require_module)
from logilab.common.pytest import SkipAwareTextTestRunner, NonStrictTestLoader
class MockTestCase(TestCase):
def __init__(self):
# Do not call unittest.TestCase's __init__
pass
def fail(self, msg):
raise AssertionError(msg)
class UtilTC(TestCase):
def test_mockobject(self):
obj = mock_object(foo='bar', baz='bam')
self.assertEqual(obj.foo, 'bar')
self.assertEqual(obj.baz, 'bam')
def test_create_files(self):
chroot = tempfile.mkdtemp()
path_to = lambda path: join(chroot, path)
dircontent = lambda path: sorted(os.listdir(join(chroot, path)))
try:
self.assertFalse(isdir(path_to('a/')))
create_files(['a/b/foo.py', 'a/b/c/', 'a/b/c/d/e.py'], chroot)
# make sure directories exist
self.assertTrue(isdir(path_to('a')))
self.assertTrue(isdir(path_to('a/b')))
self.assertTrue(isdir(path_to('a/b/c')))
self.assertTrue(isdir(path_to('a/b/c/d')))
# make sure files exist
self.assertTrue(isfile(path_to('a/b/foo.py')))
self.assertTrue(isfile(path_to('a/b/c/d/e.py')))
# make sure only asked files were created
self.assertEqual(dircontent('a'), ['b'])
self.assertEqual(dircontent('a/b'), ['c', 'foo.py'])
self.assertEqual(dircontent('a/b/c'), ['d'])
self.assertEqual(dircontent('a/b/c/d'), ['e.py'])
finally:
shutil.rmtree(chroot)
class TestlibTC(TestCase):
def mkdir(self, path):
if not exists(path):
self._dirs.add(path)
os.mkdir(path)
def setUp(self):
self.tc = MockTestCase()
self._dirs = set()
def tearDown(self):
while(self._dirs):
shutil.rmtree(self._dirs.pop(), ignore_errors=True)
def test_dict_equals(self):
"""tests TestCase.assertDictEqual"""
d1 = {'a' : 1, 'b' : 2}
d2 = {'a' : 1, 'b' : 3}
d3 = dict(d1)
self.assertRaises(AssertionError, self.tc.assertDictEqual, d1, d2)
self.tc.assertDictEqual(d1, d3)
self.tc.assertDictEqual(d3, d1)
self.tc.assertDictEqual(d1, d1)
def test_list_equals(self):
"""tests TestCase.assertListEqual"""
l1 = range(10)
l2 = range(5)
l3 = range(10)
self.assertRaises(AssertionError, self.tc.assertListEqual, l1, l2)
self.tc.assertListEqual(l1, l1)
self.tc.assertListEqual(l1, l3)
self.tc.assertListEqual(l3, l1)
def test_xml_valid(self):
"""tests xml is valid"""
valid = """
Logilab
"""
invalid = """
"""
self.tc.assertXMLStringWellFormed(valid)
self.assertRaises(AssertionError, self.tc.assertXMLStringWellFormed, invalid)
invalid = """
"""
self.assertRaises(AssertionError, self.tc.assertXMLStringWellFormed, invalid)
def test_equality_for_sets(self):
s1 = set('ab')
s2 = set('a')
self.assertRaises(AssertionError, self.tc.assertSetEqual, s1, s2)
self.tc.assertSetEqual(s1, s1)
self.tc.assertSetEqual(set(), set())
def test_file_equality(self):
foo = join(dirname(__file__), 'data', 'foo.txt')
spam = join(dirname(__file__), 'data', 'spam.txt')
self.assertRaises(AssertionError, self.tc.assertFileEqual, foo, spam)
self.tc.assertFileEqual(foo, foo)
def test_dir_equality(self):
ref = join(dirname(__file__), 'data', 'reference_dir')
same = join(dirname(__file__), 'data', 'same_dir')
subdir_differ = join(dirname(__file__), 'data', 'subdir_differ_dir')
file_differ = join(dirname(__file__), 'data', 'file_differ_dir')
content_differ = join(dirname(__file__), 'data', 'content_differ_dir')
ed1 = join(dirname(__file__), 'data', 'empty_dir_1')
ed2 = join(dirname(__file__), 'data', 'empty_dir_2')
for path in (ed1, ed2, join(subdir_differ, 'unexpected')):
self.mkdir(path)
self.assertDirEqual(ed1, ed2)
self.assertDirEqual(ref, ref)
self.assertDirEqual( ref, same)
self.assertRaises(AssertionError, self.assertDirEqual, ed1, ref)
self.assertRaises(AssertionError, self.assertDirEqual, ref, ed2)
self.assertRaises(AssertionError, self.assertDirEqual, subdir_differ, ref)
self.assertRaises(AssertionError, self.assertDirEqual, file_differ, ref)
self.assertRaises(AssertionError, self.assertDirEqual, ref, content_differ)
def test_stream_equality(self):
foo = join(dirname(__file__), 'data', 'foo.txt')
spam = join(dirname(__file__), 'data', 'spam.txt')
stream1 = open(foo)
self.tc.assertStreamEqual(stream1, stream1)
stream1 = open(foo)
stream2 = open(spam)
self.assertRaises(AssertionError, self.tc.assertStreamEqual, stream1, stream2)
def test_text_equality(self):
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, "toto", 12)
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, "toto", 12)
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, "toto", None)
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, "toto", None)
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, 3.12, u"toto")
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, 3.12, u"toto")
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, None, u"toto")
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, None, u"toto")
self.tc.assertMultiLineEqual('toto\ntiti', 'toto\ntiti')
self.tc.assertMultiLineEqual('toto\ntiti', 'toto\ntiti')
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, 'toto\ntiti', 'toto\n titi\n')
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, 'toto\ntiti', 'toto\n titi\n')
foo = join(dirname(__file__), 'data', 'foo.txt')
spam = join(dirname(__file__), 'data', 'spam.txt')
text1 = open(foo).read()
self.tc.assertMultiLineEqual(text1, text1)
self.tc.assertMultiLineEqual(text1, text1)
text2 = open(spam).read()
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, text1, text2)
self.assertRaises(AssertionError, self.tc.assertMultiLineEqual, text1, text2)
def test_default_datadir(self):
expected_datadir = join(dirname(abspath(__file__)), 'data')
self.assertEqual(self.datadir, expected_datadir)
self.assertEqual(self.datapath('foo'), join(expected_datadir, 'foo'))
def test_multiple_args_datadir(self):
expected_datadir = join(dirname(abspath(__file__)), 'data')
self.assertEqual(self.datadir, expected_datadir)
self.assertEqual(self.datapath('foo', 'bar'), join(expected_datadir, 'foo', 'bar'))
def test_custom_datadir(self):
class MyTC(TestCase):
datadir = 'foo'
def test_1(self): pass
# class' custom datadir
tc = MyTC('test_1')
self.assertEqual(tc.datapath('bar'), join('foo', 'bar'))
def test_cached_datadir(self):
"""test datadir is cached on the class"""
class MyTC(TestCase):
def test_1(self): pass
expected_datadir = join(dirname(abspath(__file__)), 'data')
tc = MyTC('test_1')
self.assertEqual(tc.datadir, expected_datadir)
# changing module should not change the datadir
MyTC.__module__ = 'os'
self.assertEqual(tc.datadir, expected_datadir)
# even on new instances
tc2 = MyTC('test_1')
self.assertEqual(tc2.datadir, expected_datadir)
def test_is(self):
obj_1 = []
obj_2 = []
self.assertIs(obj_1, obj_1)
self.assertRaises(AssertionError, self.assertIs, obj_1, obj_2)
def test_isnot(self):
obj_1 = []
obj_2 = []
self.assertIsNot(obj_1, obj_2)
self.assertRaises(AssertionError, self.assertIsNot, obj_1, obj_1)
def test_none(self):
self.assertIsNone(None)
self.assertRaises(AssertionError, self.assertIsNone, object())
def test_not_none(self):
self.assertIsNotNone(object())
self.assertRaises(AssertionError, self.assertIsNotNone, None)
def test_in(self):
self.assertIn("a", "dsqgaqg")
obj, seq = 'a', ('toto', "azf", "coin")
self.assertRaises(AssertionError, self.assertIn, obj, seq)
def test_not_in(self):
self.assertNotIn('a', ('toto', "azf", "coin"))
self.assertRaises(AssertionError, self.assertNotIn, 'a', "dsqgaqg")
class GenerativeTestsTC(TestCase):
def setUp(self):
output = StringIO()
self.runner = SkipAwareTextTestRunner(stream=output)
def test_generative_ok(self):
class FooTC(TestCase):
def test_generative(self):
for i in xrange(10):
yield self.assertEqual, i, i
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 10)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 0)
def test_generative_half_bad(self):
class FooTC(TestCase):
def test_generative(self):
for i in xrange(10):
yield self.assertEqual, i%2, 0
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 10)
self.assertEqual(len(result.failures), 5)
self.assertEqual(len(result.errors), 0)
def test_generative_error(self):
class FooTC(TestCase):
def test_generative(self):
for i in xrange(10):
if i == 5:
raise ValueError('STOP !')
yield self.assertEqual, i, i
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 5)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 1)
def test_generative_error2(self):
class FooTC(TestCase):
def test_generative(self):
for i in xrange(10):
if i == 5:
yield self.ouch
yield self.assertEqual, i, i
def ouch(self): raise ValueError('stop !')
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 11)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 1)
def test_generative_setup(self):
class FooTC(TestCase):
def setUp(self):
raise ValueError('STOP !')
def test_generative(self):
for i in xrange(10):
yield self.assertEqual, i, i
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 1)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 1)
def test_generative_inner_skip(self):
class FooTC(TestCase):
def check(self, val):
if val == 5:
self.innerSkip("no 5")
else:
self.assertEqual(val, val)
def test_generative(self):
for i in xrange(10):
yield InnerTest("check_%s"%i, self.check, i)
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 10)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 0)
self.assertEqual(len(result.skipped), 1)
def test_generative_skip(self):
class FooTC(TestCase):
def check(self, val):
if val == 5:
self.skipTest("no 5")
else:
self.assertEqual(val, val)
def test_generative(self):
for i in xrange(10):
yield InnerTest("check_%s"%i, self.check, i)
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 10)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 0)
self.assertEqual(len(result.skipped), 1)
def test_generative_inner_error(self):
class FooTC(TestCase):
def check(self, val):
if val == 5:
raise ValueError("no 5")
else:
self.assertEqual(val, val)
def test_generative(self):
for i in xrange(10):
yield InnerTest("check_%s"%i, self.check, i)
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 10)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 1)
self.assertEqual(len(result.skipped), 0)
def test_generative_inner_failure(self):
class FooTC(TestCase):
def check(self, val):
if val == 5:
self.assertEqual(val, val+1)
else:
self.assertEqual(val, val)
def test_generative(self):
for i in xrange(10):
yield InnerTest("check_%s"%i, self.check, i)
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 10)
self.assertEqual(len(result.failures), 1)
self.assertEqual(len(result.errors), 0)
self.assertEqual(len(result.skipped), 0)
class ExitFirstTC(TestCase):
def setUp(self):
output = StringIO()
self.runner = SkipAwareTextTestRunner(stream=output, exitfirst=True)
def test_failure_exit_first(self):
class FooTC(TestCase):
def test_1(self): pass
def test_2(self): assert False
def test_3(self): pass
tests = [FooTC('test_1'), FooTC('test_2')]
result = self.runner.run(TestSuite(tests))
self.assertEqual(result.testsRun, 2)
self.assertEqual(len(result.failures), 1)
self.assertEqual(len(result.errors), 0)
def test_error_exit_first(self):
class FooTC(TestCase):
def test_1(self): pass
def test_2(self): raise ValueError()
def test_3(self): pass
tests = [FooTC('test_1'), FooTC('test_2'), FooTC('test_3')]
result = self.runner.run(TestSuite(tests))
self.assertEqual(result.testsRun, 2)
self.assertEqual(len(result.failures), 0)
self.assertEqual(len(result.errors), 1)
def test_generative_exit_first(self):
class FooTC(TestCase):
def test_generative(self):
for i in xrange(10):
yield self.assert_, False
result = self.runner.run(FooTC('test_generative'))
self.assertEqual(result.testsRun, 1)
self.assertEqual(len(result.failures), 1)
self.assertEqual(len(result.errors), 0)
class TestLoaderTC(TestCase):
## internal classes for test purposes ########
class FooTC(TestCase):
def test_foo1(self): pass
def test_foo2(self): pass
def test_bar1(self): pass
class BarTC(TestCase):
def test_bar2(self): pass
##############################################
def setUp(self):
self.loader = NonStrictTestLoader()
self.module = TestLoaderTC # mock_object(FooTC=TestLoaderTC.FooTC, BarTC=TestLoaderTC.BarTC)
self.output = StringIO()
self.runner = SkipAwareTextTestRunner(stream=self.output)
def assertRunCount(self, pattern, module, expected_count, skipped=()):
self.loader.test_pattern = pattern
self.loader.skipped_patterns = skipped
if pattern:
suite = self.loader.loadTestsFromNames([pattern], module)
else:
suite = self.loader.loadTestsFromModule(module)
result = self.runner.run(suite)
self.loader.test_pattern = None
self.loader.skipped_patterns = ()
self.assertEqual(result.testsRun, expected_count)
def test_collect_everything(self):
"""make sure we don't change the default behaviour
for loadTestsFromModule() and loadTestsFromTestCase
"""
testsuite = self.loader.loadTestsFromModule(self.module)
self.assertEqual(len(testsuite._tests), 2)
suite1, suite2 = testsuite._tests
self.assertEqual(len(suite1._tests) + len(suite2._tests), 4)
def test_collect_with_classname(self):
self.assertRunCount('FooTC', self.module, 3)
self.assertRunCount('BarTC', self.module, 1)
def test_collect_with_classname_and_pattern(self):
data = [('FooTC.test_foo1', 1), ('FooTC.test_foo', 2), ('FooTC.test_fo', 2),
('FooTC.foo1', 1), ('FooTC.foo', 2), ('FooTC.whatever', 0)
]
for pattern, expected_count in data:
yield self.assertRunCount, pattern, self.module, expected_count
def test_collect_with_pattern(self):
data = [('test_foo1', 1), ('test_foo', 2), ('test_bar', 2),
('foo1', 1), ('foo', 2), ('bar', 2), ('ba', 2),
('test', 4), ('ab', 0),
]
for pattern, expected_count in data:
yield self.assertRunCount, pattern, self.module, expected_count
def test_testcase_with_custom_metaclass(self):
class mymetaclass(type): pass
class MyMod:
class MyTestCase(TestCase):
__metaclass__ = mymetaclass
def test_foo1(self): pass
def test_foo2(self): pass
def test_bar(self): pass
data = [('test_foo1', 1), ('test_foo', 2), ('test_bar', 1),
('foo1', 1), ('foo', 2), ('bar', 1), ('ba', 1),
('test', 3), ('ab', 0),
('MyTestCase.test_foo1', 1), ('MyTestCase.test_foo', 2),
('MyTestCase.test_fo', 2), ('MyTestCase.foo1', 1),
('MyTestCase.foo', 2), ('MyTestCase.whatever', 0)
]
for pattern, expected_count in data:
yield self.assertRunCount, pattern, MyMod, expected_count
def test_collect_everything_and_skipped_patterns(self):
testdata = [ (['foo1'], 3), (['foo'], 2),
(['foo', 'bar'], 0), ]
for skipped, expected_count in testdata:
yield self.assertRunCount, None, self.module, expected_count, skipped
def test_collect_specific_pattern_and_skip_some(self):
testdata = [ ('bar', ['foo1'], 2), ('bar', [], 2),
('bar', ['bar'], 0), ]
for runpattern, skipped, expected_count in testdata:
yield self.assertRunCount, runpattern, self.module, expected_count, skipped
def test_skip_classname(self):
testdata = [ (['BarTC'], 3), (['FooTC'], 1), ]
for skipped, expected_count in testdata:
yield self.assertRunCount, None, self.module, expected_count, skipped
def test_skip_classname_and_specific_collect(self):
testdata = [ ('bar', ['BarTC'], 1), ('foo', ['FooTC'], 0), ]
for runpattern, skipped, expected_count in testdata:
yield self.assertRunCount, runpattern, self.module, expected_count, skipped
def test_nonregr_dotted_path(self):
self.assertRunCount('FooTC.test_foo', self.module, 2)
def test_inner_tests_selection(self):
class MyMod:
class MyTestCase(TestCase):
def test_foo(self): pass
def test_foobar(self):
for i in xrange(5):
if i%2 == 0:
yield InnerTest('even', lambda: None)
else:
yield InnerTest('odd', lambda: None)
yield lambda: None
# FIXME InnerTest masked by pattern usage
# data = [('foo', 7), ('test_foobar', 6), ('even', 3), ('odd', 2), ]
data = [('foo', 7), ('test_foobar', 6), ('even', 0), ('odd', 0), ]
for pattern, expected_count in data:
yield self.assertRunCount, pattern, MyMod, expected_count
def test_nonregr_class_skipped_option(self):
class MyMod:
class MyTestCase(TestCase):
def test_foo(self): pass
def test_bar(self): pass
class FooTC(TestCase):
def test_foo(self): pass
self.assertRunCount('foo', MyMod, 2)
self.assertRunCount(None, MyMod, 3)
self.assertRunCount('foo', MyMod, 1, ['FooTC'])
self.assertRunCount(None, MyMod, 2, ['FooTC'])
def test__classes_are_ignored(self):
class MyMod:
class _Base(TestCase):
def test_1(self): pass
class MyTestCase(_Base):
def test_2(self): pass
self.assertRunCount(None, MyMod, 2)
class DecoratorTC(TestCase):
@with_tempdir
def test_tmp_dir_normal_1(self):
tempdir = tempfile.gettempdir()
# assert temp directory is empty
self.assertListEqual(list(os.walk(tempdir)),
[(tempdir, [], [])])
witness = []
@with_tempdir
def createfile(list):
fd1, fn1 = tempfile.mkstemp()
fd2, fn2 = tempfile.mkstemp()
dir = tempfile.mkdtemp()
fd3, fn3 = tempfile.mkstemp(dir=dir)
tempfile.mkdtemp()
list.append(True)
for fd in (fd1, fd2, fd3):
os.close(fd)
self.assertFalse(witness)
createfile(witness)
self.assertTrue(witness)
self.assertEqual(tempfile.gettempdir(), tempdir)
# assert temp directory is empty
self.assertListEqual(list(os.walk(tempdir)),
[(tempdir, [], [])])
@with_tempdir
def test_tmp_dir_normal_2(self):
tempdir = tempfile.gettempdir()
# assert temp directory is empty
self.assertListEqual(list(os.walk(tempfile.tempdir)),
[(tempfile.tempdir, [], [])])
class WitnessException(Exception):
pass
@with_tempdir
def createfile():
fd1, fn1 = tempfile.mkstemp()
fd2, fn2 = tempfile.mkstemp()
dir = tempfile.mkdtemp()
fd3, fn3 = tempfile.mkstemp(dir=dir)
tempfile.mkdtemp()
for fd in (fd1, fd2, fd3):
os.close(fd)
raise WitnessException()
self.assertRaises(WitnessException, createfile)
# assert tempdir didn't change
self.assertEqual(tempfile.gettempdir(), tempdir)
# assert temp directory is empty
self.assertListEqual(list(os.walk(tempdir)),
[(tempdir, [], [])])
def setUp(self):
self.pyversion = sys.version_info
def tearDown(self):
sys.version_info = self.pyversion
def test_require_version_good(self):
""" should return the same function
"""
def func() :
pass
sys.version_info = (2, 5, 5, 'final', 4)
current = sys.version_info[:3]
compare = ('2.4', '2.5', '2.5.4', '2.5.5')
for version in compare:
decorator = require_version(version)
self.assertEqual(func, decorator(func), '%s =< %s : function \
return by the decorator should be the same.' % (version,
'.'.join([str(element) for element in current])))
def test_require_version_bad(self):
""" should return a different function : skipping test
"""
def func() :
pass
sys.version_info = (2, 5, 5, 'final', 4)
current = sys.version_info[:3]
compare = ('2.5.6', '2.6', '2.6.5')
for version in compare:
decorator = require_version(version)
self.assertNotEqual(func, decorator(func), '%s >= %s : function \
return by the decorator should NOT be the same.'
% ('.'.join([str(element) for element in current]), version))
def test_require_version_exception(self):
""" should throw a ValueError exception
"""
def func() :
pass
compare = ('2.5.a', '2.a', 'azerty')
for version in compare:
decorator = require_version(version)
self.assertRaises(ValueError, decorator, func)
def test_require_module_good(self):
""" should return the same function
"""
def func() :
pass
module = 'sys'
decorator = require_module(module)
self.assertEqual(func, decorator(func), 'module %s exists : function \
return by the decorator should be the same.' % module)
def test_require_module_bad(self):
""" should return a different function : skipping test
"""
def func() :
pass
modules = ('bla', 'blo', 'bli')
for module in modules:
try:
__import__(module)
pass
except ImportError:
decorator = require_module(module)
self.assertNotEqual(func, decorator(func), 'module %s does \
not exist : function return by the decorator should \
NOT be the same.' % module)
return
print 'all modules in %s exist. Could not test %s' % (', '.join(modules),
sys._getframe().f_code.co_name)
class TagTC(TestCase):
def setUp(self):
@tag('testing', 'bob')
def bob(a, b, c):
return (a + b) * c
self.func = bob
class TagTestTC(TestCase):
tags = Tags('one', 'two')
def test_one(self):
self.assertTrue(True)
@tag('two', 'three')
def test_two(self):
self.assertTrue(True)
@tag('three', inherit=False)
def test_three(self):
self.assertTrue(True)
self.cls = TagTestTC
def test_tag_decorator(self):
bob = self.func
self.assertEqual(bob(2, 3, 7), 35)
self.assertTrue(hasattr(bob, 'tags'))
self.assertSetEqual(bob.tags, set(['testing', 'bob']))
def test_tags_class(self):
tags = self.func.tags
self.assertTrue(tags['testing'])
self.assertFalse(tags['Not inside'])
def test_tags_match(self):
tags = self.func.tags
self.assertTrue(tags.match('testing'))
self.assertFalse(tags.match('other'))
self.assertFalse(tags.match('testing and coin'))
self.assertTrue(tags.match('testing or other'))
self.assertTrue(tags.match('not other'))
self.assertTrue(tags.match('not other or (testing and bibi)'))
self.assertTrue(tags.match('other or (testing and bob)'))
def test_tagged_class(self):
def options(tags):
class Options(object):
tags_pattern = tags
return Options()
cls = self.cls
runner = SkipAwareTextTestRunner()
self.assertTrue(runner.does_match_tags(cls.test_one))
self.assertTrue(runner.does_match_tags(cls.test_two))
self.assertTrue(runner.does_match_tags(cls.test_three))
runner = SkipAwareTextTestRunner(options=options('one'))
self.assertTrue(runner.does_match_tags(cls.test_one))
self.assertTrue(runner.does_match_tags(cls.test_two))
self.assertFalse(runner.does_match_tags(cls.test_three))
runner = SkipAwareTextTestRunner(options=options('two'))
self.assertTrue(runner.does_match_tags(cls.test_one))
self.assertTrue(runner.does_match_tags(cls.test_two))
self.assertFalse(runner.does_match_tags(cls.test_three))
runner = SkipAwareTextTestRunner(options=options('three'))
self.assertFalse(runner.does_match_tags(cls.test_one))
self.assertTrue(runner.does_match_tags(cls.test_two))
self.assertTrue(runner.does_match_tags(cls.test_three))
runner = SkipAwareTextTestRunner(options=options('two or three'))
self.assertTrue(runner.does_match_tags(cls.test_one))
self.assertTrue(runner.does_match_tags(cls.test_two))
self.assertTrue(runner.does_match_tags(cls.test_three))
runner = SkipAwareTextTestRunner(options=options('two and three'))
self.assertFalse(runner.does_match_tags(cls.test_one))
self.assertTrue(runner.does_match_tags(cls.test_two))
self.assertFalse(runner.does_match_tags(cls.test_three))
if __name__ == '__main__':
unittest_main()