From c48dae981b27ff5ec382393ea2ebcf2afe287408 Mon Sep 17 00:00:00 2001 From: Oleksandr Savatieiev Date: Wed, 14 Sep 2016 12:36:41 +0300 Subject: [PATCH] Added 'detailed' option to switch messages/traces column on/off --- setup.py | 7 ++- tempest_parser/etc/tempest-parser.conf | 3 +- tempest_parser/reports/csv_reporter.py | 59 ++++++++++++------- tempest_parser/reports/reporter.py | 7 ++- .../templates/tempest_trending_report.html | 6 ++ tempest_parser/tparser.py | 19 +++++- tempest_parser/utils/config.py | 12 ++++ 7 files changed, 84 insertions(+), 29 deletions(-) diff --git a/setup.py b/setup.py index 8240960..2b2d4d1 100644 --- a/setup.py +++ b/setup.py @@ -4,7 +4,7 @@ from setuptools import setup, find_packages here = os.path.abspath(os.path.dirname(__file__)) -README = open(os.path.join(here, 'README.md')).read() +README = open(os.path.join(here, 'README')).read() DATA = [ ('etc', [f for f in glob.glob(os.path.join('etc', '*'))]), @@ -18,13 +18,14 @@ ] entry_points = { - "console_scripts": "tparser = tempest_parser.tparser:main" + "console_scripts": + "tparser = tempest_parser.tparser:tempest_cli_parser_main" } setup( name="TempestParser", - version="0.1.2", + version="0.2", author="Alex Savatieiev", author_email="a.savex@gmail.com", classifiers=[ diff --git a/tempest_parser/etc/tempest-parser.conf b/tempest_parser/etc/tempest-parser.conf index 6d1e98c..be2b05d 100644 --- a/tempest_parser/etc/tempest-parser.conf +++ b/tempest_parser/etc/tempest-parser.conf @@ -1,2 +1,3 @@ [ParserConfig] -default_test_list=res/all_tests_master_ad37b61.list \ No newline at end of file +default_test_list=res/all_tests_master_ad37b61.list +default_detailed=false \ No newline at end of file diff --git a/tempest_parser/reports/csv_reporter.py b/tempest_parser/reports/csv_reporter.py index 7c7a389..b9c7cbc 100644 --- a/tempest_parser/reports/csv_reporter.py +++ b/tempest_parser/reports/csv_reporter.py @@ -14,7 +14,7 @@ def __init__(self, test_manager): self._total_executions = sorted(self._tests["executions"].keys()) return - def generate_to_file(self, filename): + def generate_to_file(self, filename, detailed=False): # clear file content if any try: remove_file(filename) @@ -40,8 +40,11 @@ def generate_to_file(self, filename): _date_prepared = _date_prepared.replace('/', '\n') _date_prepared = _date_prepared.replace(' ', '\n') csv_header += '"' + _date_prepared + '",' - csv_header += '"' + os.path.basename(_execution) + '",' - _result_columns += 2 + if detailed: + csv_header += '"' + os.path.basename(_execution) + '",' + _result_columns += 2 + else: + _result_columns += 1 append_line_to_file(filename, csv_header) _tests_counter = 0 @@ -61,7 +64,11 @@ def generate_to_file(self, filename): # iterate tests for _test in self._tests['tests'][class_name]: _tests_counter += 1 - _test_line = str(_tests_counter) + ',' + _test['test_name'] + _test['test_options'] + ',' + _test_line = str(_tests_counter) + \ + ',' + \ + _test['test_name'] + \ + _test['test_options'] + \ + ',' # iterate results _results = "" @@ -75,23 +82,35 @@ def generate_to_file(self, filename): for _execution in self._total_executions: if _execution != 'required': if _execution in _test['results']: - _results += _test['results'][_execution]['result'] + ',' - # new template has no 'time' mark, just comment it out - # _results += _test['results'][_execution]['time'] + ',' + _results += _test['results'][_execution][ + 'result'] + ',' + if detailed: + # new template has no 'time' mark, + # just comment it out + # _results += _ + # test['results'][_execution]['time'] + ',' - # check if there is a fail - _tmp_result = _test['results'][_execution]['result'] - if _tmp_result == 'FAIL': - _trace = copy(_test['results'][_execution]['trace']) - _trace = _trace.replace('"', '\'') - _results += '\"' + _test['results'][_execution]['message'] + '\x0a' \ - + _trace + '\"' + ',' - elif _tmp_result == 'SKIP': - _message = copy(_test['results'][_execution]['message']).replace("\'", '\'') - _results += '\"' + _message + '\"' + ',' + # check if there is a fail + _tmp_result = _test['results'][_execution][ + 'result'] + if _tmp_result == 'FAIL': + _trace = copy( + _test['results'][_execution]['trace']) + _trace = _trace.replace('"', '\'') + _results += \ + '\"' + _test['results'][_execution][ + 'message'] + '\x0a' + _trace + \ + '\"' + ',' + elif _tmp_result == 'SKIP': + _message = \ + copy(_test['results'][_execution] + ['message']).replace("\'", '\'') + _results += '\"' + _message + '\"' + ',' + else: + _results += ',' + else: + if detailed: + _results += ',' + ',' else: _results += ',' - else: - _results += ',' + ',' - # _results += ',' append_line_to_file(filename, _test_line + _results) diff --git a/tempest_parser/reports/reporter.py b/tempest_parser/reports/reporter.py index 5f74433..38d7e0d 100644 --- a/tempest_parser/reports/reporter.py +++ b/tempest_parser/reports/reporter.py @@ -32,10 +32,11 @@ class _TMPLBase(_Base): def tmpl(self): pass - def __call__(self, results): + def __call__(self, results, detailed=False): data = self.common_data() data.update({ "executions": {}, + "detailed": detailed, "tests": results['tests'] }) @@ -108,8 +109,8 @@ def __init__(self, report, target): self.report = report self.target = target - def __call__(self, payload): - payload = self.report(payload) + def __call__(self, payload, detailed=False): + payload = self.report(payload, detailed) if isinstance(self.target, six.string_types): self._wrapped_dump(payload) diff --git a/tempest_parser/templates/tempest_trending_report.html b/tempest_parser/templates/tempest_trending_report.html index d5670e6..da485a6 100644 --- a/tempest_parser/templates/tempest_trending_report.html +++ b/tempest_parser/templates/tempest_trending_report.html @@ -187,9 +187,11 @@
{{ totals[execution][STATUS_SKIP] }}
{{ totals[execution][STATUS_NA] }}
+ {% if detailed %} Notes + {% endif %} {%- endfor -%} @@ -198,7 +200,9 @@ Required vs Added {% for execution in executions if execution != 'required' %} {{ executions[execution]['date'] }} + {% if detailed %} {{ executions[execution]['filename'] }} + {% endif %} {%- endfor -%} {% set counter = 1 %} @@ -224,7 +228,9 @@ {% for execution in executions if execution != 'required' %} {% if test['results'].has_key(execution) %} {{ test['results'][execution]['result'] }} + {% if detailed %} {{ test['results'][execution]['message'] }}
{{ test['results'][execution]['trace'] }} + {% endif %} {% else %} diff --git a/tempest_parser/tparser.py b/tempest_parser/tparser.py index 62598b4..2652b69 100644 --- a/tempest_parser/tparser.py +++ b/tempest_parser/tparser.py @@ -71,6 +71,14 @@ def tempest_cli_parser_main(): help="file with tempest results (CSV/LOG/XML/JSON) or folder full of these files" ) + parser.add_argument( + "-d", + "--detailed", + action="store_true", + help="Include messages column with tracebacks and other messages. " + "Default comes from config" + ) + parser.add_argument( "-i", "--include-required", @@ -103,6 +111,13 @@ def tempest_cli_parser_main(): _config_file_path = args.config_file config = ParserConfigFile(_config_file_path) + # use config to set value for 'detailed' option + _config_detailed_default = config.get_detailed_column_default_value() + _args_detailed = args.detailed + + do_detailed = _args_detailed if _args_detailed \ + else _config_detailed_default + # Check for supplied folder/file to be exists if not os.path.exists(args.filepath): print("Error: Supplied path/file not exists, '{}'".format(args.filepath)) @@ -148,12 +163,12 @@ def tempest_cli_parser_main(): ) # call-n-render report print("Generating HTML Trending report...") - trending_report(tests_manager.get_tests_list()) + trending_report(tests_manager.get_tests_list(), detailed=do_detailed) if args.csv_file is not None: print("Generating CSV report...") csv_reporter = CSVReporter(tests_manager) - csv_reporter.generate_to_file(args.csv_file) + csv_reporter.generate_to_file(args.csv_file, detailed=do_detailed) if __name__ == '__main__': diff --git a/tempest_parser/utils/config.py b/tempest_parser/utils/config.py index dea17d6..03b57ff 100644 --- a/tempest_parser/utils/config.py +++ b/tempest_parser/utils/config.py @@ -7,6 +7,9 @@ class ParserConfigFile: + _truth = ['true', '1', 't', 'y', 'yes', 'yeah', 'yup', + 'certainly', 'uh-huh'] + def __init__(self, filepath): self.config_file_path = filepath @@ -24,3 +27,12 @@ def get_all_tests_list_filepath(self): return os.path.join(pkg_dir, _path) else: return _path + + def get_detailed_column_default_value(self): + # value + _value = self.config.get(self.section_name, 'default_detailed') + # parse if + if _value.lower() in self._truth: + return True + else: + return False