Use i18n for undercloud installer and utils messages

Closes-bug: #1751078

Change-Id: I4402f79b1155630fc7c7f702c58e844d05284246
Signed-off-by: Bogdan Dobrelya <bdobreli@redhat.com>
changes/98/568298/6
Bogdan Dobrelya 4 years ago
parent 3d9183fc03
commit 4437037fa0
  1. 58
      tripleoclient/config/standalone.py
  2. 163
      tripleoclient/config/undercloud.py
  3. 60
      tripleoclient/utils.py
  4. 47
      tripleoclient/v1/tripleo_deploy.py
  5. 8
      tripleoclient/v1/undercloud.py
  6. 9
      tripleoclient/v1/undercloud_backup.py
  7. 12
      tripleoclient/v1/undercloud_config.py
  8. 98
      tripleoclient/v1/undercloud_preflight.py

@ -13,7 +13,7 @@
# under the License.
#
from osc_lib.i18n import _
from oslo_config import cfg
from tripleoclient.config.base import BaseConfig
@ -57,49 +57,49 @@ class StandaloneConfig(BaseConfig):
# service enablement
cfg.BoolOpt('enable_cinder',
default=cinder,
help=(
help=_(
'Whether to install the Volume service. It is not '
'currently used in the undercloud.')),
cfg.BoolOpt('enable_ironic',
default=ironic,
help=('Whether to enable the ironic service.')),
help=_('Whether to enable the ironic service.')),
cfg.BoolOpt('enable_ironic_inspector',
default=ironic_inspector,
help=(
help=_(
'Whether to enable the ironic inspector service.')
),
cfg.BoolOpt('enable_mistral',
default=mistral,
help=('Whether to enable the mistral service.')),
help=_('Whether to enable the mistral service.')),
cfg.BoolOpt('enable_novajoin',
default=novajoin,
help=('Whether to install novajoin metadata service '
'in the Undercloud.')
help=_('Whether to install novajoin metadata service '
'in the Undercloud.')
),
cfg.BoolOpt('enable_tempest',
default=tempest,
help=('Whether to install Tempest in the Undercloud.'
'This is a no-op for containerized undercloud.')
help=_('Whether to install Tempest in the Undercloud.'
'This is a no-op for containerized undercloud.')
),
cfg.BoolOpt('enable_telemetry',
default=telemetry,
help=('Whether to install Telemetry services '
'(ceilometer, gnocchi, aodh, panko ) in the '
'Undercloud.')
help=_('Whether to install Telemetry services '
'(ceilometer, gnocchi, aodh, panko ) in the '
'Undercloud.')
),
cfg.BoolOpt('enable_ui',
default=tripleo_ui,
help=('Whether to install the TripleO UI.')
help=_('Whether to install the TripleO UI.')
),
cfg.BoolOpt('enable_validations',
default=validations,
help=(
help=_(
'Whether to install requirements to run the '
'TripleO validations.')
),
cfg.BoolOpt('enable_zaqar',
default=zaqar,
help=('Whether to enable the zaqar service.')),
help=_('Whether to enable the zaqar service.')),
]
return self.sort_opts(_opts)
@ -108,14 +108,14 @@ class StandaloneConfig(BaseConfig):
_opts = [
# deployment options
cfg.StrOpt('deployment_user',
help=(
help=_(
'User used to run openstack undercloud install '
'command which will be used to add the user to the '
'docker group, required to upload containers'),
),
cfg.StrOpt('hieradata_override',
default='',
help=(
help=_(
'Path to hieradata override file. Relative paths '
'get computed inside of $HOME. When it points to a '
'heat env file, it is passed in t-h-t via "-e '
@ -128,7 +128,7 @@ class StandaloneConfig(BaseConfig):
),
cfg.StrOpt('net_config_override',
default='',
help=(
help=_(
'Path to network config override template.'
'Relative paths get computed inside of the '
'given heat templates directory. Must be in '
@ -146,42 +146,42 @@ class StandaloneConfig(BaseConfig):
),
cfg.StrOpt('templates',
default='',
help=('heat templates file to override.')
help=_('heat templates file to override.')
),
cfg.StrOpt('roles_file',
default=None,
help=('Roles file to override for heat. '
'The file path is related to the templates path')
help=_('Roles file to override for heat. '
'The file path is related to the templates path')
),
cfg.BoolOpt('heat_native',
default=True,
help=('Use native heat templates.')),
help=_('Use native heat templates.')),
cfg.StrOpt('heat_container_image',
default='',
help=('URL for the heat container image to use.')
help=_('URL for the heat container image to use.')
),
cfg.StrOpt('container_images_file',
default='',
help=(
help=_(
'Heat environment file with parameters for all '
'required container images. Or alternatively, '
'parameter "ContainerImagePrepare" to drive the '
'required image preparation.')),
cfg.ListOpt('custom_env_files',
default=[],
help=('List of any custom environment yaml files to '
'use')),
help=_('List of any custom environment yaml files to '
'use')),
# docker config bits
cfg.StrOpt('docker_registry_mirror',
default='',
help=(
help=_(
'An optional docker \'registry-mirror\' that will '
'beconfigured in /etc/docker/daemon.json.')
),
cfg.ListOpt('docker_insecure_registries',
default=[],
help=('Used to add custom insecure registries in '
'/etc/sysconfig/docker.')
help=_('Used to add custom insecure registries in '
'/etc/sysconfig/docker.')
),
]
return self.sort_opts(_base_opts + _opts)

@ -13,7 +13,7 @@
# under the License.
#
from osc_lib.i18n import _
from oslo_config import cfg
from tripleoclient.config.standalone import StandaloneConfig
@ -50,7 +50,7 @@ class UndercloudConfig(StandaloneConfig):
_base_opts = super(UndercloudConfig, self).get_base_opts()
_opts = [
cfg.StrOpt('undercloud_hostname',
help=(
help=_(
'Fully qualified hostname (including domain) to '
'set on the Undercloud. If left unset, the current '
'hostname will be used, but the user is '
@ -61,7 +61,7 @@ class UndercloudConfig(StandaloneConfig):
),
cfg.StrOpt('local_ip',
default='192.168.24.1/24',
help=(
help=_(
'IP information for the interface on the '
'Undercloud that will be handling the PXE boots '
'and DHCP for Overcloud instances. The IP portion '
@ -73,63 +73,66 @@ class UndercloudConfig(StandaloneConfig):
cfg.StrOpt('undercloud_public_host',
deprecated_name='undercloud_public_vip',
default='192.168.24.2',
help=('Virtual IP or DNS address to use for the public '
'endpoints of Undercloud services. Only used '
'with SSL.')
help=_(
'Virtual IP or DNS address to use for the public '
'endpoints of Undercloud services. Only used '
'with SSL.')
),
cfg.StrOpt('undercloud_admin_host',
deprecated_name='undercloud_admin_vip',
default='192.168.24.3',
help=('Virtual IP or DNS address to use for the admin '
'endpoints of Undercloud services. Only used '
'with SSL.')
help=_(
'Virtual IP or DNS address to use for the admin '
'endpoints of Undercloud services. Only used '
'with SSL.')
),
cfg.ListOpt('undercloud_nameservers',
default=[],
help=(
help=_(
'DNS nameserver(s) to use for the undercloud '
'node.'),
),
cfg.ListOpt('undercloud_ntp_servers',
default=[],
help=('List of ntp servers to use.')),
help=_('List of ntp servers to use.')),
cfg.StrOpt('overcloud_domain_name',
default='localdomain',
help=(
help=_(
'DNS domain name to use when deploying the '
'overcloud. The overcloud parameter "CloudDomain" '
'must be set to a matching value.')
),
cfg.ListOpt('subnets',
default=SUBNETS_DEFAULT,
help=('List of routed network subnets for '
'provisioning and introspection. Comma '
'separated list of names/tags. For each network '
'a section/group needs to be added to the '
'configuration file with these parameters set: '
'cidr, dhcp_start, dhcp_end, '
'inspection_iprange, gateway and '
'masquerade_network.'
'\n\n'
'Example:\n\n'
'subnets = subnet1,subnet2\n'
'\n'
'An example section/group in config file:\n'
'\n'
'[subnet1]\n'
'cidr = 192.168.10.0/24\n'
'dhcp_start = 192.168.10.100\n'
'dhcp_end = 192.168.10.200\n'
'inspection_iprange = 192.168.10.20,'
'192.168.10.90\n'
'gateway = 192.168.10.254\n'
'masquerade = True'
'\n'
'[subnet2]\n'
'. . .\n')),
help=_(
'List of routed network subnets for '
'provisioning and introspection. Comma '
'separated list of names/tags. For each network '
'a section/group needs to be added to the '
'configuration file with these parameters set: '
'cidr, dhcp_start, dhcp_end, '
'inspection_iprange, gateway and '
'masquerade_network.'
'\n\n'
'Example:\n\n'
'subnets = subnet1,subnet2\n'
'\n'
'An example section/group in config file:\n'
'\n'
'[subnet1]\n'
'cidr = 192.168.10.0/24\n'
'dhcp_start = 192.168.10.100\n'
'dhcp_end = 192.168.10.200\n'
'inspection_iprange = 192.168.10.20,'
'192.168.10.90\n'
'gateway = 192.168.10.254\n'
'masquerade = True'
'\n'
'[subnet2]\n'
'. . .\n')),
cfg.StrOpt('local_subnet',
default=SUBNETS_DEFAULT[0],
help=(
help=_(
'Name of the local subnet, where the PXE boot and '
'DHCP interfaces for overcloud instances is '
'located. The IP address of the '
@ -137,7 +140,7 @@ class UndercloudConfig(StandaloneConfig):
'in this subnet.')),
cfg.StrOpt('undercloud_service_certificate',
default='',
help=(
help=_(
'Certificate file to use for OpenStack service SSL '
'connections. Setting this enables SSL for the '
'OpenStack API endpoints, leaving it unset '
@ -145,7 +148,7 @@ class UndercloudConfig(StandaloneConfig):
),
cfg.BoolOpt('generate_service_certificate',
default=True,
help=(
help=_(
'When set to True, an SSL certificate will be '
'generated as part of the undercloud install and '
'this certificate will be used in place of the '
@ -158,19 +161,19 @@ class UndercloudConfig(StandaloneConfig):
),
cfg.StrOpt('certificate_generation_ca',
default='local',
help=('The certmonger nickname of the CA from which '
'the certificate will be requested. This is used '
'only if the generate_service_certificate option '
'is set. Note that if the "local" CA is selected '
'the certmonger\'s local CA certificate will be '
'extracted to /etc/pki/ca-trust/source/anchors/'
'cm-local-ca.pem and subsequently added to the '
'trust chain.')
help=_(
'The certmonger nickname of the CA from which '
'the certificate will be requested. This is used '
'only if the generate_service_certificate option '
'is set. Note that if the "local" CA is selected '
'the certmonger\'s local CA certificate will be '
'extracted to /etc/pki/ca-trust/source/anchors/'
'cm-local-ca.pem and subsequently added to the '
'trust chain.')
),
cfg.StrOpt('service_principal',
default='',
help=(
help=_(
'The kerberos principal for the service that will '
'use the certificate. This is only needed if your '
'CA requires a kerberos principal. e.g. with '
@ -178,25 +181,25 @@ class UndercloudConfig(StandaloneConfig):
),
cfg.StrOpt('local_interface',
default='eth1',
help=('Network interface on the Undercloud that will '
'be handling the PXE boots and DHCP for '
'Overcloud instances.')
help=_('Network interface on the Undercloud that will '
'be handling the PXE boots and DHCP for '
'Overcloud instances.')
),
cfg.IntOpt('local_mtu',
default=1500,
help=('MTU to use for the local_interface.')
help=_('MTU to use for the local_interface.')
),
cfg.StrOpt('inspection_interface',
default='br-ctlplane',
deprecated_name='discovery_interface',
help=(
help=_(
'Network interface on which inspection dnsmasq '
'will listen. If in doubt, use the default value.')
),
cfg.BoolOpt('inspection_extras',
default=True,
help=(
help=_(
'Whether to enable extra hardware collection '
'during the inspection process. Requires '
'python-hardware or python-hardware-detect '
@ -204,13 +207,13 @@ class UndercloudConfig(StandaloneConfig):
cfg.BoolOpt('inspection_runbench',
default=False,
deprecated_name='discovery_runbench',
help=(
help=_(
'Whether to run benchmarks when inspecting '
'nodes. Requires inspection_extras set to True.')
),
cfg.BoolOpt('enable_node_discovery',
default=False,
help=(
help=_(
'Makes ironic-inspector enroll any unknown node '
'that PXE-boots introspection ramdisk in Ironic. '
'By default, the "fake" driver is used for new '
@ -222,7 +225,7 @@ class UndercloudConfig(StandaloneConfig):
),
cfg.StrOpt('discovery_default_driver',
default='ipmi',
help=(
help=_(
'The default driver or hardware type to use for '
'newly discovered nodes (requires '
'enable_node_discovery set to True). It is '
@ -230,39 +233,39 @@ class UndercloudConfig(StandaloneConfig):
),
cfg.BoolOpt('undercloud_debug',
default=True,
help=(
help=_(
'Whether to enable the debug log level for '
'Undercloud OpenStack services.')
),
cfg.BoolOpt('undercloud_update_packages',
default=False,
help=(
help=_(
'Whether to update packages during the Undercloud '
'install. This is a no-op for containerized '
'undercloud.')
),
cfg.BoolOpt('enable_container_images_build',
default=True,
help=(
help=_(
'Whether to enable docker container images to be '
'build on the undercloud.')
),
cfg.StrOpt('ipa_otp',
default='',
help=(
help=_(
'One Time Password to register Undercloud node '
'with an IPA server. Required when '
'enable_novajoin = True.')
),
cfg.BoolOpt('ipxe_enabled',
default=True,
help=('Whether to use iPXE for deploy and '
'inspection.'),
help=_('Whether to use iPXE for deploy and '
'inspection.'),
deprecated_name='ipxe_deploy',
),
cfg.IntOpt('scheduler_max_attempts',
default=30, min=1,
help=(
help=_(
'Maximum number of attempts the scheduler will '
'make when deploying the instance. You should keep '
'it greater or equal to the number of bare metal '
@ -270,20 +273,21 @@ class UndercloudConfig(StandaloneConfig):
'potential race condition when scheduling.')),
cfg.BoolOpt('clean_nodes',
default=False,
help=(
help=_(
'Whether to clean overcloud nodes (wipe the hard '
'drive) between deployments and after the '
'introspection.')),
cfg.ListOpt('enabled_hardware_types',
default=['ipmi', 'redfish', 'ilo', 'idrac'],
help=('List of enabled bare metal hardware types '
'(next generation drivers).')),
help=_('List of enabled bare metal hardware types '
'(next generation drivers).')),
cfg.BoolOpt('enable_routed_networks',
default=False,
help=('Enable support for routed ctlplane networks.')),
help=_(
'Enable support for routed ctlplane networks.')),
cfg.BoolOpt('enable_swift_encryption',
default=False,
help=(
help=_(
'Whether to enable Swift encryption at-rest or '
'not.'
)),
@ -300,23 +304,24 @@ class UndercloudConfig(StandaloneConfig):
cfg.StrOpt('cidr',
default='192.168.24.0/24',
deprecated_opts=_deprecated_opt_network_cidr,
help=('Network CIDR for the Neutron-managed subnet for '
'Overcloud instances.')),
help=_(
'Network CIDR for the Neutron-managed subnet for '
'Overcloud instances.')),
cfg.StrOpt('dhcp_start',
default='192.168.24.5',
deprecated_opts=_deprecated_opt_dhcp_start,
help=(
help=_(
'Start of DHCP allocation range for PXE and DHCP '
'of Overcloud instances on this network.')),
cfg.StrOpt('dhcp_end',
default='192.168.24.24',
deprecated_opts=_deprecated_opt_dhcp_end,
help=('End of DHCP allocation range for PXE and DHCP '
'of Overcloud instances on this network.')),
help=_('End of DHCP allocation range for PXE and DHCP '
'of Overcloud instances on this network.')),
cfg.StrOpt('inspection_iprange',
default='192.168.24.100,192.168.24.120',
deprecated_opts=_deprecated_opt_inspection_iprange,
help=(
help=_(
'Temporary IP range that will be given to nodes on '
'this network during the inspection process. '
'Should not overlap with the range defined by '
@ -326,12 +331,12 @@ class UndercloudConfig(StandaloneConfig):
cfg.StrOpt('gateway',
default='192.168.24.1',
deprecated_opts=_deprecated_opt_network_gateway,
help=(
help=_(
'Network gateway for the Neutron-managed network '
'for Overcloud instances on this network.')),
cfg.BoolOpt('masquerade',
default=False,
help=(
help=_(
'The network will be masqueraded for external '
'access.')),
]

@ -101,8 +101,8 @@ def store_cli_param(command_name, parsed_args):
try:
os.mkdir(history_path)
except OSError as e:
messages = "Unable to create TripleO history directory: " \
"{0}, {1}".format(history_path, e)
messages = _("Unable to create TripleO history directory: "
"{0}, {1}").format(history_path, e)
raise OSError(messages)
if os.path.isdir(history_path):
try:
@ -114,12 +114,12 @@ def store_cli_param(command_name, parsed_args):
history.write(' '.join([str(datetime.datetime.now()),
str(command_name), used_args, "\n"]))
except IOError as e:
messages = "Unable to write into TripleO history file: "
"{0}, {1}".format(history_path, e)
messages = _("Unable to write into TripleO history file: "
"{0}, {1}").format(history_path, e)
raise IOError(messages)
else:
raise exceptions.InvalidConfiguration("Target path %s is not a "
"directory" % history_path)
raise exceptions.InvalidConfiguration(_("Target path %s is not a "
"directory") % history_path)
def create_tempest_deployer_input(config_name='tempest-deployer-input.conf'):
@ -247,9 +247,9 @@ def wait_for_provision_state(baremetal_client, node_uuid, provision_state,
# node.last_error should be None after any successful operation
if node.last_error:
raise exceptions.StateTransitionFailed(
raise exceptions.StateTransitionFailed(_(
"Error transitioning node %(uuid)s to provision state "
"%(state)s: %(error)s. Now in state %(actual)s." % {
"%(state)s: %(error)s. Now in state %(actual)s.") % {
'uuid': node_uuid,
'state': provision_state,
'error': node.last_error,
@ -259,9 +259,9 @@ def wait_for_provision_state(baremetal_client, node_uuid, provision_state,
time.sleep(sleep)
raise exceptions.Timeout(
raise exceptions.Timeout(_(
"Node %(uuid)s did not reach provision state %(state)s. "
"Now in state %(actual)s." % {
"Now in state %(actual)s.") % {
'uuid': node_uuid,
'state': provision_state,
'actual': node.provision_state
@ -315,18 +315,18 @@ def set_nodes_state(baremetal_client, nodes, transition, target_state,
if node.provision_state in skipped_states:
continue
log.debug(
"Setting provision state from '{0}' to '{1}' for Node {2}"
log.debug(_(
"Setting provision state from '{0}' to '{1}' for Node {2}")
.format(node.provision_state, transition, node.uuid))
baremetal_client.node.set_provision_state(node.uuid, transition)
try:
wait_for_provision_state(baremetal_client, node.uuid, target_state)
except exceptions.StateTransitionFailed as e:
log.error("FAIL: State transition failed for Node {0}. {1}"
log.error(_("FAIL: State transition failed for Node {0}. {1}")
.format(node.uuid, e))
except exceptions.Timeout as e:
log.error("FAIL: Timeout waiting for Node {0}. {1}"
log.error(_("FAIL: Timeout waiting for Node {0}. {1}")
.format(node.uuid, e))
yield node.uuid
@ -431,8 +431,8 @@ def file_checksum(filepath):
"""
if not os.path.isfile(filepath):
raise ValueError("The given file {0} is not a regular "
"file".format(filepath))
raise ValueError(_("The given file {0} is not a regular "
"file").format(filepath))
checksum = hashlib.md5()
with open(filepath, 'rb') as f:
while True:
@ -446,9 +446,9 @@ def file_checksum(filepath):
def ensure_run_as_normal_user():
"""Check if the command runs under normal user (EUID!=0)"""
if os.geteuid() == 0:
raise exceptions.RootUserExecution(
raise exceptions.RootUserExecution(_(
'This command cannot run under root user.'
' Switch to a normal user.')
' Switch to a normal user.'))
def get_deployment_user():
@ -847,14 +847,14 @@ def get_tripleo_ansible_inventory(inventory_file='',
'--ansible_ssh_user', ssh_user,
'--static-yaml-inventory', inventory_file)
except processutils.ProcessExecutionError as e:
message = "Failed to generate inventory: %s" % str(e)
message = _("Failed to generate inventory: %s") % str(e)
raise exceptions.InvalidConfiguration(message)
if os.path.exists(inventory_file):
inventory = open(inventory_file, 'r').read()
return inventory
else:
raise exceptions.InvalidConfiguration(
"Inventory file %s can not be found." % inventory_file)
raise exceptions.InvalidConfiguration(_(
"Inventory file %s can not be found.") % inventory_file)
def process_multiple_environments(created_env_files, tht_root,
@ -962,9 +962,9 @@ def prepend_environment(environment_files, templates_dir, environment):
# We need to prepend before the files provided by user.
environment_files.insert(0, full_path)
else:
raise exceptions.InvalidConfiguration(
"Expected environment file %s not found in %s cannot proceed."
% (environment, templates_dir))
raise exceptions.InvalidConfiguration(_(
"Expected environment file {0} not found in {1} cannot proceed.")
.format(environment, templates_dir))
return environment_files
@ -975,12 +975,12 @@ def load_container_registry(log, path):
with open(os.path.abspath(path)) as content:
registry = yaml.load(content.read())
else:
log.warning(
log.warning(_(
"You have not provided a container registry file. Note "
"that none of the containers on your environment will be "
"updated. If you want to update your containers you have "
"to re-run this command and provide the registry file "
"with: --container-registry-file option.")
"with: --container-registry-file option."))
return registry
@ -1082,8 +1082,8 @@ def ffwd_upgrade_operator_confirm(parsed_args_yes, log):
"in production, ensure you are adequately prepared "
"with valid backup of your current deployment state.")
if parsed_args_yes:
log.debug("Fast forward upgrade --yes continuing")
print("Continuing fast forward upgrade")
log.debug(_("Fast forward upgrade --yes continuing"))
print(_("Continuing fast forward upgrade"))
return
else:
# Fix Python 2.x.
@ -1096,6 +1096,6 @@ def ffwd_upgrade_operator_confirm(parsed_args_yes, log):
"cancel. Consider using the --yes parameter if "
"you wish to skip this warning in future. ")
if response != 'yes':
log.debug("Fast forward upgrade cancelled on user request")
print("Cancelling fast forward upgrade")
log.debug(_("Fast forward upgrade cancelled on user request"))
print(_("Cancelling fast forward upgrade"))
sys.exit(1)

@ -31,7 +31,7 @@ from cliff import command
from datetime import datetime
from heatclient.common import event_utils
from heatclient.common import template_utils
from openstackclient.i18n import _
from osc_lib.i18n import _
from six.moves import configparser
from tripleoclient import constants
@ -92,7 +92,7 @@ class Deploy(command.Command):
def _create_install_artifact(self):
"""Create a tarball of the temporary folders used"""
self.log.debug("Preserving deployment artifacts")
self.log.debug(_("Preserving deployment artifacts"))
def remove_output_dir(info):
"""Tar filter to remove output dir from path"""
@ -149,15 +149,15 @@ class Deploy(command.Command):
shutil.rmtree(self.tmp_ansible_dir)
self.tmp_ansible_dir = None
else:
self.log.warning("Not cleaning working directory %s"
self.log.warning(_("Not cleaning working directory %s")
% self.tht_render)
self.log.warning("Not removing temporary environment file %s"
self.log.warning(_("Not removing temporary environment file %s")
% self.tmp_env_file_name)
self.log.warning("Not cleaning ansible directory %s"
self.log.warning(_("Not cleaning ansible directory %s")
% self.tmp_ansible_dir)
def _configure_puppet(self):
self.log.info('Configuring puppet modules symlinks ...')
self.log.info(_('Configuring puppet modules symlinks ...'))
utils.bulk_symlink(self.log, constants.TRIPLEO_PUPPET_MODULES,
constants.PUPPET_MODULES,
constants.PUPPET_BASE)
@ -356,7 +356,7 @@ class Deploy(command.Command):
shutil.copytree(parsed_args.templates, self.tht_render, symlinks=True)
# generate jinja templates by its work dir location
self.log.debug("Using roles file %s" % parsed_args.roles_file)
self.log.debug(_("Using roles file %s") % parsed_args.roles_file)
process_templates = os.path.join(parsed_args.templates,
'tools/process-templates.py')
args = ['python', process_templates, '--roles-data',
@ -367,10 +367,10 @@ class Deploy(command.Command):
self.log.error(msg)
raise exceptions.DeploymentError(msg)
self.log.info("Deploying templates in the directory {0}".format(
os.path.abspath(self.tht_render)))
self.log.info(_("Deploying templates in the directory {0}").format(
os.path.abspath(self.tht_render)))
self.log.warning("** Creating Environment file **")
self.log.warning(_("** Creating Environment file **"))
environments = []
resource_registry_path = os.path.join(
@ -456,7 +456,7 @@ class Deploy(command.Command):
environments = self._setup_heat_environments(parsed_args)
# rewrite paths to consume t-h-t env files from the working dir
self.log.debug("Processing environment files %s" % environments)
self.log.debug(_("Processing environment files %s") % environments)
env_files, env = utils.process_multiple_environments(
environments, self.tht_render, parsed_args.templates,
cleanup=parsed_args.cleanup)
@ -465,7 +465,7 @@ class Deploy(command.Command):
self.tht_render, parsed_args.roles_file)
self._prepare_container_images(env, roles_file)
self.log.debug("Getting template contents")
self.log.debug(_("Getting template contents"))
template_path = os.path.join(self.tht_render, 'overcloud.yaml')
template_files, template = \
template_utils.get_template_contents(template_path)
@ -474,10 +474,10 @@ class Deploy(command.Command):
stack_name = parsed_args.stack
self.log.debug("Deploying stack: %s", stack_name)
self.log.debug("Deploying template: %s", template)
self.log.debug("Deploying environment: %s", env)
self.log.debug("Deploying files: %s", files)
self.log.debug(_("Deploying stack: %s") % stack_name)
self.log.debug(_("Deploying template: %s") % template)
self.log.debug(_("Deploying environment: %s") % env)
self.log.debug(_("Deploying files: %s") % files)
stack_args = {
'stack_name': stack_name,
@ -489,7 +489,7 @@ class Deploy(command.Command):
if parsed_args.timeout:
stack_args['timeout_mins'] = parsed_args.timeout
self.log.warning("** Performing Heat stack create.. **")
self.log.warning(_("** Performing Heat stack create.. **"))
stack = orchestration_client.stacks.create(**stack_args)
stack_id = stack['stack']['id']
@ -499,7 +499,7 @@ class Deploy(command.Command):
stack_config = config.Config(client)
self._create_working_dirs()
self.log.warning('** Downloading undercloud ansible.. **')
self.log.warning(_('** Downloading undercloud ansible.. **'))
# python output buffering is making this seem to take forever..
sys.stdout.flush()
stack_config.write_config(stack_config.fetch_config('undercloud'),
@ -515,14 +515,14 @@ class Deploy(command.Command):
extra_vars = {'Undercloud': {'ansible_connection': 'local'}}
inventory.write_static_inventory(inv_path, extra_vars)
self.log.info('** Downloaded undercloud ansible to %s **' %
self.log.info(_('** Downloaded undercloud ansible to %s **') %
self.tmp_ansible_dir)
sys.stdout.flush()
return self.tmp_ansible_dir
# Never returns, calls exec()
def _launch_ansible_deploy(self, ansible_dir):
self.log.warning('** Running ansible deploy tasks **')
self.log.warning(_('** Running ansible deploy tasks **'))
os.chdir(ansible_dir)
playbook_inventory = os.path.join(ansible_dir, 'inventory.yaml')
cmd = ['ansible-playbook', '-i', playbook_inventory,
@ -669,8 +669,8 @@ class Deploy(command.Command):
if not override_file or not os.path.exists(override_file):
# we should never get here because there's a check in
# undercloud_conf but stranger things have happened.
msg = 'hieradata_override file could not be found %s' %\
override_file
msg = (_('hieradata_override file could not be found %s') %
override_file)
self.log.error(msg)
raise exceptions.DeploymentError(msg)
@ -678,7 +678,8 @@ class Deploy(command.Command):
data = open(target, 'r').read()
hiera_data = yaml.safe_load(data)
if not hiera_data:
msg = 'Unsupported data format in hieradata override %s' % target
msg = (_('Unsupported data format in hieradata override %s') %
target)
self.log.error(msg)
raise exceptions.DeploymentError(msg)
self._create_working_dirs()

@ -72,8 +72,8 @@ class InstallUndercloud(command.Command):
no_validations=no_validations,
verbose_level=self.app_args.verbose_level)
else:
self.log.warning('Non-containerized undercloud deployment is '
'deprecated in Rocky cycle.')
self.log.warning(_('Non-containerized undercloud deployment is '
'deprecated in Rocky cycle.'))
cmd = ["instack-install-undercloud"]
if parsed_args.dry_run:
print(' '.join(cmd))
@ -101,8 +101,8 @@ class UpgradeUndercloud(InstallUndercloud):
print("Running: %s" % ' '.join(cmd))
subprocess.check_call(cmd)
else:
self.log.warning('Non-containerized undercloud deployment is '
'deprecated in Rocky cycle.')
self.log.warning(_('Non-containerized undercloud deployment is '
'deprecated in Rocky cycle.'))
subprocess.check_call(['sudo', 'yum', 'update', '-y',
'instack-undercloud'])
subprocess.check_call("instack-pre-upgrade-undercloud")

@ -16,8 +16,8 @@
import argparse
import logging
from openstackclient.i18n import _
from osc_lib.command import command
from osc_lib.i18n import _
from tripleoclient.workflows import undercloud_backup
LOG = logging.getLogger(__name__ + ".BackupUndercloud")
@ -73,18 +73,18 @@ class BackupUndercloud(command.Command):
"sources_path": files_to_backup
}
LOG.debug('Launch the Undercloud Backup')
LOG.debug(_('Launch the Undercloud Backup'))
try:
output = undercloud_backup.backup(clients, workflow_input)
LOG.info(output)
except Exception as e:
print("Undercloud backup finished with errors")
print(_("Undercloud backup finished with errors"))
print('Output: {}'.format(e))
LOG.info(e)
def take_action(self, parsed_args):
LOG.info(
LOG.info(_(
'\n'
' #############################################################\n'
' # Disclaimer #\n'
@ -95,5 +95,6 @@ class BackupUndercloud(command.Command):
' # #\n'
' # .-Stay safe and avoid future issues-. #\n'
' #############################################################\n')
)
self._run_backup_undercloud(parsed_args)

@ -126,7 +126,7 @@ def _load_config():
if os.path.isfile(PATHS.CONF_PATH):
conf_params += ['--config-file', PATHS.CONF_PATH]
else:
LOG.warning('%s does not exist. Using defaults.' % PATHS.CONF_PATH)
LOG.warning(_('%s does not exist. Using defaults.') % PATHS.CONF_PATH)
CONF(conf_params)
@ -483,7 +483,7 @@ def prepare_undercloud_deploy(upgrade=False, no_validations=False,
data_file = os.path.join(tht_templates, data_file)
if not os.path.exists(data_file):
msg = "Could not find net_config_override file '%s'" % data_file
msg = _("Could not find net_config_override file '%s'") % data_file
LOG.error(msg)
raise RuntimeError(msg)
@ -496,9 +496,9 @@ def prepare_undercloud_deploy(upgrade=False, no_validations=False,
unknown_tags = _get_unknown_instack_tags(net_config_env,
template_source)
if unknown_tags:
msg = ('Can not render net_config_override file %s contains '
'unknown instack_env j2 tags: %s' % (
data_file, unknown_tags))
msg = (_('Can not render net_config_override file {0} contains '
'unknown instack_env j2 tags: {1}').format(
data_file, unknown_tags))
LOG.error(msg)
raise exceptions.DeploymentError(msg)
@ -538,7 +538,7 @@ def prepare_undercloud_deploy(upgrade=False, no_validations=False,
data_file = os.path.join(USER_HOME, data_file)
if not os.path.exists(data_file):
msg = "Could not find hieradata_override file '%s'" % data_file
msg = _("Could not find hieradata_override file '%s'") % data_file
LOG.error(msg)
raise RuntimeError(msg)

@ -126,7 +126,7 @@ def _check_hostname():
else:
short_hostname = detected_static_hostname.split('.')[0]
if short_hostname == detected_static_hostname:
message = 'Configured hostname is not fully qualified.'
message = _('Configured hostname is not fully qualified.')
LOG.error(message)
raise RuntimeError(message)
sed_cmd = ('sed -i "s/127.0.0.1\(\s*\)/127.0.0.1\\1%s %s /" '
@ -149,10 +149,10 @@ def _check_memory():
swap = psutil.swap_memory()
total_mb = (mem.total + swap.total) / 1024 / 1024
if total_mb < REQUIRED_MB:
LOG.error('At least %d MB of memory is required for undercloud '
'installation. A minimum of 8 GB is recommended. '
'Only detected %d MB' % (REQUIRED_MB, total_mb))
raise RuntimeError('Insufficient memory available')
LOG.error(_('At least {0} MB of memory is required for undercloud '
'installation. A minimum of 8 GB is recommended. '
'Only detected {1} MB').format(REQUIRED_MB, total_mb))
raise RuntimeError(_('Insufficient memory available'))
def _check_ipv6_enabled():
@ -189,10 +189,10 @@ def _check_sysctl():
not_available.append(option)
if not_available:
LOG.error('Required sysctl options are not available. Check '
'that your kernel is up to date. Missing: {options}'
' '.format(options=", ".join(not_available)))
raise RuntimeError('Missing sysctl options')
LOG.error(_('Required sysctl options are not available. Check '
'that your kernel is up to date. Missing: {options}')
.format(options=", ".join(not_available)))
raise RuntimeError(_('Missing sysctl options'))
def _validate_ips():
@ -200,8 +200,8 @@ def _validate_ips():
try:
netaddr.IPAddress(value)
except netaddr.core.AddrFormatError:
msg = '%s "%s" must be a valid IP address' % \
(param_name, value)
msg = (_('{0} "{1}" must be a valid IP address')
.format(param_name, value))
LOG.error(msg)
raise FailedValidation(msg)
for ip in CONF.undercloud_nameservers:
@ -218,22 +218,22 @@ def _validate_value_formats():
try:
local_ip = netaddr.IPNetwork(CONF.local_ip)
if local_ip.prefixlen == 32:
LOG.error('Invalid netmask')
raise netaddr.AddrFormatError('Invalid netmask')
LOG.error(_('Invalid netmask'))
raise netaddr.AddrFormatError(_('Invalid netmask'))
# If IPv6 the ctlplane network uses the EUI-64 address format,
# which requires the prefix to be /64
if local_ip.version == 6 and local_ip.prefixlen != 64:
LOG.error('Prefix must be 64 for IPv6')
raise netaddr.AddrFormatError('Prefix must be 64 for IPv6')
LOG.error(_('Prefix must be 64 for IPv6'))
raise netaddr.AddrFormatError(_('Prefix must be 64 for IPv6'))
except netaddr.core.AddrFormatError as e:
message = ('local_ip "%s" not valid: "%s" '
'Value must be in CIDR format.' %
(CONF.local_ip, str(e)))
message = (_('local_ip "{0}" not valid: "{1}" '
'Value must be in CIDR format.')
.format(CONF.local_ip, str(e)))
LOG.error(message)
raise FailedValidation(message)
hostname = CONF['undercloud_hostname']
if hostname is not None and '.' not in hostname:
message = 'Hostname "%s" is not fully qualified.' % hostname
message = (_('Hostname "%s" is not fully qualified.') % hostname)
LOG.error(message)
raise FailedValidation(message)
@ -245,8 +245,8 @@ def _validate_in_cidr(subnet_props, subnet_name):
log_only=False):
try:
if netaddr.IPAddress(addr) not in cidr:
message = ('Config option %s "%s" not in defined CIDR "%s"' %
(pretty_name, addr, cidr))
message = (_('Config option {0} "{1}" not in defined '
'CIDR "{2}"').format(pretty_name, addr, cidr))
if log_only:
LOG.warning(message)
else:
@ -254,7 +254,7 @@ def _validate_in_cidr(subnet_props, subnet_name):
raise FailedValidation(message)
except netaddr.core.AddrFormatError:
if require_ip:
message = 'Invalid IP address: %s' % addr
message = (_('Invalid IP address: %s') % addr)
LOG.error(message)
raise FailedValidation(message)
@ -283,8 +283,8 @@ def _validate_dhcp_range(subnet_props):
start = netaddr.IPAddress(subnet_props.dhcp_start)
end = netaddr.IPAddress(subnet_props.dhcp_end)
if start >= end:
message = ('Invalid dhcp range specified, dhcp_start "%s" does '
'not come before dhcp_end "%s"' % (start, end))
message = (_('Invalid dhcp range specified, dhcp_start "{0}" does '
'not come before dhcp_end "{1}"').format(start, end))
LOG.error(message)
raise FailedValidation(message)
@ -293,8 +293,8 @@ def _validate_inspection_range(subnet_props):
start = netaddr.IPAddress(subnet_props.inspection_iprange.split(',')[0])
end = netaddr.IPAddress(subnet_props.inspection_iprange.split(',')[1])
if start >= end:
message = ('Invalid inspection range specified, inspection_iprange '
'"%s" does not come before "%s"' % (start, end))
message = (_('Invalid inspection range specified, inspection_iprange '
'"{0}" does not come before "{1}"').format(start, end))
LOG.error(message)
raise FailedValidation(message)
@ -307,8 +307,8 @@ def _validate_no_overlap(subnet_props):
subnet_props.inspection_iprange.split(',')[0],
subnet_props.inspection_iprange.split(',')[1]))
if dhcp_set.intersection(inspection_set):
message = ('Inspection DHCP range "%s-%s" overlaps provisioning '
'DHCP range "%s-%s".' %
message = (_('Inspection DHCP range "{0}-{1} overlaps provisioning '
'DHCP range "{2}-{3}".') %
(subnet_props.inspection_iprange.split(',')[0],
subnet_props.inspection_iprange.split(',')[1],
subnet_props.dhcp_start, subnet_props.dhcp_end))
@ -320,8 +320,8 @@ def _validate_interface_exists():
"""Validate the provided local interface exists"""
if (not CONF.net_config_override
and CONF.local_interface not in netifaces.interfaces()):
message = ('Invalid local_interface specified. %s is not available.' %
CONF.local_interface)
message = (_('Invalid local_interface specified. '
'%s is not available.') % CONF.local_interface)
LOG.error(message)
raise FailedValidation(message)
@ -354,9 +354,9 @@ def _validate_no_ip_change():
return
existing_ip = ctlplane['addresses'][0]['ip_netmask']
if existing_ip != CONF.local_ip:
message = ('Changing the local_ip is not allowed. Existing IP: '
'%s, Configured IP: %s') % (existing_ip,
CONF.local_ip)
message = _('Changing the local_ip is not allowed. Existing IP: '
'{0}, Configured IP: {1}').format(
existing_ip, CONF.local_ip)
LOG.error(message)
raise FailedValidation(message)
@ -371,9 +371,9 @@ def _validate_passwords_file():
"""
if (os.path.isfile(os.path.expanduser('~/stackrc')) and
not os.path.isfile(PASSWORD_PATH)):
message = ('The %s file is missing. This will cause all service '
'passwords to change and break the existing undercloud. ' %
PASSWORD_PATH)
message = (_('The %s file is missing. This will cause all service '
'passwords to change and break the existing '
'undercloud. ') % PASSWORD_PATH)
LOG.error(message)
raise FailedValidation(message)
@ -384,7 +384,7 @@ def _validate_env_files_paths():
roles_file = CONF.get('roles_file') or constants.UNDERCLOUD_ROLES_FILE
# get the list of jinja templates normally rendered for UC installations
LOG.debug("Using roles file %s from %s" % (roles_file, tht_path))
LOG.debug(_("Using roles file {0} from {1}").format(roles_file, tht_path))
process_templates = os.path.join(tht_path,
'tools/process-templates.py')
p = _run_live_command(
@ -418,14 +418,14 @@ def _run_yum_clean_all(instack_env):
args = ['sudo', 'yum', 'clean', 'all']
LOG.info('Running yum clean all')
_run_live_command(args, instack_env, 'yum-clean-all')
LOG.info('yum-clean-all completed successfully')
LOG.info(_('yum-clean-all completed successfully'))
def _run_yum_update(instack_env):
args = ['sudo', 'yum', 'update', '-y']
LOG.info('Running yum update')
_run_live_command(args, instack_env, 'yum-update')
LOG.info('yum-update completed successfully')
LOG.info(_('yum-update completed successfully'))
def check():
@ -452,18 +452,18 @@ def check():
_validate_interface_exists()
_validate_no_ip_change()
except KeyError as e:
LOG.error('Key error in configuration: {error}\n'
'Value is missing in configuration.'.format(error=e))
LOG.error(_('Key error in configuration: {error}\n'
'Value is missing in configuration.').format(error=e))
sys.exit(1)
except FailedValidation as e:
LOG.error('An error occurred during configuration '
'validation, please check your host '
'configuration and try again.\nError '
'message: {error}'.format(error=e))
LOG.error(_('An error occurred during configuration '
'validation, please check your host '
'configuration and try again.\nError '
'message: {error}').format(error=e))
sys.exit(1)
except RuntimeError as e:
LOG.error('An error occurred during configuration '
'validation, please check your host '
'configuration and try again. Error '
'message: {error}'.format(error=e))
LOG.error(_('An error occurred during configuration '
'validation, please check your host '
'configuration and try again. Error '
'message: {error}').format(error=e))
sys.exit(1)

Loading…
Cancel
Save