feat(uti): Add iterative data
[csit.git] / resources / tools / dash / app / pal / report / graphs.py
1 # Copyright (c) 2022 Cisco and/or its affiliates.
2 # Licensed under the Apache License, Version 2.0 (the "License");
3 # you may not use this file except in compliance with the License.
4 # You may obtain a copy of the License at:
5 #
6 #     http://www.apache.org/licenses/LICENSE-2.0
7 #
8 # Unless required by applicable law or agreed to in writing, software
9 # distributed under the License is distributed on an "AS IS" BASIS,
10 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 # See the License for the specific language governing permissions and
12 # limitations under the License.
13
14 """
15 """
16
17 import plotly.graph_objects as go
18 import pandas as pd
19
20 import hdrh.histogram
21 import hdrh.codec
22
23
24 _COLORS = (
25     u"#1A1110", u"#DA2647", u"#214FC6", u"#01786F", u"#BD8260", u"#FFD12A",
26     u"#A6E7FF", u"#738276", u"#C95A49", u"#FC5A8D", u"#CEC8EF", u"#391285",
27     u"#6F2DA8", u"#FF878D", u"#45A27D", u"#FFD0B9", u"#FD5240", u"#DB91EF",
28     u"#44D7A8", u"#4F86F7", u"#84DE02", u"#FFCFF1", u"#614051"
29 )
30 _VALUE = {
31     "mrr": "result_receive_rate_rate_avg",
32     "ndr": "result_ndr_lower_rate_value",
33     "pdr": "result_pdr_lower_rate_value",
34     "pdr-lat": "result_latency_forward_pdr_50_avg"
35 }
36 _UNIT = {
37     "mrr": "result_receive_rate_rate_unit",
38     "ndr": "result_ndr_lower_rate_unit",
39     "pdr": "result_pdr_lower_rate_unit",
40     "pdr-lat": "result_latency_forward_pdr_50_unit"
41 }
42 _LAT_HDRH = (  # Do not change the order
43     "result_latency_forward_pdr_0_hdrh",
44     "result_latency_reverse_pdr_0_hdrh",
45     "result_latency_forward_pdr_10_hdrh",
46     "result_latency_reverse_pdr_10_hdrh",
47     "result_latency_forward_pdr_50_hdrh",
48     "result_latency_reverse_pdr_50_hdrh",
49     "result_latency_forward_pdr_90_hdrh",
50     "result_latency_reverse_pdr_90_hdrh",
51 )
52 # This value depends on latency stream rate (9001 pps) and duration (5s).
53 # Keep it slightly higher to ensure rounding errors to not remove tick mark.
54 PERCENTILE_MAX = 99.999501
55
56 _GRAPH_LAT_HDRH_DESC = {
57     u"result_latency_forward_pdr_0_hdrh": u"No-load.",
58     u"result_latency_reverse_pdr_0_hdrh": u"No-load.",
59     u"result_latency_forward_pdr_10_hdrh": u"Low-load, 10% PDR.",
60     u"result_latency_reverse_pdr_10_hdrh": u"Low-load, 10% PDR.",
61     u"result_latency_forward_pdr_50_hdrh": u"Mid-load, 50% PDR.",
62     u"result_latency_reverse_pdr_50_hdrh": u"Mid-load, 50% PDR.",
63     u"result_latency_forward_pdr_90_hdrh": u"High-load, 90% PDR.",
64     u"result_latency_reverse_pdr_90_hdrh": u"High-load, 90% PDR."
65 }
66
67
68 def select_iterative_data(data: pd.DataFrame, itm:dict) -> pd.DataFrame:
69     """
70     """
71
72     phy = itm["phy"].split("-")
73     if len(phy) == 4:
74         topo, arch, nic, drv = phy
75         if drv == "dpdk":
76             drv = ""
77         else:
78             drv += "-"
79             drv = drv.replace("_", "-")
80     else:
81         return None
82
83     core = str() if itm["dut"] == "trex" else f"{itm['core']}"
84     ttype = "ndrpdr" if itm["testtype"] in ("ndr", "pdr") else itm["testtype"]
85     dut = "none" if itm["dut"] == "trex" else itm["dut"].upper()
86
87     df = data.loc[(
88         (data["dut_type"] == dut) &
89         (data["test_type"] == ttype) &
90         (data["passed"] == True)
91     )]
92     df = df[df.job.str.endswith(f"{topo}-{arch}")]
93     df = df[df.test_id.str.contains(
94         f"^.*[.|-]{nic}.*{itm['framesize']}-{core}-{drv}{itm['test']}-{ttype}$",
95         regex=True
96     )].sort_values(by="start_time", ignore_index=True)
97
98     return df
99
100
101 def graph_iterative(data: pd.DataFrame, sel:dict, layout: dict) -> tuple:
102     """
103     """
104
105     fig_tput = go.Figure()
106     fig_tsa = go.Figure()
107
108     return fig_tput, fig_tsa
109
110
111 def table_comparison(data: pd.DataFrame, sel:dict) -> pd.DataFrame:
112     """
113     """
114     table = pd.DataFrame(
115     {
116         "Test Case": [
117             "64b-2t1c-avf-eth-l2xcbase-eth-2memif-1dcr",
118             "64b-2t1c-avf-eth-l2xcbase-eth-2vhostvr1024-1vm-vppl2xc",
119             "64b-2t1c-avf-ethip4udp-ip4base-iacl50sl-10kflows",
120             "78b-2t1c-avf-ethip6-ip6scale2m-rnd "],
121         "2106.0-8": [
122             "14.45 +- 0.08",
123             "9.63 +- 0.05",
124             "9.7 +- 0.02",
125             "8.95 +- 0.06"],
126         "2110.0-8": [
127             "14.45 +- 0.08",
128             "9.63 +- 0.05",
129             "9.7 +- 0.02",
130             "8.95 +- 0.06"],
131         "2110.0-9": [
132             "14.45 +- 0.08",
133             "9.63 +- 0.05",
134             "9.7 +- 0.02",
135             "8.95 +- 0.06"],
136         "2202.0-9": [
137             "14.45 +- 0.08",
138             "9.63 +- 0.05",
139             "9.7 +- 0.02",
140             "8.95 +- 0.06"],
141         "2110.0-9 vs 2110.0-8": [
142             "-0.23 +-  0.62",
143             "-1.37 +-   1.3",
144             "+0.08 +-   0.2",
145             "-2.16 +-  0.83"],
146         "2202.0-9 vs 2110.0-9": [
147             "+6.95 +-  0.72",
148             "+5.35 +-  1.26",
149             "+4.48 +-  1.48",
150             "+4.09 +-  0.95"]
151     }
152 )
153
154     return table
155
156
157 def graph_hdrh_latency(data: dict, layout: dict) -> go.Figure:
158     """
159     """
160
161     fig = None
162
163     traces = list()
164     for idx, (lat_name, lat_hdrh) in enumerate(data.items()):
165         try:
166             decoded = hdrh.histogram.HdrHistogram.decode(lat_hdrh)
167         except (hdrh.codec.HdrLengthException, TypeError) as err:
168             continue
169         previous_x = 0.0
170         prev_perc = 0.0
171         xaxis = list()
172         yaxis = list()
173         hovertext = list()
174         for item in decoded.get_recorded_iterator():
175             # The real value is "percentile".
176             # For 100%, we cut that down to "x_perc" to avoid
177             # infinity.
178             percentile = item.percentile_level_iterated_to
179             x_perc = min(percentile, PERCENTILE_MAX)
180             xaxis.append(previous_x)
181             yaxis.append(item.value_iterated_to)
182             hovertext.append(
183                 f"<b>{_GRAPH_LAT_HDRH_DESC[lat_name]}</b><br>"
184                 f"Direction: {(u'W-E', u'E-W')[idx % 2]}<br>"
185                 f"Percentile: {prev_perc:.5f}-{percentile:.5f}%<br>"
186                 f"Latency: {item.value_iterated_to}uSec"
187             )
188             next_x = 100.0 / (100.0 - x_perc)
189             xaxis.append(next_x)
190             yaxis.append(item.value_iterated_to)
191             hovertext.append(
192                 f"<b>{_GRAPH_LAT_HDRH_DESC[lat_name]}</b><br>"
193                 f"Direction: {(u'W-E', u'E-W')[idx % 2]}<br>"
194                 f"Percentile: {prev_perc:.5f}-{percentile:.5f}%<br>"
195                 f"Latency: {item.value_iterated_to}uSec"
196             )
197             previous_x = next_x
198             prev_perc = percentile
199
200         traces.append(
201             go.Scatter(
202                 x=xaxis,
203                 y=yaxis,
204                 name=_GRAPH_LAT_HDRH_DESC[lat_name],
205                 mode=u"lines",
206                 legendgroup=_GRAPH_LAT_HDRH_DESC[lat_name],
207                 showlegend=bool(idx % 2),
208                 line=dict(
209                     color=_COLORS[int(idx/2)],
210                     dash=u"solid",
211                     width=1 if idx % 2 else 2
212                 ),
213                 hovertext=hovertext,
214                 hoverinfo=u"text"
215             )
216         )
217     if traces:
218         fig = go.Figure()
219         fig.add_traces(traces)
220         layout_hdrh = layout.get("plot-hdrh-latency", None)
221         if lat_hdrh:
222             fig.update_layout(layout_hdrh)
223
224     return fig