integration: Support of PVP and PVVP integration TCs
[vswitchperf.git] / tools / report / report.py
1 # Copyright 2015-2016 Intel Corporation.
2 #
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
6 #
7 #   http://www.apache.org/licenses/LICENSE-2.0
8 #
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
14
15 """
16 vSwitch Characterization Report Generation.
17
18 Generate reports in format defined by X.
19 """
20
21 import sys
22 import os
23 import jinja2
24 import logging
25
26 from core.results.results_constants import ResultsConstants
27 from conf import settings as S
28 from tools import systeminfo
29
30 _TEMPLATE_FILES = ['report.jinja', 'report_rst.jinja']
31 _ROOT_DIR = os.path.normpath(os.path.dirname(os.path.realpath(__file__)))
32
33
34 def _get_env(result):
35     """
36     Get system configuration.
37
38     :returns: Return a dictionary of the test environment.
39               The following is an example return value:
40                {'kernel': '3.10.0-229.4.2.el7.x86_64',
41                 'os': 'OS Version',
42                 'cpu': ' CPU 2.30GHz',
43                 'platform': '[2 sockets]',
44                 'nic': 'NIC'}
45
46     """
47
48     env = {
49         'os': systeminfo.get_os(),
50         'kernel': systeminfo.get_kernel(),
51         'nics': systeminfo.get_nic(),
52         'cpu': systeminfo.get_cpu(),
53         'cpu_cores': systeminfo.get_cpu_cores(),
54         'memory' : systeminfo.get_memory(),
55         'platform': systeminfo.get_platform(),
56         'vsperf': systeminfo.get_version('vswitchperf'),
57         'traffic_gen': systeminfo.get_version(S.getValue('TRAFFICGEN')),
58         'vswitch': systeminfo.get_version(S.getValue('VSWITCH')),
59     }
60
61     if S.getValue('VSWITCH').lower().count('dpdk'):
62         env.update({'dpdk': systeminfo.get_version('dpdk')})
63
64     if result[ResultsConstants.DEPLOYMENT].count('v'):
65         env.update({'vnf': systeminfo.get_version(S.getValue('VNF')),
66                     'guest_image': S.getValue('GUEST_IMAGE'),
67                     'loopback_app': list(map(systeminfo.get_version, S.getValue('GUEST_LOOPBACK'))),
68                    })
69
70     return env
71
72
73 def generate(input_file, tc_results, tc_stats, test_type='performance'):
74     """Generate actual report.
75
76     Generate a Markdown and RST formatted files using results of tests and some
77     parsed system info.
78
79     :param input_file: Path to CSV results file
80     :param tc_results: A list of dictionaries with detailed test results.
81         Each dictionary represents test results for one of specified packet
82         sizes.
83     :param tc_stats: System statistics collected during testcase execution.
84         These statistics are overall statistics for all specified packet
85         sizes.
86     :test_type: Specifies type of the testcase. Supported values are
87         'performance' and 'integration'.
88
89     :returns: Path to generated report
90     """
91     output_files = [('.'.join([os.path.splitext(input_file)[0], 'md'])),
92                     ('.'.join([os.path.splitext(input_file)[0], 'rst']))]
93     template_loader = jinja2.FileSystemLoader(searchpath=_ROOT_DIR)
94     template_env = jinja2.Environment(loader=template_loader)
95
96     tests = []
97     try:
98         for result in tc_results:
99             test_config = {}
100             if test_type == 'performance':
101                 for tc_conf in S.getValue('PERFORMANCE_TESTS'):
102                     if tc_conf['Name'] == result[ResultsConstants.ID]:
103                         test_config = tc_conf
104                         break
105             elif test_type == 'integration':
106                 for tc_conf in S.getValue('INTEGRATION_TESTS'):
107                     if tc_conf['Name'] == result[ResultsConstants.ID]:
108                         test_config = tc_conf
109                         break
110             else:
111                 logging.error("Unsupported test type '%s'. Test details are not known.", test_type)
112
113             # pass test results, env details and configuration to template
114             tests.append({
115                 'ID': result[ResultsConstants.ID].upper(),
116                 'id': result[ResultsConstants.ID],
117                 'deployment': result[ResultsConstants.DEPLOYMENT],
118                 'conf': test_config,
119                 'result': result,
120                 'env': _get_env(result),
121                 'stats': tc_stats
122             })
123
124             # remove id and deployment from results before rendering
125             # but after _get_env() is called; tests dict has its shallow copy
126             del result[ResultsConstants.ID]
127             del result[ResultsConstants.DEPLOYMENT]
128
129         template_vars = {
130             'tests': tests,
131         }
132         i = 0
133         for output_file in output_files:
134             template = template_env.get_template(_TEMPLATE_FILES[i])
135             output_text = template.render(template_vars) #pylint: disable=no-member
136             with open(output_file, 'w') as file_:
137                 file_.write(output_text)
138                 logging.info('Test report written to "%s"', output_file)
139             i += 1
140
141     except KeyError:
142         logging.info("Report: Ignoring file (Wrongly defined columns): %s",
143                      (input_file))
144         raise
145     return output_files
146
147
148 if __name__ == '__main__':
149     S.load_from_dir('conf')
150     OUT = generate(sys.argv[1], '', '')
151     print('Test report written to "%s"...' % OUT)