Beispiel #1
0
 def test_update_dhcp_some_failures(self, mock_gnvi, mock_updo):
     # confirm update is called twice, one fails, but no exception raised
     mock_gnvi.return_value = {
         'ports': {
             'p1': 'v1',
             'p2': 'v2'
         },
         'portgroups': {}
     }
     exc = exception.FailedToUpdateDHCPOptOnPort('fake exception')
     mock_updo.side_effect = [None, exc]
     with task_manager.acquire(self.context, self.node.uuid) as task:
         api = dhcp_factory.DHCPFactory()
         api.update_dhcp(task, self.node)
         mock_gnvi.assert_called_once_with(task)
     self.assertEqual(2, mock_updo.call_count)
Beispiel #2
0
    def test_create_cleaning_ports_fail(self, create_mock, rollback_mock):
        # Check that if creating a port fails, the ports are cleaned up
        create_mock.side_effect = neutron_client_exc.ConnectionFailed
        api = dhcp_factory.DHCPFactory().provider

        with task_manager.acquire(self.context, self.node.uuid) as task:
            self.assertRaises(exception.NodeCleaningFailure,
                              api.create_cleaning_ports, task)
            create_mock.assert_called_once_with({
                'port': {
                    'network_id': '00000000-0000-0000-0000-000000000000',
                    'admin_state_up': True,
                    'mac_address': self.ports[0].address
                }
            })
            rollback_mock.assert_called_once_with(task)
Beispiel #3
0
 def _test__get_ip_addresses_portgroup(self, key, mock_gfia):
     if key == "extra":
         kwargs1 = {key: {'vif_port_id': 'test-vif-A'}}
     else:
         kwargs1 = {key: {'tenant_vif_port_id': 'test-vif-A'}}
     ip_address = '10.10.0.1'
     expected = [ip_address]
     pg = object_utils.create_test_portgroup(
         self.context, node_id=self.node.id,
         address='aa:bb:cc:dd:ee:ff', uuid=uuidutils.generate_uuid(),
         **kwargs1)
     mock_gfia.return_value = ip_address
     with task_manager.acquire(self.context, self.node.uuid) as task:
         api = dhcp_factory.DHCPFactory().provider
         result = api._get_ip_addresses(task, [pg], mock.sentinel.client)
     self.assertEqual(expected, result)
Beispiel #4
0
    def test_create_cleaning_ports(self, create_mock):
        # Ensure we can create cleaning ports for in band cleaning
        create_mock.return_value = {'port': self.neutron_port}
        expected = {self.ports[0].uuid: self.neutron_port['id']}
        api = dhcp_factory.DHCPFactory().provider

        with task_manager.acquire(self.context, self.node.uuid) as task:
            ports = api.create_cleaning_ports(task)
            self.assertEqual(expected, ports)
            create_mock.assert_called_once_with({
                'port': {
                    'network_id': '00000000-0000-0000-0000-000000000000',
                    'admin_state_up': True,
                    'mac_address': self.ports[0].address
                }
            })
Beispiel #5
0
    def test_get_ip_addresses_for_port_and_portgroup(self, get_ip_mock,
                                                     client_mock):
        object_utils.create_test_portgroup(
            self.context, node_id=self.node.id, address='aa:bb:cc:dd:ee:ff',
            uuid=uuidutils.generate_uuid(),
            internal_info={'tenant_vif_port_id': 'test-vif-A'})

        with task_manager.acquire(self.context, self.node.uuid) as task:
            api = dhcp_factory.DHCPFactory().provider
            api.get_ip_addresses(task)
            get_ip_mock.assert_has_calls(
                [mock.call(mock.ANY, task, task.ports[0],
                           client_mock.return_value),
                 mock.call(mock.ANY, task, task.portgroups[0],
                           client_mock.return_value)]
            )
Beispiel #6
0
 def test__get_port_ip_address_with_exception(self, mock_gnvi, mock_gfia):
     expected = "192.168.1.3"
     port = object_utils.create_test_port(
         self.context,
         node_id=self.node.id,
         id=6,
         address='aa:bb:cc',
         uuid=utils.generate_uuid(),
         extra={'vif_port_id': 'test-vif-A'},
         driver='fake')
     mock_gnvi.return_value = None
     mock_gfia.return_value = expected
     with task_manager.acquire(self.context, self.node.uuid) as task:
         api = dhcp_factory.DHCPFactory().provider
         self.assertRaises(exception.FailedToGetIPAddressOnPort,
                           api._get_port_ip_address, task, port)
Beispiel #7
0
def prepare_instance_pxe_config(task,
                                image_info,
                                iscsi_boot=False,
                                ramdisk_boot=False,
                                ipxe_enabled=False):
    """Prepares the config file for PXE boot

    :param task: a task from TaskManager.
    :param image_info: a dict of values of instance image
                       metadata to set on the configuration file.
    :param iscsi_boot: if boot is from an iSCSI volume or not.
    :param ramdisk_boot: if the boot is to a ramdisk configuration.
    :param ipxe_enabled: Default false boolean to indicate if ipxe
                         is in use by the caller.
    :returns: None
    """

    node = task.node
    # Generate options for both IPv4 and IPv6, and they can be
    # filtered down later based upon the port options.
    # TODO(TheJulia): This should be re-tooled during the Victoria
    # development cycle so that we call a single method and return
    # combined options. The method we currently call is relied upon
    # by two eternal projects, to changing the behavior is not ideal.
    dhcp_opts = dhcp_options_for_instance(task, ipxe_enabled, ip_version=4)
    dhcp_opts += dhcp_options_for_instance(task, ipxe_enabled, ip_version=6)
    provider = dhcp_factory.DHCPFactory()
    provider.update_dhcp(task, dhcp_opts)
    pxe_config_path = get_pxe_config_file_path(node.uuid,
                                               ipxe_enabled=ipxe_enabled)
    if not os.path.isfile(pxe_config_path):
        pxe_options = build_pxe_config_options(task,
                                               image_info,
                                               service=ramdisk_boot,
                                               ipxe_enabled=ipxe_enabled)
        pxe_config_template = (deploy_utils.get_pxe_config_template(node))
        create_pxe_config(task,
                          pxe_options,
                          pxe_config_template,
                          ipxe_enabled=ipxe_enabled)
    deploy_utils.switch_pxe_config(pxe_config_path,
                                   None,
                                   boot_mode_utils.get_boot_mode(node),
                                   False,
                                   iscsi_boot=iscsi_boot,
                                   ramdisk_boot=ramdisk_boot,
                                   ipxe_enabled=ipxe_enabled)
Beispiel #8
0
 def test__get_port_ip_address(self, mock_gnvi, mock_gfia):
     expected = "192.168.1.3"
     port = object_utils.create_test_port(
         self.context,
         node_id=self.node.id,
         id=6,
         address='aa:bb:cc',
         uuid=utils.generate_uuid(),
         extra={'vif_port_id': 'test-vif-A'},
         driver='fake')
     mock_gnvi.return_value = {port.uuid: 'vif-uuid'}
     mock_gfia.return_value = expected
     with task_manager.acquire(self.context, self.node.uuid) as task:
         api = dhcp_factory.DHCPFactory(token=task.context.auth_token)
         api = api.provider
         result = api._get_port_ip_address(task, port.uuid)
     self.assertEqual(expected, result)
Beispiel #9
0
 def test_update_dhcp_set_sleep_and_fake(self, mock_gnvi, mock_updo,
                                         mock_ts, mock_log):
     mock_gnvi.return_value = {
         'ports': {
             'port-uuid': 'vif-uuid'
         },
         'portgroups': {}
     }
     self.config(port_setup_delay=30, group='neutron')
     with task_manager.acquire(self.context, self.node.uuid) as task:
         opts = pxe_utils.dhcp_options_for_instance(task)
         api = dhcp_factory.DHCPFactory()
         api.update_dhcp(task, opts)
         mock_log.debug.assert_called_once_with(
             "Waiting %d seconds for Neutron.", 30)
         mock_ts.assert_called_with(30)
     mock_updo.assert_called_once_with(mock.ANY, 'vif-uuid', opts)
Beispiel #10
0
def clean_up_pxe_config(task):
    """Clean up the TFTP environment for the task's node.

    :param task: A TaskManager instance.

    """
    LOG.debug("Cleaning up PXE config for node %s", task.node.uuid)

    is_uefi_boot_mode = (boot_mode_utils.get_boot_mode_for_deploy(task.node)
                         == 'uefi')
    if is_uefi_boot_mode and not CONF.pxe.ipxe_enabled:
        api = dhcp_factory.DHCPFactory().provider
        ip_addresses = api.get_ip_addresses(task)
        if not ip_addresses:
            return

        for port_ip_address in ip_addresses:
            try:
                # Get xx.xx.xx.xx based grub config file
                ip_address_path = _get_pxe_ip_address_path(port_ip_address,
                                                           False)
                # NOTE(TheJulia): Remove elilo support after the deprecation
                # period, in the Queens release.
                # Get 0AOAOAOA based elilo config file
                hex_ip_path = _get_pxe_ip_address_path(port_ip_address,
                                                       True)
            except exception.InvalidIPv4Address:
                continue
            except exception.FailedToGetIPAddressOnPort:
                continue
            # Cleaning up config files created for grub2.
            ironic_utils.unlink_without_raise(ip_address_path)
            # Cleaning up config files created for elilo.
            ironic_utils.unlink_without_raise(hex_ip_path)

    for port in task.ports:
        client_id = port.extra.get('client-id')
        # syslinux, ipxe, etc.
        ironic_utils.unlink_without_raise(
            _get_pxe_mac_path(port.address, client_id=client_id))
        # Grub2 MAC address based confiuration
        ironic_utils.unlink_without_raise(
            _get_pxe_grub_mac_path(port.address))
    utils.rmtree_without_raise(os.path.join(get_root_dir(),
                                            task.node.uuid))
Beispiel #11
0
 def test_update_dhcp_unset_sleep_and_fake(self, mock_gnvi, mock_log):
     mock_gnvi.return_value = {
         'ports': {
             'port-uuid': 'vif-uuid'
         },
         'portgroups': {}
     }
     with task_manager.acquire(self.context, self.node.uuid) as task:
         opts = pxe_utils.dhcp_options_for_instance(task)
         api = dhcp_factory.DHCPFactory()
         with mock.patch.object(api.provider,
                                'update_port_dhcp_opts',
                                autospec=True) as mock_updo:
             api.update_dhcp(task, opts)
             mock_log.debug.assert_not_called()
             mock_updo.assert_called_once_with('vif-uuid',
                                               opts,
                                               context=task.context)
Beispiel #12
0
    def test_update_port_dhcp_opts(self, mock_client_init, mock_update_port):
        opts = [{
            'opt_name': 'bootfile-name',
            'opt_value': 'pxelinux.0'
        }, {
            'opt_name': 'tftp-server',
            'opt_value': '1.1.1.1'
        }, {
            'opt_name': 'server-ip-address',
            'opt_value': '1.1.1.1'
        }]
        port_id = 'fake-port-id'
        expected = {'port': {'extra_dhcp_opts': opts}}

        mock_client_init.return_value = None
        api = dhcp_factory.DHCPFactory()
        api.provider.update_port_dhcp_opts(port_id, opts)
        mock_update_port.assert_called_once_with(port_id, expected)
Beispiel #13
0
 def test__get_port_ip_address(self, mock_gnvi, mock_gfia):
     expected = "192.168.1.3"
     port = object_utils.create_test_port(
         self.context,
         node_id=self.node.id,
         address='aa:bb:cc:dd:ee:ff',
         uuid=uuidutils.generate_uuid(),
         extra={'vif_port_id': 'test-vif-A'},
         driver='fake')
     mock_gnvi.return_value = {port.uuid: 'vif-uuid'}
     mock_gfia.return_value = expected
     with task_manager.acquire(self.context, self.node.uuid) as task:
         api = dhcp_factory.DHCPFactory().provider
         result = api._get_port_ip_address(task, port.uuid,
                                           mock.sentinel.client)
         mock_gnvi.assert_called_once_with(task)
     self.assertEqual(expected, result)
     mock_gfia.assert_called_once_with('vif-uuid', mock.sentinel.client)
Beispiel #14
0
    def deploy(self, task):
        """Perform a deployment to a node.

        Perform the necessary work to deploy an image onto the specified node.
        This method will be called after prepare(), which may have already
        performed any preparatory steps, such as pre-caching some data for the
        node.

        :param task: a TaskManager instance.
        :returns: status of the deploy. One of ironic.common.states.
        """
        dhcp_opts = pxe_utils.dhcp_options_for_instance(task)
        provider = dhcp_factory.DHCPFactory(token=task.context.auth_token)
        provider.update_dhcp(task, dhcp_opts)
        manager_utils.node_set_boot_device(task, 'pxe', persistent=True)
        manager_utils.node_power_action(task, states.REBOOT)

        return states.DEPLOYWAIT
Beispiel #15
0
 def test_update_dhcp_unset_sleep_and_fake(self, mock_gnvi, mock_updo,
                                           mock_log):
     mock_gnvi.return_value = {
         'ports': {
             'port-uuid': 'vif-uuid'
         },
         'portgroups': {}
     }
     with task_manager.acquire(self.context, self.node.uuid) as task:
         opts = pxe_utils.dhcp_options_for_instance(task)
         api = dhcp_factory.DHCPFactory()
         api.update_dhcp(task, opts)
         mock_log.debug.assert_not_called()
         mock_log.warning.assert_not_called()
     mock_updo.assert_called_once_with(mock.ANY,
                                       'vif-uuid',
                                       opts,
                                       token=self.context.auth_token)
Beispiel #16
0
    def deploy(self, task):
        """Start deployment of the task's node'.

        Fetches instance image, creates a temporary keystone token file,
        updates the DHCP port options for next boot, and issues a reboot
        request to the power driver.
        This causes the node to boot into the deployment ramdisk and triggers
        the next phase of PXE-based deployment via
        VendorPassthru._continue_deploy().

        :param task: a TaskManager instance containing the node to act on.
        :returns: deploy state DEPLOYWAIT.
        """
        iscsi_deploy.cache_instance_image(task.context, task.node)
        iscsi_deploy.check_image_size(task)

        # TODO(yuriyz): more secure way needed for pass auth token
        #               to deploy ramdisk
        _create_token_file(task)
        dhcp_opts = pxe_utils.dhcp_options_for_instance(task)
        provider = dhcp_factory.DHCPFactory()
        provider.update_dhcp(task, dhcp_opts)

        # NOTE(faizan): Under UEFI boot mode, setting of boot device may differ
        # between different machines. IPMI does not work for setting boot
        # devices in UEFI mode for certain machines.
        # Expected IPMI failure for uefi boot mode. Logging a message to
        # set the boot device manually and continue with deploy.
        try:
            manager_utils.node_set_boot_device(task, 'pxe', persistent=True)
        except exception.IPMIFailure:
            if driver_utils.get_node_capability(task.node,
                                                'boot_mode') == 'uefi':
                LOG.warning(
                    _LW("ipmitool is unable to set boot device while "
                        "the node is in UEFI boot mode."
                        "Please set the boot device manually."))
            else:
                raise

        manager_utils.node_power_action(task, states.REBOOT)

        return states.DEPLOYWAIT
Beispiel #17
0
 def test_update_dhcp_set_sleep_and_ssh(self, mock_gnvi, mock_updo,
                                        mock_ts):
     mock_gnvi.return_value = {
         'ports': {
             'port-uuid': 'vif-uuid'
         },
         'portgroups': {}
     }
     self.config(port_setup_delay=30, group='neutron')
     with task_manager.acquire(self.context, self.node.uuid) as task:
         task.driver.power = ssh.SSHPower()
         opts = pxe_utils.dhcp_options_for_instance(task)
         api = dhcp_factory.DHCPFactory()
         api.update_dhcp(task, opts)
         mock_ts.assert_called_with(30)
     mock_updo.assert_called_once_with(mock.ANY,
                                       'vif-uuid',
                                       opts,
                                       token=self.context.auth_token)
Beispiel #18
0
    def prepare_cleaning(self, task):
        """Boot into the agent to prepare for cleaning."""
        # Create cleaning ports if necessary
        provider = dhcp_factory.DHCPFactory().provider

        # If we have left over ports from a previous cleaning, remove them
        if getattr(provider, 'delete_cleaning_ports', None):
            provider.delete_cleaning_ports(task)

        if getattr(provider, 'create_cleaning_ports', None):
            provider.create_cleaning_ports(task)

        # Append required config parameters to node's driver_internal_info
        # to pass to IPA.
        deploy_utils.agent_add_clean_params(task)

        _prepare_agent_vmedia_boot(task)
        # Tell the conductor we are waiting for the agent to boot.
        return states.CLEANING
Beispiel #19
0
def clean_up_pxe_config(task, ipxe_enabled=False):
    """Clean up the TFTP environment for the task's node.

    :param task: A TaskManager instance.

    """
    LOG.debug("Cleaning up PXE config for node %s", task.node.uuid)

    is_uefi_boot_mode = (boot_mode_utils.get_boot_mode(task.node) == 'uefi')

    if is_uefi_boot_mode and not ipxe_enabled:
        api = dhcp_factory.DHCPFactory().provider
        ip_addresses = api.get_ip_addresses(task)
        if not ip_addresses:
            return

        for port_ip_address in ip_addresses:
            try:
                # Get xx.xx.xx.xx based grub config file
                ip_address_path = _get_pxe_ip_address_path(port_ip_address)
            except exception.InvalidIPv4Address:
                continue
            except exception.FailedToGetIPAddressOnPort:
                continue
            # Cleaning up config files created for grub2.
            ironic_utils.unlink_without_raise(ip_address_path)

    for port in task.ports:
        client_id = port.extra.get('client-id')
        # syslinux, ipxe, etc.
        ironic_utils.unlink_without_raise(
            _get_pxe_mac_path(port.address,
                              client_id=client_id,
                              ipxe_enabled=ipxe_enabled))
        # Grub2 MAC address based confiuration
        ironic_utils.unlink_without_raise(
            _get_pxe_grub_mac_path(port.address, ipxe_enabled=ipxe_enabled))
    if ipxe_enabled:
        utils.rmtree_without_raise(
            os.path.join(get_ipxe_root_dir(), task.node.uuid))
    else:
        utils.rmtree_without_raise(os.path.join(get_root_dir(),
                                                task.node.uuid))
Beispiel #20
0
    def take_over(self, task):
        """Take over management of this node from a dead conductor.

        If conductors' hosts maintain a static relationship to nodes, this
        method should be implemented by the driver to allow conductors to
        perform the necessary work during the remapping of nodes to conductors
        when a conductor joins or leaves the cluster.

        For example, the PXE driver has an external dependency:
            Neutron must forward DHCP BOOT requests to a conductor which has
            prepared the tftpboot environment for the given node. When a
            conductor goes offline, another conductor must change this setting
            in Neutron as part of remapping that node's control to itself.
            This is performed within the `takeover` method.

        :param task: a TaskManager instance.
        """
        provider = dhcp_factory.DHCPFactory(token=task.context.auth_token)
        provider.update_dhcp(task, CONF.agent.agent_pxe_bootfile_name)
Beispiel #21
0
    def test_update_port_dhcp_opts_v6(self, update_mock, client_mock):
        opts = [{
            'opt_name': 'bootfile-name',
            'opt_value': 'pxelinux.0',
            'ip_version': 4
        }, {
            'opt_name': 'tftp-server',
            'opt_value': '1.1.1.1',
            'ip_version': 4
        }, {
            'opt_name': 'server-ip-address',
            'opt_value': '1.1.1.1',
            'ip_version': 4
        }, {
            'opt_name': 'bootfile-url',
            'opt_value': 'tftp://::1/file.name',
            'ip_version': 6
        }]
        port_id = 'fake-port-id'
        expected = {
            'port': {
                'extra_dhcp_opts': [{
                    'opt_name': 'bootfile-url',
                    'opt_value': 'tftp://::1/file.name',
                    'ip_version': 6
                }]
            }
        }
        port_data = {
            "id": port_id,
            "fixed_ips": [{
                "ip_address": "2001:db8::201",
            }],
        }
        client_mock.return_value.show_port.return_value = {'port': port_data}

        api = dhcp_factory.DHCPFactory()
        with task_manager.acquire(self.context, self.node.uuid) as task:
            api.provider.update_port_dhcp_opts(port_id,
                                               opts,
                                               context=task.context)
        update_mock.assert_called_once_with(task.context, port_id, expected)
Beispiel #22
0
    def test_update_port_dhcp_opts(self, update_mock):
        opts = [{
            'opt_name': 'bootfile-name',
            'opt_value': 'pxelinux.0'
        }, {
            'opt_name': 'tftp-server',
            'opt_value': '1.1.1.1'
        }, {
            'opt_name': 'server-ip-address',
            'opt_value': '1.1.1.1'
        }]
        port_id = 'fake-port-id'
        expected = {'port': {'extra_dhcp_opts': opts}}

        api = dhcp_factory.DHCPFactory()
        with task_manager.acquire(self.context, self.node.uuid) as task:
            api.provider.update_port_dhcp_opts(port_id,
                                               opts,
                                               context=task.context)
        update_mock.assert_called_once_with(task.context, port_id, expected)
Beispiel #23
0
    def clean_up(self, task):
        """Clean up the deployment environment for this node.

        If preparation of the deployment environment ahead of time is possible,
        this method should be implemented by the driver. It should erase
        anything cached by the `prepare` method.

        If implemented, this method must be idempotent. It may be called
        multiple times for the same node on the same conductor, and it may be
        called by multiple conductors in parallel. Therefore, it must not
        require an exclusive lock.

        This method is called before `tear_down`.

        :param task: a TaskManager instance.
        """
        if CONF.agent.manage_agent_boot:
            task.driver.boot.clean_up_ramdisk(task)
        provider = dhcp_factory.DHCPFactory()
        provider.clean_dhcp(task)
Beispiel #24
0
def _link_ip_address_pxe_configs(task):
    """Link each IP address with the PXE configuration file.

    :param task: A TaskManager instance.
    :raises: FailedToGetIPAddressOnPort
    :raises: InvalidIPv4Address

    """
    pxe_config_file_path = get_pxe_config_file_path(task.node.uuid)

    api = dhcp_factory.DHCPFactory().provider
    ip_addrs = api.get_ip_addresses(task)
    if not ip_addrs:
        raise exception.FailedToGetIPAddressOnPort(
            _("Failed to get IP address for any port on node %s.") %
            task.node.uuid)
    for port_ip_address in ip_addrs:
        ip_address_path = _get_pxe_ip_address_path(port_ip_address)
        utils.unlink_without_raise(ip_address_path)
        utils.create_link_without_raise(pxe_config_file_path, ip_address_path)
Beispiel #25
0
    def test_update_port_dhcp_opts_with_exception(self, update_mock,
                                                  client_mock):
        opts = [{}]
        port_id = 'fake-port-id'
        port_data = {
            "id": port_id,
            "fixed_ips": [{
                "ip_address": "192.168.1.3",
            }],
        }
        client_mock.return_value.show_port.return_value = {'port': port_data}
        update_mock.side_effect = (neutron_client_exc.NeutronClientException())

        api = dhcp_factory.DHCPFactory()
        with task_manager.acquire(self.context, self.node.uuid) as task:
            self.assertRaises(exception.FailedToUpdateDHCPOptOnPort,
                              api.provider.update_port_dhcp_opts,
                              port_id,
                              opts,
                              context=task.context)
Beispiel #26
0
def prepare_cleaning_ports(task):
    """Prepare the Ironic ports of the node for cleaning.

    This method deletes the cleaning ports currently existing
    for all the ports of the node and then creates a new one
    for each one of them.  It also adds 'vif_port_id' to port.extra
    of each Ironic port, after creating the cleaning ports.

    :param task: a TaskManager object containing the node
    :raises NodeCleaningFailure: if the previous cleaning ports cannot
        be removed or if new cleaning ports cannot be created
    """
    provider = dhcp_factory.DHCPFactory()
    # If we have left over ports from a previous cleaning, remove them
    if getattr(provider.provider, 'delete_cleaning_ports', None):
        # Allow to raise if it fails, is caught and handled in conductor
        provider.provider.delete_cleaning_ports(task)

    # Create cleaning ports if necessary
    if getattr(provider.provider, 'create_cleaning_ports', None):
        # Allow to raise if it fails, is caught and handled in conductor
        ports = provider.provider.create_cleaning_ports(task)

        # Add vif_port_id for each of the ports because some boot
        # interfaces expects these to prepare for booting ramdisk.
        for port in task.ports:
            extra_dict = port.extra
            try:
                extra_dict['vif_port_id'] = ports[port.uuid]
            except KeyError:
                # This is an internal error in Ironic.  All DHCP providers
                # implementing create_cleaning_ports are supposed to
                # return a VIF port ID for all Ironic ports.  But
                # that doesn't seem to be true here.
                error = (_("When creating cleaning ports, DHCP provider "
                           "didn't return VIF port ID for %s") % port.uuid)
                raise exception.NodeCleaningFailure(
                    node=task.node.uuid, reason=error)
            else:
                port.extra = extra_dict
                port.save()
Beispiel #27
0
    def test_update_port_address_with_binding(self, mock_client_init,
                                              mock_update_port,
                                              mock_show_port):
        address = 'fe:54:00:77:07:d9'
        port_id = 'fake-port-id'
        expected = {
            'port': {
                'mac_address': address,
                'binding:host_id': 'host'
            }
        }
        mock_client_init.return_value = None
        mock_show_port.return_value = {'port': {'binding:host_id': 'host'}}

        api = dhcp_factory.DHCPFactory()
        api.provider.update_port_address(port_id, address)
        mock_update_port.assert_any_call(port_id,
                                         {'port': {
                                             'binding:host_id': ''
                                         }})
        mock_update_port.assert_any_call(port_id, expected)
Beispiel #28
0
 def test_update_dhcp_unset_sleep_and_ssh(self, mock_gnvi, mock_updo,
                                          mock_ts, mock_log):
     mock_gnvi.return_value = {
         'ports': {
             'port-uuid': 'vif-uuid'
         },
         'portgroups': {}
     }
     with task_manager.acquire(self.context, self.node.uuid) as task:
         opts = pxe_utils.dhcp_options_for_instance(task)
         task.driver.power = ssh.SSHPower()
         api = dhcp_factory.DHCPFactory()
         api.update_dhcp(task, opts)
         self.assertTrue(mock_log.warning.called)
         self.assertIn('Setting the port delay to 15 for SSH',
                       mock_log.warning.call_args[0][0])
         mock_ts.assert_called_with(15)
     mock_updo.assert_called_once_with(mock.ANY,
                                       'vif-uuid',
                                       opts,
                                       token=self.context.auth_token)
Beispiel #29
0
 def _test__get_port_ip_address(self, mock_gfia, network):
     expected = "192.168.1.3"
     fake_vif = 'test-vif-%s' % network
     port = object_utils.create_test_port(
         self.context,
         node_id=self.node.id,
         address='aa:bb:cc:dd:ee:ff',
         uuid=uuidutils.generate_uuid(),
         extra={'vif_port_id': fake_vif} if network == 'tenant' else {},
         internal_info={
             'cleaning_vif_port_id':
             (fake_vif if network == 'cleaning' else None),
             'provisioning_vif_port_id':
             (fake_vif if network == 'provisioning' else None),
         })
     mock_gfia.return_value = expected
     with task_manager.acquire(self.context, self.node.uuid) as task:
         api = dhcp_factory.DHCPFactory().provider
         result = api._get_port_ip_address(task, port, mock.sentinel.client)
     self.assertEqual(expected, result)
     mock_gfia.assert_called_once_with(fake_vif, mock.sentinel.client)
Beispiel #30
0
def prepare_instance_pxe_config(task,
                                image_info,
                                iscsi_boot=False,
                                ramdisk_boot=False,
                                ipxe_enabled=False):
    """Prepares the config file for PXE boot

    :param task: a task from TaskManager.
    :param image_info: a dict of values of instance image
                       metadata to set on the configuration file.
    :param iscsi_boot: if boot is from an iSCSI volume or not.
    :param ramdisk_boot: if the boot is to a ramdisk configuration.
    :param ipxe_enabled: Default false boolean to indicate if ipxe
                         is in use by the caller.
    :returns: None
    """

    node = task.node
    dhcp_opts = dhcp_options_for_instance(task, ipxe_enabled)
    provider = dhcp_factory.DHCPFactory()
    provider.update_dhcp(task, dhcp_opts)
    pxe_config_path = get_pxe_config_file_path(node.uuid,
                                               ipxe_enabled=ipxe_enabled)
    if not os.path.isfile(pxe_config_path):
        pxe_options = build_pxe_config_options(task,
                                               image_info,
                                               service=ramdisk_boot,
                                               ipxe_enabled=ipxe_enabled)
        pxe_config_template = (deploy_utils.get_pxe_config_template(node))
        create_pxe_config(task,
                          pxe_options,
                          pxe_config_template,
                          ipxe_enabled=ipxe_enabled)
    deploy_utils.switch_pxe_config(pxe_config_path,
                                   None,
                                   boot_mode_utils.get_boot_mode(node),
                                   False,
                                   iscsi_boot=iscsi_boot,
                                   ramdisk_boot=ramdisk_boot,
                                   ipxe_enabled=ipxe_enabled)