Files
browbeat/rally/rally-plugins/dynamic-workloads/rally_context.py
Sanjay Chari 7e45cad2a1 Add cidr prefix parameter in dynamic workloads
This patch adds a parameter in dynamic workloads for the cidr prefix of
the multiple external networks that are created as part of rally context.
This cidr prefix was hardcoded as 172.31 before, but it should be accepted
as a parameter from the user.

Change-Id: I51a0dd34cb8090cb3ba3afa391c36fc29911ce0e
2022-06-22 10:51:51 +05:30

216 lines
9.3 KiB
Python

# 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.task import context
from rally.common import logging
from rally.common import utils
from rally import consts
from rally_openstack import osclients
from rally_openstack.wrappers import network as network_wrapper
import subprocess
LOG = logging.getLogger(__name__)
@context.configure(name="create_external_networks", order=1000)
class CreateExternalNetworksContext(context.Context):
"""This plugin creates external networks with specified option."""
CONFIG_SCHEMA = {
"type": "object",
"$schema": consts.JSON_SCHEMA,
"additionalProperties": False,
"properties": {
"cidr_prefix": {
"type": "string",
},
"num_external_networks": {
"type": "integer",
"minimum": 0
},
"interface_name": {
"type": "string"
},
"provider_phys_net": {
"type": "string"
}
}
}
def _create_subnet(self, tenant_id, network_id, network_number):
"""Create subnet for external network
:param tenant_id: ID of tenant
:param network_id: ID of external network
:param network_number: int, number for CIDR of subnet
:returns: subnet object
"""
subnet_args = {
"subnet": {
"tenant_id": tenant_id,
"network_id": network_id,
"name": self.net_wrapper.owner.generate_random_name(),
"ip_version": 4,
"cidr": "{}.{}.0/23".format(self.cidr_prefix, network_number),
"enable_dhcp": False,
"gateway_ip": "{}.{}.1".format(self.cidr_prefix, network_number),
"allocation_pools": [{"start": "{}.{}.2".format(self.cidr_prefix, network_number),
"end": "{}.{}.254".format(
self.cidr_prefix, network_number+1)}]
}
}
return self.net_wrapper.client.create_subnet(subnet_args)["subnet"]
def setup(self):
"""This method is called before the task starts."""
self.net_wrapper = network_wrapper.wrap(
osclients.Clients(self.context["admin"]["credential"]),
self,
config=self.config,
)
self.context["external_networks"] = []
self.context["external_subnets"] = {}
self.num_external_networks = self.config.get("num_external_networks", 16)
self.interface_name = self.config.get("interface_name", "ens7f1")
self.cidr_prefix = self.config.get("cidr_prefix", "172.31")
num_external_networks_created = 0
while num_external_networks_created < self.num_external_networks:
has_error_occured = False
for user, tenant_id in utils.iterate_per_tenants(
self.context.get("users", [])
):
cmd = ["sudo", "ip", "link", "add", "link", self.interface_name, "name",
"{}.{}".format(self.interface_name, num_external_networks_created + 1),
"type", "vlan", "id", str(num_external_networks_created + 1)]
proc = subprocess.Popen(cmd)
proc.wait()
if proc.returncode == 0:
LOG.debug("Creating vlan {} on interface {} was successful".format(
num_external_networks_created + 1, self.interface_name))
else:
LOG.exception("Creating vlan {} on interface {} failed".format(
num_external_networks_created + 1, self.interface_name))
has_error_occured = True
break
cmd = ["sudo", "ip", "link", "set", "dev",
"{}.{}".format(self.interface_name, num_external_networks_created + 1),
"up"]
proc = subprocess.Popen(cmd)
proc.wait()
if proc.returncode == 0:
LOG.debug("Setting vlan {} up on interface {} was successful".format(
num_external_networks_created + 1, self.interface_name))
else:
LOG.exception("Setting vlan {} up on interface {} failed".format(
num_external_networks_created + 1, self.interface_name))
has_error_occured = True
break
cmd = ["sudo", "ip", "a", "a", "{}.{}.1/23".format(
self.cidr_prefix, num_external_networks_created*2), "dev",
"{}.{}".format(self.interface_name, num_external_networks_created + 1)]
proc = subprocess.Popen(cmd)
proc.wait()
if proc.returncode == 0:
LOG.debug("Adding IP range to interface {} was successful".format(
self.interface_name))
else:
LOG.exception("Adding IP range to interface {} failed".format(
self.interface_name))
has_error_occured = True
break
try:
kwargs = {
"network_create_args": {
"provider:network_type": "vlan",
"provider:physical_network": self.config.get("provider_phys_net",
"datacentre"),
"provider:segmentation_id": num_external_networks_created + 1,
"router:external": True
}
}
self.context["external_networks"].append(
self.net_wrapper.create_network(tenant_id, **kwargs)
)
LOG.debug(
"External network with id '%s' created as part of context"
% self.context["external_networks"][-1]["id"]
)
num_external_networks_created += 1
except Exception as e:
msg = "Can't create external network {} as part of context: {}".format(
num_external_networks_created, e
)
LOG.exception(msg)
has_error_occured = True
break
try:
subnet = self._create_subnet(tenant_id,
self.context["external_networks"][-1]["id"],
(num_external_networks_created - 1) * 2)
self.context["external_subnets"][
self.context["external_networks"][-1]["id"]] = subnet
LOG.debug(
"External subnet with id '%s' created as part of context"
% subnet["id"]
)
except Exception as e:
msg = "Can't create external subnet {} as part of context: {}".format(
num_external_networks_created, e
)
LOG.exception(msg)
has_error_occured = True
break
if has_error_occured:
break
def cleanup(self):
"""This method is called after the task finishes."""
for i in range(self.num_external_networks):
try:
external_net = self.context["external_networks"][i]
external_net_id = external_net["id"]
external_subnet = self.context["external_subnets"][external_net_id]
external_subnet_id = external_subnet["id"]
self.net_wrapper._delete_subnet(external_subnet_id)
LOG.debug(
"External subnet with id '%s' deleted from context"
% external_subnet_id
)
self.net_wrapper.delete_network(external_net)
LOG.debug(
"External network with id '%s' deleted from context"
% external_net_id
)
except Exception as e:
msg = "Can't delete external network {} from context: {}".format(
external_net_id, e
)
LOG.warning(msg)
cmd = ["sudo", "ip", "link", "delete", "{}.{}".format(self.interface_name, i + 1)]
proc = subprocess.Popen(cmd)
proc.wait()
if proc.returncode == 0:
LOG.debug("Deleting vlan {}.{} was successful".format(
self.interface_name, i + 1))
else:
LOG.exception("Deleting vlan {}.{} failed".format(
self.interface_name, i + 1))