Merge "Adding new vFirewall Test cases based on Concurrency, Connections per second...
[yardstick.git] / yardstick / network_services / vnf_generic / vnf / tg_ixload.py
1 #  Copyright (c) 2016-2017 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 from __future__ import absolute_import
16 import csv
17 import glob
18 import logging
19 import os
20 import shutil
21
22 from collections import OrderedDict
23 from subprocess import call
24
25 from yardstick.common.utils import makedirs
26 from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNFTrafficGen
27 from yardstick.network_services.vnf_generic.vnf.sample_vnf import ClientResourceHelper
28 from yardstick.benchmark.scenarios.networking.vnf_generic import find_relative_file
29
30 LOG = logging.getLogger(__name__)
31
32 VNF_PATH = os.path.dirname(os.path.realpath(__file__))
33
34 MOUNT_CMD = """\
35 mount.cifs //{0[ip]}/Results {1.RESULTS_MOUNT} \
36 -o username={0[user]},password={0[password]}\
37 """
38
39 IXLOAD_CONFIG_TEMPLATE = '''\
40 {
41     "ixia_chassis": "%s",
42     "IXIA": {
43         "ports": %s,
44         "card": %s
45     },
46     "remote_server": "%s",
47     "result_dir": "%s",
48     "ixload_cfg": "C:/Results/%s"
49 }'''
50
51 IXLOAD_CMD = "{ixloadpy} {http_ixload} {args}"
52
53
54 class ResourceDataHelper(list):
55
56     def get_aggregates(self):
57         return {
58             "min": min(self),
59             "max": max(self),
60             "avg": sum(self) / len(self),
61         }
62
63
64 class IxLoadResourceHelper(ClientResourceHelper):
65
66     RESULTS_MOUNT = "/mnt/Results"
67
68     KPI_LIST = OrderedDict((
69         ('http_throughput', 'HTTP Total Throughput (Kbps)'),
70         ('simulated_users', 'HTTP Simulated Users'),
71         ('concurrent_connections', 'HTTP Concurrent Connections'),
72         ('connection_rate', 'HTTP Connection Rate'),
73         ('transaction_rate', 'HTTP Transaction Rate'),
74     ))
75
76     def __init__(self, setup_helper):
77         super(IxLoadResourceHelper, self).__init__(setup_helper)
78         self.result = OrderedDict((key, ResourceDataHelper()) for key in self.KPI_LIST)
79         self.resource_file_name = ''
80         self.data = None
81
82     def parse_csv_read(self, reader):
83         for row in reader:
84             try:
85                 new_data = {key_left: int(row[key_right])
86                             for key_left, key_right in self.KPI_LIST.items()}
87             except (TypeError, ValueError):
88                 continue
89             else:
90                 for key, value in new_data.items():
91                     self.result[key].append(value)
92
93     def setup(self):
94         # NOTE: fixup scenario_helper to hanlde ixia
95         self.resource_file_name = \
96             find_relative_file(self.scenario_helper.scenario_cfg['ixia_profile'],
97                                self.scenario_helper.scenario_cfg["task_path"])
98         makedirs(self.RESULTS_MOUNT)
99         cmd = MOUNT_CMD.format(self.vnfd_helper.mgmt_interface, self)
100         LOG.debug(cmd)
101
102         if not os.path.ismount(self.RESULTS_MOUNT):
103             call(cmd, shell=True)
104
105         shutil.rmtree(self.RESULTS_MOUNT, ignore_errors=True)
106         makedirs(self.RESULTS_MOUNT)
107         shutil.copy(self.resource_file_name, self.RESULTS_MOUNT)
108
109     def make_aggregates(self):
110         return {key_right: self.result[key_left].get_aggregates()
111                 for key_left, key_right in self.KPI_LIST.items()}
112
113     def collect_kpi(self):
114         if self.data:
115             self._result.update(self.data)
116         LOG.info("Collect %s KPIs %s", self.RESOURCE_WORD, self._result)
117         return self._result
118
119     def log(self):
120         for key in self.KPI_LIST:
121             LOG.debug(self.result[key])
122
123
124 class IxLoadTrafficGen(SampleVNFTrafficGen):
125
126     def __init__(self, name, vnfd, setup_env_helper_type=None, resource_helper_type=None):
127         if resource_helper_type is None:
128             resource_helper_type = IxLoadResourceHelper
129
130         super(IxLoadTrafficGen, self).__init__(name, vnfd, setup_env_helper_type,
131                                                resource_helper_type)
132         self._result = {}
133
134     def run_traffic(self, traffic_profile):
135         ports = []
136         card = None
137         for interface in self.vnfd_helper.interfaces:
138             vpci_list = interface['virtual-interface']["vpci"].split(":")
139             card = vpci_list[0]
140             ports.append(str(vpci_list[1]))
141
142         for csv_file in glob.iglob(self.ssh_helper.join_bin_path('*.csv')):
143             os.unlink(csv_file)
144
145         ixia_config = self.vnfd_helper.mgmt_interface["tg-config"]
146         ixload_config = IXLOAD_CONFIG_TEMPLATE % (
147             ixia_config["ixchassis"], ports, card,
148             self.vnfd_helper.mgmt_interface["ip"], self.ssh_helper.bin_path,
149             os.path.basename(self.resource_helper.resource_file_name))
150
151         http_ixload_path = os.path.join(VNF_PATH, "../../traffic_profile")
152
153         cmd = IXLOAD_CMD.format(
154             ixloadpy=os.path.join(ixia_config["py_bin_path"], "ixloadpython"),
155             http_ixload=os.path.join(http_ixload_path, "http_ixload.py"),
156             args="'%s'" % ixload_config)
157
158         LOG.debug(cmd)
159         call(cmd, shell=True)
160
161         with open(self.ssh_helper.join_bin_path("ixLoad_HTTP_Client.csv")) as csv_file:
162             lines = csv_file.readlines()[10:]
163         with open(self.ssh_helper.join_bin_path("http_result.csv"), 'wb+') as result_file:
164             result_file.writelines(lines[:-1])
165             result_file.flush()
166             result_file.seek(0)
167             reader = csv.DictReader(result_file)
168             self.resource_helper.parse_csv_read(reader)
169
170         self.resource_helper.log()
171         self.resource_helper.data = self.resource_helper.make_aggregates()
172
173     def terminate(self):
174         call(["pkill", "-9", "http_ixload.py"])
175         super(IxLoadTrafficGen, self).terminate()