Add neutron scenarios
Add neutron client to nmanager, add sanity and smoke scenarios for neutron Change-Id: I7bc8a9171a995041c04d67538ccf6cf429bf1c12 Implements-blueprint: ostf-checks-for-neutron
This commit is contained in:
parent
f238ecaef0
commit
fd5b87b5ae
|
@ -0,0 +1,141 @@
|
|||
# Copyright 2014 Mirantis, 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 logging
|
||||
import traceback
|
||||
|
||||
import fuel_health.nmanager
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class NeutronBaseTest(fuel_health.nmanager.NovaNetworkScenarioTest):
|
||||
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
super(NeutronBaseTest, cls).setUpClass()
|
||||
cls.routers = {}
|
||||
cls.subnets = []
|
||||
cls.networks = []
|
||||
cls.security_groups = {}
|
||||
|
||||
def setUp(self):
|
||||
super(NeutronBaseTest, self).setUp()
|
||||
self.check_clients_state()
|
||||
self.tenant_id = self.identity_client.tenant_id
|
||||
if not self.neutron_client:
|
||||
self.skipTest('Neutron is unavailable.')
|
||||
|
||||
def create_router(self, name):
|
||||
external_network = None
|
||||
for network in self.neutron_client.list_networks()["networks"]:
|
||||
if network.get("router:external"):
|
||||
external_network = network
|
||||
|
||||
if not external_network:
|
||||
self.fail('Can not find external network')
|
||||
|
||||
gw_info = {
|
||||
"network_id": external_network["id"],
|
||||
"enable_snat": True
|
||||
}
|
||||
|
||||
router_info = {
|
||||
"router": {
|
||||
"name": name,
|
||||
"external_gateway_info": gw_info,
|
||||
"tenant_id": self.tenant_id
|
||||
}
|
||||
}
|
||||
|
||||
router = self.neutron_client.create_router(router_info)['router']
|
||||
self.routers.setdefault(router['id'], [])
|
||||
|
||||
return router
|
||||
|
||||
def create_network(self, name):
|
||||
internal_network_info = {
|
||||
"network": {
|
||||
"name": name,
|
||||
"tenant_id": self.tenant_id
|
||||
}
|
||||
}
|
||||
|
||||
network = self.neutron_client.create_network(
|
||||
internal_network_info)['network']
|
||||
self.networks.append(network)
|
||||
|
||||
return network
|
||||
|
||||
def create_subnet(self, internal_network):
|
||||
subnet_info = {
|
||||
"subnet": {
|
||||
"network_id": internal_network['id'],
|
||||
"ip_version": 4,
|
||||
"cidr": "10.0.7.0/24",
|
||||
"tenant_id": self.tenant_id
|
||||
}
|
||||
}
|
||||
|
||||
subnet = self.neutron_client.create_subnet(subnet_info)['subnet']
|
||||
self.subnets.append(subnet)
|
||||
|
||||
return subnet
|
||||
|
||||
def uplink_subnet_to_router(self, router, subnet):
|
||||
if not self.routers.get(router['id'], None):
|
||||
self.routers[router['id']].append(subnet['id'])
|
||||
|
||||
return self.neutron_client.add_interface_router(
|
||||
router["id"], {"subnet_id": subnet["id"]})
|
||||
|
||||
def _remove_router(self, router, subnets_id=[]):
|
||||
self.neutron_client.remove_gateway_router(router['id'])
|
||||
|
||||
for subnet_id in subnets_id:
|
||||
self.neutron_client.remove_interface_router(
|
||||
router['id'], {"subnet_id": subnet_id})
|
||||
|
||||
self.neutron_client.delete_router(router['id'])
|
||||
|
||||
def _remove_subnet(self, subnet):
|
||||
return self.neutron_client.delete_subnet(subnet['id'])
|
||||
|
||||
def _remove_network(self, network):
|
||||
self.neutron_client.delete_network(network['id'])
|
||||
|
||||
@classmethod
|
||||
def _clear_networks(cls):
|
||||
|
||||
for router in cls.routers:
|
||||
try:
|
||||
cls._remove_router(router, cls.routers[router])
|
||||
except Exception as exc:
|
||||
cls.error_msg.append(exc)
|
||||
LOG.debug(traceback.format_exc())
|
||||
|
||||
for subnet in cls.subnets:
|
||||
try:
|
||||
cls._remove_subnet(subnet)
|
||||
except Exception as exc:
|
||||
cls.error_msg.append(exc)
|
||||
LOG.debug(traceback.format_exc())
|
||||
|
||||
for network in cls.networks:
|
||||
try:
|
||||
cls._remove_network(network)
|
||||
except Exception as exc:
|
||||
cls.error_msg.append(exc)
|
||||
LOG.debug(traceback.format_exc())
|
|
@ -41,6 +41,10 @@ try:
|
|||
import ceilometerclient.v2.client
|
||||
except:
|
||||
LOG.warning('Ceilometer client could not be imported.')
|
||||
try:
|
||||
import neutronclient.neutron.client
|
||||
except:
|
||||
LOG.warning('Neutron client could not be imported.')
|
||||
|
||||
import cinderclient.client
|
||||
import keystoneclient.v2_0.client
|
||||
|
@ -92,6 +96,7 @@ class OfficialClientManager(fuel_health.manager.Manager):
|
|||
self.murano_client = self._get_murano_client()
|
||||
self.sahara_client = self._get_sahara_client()
|
||||
self.ceilometer_client = self._get_ceilometer_client()
|
||||
self.neutron_client = self._get_neutron_client()
|
||||
self.client_attr_names = [
|
||||
'compute_client',
|
||||
'identity_client',
|
||||
|
@ -99,7 +104,8 @@ class OfficialClientManager(fuel_health.manager.Manager):
|
|||
'heat_client',
|
||||
'murano_client',
|
||||
'sahara_client',
|
||||
'ceilometer_client'
|
||||
'ceilometer_client',
|
||||
'neutron_client'
|
||||
]
|
||||
|
||||
def _get_compute_client(self, username=None, password=None,
|
||||
|
@ -244,6 +250,21 @@ class OfficialClientManager(fuel_health.manager.Manager):
|
|||
return ceilometerclient.v2.Client(endpoint=endpoint,
|
||||
token=lambda: keystone.auth_token)
|
||||
|
||||
def _get_neutron_client(self, version='2.0'):
|
||||
keystone = self._get_identity_client()
|
||||
|
||||
try:
|
||||
endpoint = keystone.service_catalog.url_for(
|
||||
service_type='network',
|
||||
endpoint_type='publicURL')
|
||||
except keystoneclient.exceptions.EndpointNotFound:
|
||||
LOG.warning('Can not initialize neutron client')
|
||||
return None
|
||||
|
||||
return neutronclient.neutron.client.Client(version,
|
||||
token=keystone.auth_token,
|
||||
endpoint_url=endpoint)
|
||||
|
||||
|
||||
class OfficialClientTest(fuel_health.test.TestCase):
|
||||
manager_class = OfficialClientManager
|
||||
|
@ -519,7 +540,7 @@ class NovaNetworkScenarioTest(OfficialClientTest):
|
|||
return nets
|
||||
|
||||
def _create_server(self, client, name, security_groups=None,
|
||||
flavor_id=None):
|
||||
flavor_id=None, net_id=None):
|
||||
base_image_id = self.get_image_from_name()
|
||||
if not flavor_id:
|
||||
flavor = self._create_nano_flavor()
|
||||
|
@ -534,9 +555,12 @@ class NovaNetworkScenarioTest(OfficialClientTest):
|
|||
security_groups = [self._create_security_group(
|
||||
self.compute_client).name]
|
||||
if 'neutron' in self.config.network.network_provider:
|
||||
network = [net.id for net in
|
||||
self.compute_client.networks.list()
|
||||
if net.label == self.private_net]
|
||||
if net_id:
|
||||
network = [net_id]
|
||||
else:
|
||||
network = [net.id for net in
|
||||
self.compute_client.networks.list()
|
||||
if net.label == self.private_net]
|
||||
|
||||
if network:
|
||||
create_kwargs = {'nics': [{'net-id': network[0]}],
|
||||
|
@ -782,8 +806,10 @@ class SanityChecksTest(OfficialClientTest):
|
|||
return users
|
||||
|
||||
def _list_networks(self, client):
|
||||
networks = client.networks.list()
|
||||
return networks
|
||||
if hasattr(client, 'list_networks'):
|
||||
return client.list_networks()
|
||||
else:
|
||||
return client.networks.list()
|
||||
|
||||
def _list_stacks(self, client):
|
||||
return client.stacks.list()
|
||||
|
|
|
@ -26,7 +26,7 @@ class NetworksTest(nmanager.SanityChecksTest):
|
|||
TestClass contains tests check base networking functionality
|
||||
"""
|
||||
|
||||
def test_list_networks(self):
|
||||
def test_list_networks_nova_network(self):
|
||||
"""Request list of networks
|
||||
Target component: Nova Networking.
|
||||
|
||||
|
@ -34,6 +34,8 @@ class NetworksTest(nmanager.SanityChecksTest):
|
|||
1. Request the list of networks.
|
||||
2. Confirm that a response is received.
|
||||
Duration: 20 s.
|
||||
|
||||
Deployment tags: nova_network
|
||||
"""
|
||||
fail_msg = "Networks list is unavailable. "
|
||||
networks = self.verify(20, self._list_networks, 1,
|
||||
|
@ -43,3 +45,23 @@ class NetworksTest(nmanager.SanityChecksTest):
|
|||
|
||||
self.verify_response_true(networks,
|
||||
"Step 2 failed: {msg}".format(msg=fail_msg))
|
||||
|
||||
def test_list_networks_neutron(self):
|
||||
"""Request list of networks
|
||||
Target component: Neutron.
|
||||
|
||||
Scenario:
|
||||
1. Request the list of networks.
|
||||
2. Confirm that a response is received.
|
||||
Duration: 20 s.
|
||||
|
||||
Deployment tags: neutron, 6.0
|
||||
"""
|
||||
fail_msg = "Networks list is unavailable. "
|
||||
networks = self.verify(20, self._list_networks, 1,
|
||||
fail_msg,
|
||||
"listing networks",
|
||||
self.neutron_client)
|
||||
|
||||
self.verify_response_true(networks,
|
||||
"Step 2 failed: {msg}".format(msg=fail_msg))
|
||||
|
|
|
@ -0,0 +1,145 @@
|
|||
# Copyright 2014 Mirantis, 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 logging
|
||||
|
||||
from fuel_health.common.utils.data_utils import rand_name
|
||||
from fuel_health import neutronmanager
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class TestNeutron(neutronmanager.NeutronBaseTest):
|
||||
"""
|
||||
Test suite verifies:
|
||||
- router creation
|
||||
- network creation
|
||||
- subnet creation
|
||||
- opportunity to attach network to router
|
||||
- instance creation in created network
|
||||
- instance network connectivity
|
||||
"""
|
||||
|
||||
def test_check_neutron_objects_creation(self):
|
||||
"""Check network connectivity from instance via floating IP
|
||||
Target component: Neutron
|
||||
|
||||
Scenario:
|
||||
1. Create a new security group (if it doesn`t exist yet).
|
||||
2. Create router
|
||||
3. Create network
|
||||
4. Create subnet
|
||||
5. Uplink subnet to router.
|
||||
6. Create an instance using the new security group
|
||||
in created subnet.
|
||||
7. Create a new floating IP
|
||||
8. Assign the new floating IP to the instance.
|
||||
9. Check connectivity to the floating IP using ping command.
|
||||
10. Check that public IP 8.8.8.8 can be pinged from instance.
|
||||
11. Disassociate server floating ip.
|
||||
12. Delete floating ip
|
||||
13. Delete server.
|
||||
14. Remove router.
|
||||
15. Remove subnet
|
||||
16. Remove network
|
||||
|
||||
Duration: 300 s.
|
||||
|
||||
Deployment tags: neutron
|
||||
"""
|
||||
|
||||
self.check_image_exists()
|
||||
if not self.security_groups:
|
||||
self.security_groups[self.tenant_id] = self.verify(
|
||||
25, self._create_security_group, 1,
|
||||
"Security group can not be created.",
|
||||
'security group creation',
|
||||
self.compute_client)
|
||||
|
||||
name = rand_name('ost1_test-server-smoke-')
|
||||
security_groups = [self.security_groups[self.tenant_id].name]
|
||||
|
||||
router = self.verify(30, self.create_router, 2,
|
||||
'Router can not be created', 'Router creation',
|
||||
name)
|
||||
|
||||
network = self.verify(20, self.create_network, 3,
|
||||
'Network can not be created',
|
||||
'Network creation', name)
|
||||
|
||||
subnet = self.verify(20, self.create_subnet, 4,
|
||||
'Subnet can not be created',
|
||||
'Subnet creation', network)
|
||||
|
||||
self.verify(20, self.uplink_subnet_to_router, 5,
|
||||
'Can not uplink subnet to router',
|
||||
'Uplink subnet to router', router, subnet)
|
||||
|
||||
server = self.verify(200, self._create_server, 6,
|
||||
"Server can not be created.",
|
||||
"server creation",
|
||||
self.compute_client, name, security_groups,
|
||||
net_id=network['id'])
|
||||
|
||||
floating_ip = self.verify(
|
||||
20,
|
||||
self._create_floating_ip,
|
||||
7,
|
||||
"Floating IP can not be created.",
|
||||
'floating IP creation')
|
||||
|
||||
self.verify(10, self._assign_floating_ip_to_instance,
|
||||
8, "Floating IP can not be assigned.",
|
||||
'floating IP assignment',
|
||||
self.compute_client, server, floating_ip)
|
||||
|
||||
self.floating_ips.append(floating_ip)
|
||||
|
||||
ip_address = floating_ip.ip
|
||||
LOG.info('is address is {0}'.format(ip_address))
|
||||
LOG.debug(ip_address)
|
||||
|
||||
self.verify(400, self._check_vm_connectivity, 9,
|
||||
"VM connectivity doesn`t function properly.",
|
||||
'VM connectivity checking', ip_address,
|
||||
30, (6, 60))
|
||||
|
||||
self.verify(400, self._check_connectivity_from_vm,
|
||||
10, ("Connectivity to 8.8.8.8 from the VM doesn`t "
|
||||
"function properly."),
|
||||
'public connectivity checking from VM', ip_address,
|
||||
30, (6, 60))
|
||||
|
||||
self.verify(10, self.compute_client.servers.remove_floating_ip,
|
||||
11, "Floating IP cannot be removed.",
|
||||
"removing floating IP", server, floating_ip)
|
||||
|
||||
self.verify(10, self.compute_client.floating_ips.delete,
|
||||
12, "Floating IP cannot be deleted.",
|
||||
"floating IP deletion", floating_ip)
|
||||
|
||||
if self.floating_ips:
|
||||
self.floating_ips.remove(floating_ip)
|
||||
|
||||
self.verify(30, self._delete_server, 13,
|
||||
"Server can not be deleted. ",
|
||||
"server deletion", server)
|
||||
|
||||
self.verify(40, self._remove_router, 14, "Router can not be deleted",
|
||||
"router deletion", router, [subnet['id']])
|
||||
self.verify(20, self._remove_subnet, 15, "Subnet can not be deleted",
|
||||
"Subnet deletion", subnet)
|
||||
self.verify(20, self._remove_network, 16,
|
||||
"Network can not be deleted", "Network deletion", network)
|
|
@ -179,6 +179,7 @@ class TestNovaNetwork(nmanager.NovaNetworkScenarioTest):
|
|||
9. Delete server.
|
||||
Duration: 300 s.
|
||||
|
||||
Deployment tags: nova_network
|
||||
"""
|
||||
self.check_image_exists()
|
||||
if not self.security_groups:
|
||||
|
|
|
@ -3,6 +3,7 @@ python-cinderclient>=1.0.7
|
|||
python-ceilometerclient>=1.0.9
|
||||
python-keystoneclient>=0.4.2
|
||||
python-novaclient>=2.17.0
|
||||
python-neutronclient>=2.3.6,<3
|
||||
python-heatclient>=0.2.9
|
||||
python-saharaclient>=0.6.0
|
||||
paramiko>=1.10.1
|
||||
|
|
Loading…
Reference in New Issue