Add Neutron benchmarks scenarios

This patch contains:
- Changes for supporting neutron scenario tests
- Add scenario "create_and_list_networks"

blueprint benchmark-scenarios-for-neutron

Change-Id: Ic6ba1b1b832529ef48c08f106473c5914a2d1564
This commit is contained in:
chen-li 2014-04-18 17:47:10 +08:00
parent 2d427b1deb
commit b81062e835
10 changed files with 245 additions and 2 deletions

View File

@ -0,0 +1,17 @@
{
"NeutronNetworks.create_and_list_networks": [
{
"runner": {
"type": "constant",
"times": 100,
"concurrency": 10
},
"context": {
"users": {
"tenants": 1,
"users_per_tenant": 1
}
}
}
]
}

View File

@ -0,0 +1,11 @@
---
NeutronNetworks.create_and_list_networks:
-
runner:
type: "constant"
times: 100
concurrency: 10
context:
users:
tenants: 1
users_per_tenant: 1

View File

@ -39,7 +39,7 @@ class ResourceCleaner(base.Context):
"$schema": rutils.JSON_SCHEMA,
"items": {
"type": "string",
"enum": ["nova", "glance", "cinder", "quotas"]
"enum": ["nova", "glance", "cinder", "quotas", "neutron"]
},
"uniqueItems": True
}
@ -64,7 +64,10 @@ class ResourceCleaner(base.Context):
clients.cinder()),
"quotas": functools.partial(utils.delete_quotas,
admin_clients,
clients.keystone().tenant_id)
clients.keystone().tenant_id),
"neutron": functools.partial(utils.delete_neutron_resources,
clients.neutron(),
clients.keystone().tenant_id)
}
for service in self.config:

View File

@ -98,6 +98,16 @@ def delete_keypairs(nova):
_wait_for_empty_list(nova.keypairs)
def delete_neutron_networks(neutron, project_uuid):
for network in neutron.list_networks()['networks']:
if network['tenant_id'] == project_uuid:
neutron.delete_network(network['id'])
def delete_neutron_resources(neutron, project_uuid):
delete_neutron_networks(neutron, project_uuid)
def _wait_for_empty_list(mgr, timeout=10, check_interval=1):
_wait_for_list_size(mgr, sizes=[0], timeout=timeout,
check_interval=check_interval)

View File

@ -0,0 +1,38 @@
# Copyright 2014: Intel Inc.
# All Rights Reserved.
#
# 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.
from rally.benchmark.scenarios import base
from rally.benchmark.scenarios.neutron import utils
class NeutronNetworks(utils.NeutronScenario):
@base.scenario(context={"cleanup": ["neutron"]})
def create_and_list_networks(self, **kwargs):
"""Tests creating a network and then listing all networks.
This scenario is a very useful tool to measure
the "neutron net-list" command performance.
If you have only 1 user in your context, you will
add 1 network on every iteration. So you will have more
and more networks and will be able to measure the
performance of the "neutron net-list" command depending on
the number of networks owned by users.
"""
network_name = self._generate_neutron_name(16)
self._create_network(network_name, **kwargs)
self._list_networks()

View File

@ -0,0 +1,54 @@
# Copyright 2014: Intel Inc.
# All Rights Reserved.
#
# 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 random
import string
from rally.benchmark.scenarios import base
from rally.benchmark.scenarios import utils as scenario_utils
TEMP_TEMPLATE = "rally_n_"
class NeutronScenario(base.Scenario):
"""This class should contain base operations for benchmarking neutron,
most of them are creating/deleting resources.
"""
def _generate_neutron_name(self, length=10):
"""Generate random name for neutron resources."""
rand_part = ''.join(random.choice(
string.lowercase) for i in range(length))
return TEMP_TEMPLATE + rand_part
@scenario_utils.atomic_action_timer('neutron.create_network')
def _create_network(self, network_name, **kwargs):
"""Creates neutron network with random name.
:param network_name: the name of network
:param **kwargs: Other optional parameters to create networks like
"tenant_id", "shared".
:return: neutron network instance
"""
kwargs.setdefault("name", network_name)
return self.clients("neutron").create_network({"network": kwargs})
@scenario_utils.atomic_action_timer('neutron.list_networks')
def _list_networks(self):
"""Returns user networks list."""
return self.clients("neutron").list_networks()['networks']

View File

@ -0,0 +1,36 @@
# Copyright 2014: Intel Inc.
# All Rights Reserved.
#
# 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 rally.benchmark.scenarios.neutron import network
from tests import test
NEUTRON_NETWORKS = "rally.benchmark.scenarios.neutron.network.NeutronNetworks"
class NeutronNetworksTestCase(test.TestCase):
@mock.patch(NEUTRON_NETWORKS + "._generate_neutron_name")
@mock.patch(NEUTRON_NETWORKS + "._list_networks")
@mock.patch(NEUTRON_NETWORKS + "._create_network")
def test_create_and_list_networks(self, mock_create, mock_list,
mock_random_name):
neutron_scenario = network.NeutronNetworks()
mock_random_name.return_value = "test-rally-network"
neutron_scenario.create_and_list_networks()
mock_create.assert_called_once_with("test-rally-network")
mock_list.assert_called_once_with()

View File

@ -0,0 +1,74 @@
# Copyright 2013: Intel Inc.
# All Rights Reserved.
#
# 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 rally.benchmark.scenarios.neutron import utils
from tests.benchmark.scenarios import test_utils
from tests import test
NEUTRON_UTILS = "rally.benchmark.scenarios.neutron.utils."
class NeutronScenarioTestCase(test.TestCase):
def setUp(self):
super(NeutronScenarioTestCase, self).setUp()
self.network = mock.Mock()
def _test_atomic_action_timer(self, atomic_actions_time, name):
action_duration = test_utils.get_atomic_action_timer_value_by_name(
atomic_actions_time, name)
self.assertIsNotNone(action_duration)
self.assertIsInstance(action_duration, float)
@mock.patch(NEUTRON_UTILS + "random.choice")
def test_generate_neutron_name(self, mock_random_choice):
mock_random_choice.return_value = "a"
for length in [10, 20]:
result = utils.NeutronScenario()._generate_neutron_name(length)
self.assertEqual(result, utils.TEMP_TEMPLATE + "a" * length)
@mock.patch(NEUTRON_UTILS + 'NeutronScenario.clients')
def test_create_network(self, mock_clients):
mock_clients("neutron").create_network.return_value = self.network
args = {"network_name": "test_network_name",
"arg1": "test_args1",
"arg2": "test_args2"}
expected_create_network_args = {"network": {
"name": "test_network_name",
"arg1": "test_args1",
"arg2": "test_args2"}}
neutron_scenario = utils.NeutronScenario()
return_network = neutron_scenario._create_network(**args)
mock_clients("neutron").create_network.assert_called_once_with(
expected_create_network_args)
self.assertEqual(self.network, return_network)
self._test_atomic_action_timer(neutron_scenario.atomic_actions(),
'neutron.create_network')
@mock.patch(NEUTRON_UTILS + 'NeutronScenario.clients')
def test_list_networks(self, mock_clients):
networks_list = []
networks_dict = {"networks": networks_list}
mock_clients("neutron").list_networks.return_value = networks_dict
neutron_scenario = utils.NeutronScenario()
return_networks_list = neutron_scenario._list_networks()
self.assertEqual(networks_list, return_networks_list)
self._test_atomic_action_timer(neutron_scenario.atomic_actions(),
'neutron.list_networks')