Ejemplo n.º 1
0
def play_scenario(scenario):
    deployment = None
    output = dict(scenario=scenario, records=[], agents={})
    output['tests'] = dict((_make_test_title(test), test)
                           for test in scenario['execution']['tests'])

    try:
        deployment = deploy.Deployment(cfg.CONF.server_endpoint)

        if (cfg.CONF.os_username and cfg.CONF.os_password
                and cfg.CONF.os_tenant_name and cfg.CONF.os_auth_url):
            deployment.connect_to_openstack(
                cfg.CONF.os_username, cfg.CONF.os_password,
                cfg.CONF.os_tenant_name, cfg.CONF.os_auth_url,
                cfg.CONF.os_region_name, cfg.CONF.external_net,
                cfg.CONF.flavor_name, cfg.CONF.image_name)

        agents = deployment.deploy(scenario['deployment'],
                                   base_dir=os.path.dirname(cfg.CONF.scenario))
        agents = _extend_agents(agents)
        output['agents'] = agents
        LOG.debug('Deployed agents: %s', agents)

        if not agents:
            LOG.warning('No agents deployed.')
        else:
            message_queue = messaging.MessageQueue(cfg.CONF.server_endpoint)

            heartbeat = multiprocessing.Process(
                target=agent_process.work,
                kwargs=dict(agent_id='heartbeat',
                            endpoint=cfg.CONF.server_endpoint,
                            polling_interval=cfg.CONF.polling_interval))
            heartbeat.daemon = True
            heartbeat.start()

            quorum = quorum_pkg.Quorum(message_queue,
                                       cfg.CONF.polling_interval,
                                       cfg.CONF.agent_loss_timeout,
                                       cfg.CONF.agent_join_timeout)
            quorum.join(set(agents.keys()))

            execution_result = execute(quorum, scenario['execution'], agents)
            for record in execution_result:
                record['scenario'] = (scenario.get('title')
                                      or scenario.get('file_name'))
            output['records'] = execution_result
    except BaseException as e:
        if isinstance(e, KeyboardInterrupt):
            LOG.info('Caught SIGINT. Terminating')
        else:
            error_msg = 'Error while executing scenario: %s' % e
            LOG.error(error_msg)
            LOG.exception(e)
            output['scenario']['error'] = error_msg
    finally:
        if deployment:
            deployment.cleanup()

    return output
Ejemplo n.º 2
0
    def test_get_compute_nodes_non_admin_zones(self, nova_nodes_mock):
        deployment = deploy.Deployment()
        deployment.openstack_client = mock.Mock()

        def raise_error(arg):
            raise nova.ForbiddenException('err')

        nova_nodes_mock.side_effect = raise_error
        accommodation = {'compute_nodes': 4, 'zones': ['nova', 'nsx']}
        expected = [
            {
                'host': None,
                'zone': 'nova'
            },
            {
                'host': None,
                'zone': 'nsx'
            },
            {
                'host': None,
                'zone': 'nova'
            },
            {
                'host': None,
                'zone': 'nsx'
            },
        ]

        observed = deployment._get_compute_nodes(accommodation)

        self.assertEqual(expected, observed)
Ejemplo n.º 3
0
    def test_get_compute_nodes_flavor_no_extra_specs(self,
                                                     nova_client_mock):
        # setup fake nova api service list response
        compute_host_1 = fakes.FakeNovaServiceList(host='host-1')
        compute_host_2 = fakes.FakeNovaServiceList(host='host-2')
        compute_host_3 = fakes.FakeNovaServiceList(host='host-3')

        nova_client_mock.nova.services.list.return_value = [compute_host_1,
                                                            compute_host_2,
                                                            compute_host_3]

        # setup fake nova api flavor list response
        flavor_no_exta_specs = fakes.FakeNovaFlavorList(
            name='flavor_no_exta_specs')

        nova_client_mock.nova.flavors.list.return_value = [
            flavor_no_exta_specs]

        deployment = deploy.Deployment()
        deployment.flavor_name = 'flavor_no_exta_specs'
        deployment.openstack_client = nova_client_mock

        accommodation = {'compute_nodes': 3}
        expected = [{'host': 'host-1', 'zone': 'nova'},
                    {'host': 'host-2', 'zone': 'nova'},
                    {'host': 'host-3', 'zone': 'nova'}]

        observed = deployment._get_compute_nodes(accommodation)

        self.assertEqual(expected, observed)
Ejemplo n.º 4
0
    def test_deploy_from_hot_with_env_file(self, nova_nodes_mock,
                                           openstack_mock, create_stack_mock,
                                           stack_output_mock):
        test_file = 'shaker/scenarios/test/sample_with_env.yaml'
        absolute_path = utils.resolve_relative_path(test_file)
        scenario = utils.read_yaml_file(absolute_path)

        stack_name = 'shaker_abcdefg'

        server_endpoint = "127.0.0.01"
        base_dir = os.path.dirname(absolute_path)

        deployment = deploy.Deployment()
        deployment.stack_name = stack_name
        deployment.external_net = 'test-external_net'
        deployment.image_name = 'test-image'
        deployment.flavor_name = 'test-flavor'
        deployment.dns_nameservers = '8.8.8.8'
        deployment.openstack_client = openstack_mock

        # read the env file to determine what cidr is set to
        # minus the last digit
        env_file = utils.read_file(scenario['deployment']['env_file'],
                                   base_dir)
        cidr = re.findall(r'[0-9]+(?:\.[0-9]+){2}', env_file)[0]

        nova_nodes_mock.return_value = [{'host': 'host-1', 'zone': 'nova'}]

        create_stack_mock.return_value = uuid.uuid4()

        heat_outputs = {
            stack_name + '_master_0_instance_name': 'instance-0000052f',
            stack_name + '_master_0_ip': '192.0.0.3',
            stack_name + '_slave_0_ip': '192.0.0.4',
            stack_name + '_slave_0_instance_name': 'instance-0000052c'}

        stack_output_mock.return_value = heat_outputs

        expected = {
            'shaker_abcdefg_master_0': {'availability_zone': 'nova:host-1',
                                        'id': 'shaker_abcdefg_master_0',
                                        'ip': cidr + '.3',
                                        'mode': 'master',
                                        'node': 'host-1',
                                        'slave_id': 'shaker_abcdefg_slave_0',
                                        'zone': 'nova'},
            'shaker_abcdefg_slave_0': {'availability_zone': 'nova:host-1',
                                       'id': 'shaker_abcdefg_slave_0',
                                       'ip': cidr + '.4',
                                       'master_id': 'shaker_abcdefg_master_0',
                                       'mode': 'slave',
                                       'node': 'host-1',
                                       'zone': 'nova'}}

        agents = deployment._deploy_from_hot(scenario['deployment'],
                                             server_endpoint,
                                             base_dir=base_dir)

        self.assertEqual(expected, agents)
Ejemplo n.º 5
0
    def test_deploy_local(self):
        deployment = deploy.Deployment()

        expected = {
            'local': {'id': 'local', 'mode': 'alone', 'node': 'localhost'}
        }
        agents = deployment.deploy({})

        self.assertEqual(expected, agents)
Ejemplo n.º 6
0
    def test_deploy_static(self):
        deployment = deploy.Deployment()

        expected = {
            'agent': {'id': 'agent', 'mode': 'alone'}
        }
        agents = deployment.deploy(
            {'agents': [{'id': 'agent', 'mode': 'alone'}]})

        self.assertEqual(expected, agents)
Ejemplo n.º 7
0
def play_scenario(scenario):
    deployment = None
    output = dict(scenario=scenario, records={}, agents={})
    output['tests'] = dict((_make_test_title(test), test)
                           for test in scenario['execution']['tests'])

    try:
        deployment = deploy.Deployment(cfg.CONF.server_endpoint)

        if (cfg.CONF.os_username and cfg.CONF.os_password
                and cfg.CONF.os_tenant_name and cfg.CONF.os_auth_url):
            deployment.connect_to_openstack(
                cfg.CONF.os_username, cfg.CONF.os_password,
                cfg.CONF.os_tenant_name, cfg.CONF.os_auth_url,
                cfg.CONF.os_region_name, cfg.CONF.external_net,
                cfg.CONF.flavor_name, cfg.CONF.image_name, cfg.CONF.os_cacert)

        base_dir = os.path.dirname(scenario['file_name'])
        agents = deployment.deploy(scenario['deployment'], base_dir=base_dir)

        agents = _extend_agents(agents)
        output['agents'] = agents
        LOG.debug('Deployed agents: %s', agents)

        if not agents:
            raise Exception('No agents deployed.')

        quorum = quorum_pkg.make_quorum(agents.keys(),
                                        cfg.CONF.server_endpoint,
                                        cfg.CONF.polling_interval,
                                        cfg.CONF.agent_loss_timeout,
                                        cfg.CONF.agent_join_timeout)

        output['records'] = execute(quorum, scenario['execution'], agents)

    except BaseException as e:
        if isinstance(e, KeyboardInterrupt):
            LOG.info('Caught SIGINT. Terminating')
            record = dict(id=utils.make_record_id(), status='interrupted')
        else:
            error_msg = 'Error while executing scenario: %s' % e
            LOG.error(error_msg)
            LOG.exception(e)
            record = dict(id=utils.make_record_id(),
                          status='error',
                          stderr=error_msg)
        output['records'][record['id']] = record
    finally:
        if deployment:
            deployment.cleanup()

    # extend every record with reference to scenario
    for record in output['records'].values():
        record['scenario'] = scenario['title']
    return output
Ejemplo n.º 8
0
    def test_deploy_from_hot_with_support_stacks(self, nova_nodes_mock,
                                                 openstack_mock,
                                                 create_stack_mock,
                                                 stack_output_mock):
        test_file = 'shaker/scenarios/test/sample_with_support_stacks.yaml'
        absolute_path = utils.resolve_relative_path(test_file)
        scenario = utils.read_yaml_file(absolute_path)

        stack_name = 'shaker_abcdefg'

        server_endpoint = "127.0.0.01"
        base_dir = os.path.dirname(absolute_path)

        deployment = deploy.Deployment()
        deployment.stack_name = stack_name
        deployment.external_net = 'test-external_net'
        deployment.image_name = 'test-image'
        deployment.flavor_name = 'test-flavor'
        deployment.dns_nameservers = '8.8.8.8'
        deployment.openstack_client = openstack_mock

        nova_nodes_mock.return_value = [{'host': 'host-1', 'zone': 'nova'}]

        create_stack_mock.return_value = uuid.uuid4()

        heat_outputs = {
            stack_name + '_master_0_instance_name': 'instance-0000052f',
            stack_name + '_master_0_ip': '10.0.0.3',
            stack_name + '_slave_0_ip': '10.0.0.4',
            stack_name + '_slave_0_instance_name': 'instance-0000052c'}

        stack_output_mock.return_value = heat_outputs

        expected = {
            'shaker_abcdefg_master_0': {'availability_zone': 'nova:host-1',
                                        'id': 'shaker_abcdefg_master_0',
                                        'ip': '10.0.0.3',
                                        'mode': 'master',
                                        'node': 'host-1',
                                        'slave_id': 'shaker_abcdefg_slave_0',
                                        'zone': 'nova'},
            'shaker_abcdefg_slave_0': {'availability_zone': 'nova:host-1',
                                       'id': 'shaker_abcdefg_slave_0',
                                       'ip': '10.0.0.4',
                                       'master_id': 'shaker_abcdefg_master_0',
                                       'mode': 'slave',
                                       'node': 'host-1',
                                       'zone': 'nova'}}

        agents = deployment._deploy_from_hot(scenario['deployment'],
                                             server_endpoint,
                                             base_dir=base_dir)

        self.assertEqual(create_stack_mock.call_count, 3)
        self.assertEqual(expected, agents)
Ejemplo n.º 9
0
    def test_get_compute_nodes_non_admin_not_configured(self, nova_nodes_mock):
        deployment = deploy.Deployment()
        deployment.openstack_client = mock.Mock()

        def raise_error(arg):
            raise nova.ForbiddenException('err')

        nova_nodes_mock.side_effect = raise_error
        accommodation = {}

        self.assertRaises(deploy.DeploymentException,
                          deployment._get_compute_nodes, accommodation)
Ejemplo n.º 10
0
    def test_get_compute_nodes_non_admin(self, nova_nodes_mock):
        deployment = deploy.Deployment()
        deployment.openstack_client = mock.Mock()

        def raise_error(arg):
            raise nova.ForbiddenException('err')

        nova_nodes_mock.side_effect = raise_error
        accommodation = {'compute_nodes': 4}
        expected = list(itertools.repeat({'host': None, 'zone': 'nova'}, 4))

        observed = deployment._get_compute_nodes(accommodation)

        self.assertEqual(expected, observed)
Ejemplo n.º 11
0
    def test_deploy_support_stacks(self, openstack_mock, create_stack_mock):
        test_file = 'shaker/scenarios/test/sample_with_support_stacks.yaml'
        absolute_path = utils.resolve_relative_path(test_file)
        scenario = utils.read_yaml_file(absolute_path)

        support_stacks = scenario['deployment']['support_templates']
        base_dir = os.path.dirname(absolute_path)

        deployment = deploy.Deployment()
        deployment.stack_name = 'shaker_abcdefg'
        deployment.openstack_client = openstack_mock

        support_stack_1 = uuid.uuid4()
        support_stack_2 = uuid.uuid4()

        create_stack_mock.side_effect = (support_stack_1, support_stack_2)

        deployment._deploy_support_stacks(support_stacks, base_dir)

        self.assertEqual(support_stack_1, deployment.support_stacks[0].id)
        self.assertEqual(support_stack_2, deployment.support_stacks[1].id)
Ejemplo n.º 12
0
    def test_get_compute_nodes_flavor_extra_specs_with_match(
            self, nova_client_mock):
        # setup fake nova api service list response
        compute_host_1 = fakes.FakeNovaServiceList(host='host-1')
        compute_host_2 = fakes.FakeNovaServiceList(host='host-2')
        compute_host_3 = fakes.FakeNovaServiceList(host='host-3')

        nova_client_mock.nova.services.list.return_value = [
            compute_host_1, compute_host_2, compute_host_3
        ]

        # setup fake nova api flavor list response
        flavor_with_extra_specs = fakes.FakeNovaFlavorList(
            name='flavor_with_extra_specs',
            extra_specs={'aggregate_instance_extra_specs:special_hw': 'true'})

        nova_client_mock.nova.flavors.list.return_value = [
            flavor_with_extra_specs
        ]

        # setup fake nova api aggregate list response
        agg_host_1 = fakes.FakeNovaAggregateList(hosts=['host-1'])
        agg_host_2 = fakes.FakeNovaAggregateList(
            hosts=['host-2'], metadata={'special_hw': 'true'})
        agg_host_3 = fakes.FakeNovaAggregateList(hosts=['host-3'])

        nova_client_mock.nova.aggregates.list.return_value = [
            agg_host_1, agg_host_2, agg_host_3
        ]

        deployment = deploy.Deployment()
        deployment.flavor_name = 'flavor_with_extra_specs'
        deployment.openstack_client = nova_client_mock

        accommodation = {'compute_nodes': 3}
        expected = [{'host': 'host-2', 'zone': 'nova'}]

        observed = deployment._get_compute_nodes(accommodation)

        self.assertEqual(expected, observed)
Ejemplo n.º 13
0
def play_scenario(message_queue, scenario):
    deployment = None
    output = dict(scenarios={}, records={}, agents={}, tests={})
    output['scenarios'][scenario['title']] = scenario

    try:
        deployment = deploy.Deployment()

        if _under_openstack():
            openstack_params = utils.pack_openstack_params(cfg.CONF)
            try:
                deployment.connect_to_openstack(openstack_params,
                                                cfg.CONF.flavor_name,
                                                cfg.CONF.image_name,
                                                cfg.CONF.external_net,
                                                cfg.CONF.dns_nameservers)
            except openstack_clients.OpenStackClientException:
                raise
            except Exception as e:
                LOG.warning(
                    'Failed to connect to OpenStack: %s. Please '
                    'verify parameters: %s', e, openstack_params)
                # try to proceed even if OpenStack connection fails
                # (in case scenario does not need it)

        base_dir = os.path.dirname(scenario['file_name'])
        scenario_deployment = scenario.get('deployment', {})
        server_endpoint = (cfg.CONF.server_endpoint
                           if 'server_endpoint' in cfg.CONF else None)

        agents = deployment.deploy(scenario_deployment,
                                   base_dir=base_dir,
                                   server_endpoint=server_endpoint)

        agents = _extend_agents(agents)
        output['agents'] = agents
        LOG.debug('Deployed agents: %s', agents)

        if not agents:
            raise Exception('No agents deployed.')

        if scenario_deployment:
            quorum = quorum_pkg.make_quorum(agents.keys(), message_queue,
                                            cfg.CONF.polling_interval,
                                            cfg.CONF.agent_loss_timeout,
                                            cfg.CONF.agent_join_timeout)
        else:
            # local
            quorum = quorum_pkg.make_local_quorum()

        matrix = cfg.CONF.matrix if 'matrix' in cfg.CONF else None
        if matrix:
            scenario['matrix'] = matrix

        execute(output, quorum, scenario['execution'], agents, matrix)

    except BaseException as e:
        if isinstance(e, KeyboardInterrupt):
            LOG.info('Caught SIGINT. Terminating')
            record = dict(id=utils.make_record_id(), status='interrupted')
        else:
            error_msg = 'Error while executing scenario: %s' % e
            LOG.exception(e)
            record = dict(id=utils.make_record_id(),
                          status='error',
                          stderr=error_msg)
        output['records'][record['id']] = record
    finally:
        if deployment:
            try:
                deployment.cleanup()
            except Exception as e:
                LOG.error('Failed to cleanup the deployment: %s',
                          e,
                          exc_info=True)

    # extend every record with reference to scenario
    for record in output['records'].values():
        record['scenario'] = scenario['title']
    return output
Ejemplo n.º 14
0
def play_scenario(scenario):
    deployment = None
    output = dict(scenario=scenario, records={}, agents={}, tests={})

    try:
        deployment = deploy.Deployment()

        if _under_openstack():
            deployment.connect_to_openstack(
                cfg.CONF.os_username, cfg.CONF.os_password,
                cfg.CONF.os_tenant_name, cfg.CONF.os_auth_url,
                cfg.CONF.os_region_name, cfg.CONF.external_net,
                cfg.CONF.flavor_name, cfg.CONF.image_name, cfg.CONF.os_cacert,
                cfg.CONF.os_insecure)

        base_dir = os.path.dirname(scenario['file_name'])
        scenario_deployment = scenario.get('deployment', {})
        server_endpoint = (cfg.CONF.server_endpoint
                           if 'server_endpoint' in cfg.CONF else None)

        agents = deployment.deploy(scenario_deployment,
                                   base_dir=base_dir,
                                   server_endpoint=server_endpoint)

        agents = _extend_agents(agents)
        output['agents'] = agents
        LOG.debug('Deployed agents: %s', agents)

        if not agents:
            raise Exception('No agents deployed.')

        if scenario_deployment:
            quorum = quorum_pkg.make_quorum(agents.keys(), server_endpoint,
                                            cfg.CONF.polling_interval,
                                            cfg.CONF.agent_loss_timeout,
                                            cfg.CONF.agent_join_timeout)
        else:
            # local
            quorum = quorum_pkg.make_local_quorum()

        matrix = cfg.CONF.matrix if 'matrix' in cfg.CONF else None
        if matrix:
            scenario['matrix'] = matrix

        execute(output, quorum, scenario['execution'], agents, matrix)

    except BaseException as e:
        if isinstance(e, KeyboardInterrupt):
            LOG.info('Caught SIGINT. Terminating')
            record = dict(id=utils.make_record_id(), status='interrupted')
        else:
            error_msg = 'Error while executing scenario: %s' % e
            LOG.error(error_msg)
            LOG.exception(e)
            record = dict(id=utils.make_record_id(),
                          status='error',
                          stderr=error_msg)
        output['records'][record['id']] = record
    finally:
        if deployment:
            try:
                deployment.cleanup()
            except Exception as e:
                LOG.error('Failed to cleanup the deployment: %s',
                          e,
                          exc_info=True)

    # extend every record with reference to scenario
    for record in output['records'].values():
        record['scenario'] = scenario['title']
    return output
Ejemplo n.º 15
0
    def test_deploy_template_error_when_non_initialized(self):
        deployment = deploy.Deployment()

        self.assertRaises(deploy.DeploymentException, deployment.deploy,
                          {'template': 'foo'})