86601b800c
W0403 relative-import is no longer suppressed by pylint.rc Note: six.moves.urllib.request was considered a relative import from six.moves import urllib is considered valid. The code is updated to satisfy pylint and pep8. nfv_scenario_tests main.py still needs to use a relative import based on how it is invoked. Story: 2004515 Task: 28575 Change-Id: I3f576f3990352e9456fe3ee5d3a80cb1307f31e0 Signed-off-by: Al Bailey <Al.Bailey@windriver.com>
368 lines
16 KiB
Python
Executable File
368 lines
16 KiB
Python
Executable File
#
|
|
# Copyright (c) 2016 Wind River Systems, Inc.
|
|
#
|
|
# SPDX-License-Identifier: Apache-2.0
|
|
#
|
|
import fixtures
|
|
import uuid
|
|
|
|
from nfv_common import config
|
|
|
|
from nfv_vim import host_fsm
|
|
from nfv_vim import nfvi
|
|
from nfv_vim import objects
|
|
|
|
from nfv_vim.nfvi.objects import v1 as nfvi_objects
|
|
from nfv_vim.objects import HOST_PERSONALITY
|
|
from nfv_vim.tables._host_aggregate_table import HostAggregateTable
|
|
from nfv_vim.tables._host_group_table import HostGroupTable
|
|
from nfv_vim.tables._host_table import HostTable
|
|
from nfv_vim.tables._image_table import ImageTable
|
|
from nfv_vim.tables._instance_group_table import InstanceGroupTable
|
|
from nfv_vim.tables._instance_table import InstanceTable
|
|
from nfv_vim.tables._instance_type_table import InstanceTypeTable
|
|
from nfv_vim.tables._table import Table
|
|
|
|
from . import testcase # noqa: H304
|
|
from . import utils # noqa: H304
|
|
|
|
|
|
def fake_event_issue(a, b, c, d):
|
|
"""
|
|
Mock out the _event_issue function because it is being called when instance
|
|
objects are created. It ends up trying to communicate with another thread
|
|
(that doesn't exist) and this eventually leads to unit tests hanging if
|
|
enough events are issued.
|
|
"""
|
|
return None
|
|
|
|
|
|
# NOTE: The following testcases test the same scenarios as the testcases in
|
|
# nova/tests/unit/virt/libvirt/test_driver.py
|
|
class TestInstance(testcase.NFVTestCase):
|
|
|
|
def setUp(self):
|
|
"""
|
|
Setup for testing.
|
|
"""
|
|
super(TestInstance, self).setUp()
|
|
self._tenant_table = Table()
|
|
self._instance_type_table = InstanceTypeTable()
|
|
self._image_table = ImageTable()
|
|
self._instance_table = InstanceTable()
|
|
self._instance_group_table = InstanceGroupTable()
|
|
self._host_table = HostTable()
|
|
self._host_group_table = HostGroupTable()
|
|
self._host_aggregate_table = HostAggregateTable()
|
|
|
|
# Don't attempt to write to the database while unit testing
|
|
self._tenant_table.persist = False
|
|
self._image_table.persist = False
|
|
self._instance_type_table.persist = False
|
|
self._instance_table.persist = False
|
|
self._instance_group_table.persist = False
|
|
self._host_table.persist = False
|
|
self._host_group_table.persist = False
|
|
self._host_aggregate_table.persist = False
|
|
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._tenant_table._tenant_table',
|
|
self._tenant_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._host_table._host_table',
|
|
self._host_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._instance_group_table._instance_group_table',
|
|
self._instance_group_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._host_group_table._host_group_table',
|
|
self._host_group_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._host_aggregate_table._host_aggregate_table',
|
|
self._host_aggregate_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._instance_table._instance_table',
|
|
self._instance_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._instance_type_table._instance_type_table',
|
|
self._instance_type_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.tables._image_table._image_table',
|
|
self._image_table))
|
|
self.useFixture(fixtures.MonkeyPatch('nfv_vim.event_log._instance._event_issue',
|
|
fake_event_issue))
|
|
|
|
def tearDown(self):
|
|
"""
|
|
Cleanup testing setup.
|
|
"""
|
|
super(TestInstance, self).tearDown()
|
|
self._tenant_table.clear()
|
|
self._instance_type_table.clear()
|
|
self._image_table.clear()
|
|
self._instance_table.clear()
|
|
self._instance_group_table.clear()
|
|
self._host_table.clear()
|
|
self._host_group_table.clear()
|
|
self._host_aggregate_table.clear()
|
|
|
|
def create_instance(self, instance_name, instance_type_name, image_name, host_name,
|
|
admin_state=nfvi.objects.v1.INSTANCE_ADMIN_STATE.UNLOCKED,
|
|
live_migration_timeout=None):
|
|
"""
|
|
Create an instance
|
|
"""
|
|
tenant_uuid = str(uuid.uuid4())
|
|
|
|
tenant = objects.Tenant(tenant_uuid, "%s_name" % tenant_uuid, '', True)
|
|
self._tenant_table[tenant_uuid] = tenant
|
|
|
|
for instance_type in self._instance_type_table.values():
|
|
if instance_type.name == instance_type_name:
|
|
for image in self._image_table.values():
|
|
if image.name == image_name:
|
|
instance_uuid = str(uuid.uuid4())
|
|
|
|
nfvi_instance = nfvi.objects.v1.Instance(
|
|
instance_uuid, instance_name, tenant_uuid,
|
|
admin_state=admin_state,
|
|
oper_state=nfvi.objects.v1.INSTANCE_OPER_STATE.ENABLED,
|
|
avail_status=list(),
|
|
action=nfvi.objects.v1.INSTANCE_ACTION.NONE,
|
|
host_name=host_name,
|
|
instance_type=utils.instance_type_to_flavor_dict(
|
|
instance_type),
|
|
image_uuid=image.uuid,
|
|
live_migration_timeout=live_migration_timeout)
|
|
|
|
instance = objects.Instance(nfvi_instance)
|
|
self._instance_table[instance.uuid] = instance
|
|
return instance
|
|
|
|
assert 0, "Unknown instance_type_name: %s" % instance_type_name
|
|
|
|
def create_instance_type(self, instance_type_name, live_migration_timeout=None):
|
|
"""
|
|
Create an instance type
|
|
"""
|
|
instance_type_uuid = str(uuid.uuid4())
|
|
instance_type = objects.InstanceType(instance_type_uuid,
|
|
instance_type_name)
|
|
instance_type.update_details(
|
|
vcpus=1, mem_mb=64, disk_gb=1, ephemeral_gb=0,
|
|
swap_gb=0, guest_services=None,
|
|
auto_recovery=True,
|
|
live_migration_timeout=live_migration_timeout,
|
|
live_migration_max_downtime=500,
|
|
storage_type='local_image')
|
|
self._instance_type_table[instance_type_uuid] = instance_type
|
|
|
|
def create_image(self, image_name, properties=None):
|
|
"""
|
|
Create an image
|
|
"""
|
|
image_uuid = str(uuid.uuid4())
|
|
nfvi_image = nfvi_objects.Image(image_uuid, image_name, 'description',
|
|
nfvi_objects.IMAGE_AVAIL_STATUS.AVAILABLE,
|
|
nfvi_objects.IMAGE_ACTION.NONE,
|
|
'BARE',
|
|
'QCOW2',
|
|
1,
|
|
64,
|
|
'public',
|
|
False,
|
|
properties=properties)
|
|
image = objects.Image(nfvi_image)
|
|
self._image_table[image_uuid] = image
|
|
|
|
def create_instance_group(self, name, members, policies):
|
|
"""
|
|
Create an instance group
|
|
"""
|
|
member_uuids = []
|
|
for instance_uuid, instance in self._instance_table.items():
|
|
if instance.name in members:
|
|
member_uuids.append(instance_uuid)
|
|
|
|
nfvi_instance_group = nfvi.objects.v1.InstanceGroup(
|
|
uuid=str(uuid.uuid4()),
|
|
name=name,
|
|
member_uuids=member_uuids,
|
|
policies=policies
|
|
)
|
|
|
|
instance_group = objects.InstanceGroup(nfvi_instance_group)
|
|
self._instance_group_table[instance_group.uuid] = instance_group
|
|
|
|
def create_host(self, host_name,
|
|
cpe=False,
|
|
admin_state=nfvi.objects.v1.HOST_ADMIN_STATE.UNLOCKED,
|
|
software_load='12.01',
|
|
target_load='12.01'):
|
|
"""
|
|
Create a host
|
|
"""
|
|
personality = ''
|
|
if host_name.startswith('controller'):
|
|
personality = HOST_PERSONALITY.CONTROLLER
|
|
if cpe:
|
|
personality = personality + ',' + HOST_PERSONALITY.WORKER
|
|
elif host_name.startswith('compute'):
|
|
personality = HOST_PERSONALITY.WORKER
|
|
elif host_name.startswith('storage'):
|
|
personality = HOST_PERSONALITY.STORAGE
|
|
else:
|
|
assert 0, "Invalid host_name: %s" % host_name
|
|
|
|
nfvi_host = nfvi.objects.v1.Host(
|
|
uuid=str(uuid.uuid4()),
|
|
name=host_name,
|
|
personality=personality,
|
|
admin_state=admin_state,
|
|
oper_state=nfvi.objects.v1.HOST_OPER_STATE.ENABLED,
|
|
avail_status=nfvi.objects.v1.HOST_AVAIL_STATUS.AVAILABLE,
|
|
action=nfvi.objects.v1.HOST_ACTION.NONE,
|
|
software_load=software_load,
|
|
target_load=target_load,
|
|
openstack_compute=False,
|
|
openstack_control=False,
|
|
uptime='1000'
|
|
)
|
|
|
|
host = objects.Host(nfvi_host,
|
|
initial_state=host_fsm.HOST_STATE.ENABLED)
|
|
self._host_table[host.name] = host
|
|
|
|
def create_host_group(self, name, members, policies):
|
|
"""
|
|
Create a host group
|
|
"""
|
|
member_uuids = []
|
|
for instance_uuid, instance in self._instance_table.items():
|
|
if instance.name in members:
|
|
member_uuids.append(instance_uuid)
|
|
|
|
nfvi_host_group = nfvi.objects.v1.HostGroup(
|
|
name=name,
|
|
member_names=members,
|
|
policies=policies
|
|
)
|
|
|
|
host_group = objects.HostGroup(nfvi_host_group)
|
|
self._host_group_table[host_group.name] = host_group
|
|
|
|
def create_host_aggregate(self, name, host_names):
|
|
"""
|
|
Create a host aggregate
|
|
"""
|
|
nfvi_host_aggregate = nfvi.objects.v1.HostAggregate(
|
|
name=name,
|
|
host_names=host_names,
|
|
availability_zone=''
|
|
)
|
|
|
|
host_aggregate = objects.HostAggregate(nfvi_host_aggregate)
|
|
self._host_aggregate_table[host_aggregate.name] = host_aggregate
|
|
|
|
def test_live_migration_completion_timeout(self):
|
|
self.create_instance_type('small')
|
|
self.create_image('image_0')
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 800 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_from_flavor(self):
|
|
self.create_instance_type('small', live_migration_timeout=300)
|
|
self.create_image('image_0')
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 300 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_from_image(self):
|
|
self.create_instance_type('small')
|
|
self.create_image('image_0',
|
|
properties={nfvi_objects.IMAGE_PROPERTY.LIVE_MIGRATION_TIMEOUT: "400"})
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 400 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_from_instance(self):
|
|
self.create_instance_type('small')
|
|
self.create_image('image_0')
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0',
|
|
live_migration_timeout=200)
|
|
assert 200 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_flavor_overwrite_image(self):
|
|
self.create_instance_type('small', live_migration_timeout=300)
|
|
self.create_image('image_0',
|
|
properties={nfvi_objects.IMAGE_PROPERTY.LIVE_MIGRATION_TIMEOUT: "400"})
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 300 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_image_overwrite_flavor(self):
|
|
self.create_instance_type('small', live_migration_timeout=300)
|
|
self.create_image('image_0',
|
|
properties={nfvi_objects.IMAGE_PROPERTY.LIVE_MIGRATION_TIMEOUT: "200"})
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 200 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_instance_overwrite_all(self):
|
|
self.create_instance_type('small', live_migration_timeout=300)
|
|
self.create_image('image_0',
|
|
properties={nfvi_objects.IMAGE_PROPERTY.LIVE_MIGRATION_TIMEOUT: "200"})
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0',
|
|
live_migration_timeout=100)
|
|
assert 100 == instance.max_live_migrate_wait_in_secs
|
|
|
|
def test_live_migration_completion_timeout_overwrite_zero(self):
|
|
self.create_instance_type('small', live_migration_timeout=300)
|
|
self.create_image('image_0',
|
|
properties={nfvi_objects.IMAGE_PROPERTY.LIVE_MIGRATION_TIMEOUT: "0"})
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0',
|
|
live_migration_timeout=400)
|
|
assert 300 == instance.max_live_migrate_wait_in_secs
|
|
|
|
self.create_instance_type('small_2', live_migration_timeout=0)
|
|
self.create_image('image_1',
|
|
properties={nfvi_objects.IMAGE_PROPERTY.LIVE_MIGRATION_TIMEOUT: "200"})
|
|
instance = self.create_instance('test_instance_0',
|
|
'small_2',
|
|
'image_1',
|
|
'compute-0')
|
|
assert 200 == instance.max_live_migrate_wait_in_secs
|
|
|
|
# NOTE: End of tests from nova
|
|
|
|
def test_live_migration_completion_timeout_out_of_range(self):
|
|
config.CONF = {'instance-configuration': {}}
|
|
|
|
self.create_instance_type('small', live_migration_timeout=1000)
|
|
self.create_image('image_0')
|
|
instance = self.create_instance('test_instance_0',
|
|
'small',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 800 == instance.max_live_migrate_wait_in_secs
|
|
|
|
self.create_instance_type('small_2', live_migration_timeout=10)
|
|
self.create_image('image_0')
|
|
instance = self.create_instance('test_instance_1',
|
|
'small_2',
|
|
'image_0',
|
|
'compute-0')
|
|
assert 120 == instance.max_live_migrate_wait_in_secs
|