aboutsummaryrefslogtreecommitdiffstats
path: root/yardstick
diff options
context:
space:
mode:
Diffstat (limited to 'yardstick')
-rw-r--r--yardstick/benchmark/contexts/heat.py56
-rw-r--r--yardstick/benchmark/contexts/model.py45
-rw-r--r--yardstick/benchmark/core/report.py8
-rw-r--r--yardstick/benchmark/core/task.py24
-rw-r--r--yardstick/benchmark/runners/duration.py6
-rw-r--r--yardstick/benchmark/runners/iteration.py6
-rw-r--r--yardstick/benchmark/scenarios/availability/ha_tools/nova/add_server_to_existing_secgroup.bash26
-rw-r--r--yardstick/benchmark/scenarios/availability/ha_tools/nova/create_instance_from_image.bash26
-rw-r--r--yardstick/benchmark/scenarios/availability/ha_tools/nova/delete_instance.bash24
-rw-r--r--yardstick/benchmark/scenarios/availability/ha_tools/nova/get_server_privateip.bash24
-rw-r--r--yardstick/benchmark/scenarios/availability/ha_tools/nova/remove_server_from_secgroup.bash25
-rw-r--r--yardstick/benchmark/scenarios/availability/operation_conf.yaml11
-rw-r--r--yardstick/benchmark/scenarios/base.py30
-rw-r--r--yardstick/benchmark/scenarios/lib/create_network.py41
-rw-r--r--yardstick/benchmark/scenarios/lib/create_router.py46
-rw-r--r--yardstick/benchmark/scenarios/lib/create_subnet.py60
-rw-r--r--yardstick/benchmark/scenarios/lib/delete_router.py24
-rw-r--r--yardstick/benchmark/scenarios/networking/moongen_testpmd.bash62
-rw-r--r--yardstick/benchmark/scenarios/networking/moongen_testpmd.py378
-rwxr-xr-xyardstick/benchmark/scenarios/networking/netperf.py4
-rw-r--r--yardstick/benchmark/scenarios/networking/pktgen_dpdk.py23
-rw-r--r--yardstick/benchmark/scenarios/networking/pktgen_dpdk_latency_benchmark.bash32
-rw-r--r--yardstick/benchmark/scenarios/networking/testpmd_fwd.bash16
-rw-r--r--yardstick/benchmark/scenarios/networking/vnf_generic.py9
-rw-r--r--yardstick/benchmark/scenarios/storage/fio.py16
-rw-r--r--yardstick/common/ansible_common.py53
-rw-r--r--yardstick/common/constants.py4
-rw-r--r--yardstick/common/exceptions.py26
-rw-r--r--yardstick/common/openstack_utils.py121
-rw-r--r--yardstick/network_services/constants.py2
-rw-r--r--yardstick/network_services/traffic_profile/prox_binsearch.py7
-rw-r--r--yardstick/network_services/vnf_generic/vnf/prox_helpers.py52
-rw-r--r--yardstick/network_services/vnf_generic/vnf/prox_vnf.py4
-rw-r--r--yardstick/network_services/vnf_generic/vnf/sample_vnf.py26
-rw-r--r--yardstick/network_services/vnf_generic/vnf/vnf_ssh_helper.py4
-rw-r--r--yardstick/orchestrator/heat.py22
-rw-r--r--yardstick/service/__init__.py12
-rw-r--r--yardstick/service/environment.py101
-rw-r--r--yardstick/tests/unit/apiserver/resources/v1/__init__.py0
-rw-r--r--yardstick/tests/unit/apiserver/resources/v1/test_testsuites.py35
-rw-r--r--yardstick/tests/unit/benchmark/contexts/test_heat.py109
-rw-r--r--yardstick/tests/unit/benchmark/contexts/test_kubernetes.py36
-rw-r--r--yardstick/tests/unit/benchmark/contexts/test_model.py11
-rw-r--r--yardstick/tests/unit/benchmark/contexts/test_node.py18
-rw-r--r--yardstick/tests/unit/benchmark/core/test_task.py30
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_add_memory_load.py6
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_attach_volume.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_check_numa_info.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_flavor.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_network.py57
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_port.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_router.py57
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_sec_group.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_server.py8
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_subnet.py60
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_create_volume.py8
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_flavor.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_floating_ip.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_image.py6
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_keypair.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_port.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router.py51
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_gateway.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_interface.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_server.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_delete_volume.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_detach_volume.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_get_flavor.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_get_migrate_target_host.py8
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_get_numa_info.py4
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/lib/test_get_server.py6
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/networking/test_iperf3.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/networking/test_moongen_testpmd.py353
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py2
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/storage/test_fio.py16
-rw-r--r--yardstick/tests/unit/benchmark/scenarios/test_base.py30
-rw-r--r--yardstick/tests/unit/common/test_ansible_common.py16
-rw-r--r--yardstick/tests/unit/common/test_openstack_utils.py102
-rw-r--r--yardstick/tests/unit/common/test_packages.py88
-rw-r--r--yardstick/tests/unit/common/test_utils.py38
-rw-r--r--yardstick/tests/unit/orchestrator/test_heat.py14
-rw-r--r--yardstick/tests/unit/service/__init__.py0
-rw-r--r--yardstick/tests/unit/service/test_environment.py49
-rw-r--r--yardstick/tests/unit/test_cmd/commands/test_env.py14
-rw-r--r--yardstick/tests/unit/test_cmd/commands/test_testcase.py2
85 files changed, 2221 insertions, 517 deletions
diff --git a/yardstick/benchmark/contexts/heat.py b/yardstick/benchmark/contexts/heat.py
index 44078892b..0d1dfb86f 100644
--- a/yardstick/benchmark/contexts/heat.py
+++ b/yardstick/benchmark/contexts/heat.py
@@ -134,16 +134,6 @@ class HeatContext(Context):
self.attrs = attrs
- self.key_filename = ''.join(
- [consts.YARDSTICK_ROOT_PATH,
- 'yardstick/resources/files/yardstick_key-',
- self.name])
- # Permissions may have changed since creation; this can be fixed. If we
- # overwrite the file, we lose future access to VMs using this key.
- # As long as the file exists, even if it is unreadable, keep it intact
- if not os.path.exists(self.key_filename):
- SSH.gen_keys(self.key_filename)
-
def check_environment(self):
try:
os.environ['OS_AUTH_URL']
@@ -185,6 +175,9 @@ class HeatContext(Context):
template.add_security_group(self.secgroup_name)
for network in self.networks.values():
+ # Using existing network
+ if network.is_existing():
+ continue
template.add_network(network.stack_name,
network.physical_network,
network.provider,
@@ -308,7 +301,7 @@ class HeatContext(Context):
timeout=self.heat_timeout)
except KeyboardInterrupt:
raise y_exc.StackCreationInterrupt
- except:
+ except Exception:
LOG.exception("stack failed")
# let the other failures happen, we want stack trace
raise
@@ -325,6 +318,16 @@ class HeatContext(Context):
"""deploys template into a stack using cloud"""
LOG.info("Deploying context '%s' START", self.name)
+ self.key_filename = ''.join(
+ [consts.YARDSTICK_ROOT_PATH,
+ 'yardstick/resources/files/yardstick_key-',
+ self.name])
+ # Permissions may have changed since creation; this can be fixed. If we
+ # overwrite the file, we lose future access to VMs using this key.
+ # As long as the file exists, even if it is unreadable, keep it intact
+ if not os.path.exists(self.key_filename):
+ SSH.gen_keys(self.key_filename)
+
heat_template = HeatTemplate(self.name, self.template_file,
self.heat_parameters)
@@ -354,18 +357,35 @@ class HeatContext(Context):
LOG.info("Deploying context '%s' DONE", self.name)
+ @staticmethod
+ def _port_net_is_existing(port_info):
+ net_flags = port_info.get('net_flags', {})
+ return net_flags.get(consts.IS_EXISTING)
+
+ @staticmethod
+ def _port_net_is_public(port_info):
+ net_flags = port_info.get('net_flags', {})
+ return net_flags.get(consts.IS_PUBLIC)
+
def add_server_port(self, server):
- # use private ip from first port in first network
- try:
- private_port = next(iter(server.ports.values()))[0]
- except IndexError:
- LOG.exception("Unable to find first private port in %s", server.ports)
- raise
- server.private_ip = self.stack.outputs[private_port["stack_name"]]
+ server_ports = server.ports.values()
+ for server_port in server_ports:
+ port_info = server_port[0]
+ port_ip = self.stack.outputs[port_info["stack_name"]]
+ port_net_is_existing = self._port_net_is_existing(port_info)
+ port_net_is_public = self._port_net_is_public(port_info)
+ if port_net_is_existing and (port_net_is_public or
+ len(server_ports) == 1):
+ server.public_ip = port_ip
+ if not server.private_ip or len(server_ports) == 1:
+ server.private_ip = port_ip
+
server.interfaces = {}
for network_name, ports in server.ports.items():
for port in ports:
# port['port'] is either port name from mapping or default network_name
+ if self._port_net_is_existing(port):
+ continue
server.interfaces[port['port']] = self.make_interface_dict(network_name,
port['port'],
port['stack_name'],
diff --git a/yardstick/benchmark/contexts/model.py b/yardstick/benchmark/contexts/model.py
index ae56066ee..a55c11f79 100644
--- a/yardstick/benchmark/contexts/model.py
+++ b/yardstick/benchmark/contexts/model.py
@@ -18,6 +18,8 @@ import logging
from collections import Mapping
from six.moves import range
+from yardstick.common import constants as consts
+
LOG = logging.getLogger(__name__)
@@ -132,11 +134,28 @@ class Network(Object):
if self.gateway_ip is None:
self.gateway_ip = "null"
- if "external_network" in attrs:
- self.router = Router("router", self.name,
- context, attrs["external_network"])
-
- Network.list.append(self)
+ self.net_flags = attrs.get('net_flags', {})
+ if self.is_existing():
+ self.subnet = attrs.get('subnet')
+ if not self.subnet:
+ raise Warning('No subnet set in existing netwrok!')
+ else:
+ if "external_network" in attrs:
+ self.router = Router("router", self.name,
+ context, attrs["external_network"])
+ Network.list.append(self)
+
+ def is_existing(self):
+ net_is_existing = self.net_flags.get(consts.IS_EXISTING)
+ if net_is_existing and not isinstance(net_is_existing, bool):
+ raise SyntaxError('Network flags should be bool type!')
+ return net_is_existing
+
+ def is_public(self):
+ net_is_public = self.net_flags.get(consts.IS_PUBLIC)
+ if net_is_public and not isinstance(net_is_public, bool):
+ raise SyntaxError('Network flags should be bool type!')
+ return net_is_public
def has_route_to(self, network_name):
"""determines if this network has a route to the named network"""
@@ -302,10 +321,13 @@ class Server(Object): # pragma: no cover
# otherwise add a port for every network with port name as network name
else:
ports = [network.name]
+ net_flags = network.net_flags
for port in ports:
port_name = "{0}-{1}-port".format(server_name, port)
- self.ports.setdefault(network.name, []).append(
- {"stack_name": port_name, "port": port})
+ port_info = {"stack_name": port_name, "port": port}
+ if net_flags:
+ port_info['net_flags'] = net_flags
+ self.ports.setdefault(network.name, []).append(port_info)
# we can't use secgroups if port_security_enabled is False
if network.port_security_enabled is False:
sec_group_id = None
@@ -314,11 +336,14 @@ class Server(Object): # pragma: no cover
sec_group_id = self.secgroup_name
# don't refactor to pass in network object, that causes JSON
# circular ref encode errors
- template.add_port(port_name, network.stack_name, network.subnet_stack_name,
- network.vnic_type, sec_group_id=sec_group_id,
+ template.add_port(port_name, network,
+ sec_group_id=sec_group_id,
provider=network.provider,
allowed_address_pairs=network.allowed_address_pairs)
- port_name_list.append(port_name)
+ if network.is_public():
+ port_name_list.insert(0, port_name)
+ else:
+ port_name_list.append(port_name)
if self.floating_ip:
external_network = self.floating_ip["external_network"]
diff --git a/yardstick/benchmark/core/report.py b/yardstick/benchmark/core/report.py
index 997a125e7..199602444 100644
--- a/yardstick/benchmark/core/report.py
+++ b/yardstick/benchmark/core/report.py
@@ -45,7 +45,7 @@ class Report(object):
self.task_id = ""
def _validate(self, yaml_name, task_id):
- if re.match("^[a-z0-9_-]+$", yaml_name):
+ if re.match(r"^[\w-]+$", yaml_name):
self.yaml_name = yaml_name
else:
raise ValueError("invalid yaml_name", yaml_name)
@@ -102,10 +102,12 @@ class Report(object):
task_time = str(task_time, 'utf8')
key = str(key, 'utf8')
task_time = task_time[11:]
- head, sep, tail = task_time.partition('.')
+ head, _, tail = task_time.partition('.')
task_time = head + "." + tail[:6]
self.Timestamp.append(task_time)
- if isinstance(task[key], float) is True:
+ if task[key] is None:
+ values.append('')
+ elif isinstance(task[key], (int, float)) is True:
values.append(task[key])
else:
values.append(ast.literal_eval(task[key]))
diff --git a/yardstick/benchmark/core/task.py b/yardstick/benchmark/core/task.py
index 7f6309a7e..955b8cae2 100644
--- a/yardstick/benchmark/core/task.py
+++ b/yardstick/benchmark/core/task.py
@@ -149,7 +149,7 @@ class Task(object): # pragma: no cover
total_end_time - total_start_time)
LOG.info('To generate report, execute command "yardstick report '
- 'generate %(task_id)s <yaml_name>s"', self.task_id)
+ 'generate %s <YAML_NAME>"', self.task_id)
LOG.info("Task ALL DONE, exiting")
return result
@@ -344,7 +344,8 @@ class Task(object): # pragma: no cover
# TODO support get multi hosts/vms info
context_cfg = {}
- server_name = scenario_cfg.get('options', {}).get('server_name', {})
+ options = scenario_cfg.get('options') or {}
+ server_name = options.get('server_name') or {}
def config_context_target(cfg):
target = cfg['target']
@@ -613,21 +614,32 @@ class TaskParser(object): # pragma: no cover
vnf__0: vnf_0.yardstick
"""
def qualified_name(name):
- node_name, context_name = name.split('.')
+ try:
+ # for openstack
+ node_name, context_name = name.split('.')
+ sep = '.'
+ except ValueError:
+ # for kubernetes, some kubernetes resources don't support
+ # name format like 'xxx.xxx', so we use '-' instead
+ # need unified later
+ node_name, context_name = name.split('-')
+ sep = '-'
+
try:
ctx = next((context for context in contexts
- if context.assigned_name == context_name))
+ if context.assigned_name == context_name))
except StopIteration:
raise y_exc.ScenarioConfigContextNameNotFound(
context_name=context_name)
- return '{}.{}'.format(node_name, ctx.name)
+ return '{}{}{}'.format(node_name, sep, ctx.name)
if 'host' in scenario:
scenario['host'] = qualified_name(scenario['host'])
if 'target' in scenario:
scenario['target'] = qualified_name(scenario['target'])
- server_name = scenario.get('options', {}).get('server_name', {})
+ options = scenario.get('options') or {}
+ server_name = options.get('server_name') or {}
if 'host' in server_name:
server_name['host'] = qualified_name(server_name['host'])
if 'target' in server_name:
diff --git a/yardstick/benchmark/runners/duration.py b/yardstick/benchmark/runners/duration.py
index fbf72a74c..60b0348c3 100644
--- a/yardstick/benchmark/runners/duration.py
+++ b/yardstick/benchmark/runners/duration.py
@@ -66,6 +66,8 @@ def _worker_process(queue, cls, method_name, scenario_cfg,
data = {}
errors = ""
+ benchmark.pre_run_wait_time(interval)
+
try:
result = method(data)
except AssertionError as assertion:
@@ -77,7 +79,7 @@ def _worker_process(queue, cls, method_name, scenario_cfg,
errors = assertion.args
# catch all exceptions because with multiprocessing we can have un-picklable exception
# problems https://bugs.python.org/issue9400
- except Exception:
+ except Exception: # pylint: disable=broad-except
errors = traceback.format_exc()
LOG.exception("")
else:
@@ -86,7 +88,7 @@ def _worker_process(queue, cls, method_name, scenario_cfg,
# if we do timeout we don't care about dropping individual KPIs
output_queue.put(result, True, QUEUE_PUT_TIMEOUT)
- time.sleep(interval)
+ benchmark.post_run_wait_time(interval)
benchmark_output = {
'timestamp': time.time(),
diff --git a/yardstick/benchmark/runners/iteration.py b/yardstick/benchmark/runners/iteration.py
index cb0424377..20d6da054 100644
--- a/yardstick/benchmark/runners/iteration.py
+++ b/yardstick/benchmark/runners/iteration.py
@@ -71,6 +71,8 @@ def _worker_process(queue, cls, method_name, scenario_cfg,
data = {}
errors = ""
+ benchmark.pre_run_wait_time(interval)
+
try:
result = method(data)
except AssertionError as assertion:
@@ -90,7 +92,7 @@ def _worker_process(queue, cls, method_name, scenario_cfg,
scenario_cfg['options']['rate'] -= delta
sequence = 1
continue
- except Exception:
+ except Exception: # pylint: disable=broad-except
errors = traceback.format_exc()
LOG.exception("")
else:
@@ -99,7 +101,7 @@ def _worker_process(queue, cls, method_name, scenario_cfg,
# if we do timeout we don't care about dropping individual KPIs
output_queue.put(result, True, QUEUE_PUT_TIMEOUT)
- time.sleep(interval)
+ benchmark.post_run_wait_time(interval)
benchmark_output = {
'timestamp': time.time(),
diff --git a/yardstick/benchmark/scenarios/availability/ha_tools/nova/add_server_to_existing_secgroup.bash b/yardstick/benchmark/scenarios/availability/ha_tools/nova/add_server_to_existing_secgroup.bash
new file mode 100644
index 000000000..3a50626f5
--- /dev/null
+++ b/yardstick/benchmark/scenarios/availability/ha_tools/nova/add_server_to_existing_secgroup.bash
@@ -0,0 +1,26 @@
+#!/bin/bash
+
+##############################################################################
+# Copyright (c) 2018 Intracom Telecom and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+# add server to existing security group
+# parameters: $1 - server name, $2 - security group name
+
+set -e
+
+if [ $OS_INSECURE ] && [ "$(echo $OS_INSECURE | tr '[:upper:]' '[:lower:]')" = "true" ]; then
+ SECURE="--insecure"
+else
+ SECURE=""
+fi
+
+SECGROUPNAME="$(openstack ${SECURE} security group list -f value -c Name | grep $2)"
+
+openstack ${SECURE} server add security group $1 ${SECGROUPNAME}
+
diff --git a/yardstick/benchmark/scenarios/availability/ha_tools/nova/create_instance_from_image.bash b/yardstick/benchmark/scenarios/availability/ha_tools/nova/create_instance_from_image.bash
new file mode 100644
index 000000000..5e0b1ccf1
--- /dev/null
+++ b/yardstick/benchmark/scenarios/availability/ha_tools/nova/create_instance_from_image.bash
@@ -0,0 +1,26 @@
+#!/bin/bash
+
+##############################################################################
+# Copyright (c) 2018 Intracom Telecom and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+# create nova server
+# parameters: $1 - server name, $2 - image name, $3 - flavor name, $4 - network name
+
+set -e
+
+if [ $OS_INSECURE ] && [ "$(echo $OS_INSECURE | tr '[:upper:]' '[:lower:]')" = "true" ]; then
+ SECURE="--insecure"
+else
+ SECURE=""
+fi
+
+NETNAME="$(openstack ${SECURE} network list -f value -c Name | grep $4)"
+
+openstack ${SECURE} server create $1 --image $2 --flavor $3 --network ${NETNAME}
+
diff --git a/yardstick/benchmark/scenarios/availability/ha_tools/nova/delete_instance.bash b/yardstick/benchmark/scenarios/availability/ha_tools/nova/delete_instance.bash
new file mode 100644
index 000000000..008e7f5ff
--- /dev/null
+++ b/yardstick/benchmark/scenarios/availability/ha_tools/nova/delete_instance.bash
@@ -0,0 +1,24 @@
+#!/bin/bash
+
+##############################################################################
+# Copyright (c) 2018 Intracom Telecom and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+# delete nova server
+# parameters: $1 - server name
+
+set -e
+
+if [ $OS_INSECURE ] && [ "$(echo $OS_INSECURE | tr '[:upper:]' '[:lower:]')" = "true" ]; then
+ SECURE="--insecure"
+else
+ SECURE=""
+fi
+
+openstack ${SECURE} server delete $1
+
diff --git a/yardstick/benchmark/scenarios/availability/ha_tools/nova/get_server_privateip.bash b/yardstick/benchmark/scenarios/availability/ha_tools/nova/get_server_privateip.bash
new file mode 100644
index 000000000..7f2bad540
--- /dev/null
+++ b/yardstick/benchmark/scenarios/availability/ha_tools/nova/get_server_privateip.bash
@@ -0,0 +1,24 @@
+#!/bin/bash
+
+##############################################################################
+# Copyright (c) 2018 Intracom Telecom and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+# get private ip of a server
+# parameter: $1 - server name
+
+set -e
+
+if [ $OS_INSECURE ] && [ "$(echo $OS_INSECURE | tr '[:upper:]' '[:lower:]')" = "true" ]; then
+ SECURE="--insecure"
+else
+ SECURE=""
+fi
+
+openstack ${SECURE} server list -f value -c Name -c Networks | grep $1 | awk '{print $2}' | sed -r 's/.*=([0-9\.\:]+)[;,]*/\1/'
+
diff --git a/yardstick/benchmark/scenarios/availability/ha_tools/nova/remove_server_from_secgroup.bash b/yardstick/benchmark/scenarios/availability/ha_tools/nova/remove_server_from_secgroup.bash
new file mode 100644
index 000000000..61d0a2b49
--- /dev/null
+++ b/yardstick/benchmark/scenarios/availability/ha_tools/nova/remove_server_from_secgroup.bash
@@ -0,0 +1,25 @@
+#!/bin/bash
+
+##############################################################################
+# Copyright (c) 2018 Intracom Telecom and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+# remove server from existing security group
+# parameters: $1 - server name, $2 - security group name
+
+set -e
+
+if [ $OS_INSECURE ] && [ "$(echo $OS_INSECURE | tr '[:upper:]' '[:lower:]')" = "true" ]; then
+ SECURE="--insecure"
+else
+ SECURE=""
+fi
+
+SECGROUPNAME="$(openstack ${SECURE} security group list -f value -c Name | grep $2)"
+
+openstack ${SECURE} server remove security group $1 ${SECGROUPNAME}
diff --git a/yardstick/benchmark/scenarios/availability/operation_conf.yaml b/yardstick/benchmark/scenarios/availability/operation_conf.yaml
index dc5169196..5f3f6c91e 100644
--- a/yardstick/benchmark/scenarios/availability/operation_conf.yaml
+++ b/yardstick/benchmark/scenarios/availability/operation_conf.yaml
@@ -35,3 +35,14 @@ get-vip-host:
action_script: ha_tools/pacemaker/get_vip_host.bash
rollback_script: ha_tools/pacemaker/get_resource_status.bash
+start-service:
+ action_script: ha_tools/start_service.bash
+ rollback_script: ha_tools/check_process_python.bash
+
+add-server-to-secgroup:
+ action_script: ha_tools/nova/add_server_to_existing_secgroup.bash
+ rollback_script: ha_tools/nova/remove_server_from_secgroup.bash
+
+get-privateip:
+ action_script: ha_tools/nova/get_server_privateip.bash
+ rollback_script: ha_tools/nova/list_servers.bash
diff --git a/yardstick/benchmark/scenarios/base.py b/yardstick/benchmark/scenarios/base.py
index 10a728828..58a02805c 100644
--- a/yardstick/benchmark/scenarios/base.py
+++ b/yardstick/benchmark/scenarios/base.py
@@ -13,9 +13,10 @@
# License for the specific language governing permissions and limitations
# under the License.
-# yardstick comment: this is a modified copy of
-# rally/rally/benchmark/scenarios/base.py
+import abc
+import time
+import six
from stevedore import extension
import yardstick.common.utils as utils
@@ -37,20 +38,29 @@ def _iter_scenario_classes(scenario_type=None):
yield scenario
+@six.add_metaclass(abc.ABCMeta)
class Scenario(object):
def setup(self):
- """ default impl for scenario setup """
+ """Default setup implementation for Scenario classes"""
pass
+ @abc.abstractmethod
def run(self, *args):
- """ catcher for not implemented run methods in subclasses """
- raise RuntimeError("run method not implemented")
+ """Entry point for scenario classes, called from runner worker"""
def teardown(self):
- """ default impl for scenario teardown """
+ """Default teardown implementation for Scenario classes"""
pass
+ def pre_run_wait_time(self, time_seconds):
+ """Time waited before executing the run method"""
+ pass
+
+ def post_run_wait_time(self, time_seconds):
+ """Time waited after executing the run method"""
+ time.sleep(time_seconds)
+
@staticmethod
def get_types():
"""return a list of known runner type (class) names"""
@@ -88,10 +98,14 @@ class Scenario(object):
"""
return cls.__doc__.splitlines()[0] if cls.__doc__ else str(None)
- def _push_to_outputs(self, keys, values):
+ @staticmethod
+ def _push_to_outputs(keys, values):
+ """Return a dictionary given the keys and the values"""
return dict(zip(keys, values))
- def _change_obj_to_dict(self, obj):
+ @staticmethod
+ def _change_obj_to_dict(obj):
+ """Return a dictionary from the __dict__ attribute of an object"""
dic = {}
for k, v in vars(obj).items():
try:
diff --git a/yardstick/benchmark/scenarios/lib/create_network.py b/yardstick/benchmark/scenarios/lib/create_network.py
index cffff132a..734820519 100644
--- a/yardstick/benchmark/scenarios/lib/create_network.py
+++ b/yardstick/benchmark/scenarios/lib/create_network.py
@@ -7,13 +7,12 @@
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
-from __future__ import print_function
-from __future__ import absolute_import
-
import logging
from yardstick.benchmark.scenarios import base
-import yardstick.common.openstack_utils as op_utils
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
+
LOG = logging.getLogger(__name__)
@@ -28,9 +27,14 @@ class CreateNetwork(base.Scenario):
self.context_cfg = context_cfg
self.options = self.scenario_cfg['options']
- self.openstack = self.options.get("openstack_paras", None)
+ self.network_name = self.options["network_name"]
+ self.shared = self.options.get("shared", False)
+ self.admin_state_up = self.options.get("admin_state_up", True)
+ self.external = self.options.get("external", False)
+ self.provider = self.options.get("provider")
+ self.project_id = self.options.get("project_id")
- self.neutron_client = op_utils.get_neutron_client()
+ self.shade_client = openstack_utils.get_shade_client()
self.setup_done = False
@@ -45,20 +49,17 @@ class CreateNetwork(base.Scenario):
if not self.setup_done:
self.setup()
- openstack_paras = {'network': self.openstack}
- network_id = op_utils.create_neutron_net(self.neutron_client,
- openstack_paras)
- if network_id:
- result.update({"network_create": 1})
- LOG.info("Create network successful!")
- else:
+ network_id = openstack_utils.create_neutron_net(
+ self.shade_client, self.network_name, shared=self.shared,
+ admin_state_up=self.admin_state_up, external=self.external,
+ provider=self.provider, project_id=self.project_id)
+ if not network_id:
result.update({"network_create": 0})
LOG.error("Create network failed!")
+ raise exceptions.ScenarioCreateNetworkError
- try:
- keys = self.scenario_cfg.get('output', '').split()
- except KeyError:
- pass
- else:
- values = [network_id]
- return self._push_to_outputs(keys, values)
+ result.update({"network_create": 1})
+ LOG.info("Create network successful!")
+ keys = self.scenario_cfg.get('output', '').split()
+ values = [network_id]
+ return self._push_to_outputs(keys, values)
diff --git a/yardstick/benchmark/scenarios/lib/create_router.py b/yardstick/benchmark/scenarios/lib/create_router.py
index 9aa57ebb2..34252f603 100644
--- a/yardstick/benchmark/scenarios/lib/create_router.py
+++ b/yardstick/benchmark/scenarios/lib/create_router.py
@@ -7,13 +7,11 @@
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
-from __future__ import print_function
-from __future__ import absolute_import
-
import logging
from yardstick.benchmark.scenarios import base
-import yardstick.common.openstack_utils as op_utils
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
LOG = logging.getLogger(__name__)
@@ -28,9 +26,14 @@ class CreateRouter(base.Scenario):
self.context_cfg = context_cfg
self.options = self.scenario_cfg['options']
- self.openstack = self.options.get("openstack_paras", None)
+ self.name = self.options.get('name')
+ self.admin_state_up = self.options.get('admin_state_up', True)
+ self.ext_gateway_net_id = self.options.get('ext_gateway_net_id')
+ self.enable_snat = self.options.get('enable_snat')
+ self.ext_fixed_ips = self.options.get('ext_fixed_ips')
+ self.project_id = self.options.get('project_id')
- self.neutron_client = op_utils.get_neutron_client()
+ self.shade_client = openstack_utils.get_shade_client()
self.setup_done = False
@@ -45,22 +48,19 @@ class CreateRouter(base.Scenario):
if not self.setup_done:
self.setup()
- openstack_paras = {'router': self.openstack}
- router_id = op_utils.create_neutron_router(self.neutron_client,
- openstack_paras)
- if router_id:
- result.update({"network_create": 1})
- LOG.info("Create router successful!")
- else:
- result.update({"network_create": 0})
+ router_id = openstack_utils.create_neutron_router(
+ self.shade_client, name=self.name,
+ admin_state_up=self.admin_state_up,
+ ext_gateway_net_id=self.ext_gateway_net_id,
+ enable_snat=self.enable_snat, ext_fixed_ips=self.ext_fixed_ips,
+ project_id=self.project_id)
+ if not router_id:
+ result.update({"router_create": 0})
LOG.error("Create router failed!")
+ raise exceptions.ScenarioCreateRouterError
- check_result = router_id
-
- try:
- keys = self.scenario_cfg.get('output', '').split()
- except KeyError:
- pass
- else:
- values = [check_result]
- return self._push_to_outputs(keys, values)
+ result.update({"router_create": 1})
+ LOG.info("Create router successful!")
+ keys = self.scenario_cfg.get('output', '').split()
+ values = [router_id]
+ return self._push_to_outputs(keys, values)
diff --git a/yardstick/benchmark/scenarios/lib/create_subnet.py b/yardstick/benchmark/scenarios/lib/create_subnet.py
index c34af8a9e..e383c99de 100644
--- a/yardstick/benchmark/scenarios/lib/create_subnet.py
+++ b/yardstick/benchmark/scenarios/lib/create_subnet.py
@@ -7,13 +7,12 @@
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
-from __future__ import print_function
-from __future__ import absolute_import
-
import logging
from yardstick.benchmark.scenarios import base
-import yardstick.common.openstack_utils as op_utils
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
+
LOG = logging.getLogger(__name__)
@@ -28,9 +27,23 @@ class CreateSubnet(base.Scenario):
self.context_cfg = context_cfg
self.options = self.scenario_cfg['options']
- self.openstack = self.options.get("openstack_paras", None)
-
- self.neutron_client = op_utils.get_neutron_client()
+ self.network_name_or_id = self.options['network_name_or_id']
+ self.cidr = self.options.get('cidr')
+ self.ip_version = self.options.get('ip_version', 4)
+ self.enable_dhcp = self.options.get('enable_dhcp', False)
+ self.subnet_name = self.options.get('subnet_name')
+ self.tenant_id = self.options.get('tenant_id')
+ self.allocation_pools = self.options.get('allocation_pools')
+ self.gateway_ip = self.options.get('gateway_ip')
+ self.disable_gateway_ip = self.options.get('disable_gateway_ip', False)
+ self.dns_nameservers = self.options.get('dns_nameservers')
+ self.host_routes = self.options.get('host_routes')
+ self.ipv6_ra_mode = self.options.get('ipv6_ra_mode')
+ self.ipv6_address_mode = self.options.get('ipv6_address_mode')
+ self.use_default_subnetpool = self.options.get(
+ 'use_default_subnetpool', False)
+
+ self.shade_client = openstack_utils.get_shade_client()
self.setup_done = False
@@ -45,22 +58,23 @@ class CreateSubnet(base.Scenario):
if not self.setup_done:
self.setup()
- openstack_paras = {'subnets': [self.openstack]}
- subnet_id = op_utils.create_neutron_subnet(self.neutron_client,
- openstack_paras)
- if subnet_id:
- result.update({"subnet_create": 1})
- LOG.info("Create subnet successful!")
- else:
+ subnet_id = openstack_utils.create_neutron_subnet(
+ self.shade_client, self.network_name_or_id, cidr=self.cidr,
+ ip_version=self.ip_version, enable_dhcp=self.enable_dhcp,
+ subnet_name=self.subnet_name, tenant_id=self.tenant_id,
+ allocation_pools=self.allocation_pools, gateway_ip=self.gateway_ip,
+ disable_gateway_ip=self.disable_gateway_ip,
+ dns_nameservers=self.dns_nameservers, host_routes=self.host_routes,
+ ipv6_ra_mode=self.ipv6_ra_mode,
+ ipv6_address_mode=self.ipv6_address_mode,
+ use_default_subnetpool=self.use_default_subnetpool)
+ if not subnet_id:
result.update({"subnet_create": 0})
LOG.error("Create subnet failed!")
+ raise exceptions.ScenarioCreateSubnetError
- check_result = subnet_id
-
- try:
- keys = self.scenario_cfg.get('output', '').split()
- except KeyError:
- pass
- else:
- values = [check_result]
- return self._push_to_outputs(keys, values)
+ result.update({"subnet_create": 1})
+ LOG.info("Create subnet successful!")
+ keys = self.scenario_cfg.get('output', '').split()
+ values = [subnet_id]
+ return self._push_to_outputs(keys, values)
diff --git a/yardstick/benchmark/scenarios/lib/delete_router.py b/yardstick/benchmark/scenarios/lib/delete_router.py
index 358fd40cf..5e7467b2c 100644
--- a/yardstick/benchmark/scenarios/lib/delete_router.py
+++ b/yardstick/benchmark/scenarios/lib/delete_router.py
@@ -7,13 +7,12 @@
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
-from __future__ import print_function
-from __future__ import absolute_import
-
import logging
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
from yardstick.benchmark.scenarios import base
-import yardstick.common.openstack_utils as op_utils
+
LOG = logging.getLogger(__name__)
@@ -28,9 +27,9 @@ class DeleteRouter(base.Scenario):
self.context_cfg = context_cfg
self.options = self.scenario_cfg['options']
- self.router_id = self.options.get("router_id", None)
+ self.router_id = self.options["router_id"]
- self.neutron_client = op_utils.get_neutron_client()
+ self.shade_client = openstack_utils.get_shade_client()
self.setup_done = False
@@ -45,11 +44,12 @@ class DeleteRouter(base.Scenario):
if not self.setup_done:
self.setup()
- status = op_utils.delete_neutron_router(self.neutron_client,
- router_id=self.router_id)
- if status:
- result.update({"delete_router": 1})
- LOG.info("Delete router successful!")
- else:
+ status = openstack_utils.delete_neutron_router(self.shade_client,
+ self.router_id)
+ if not status:
result.update({"delete_router": 0})
LOG.error("Delete router failed!")
+ raise exceptions.ScenarioDeleteRouterError
+
+ result.update({"delete_router": 1})
+ LOG.info("Delete router successful!")
diff --git a/yardstick/benchmark/scenarios/networking/moongen_testpmd.bash b/yardstick/benchmark/scenarios/networking/moongen_testpmd.bash
new file mode 100644
index 000000000..3e92cc900
--- /dev/null
+++ b/yardstick/benchmark/scenarios/networking/moongen_testpmd.bash
@@ -0,0 +1,62 @@
+##############################################################################
+# Copyright (c) 2018 Huawei Technologies Co.,Ltd and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+#!/bin/bash
+
+set -e
+
+# Commandline arguments
+MOONGEN_PORT1_MAC=$1 # MAC address of the peer port
+MOONGEN_PORT2_MAC=$2 # MAC address of the peer port
+TESTPMD_QUEUE=$3
+
+BIND_ROOT='/opt/nsb_bin'
+DRIVER_ROOT='/opt/tempT/dpdk-17.02/'
+
+load_modules()
+{
+ if ! lsmod | grep "uio" &> /dev/null; then
+ modprobe uio
+ fi
+
+ if ! lsmod | grep "igb_uio" &> /dev/null; then
+ insmod ${DRIVER_ROOT}/x86_64-native-linuxapp-gcc/kmod/igb_uio.ko
+ fi
+
+ if ! lsmod | grep "rte_kni" &> /dev/null; then
+ insmod ${DRIVER_ROOT}/x86_64-native-linuxapp-gcc/kmod/rte_kni.ko
+ fi
+}
+
+change_permissions()
+{
+ chmod 777 /sys/bus/pci/drivers/virtio-pci/*
+ chmod 777 /sys/bus/pci/drivers/igb_uio/*
+}
+
+add_interface_to_dpdk(){
+ interfaces=$(lspci |grep Eth |tail -n +2 |awk '{print $1}')
+ ${BIND_ROOT}/dpdk_nic_bind.py --bind=igb_uio $interfaces &> /dev/null
+}
+
+run_testpmd()
+{
+ blacklist=$(lspci |grep Eth |awk '{print $1}'|head -1)
+ cd ${DRIVER_ROOT}
+ sudo ./x86_64-native-linuxapp-gcc/app/testpmd -c 0x3f -n 4 -b $blacklist -- -a --nb-cores=4 --coremask=0x3c --burst=64 --txd=4096 --rxd=4096 --rxq=$TESTPMD_QUEUE --txq=$TESTPMD_QUEUE --rss-udp --eth-peer=0,$MOONGEN_PORT1_MAC --eth-peer=1,$MOONGEN_PORT2_MAC --forward-mode=mac
+}
+
+main()
+{
+ load_modules
+ change_permissions
+ add_interface_to_dpdk
+ run_testpmd
+}
+
+main
diff --git a/yardstick/benchmark/scenarios/networking/moongen_testpmd.py b/yardstick/benchmark/scenarios/networking/moongen_testpmd.py
new file mode 100644
index 000000000..86173c9da
--- /dev/null
+++ b/yardstick/benchmark/scenarios/networking/moongen_testpmd.py
@@ -0,0 +1,378 @@
+# Copyright (c) 2018 Huawei Technologies Co.,Ltd and others.
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+""" VsperfDPDK specific scenario definition """
+
+from __future__ import absolute_import
+import pkg_resources
+import logging
+import subprocess
+import time
+import re
+from oslo_serialization import jsonutils
+
+import yardstick.ssh as ssh
+import yardstick.common.utils as utils
+from yardstick.benchmark.scenarios import base
+
+LOG = logging.getLogger(__name__)
+
+
+class MoongenTestPMD(base.Scenario):
+ """Execute vsperf with defined parameters
+
+ Parameters:
+ frame_size - a frame size for which test should be executed;
+ Multiple frame sizes can be tested by modification of sequence runner
+ section inside TC YAML definition.
+ type: string
+ default: "64"
+ multistream - the number of simulated streams
+ type: string
+ default: 0 (disabled)
+ testpmd_queue - specifies how many queues you will use the VM
+ only useful when forward_type is true.
+ type: int
+ default: 1(one queue)
+ trafficgen_port1 - specifies device name of 1st interface connected to
+ the trafficgen
+ type: string
+ default: NA
+ trafficgen_port2 - specifies device name of 2nd interface connected to
+ the trafficgen
+ type: string
+ default: NA
+ moongen_host_user - specifies moongen host ssh user name
+ type: string
+ default: root
+ moongen_host_passwd - specifies moongen host ssh user password
+ type: string
+ default: root
+ moongen_host_ip - specifies moongen host ssh ip address
+ type: string
+ default NA
+ moongen_dir - specifies where is the moongen installtion dir
+ type: string
+ default NA
+ moongen_runBidirec - specifies moongen will run in one traffic
+ or two traffic.
+ type: string
+ default true
+ Package_Loss - specifies the package_Loss number in moongen server.
+ type: int
+ default 0(0%)
+ SearchRuntime - specifies the SearchRuntime and validation time
+ on moongen server.
+ type: int
+ default 60(s)
+ moongen_port1_mac - moongen server port1 mac address.
+ type: string
+ default NA
+ moongen_port2_mac - moongen server port2 mac address.
+ type: string
+ default NA
+ forward_type - VM forward type is l2fwd or testpmd.
+ type: string
+ default: testpmd
+ """
+ __scenario_type__ = "MoongenTestPMD"
+
+ TESTPMD_SCRIPT = 'moongen_testpmd.bash'
+ VSPERF_CONFIG = '/tmp/opnfv-vsperf-cfg.lua'
+
+ def __init__(self, scenario_cfg, context_cfg):
+ self.scenario_cfg = scenario_cfg
+ self.context_cfg = context_cfg
+ self.forward_setup_done = False
+ self.options = scenario_cfg.get('options', {})
+ self.moongen_host_user = \
+ self.options.get('moongen_host_user', "root")
+ self.moongen_host_passwd = \
+ self.options.get('moongen_host_passwd', "r00t")
+ self.moongen_dir = \
+ self.options.get('moongen_dir', '~/moongen.py')
+ self.testpmd_queue = \
+ self.options.get('testpmd_queue', 1)
+ self.moongen_host_ip = \
+ self.options.get('moongen_host_ip', "127.0.0.1")
+ self.moongen_port1_mac = \
+ self.options.get('moongen_port1_mac', None)
+ self.moongen_port2_mac = \
+ self.options.get('moongen_port2_mac', None)
+ self.tg_port1 = \
+ self.options.get('trafficgen_port1', "enp2s0f0")
+ self.tg_port2 = \
+ self.options.get('trafficgen_port2', "enp2s0f1")
+ self.forward_type = \
+ self.options.get('forward_type', 'testpmd')
+ self.tgen_port1_mac = None
+ self.tgen_port2_mac = None
+
+ def setup(self):
+ """scenario setup"""
+ host = self.context_cfg['host']
+
+ task_id = self.scenario_cfg['task_id']
+ context_number = task_id.split('-')[0]
+ self.tg_port1_nw = 'demo' + \
+ "-" + context_number + "-" + \
+ self.options.get('trafficgen_port1_nw', 'test2')
+ self.tg_port2_nw = 'demo' + \
+ "-" + context_number + "-" + \
+ self.options.get('trafficgen_port2_nw', 'test3')
+
+ # copy vsperf conf to VM
+ self.client = ssh.SSH.from_node(host, defaults={"user": "ubuntu"})
+ # traffic generation could last long
+ self.client.wait(timeout=1800)
+
+ self.server = ssh.SSH(
+ self.moongen_host_user,
+ self.moongen_host_ip,
+ password=self.moongen_host_passwd
+ )
+ # traffic generation could last long
+ self.server.wait(timeout=1800)
+
+ self.setup_done = True
+
+ def forward_setup(self):
+ """forward tool setup"""
+
+ # setup forward loopback in VM
+ self.testpmd_script = pkg_resources.resource_filename(
+ 'yardstick.benchmark.scenarios.networking',
+ self.TESTPMD_SCRIPT)
+
+ self.client._put_file_shell(self.testpmd_script,
+ '~/testpmd_vsperf.sh')
+
+ # disable Address Space Layout Randomization (ASLR)
+ cmd = "echo 0 | sudo tee /proc/sys/kernel/randomize_va_space"
+ self.client.send_command(cmd)
+
+ if not self._is_forward_setup():
+ self.tgen_port1_ip = \
+ utils.get_port_ip(self.client, self.tg_port1)
+ self.tgen_port1_mac = \
+ utils.get_port_mac(self.client, self.tg_port1)
+ self.client.run("tee ~/.testpmd.ipaddr.port1 > /dev/null",
+ stdin=self.tgen_port1_ip)
+ self.client.run("tee ~/.testpmd.macaddr.port1 > /dev/null",
+ stdin=self.tgen_port1_mac)
+ self.tgen_port2_ip = \
+ utils.get_port_ip(self.client, self.tg_port2)
+ self.tgen_port2_mac = \
+ utils.get_port_mac(self.client, self.tg_port2)
+ self.client.run("tee ~/.testpmd.ipaddr.port2 > /dev/null",
+ stdin=self.tgen_port2_ip)
+ self.client.run("tee ~/.testpmd.macaddr.port2 > /dev/null",
+ stdin=self.tgen_port2_mac)
+ else:
+ cmd = "cat ~/.testpmd.macaddr.port1"
+ status, stdout, stderr = self.client.execute(cmd)
+ if status:
+ raise RuntimeError(stderr)
+ self.tgen_port1_mac = stdout
+ cmd = "cat ~/.testpmd.ipaddr.port1"
+ status, stdout, stderr = self.client.execute(cmd)
+ if status:
+ raise RuntimeError(stderr)
+ self.tgen_port1_ip = stdout
+ cmd = "cat ~/.testpmd.macaddr.port2"
+ status, stdout, stderr = self.client.execute(cmd)
+ if status:
+ raise RuntimeError(stderr)
+ self.tgen_port2_mac = stdout
+ cmd = "cat ~/.testpmd.ipaddr.port2"
+ status, stdout, stderr = self.client.execute(cmd)
+ if status:
+ raise RuntimeError(stderr)
+ self.tgen_port2_ip = stdout
+
+ LOG.info("forward type is %s", self.forward_type)
+ if self.forward_type == 'testpmd':
+ cmd = "sudo ip link set %s down" % (self.tg_port1)
+ LOG.debug("Executing command: %s", cmd)
+ self.client.execute(cmd)
+ cmd = "sudo ip link set %s down" % (self.tg_port2)
+ LOG.debug("Executing command: %s", cmd)
+ self.client.execute(cmd)
+ cmd = "screen -d -m sudo -E bash ~/testpmd_vsperf.sh %s %s %d" % \
+ (self.moongen_port1_mac, self.moongen_port2_mac,
+ self.testpmd_queue)
+ LOG.debug("Executing command: %s", cmd)
+ status, stdout, stderr = self.client.execute(cmd)
+ if status:
+ raise RuntimeError(stderr)
+
+ elif self.forward_type == 'l2fwd':
+ cmd = ('sed -i "s/static char *net1 = \\\"eth1\\\";'
+ '/static char *net1 = \\\"%s %s %s\\\";/g" /home/l2fwd/l2fwd.c'
+ % (self.tg_port1, self.tgen_port1_ip, self.moongen_port1_mac))
+ LOG.debug("Executing command: %s", cmd)
+ status, stdout, stderr = self.client.execute(cmd)
+
+ cmd = ('sed -i "s/static char *net2 = \\\"eth2\\\";'
+ '/static char *net2 = \\\"%s %s %s\\\";/g" /home/l2fwd/l2fwd.c'
+ % (self.tg_port2, self.tgen_port2_ip, self.moongen_port2_mac))
+ LOG.debug("Executing command: %s", cmd)
+ status, stdout, stderr = self.client.execute(cmd)
+
+ cmd = ('cd /home/l2fwd/;make;./gen_debian_package.sh;'
+ 'sudo dpkg -i *.deb;'
+ 'sudo modprobe l2fwd')
+ LOG.debug("Executing command: %s", cmd)
+ status, stdout, stderr = self.client.execute(cmd)
+
+ time.sleep(1)
+
+ self.forward_setup_done = True
+
+ def _is_forward_setup(self):
+ """Is forward already setup in the host?"""
+ if self.forward_type is 'testpmd':
+ is_run = True
+ cmd = "ip a | grep %s 2>/dev/null" % (self.tg_port1)
+ LOG.debug("Executing command: %s", cmd)
+ _, stdout, _ = self.client.execute(cmd)
+ if stdout:
+ is_run = False
+ return is_run
+ elif self.forward_type is 'l2fwd':
+ cmd = ('sudo lsmod |grep l2fwd')
+ LOG.debug("Executing command: %s", cmd)
+ _, stdout, _ = self.client.execute(cmd)
+ if stdout:
+ return True
+ else:
+ return False
+
+ def generate_config_file(self, frame_size, multistream,
+ runBidirec, tg_port1_vlan, tg_port2_vlan,
+ SearchRuntime, Package_Loss):
+ out_text = """\
+VSPERF {
+testType = 'throughput',
+nrFlows = %d,
+runBidirec = %s,
+frameSize = %d,
+srcMacs = {\'%s\', \'%s\'},
+dstMacs = {\'%s\', \'%s\'},
+vlanIds = {%d, %d},
+searchRunTime = %d,
+validationRunTime = %d,
+acceptableLossPct = %d,
+ports = {0,1},
+}
+""" % (multistream, runBidirec, frame_size, self.moongen_port1_mac,
+ self.moongen_port2_mac, self.tgen_port1_mac, self.tgen_port2_mac,
+ tg_port1_vlan, tg_port2_vlan, SearchRuntime, SearchRuntime, Package_Loss)
+ with open(self.VSPERF_CONFIG, "wt") as out_file:
+ out_file.write(out_text)
+ self.CONFIG_FILE = True
+
+ def result_to_data(self, result):
+ search_pattern = re.compile(
+ r'\[REPORT\]\s+total\:\s+'
+ r'Tx\s+frames\:\s+(\d+)\s+'
+ r'Rx\s+Frames\:\s+(\d+)\s+'
+ r'frame\s+loss\:\s+(\d+)\,'
+ r'\s+(\d+\.\d+|\d+)%\s+'
+ r'Tx\s+Mpps\:\s+(\d+.\d+|\d+)\s+'
+ r'Rx\s+Mpps\:\s+(\d+\.\d+|\d+)',
+ re.IGNORECASE)
+ results_match = search_pattern.search(result)
+ if results_match:
+ rx_mpps = float(results_match.group(6))
+ tx_mpps = float(results_match.group(5))
+ else:
+ rx_mpps = 0
+ tx_mpps = 0
+ test_result = {"rx_mpps": rx_mpps, "tx_mpps": tx_mpps}
+ self.TO_DATA = True
+ return test_result
+
+ def run(self, result):
+ """ execute the vsperf benchmark and return test results
+ within result dictionary
+ """
+
+ if not self.setup_done:
+ self.setup()
+
+ # get vsperf options
+ multistream = self.options.get("multistream", 1)
+
+ if not self.forward_setup_done:
+ self.forward_setup()
+
+ if 'frame_size' in self.options:
+ frame_size = self.options.get("frame_size", 64)
+ Package_Loss = self.options.get("Package_Loss", 0)
+ runBidirec = self.options.get("moongen_runBidirec",
+ "true")
+ SearchRuntime = self.options.get("SearchRuntime", 10)
+
+ cmd = "openstack network show %s --format json -c " \
+ "provider:segmentation_id" % (self.tg_port1_nw)
+ LOG.debug("Executing command: %s", cmd)
+ output = subprocess.check_output(cmd, shell=True)
+ try:
+ tg_port1_vlan = jsonutils.loads(output).get("provider:segmentation_id", 1)
+ except TypeError:
+ tg_port1_vlan = 1
+
+ cmd = "openstack network show %s --format json -c " \
+ "provider:segmentation_id" % (self.tg_port2_nw)
+ LOG.debug("Executing command: %s", cmd)
+ output = subprocess.check_output(cmd, shell=True)
+ try:
+ tg_port2_vlan = jsonutils.loads(output).get("provider:segmentation_id", 2)
+ except TypeError:
+ tg_port2_vlan = 2
+
+ self.generate_config_file(frame_size, multistream,
+ runBidirec, tg_port1_vlan,
+ tg_port2_vlan, SearchRuntime, Package_Loss)
+
+ self.server.execute("rm -f -- %s/opnfv-vsperf-cfg.lua" %
+ (self.moongen_dir))
+ self.server._put_file_shell(self.VSPERF_CONFIG,
+ "%s/opnfv-vsperf-cfg.lua"
+ % (self.moongen_dir))
+
+ # execute moongen
+ cmd = ("cd %s;./MoonGen/build/MoonGen ./trafficgen.lua"
+ % (self.moongen_dir))
+ status, stdout, stderr = self.server.execute(cmd)
+ if status:
+ raise RuntimeError(stderr)
+
+ moongen_result = self.result_to_data(stdout)
+ LOG.info(moongen_result)
+ result.update(moongen_result)
+
+ if "sla" in self.scenario_cfg:
+ throughput_rx_mpps = int(
+ self.scenario_cfg["sla"]["throughput_rx_mpps"])
+
+ assert throughput_rx_mpps <= moongen_result["tx_mpps"], \
+ "sla_throughput_rx_mpps %f > throughput_rx_mpps(%f); " % \
+ (throughput_rx_mpps, moongen_result["tx_mpps"])
+
+ def teardown(self):
+ """cleanup after the test execution"""
+
+ # execute external setup script
+ self.setup_done = False
diff --git a/yardstick/benchmark/scenarios/networking/netperf.py b/yardstick/benchmark/scenarios/networking/netperf.py
index a8d9010ed..33c02d409 100755
--- a/yardstick/benchmark/scenarios/networking/netperf.py
+++ b/yardstick/benchmark/scenarios/networking/netperf.py
@@ -104,7 +104,9 @@ class Netperf(base.Scenario):
cmd_args = "-H %s -l %s -t %s" % (ipaddr, testlen, testname)
# get test specific options
- default_args = "-O 'THROUGHPUT,THROUGHPUT_UNITS,MEAN_LATENCY'"
+ output_opt = options.get(
+ "output_opt", "THROUGHPUT,THROUGHPUT_UNITS,MEAN_LATENCY")
+ default_args = "-O %s" % output_opt
cmd_args += " -- %s" % default_args
option_pair_list = [("send_msg_size", "-m"),
("recv_msg_size", "-M"),
diff --git a/yardstick/benchmark/scenarios/networking/pktgen_dpdk.py b/yardstick/benchmark/scenarios/networking/pktgen_dpdk.py
index ce8a7f497..9a7b975a2 100644
--- a/yardstick/benchmark/scenarios/networking/pktgen_dpdk.py
+++ b/yardstick/benchmark/scenarios/networking/pktgen_dpdk.py
@@ -70,39 +70,42 @@ class PktgenDPDKLatency(base.Scenario):
def run(self, result):
"""execute the benchmark"""
+ options = self.scenario_cfg['options']
+ eth1 = options.get("eth1", "ens4")
+ eth2 = options.get("eth2", "ens5")
if not self.setup_done:
self.setup()
if not self.testpmd_args:
- self.testpmd_args = utils.get_port_mac(self.client, 'eth2')
+ self.testpmd_args = utils.get_port_mac(self.client, eth2)
if not self.pktgen_args:
- server_rev_mac = utils.get_port_mac(self.server, 'eth1')
- server_send_mac = utils.get_port_mac(self.server, 'eth2')
- client_src_ip = utils.get_port_ip(self.client, 'eth1')
- client_dst_ip = utils.get_port_ip(self.client, 'eth2')
+ server_rev_mac = utils.get_port_mac(self.server, eth1)
+ server_send_mac = utils.get_port_mac(self.server, eth2)
+ client_src_ip = utils.get_port_ip(self.client, eth1)
+ client_dst_ip = utils.get_port_ip(self.client, eth2)
self.pktgen_args = [client_src_ip, client_dst_ip,
server_rev_mac, server_send_mac]
- options = self.scenario_cfg['options']
packetsize = options.get("packetsize", 64)
rate = options.get("rate", 100)
- cmd = "screen sudo -E bash ~/testpmd_fwd.sh %s " % (self.testpmd_args)
+ cmd = "screen sudo -E bash ~/testpmd_fwd.sh %s %s %s" % \
+ (self.testpmd_args, eth1, eth2)
LOG.debug("Executing command: %s", cmd)
self.server.send_command(cmd)
time.sleep(1)
- cmd = "screen sudo -E bash ~/pktgen_dpdk.sh %s %s %s %s %s %s" % \
+ cmd = "screen sudo -E bash ~/pktgen_dpdk.sh %s %s %s %s %s %s %s %s" % \
(self.pktgen_args[0], self.pktgen_args[1], self.pktgen_args[2],
- self.pktgen_args[3], rate, packetsize)
+ self.pktgen_args[3], rate, packetsize, eth1, eth2)
LOG.debug("Executing command: %s", cmd)
self.client.send_command(cmd)
# wait for finishing test
- time.sleep(1)
+ time.sleep(60)
cmd = r"""\
cat ~/result.log -vT \
diff --git a/yardstick/benchmark/scenarios/networking/pktgen_dpdk_latency_benchmark.bash b/yardstick/benchmark/scenarios/networking/pktgen_dpdk_latency_benchmark.bash
index b872aa3df..dcd5a9bfb 100644
--- a/yardstick/benchmark/scenarios/networking/pktgen_dpdk_latency_benchmark.bash
+++ b/yardstick/benchmark/scenarios/networking/pktgen_dpdk_latency_benchmark.bash
@@ -7,7 +7,7 @@
# which accompanies this distribution, and is available at
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
-!/bin/sh
+#!/bin/sh
set -e
@@ -18,6 +18,11 @@ FWD_REV_MAC=$3 # MAC address of forwarding receiver in VM B
FWD_SEND_MAC=$4 # MAC address of forwarding sender in VM B
RATE=$5 # packet rate in percentage
PKT_SIZE=$6 # packet size
+ETH1=$7
+ETH2=$8
+
+DPDK_VERSION="dpdk-17.02"
+PKTGEN_VERSION="pktgen-3.2.12"
load_modules()
@@ -31,13 +36,13 @@ load_modules()
if lsmod | grep "igb_uio" &> /dev/null ; then
echo "igb_uio module is loaded"
else
- insmod /dpdk/x86_64-native-linuxapp-gcc/kmod/igb_uio.ko
+ insmod /opt/tempT/$DPDK_VERSION/x86_64-native-linuxapp-gcc/kmod/igb_uio.ko
fi
if lsmod | grep "rte_kni" &> /dev/null ; then
echo "rte_kni module is loaded"
else
- insmod /dpdk/x86_64-native-linuxapp-gcc/kmod/rte_kni.ko
+ insmod /opt/tempT/$DPDK_VERSION/x86_64-native-linuxapp-gcc/kmod/rte_kni.ko
fi
}
@@ -48,8 +53,10 @@ change_permissions()
}
add_interface_to_dpdk(){
+ ip link set $ETH1 down
+ ip link set $ETH2 down
interfaces=$(lspci |grep Eth |tail -n +2 |awk '{print $1}')
- /dpdk/tools/dpdk-devbind.py --bind=igb_uio $interfaces
+ /opt/tempT/$DPDK_VERSION/usertools/dpdk-devbind.py --bind=igb_uio $interfaces
}
@@ -106,20 +113,14 @@ spawn ./app/app/x86_64-native-linuxapp-gcc/pktgen -c 0x07 -n 4 -b $blacklist --
expect "Pktgen>"
send "\n"
expect "Pktgen>"
-send "screen on\n"
+send "on\n"
expect "Pktgen>"
set count 10
while { $count } {
send "page latency\n"
- expect {
- timeout { send "\n" }
- -regexp {..*} {
- set result "${result}$expect_out(0,string)"
- set timeout 1
- exp_continue
- }
- "Pktgen>"
- }
+ expect -re "(..*)"
+ set result "${result}$expect_out(0,string)"
+ set timeout 1
set count [expr $count-1]
}
send "stop 0\n"
@@ -136,7 +137,7 @@ EOF
run_pktgen()
{
blacklist=$(lspci |grep Eth |awk '{print $1}'|head -1)
- cd /pktgen-dpdk
+ cd /opt/tempT/$PKTGEN_VERSION
touch /home/ubuntu/result.log
result_log="/home/ubuntu/result.log"
sudo expect /home/ubuntu/pktgen.exp $blacklist $result_log
@@ -153,4 +154,3 @@ main()
}
main
-
diff --git a/yardstick/benchmark/scenarios/networking/testpmd_fwd.bash b/yardstick/benchmark/scenarios/networking/testpmd_fwd.bash
index 247a8a833..30b63a734 100644
--- a/yardstick/benchmark/scenarios/networking/testpmd_fwd.bash
+++ b/yardstick/benchmark/scenarios/networking/testpmd_fwd.bash
@@ -13,6 +13,10 @@ set -e
# Commandline arguments
DST_MAC=$1 # MAC address of the peer port
+ETH1=$2
+ETH2=$3
+
+DPDK_VERSION="dpdk-17.02"
load_modules()
{
@@ -25,13 +29,13 @@ load_modules()
if lsmod | grep "igb_uio" &> /dev/null ; then
echo "igb_uio module is loaded"
else
- insmod /dpdk/x86_64-native-linuxapp-gcc/kmod/igb_uio.ko
+ insmod /opt/tempT/$DPDK_VERSION/x86_64-native-linuxapp-gcc/kmod/igb_uio.ko
fi
if lsmod | grep "rte_kni" &> /dev/null ; then
echo "rte_kni module is loaded"
else
- insmod /dpdk/x86_64-native-linuxapp-gcc/kmod/rte_kni.ko
+ insmod /opt/tempT/$DPDK_VERSION/x86_64-native-linuxapp-gcc/kmod/rte_kni.ko
fi
}
@@ -42,15 +46,17 @@ change_permissions()
}
add_interface_to_dpdk(){
+ ip link set $ETH1 down
+ ip link set $ETH2 down
interfaces=$(lspci |grep Eth |tail -n +2 |awk '{print $1}')
- /dpdk/tools/dpdk-devbind.py --bind=igb_uio $interfaces
+ /opt/tempT/$DPDK_VERSION/usertools//dpdk-devbind.py --bind=igb_uio $interfaces
}
run_testpmd()
{
blacklist=$(lspci |grep Eth |awk '{print $1}'|head -1)
- cd /dpdk
- sudo ./destdir/bin/testpmd -c 0x07 -n 4 -b $blacklist -- -a --eth-peer=1,$DST_MAC --forward-mode=mac
+ cd /opt/tempT/$DPDK_VERSION/x86_64-native-linuxapp-gcc/app
+ sudo ./testpmd -c 0x07 -n 4 -b $blacklist -- -a --eth-peer=1,$DST_MAC --forward-mode=mac
}
main()
diff --git a/yardstick/benchmark/scenarios/networking/vnf_generic.py b/yardstick/benchmark/scenarios/networking/vnf_generic.py
index 0e4785294..be2fa3f3b 100644
--- a/yardstick/benchmark/scenarios/networking/vnf_generic.py
+++ b/yardstick/benchmark/scenarios/networking/vnf_generic.py
@@ -14,6 +14,7 @@
import copy
import logging
+import time
import ipaddress
from itertools import chain
@@ -484,3 +485,11 @@ class NetworkServiceTestCase(scenario_base.Scenario):
# https://bugs.python.org/issue9400
LOG.exception("")
raise RuntimeError("Error in teardown")
+
+ def pre_run_wait_time(self, time_seconds):
+ """Time waited before executing the run method"""
+ time.sleep(time_seconds)
+
+ def post_run_wait_time(self, time_seconds):
+ """Time waited after executing the run method"""
+ pass
diff --git a/yardstick/benchmark/scenarios/storage/fio.py b/yardstick/benchmark/scenarios/storage/fio.py
index 125bc7ed4..d3ed840d8 100644
--- a/yardstick/benchmark/scenarios/storage/fio.py
+++ b/yardstick/benchmark/scenarios/storage/fio.py
@@ -124,12 +124,16 @@ class Fio(base.Scenario):
if mount_dir:
LOG.debug("Formating volume...")
- self.client.execute("sudo mkfs.ext4 /dev/vdb")
- cmd = "sudo mkdir %s" % mount_dir
- self.client.execute(cmd)
- LOG.debug("Mounting volume at: %s", mount_dir)
- cmd = "sudo mount /dev/vdb %s" % mount_dir
- self.client.execute(cmd)
+ _, stdout, _ = self.client.execute(
+ "lsblk -dps | grep -m 1 disk | awk '{print $1}'")
+ block_device = stdout.strip()
+ if block_device:
+ self.client.execute("sudo mkfs.ext4 %s" % block_device)
+ cmd = "sudo mkdir %s" % mount_dir
+ self.client.execute(cmd)
+ LOG.debug("Mounting volume at: %s", mount_dir)
+ cmd = "sudo mount %s %s" % (block_device, mount_dir)
+ self.client.execute(cmd)
self.setup_done = True
diff --git a/yardstick/common/ansible_common.py b/yardstick/common/ansible_common.py
index be262c215..38d2dd7c2 100644
--- a/yardstick/common/ansible_common.py
+++ b/yardstick/common/ansible_common.py
@@ -31,6 +31,7 @@ import six.moves.configparser as ConfigParser
import yaml
from six import StringIO
from chainmap import ChainMap
+from oslo_serialization import jsonutils
from yardstick.common.utils import Timer
from yardstick.common import constants as consts
@@ -508,6 +509,58 @@ class AnsibleCommon(object):
timeout = 1200.0
return timeout
+ def _generate_ansible_cfg(self, directory):
+ parser = ConfigParser.ConfigParser()
+ parser.add_section('defaults')
+ parser.set('defaults', 'host_key_checking', 'False')
+
+ cfg_path = os.path.join(directory, 'setup.cfg')
+ with open(cfg_path, 'w') as f:
+ parser.write(f)
+
+ def get_sut_info(self, directory, sut_dir='sut'):
+ if not os.path.isdir(directory):
+ raise OSError('No such directory: %s' % directory)
+
+ self._generate_ansible_cfg(directory)
+
+ prefix = 'tmp'
+ self.gen_inventory_ini_dict()
+ ini_file = self._gen_ansible_inventory_file(directory, prefix=prefix)
+ with ini_file as f:
+ inventory_path = str(f)
+
+ self._exec_get_sut_info_cmd(directory, inventory_path, sut_dir)
+
+ sut_dir = os.path.join(directory, sut_dir)
+ sut_info = self._gen_sut_info_dict(sut_dir)
+
+ return sut_info
+
+ def _exec_get_sut_info_cmd(self, directory, inventory_path, sut_dir):
+ cmd = ['ansible', 'all', '-m', 'setup', '-i',
+ inventory_path, '--tree', sut_dir]
+
+ proc = Popen(cmd, stdout=PIPE, cwd=directory)
+ output, _ = proc.communicate()
+ retcode = proc.wait()
+ LOG.debug("exit status = %s", retcode)
+ if retcode != 0:
+ raise CalledProcessError(retcode, cmd, output)
+
+ def _gen_sut_info_dict(self, sut_dir):
+ sut_info = {}
+
+ if os.path.isdir(sut_dir):
+ root, _, files = next(os.walk(sut_dir))
+ for filename in files:
+ abs_path = os.path.join(root, filename)
+ with open(abs_path) as f:
+ data = jsonutils.load(f)
+ sut_info[filename] = data
+
+ return sut_info
+
def execute_ansible(self, playbooks, directory, timeout=None,
extra_vars=None, ansible_check=False, prefix='tmp',
verbose=False):
diff --git a/yardstick/common/constants.py b/yardstick/common/constants.py
index 43c2c19cb..153bd4bf4 100644
--- a/yardstick/common/constants.py
+++ b/yardstick/common/constants.py
@@ -145,6 +145,10 @@ BASE_URL = 'http://localhost:5000'
ENV_ACTION_API = BASE_URL + '/yardstick/env/action'
ASYNC_TASK_API = BASE_URL + '/yardstick/asynctask'
+# flags
+IS_EXISTING = 'is_existing'
+IS_PUBLIC = 'is_public'
+
# general
TESTCASE_PRE = 'opnfv_yardstick_'
TESTSUITE_PRE = 'opnfv_'
diff --git a/yardstick/common/exceptions.py b/yardstick/common/exceptions.py
index 9946bf1cb..8160c5b0c 100644
--- a/yardstick/common/exceptions.py
+++ b/yardstick/common/exceptions.py
@@ -67,7 +67,7 @@ class YardstickBannedModuleImported(YardstickException):
class HeatTemplateError(YardstickException):
"""Error in Heat during the stack deployment"""
message = ('Error in Heat during the creation of the OpenStack stack '
- '"%(stack_name)"')
+ '"%(stack_name)s"')
class IPv6RangeError(YardstickException):
@@ -100,3 +100,27 @@ class TaskReadError(YardstickException):
class TaskRenderError(YardstickException):
message = 'Failed to render template:\n%(input_task)s'
+
+
+class ScenarioCreateNetworkError(YardstickException):
+ message = 'Create Neutron Network Scenario failed'
+
+
+class ScenarioCreateSubnetError(YardstickException):
+ message = 'Create Neutron Subnet Scenario failed'
+
+
+class ScenarioDeleteRouterError(YardstickException):
+ message = 'Delete Neutron Router Scenario failed'
+
+
+class MissingPodInfoError(YardstickException):
+ message = 'Missing pod args, please check'
+
+
+class UnsupportedPodFormatError(YardstickException):
+ message = 'Failed to load pod info, unsupported format'
+
+
+class ScenarioCreateRouterError(YardstickException):
+ message = 'Create Neutron Router Scenario failed'
diff --git a/yardstick/common/openstack_utils.py b/yardstick/common/openstack_utils.py
index e3f67baa5..a4fd4e550 100644
--- a/yardstick/common/openstack_utils.py
+++ b/yardstick/common/openstack_utils.py
@@ -435,13 +435,29 @@ def get_network_id(shade_client, network_name):
return networks[0]['id']
-def create_neutron_net(neutron_client, json_body): # pragma: no cover
+def create_neutron_net(shade_client, network_name, shared=False,
+ admin_state_up=True, external=False, provider=None,
+ project_id=None):
+ """Create a neutron network.
+
+ :param network_name:(string) name of the network being created.
+ :param shared:(bool) whether the network is shared.
+ :param admin_state_up:(bool) set the network administrative state.
+ :param external:(bool) whether this network is externally accessible.
+ :param provider:(dict) a dict of network provider options.
+ :param project_id:(string) specify the project ID this network
+ will be created on (admin-only).
+ :returns:(string) the network id.
+ """
try:
- network = neutron_client.create_network(body=json_body)
- return network['network']['id']
- except Exception: # pylint: disable=broad-except
- log.error("Error [create_neutron_net(neutron_client)]")
- raise Exception("operation error")
+ networks = shade_client.create_network(
+ name=network_name, shared=shared, admin_state_up=admin_state_up,
+ external=external, provider=provider, project_id=project_id)
+ return networks['id']
+ except exc.OpenStackCloudException as o_exc:
+ log.error("Error [create_neutron_net(shade_client)]."
+ "Exception message, '%s'", o_exc.orig_message)
+ return None
def delete_neutron_net(shade_client, network_id):
@@ -452,31 +468,88 @@ def delete_neutron_net(shade_client, network_id):
return False
-def create_neutron_subnet(neutron_client, json_body): # pragma: no cover
+def create_neutron_subnet(shade_client, network_name_or_id, cidr=None,
+ ip_version=4, enable_dhcp=False, subnet_name=None,
+ tenant_id=None, allocation_pools=None,
+ gateway_ip=None, disable_gateway_ip=False,
+ dns_nameservers=None, host_routes=None,
+ ipv6_ra_mode=None, ipv6_address_mode=None,
+ use_default_subnetpool=False):
+ """Create a subnet on a specified network.
+
+ :param network_name_or_id:(string) the unique name or ID of the
+ attached network. If a non-unique name is
+ supplied, an exception is raised.
+ :param cidr:(string) the CIDR.
+ :param ip_version:(int) the IP version.
+ :param enable_dhcp:(bool) whether DHCP is enable.
+ :param subnet_name:(string) the name of the subnet.
+ :param tenant_id:(string) the ID of the tenant who owns the network.
+ :param allocation_pools: A list of dictionaries of the start and end
+ addresses for the allocation pools.
+ :param gateway_ip:(string) the gateway IP address.
+ :param disable_gateway_ip:(bool) whether gateway IP address is enabled.
+ :param dns_nameservers: A list of DNS name servers for the subnet.
+ :param host_routes: A list of host route dictionaries for the subnet.
+ :param ipv6_ra_mode:(string) IPv6 Router Advertisement mode.
+ Valid values are: 'dhcpv6-stateful',
+ 'dhcpv6-stateless', or 'slaac'.
+ :param ipv6_address_mode:(string) IPv6 address mode.
+ Valid values are: 'dhcpv6-stateful',
+ 'dhcpv6-stateless', or 'slaac'.
+ :param use_default_subnetpool:(bool) use the default subnetpool for
+ ``ip_version`` to obtain a CIDR. It is
+ required to pass ``None`` to the ``cidr``
+ argument when enabling this option.
+ :returns:(string) the subnet id.
+ """
try:
- subnet = neutron_client.create_subnet(body=json_body)
- return subnet['subnets'][0]['id']
- except Exception: # pylint: disable=broad-except
- log.error("Error [create_neutron_subnet")
- raise Exception("operation error")
+ subnet = shade_client.create_subnet(
+ network_name_or_id, cidr=cidr, ip_version=ip_version,
+ enable_dhcp=enable_dhcp, subnet_name=subnet_name,
+ tenant_id=tenant_id, allocation_pools=allocation_pools,
+ gateway_ip=gateway_ip, disable_gateway_ip=disable_gateway_ip,
+ dns_nameservers=dns_nameservers, host_routes=host_routes,
+ ipv6_ra_mode=ipv6_ra_mode, ipv6_address_mode=ipv6_address_mode,
+ use_default_subnetpool=use_default_subnetpool)
+ return subnet['id']
+ except exc.OpenStackCloudException as o_exc:
+ log.error("Error [create_neutron_subnet(shade_client)]. "
+ "Exception message: %s", o_exc.orig_message)
+ return None
+
+def create_neutron_router(shade_client, name=None, admin_state_up=True,
+ ext_gateway_net_id=None, enable_snat=None,
+ ext_fixed_ips=None, project_id=None):
+ """Create a logical router.
-def create_neutron_router(neutron_client, json_body): # pragma: no cover
+ :param name:(string) the router name.
+ :param admin_state_up:(bool) the administrative state of the router.
+ :param ext_gateway_net_id:(string) network ID for the external gateway.
+ :param enable_snat:(bool) enable Source NAT (SNAT) attribute.
+ :param ext_fixed_ips: List of dictionaries of desired IP and/or subnet
+ on the external network.
+ :param project_id:(string) project ID for the router.
+
+ :returns:(string) the router id.
+ """
try:
- router = neutron_client.create_router(json_body)
- return router['router']['id']
- except Exception: # pylint: disable=broad-except
- log.error("Error [create_neutron_router(neutron_client)]")
- raise Exception("operation error")
+ router = shade_client.create_router(
+ name, admin_state_up, ext_gateway_net_id, enable_snat,
+ ext_fixed_ips, project_id)
+ return router['id']
+ except exc.OpenStackCloudException as o_exc:
+ log.error("Error [create_neutron_router(shade_client)]. "
+ "Exception message: %s", o_exc.orig_message)
-def delete_neutron_router(neutron_client, router_id): # pragma: no cover
+def delete_neutron_router(shade_client, router_id):
try:
- neutron_client.delete_router(router=router_id)
- return True
- except Exception: # pylint: disable=broad-except
- log.error("Error [delete_neutron_router(neutron_client, '%s')]",
- router_id)
+ return shade_client.delete_router(router_id)
+ except exc.OpenStackCloudException as o_exc:
+ log.error("Error [delete_neutron_router(shade_client, '%s')]. "
+ "Exception message: %s", router_id, o_exc.orig_message)
return False
diff --git a/yardstick/network_services/constants.py b/yardstick/network_services/constants.py
index 79951e353..0064b4fc5 100644
--- a/yardstick/network_services/constants.py
+++ b/yardstick/network_services/constants.py
@@ -15,3 +15,5 @@
REMOTE_TMP = "/tmp"
DEFAULT_VNF_TIMEOUT = 3600
PROCESS_JOIN_TIMEOUT = 3
+ONE_GIGABIT_IN_BITS = 1000000000
+NIC_GBPS_DEFAULT = 10
diff --git a/yardstick/network_services/traffic_profile/prox_binsearch.py b/yardstick/network_services/traffic_profile/prox_binsearch.py
index 5700f98e5..c3277fb12 100644
--- a/yardstick/network_services/traffic_profile/prox_binsearch.py
+++ b/yardstick/network_services/traffic_profile/prox_binsearch.py
@@ -20,6 +20,7 @@ import datetime
import time
from yardstick.network_services.traffic_profile.prox_profile import ProxProfile
+from yardstick.network_services import constants
LOG = logging.getLogger(__name__)
@@ -99,9 +100,13 @@ class ProxBinSearchProfile(ProxProfile):
# throughput and packet loss from the most recent successful test
successful_pkt_loss = 0.0
+ line_speed = traffic_gen.scenario_helper.all_options.get(
+ "interface_speed_gbps", constants.NIC_GBPS_DEFAULT) * constants.ONE_GIGABIT_IN_BITS
for test_value in self.bounds_iterator(LOG):
result, port_samples = self._profile_helper.run_test(pkt_size, duration,
- test_value, self.tolerated_loss)
+ test_value,
+ self.tolerated_loss,
+ line_speed)
self.curr_time = time.time()
diff_time = self.curr_time - self.prev_time
self.prev_time = self.curr_time
diff --git a/yardstick/network_services/vnf_generic/vnf/prox_helpers.py b/yardstick/network_services/vnf_generic/vnf/prox_helpers.py
index 29f9c7bba..31ed30140 100644
--- a/yardstick/network_services/vnf_generic/vnf/prox_helpers.py
+++ b/yardstick/network_services/vnf_generic/vnf/prox_helpers.py
@@ -35,6 +35,7 @@ from yardstick.common.utils import SocketTopology, join_non_strings, try_int
from yardstick.network_services.helpers.iniparser import ConfigParser
from yardstick.network_services.vnf_generic.vnf.sample_vnf import ClientResourceHelper
from yardstick.network_services.vnf_generic.vnf.sample_vnf import DpdkVnfSetupEnvHelper
+from yardstick.network_services import constants
PROX_PORT = 8474
@@ -44,7 +45,6 @@ SECTION_CONTENTS = 1
LOG = logging.getLogger(__name__)
LOG.setLevel(logging.DEBUG)
-TEN_GIGABIT = 1e10
BITS_PER_BYTE = 8
RETRY_SECONDS = 60
RETRY_INTERVAL = 1
@@ -466,13 +466,14 @@ class ProxSocketHelper(object):
core_data['current'] = core_data[key1] + core_data[key2]
self.set_speed(core_data['cores'], core_data['current'])
- def set_pps(self, cores, pps, pkt_size):
+ def set_pps(self, cores, pps, pkt_size,
+ line_speed=(constants.ONE_GIGABIT_IN_BITS * constants.NIC_GBPS_DEFAULT)):
""" set packets per second for specific cores on the remote instance """
msg = "Set packets per sec for core(s) %s to %g%% of line rate (packet size: %d)"
LOG.debug(msg, cores, pps, pkt_size)
# speed in percent of line-rate
- speed = float(pps) * (pkt_size + 20) / TEN_GIGABIT / BITS_PER_BYTE
+ speed = float(pps) * (pkt_size + 20) / line_speed / BITS_PER_BYTE
self._run_template_over_cores("speed {} 0 {}\n", cores, speed)
def lat_stats(self, cores, task=0):
@@ -698,6 +699,20 @@ class ProxDpdkVnfSetupEnvHelper(DpdkVnfSetupEnvHelper):
mac = intf["virtual-interface"]["dst_mac"]
section_data[1] = mac
+ if item_val.startswith("@@src_mac"):
+ tx_port_iter = re.finditer(r'\d+', item_val)
+ tx_port_no = int(next(tx_port_iter).group(0))
+ intf = self.vnfd_helper.find_interface_by_port(tx_port_no)
+ mac = intf["virtual-interface"]["local_mac"]
+ section_data[1] = mac.replace(":", " ", 6)
+
+ if item_key == "src mac" and item_val.startswith("@@"):
+ tx_port_iter = re.finditer(r'\d+', item_val)
+ tx_port_no = int(next(tx_port_iter).group(0))
+ intf = self.vnfd_helper.find_interface_by_port(tx_port_no)
+ mac = intf["virtual-interface"]["local_mac"]
+ section_data[1] = mac
+
# if addition file specified in prox config
if not self.additional_files:
return sections
@@ -967,12 +982,13 @@ class ProxResourceHelper(ClientResourceHelper):
class ProxDataHelper(object):
- def __init__(self, vnfd_helper, sut, pkt_size, value, tolerated_loss):
+ def __init__(self, vnfd_helper, sut, pkt_size, value, tolerated_loss, line_speed):
super(ProxDataHelper, self).__init__()
self.vnfd_helper = vnfd_helper
self.sut = sut
self.pkt_size = pkt_size
self.value = value
+ self.line_speed = line_speed
self.tolerated_loss = tolerated_loss
self.port_count = len(self.vnfd_helper.port_pairs.all_ports)
self.tsc_hz = None
@@ -1058,9 +1074,7 @@ class ProxDataHelper(object):
self.tsc_hz = float(self.sut.hz())
def line_rate_to_pps(self):
- # NOTE: to fix, don't hardcode 10Gb/s
- return self.port_count * TEN_GIGABIT / BITS_PER_BYTE / (self.pkt_size + 20)
-
+ return self.port_count * self.line_speed / BITS_PER_BYTE / (self.pkt_size + 20)
class ProxProfileHelper(object):
@@ -1139,8 +1153,10 @@ class ProxProfileHelper(object):
return cores
- def run_test(self, pkt_size, duration, value, tolerated_loss=0.0):
- data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size, value, tolerated_loss)
+ def run_test(self, pkt_size, duration, value, tolerated_loss=0.0,
+ line_speed=(constants.ONE_GIGABIT_IN_BITS * constants.NIC_GBPS_DEFAULT)):
+ data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size,
+ value, tolerated_loss, line_speed)
with data_helper, self.traffic_context(pkt_size, value):
with data_helper.measure_tot_stats():
@@ -1396,8 +1412,10 @@ class ProxBngProfileHelper(ProxProfileHelper):
time.sleep(3)
self.sut.stop(self.all_rx_cores)
- def run_test(self, pkt_size, duration, value, tolerated_loss=0.0):
- data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size, value, tolerated_loss)
+ def run_test(self, pkt_size, duration, value, tolerated_loss=0.0,
+ line_speed=(constants.ONE_GIGABIT_IN_BITS * constants.NIC_GBPS_DEFAULT)):
+ data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size,
+ value, tolerated_loss, line_speed)
with data_helper, self.traffic_context(pkt_size, value):
with data_helper.measure_tot_stats():
@@ -1583,8 +1601,10 @@ class ProxVpeProfileHelper(ProxProfileHelper):
time.sleep(3)
self.sut.stop(self.all_rx_cores)
- def run_test(self, pkt_size, duration, value, tolerated_loss=0.0):
- data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size, value, tolerated_loss)
+ def run_test(self, pkt_size, duration, value, tolerated_loss=0.0,
+ line_speed=(constants.ONE_GIGABIT_IN_BITS * constants.NIC_GBPS_DEFAULT)):
+ data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size,
+ value, tolerated_loss, line_speed)
with data_helper, self.traffic_context(pkt_size, value):
with data_helper.measure_tot_stats():
@@ -1772,8 +1792,10 @@ class ProxlwAFTRProfileHelper(ProxProfileHelper):
time.sleep(3)
self.sut.stop(self.all_rx_cores)
- def run_test(self, pkt_size, duration, value, tolerated_loss=0.0):
- data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size, value, tolerated_loss)
+ def run_test(self, pkt_size, duration, value, tolerated_loss=0.0,
+ line_speed=(constants.ONE_GIGABIT_IN_BITS * constants.NIC_GBPS_DEFAULT)):
+ data_helper = ProxDataHelper(self.vnfd_helper, self.sut, pkt_size,
+ value, tolerated_loss, line_speed)
with data_helper, self.traffic_context(pkt_size, value):
with data_helper.measure_tot_stats():
diff --git a/yardstick/network_services/vnf_generic/vnf/prox_vnf.py b/yardstick/network_services/vnf_generic/vnf/prox_vnf.py
index 2cdb3f904..285e08659 100644
--- a/yardstick/network_services/vnf_generic/vnf/prox_vnf.py
+++ b/yardstick/network_services/vnf_generic/vnf/prox_vnf.py
@@ -22,7 +22,7 @@ from yardstick.common.process import check_if_process_failed
from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxDpdkVnfSetupEnvHelper
from yardstick.network_services.vnf_generic.vnf.prox_helpers import ProxResourceHelper
from yardstick.network_services.vnf_generic.vnf.sample_vnf import SampleVNF
-from yardstick.network_services.constants import PROCESS_JOIN_TIMEOUT
+from yardstick.network_services import constants
LOG = logging.getLogger(__name__)
@@ -136,5 +136,5 @@ class ProxApproxVnf(SampleVNF):
self._tear_down()
if self._vnf_process is not None:
LOG.debug("joining before terminate %s", self._vnf_process.name)
- self._vnf_process.join(PROCESS_JOIN_TIMEOUT)
+ self._vnf_process.join(constants.PROCESS_JOIN_TIMEOUT)
self._vnf_process.terminate()
diff --git a/yardstick/network_services/vnf_generic/vnf/sample_vnf.py b/yardstick/network_services/vnf_generic/vnf/sample_vnf.py
index f16b4142d..77488c479 100644
--- a/yardstick/network_services/vnf_generic/vnf/sample_vnf.py
+++ b/yardstick/network_services/vnf_generic/vnf/sample_vnf.py
@@ -32,9 +32,7 @@ from yardstick.benchmark.contexts.base import Context
from yardstick.common import exceptions as y_exceptions
from yardstick.common.process import check_if_process_failed
from yardstick.common import utils
-from yardstick.network_services.constants import DEFAULT_VNF_TIMEOUT
-from yardstick.network_services.constants import PROCESS_JOIN_TIMEOUT
-from yardstick.network_services.constants import REMOTE_TMP
+from yardstick.network_services import constants
from yardstick.network_services.helpers.dpdkbindnic_helper import DpdkBindHelper, DpdkNode
from yardstick.network_services.helpers.samplevnf_helper import MultiPortConfig
from yardstick.network_services.helpers.samplevnf_helper import PortPairs
@@ -51,8 +49,8 @@ LOG = logging.getLogger(__name__)
class SetupEnvHelper(object):
- CFG_CONFIG = os.path.join(REMOTE_TMP, "sample_config")
- CFG_SCRIPT = os.path.join(REMOTE_TMP, "sample_script")
+ CFG_CONFIG = os.path.join(constants.REMOTE_TMP, "sample_config")
+ CFG_SCRIPT = os.path.join(constants.REMOTE_TMP, "sample_script")
DEFAULT_CONFIG_TPL_CFG = "sample.cfg"
PIPELINE_COMMAND = ''
VNF_TYPE = "SAMPLE"
@@ -81,7 +79,6 @@ class DpdkVnfSetupEnvHelper(SetupEnvHelper):
APP_NAME = 'DpdkVnf'
FIND_NET_CMD = "find /sys/class/net -lname '*{}*' -printf '%f'"
NR_HUGEPAGES_PATH = '/proc/sys/vm/nr_hugepages'
- HUGEPAGES_KB = 1024 * 1024 * 16
@staticmethod
def _update_packet_type(ip_pipeline_cfg, traffic_options):
@@ -120,7 +117,8 @@ class DpdkVnfSetupEnvHelper(SetupEnvHelper):
def _setup_hugepages(self):
meminfo = utils.read_meminfo(self.ssh_helper)
hp_size_kb = int(meminfo['Hugepagesize'])
- nr_hugepages = int(abs(self.HUGEPAGES_KB / hp_size_kb))
+ hugepages_gb = self.scenario_helper.all_options.get('hugepages_gb', 16)
+ nr_hugepages = int(abs(hugepages_gb * 1024 * 1024 / hp_size_kb))
self.ssh_helper.execute('echo %s | sudo tee %s' %
(nr_hugepages, self.NR_HUGEPAGES_PATH))
hp = six.BytesIO()
@@ -371,7 +369,7 @@ class ClientResourceHelper(ResourceHelper):
try:
return self.client.get_stats(*args, **kwargs)
except STLError:
- LOG.exception("TRex client not connected")
+ LOG.error('TRex client not connected')
return {}
def generate_samples(self, ports, key=None, default=None):
@@ -609,8 +607,10 @@ class ScenarioHelper(object):
@property
def timeout(self):
- return self.options.get('timeout', DEFAULT_VNF_TIMEOUT)
-
+ test_duration = self.scenario_cfg.get('runner', {}).get('duration',
+ self.options.get('timeout', constants.DEFAULT_VNF_TIMEOUT))
+ test_timeout = self.options.get('timeout', constants.DEFAULT_VNF_TIMEOUT)
+ return test_duration if test_duration > test_timeout else test_timeout
class SampleVNF(GenericVNF):
""" Class providing file-like API for generic VNF implementation """
@@ -794,7 +794,7 @@ class SampleVNF(GenericVNF):
if self._vnf_process is not None:
# be proper and join first before we kill
LOG.debug("joining before terminate %s", self._vnf_process.name)
- self._vnf_process.join(PROCESS_JOIN_TIMEOUT)
+ self._vnf_process.join(constants.PROCESS_JOIN_TIMEOUT)
self._vnf_process.terminate()
# no terminate children here because we share processes with tg
@@ -938,12 +938,12 @@ class SampleVNFTrafficGen(GenericTrafficGen):
if self._traffic_process is not None:
# be proper and try to join before terminating
LOG.debug("joining before terminate %s", self._traffic_process.name)
- self._traffic_process.join(PROCESS_JOIN_TIMEOUT)
+ self._traffic_process.join(constants.PROCESS_JOIN_TIMEOUT)
self._traffic_process.terminate()
if self._tg_process is not None:
# be proper and try to join before terminating
LOG.debug("joining before terminate %s", self._tg_process.name)
- self._tg_process.join(PROCESS_JOIN_TIMEOUT)
+ self._tg_process.join(constants.PROCESS_JOIN_TIMEOUT)
self._tg_process.terminate()
# no terminate children here because we share processes with vnf
diff --git a/yardstick/network_services/vnf_generic/vnf/vnf_ssh_helper.py b/yardstick/network_services/vnf_generic/vnf/vnf_ssh_helper.py
index 8e02cf3ac..de6fd9329 100644
--- a/yardstick/network_services/vnf_generic/vnf/vnf_ssh_helper.py
+++ b/yardstick/network_services/vnf_generic/vnf/vnf_ssh_helper.py
@@ -17,7 +17,7 @@ import os
from six.moves import StringIO
-from yardstick.network_services.constants import REMOTE_TMP
+from yardstick.network_services import constants
from yardstick.ssh import AutoConnectSSH
LOG = logging.getLogger(__name__)
@@ -46,7 +46,7 @@ class VnfSshHelper(AutoConnectSSH):
return self.get_class()(self.node, self.bin_path)
def upload_config_file(self, prefix, content):
- cfg_file = os.path.join(REMOTE_TMP, prefix)
+ cfg_file = os.path.join(constants.REMOTE_TMP, prefix)
LOG.debug(content)
file_obj = StringIO(content)
self.put_file_obj(file_obj, cfg_file)
diff --git a/yardstick/orchestrator/heat.py b/yardstick/orchestrator/heat.py
index 20be89f57..d69f86044 100644
--- a/yardstick/orchestrator/heat.py
+++ b/yardstick/orchestrator/heat.py
@@ -26,6 +26,7 @@ import shade
import yardstick.common.openstack_utils as op_utils
from yardstick.common import exceptions
from yardstick.common import template_format
+from yardstick.common import constants as consts
log = logging.getLogger(__name__)
@@ -333,21 +334,24 @@ name (i.e. %s).
}
}
- def add_port(self, name, network_name, subnet_name, vnic_type, sec_group_id=None,
+ def add_port(self, name, network, sec_group_id=None,
provider=None, allowed_address_pairs=None):
"""add to the template a named Neutron Port
"""
- log.debug("adding Neutron::Port '%s', network:'%s', subnet:'%s', vnic_type:'%s', "
- "secgroup:%s", name, network_name, subnet_name, vnic_type, sec_group_id)
+ net_is_existing = network.net_flags.get(consts.IS_EXISTING)
+ depends_on = [] if net_is_existing else [network.subnet_stack_name]
+ fixed_ips = [{'subnet': network.subnet}] if net_is_existing else [
+ {'subnet': {'get_resource': network.subnet_stack_name}}]
+ network_ = network.name if net_is_existing else {
+ 'get_resource': network.stack_name}
self.resources[name] = {
'type': 'OS::Neutron::Port',
- 'depends_on': [subnet_name],
+ 'depends_on': depends_on,
'properties': {
'name': name,
- 'binding:vnic_type': vnic_type,
- 'fixed_ips': [{'subnet': {'get_resource': subnet_name}}],
- 'network_id': {'get_resource': network_name},
- 'replacement_policy': 'AUTO',
+ 'binding:vnic_type': network.vnic_type,
+ 'fixed_ips': fixed_ips,
+ 'network': network_,
}
}
@@ -364,6 +368,8 @@ name (i.e. %s).
self.resources[name]['properties'][
'allowed_address_pairs'] = allowed_address_pairs
+ log.debug("adding Neutron::Port %s", self.resources[name])
+
self._template['outputs'][name] = {
'description': 'Address for interface %s' % name,
'value': {'get_attr': [name, 'fixed_ips', 0, 'ip_address']}
diff --git a/yardstick/service/__init__.py b/yardstick/service/__init__.py
new file mode 100644
index 000000000..1c3953de6
--- /dev/null
+++ b/yardstick/service/__init__.py
@@ -0,0 +1,12 @@
+##############################################################################
+# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+
+
+class Service(object):
+ pass
diff --git a/yardstick/service/environment.py b/yardstick/service/environment.py
new file mode 100644
index 000000000..324589f79
--- /dev/null
+++ b/yardstick/service/environment.py
@@ -0,0 +1,101 @@
+##############################################################################
+# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+import tempfile
+import logging
+import collections
+
+from oslo_serialization import jsonutils
+
+from yardstick.service import Service
+from yardstick.common.exceptions import MissingPodInfoError
+from yardstick.common.exceptions import UnsupportedPodFormatError
+from yardstick.common.ansible_common import AnsibleCommon
+
+LOG = logging.getLogger(__name__)
+
+
+class Environment(Service):
+ def __init__(self, pod=None):
+ super(Environment, self).__init__()
+ # pod can be a dict or a json format string
+ self.pod = pod
+
+ def get_sut_info(self):
+ temdir = tempfile.mkdtemp(prefix='sut')
+
+ nodes = self._load_pod_info()
+ ansible = AnsibleCommon(nodes=nodes)
+ ansible.gen_inventory_ini_dict()
+ sut_info = ansible.get_sut_info(temdir)
+
+ return self._format_sut_info(sut_info)
+
+ def _load_pod_info(self):
+ if self.pod is None:
+ raise MissingPodInfoError
+
+ if isinstance(self.pod, collections.Mapping):
+ try:
+ return self.pod['nodes']
+ except KeyError:
+ raise UnsupportedPodFormatError
+
+ try:
+ return jsonutils.loads(self.pod)['nodes']
+ except (ValueError, KeyError):
+ raise UnsupportedPodFormatError
+
+ def _format_sut_info(self, sut_info):
+ return {k: self._format_node_info(v) for k, v in sut_info.items()}
+
+ def _format_node_info(self, node_info):
+ info = []
+ facts = node_info.get('ansible_facts', {})
+
+ info.append(['hostname', facts.get('ansible_hostname')])
+
+ info.append(['product_name', facts.get('ansible_product_name')])
+ info.append(['product_version', facts.get('ansible_product_version')])
+
+ processors = facts.get('ansible_processor', [])
+ try:
+ processor_type = '{} {}'.format(processors[0], processors[1])
+ except IndexError:
+ LOG.exception('No Processor in SUT data')
+ processor_type = None
+
+ info.append(['processor_type', processor_type])
+ info.append(['architecture', facts.get('ansible_architecture')])
+ info.append(['processor_cores', facts.get('ansible_processor_cores')])
+ info.append(['processor_vcpus', facts.get('ansible_processor_vcpus')])
+
+ memory = facts.get('ansible_memtotal_mb')
+ memory = round(memory * 1.0 / 1024, 2) if memory else None
+ info.append(['memory', '{} GB'.format(memory)])
+
+ devices = facts.get('ansible_devices', {})
+ info.extend([self._get_device_info(k, v) for k, v in devices.items()])
+
+ lsb_description = facts.get('ansible_lsb', {}).get('description')
+ info.append(['OS', lsb_description])
+
+ interfaces = facts.get('ansible_interfaces')
+ info.append(['interfaces', interfaces])
+ if isinstance(interfaces, collections.Sequence):
+ info.extend([self._get_interface_info(facts, i) for i in interfaces])
+ info = [i for i in info if i]
+
+ return info
+
+ def _get_interface_info(self, facts, name):
+ mac = facts.get('ansible_{}'.format(name), {}).get('macaddress')
+ return [name, mac] if mac else []
+
+ def _get_device_info(self, name, info):
+ return ['disk_{}'.format(name), info.get('size')]
diff --git a/yardstick/tests/unit/apiserver/resources/v1/__init__.py b/yardstick/tests/unit/apiserver/resources/v1/__init__.py
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/yardstick/tests/unit/apiserver/resources/v1/__init__.py
diff --git a/yardstick/tests/unit/apiserver/resources/v1/test_testsuites.py b/yardstick/tests/unit/apiserver/resources/v1/test_testsuites.py
new file mode 100644
index 000000000..85c045f44
--- /dev/null
+++ b/yardstick/tests/unit/apiserver/resources/v1/test_testsuites.py
@@ -0,0 +1,35 @@
+##############################################################################
+# Copyright (c) 2018 Huawei Technologies Co.,Ltd and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+import mock
+
+import unittest
+
+from yardstick.tests.unit.apiserver import APITestCase
+from api.utils.thread import TaskThread
+
+
+class TestsuiteTestCase(APITestCase):
+
+ def test_run_test_suite(self):
+ if self.app is None:
+ unittest.skip('host config error')
+ return
+
+ TaskThread.start = mock.MagicMock()
+
+ url = 'yardstick/testsuites/action'
+ data = {
+ 'action': 'run_test_suite',
+ 'args': {
+ 'opts': {},
+ 'testsuite': 'opnfv_smoke'
+ }
+ }
+ resp = self._post(url, data)
+ self.assertEqual(resp.get('status'), 1)
diff --git a/yardstick/tests/unit/benchmark/contexts/test_heat.py b/yardstick/tests/unit/benchmark/contexts/test_heat.py
index f48d6f32c..625f97bf4 100644
--- a/yardstick/tests/unit/benchmark/contexts/test_heat.py
+++ b/yardstick/tests/unit/benchmark/contexts/test_heat.py
@@ -10,17 +10,16 @@
from collections import OrderedDict
from itertools import count
import logging
+import os
import mock
import unittest
-import shade
-
from yardstick.benchmark.contexts import base
from yardstick.benchmark.contexts import heat
from yardstick.benchmark.contexts import model
+from yardstick.common import constants as consts
from yardstick.common import exceptions as y_exc
-from yardstick.orchestrator import heat as orch_heat
from yardstick import ssh
@@ -62,12 +61,11 @@ class HeatContextTestCase(unittest.TestCase):
self.assertIsNone(self.test_context.heat_parameters)
self.assertIsNone(self.test_context.key_filename)
- @mock.patch.object(ssh.SSH, 'gen_keys')
@mock.patch('yardstick.benchmark.contexts.heat.PlacementGroup')
@mock.patch('yardstick.benchmark.contexts.heat.ServerGroup')
@mock.patch('yardstick.benchmark.contexts.heat.Network')
@mock.patch('yardstick.benchmark.contexts.heat.Server')
- def test_init(self, mock_server, mock_network, mock_sg, mock_pg, mock_ssh_gen_keys):
+ def test_init(self, mock_server, mock_network, mock_sg, mock_pg):
pgs = {'pgrp1': {'policy': 'availability'}}
sgs = {'servergroup1': {'policy': 'affinity'}}
@@ -105,8 +103,6 @@ class HeatContextTestCase(unittest.TestCase):
servers['baz'])
self.assertEqual(len(self.test_context.servers), 1)
- mock_ssh_gen_keys.assert_called()
-
def test_init_no_name_or_task_id(self):
attrs = {}
self.assertRaises(KeyError, self.test_context.init, attrs)
@@ -128,8 +124,7 @@ class HeatContextTestCase(unittest.TestCase):
self.assertEqual(self.test_context.name, 'foo')
self.assertEqual(self.test_context.assigned_name, 'foo')
- @mock.patch('yardstick.ssh.SSH.gen_keys')
- def test_init_no_setup_no_teardown(self, *args):
+ def test_init_no_setup_no_teardown(self):
attrs = {'name': 'foo',
'task_id': '1234567890',
@@ -222,9 +217,11 @@ class HeatContextTestCase(unittest.TestCase):
self.test_context._create_new_stack,
template)
- @mock.patch.object(orch_heat.HeatTemplate, 'add_keypair')
+ @mock.patch.object(os.path, 'exists', return_value=True)
+ @mock.patch.object(heat.HeatContext, '_add_resources_to_template')
@mock.patch.object(heat.HeatContext, '_create_new_stack')
- def test_deploy_stack_creation_failed(self, mock_create, *args):
+ def test_deploy_stack_creation_failed(self, mock_create,
+ mock_resources_template, mock_path_exists):
self.test_context._name = 'foo'
self.test_context._task_id = '1234567890'
self.test_context._name_task_id = 'foo-12345678'
@@ -232,8 +229,13 @@ class HeatContextTestCase(unittest.TestCase):
self.assertRaises(y_exc.HeatTemplateError,
self.test_context.deploy)
+ mock_path_exists.assert_called_once()
+ mock_resources_template.assert_called_once()
+
+ @mock.patch.object(os.path, 'exists', return_value=False)
+ @mock.patch.object(ssh.SSH, 'gen_keys')
@mock.patch('yardstick.benchmark.contexts.heat.HeatTemplate')
- def test_deploy(self, mock_template):
+ def test_deploy(self, mock_template, mock_genkeys, mock_path_exists):
self.test_context._name = 'foo'
self.test_context._task_id = '1234567890'
self.test_context._name_task_id = '{}-{}'.format(
@@ -247,46 +249,98 @@ class HeatContextTestCase(unittest.TestCase):
'/bar/baz/some-heat-file',
{'image': 'cirros'})
self.assertIsNotNone(self.test_context.stack)
+ key_filename = ''.join(
+ [consts.YARDSTICK_ROOT_PATH,
+ 'yardstick/resources/files/yardstick_key-',
+ self.test_context._name_task_id])
+ mock_genkeys.assert_called_once_with(key_filename)
+ mock_path_exists.assert_called_once_with(key_filename)
- # TODO: patch objects
@mock.patch.object(heat, 'HeatTemplate')
+ @mock.patch.object(os.path, 'exists', return_value=False)
+ @mock.patch.object(ssh.SSH, 'gen_keys')
@mock.patch.object(heat.HeatContext, '_retrieve_existing_stack')
@mock.patch.object(heat.HeatContext, '_create_new_stack')
- def test_deploy_no_setup(self, mock_create_new_stack, mock_retrieve_existing_stack, *args):
+ def test_deploy_no_setup(self, mock_create_new_stack,
+ mock_retrieve_existing_stack, mock_genkeys, mock_path_exists,
+ *args):
self.test_context._name = 'foo'
self.test_context._task_id = '1234567890'
- # Might be able to get rid of these
self.test_context.template_file = '/bar/baz/some-heat-file'
self.test_context.heat_parameters = {'image': 'cirros'}
self.test_context.get_neutron_info = mock.MagicMock()
self.test_context._flags.no_setup = True
self.test_context.deploy()
- # check that heat client is called...
mock_create_new_stack.assert_not_called()
mock_retrieve_existing_stack.assert_called_with(self.test_context.name)
self.assertIsNotNone(self.test_context.stack)
+ key_filename = ''.join(
+ [consts.YARDSTICK_ROOT_PATH,
+ 'yardstick/resources/files/yardstick_key-',
+ self.test_context._name])
+ mock_genkeys.assert_called_once_with(key_filename)
+ mock_path_exists.assert_called_once_with(key_filename)
- @mock.patch.object(shade, 'openstack_cloud')
- @mock.patch.object(heat.HeatTemplate, 'add_keypair')
+ @mock.patch.object(heat, 'HeatTemplate')
+ @mock.patch.object(os.path, 'exists', return_value=False)
+ @mock.patch.object(ssh.SSH, 'gen_keys')
@mock.patch.object(heat.HeatContext, '_create_new_stack')
- @mock.patch.object(heat.HeatStack, 'get')
+ @mock.patch.object(heat.HeatContext, '_retrieve_existing_stack',
+ return_value=None)
def test_deploy_try_retrieve_context_does_not_exist(self,
- mock_get_stack,
- mock_create_new_stack,
- *args):
+ mock_retrieve_stack, mock_create_new_stack, mock_genkeys,
+ mock_path_exists, *args):
self.test_context._name = 'demo'
self.test_context._task_id = '1234567890'
self.test_context._flags.no_setup = True
+ self.test_context.template_file = '/bar/baz/some-heat-file'
self.test_context.get_neutron_info = mock.MagicMock()
- # TODo: Check is this the right value to return, should it be None instead?
- mock_get_stack.return_value = []
-
self.test_context.deploy()
- mock_get_stack.assert_called()
+ mock_retrieve_stack.assert_called_once_with(self.test_context._name)
mock_create_new_stack.assert_called()
+ key_filename = ''.join(
+ [consts.YARDSTICK_ROOT_PATH,
+ 'yardstick/resources/files/yardstick_key-',
+ self.test_context._name])
+ mock_genkeys.assert_called_once_with(key_filename)
+ mock_path_exists.assert_called_once_with(key_filename)
+
+ @mock.patch.object(heat, 'HeatTemplate', return_value='heat_template')
+ @mock.patch.object(heat.HeatContext, '_add_resources_to_template')
+ @mock.patch.object(os.path, 'exists', return_value=False)
+ @mock.patch.object(ssh.SSH, 'gen_keys')
+ def test_deploy_ssh_key_before_adding_resources(self, mock_genkeys,
+ mock_path_exists, mock_add_resources, *args):
+ mock_manager = mock.Mock()
+ mock_manager.attach_mock(mock_add_resources,
+ '_add_resources_to_template')
+ mock_manager.attach_mock(mock_genkeys, 'gen_keys')
+ mock_manager.reset_mock()
+ self.test_context._name_task_id = 'demo-12345678'
+ self.test_context.get_neutron_info = mock.Mock()
+ with mock.patch.object(self.test_context, '_create_new_stack') as \
+ mock_create_stack, \
+ mock.patch.object(self.test_context, 'get_neutron_info') as \
+ mock_neutron_info:
+ self.test_context.deploy()
+
+ mock_neutron_info.assert_called_once()
+ mock_create_stack.assert_called_once()
+ key_filename = ''.join(
+ [consts.YARDSTICK_ROOT_PATH,
+ 'yardstick/resources/files/yardstick_key-',
+ self.test_context._name_task_id])
+ mock_genkeys.assert_called_once_with(key_filename)
+ mock_path_exists.assert_called_with(key_filename)
+
+ mock_call_gen_keys = mock.call.gen_keys(key_filename)
+ mock_call_add_resources = (
+ mock.call._add_resources_to_template('heat_template'))
+ self.assertTrue(mock_manager.mock_calls.index(mock_call_gen_keys) <
+ mock_manager.mock_calls.index(mock_call_add_resources))
def test_check_for_context(self):
pass
@@ -326,6 +380,7 @@ class HeatContextTestCase(unittest.TestCase):
u'e-network_id': u'net987',
}
server = mock.MagicMock()
+ server.private_ip = None
server.ports = OrderedDict([
('a', [{'stack_name': 'b', 'port': 'port_a'}]),
('c', [{'stack_name': 'd', 'port': 'port_c'},
@@ -365,7 +420,7 @@ class HeatContextTestCase(unittest.TestCase):
self.test_context.key_filename = 'foo/bar/foobar'
self.test_context.undeploy()
mock_delete_key.assert_called()
- self.assertTrue(mock_template.delete.called)
+ mock_template.delete.assert_called_once()
@mock.patch('yardstick.benchmark.contexts.heat.HeatTemplate')
def test_undeploy_no_teardown(self, mock_template):
diff --git a/yardstick/tests/unit/benchmark/contexts/test_kubernetes.py b/yardstick/tests/unit/benchmark/contexts/test_kubernetes.py
index 22153e4e8..4dd9d40d1 100644
--- a/yardstick/tests/unit/benchmark/contexts/test_kubernetes.py
+++ b/yardstick/tests/unit/benchmark/contexts/test_kubernetes.py
@@ -58,10 +58,10 @@ class KubernetesTestCase(unittest.TestCase):
mock_delete_services):
self.k8s_context.undeploy()
- self.assertTrue(mock_delete_ssh.called)
- self.assertTrue(mock_delete_rcs.called)
- self.assertTrue(mock_delete_pods.called)
- self.assertTrue(mock_delete_services.called)
+ mock_delete_ssh.assert_called_once()
+ mock_delete_rcs.assert_called_once()
+ mock_delete_pods.assert_called_once()
+ mock_delete_services.assert_called_once()
@mock.patch.object(kubernetes.KubernetesContext, '_create_services')
@mock.patch.object(kubernetes.KubernetesContext, '_wait_until_running')
@@ -77,11 +77,11 @@ class KubernetesTestCase(unittest.TestCase):
with mock.patch("yardstick.benchmark.contexts.kubernetes.time"):
self.k8s_context.deploy()
- self.assertTrue(mock_set_ssh_key.called)
- self.assertTrue(mock_create_rcs.called)
- self.assertTrue(mock_create_services.called)
- self.assertTrue(mock_get_rc_pods.called)
- self.assertTrue(mock_wait_until_running.called)
+ mock_set_ssh_key.assert_called_once()
+ mock_create_rcs.assert_called_once()
+ mock_create_services.assert_called_once()
+ mock_get_rc_pods.assert_called_once()
+ mock_wait_until_running.assert_called_once()
@mock.patch.object(kubernetes, 'paramiko', **{"resource_filename.return_value": ""})
@mock.patch.object(kubernetes, 'pkg_resources', **{"resource_filename.return_value": ""})
@@ -93,8 +93,8 @@ class KubernetesTestCase(unittest.TestCase):
self.k8s_context._set_ssh_key()
self.k8s_context._delete_ssh_key()
- self.assertTrue(mock_create.called)
- self.assertTrue(mock_delete.called)
+ mock_create.assert_called_once()
+ mock_delete.assert_called_once()
@mock.patch.object(kubernetes.k8s_utils, 'read_pod_status')
def test_wait_until_running(self, mock_read_pod_status):
@@ -136,34 +136,34 @@ class KubernetesTestCase(unittest.TestCase):
@mock.patch.object(kubernetes.KubernetesContext, '_create_rc')
def test_create_rcs(self, mock_create_rc):
self.k8s_context._create_rcs()
- self.assertTrue(mock_create_rc.called)
+ mock_create_rc.assert_called()
@mock.patch.object(kubernetes.k8s_utils, 'create_replication_controller')
def test_create_rc(self, mock_create_replication_controller):
self.k8s_context._create_rc({})
- self.assertTrue(mock_create_replication_controller.called)
+ mock_create_replication_controller.assert_called_once()
@mock.patch.object(kubernetes.KubernetesContext, '_delete_rc')
def test_delete_rcs(self, mock_delete_rc):
self.k8s_context._delete_rcs()
- self.assertTrue(mock_delete_rc.called)
+ mock_delete_rc.assert_called()
@mock.patch.object(kubernetes.k8s_utils, 'delete_replication_controller')
def test_delete_rc(self, mock_delete_replication_controller):
self.k8s_context._delete_rc({})
- self.assertTrue(mock_delete_replication_controller.called)
+ mock_delete_replication_controller.assert_called_once()
@mock.patch.object(kubernetes.k8s_utils, 'get_node_list')
def test_get_node_ip(self, mock_get_node_list):
self.k8s_context._get_node_ip()
- self.assertTrue(mock_get_node_list.called)
+ mock_get_node_list.assert_called_once()
@mock.patch('yardstick.orchestrator.kubernetes.ServiceObject.create')
def test_create_services(self, mock_create):
self.k8s_context._create_services()
- self.assertTrue(mock_create.called)
+ mock_create.assert_called()
@mock.patch('yardstick.orchestrator.kubernetes.ServiceObject.delete')
def test_delete_services(self, mock_delete):
self.k8s_context._delete_services()
- self.assertTrue(mock_delete.called)
+ mock_delete.assert_called()
diff --git a/yardstick/tests/unit/benchmark/contexts/test_model.py b/yardstick/tests/unit/benchmark/contexts/test_model.py
index 76c4da533..20cc00b4e 100644
--- a/yardstick/tests/unit/benchmark/contexts/test_model.py
+++ b/yardstick/tests/unit/benchmark/contexts/test_model.py
@@ -239,6 +239,7 @@ class ServerTestCase(unittest.TestCase):
mock_network.vnic_type = 'normal'
mock_network.subnet_stack_name = 'some-network-stack-subnet'
mock_network.provider = 'sriov'
+ mock_network.net_flags = {}
mock_network.external_network = 'ext_net'
mock_network.router = model.Router('some-router', 'some-network', self.mock_context,
'ext_net')
@@ -248,9 +249,7 @@ class ServerTestCase(unittest.TestCase):
mock_template.add_port.assert_called_with(
'some-server-some-network-port',
- mock_network.stack_name,
- mock_network.subnet_stack_name,
- mock_network.vnic_type,
+ mock_network,
sec_group_id=self.mock_context.secgroup_name,
provider=mock_network.provider,
allowed_address_pairs=mock_network.allowed_address_pairs)
@@ -511,6 +510,7 @@ class ServerTestCase(unittest.TestCase):
mock_network = mock.Mock()
mock_network.allowed_address_pairs = ["1", "2"]
mock_network.vnic_type = 'normal'
+ mock_network.net_flags = {}
mock_network.configure_mock(name='some-network', stack_name='some-network-stack',
subnet_stack_name='some-network-stack-subnet',
provider='some-provider')
@@ -520,9 +520,7 @@ class ServerTestCase(unittest.TestCase):
mock_template.add_port.assert_called_with(
'ServerFlavor-2-some-network-port',
- mock_network.stack_name,
- mock_network.subnet_stack_name,
- mock_network.vnic_type,
+ mock_network,
provider=mock_network.provider,
sec_group_id=self.mock_context.secgroup_name,
allowed_address_pairs=mock_network.allowed_address_pairs)
@@ -554,6 +552,7 @@ class ServerTestCase(unittest.TestCase):
mock_network.name = 'some-network'
mock_network.stack_name = 'some-network-stack'
mock_network.subnet_stack_name = 'some-network-stack-subnet'
+ mock_network.net_flags = {}
test_server._add_instance(mock_template, 'ServerFlavor-3',
[mock_network], 'hints')
diff --git a/yardstick/tests/unit/benchmark/contexts/test_node.py b/yardstick/tests/unit/benchmark/contexts/test_node.py
index 9761f6d53..8b232481b 100644
--- a/yardstick/tests/unit/benchmark/contexts/test_node.py
+++ b/yardstick/tests/unit/benchmark/contexts/test_node.py
@@ -176,7 +176,7 @@ class NodeContextTestCase(unittest.TestCase):
'type': 'script'
}
obj.deploy()
- self.assertTrue(dispatch_script_mock.called)
+ dispatch_script_mock.assert_called_once()
@mock.patch('{}.NodeContext._dispatch_ansible'.format(PREFIX))
def test_deploy_anisible(self, dispatch_ansible_mock):
@@ -186,7 +186,7 @@ class NodeContextTestCase(unittest.TestCase):
'type': 'ansible'
}
obj.deploy()
- self.assertTrue(dispatch_ansible_mock.called)
+ dispatch_ansible_mock.assert_called_once()
@mock.patch('{}.NodeContext._dispatch_script'.format(PREFIX))
def test_undeploy(self, dispatch_script_mock):
@@ -195,7 +195,7 @@ class NodeContextTestCase(unittest.TestCase):
'type': 'script'
}
obj.undeploy()
- self.assertTrue(dispatch_script_mock.called)
+ dispatch_script_mock.assert_called_once()
@mock.patch('{}.NodeContext._dispatch_ansible'.format(PREFIX))
def test_undeploy_anisble(self, dispatch_ansible_mock):
@@ -204,7 +204,7 @@ class NodeContextTestCase(unittest.TestCase):
'type': 'ansible'
}
obj.undeploy()
- self.assertTrue(dispatch_ansible_mock.called)
+ dispatch_ansible_mock.assert_called_once()
@mock.patch('{}.ssh.SSH._put_file_shell'.format(PREFIX))
@mock.patch('{}.ssh.SSH.execute'.format(PREFIX))
@@ -224,8 +224,8 @@ class NodeContextTestCase(unittest.TestCase):
execute_mock.return_value = (0, '', '')
obj._execute_remote_script('node5', info)
- self.assertTrue(put_file_mock.called)
- self.assertTrue(execute_mock.called)
+ put_file_mock.assert_called_once()
+ execute_mock.assert_called()
@mock.patch('{}.NodeContext._execute_local_script'.format(PREFIX))
def test_execute_script_local(self, local_execute_mock):
@@ -234,7 +234,7 @@ class NodeContextTestCase(unittest.TestCase):
obj = node.NodeContext()
self.addCleanup(obj._delete_context)
obj._execute_script(node_name, info)
- self.assertTrue(local_execute_mock.called)
+ local_execute_mock.assert_called_once()
@mock.patch('{}.NodeContext._execute_remote_script'.format(PREFIX))
def test_execute_script_remote(self, remote_execute_mock):
@@ -243,7 +243,7 @@ class NodeContextTestCase(unittest.TestCase):
obj = node.NodeContext()
self.addCleanup(obj._delete_context)
obj._execute_script(node_name, info)
- self.assertTrue(remote_execute_mock.called)
+ remote_execute_mock.assert_called_once()
def test_get_script(self):
script_args = 'hello.bash'
@@ -276,7 +276,7 @@ class NodeContextTestCase(unittest.TestCase):
'pwd': 'ubuntu',
}]
obj._get_client(node_name_args)
- self.assertTrue(wait_mock.called)
+ wait_mock.assert_called_once()
def test_get_server(self):
self.test_context.init(self.attrs)
diff --git a/yardstick/tests/unit/benchmark/core/test_task.py b/yardstick/tests/unit/benchmark/core/test_task.py
index 82a90b172..9e8e4e9f7 100644
--- a/yardstick/tests/unit/benchmark/core/test_task.py
+++ b/yardstick/tests/unit/benchmark/core/test_task.py
@@ -153,7 +153,7 @@ class TaskTestCase(unittest.TestCase):
runner.get_result.return_value = []
mock_base_runner.Runner.get.return_value = runner
t._run([scenario], False, "yardstick.out")
- self.assertTrue(runner.run.called)
+ runner.run.assert_called_once()
@mock.patch.object(os, 'environ')
def test_check_precondition(self, mock_os_environ):
@@ -421,6 +421,34 @@ key2:
self.parser._change_node_names(scenario, [my_context])
self.assertEqual(scenario, expected_scenario)
+ def test__change_node_names_options_empty(self):
+ ctx_attrs = {
+ 'name': 'demo',
+ 'task_id': '1234567890'
+ }
+
+ my_context = dummy.DummyContext()
+ my_context.init(ctx_attrs)
+ scenario = copy.deepcopy(self.scenario)
+ scenario['options'] = None
+
+ self.parser._change_node_names(scenario, [my_context])
+ self.assertIsNone(scenario['options'])
+
+ def test__change_node_names_options_server_name_empty(self):
+ ctx_attrs = {
+ 'name': 'demo',
+ 'task_id': '1234567890'
+ }
+
+ my_context = dummy.DummyContext()
+ my_context.init(ctx_attrs)
+ scenario = copy.deepcopy(self.scenario)
+ scenario['options']['server_name'] = None
+
+ self.parser._change_node_names(scenario, [my_context])
+ self.assertIsNone(scenario['options']['server_name'])
+
def test__parse_tasks(self):
task_obj = task.Task()
_uuid = uuid.uuid4()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_add_memory_load.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_add_memory_load.py
index 98d967f2b..af4f0c8ab 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_add_memory_load.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_add_memory_load.py
@@ -27,7 +27,7 @@ class AddMemoryLoadTestCase(unittest.TestCase):
mock_from_node().execute.return_value = (0, '0 2048 512', '')
obj = AddMemoryLoad(scenario_cfg, context_cfg)
obj.run({})
- self.assertTrue(mock_from_node.called)
+ mock_from_node.assert_called()
@mock.patch('yardstick.ssh.SSH.from_node')
def test_add_memory_load_without_load(self, mock_from_node):
@@ -41,7 +41,7 @@ class AddMemoryLoadTestCase(unittest.TestCase):
}
obj = AddMemoryLoad(scenario_cfg, context_cfg)
obj.run({})
- self.assertTrue(mock_from_node.called)
+ mock_from_node.assert_called_once()
@mock.patch('yardstick.ssh.SSH.from_node')
def test_add_memory_load_without_args(self, mock_from_node):
@@ -54,4 +54,4 @@ class AddMemoryLoadTestCase(unittest.TestCase):
}
obj = AddMemoryLoad(scenario_cfg, context_cfg)
obj.run({})
- self.assertTrue(mock_from_node.called)
+ mock_from_node.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_attach_volume.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_attach_volume.py
index a61195f66..2964ecc14 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_attach_volume.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_attach_volume.py
@@ -23,4 +23,4 @@ class AttachVolumeTestCase(unittest.TestCase):
args = {"options": options}
obj = AttachVolume(args, {})
obj.run({})
- self.assertTrue(mock_attach_server_volume.called)
+ mock_attach_server_volume.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_check_numa_info.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_check_numa_info.py
index a50e752fa..270c9d3c9 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_check_numa_info.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_check_numa_info.py
@@ -19,7 +19,7 @@ class CheckNumaInfoTestCase(unittest.TestCase):
scenario_cfg = {'info1': {}, 'info2': {}}
obj = CheckNumaInfo(scenario_cfg, {})
obj.run({})
- self.assertTrue(mock_check_vm2.called)
+ mock_check_vm2.assert_called_once()
def test_check_vm2_status_length_eq_1(self):
info1 = {
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_flavor.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_flavor.py
index 663ca5d5b..0b175fae8 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_flavor.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_flavor.py
@@ -26,4 +26,4 @@ class CreateFlavorTestCase(unittest.TestCase):
args = {"options": options}
obj = CreateFlavor(args, {})
obj.run({})
- self.assertTrue(mock_create_flavor.called)
+ mock_create_flavor.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_network.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_network.py
index ad4adeeb2..17a4ef2e1 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_network.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_network.py
@@ -6,25 +6,52 @@
# which accompanies this distribution, and is available at
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
+
+from oslo_utils import uuidutils
import unittest
import mock
-from yardstick.benchmark.scenarios.lib.create_network import CreateNetwork
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
+from yardstick.benchmark.scenarios.lib import create_network
class CreateNetworkTestCase(unittest.TestCase):
- @mock.patch('yardstick.common.openstack_utils.get_neutron_client')
- @mock.patch('yardstick.common.openstack_utils.create_neutron_net')
- def test_create_network(self, mock_get_neutron_client, mock_create_neutron_net):
- options = {
- 'openstack_paras': {
- 'name': 'yardstick_net',
- 'admin_state_up': 'True'
- }
- }
- args = {"options": options}
- obj = CreateNetwork(args, {})
- obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_create_neutron_net.called)
+ def setUp(self):
+
+ self._mock_create_neutron_net = mock.patch.object(
+ openstack_utils, 'create_neutron_net')
+ self.mock_create_neutron_net = self._mock_create_neutron_net.start()
+ self._mock_get_shade_client = mock.patch.object(
+ openstack_utils, 'get_shade_client')
+ self.mock_get_shade_client = self._mock_get_shade_client.start()
+ self._mock_log = mock.patch.object(create_network, 'LOG')
+ self.mock_log = self._mock_log.start()
+ self.args = {'options': {'network_name': 'yardstick_net'}}
+ self.result = {}
+
+ self._cnet_obj = create_network.CreateNetwork(self.args, mock.ANY)
+ self.addCleanup(self._stop_mock)
+
+ def _stop_mock(self):
+ self._mock_create_neutron_net.stop()
+ self._mock_get_shade_client.stop()
+ self._mock_log.stop()
+
+ def test_run(self):
+ _uuid = uuidutils.generate_uuid()
+ self._cnet_obj.scenario_cfg = {'output': 'id'}
+ self.mock_create_neutron_net.return_value = _uuid
+ output = self._cnet_obj.run(self.result)
+ self.assertEqual({"network_create": 1}, self.result)
+ self.assertEqual({'id': _uuid}, output)
+ self.mock_log.info.asset_called_once_with('Create network successful!')
+
+ def test_run_fail_exception(self):
+ self.mock_create_neutron_net.return_value = None
+ with self.assertRaises(exceptions.ScenarioCreateNetworkError):
+ self._cnet_obj.run(self.result)
+ self.assertEqual({"network_create": 0}, self.result)
+ self.mock_log.error.assert_called_once_with(
+ 'Create network failed!')
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_port.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_port.py
index 9a1611c3d..bea02a630 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_port.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_port.py
@@ -24,4 +24,4 @@ class CreatePortTestCase(unittest.TestCase):
args = {"options": options}
obj = CreatePort(args, {})
obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
+ mock_get_neutron_client.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_router.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_router.py
index 107921403..8d6f119ab 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_router.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_router.py
@@ -6,25 +6,52 @@
# which accompanies this distribution, and is available at
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
+
+from oslo_utils import uuidutils
import unittest
import mock
-from yardstick.benchmark.scenarios.lib.create_router import CreateRouter
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
+from yardstick.benchmark.scenarios.lib import create_router
class CreateRouterTestCase(unittest.TestCase):
- @mock.patch('yardstick.common.openstack_utils.get_neutron_client')
- @mock.patch('yardstick.common.openstack_utils.create_neutron_router')
- def test_create_router(self, mock_get_neutron_client, mock_create_neutron_router):
- options = {
- 'openstack_paras': {
- 'admin_state_up': 'True',
- 'name': 'yardstick_router'
- }
- }
- args = {"options": options}
- obj = CreateRouter(args, {})
- obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_create_neutron_router.called)
+ def setUp(self):
+
+ self._mock_create_neutron_router = mock.patch.object(
+ openstack_utils, 'create_neutron_router')
+ self.mock_create_neutron_router = (
+ self._mock_create_neutron_router.start())
+ self._mock_get_shade_client = mock.patch.object(
+ openstack_utils, 'get_shade_client')
+ self.mock_get_shade_client = self._mock_get_shade_client.start()
+ self._mock_log = mock.patch.object(create_router, 'LOG')
+ self.mock_log = self._mock_log.start()
+ self.args = {'options': {'name': 'yardstick_net'}}
+ self.result = {}
+
+ self.crouter_obj = create_router.CreateRouter(self.args, mock.ANY)
+ self.addCleanup(self._stop_mock)
+
+ def _stop_mock(self):
+ self._mock_create_neutron_router.stop()
+ self._mock_get_shade_client.stop()
+ self._mock_log.stop()
+
+ def test_run(self):
+ _uuid = uuidutils.generate_uuid()
+ self.crouter_obj.scenario_cfg = {'output': 'id'}
+ self.mock_create_neutron_router.return_value = _uuid
+ output = self.crouter_obj.run(self.result)
+ self.assertEqual({"router_create": 1}, self.result)
+ self.assertEqual({'id': _uuid}, output)
+ self.mock_log.info.asset_called_once_with('Create router successful!')
+
+ def test_run_fail(self):
+ self.mock_create_neutron_router.return_value = None
+ with self.assertRaises(exceptions.ScenarioCreateRouterError):
+ self.crouter_obj.run(self.result)
+ self.assertEqual({"router_create": 0}, self.result)
+ self.mock_log.error.assert_called_once_with('Create router failed!')
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_sec_group.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_sec_group.py
index b55767360..21158ab17 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_sec_group.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_sec_group.py
@@ -26,5 +26,5 @@ class CreateSecGroupTestCase(unittest.TestCase):
args = {"options": options}
obj = CreateSecgroup(args, {})
obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_create_security_group_full.called)
+ mock_get_neutron_client.assert_called_once()
+ mock_create_security_group_full.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_server.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_server.py
index faee98fd1..9d6d8cb1b 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_server.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_server.py
@@ -28,7 +28,7 @@ class CreateServerTestCase(unittest.TestCase):
}
obj = CreateServer(scenario_cfg, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_get_glance_client.called)
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_create_instance_and_wait_for_active.called)
+ mock_get_nova_client.assert_called_once()
+ mock_get_glance_client.assert_called_once()
+ mock_get_neutron_client.assert_called_once()
+ mock_create_instance_and_wait_for_active.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_subnet.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_subnet.py
index 1536e83e0..856e985c4 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_subnet.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_subnet.py
@@ -6,27 +6,53 @@
# which accompanies this distribution, and is available at
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
+
+from oslo_utils import uuidutils
import unittest
import mock
-from yardstick.benchmark.scenarios.lib.create_subnet import CreateSubnet
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
+from yardstick.benchmark.scenarios.lib import create_subnet
class CreateSubnetTestCase(unittest.TestCase):
- @mock.patch('yardstick.common.openstack_utils.get_neutron_client')
- @mock.patch('yardstick.common.openstack_utils.create_neutron_subnet')
- def test_create_subnet(self, mock_get_neutron_client, mock_create_neutron_subnet):
- options = {
- 'openstack_paras': {
- 'network_id': '123-123-123',
- 'name': 'yardstick_subnet',
- 'cidr': '10.10.10.0/24',
- 'ip_version': '4'
- }
- }
- args = {"options": options}
- obj = CreateSubnet(args, {})
- obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_create_neutron_subnet.called)
+ def setUp(self):
+
+ self._mock_create_neutron_subnet = mock.patch.object(
+ openstack_utils, 'create_neutron_subnet')
+ self.mock_create_neutron_subnet = (
+ self._mock_create_neutron_subnet.start())
+ self._mock_get_shade_client = mock.patch.object(
+ openstack_utils, 'get_shade_client')
+ self.mock_get_shade_client = self._mock_get_shade_client.start()
+ self._mock_log = mock.patch.object(create_subnet, 'LOG')
+ self.mock_log = self._mock_log.start()
+ self.args = {'options': {'network_name_or_id': 'yardstick_net'}}
+ self.result = {"subnet_create": 0}
+
+ self._csubnet_obj = create_subnet.CreateSubnet(self.args, mock.ANY)
+ self.addCleanup(self._stop_mock)
+
+ def _stop_mock(self):
+ self._mock_create_neutron_subnet.stop()
+ self._mock_get_shade_client.stop()
+ self._mock_log.stop()
+
+ def test_run(self):
+ _uuid = uuidutils.generate_uuid()
+ self._csubnet_obj.scenario_cfg = {'output': 'id'}
+ self.mock_create_neutron_subnet.return_value = _uuid
+ output = self._csubnet_obj.run(self.result)
+ self.assertDictEqual({"subnet_create": 1}, self.result)
+ self.assertDictEqual({'id': _uuid}, output)
+ self.mock_log.info.asset_called_once_with('Create subnet successful!')
+
+ def test_run_fail(self):
+ self._csubnet_obj.scenario_cfg = {'output': 'id'}
+ self.mock_create_neutron_subnet.return_value = None
+ with self.assertRaises(exceptions.ScenarioCreateSubnetError):
+ self._csubnet_obj.run(self.result)
+ self.assertDictEqual({"subnet_create": 0}, self.result)
+ self.mock_log.error.assert_called_once_with('Create subnet failed!')
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_volume.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_volume.py
index 4bfec3252..30333dda8 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_create_volume.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_create_volume.py
@@ -94,7 +94,7 @@ class CreateVolumeTestCase(unittest.TestCase):
args = {"options": options}
scenario = create_volume.CreateVolume(args, {})
scenario.run()
- self.assertTrue(mock_create_volume.called)
- self.assertTrue(mock_image_id.called)
- self.assertTrue(mock_get_glance_client.called)
- self.assertTrue(mock_get_cinder_client.called)
+ mock_create_volume.assert_called_once()
+ mock_image_id.assert_called_once()
+ mock_get_glance_client.assert_called_once()
+ mock_get_cinder_client.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_flavor.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_flavor.py
index e345afe3c..24dbf8a16 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_flavor.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_flavor.py
@@ -23,5 +23,5 @@ class DeleteFlavorTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteFlavor(args, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_delete_flavor.called)
+ mock_get_nova_client.assert_called_once()
+ mock_delete_flavor.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_floating_ip.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_floating_ip.py
index be997199c..3185ec59f 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_floating_ip.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_floating_ip.py
@@ -23,5 +23,5 @@ class DeleteFloatingIpTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteFloatingIp(args, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_delete_floating_ip.called)
+ mock_get_nova_client.assert_called_once()
+ mock_delete_floating_ip.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_image.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_image.py
index eb3f9fc85..e382d46fa 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_image.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_image.py
@@ -24,6 +24,6 @@ class DeleteImageTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteImage(args, {})
obj.run({})
- self.assertTrue(mock_delete_image.called)
- self.assertTrue(mock_image_id.called)
- self.assertTrue(mock_get_glance_client.called)
+ mock_delete_image.assert_called_once()
+ mock_image_id.assert_called_once()
+ mock_get_glance_client.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_keypair.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_keypair.py
index 38cc929c0..6e790ba90 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_keypair.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_keypair.py
@@ -23,5 +23,5 @@ class DeleteKeypairTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteKeypair(args, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_delete_keypair.called)
+ mock_get_nova_client.assert_called_once()
+ mock_delete_keypair.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_port.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_port.py
index 008ed9168..9fd318580 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_port.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_port.py
@@ -22,4 +22,4 @@ class DeletePortTestCase(unittest.TestCase):
args = {"options": options}
obj = DeletePort(args, {})
obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
+ mock_get_neutron_client.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router.py
index 9b31566ac..b76100f19 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router.py
@@ -6,22 +6,49 @@
# which accompanies this distribution, and is available at
# http://www.apache.org/licenses/LICENSE-2.0
##############################################################################
+
+from oslo_utils import uuidutils
import unittest
import mock
-from yardstick.benchmark.scenarios.lib.delete_router import DeleteRouter
+from yardstick.common import openstack_utils
+from yardstick.common import exceptions
+from yardstick.benchmark.scenarios.lib import delete_router
class DeleteRouterTestCase(unittest.TestCase):
- @mock.patch('yardstick.common.openstack_utils.get_neutron_client')
- @mock.patch('yardstick.common.openstack_utils.delete_neutron_router')
- def test_delete_router(self, mock_get_neutron_client, mock_delete_neutron_router):
- options = {
- 'router_id': '123-123-123'
- }
- args = {"options": options}
- obj = DeleteRouter(args, {})
- obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_delete_neutron_router.called)
+ def setUp(self):
+ self._mock_delete_neutron_router = mock.patch.object(
+ openstack_utils, 'delete_neutron_router')
+ self.mock_delete_neutron_router = (
+ self._mock_delete_neutron_router.start())
+ self._mock_get_shade_client = mock.patch.object(
+ openstack_utils, 'get_shade_client')
+ self.mock_get_shade_client = self._mock_get_shade_client.start()
+ self._mock_log = mock.patch.object(delete_router, 'LOG')
+ self.mock_log = self._mock_log.start()
+ self.args = {'options': {'router_id': uuidutils.generate_uuid()}}
+ self.result = {"delete_router": 0}
+
+ self._del_obj = delete_router.DeleteRouter(self.args, mock.ANY)
+
+ self.addCleanup(self._stop_mock)
+
+ def _stop_mock(self):
+ self._mock_delete_neutron_router.stop()
+ self._mock_get_shade_client.stop()
+ self._mock_log.stop()
+
+ def test_run(self):
+ self.mock_delete_neutron_router.return_value = True
+ self.assertIsNone(self._del_obj.run(self.result))
+ self.assertEqual({"delete_router": 1}, self.result)
+ self.mock_log.info.assert_called_once_with("Delete router successful!")
+
+ def test_run_fail(self):
+ self.mock_delete_neutron_router.return_value = False
+ with self.assertRaises(exceptions.ScenarioDeleteRouterError):
+ self._del_obj.run(self.result)
+ self.assertEqual({"delete_router": 0}, self.result)
+ self.mock_log.error.assert_called_once_with("Delete router failed!")
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_gateway.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_gateway.py
index e19c38d47..0c9cf7c17 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_gateway.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_gateway.py
@@ -23,5 +23,5 @@ class DeleteRouterGatewayTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteRouterGateway(args, {})
obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_remove_gateway_router.called)
+ mock_get_neutron_client.assert_called_once()
+ mock_remove_gateway_router.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_interface.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_interface.py
index 6c4fdd5e3..9e9c5a5b6 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_interface.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_router_interface.py
@@ -24,5 +24,5 @@ class DeleteRouterInterfaceTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteRouterInterface(args, {})
obj.run({})
- self.assertTrue(mock_get_neutron_client.called)
- self.assertTrue(mock_remove_interface_router.called)
+ mock_get_neutron_client.assert_called_once()
+ mock_remove_interface_router.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_server.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_server.py
index dedce2d4a..eee565de7 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_server.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_server.py
@@ -23,5 +23,5 @@ class DeleteServerTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteServer(args, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_delete_instance.called)
+ mock_get_nova_client.assert_called_once()
+ mock_delete_instance.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_volume.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_volume.py
index 2ea82e2a4..93f76e819 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_volume.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_delete_volume.py
@@ -23,5 +23,5 @@ class DeleteVolumeTestCase(unittest.TestCase):
args = {"options": options}
obj = DeleteVolume(args, {})
obj.run({})
- self.assertTrue(mock_get_cinder_client.called)
- self.assertTrue(mock_delete_volume.called)
+ mock_get_cinder_client.assert_called_once()
+ mock_delete_volume.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_detach_volume.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_detach_volume.py
index 34fbac68c..9794d2129 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_detach_volume.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_detach_volume.py
@@ -23,4 +23,4 @@ class DetachVolumeTestCase(unittest.TestCase):
args = {"options": options}
obj = DetachVolume(args, {})
obj.run({})
- self.assertTrue(mock_detach_volume.called)
+ mock_detach_volume.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_flavor.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_flavor.py
index e9025f33f..15a6f7c8f 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_flavor.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_flavor.py
@@ -22,4 +22,4 @@ class GetFlavorTestCase(unittest.TestCase):
args = {"options": options}
obj = GetFlavor(args, {})
obj.run({})
- self.assertTrue(mock_get_flavor_by_name.called)
+ mock_get_flavor_by_name.assert_called_once()
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_migrate_target_host.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_migrate_target_host.py
index aa9f63e26..879b2b988 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_migrate_target_host.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_migrate_target_host.py
@@ -25,9 +25,9 @@ class GetMigrateTargetHostTestCase(unittest.TestCase):
mock_get_nova_client):
obj = GetMigrateTargetHost({}, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_get_current_host_name.called)
- self.assertTrue(mock_get_migrate_host.called)
+ mock_get_nova_client.assert_called_once()
+ mock_get_current_host_name.assert_called_once()
+ mock_get_migrate_host.assert_called_once()
@mock.patch('{}.openstack_utils.get_nova_client'.format(BASE))
def test_get_migrate_host(self, mock_get_nova_client):
@@ -39,5 +39,5 @@ class GetMigrateTargetHostTestCase(unittest.TestCase):
mock_get_nova_client().hosts.list_all.return_value = [A('compute')]
obj = GetMigrateTargetHost({}, {})
host = obj._get_migrate_host('host5')
- self.assertTrue(mock_get_nova_client.called)
+ mock_get_nova_client.assert_called()
self.assertEqual(host, 'host4')
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_numa_info.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_numa_info.py
index 4b2132c2c..bea978b8a 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_numa_info.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_numa_info.py
@@ -44,8 +44,8 @@ class GetNumaInfoTestCase(unittest.TestCase):
}
obj = GetNumaInfo(scenario_cfg, {})
obj.run({})
- self.assertTrue(mock_get_current_host_name.called)
- self.assertTrue(mock_check_numa_node.called)
+ mock_get_current_host_name.assert_called_once()
+ mock_check_numa_node.assert_called_once()
@mock.patch('yardstick.ssh.SSH.from_node')
@mock.patch('{}.GetNumaInfo._get_current_host_name'.format(BASE))
diff --git a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_server.py b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_server.py
index 97b81ed60..83ec903bc 100644
--- a/yardstick/tests/unit/benchmark/scenarios/lib/test_get_server.py
+++ b/yardstick/tests/unit/benchmark/scenarios/lib/test_get_server.py
@@ -25,8 +25,8 @@ class GetServerTestCase(unittest.TestCase):
}
obj = GetServer(scenario_cfg, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
- self.assertTrue(mock_get_server_by_name.called)
+ mock_get_nova_client.assert_called_once()
+ mock_get_server_by_name.assert_called_once()
@mock.patch('yardstick.common.openstack_utils.get_nova_client')
def test_get_server_with_id(self, mock_get_nova_client):
@@ -39,4 +39,4 @@ class GetServerTestCase(unittest.TestCase):
mock_get_nova_client().servers.get.return_value = None
obj = GetServer(scenario_cfg, {})
obj.run({})
- self.assertTrue(mock_get_nova_client.called)
+ mock_get_nova_client.assert_called()
diff --git a/yardstick/tests/unit/benchmark/scenarios/networking/test_iperf3.py b/yardstick/tests/unit/benchmark/scenarios/networking/test_iperf3.py
index d6636383a..74144afd5 100644
--- a/yardstick/tests/unit/benchmark/scenarios/networking/test_iperf3.py
+++ b/yardstick/tests/unit/benchmark/scenarios/networking/test_iperf3.py
@@ -65,7 +65,7 @@ class IperfTestCase(unittest.TestCase):
p.target = mock_ssh.SSH.from_node()
p.teardown()
- self.assertTrue(mock_ssh.SSH.from_node().close.called)
+ mock_ssh.SSH.from_node().close.assert_called()
mock_ssh.SSH.from_node().execute.assert_called_with("pkill iperf3")
def test_iperf_successful_no_sla(self, mock_ssh):
diff --git a/yardstick/tests/unit/benchmark/scenarios/networking/test_moongen_testpmd.py b/yardstick/tests/unit/benchmark/scenarios/networking/test_moongen_testpmd.py
new file mode 100644
index 000000000..620155c7e
--- /dev/null
+++ b/yardstick/tests/unit/benchmark/scenarios/networking/test_moongen_testpmd.py
@@ -0,0 +1,353 @@
+#!/usr/bin/env python
+
+# Copyright 2017 Nokia
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# Unittest for yardstick.benchmark.scenarios.networking.MoongenTestPMD
+
+from __future__ import absolute_import
+try:
+ from unittest import mock
+except ImportError:
+ import mock
+import unittest
+
+from yardstick.benchmark.scenarios.networking import moongen_testpmd
+
+
+@mock.patch('yardstick.benchmark.scenarios.networking.moongen_testpmd.subprocess')
+class MoongenTestPMDTestCase(unittest.TestCase):
+
+ def setUp(self):
+ self.ctx = {
+ "host": {
+ "ip": "10.229.47.137",
+ "user": "ubuntu",
+ "password": "ubuntu",
+ },
+ }
+ self.TestPMDargs = {
+ 'task_id': "1234-5678",
+ 'options': {
+ 'multistream': 1,
+ 'frame_size': 1024,
+ 'testpmd_queue': 2,
+ 'trafficgen_port1': 'ens5',
+ 'trafficgen_port2': 'ens6',
+ 'moongen_host_user': 'root',
+ 'moongen_host_passwd': 'root',
+ 'moongen_host_ip': '10.5.201.151',
+ 'moongen_dir': '/home/lua-trafficgen',
+ 'moongen_runBidirec': 'true',
+ 'Package_Loss': 0,
+ 'SearchRuntime': 60,
+ 'moongen_port1_mac': '88:cf:98:2f:4d:ed',
+ 'moongen_port2_mac': '88:cf:98:2f:4d:ee',
+ 'forward_type': 'testpmd',
+ },
+ 'sla': {
+ 'metrics': 'throughput_rx_mpps',
+ 'throughput_rx_mpps': 0.5,
+ 'action': 'monitor',
+ }
+ }
+ self.L2fwdargs = {
+ 'task_id': "1234-5678",
+ 'options': {
+ 'multistream': 1,
+ 'frame_size': 1024,
+ 'testpmd_queue': 2,
+ 'trafficgen_port1': 'ens5',
+ 'trafficgen_port2': 'ens6',
+ 'moongen_host_user': 'root',
+ 'moongen_host_passwd': 'root',
+ 'moongen_host_ip': '10.5.201.151',
+ 'moongen_dir': '/home/lua-trafficgen',
+ 'moongen_runBidirec': 'true',
+ 'Package_Loss': 0,
+ 'SearchRuntime': 60,
+ 'moongen_port1_mac': '88:cf:98:2f:4d:ed',
+ 'moongen_port2_mac': '88:cf:98:2f:4d:ee',
+ 'forward_type': 'l2fwd',
+ },
+ 'sla': {
+ 'metrics': 'throughput_rx_mpps',
+ 'throughput_rx_mpps': 0.5,
+ 'action': 'monitor',
+ }
+ }
+
+ self._mock_ssh = mock.patch(
+ 'yardstick.benchmark.scenarios.networking.moongen_testpmd.ssh')
+ self.mock_ssh = self._mock_ssh.start()
+
+ self.addCleanup(self._cleanup)
+
+ def _cleanup(self):
+ self._mock_ssh.stop()
+
+ def test_MoongenTestPMD_setup(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ def test_MoongenTestPMD_teardown(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ p.teardown()
+ self.assertFalse(p.setup_done)
+
+ def test_MoongenTestPMD_l2fwd_is_forward_setup_no(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.L2fwdargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # is_dpdk_setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+
+ result = p._is_forward_setup()
+ self.assertFalse(result)
+
+ def test_MoongenTestPMD_l2fwd_is_forward_setup_yes(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.L2fwdargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # is_dpdk_setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, 'dummy', '')
+
+ result = p._is_forward_setup()
+ self.assertTrue(result)
+
+ def test_MoongenTestPMD_testpmd_is_forward_setup_no(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # is_dpdk_setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, 'dummy', '')
+
+ result = p._is_forward_setup()
+ self.assertFalse(result)
+
+ def test_MoongenTestPMD_testpmd_is_forward_setup_yes(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # is_dpdk_setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+
+ result = p._is_forward_setup()
+ self.assertTrue(result)
+
+ @mock.patch('time.sleep')
+ def test_MoongenTestPMD_testpmd_forward_setup_first(self, _, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # is_dpdk_setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, 'dummy', '')
+
+ p.forward_setup()
+ self.assertFalse(p._is_forward_setup())
+ self.assertTrue(p.forward_setup_done)
+
+ @mock.patch('time.sleep')
+ def test_MoongenTestPMD_testpmd_dpdk_setup_next(self, _, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ p.forward_setup()
+ self.assertTrue(p._is_forward_setup())
+ self.assertTrue(p.forward_setup_done)
+
+ @mock.patch('time.sleep')
+ def test_MoongenTestPMD_l2fwd_forward_setup_first(self, _, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.L2fwdargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # is_dpdk_setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+
+ p.forward_setup()
+ self.assertFalse(p._is_forward_setup())
+ self.assertTrue(p.forward_setup_done)
+
+ @mock.patch('time.sleep')
+ def test_MoongenTestPMD_l2fwd_dpdk_setup_next(self, _, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.L2fwdargs, self.ctx)
+
+ # setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, 'dummy', '')
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ p.forward_setup()
+ self.assertTrue(p._is_forward_setup())
+ self.assertTrue(p.forward_setup_done)
+
+ def test_moongen_testpmd_generate_config_file(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ mock_subprocess.call().execute.return_value = None
+
+ p.generate_config_file(frame_size=1, multistream=1,
+ runBidirec="True", tg_port1_vlan=1,
+ tg_port2_vlan=2, SearchRuntime=1,
+ Package_Loss=0)
+ self.assertTrue(p.CONFIG_FILE)
+
+ def test_moongen_testpmd_result_to_data_match(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ mock_subprocess.call().execute.return_value = None
+ result = ("[REPORT]Device 1->0: Tx frames: 420161490 Rx Frames: 420161490"
+ " frame loss: 0, 0.000000% Rx Mpps: 7.002708\n[REPORT] "
+ "total: Tx frames: 840321216 Rx Frames: 840321216 frame loss: "
+ "0, 0.000000% Tx Mpps: 14.005388 Rx Mpps: 14.005388\n'")
+ p.result_to_data(result=result)
+ self.assertTrue(p.TO_DATA)
+
+ def test_moongen_testpmd_result_to_data_not_match(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ mock_subprocess.call().execute.return_value = None
+ result = ("")
+ p.result_to_data(result=result)
+ self.assertTrue(p.TO_DATA)
+
+ @mock.patch('time.sleep')
+ def test_moongen_testpmd_run_ok(self, _, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+ p.setup_done = True
+ p.forward_setup_done = True
+ p.setup()
+
+ # run() specific mocks
+ p.server = self.mock_ssh.SSH.from_node()
+ mock_subprocess.call().execute.return_value = None
+ mock_subprocess.call().execute.return_value = None
+ result = ("[REPORT]Device 1->0: Tx frames: 420161490 Rx Frames: 420161490"
+ " frame loss: 0, 0.000000% Rx Mpps: 7.002708\n[REPORT] "
+ "total: Tx frames: 840321216 Rx Frames: 840321216 frame loss: "
+ "0, 0.000000% Tx Mpps: 14.005388 Rx Mpps: 14.005388\n'")
+ self.mock_ssh.SSH.from_node().execute.return_value = (
+ 0, result, '')
+
+ test_result = {}
+ p.run(test_result)
+
+ self.assertEqual(test_result['rx_mpps'], 14.005388)
+
+ def test_moongen_testpmd_run_falied_vsperf_execution(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # run() specific mocks
+ mock_subprocess.call().execute.return_value = None
+ mock_subprocess.call().execute.return_value = None
+ self.mock_ssh.SSH.from_node().execute.return_value = (1, '', '')
+
+ result = {}
+ self.assertRaises(RuntimeError, p.run, result)
+
+ def test_moongen_testpmd_run_falied_csv_report(self, mock_subprocess):
+ p = moongen_testpmd.MoongenTestPMD(self.TestPMDargs, self.ctx)
+
+ # setup() specific mocks
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+ mock_subprocess.call().execute.return_value = None
+
+ p.setup()
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ # run() specific mocks
+ mock_subprocess.call().execute.return_value = None
+ mock_subprocess.call().execute.return_value = None
+ self.mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+ self.mock_ssh.SSH.from_node().execute.return_value = (1, '', '')
+
+ result = {}
+ self.assertRaises(RuntimeError, p.run, result)
+
+def main():
+ unittest.main()
+
+
+if __name__ == '__main__':
+ main()
diff --git a/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py b/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py
index ec22d6147..9bfbf0752 100644
--- a/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py
+++ b/yardstick/tests/unit/benchmark/scenarios/networking/test_vnf_generic.py
@@ -355,7 +355,7 @@ class TestNetworkServiceTestCase(unittest.TestCase):
return file_path
def test___init__(self):
- assert self.topology
+ self.assertIsNotNone(self.topology)
def test__get_ip_flow_range_string(self):
self.scenario_cfg["traffic_options"]["flow"] = \
diff --git a/yardstick/tests/unit/benchmark/scenarios/storage/test_fio.py b/yardstick/tests/unit/benchmark/scenarios/storage/test_fio.py
index f47d1ca29..f149cee69 100644
--- a/yardstick/tests/unit/benchmark/scenarios/storage/test_fio.py
+++ b/yardstick/tests/unit/benchmark/scenarios/storage/test_fio.py
@@ -61,6 +61,22 @@ class FioTestCase(unittest.TestCase):
}
args = {'options': options}
p = fio.Fio(args, self.ctx)
+ mock_ssh.SSH.from_node().execute.return_value = (0, '/dev/vdb', '')
+ p.setup()
+
+ mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
+ self.assertIsNotNone(p.client)
+ self.assertTrue(p.setup_done)
+
+ def test_fio_job_file_no_disk__setup(self, mock_ssh):
+
+ options = {
+ 'job_file': 'job_file.ini',
+ 'directory': '/FIO_Test'
+ }
+ args = {'options': options}
+ p = fio.Fio(args, self.ctx)
+ mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
p.setup()
mock_ssh.SSH.from_node().execute.return_value = (0, '', '')
diff --git a/yardstick/tests/unit/benchmark/scenarios/test_base.py b/yardstick/tests/unit/benchmark/scenarios/test_base.py
index 985338532..284a71cc8 100644
--- a/yardstick/tests/unit/benchmark/scenarios/test_base.py
+++ b/yardstick/tests/unit/benchmark/scenarios/test_base.py
@@ -13,10 +13,21 @@
# License for the specific language governing permissions and limitations
# under the License.
+import time
+
+import mock
+
from yardstick.benchmark.scenarios import base
from yardstick.tests.unit import base as ut_base
+class _TestScenario(base.Scenario):
+ __scenario_type__ = 'Test Scenario'
+
+ def run(self):
+ pass
+
+
class ScenarioTestCase(ut_base.BaseUnitTestCase):
def test_get_scenario_type(self):
@@ -85,6 +96,25 @@ class ScenarioTestCase(ut_base.BaseUnitTestCase):
self.assertEqual('No such scenario type %s' % wrong_scenario_name,
str(exc.exception))
+ def test_scenario_abstract_class(self):
+ # pylint: disable=abstract-class-instantiated
+ with self.assertRaises(TypeError):
+ base.Scenario()
+
+ @mock.patch.object(time, 'sleep')
+ def test_pre_run_wait_time(self, mock_sleep):
+ """Ensure default behaviour (backwards compatibility): no wait time"""
+ test_scenario = _TestScenario()
+ test_scenario.pre_run_wait_time(mock.ANY)
+ mock_sleep.assert_not_called()
+
+ @mock.patch.object(time, 'sleep')
+ def test_post_run_wait_time(self, mock_sleep):
+ """Ensure default behaviour (backwards compatibility): wait time"""
+ test_scenario = _TestScenario()
+ test_scenario.post_run_wait_time(100)
+ mock_sleep.assert_called_once_with(100)
+
class IterScenarioClassesTestCase(ut_base.BaseUnitTestCase):
diff --git a/yardstick/tests/unit/common/test_ansible_common.py b/yardstick/tests/unit/common/test_ansible_common.py
index b01195fcc..48d8a60c8 100644
--- a/yardstick/tests/unit/common/test_ansible_common.py
+++ b/yardstick/tests/unit/common/test_ansible_common.py
@@ -17,6 +17,7 @@ from __future__ import absolute_import
import os
import tempfile
+import shutil
from collections import defaultdict
import mock
@@ -246,3 +247,18 @@ class AnsibleCommonTestCase(unittest.TestCase):
a.execute_ansible('', d, ansible_check=True, verbose=True)
finally:
os.rmdir(d)
+
+ def test_get_sut_info(self):
+ d = tempfile.mkdtemp()
+ a = ansible_common.AnsibleCommon({})
+ try:
+ a.get_sut_info(d)
+ finally:
+ shutil.rmtree(d)
+
+ def test_get_sut_info_not_exist(self):
+ a = ansible_common.AnsibleCommon({})
+ try:
+ a.get_sut_info('/hello/world')
+ except OSError:
+ pass
diff --git a/yardstick/tests/unit/common/test_openstack_utils.py b/yardstick/tests/unit/common/test_openstack_utils.py
index 4863f05c0..e39a13f1b 100644
--- a/yardstick/tests/unit/common/test_openstack_utils.py
+++ b/yardstick/tests/unit/common/test_openstack_utils.py
@@ -83,3 +83,105 @@ class DeleteNeutronNetTestCase(unittest.TestCase):
'network_id')
self.assertFalse(output)
mock_logger.error.assert_called_once()
+
+
+class CreateNeutronNetTestCase(unittest.TestCase):
+
+ def setUp(self):
+ self.mock_shade_client = mock.Mock()
+ self.network_name = 'name'
+ self.mock_shade_client.create_network = mock.Mock()
+
+ def test_create_neutron_net(self):
+ _uuid = uuidutils.generate_uuid()
+ self.mock_shade_client.create_network.return_value = {'id': _uuid}
+ output = openstack_utils.create_neutron_net(self.mock_shade_client,
+ self.network_name)
+ self.assertEqual(_uuid, output)
+
+ @mock.patch.object(openstack_utils, 'log')
+ def test_create_neutron_net_exception(self, mock_logger):
+ self.mock_shade_client.create_network.side_effect = (
+ exc.OpenStackCloudException('error message'))
+
+ output = openstack_utils.create_neutron_net(self.mock_shade_client,
+ self.network_name)
+ mock_logger.error.assert_called_once()
+ self.assertIsNone(output)
+
+
+class CreateNeutronSubnetTestCase(unittest.TestCase):
+
+ def setUp(self):
+ self.mock_shade_client = mock.Mock()
+ self.network_name_or_id = 'name_or_id'
+ self.mock_shade_client.create_subnet = mock.Mock()
+
+ def test_create_neutron_subnet(self):
+ _uuid = uuidutils.generate_uuid()
+ self.mock_shade_client.create_subnet.return_value = {'id': _uuid}
+ output = openstack_utils.create_neutron_subnet(
+ self.mock_shade_client, self.network_name_or_id)
+ self.assertEqual(_uuid, output)
+
+ @mock.patch.object(openstack_utils, 'log')
+ def test_create_neutron_subnet_exception(self, mock_logger):
+ self.mock_shade_client.create_subnet.side_effect = (
+ exc.OpenStackCloudException('error message'))
+
+ output = openstack_utils.create_neutron_subnet(
+ self.mock_shade_client, self.network_name_or_id)
+ mock_logger.error.assert_called_once()
+ self.assertIsNone(output)
+
+
+class DeleteNeutronRouterTestCase(unittest.TestCase):
+
+ def setUp(self):
+ self.mock_shade_client = mock.Mock()
+ self.mock_shade_client.delete_router = mock.Mock()
+
+ def test_delete_neutron_router(self):
+ self.mock_shade_client.delete_router.return_value = True
+ output = openstack_utils.delete_neutron_router(self.mock_shade_client,
+ 'router_id')
+ self.assertTrue(output)
+
+ def test_delete_neutron_router_fail(self):
+ self.mock_shade_client.delete_router.return_value = False
+ output = openstack_utils.delete_neutron_router(self.mock_shade_client,
+ 'router_id')
+ self.assertFalse(output)
+
+ @mock.patch.object(openstack_utils, 'log')
+ def test_delete_neutron_router_exception(self, mock_logger):
+ self.mock_shade_client.delete_router.side_effect = (
+ exc.OpenStackCloudException('error message'))
+ output = openstack_utils.delete_neutron_router(self.mock_shade_client,
+ 'router_id')
+ mock_logger.error.assert_called_once()
+ self.assertFalse(output)
+
+
+class CreateNeutronRouterTestCase(unittest.TestCase):
+
+ def setUp(self):
+ self.mock_shade_client = mock.Mock()
+ self.mock_shade_client.create_subnet = mock.Mock()
+
+ def test_create_neutron_router(self):
+ _uuid = uuidutils.generate_uuid()
+ self.mock_shade_client.create_router.return_value = {'id': _uuid}
+ output = openstack_utils.create_neutron_router(
+ self.mock_shade_client)
+ self.assertEqual(_uuid, output)
+
+ @mock.patch.object(openstack_utils, 'log')
+ def test_create_neutron_subnet_exception(self, mock_logger):
+ self.mock_shade_client.create_router.side_effect = (
+ exc.OpenStackCloudException('error message'))
+
+ output = openstack_utils.create_neutron_router(
+ self.mock_shade_client)
+ mock_logger.error.assert_called_once()
+ self.assertIsNone(output)
diff --git a/yardstick/tests/unit/common/test_packages.py b/yardstick/tests/unit/common/test_packages.py
deleted file mode 100644
index ba59a3015..000000000
--- a/yardstick/tests/unit/common/test_packages.py
+++ /dev/null
@@ -1,88 +0,0 @@
-# Copyright (c) 2018 Intel Corporation
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import mock
-from pip import exceptions as pip_exceptions
-from pip.operations import freeze
-import unittest
-
-from yardstick.common import packages
-
-
-class PipExecuteActionTestCase(unittest.TestCase):
-
- def setUp(self):
- self._mock_pip_main = mock.patch.object(packages, '_pip_main')
- self.mock_pip_main = self._mock_pip_main.start()
- self.mock_pip_main.return_value = 0
- self._mock_freeze = mock.patch.object(freeze, 'freeze')
- self.mock_freeze = self._mock_freeze.start()
- self.addCleanup(self._cleanup)
-
- def _cleanup(self):
- self._mock_pip_main.stop()
- self._mock_freeze.stop()
-
- def test_pip_execute_action(self):
- self.assertEqual(0, packages._pip_execute_action('test_package'))
-
- def test_remove(self):
- self.assertEqual(0, packages._pip_execute_action('test_package',
- action='uninstall'))
-
- def test_install(self):
- self.assertEqual(0, packages._pip_execute_action(
- 'test_package', action='install', target='temp_dir'))
-
- def test_pip_execute_action_error(self):
- self.mock_pip_main.return_value = 1
- self.assertEqual(1, packages._pip_execute_action('test_package'))
-
- def test_pip_execute_action_exception(self):
- self.mock_pip_main.side_effect = pip_exceptions.PipError
- self.assertEqual(1, packages._pip_execute_action('test_package'))
-
- def test_pip_list(self):
- pkg_input = [
- 'XStatic-Rickshaw==1.5.0.0',
- 'xvfbwrapper==0.2.9',
- '-e git+https://git.opnfv.org/yardstick@50773a24afc02c9652b662ecca'
- '2fc5621ea6097a#egg=yardstick',
- 'zope.interface==4.4.3'
- ]
- pkg_dict = {
- 'XStatic-Rickshaw': '1.5.0.0',
- 'xvfbwrapper': '0.2.9',
- 'yardstick': '50773a24afc02c9652b662ecca2fc5621ea6097a',
- 'zope.interface': '4.4.3'
- }
- self.mock_freeze.return_value = pkg_input
-
- pkg_output = packages.pip_list()
- for pkg_name, pkg_version in pkg_output.items():
- self.assertEqual(pkg_dict.get(pkg_name), pkg_version)
-
- def test_pip_list_single_package(self):
- pkg_input = [
- 'XStatic-Rickshaw==1.5.0.0',
- 'xvfbwrapper==0.2.9',
- '-e git+https://git.opnfv.org/yardstick@50773a24afc02c9652b662ecca'
- '2fc5621ea6097a#egg=yardstick',
- 'zope.interface==4.4.3'
- ]
- self.mock_freeze.return_value = pkg_input
-
- pkg_output = packages.pip_list(pkg_name='xvfbwrapper')
- self.assertEqual(1, len(pkg_output))
- self.assertEqual(pkg_output.get('xvfbwrapper'), '0.2.9')
diff --git a/yardstick/tests/unit/common/test_utils.py b/yardstick/tests/unit/common/test_utils.py
index e71d0ff0f..9540a39e8 100644
--- a/yardstick/tests/unit/common/test_utils.py
+++ b/yardstick/tests/unit/common/test_utils.py
@@ -305,8 +305,8 @@ power management:
"""
socket_map = utils.SocketTopology.parse_cpuinfo(cpuinfo)
- assert sorted(socket_map.keys()) == [0]
- assert sorted(socket_map[0].keys()) == [2, 3, 4]
+ self.assertEqual(sorted(socket_map.keys()), [0])
+ self.assertEqual(sorted(socket_map[0].keys()), [2, 3, 4])
def test_single_socket_hyperthread(self):
cpuinfo = """\
@@ -393,11 +393,11 @@ power management:
"""
socket_map = utils.SocketTopology.parse_cpuinfo(cpuinfo)
- assert sorted(socket_map.keys()) == [0]
- assert sorted(socket_map[0].keys()) == [1, 2, 3]
- assert sorted(socket_map[0][1]) == [5]
- assert sorted(socket_map[0][2]) == [6]
- assert sorted(socket_map[0][3]) == [7]
+ self.assertEqual(sorted(socket_map.keys()), [0])
+ self.assertEqual(sorted(socket_map[0].keys()), [1, 2, 3])
+ self.assertEqual(sorted(socket_map[0][1]), [5])
+ self.assertEqual(sorted(socket_map[0][2]), [6])
+ self.assertEqual(sorted(socket_map[0][3]), [7])
def test_dual_socket_hyperthread(self):
cpuinfo = """\
@@ -592,15 +592,15 @@ power management:
"""
socket_map = utils.SocketTopology.parse_cpuinfo(cpuinfo)
- assert sorted(socket_map.keys()) == [0, 1]
- assert sorted(socket_map[0].keys()) == [0, 1, 2]
- assert sorted(socket_map[1].keys()) == [26, 27, 28]
- assert sorted(socket_map[0][0]) == [44]
- assert sorted(socket_map[0][1]) == [1]
- assert sorted(socket_map[0][2]) == [2]
- assert sorted(socket_map[1][26]) == [85]
- assert sorted(socket_map[1][27]) == [86]
- assert sorted(socket_map[1][28]) == [43, 87]
+ self.assertEqual(sorted(socket_map.keys()), [0, 1])
+ self.assertEqual(sorted(socket_map[0].keys()), [0, 1, 2])
+ self.assertEqual(sorted(socket_map[1].keys()), [26, 27, 28])
+ self.assertEqual(sorted(socket_map[0][0]), [44])
+ self.assertEqual(sorted(socket_map[0][1]), [1])
+ self.assertEqual(sorted(socket_map[0][2]), [2])
+ self.assertEqual(sorted(socket_map[1][26]), [85])
+ self.assertEqual(sorted(socket_map[1][27]), [86])
+ self.assertEqual(sorted(socket_map[1][28]), [43, 87])
def test_dual_socket_no_hyperthread(self):
cpuinfo = """\
@@ -796,11 +796,11 @@ power management:
"""
socket_map = utils.SocketTopology.parse_cpuinfo(cpuinfo)
processors = socket_map.processors()
- assert processors == [1, 2, 43, 44, 85, 86, 87]
+ self.assertEqual(processors, [1, 2, 43, 44, 85, 86, 87])
cores = socket_map.cores()
- assert cores == [0, 1, 2, 26, 27, 28]
+ self.assertEqual(cores, [0, 1, 2, 26, 27, 28])
sockets = socket_map.sockets()
- assert sockets == [0, 1]
+ self.assertEqual(sockets, [0, 1])
class ChangeObjToDictTestCase(unittest.TestCase):
diff --git a/yardstick/tests/unit/orchestrator/test_heat.py b/yardstick/tests/unit/orchestrator/test_heat.py
index 9ab8740e3..aae2487aa 100644
--- a/yardstick/tests/unit/orchestrator/test_heat.py
+++ b/yardstick/tests/unit/orchestrator/test_heat.py
@@ -272,10 +272,18 @@ class HeatTemplateTestCase(unittest.TestCase):
heat_template.add_subnet("subnet2", "network2", "cidr2")
heat_template.add_router("router1", "gw1", "subnet1")
heat_template.add_router_interface("router_if1", "router1", "subnet1")
- heat_template.add_port("port1", "network1", "subnet1", "normal")
- heat_template.add_port("port2", "network2", "subnet2", "normal",
+ network1 = mock.MagicMock()
+ network1.stack_name = "network1"
+ network1.subnet_stack_name = "subnet1"
+ network1.vnic_type = "normal"
+ network2 = mock.MagicMock()
+ network2.stack_name = "network2"
+ network2.subnet_stack_name = "subnet2"
+ network2.vnic_type = "normal"
+ heat_template.add_port("port1", network1)
+ heat_template.add_port("port2", network2,
sec_group_id="sec_group1", provider="not-sriov")
- heat_template.add_port("port3", "network2", "subnet2", "normal",
+ heat_template.add_port("port3", network2,
sec_group_id="sec_group1", provider="sriov")
heat_template.add_floating_ip("floating_ip1", "network1", "port1",
"router_if1")
diff --git a/yardstick/tests/unit/service/__init__.py b/yardstick/tests/unit/service/__init__.py
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/yardstick/tests/unit/service/__init__.py
diff --git a/yardstick/tests/unit/service/test_environment.py b/yardstick/tests/unit/service/test_environment.py
new file mode 100644
index 000000000..4af9a3958
--- /dev/null
+++ b/yardstick/tests/unit/service/test_environment.py
@@ -0,0 +1,49 @@
+##############################################################################
+# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others.
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Apache License, Version 2.0
+# which accompanies this distribution, and is available at
+# http://www.apache.org/licenses/LICENSE-2.0
+##############################################################################
+import unittest
+
+import mock
+
+from yardstick.service.environment import Environment
+from yardstick.service.environment import AnsibleCommon
+from yardstick.common.exceptions import UnsupportedPodFormatError
+
+
+class EnvironmentTestCase(unittest.TestCase):
+
+ def test_get_sut_info(self):
+ pod_info = {
+ 'nodes': [
+ {
+ 'name': 'node1',
+ 'host_name': 'host1',
+ 'role': 'Controller',
+ 'ip': '10.1.0.50',
+ 'user': 'root',
+ 'passward': 'root'
+ }
+ ]
+ }
+
+ AnsibleCommon.gen_inventory_ini_dict = mock.MagicMock()
+ AnsibleCommon.get_sut_info = mock.MagicMock(return_value={'node1': {}})
+
+ env = Environment(pod=pod_info)
+ env.get_sut_info()
+
+ def test_get_sut_info_pod_str(self):
+ pod_info = 'nodes'
+
+ env = Environment(pod=pod_info)
+ with self.assertRaises(UnsupportedPodFormatError):
+ env.get_sut_info()
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/yardstick/tests/unit/test_cmd/commands/test_env.py b/yardstick/tests/unit/test_cmd/commands/test_env.py
index 1156b6642..57dacbcd3 100644
--- a/yardstick/tests/unit/test_cmd/commands/test_env.py
+++ b/yardstick/tests/unit/test_cmd/commands/test_env.py
@@ -21,30 +21,30 @@ class EnvCommandTestCase(unittest.TestCase):
def test_do_influxdb(self, check_status_mock, start_async_task_mock):
env = EnvCommand()
env.do_influxdb({})
- self.assertTrue(start_async_task_mock.called)
- self.assertTrue(check_status_mock.called)
+ start_async_task_mock.assert_called_once()
+ check_status_mock.assert_called_once()
@mock.patch('yardstick.cmd.commands.env.EnvCommand._start_async_task')
@mock.patch('yardstick.cmd.commands.env.EnvCommand._check_status')
def test_do_grafana(self, check_status_mock, start_async_task_mock):
env = EnvCommand()
env.do_grafana({})
- self.assertTrue(start_async_task_mock.called)
- self.assertTrue(check_status_mock.called)
+ start_async_task_mock.assert_called_once()
+ check_status_mock.assert_called_once()
@mock.patch('yardstick.cmd.commands.env.EnvCommand._start_async_task')
@mock.patch('yardstick.cmd.commands.env.EnvCommand._check_status')
def test_do_prepare(self, check_status_mock, start_async_task_mock):
env = EnvCommand()
env.do_prepare({})
- self.assertTrue(start_async_task_mock.called)
- self.assertTrue(check_status_mock.called)
+ start_async_task_mock.assert_called_once()
+ check_status_mock.assert_called_once()
@mock.patch('yardstick.cmd.commands.env.HttpClient.post')
def test_start_async_task(self, post_mock):
data = {'action': 'create_grafana'}
EnvCommand()._start_async_task(data)
- self.assertTrue(post_mock.called)
+ post_mock.assert_called_once()
@mock.patch('yardstick.cmd.commands.env.HttpClient.get')
@mock.patch('yardstick.cmd.commands.env.EnvCommand._print_status')
diff --git a/yardstick/tests/unit/test_cmd/commands/test_testcase.py b/yardstick/tests/unit/test_cmd/commands/test_testcase.py
index f6f842e20..922167614 100644
--- a/yardstick/tests/unit/test_cmd/commands/test_testcase.py
+++ b/yardstick/tests/unit/test_cmd/commands/test_testcase.py
@@ -18,4 +18,4 @@ class TestcaseCommandsUT(unittest.TestCase):
def test_do_list(self, mock_client, mock_print):
mock_client.get.return_value = {'result': []}
TestcaseCommands().do_list({})
- self.assertTrue(mock_print.called)
+ mock_print.assert_called_once()