diff --git a/os_testr/os_testr.py b/os_testr/os_testr.py index 9751c02..0e5176d 100755 --- a/os_testr/os_testr.py +++ b/os_testr/os_testr.py @@ -26,9 +26,14 @@ from testtools import run as testtools_run def get_parser(args): parser = argparse.ArgumentParser( description='Tool to run openstack tests') - parser.add_argument('--blacklist_file', '-b', - help='Path to a blacklist file, this file contains a' - ' separate regex exclude on each newline') + list_files = parser.add_mutually_exclusive_group() + list_files.add_argument('--blacklist_file', '-b', + help='Path to a blacklist file, this file ' + 'contains a separate regex exclude on each ' + 'newline') + list_files.add_argument('--whitelist_file', '-w', + help='Path to a whitelist file, this file ' + 'contains a separate regex on each newline.') group = parser.add_mutually_exclusive_group() group.add_argument('--regex', '-r', help='A normal testr selection regex. If a blacklist ' @@ -124,7 +129,11 @@ def path_to_regex(path): return root.replace('/', '.') -def construct_regex(blacklist_file, regex, print_exclude): +def get_regex_from_whitelist_file(file_path): + return '|'.join(open(file_path).read().splitlines()) + + +def construct_regex(blacklist_file, whitelist_file, regex, print_exclude): if not blacklist_file: exclude_regex = '' else: @@ -148,6 +157,8 @@ def construct_regex(blacklist_file, regex, print_exclude): exclude_regex = "(?!.*" + exclude_regex + ")" if regex: exclude_regex += regex + if whitelist_file: + exclude_regex += '%s' % get_regex_from_whitelist_file(whitelist_file) return exclude_regex @@ -280,7 +291,9 @@ def main(): regex = path_to_regex(opts.path) else: regex = opts.regex - exclude_regex = construct_regex(opts.blacklist_file, regex, + exclude_regex = construct_regex(opts.blacklist_file, + opts.whitelist_file, + regex, opts.print_exclude) exit(_select_and_call_runner(opts, exclude_regex)) diff --git a/os_testr/tests/test_os_testr.py b/os_testr/tests/test_os_testr.py index f820ed1..85d23ff 100644 --- a/os_testr/tests/test_os_testr.py +++ b/os_testr/tests/test_os_testr.py @@ -129,7 +129,7 @@ class TestCallers(base.TestCase): class TestConstructRegex(base.TestCase): def test_regex_passthrough(self): - result = os_testr.construct_regex(None, 'fake_regex', False) + result = os_testr.construct_regex(None, None, 'fake_regex', False) self.assertEqual(result, 'fake_regex') def test_blacklist_regex_with_comments(self): @@ -139,7 +139,7 @@ class TestConstructRegex(base.TestCase): blacklist_file.seek(0) with mock.patch('six.moves.builtins.open', return_value=blacklist_file): - result = os_testr.construct_regex('fake_path', None, False) + result = os_testr.construct_regex('fake_path', None, None, False) self.assertEqual( result, "(?!.*fake_regex_3|fake_regex_2|fake_regex_1|fake_regex_0|)") @@ -151,7 +151,7 @@ class TestConstructRegex(base.TestCase): blacklist_file.seek(0) with mock.patch('six.moves.builtins.open', return_value=blacklist_file): - result = os_testr.construct_regex('fake_path', None, False) + result = os_testr.construct_regex('fake_path', None, None, False) self.assertEqual( result, "(?!.*fake_regex_3|fake_regex_2|fake_regex_1|fake_regex_0|)") @@ -163,7 +163,8 @@ class TestConstructRegex(base.TestCase): blacklist_file.seek(0) with mock.patch('six.moves.builtins.open', return_value=blacklist_file): - result = os_testr.construct_regex('fake_path', 'fake_regex', False) + result = os_testr.construct_regex('fake_path', None, + 'fake_regex', False) expected_regex = ("(?!.*fake_regex_3|fake_regex_2|fake_regex_1|" "fake_regex_0|)fake_regex") @@ -176,7 +177,8 @@ class TestConstructRegex(base.TestCase): blacklist_file.seek(0) with mock.patch('six.moves.builtins.open', return_value=blacklist_file): - result = os_testr.construct_regex('fake_path', 'fake_regex', False) + result = os_testr.construct_regex('fake_path', None, + 'fake_regex', False) expected_regex = ("(?!.*fake_regex_3|fake_regex_2|fake_regex_1|" "fake_regex_0|)fake_regex") @@ -190,7 +192,8 @@ class TestConstructRegex(base.TestCase): blacklist_file.seek(0) with mock.patch('six.moves.builtins.open', return_value=blacklist_file): - result = os_testr.construct_regex('fake_path', None, True) + result = os_testr.construct_regex('fake_path', None, + None, True) expected_regex = ("(?!.*fake_regex_3|fake_regex_2|fake_regex_1|" "fake_regex_0|)") @@ -211,7 +214,8 @@ class TestConstructRegex(base.TestCase): blacklist_file.seek(0) with mock.patch('six.moves.builtins.open', return_value=blacklist_file): - result = os_testr.construct_regex('fake_path', None, True) + result = os_testr.construct_regex('fake_path', None, + None, True) expected_regex = ("(?!.*fake_regex_3|fake_regex_2|fake_regex_1|" "fake_regex_0|)") @@ -223,3 +227,30 @@ class TestConstructRegex(base.TestCase): self.assertIn(('fake_regex_1', ''), args) self.assertIn(('fake_regex_2', ''), args) self.assertIn(('fake_regex_3', ''), args) + + +class TestWhitelistFile(base.TestCase): + def test_read_whitelist_file(self): + file_contents = """regex_a +regex_b""" + whitelist_file = six.StringIO() + whitelist_file.write(file_contents) + whitelist_file.seek(0) + with mock.patch('six.moves.builtins.open', + return_value=whitelist_file): + regex = os_testr.get_regex_from_whitelist_file('/path/to/not_used') + self.assertEqual('regex_a|regex_b', regex) + + def test_whitelist_regex_without_comments_and_regex(self): + file_contents = """regex_a +regex_b""" + whitelist_file = six.StringIO() + whitelist_file.write(file_contents) + whitelist_file.seek(0) + with mock.patch('six.moves.builtins.open', + return_value=whitelist_file): + result = os_testr.construct_regex(None, 'fake_path', + None, False) + + expected_regex = 'regex_a|regex_b' + self.assertEqual(result, expected_regex)