207 lines
7.3 KiB
Python
207 lines
7.3 KiB
Python
# Copyright 2015 Red Hat, Inc.
|
|
#
|
|
# 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 fixtures
|
|
from neutronclient.common import exceptions as nc_exc
|
|
from oslo_config import cfg
|
|
from oslo_log import log as logging
|
|
|
|
from neutron.agent.linux import utils
|
|
from neutron.tests.common import net_helpers
|
|
from neutron.tests.fullstack.resources import config
|
|
from neutron.tests.fullstack.resources import process
|
|
|
|
LOG = logging.getLogger(__name__)
|
|
|
|
|
|
class EnvironmentDescription(object):
|
|
"""A set of characteristics of an environment setup.
|
|
|
|
Does the setup, as a whole, support tunneling? How about l2pop?
|
|
"""
|
|
pass
|
|
|
|
|
|
class HostDescription(object):
|
|
"""A set of characteristics of an environment Host.
|
|
|
|
What agents should the host spawn? What mode should each agent operate
|
|
under?
|
|
"""
|
|
def __init__(self, l3_agent=False):
|
|
self.l3_agent = l3_agent
|
|
|
|
|
|
class Host(fixtures.Fixture):
|
|
"""The Host class models a physical host running agents, all reporting with
|
|
the same hostname.
|
|
|
|
OpenStack installers or administrators connect compute nodes to the
|
|
physical tenant network by connecting the provider bridges to their
|
|
respective physical NICs. Or, if using tunneling, by configuring an
|
|
IP address on the appropriate physical NIC. The Host class does the same
|
|
with the connect_* methods.
|
|
|
|
TODO(amuller): Add start/stop/restart methods that will start/stop/restart
|
|
all of the agents on this host. Add a kill method that stops all agents
|
|
and disconnects the host from other hosts.
|
|
"""
|
|
|
|
def __init__(self, env_desc, host_desc,
|
|
test_name, neutron_config,
|
|
central_data_bridge, central_external_bridge):
|
|
self.env_desc = env_desc
|
|
self.host_desc = host_desc
|
|
self.test_name = test_name
|
|
self.neutron_config = neutron_config
|
|
self.central_data_bridge = central_data_bridge
|
|
self.central_external_bridge = central_external_bridge
|
|
self.agents = {}
|
|
|
|
def _setUp(self):
|
|
agent_cfg_fixture = config.OVSConfigFixture(
|
|
self.env_desc, self.host_desc, self.neutron_config.temp_dir)
|
|
self.useFixture(agent_cfg_fixture)
|
|
|
|
br_phys = self.useFixture(
|
|
net_helpers.OVSBridgeFixture(
|
|
agent_cfg_fixture.get_br_phys_name())).bridge
|
|
self.connect_to_internal_network_via_vlans(br_phys)
|
|
|
|
self.ovs_agent = self.useFixture(
|
|
process.OVSAgentFixture(
|
|
self.env_desc, self.host_desc,
|
|
self.test_name, self.neutron_config, agent_cfg_fixture))
|
|
|
|
if self.host_desc.l3_agent:
|
|
l3_agent_cfg_fixture = self.useFixture(
|
|
config.L3ConfigFixture(
|
|
self.env_desc, self.host_desc,
|
|
self.neutron_config.temp_dir,
|
|
self.ovs_agent.agent_cfg_fixture.get_br_int_name()))
|
|
br_ex = self.useFixture(
|
|
net_helpers.OVSBridgeFixture(
|
|
l3_agent_cfg_fixture.get_external_bridge())).bridge
|
|
self.connect_to_external_network(br_ex)
|
|
self.l3_agent = self.useFixture(
|
|
process.L3AgentFixture(
|
|
self.env_desc, self.host_desc,
|
|
self.test_name,
|
|
self.neutron_config,
|
|
l3_agent_cfg_fixture))
|
|
|
|
def connect_to_internal_network_via_vlans(self, host_data_bridge):
|
|
# If using VLANs as a segmentation device, it's needed to connect
|
|
# a provider bridge to a centralized, shared bridge.
|
|
net_helpers.create_patch_ports(
|
|
self.central_data_bridge, host_data_bridge)
|
|
|
|
def connect_to_external_network(self, host_external_bridge):
|
|
net_helpers.create_patch_ports(
|
|
self.central_external_bridge, host_external_bridge)
|
|
|
|
@property
|
|
def hostname(self):
|
|
return self.neutron_config.config.DEFAULT.host
|
|
|
|
@property
|
|
def l3_agent(self):
|
|
return self.agents['l3']
|
|
|
|
@l3_agent.setter
|
|
def l3_agent(self, agent):
|
|
self.agents['l3'] = agent
|
|
|
|
@property
|
|
def ovs_agent(self):
|
|
return self.agents['ovs']
|
|
|
|
@ovs_agent.setter
|
|
def ovs_agent(self, agent):
|
|
self.agents['ovs'] = agent
|
|
|
|
|
|
class Environment(fixtures.Fixture):
|
|
"""Represents a deployment topology.
|
|
|
|
Environment is a collection of hosts. It starts a Neutron server
|
|
and a parametrized number of Hosts, each a collection of agents.
|
|
The Environment accepts a collection of HostDescription, each describing
|
|
the type of Host to create.
|
|
"""
|
|
|
|
def __init__(self, env_desc, hosts_desc):
|
|
"""
|
|
:param env_desc: An EnvironmentDescription instance.
|
|
:param hosts_desc: A list of HostDescription instances.
|
|
"""
|
|
|
|
super(Environment, self).__init__()
|
|
self.env_desc = env_desc
|
|
self.hosts_desc = hosts_desc
|
|
self.hosts = []
|
|
|
|
def wait_until_env_is_up(self):
|
|
utils.wait_until_true(self._processes_are_ready)
|
|
|
|
def _processes_are_ready(self):
|
|
try:
|
|
running_agents = self.neutron_server.client.list_agents()['agents']
|
|
agents_count = sum(len(host.agents) for host in self.hosts)
|
|
return len(running_agents) == agents_count
|
|
except nc_exc.NeutronClientException:
|
|
return False
|
|
|
|
def _create_host(self, host_desc):
|
|
temp_dir = self.useFixture(fixtures.TempDir()).path
|
|
neutron_config = config.NeutronConfigFixture(
|
|
self.env_desc, host_desc, temp_dir,
|
|
cfg.CONF.database.connection, self.rabbitmq_environment)
|
|
self.useFixture(neutron_config)
|
|
|
|
return self.useFixture(
|
|
Host(self.env_desc,
|
|
host_desc,
|
|
self.test_name,
|
|
neutron_config,
|
|
self.central_data_bridge,
|
|
self.central_external_bridge))
|
|
|
|
def _setUp(self):
|
|
self.temp_dir = self.useFixture(fixtures.TempDir()).path
|
|
|
|
self.rabbitmq_environment = self.useFixture(
|
|
process.RabbitmqEnvironmentFixture())
|
|
|
|
plugin_cfg_fixture = self.useFixture(
|
|
config.ML2ConfigFixture(
|
|
self.env_desc, None, self.temp_dir, 'vlan'))
|
|
neutron_cfg_fixture = self.useFixture(
|
|
config.NeutronConfigFixture(
|
|
self.env_desc, None, self.temp_dir,
|
|
cfg.CONF.database.connection, self.rabbitmq_environment))
|
|
self.neutron_server = self.useFixture(
|
|
process.NeutronServerFixture(
|
|
self.env_desc, None,
|
|
self.test_name, neutron_cfg_fixture, plugin_cfg_fixture))
|
|
|
|
self.central_data_bridge = self.useFixture(
|
|
net_helpers.OVSBridgeFixture('cnt-data')).bridge
|
|
self.central_external_bridge = self.useFixture(
|
|
net_helpers.OVSBridgeFixture('cnt-ex')).bridge
|
|
|
|
self.hosts = [self._create_host(desc) for desc in self.hosts_desc]
|
|
|
|
self.wait_until_env_is_up()
|