diff --git a/plugins/module_utils/_filelock.py b/plugins/module_utils/_filelock.py index 3200dd3e06..f5d0e27608 100644 --- a/plugins/module_utils/_filelock.py +++ b/plugins/module_utils/_filelock.py @@ -56,7 +56,7 @@ class FileLock: Default is None, wait indefinitely until lock is released. :returns: True ''' - lock_path = os.path.join(tmpdir, 'ansible-{0}.lock'.format(os.path.basename(path))) + lock_path = os.path.join(tmpdir, f'ansible-{os.path.basename(path)}.lock') l_wait = 0.1 r_exception = IOError if sys.version_info[0] == 3: @@ -82,7 +82,7 @@ class FileLock: continue self.lockfd.close() - raise LockTimeout('{0} sec'.format(lock_timeout)) + raise LockTimeout(f'{lock_timeout} sec') fcntl.flock(self.lockfd, fcntl.LOCK_EX) os.chmod(lock_path, stat.S_IWRITE | stat.S_IREAD) diff --git a/plugins/module_utils/_stormssh.py b/plugins/module_utils/_stormssh.py index 4eb1cfd45a..42a72eb674 100644 --- a/plugins/module_utils/_stormssh.py +++ b/plugins/module_utils/_stormssh.py @@ -68,7 +68,7 @@ class StormConfig(SSHConfig): while (i < len(line)) and not line[i].isspace(): i += 1 if i == len(line): - raise Exception('Unparsable line: %r' % line) + raise Exception(f'Unparsable line: {line!r}') key = line[:i].lower() value = line[i:].lstrip() if key == 'host': @@ -185,7 +185,7 @@ class ConfigParser(object): if isinstance(value, int): value = str(value) - searchable_information += " " + value + searchable_information += f" {value}" if search_string in searchable_information: results.append(host_entry) @@ -218,21 +218,17 @@ class ConfigParser(object): for host_item in self.config_data: if host_item.get("type") in ['comment', 'empty_line']: - file_content += host_item.get("value") + "\n" + file_content += f"{host_item.get('value')}\n" continue - host_item_content = "Host {0}\n".format(host_item.get("host")) + host_item_content = f"Host {host_item.get('host')}\n" for key, value in host_item.get("options").items(): if isinstance(value, list): sub_content = "" for value_ in value: - sub_content += " {0} {1}\n".format( - key, value_ - ) + sub_content += f" {key} {value_}\n" host_item_content += sub_content else: - host_item_content += " {0} {1}\n".format( - key, value - ) + host_item_content += f" {key} {value}\n" file_content += host_item_content return file_content diff --git a/plugins/module_utils/alicloud_ecs.py b/plugins/module_utils/alicloud_ecs.py index 5c24a9f8a8..e752b4aa4a 100644 --- a/plugins/module_utils/alicloud_ecs.py +++ b/plugins/module_utils/alicloud_ecs.py @@ -88,10 +88,10 @@ def connect_to_acs(acs_module, region, **params): if not conn: if region not in [acs_module_region.id for acs_module_region in acs_module.regions()]: raise AnsibleACSError( - "Region %s does not seem to be available for acs module %s." % (region, acs_module.__name__)) + f"Region {region} does not seem to be available for acs module {acs_module.__name__}.") else: raise AnsibleACSError( - "Unknown problem connecting to region %s for acs module %s." % (region, acs_module.__name__)) + f"Unknown problem connecting to region {region} for acs module {acs_module.__name__}.") return conn @@ -125,7 +125,7 @@ def get_assume_role(params): def get_profile(params): if not params['alicloud_access_key'] and not params['ecs_role_name'] and params['profile']: - path = params['shared_credentials_file'] if params['shared_credentials_file'] else os.getenv('HOME') + '/.aliyun/config.json' + path = params['shared_credentials_file'] if params['shared_credentials_file'] else f"{os.getenv('HOME')}/.aliyun/config.json" auth = {} with open(path, 'r') as f: for pro in json.load(f)['profiles']: diff --git a/plugins/module_utils/android_sdkmanager.py b/plugins/module_utils/android_sdkmanager.py index 5daf830316..b25a1a04fc 100644 --- a/plugins/module_utils/android_sdkmanager.py +++ b/plugins/module_utils/android_sdkmanager.py @@ -26,7 +26,7 @@ __channel_map = { def __map_channel(channel_name): if channel_name not in __channel_map: - raise ValueError("Unknown channel name '%s'" % channel_name) + raise ValueError(f"Unknown channel name '{channel_name}'") return __channel_map[channel_name] @@ -41,7 +41,7 @@ def sdkmanager_runner(module, **kwargs): list=cmd_runner_fmt.as_fixed('--list'), newer=cmd_runner_fmt.as_fixed("--newer"), sdk_root=cmd_runner_fmt.as_opt_eq_val("--sdk_root"), - channel=cmd_runner_fmt.as_func(lambda x: ["{0}={1}".format("--channel", __map_channel(x))]) + channel=cmd_runner_fmt.as_func(lambda x: [f"--channel={__map_channel(x)}"]) ), force_lang="C.UTF-8", # Without this, sdkmanager binary crashes **kwargs @@ -126,7 +126,7 @@ class AndroidSdkManager(object): unknown_package_regex = self._RE_UNKNOWN_PACKAGE.match(line) if unknown_package_regex: package = unknown_package_regex.group('package') - raise SdkManagerException("Unknown package %s" % package) + raise SdkManagerException(f"Unknown package {package}") @staticmethod def _parse_packages(stdout, header_regexp, row_regexp): diff --git a/plugins/module_utils/btrfs.py b/plugins/module_utils/btrfs.py index 39a3268c6b..3c9ad3b382 100644 --- a/plugins/module_utils/btrfs.py +++ b/plugins/module_utils/btrfs.py @@ -15,7 +15,7 @@ def normalize_subvolume_path(path): In addition, if the path is prefixed with a leading , this value is removed. """ fstree_stripped = re.sub(r'^', '', path) - result = re.sub(r'/+$', '', re.sub(r'/+', '/', '/' + fstree_stripped)) + result = re.sub(r'/+$', '', re.sub(r'/+', '/', f"/{fstree_stripped}")) return result if len(result) > 0 else '/' @@ -34,7 +34,7 @@ class BtrfsCommands(object): self.__btrfs = self.__module.get_bin_path("btrfs", required=True) def filesystem_show(self): - command = "%s filesystem show -d" % (self.__btrfs) + command = f"{self.__btrfs} filesystem show -d" result = self.__module.run_command(command, check_rc=True) stdout = [x.strip() for x in result[1].splitlines()] filesystems = [] @@ -64,7 +64,7 @@ class BtrfsCommands(object): return re.sub(r'^.*path\s', '', line) def subvolumes_list(self, filesystem_path): - command = "%s subvolume list -tap %s" % (self.__btrfs, filesystem_path) + command = f"{self.__btrfs} subvolume list -tap {filesystem_path}" result = self.__module.run_command(command, check_rc=True) stdout = [x.split('\t') for x in result[1].splitlines()] subvolumes = [{'id': 5, 'parent': None, 'path': '/'}] @@ -143,7 +143,7 @@ class BtrfsInfoProvider(object): return [m for m in mountpoints if (m['device'] in devices)] def __find_mountpoints(self): - command = "%s -t btrfs -nvP" % self.__findmnt_path + command = f"{self.__findmnt_path} -t btrfs -nvP" result = self.__module.run_command(command) mountpoints = [] if result[0] == 0: @@ -165,13 +165,13 @@ class BtrfsInfoProvider(object): 'subvolid': self.__extract_mount_subvolid(groups['options']), } else: - raise BtrfsModuleException("Failed to parse findmnt result for line: '%s'" % line) + raise BtrfsModuleException(f"Failed to parse findmnt result for line: '{line}'") def __extract_mount_subvolid(self, mount_options): for option in mount_options.split(','): if option.startswith('subvolid='): return int(option[len('subvolid='):]) - raise BtrfsModuleException("Failed to find subvolid for mountpoint in options '%s'" % mount_options) + raise BtrfsModuleException(f"Failed to find subvolid for mountpoint in options '{mount_options}'") class BtrfsSubvolume(object): @@ -222,7 +222,7 @@ class BtrfsSubvolume(object): relative = absolute_child_path[len(path):] return re.sub(r'^/*', '', relative) else: - raise BtrfsModuleException("Path '%s' doesn't start with '%s'" % (absolute_child_path, path)) + raise BtrfsModuleException(f"Path '{absolute_child_path}' doesn't start with '{path}'") def get_parent_subvolume(self): parent_id = self.parent @@ -373,7 +373,7 @@ class BtrfsFilesystem(object): if nearest.path == subvolume_name: nearest = nearest.get_parent_subvolume() if nearest is None or nearest.get_mounted_path() is None: - raise BtrfsModuleException("Failed to find a path '%s' through a mounted parent subvolume" % subvolume_name) + raise BtrfsModuleException(f"Failed to find a path '{subvolume_name}' through a mounted parent subvolume") else: return nearest.get_mounted_path() + os.path.sep + nearest.get_child_relative_path(subvolume_name) @@ -431,12 +431,9 @@ class BtrfsFilesystemsProvider(object): if len(matching) == 1: return matching[0] else: - raise BtrfsModuleException("Found %d filesystems matching criteria uuid=%s label=%s device=%s" % ( - len(matching), - criteria['uuid'], - criteria['label'], - criteria['device'] - )) + raise BtrfsModuleException( + f"Found {len(matching)} filesystems matching criteria uuid={criteria['uuid']} label={criteria['label']} device={criteria['device']}" + ) def __filesystem_matches_criteria(self, filesystem, criteria): return ((criteria['uuid'] is None or filesystem.uuid == criteria['uuid']) and diff --git a/plugins/module_utils/cloud.py b/plugins/module_utils/cloud.py index bf5571643b..c8043a8d9e 100644 --- a/plugins/module_utils/cloud.py +++ b/plugins/module_utils/cloud.py @@ -132,7 +132,7 @@ class CloudRetry(object): if isinstance(e, cls.base_class): # pylint: disable=isinstance-second-argument-not-valid-type response_code = cls.status_code_from_exception(e) if cls.found(response_code, catch_extra_error_codes): - msg = "{0}: Retrying in {1} seconds...".format(str(e), delay) + msg = f"{e}: Retrying in {delay} seconds..." syslog.syslog(syslog.LOG_INFO, msg) time.sleep(delay) else: diff --git a/plugins/module_utils/cmd_runner.py b/plugins/module_utils/cmd_runner.py index e70889e7f3..b4903e1452 100644 --- a/plugins/module_utils/cmd_runner.py +++ b/plugins/module_utils/cmd_runner.py @@ -30,18 +30,10 @@ class MissingArgumentFormat(CmdRunnerException): self.args_formats = args_formats def __repr__(self): - return "MissingArgumentFormat({0!r}, {1!r}, {2!r})".format( - self.arg, - self.args_order, - self.args_formats, - ) + return f"MissingArgumentFormat({self.arg!r}, {self.args_order!r}, {self.args_formats!r})" def __str__(self): - return "Cannot find format for parameter {0} {1} in: {2}".format( - self.arg, - self.args_order, - self.args_formats, - ) + return f"Cannot find format for parameter {self.arg} {self.args_order} in: {self.args_formats}" class MissingArgumentValue(CmdRunnerException): @@ -50,16 +42,10 @@ class MissingArgumentValue(CmdRunnerException): self.arg = arg def __repr__(self): - return "MissingArgumentValue({0!r}, {1!r})".format( - self.args_order, - self.arg, - ) + return f"MissingArgumentValue({self.args_order!r}, {self.arg!r})" def __str__(self): - return "Cannot find value for parameter {0} in {1}".format( - self.arg, - self.args_order, - ) + return f"Cannot find value for parameter {self.arg} in {self.args_order}" class FormatError(CmdRunnerException): @@ -71,19 +57,10 @@ class FormatError(CmdRunnerException): super(FormatError, self).__init__() def __repr__(self): - return "FormatError({0!r}, {1!r}, {2!r}, {3!r})".format( - self.name, - self.value, - self.args_formats, - self.exc, - ) + return f"FormatError({self.name!r}, {self.value!r}, {self.args_formats!r}, {self.exc!r})" def __str__(self): - return "Failed to format parameter {0} with value {1}: {2}".format( - self.name, - self.value, - self.exc, - ) + return f"Failed to format parameter {self.name} with value {self.value}: {self.exc}" class CmdRunner(object): diff --git a/plugins/module_utils/cmd_runner_fmt.py b/plugins/module_utils/cmd_runner_fmt.py index 32e8bdff71..dcb9fc8e20 100644 --- a/plugins/module_utils/cmd_runner_fmt.py +++ b/plugins/module_utils/cmd_runner_fmt.py @@ -27,11 +27,7 @@ class _ArgFormat(object): return [str(x) for x in f(value)] def __str__(self): - return "".format( - self.func, - self.ignore_none, - self.ignore_missing_value, - ) + return f"" def __repr__(self): return str(self) @@ -51,7 +47,7 @@ def as_bool_not(args): def as_optval(arg, ignore_none=None): - return _ArgFormat(lambda value: ["{0}{1}".format(arg, value)], ignore_none=ignore_none) + return _ArgFormat(lambda value: [f"{arg}{value}"], ignore_none=ignore_none) def as_opt_val(arg, ignore_none=None): @@ -59,16 +55,16 @@ def as_opt_val(arg, ignore_none=None): def as_opt_eq_val(arg, ignore_none=None): - return _ArgFormat(lambda value: ["{0}={1}".format(arg, value)], ignore_none=ignore_none) + return _ArgFormat(lambda value: [f"{arg}={value}"], ignore_none=ignore_none) def as_list(ignore_none=None, min_len=0, max_len=None): def func(value): value = _ensure_list(value) if len(value) < min_len: - raise ValueError("Parameter must have at least {0} element(s)".format(min_len)) + raise ValueError(f"Parameter must have at least {min_len} element(s)") if max_len is not None and len(value) > max_len: - raise ValueError("Parameter must have at most {0} element(s)".format(max_len)) + raise ValueError(f"Parameter must have at most {max_len} element(s)") return value return _ArgFormat(func, ignore_none=ignore_none) diff --git a/plugins/module_utils/consul.py b/plugins/module_utils/consul.py index 1a73a131a8..b814485c55 100644 --- a/plugins/module_utils/consul.py +++ b/plugins/module_utils/consul.py @@ -16,11 +16,7 @@ from ansible.module_utils.urls import open_url def get_consul_url(configuration): - return "%s://%s:%s/v1" % ( - configuration.scheme, - configuration.host, - configuration.port, - ) + return f"{configuration.scheme}://{configuration.host}:{configuration.port}/v1" def get_auth_headers(configuration): @@ -39,12 +35,12 @@ class RequestError(Exception): if self.response_data is None: # self.status is already the message (backwards compat) return self.status - return "HTTP %d: %s" % (self.status, self.response_data) + return f"HTTP {self.status}: {self.response_data}" def handle_consul_response_error(response): if 400 <= response.status_code < 600: - raise RequestError("%d %s" % (response.status_code, response.content)) + raise RequestError(f"{response.status_code} {response.content}") AUTH_ARGUMENTS_SPEC = dict( @@ -82,7 +78,7 @@ def validate_check(check): def validate_duration(duration): if duration: if not re.search(r"\d+(?:ns|us|ms|s|m|h)", duration): - duration = "{0}s".format(duration) + duration = f"{duration}s" return duration @@ -246,7 +242,7 @@ class _ConsulModule: if operation == OPERATION_CREATE: return self.api_endpoint elif identifier: - return "/".join([self.api_endpoint, identifier]) + return f"{self.api_endpoint}/{identifier}" raise RuntimeError("invalid arguments passed") def read_object(self): @@ -299,11 +295,7 @@ class _ConsulModule: params = {k: v for k, v in params.items() if v is not None} ca_path = module_params.get("ca_path") - base_url = "%s://%s:%s/v1" % ( - module_params["scheme"], - module_params["host"], - module_params["port"], - ) + base_url = f"{module_params['scheme']}://{module_params['host']}:{module_params['port']}/v1" url = "/".join([base_url] + list(url_parts)) headers = {} @@ -316,7 +308,7 @@ class _ConsulModule: data = json.dumps(data) headers["Content-Type"] = "application/json" if params: - url = "%s?%s" % (url, urlencode(params)) + url = f"{url}?{urlencode(params)}" response = open_url( url, method=method, @@ -336,8 +328,7 @@ class _ConsulModule: response_data = e.fp.read() else: self._module.fail_json( - msg="Could not connect to consul agent at %s:%s, error was %s" - % (module_params["host"], module_params["port"], str(e)) + msg=f"Could not connect to consul agent at {module_params['host']}:{module_params['port']}, error was {e}" ) raise diff --git a/plugins/module_utils/csv.py b/plugins/module_utils/csv.py index d8bd58d1d9..66268f12b6 100644 --- a/plugins/module_utils/csv.py +++ b/plugins/module_utils/csv.py @@ -37,7 +37,7 @@ def initialize_dialect(dialect, **kwargs): csv.register_dialect("unix", unix_dialect) if dialect not in csv.list_dialects(): - raise DialectNotAvailableError("Dialect '%s' is not supported by your version of python." % dialect) + raise DialectNotAvailableError(f"Dialect '{dialect}' is not supported by your version of python.") # Create a dictionary from only set options dialect_params = {k: v for k, v in kwargs.items() if v is not None} @@ -45,7 +45,7 @@ def initialize_dialect(dialect, **kwargs): try: csv.register_dialect('custom', dialect, **dialect_params) except TypeError as e: - raise CustomDialectFailureError("Unable to create custom dialect: %s" % to_native(e)) + raise CustomDialectFailureError(f"Unable to create custom dialect: {e}") dialect = 'custom' return dialect diff --git a/plugins/module_utils/database.py b/plugins/module_utils/database.py index ee6ee71304..bb4c0efcee 100644 --- a/plugins/module_utils/database.py +++ b/plugins/module_utils/database.py @@ -102,19 +102,19 @@ def _identifier_parse(identifier, quote_char): dot = identifier.index('.') except ValueError: identifier = identifier.replace(quote_char, quote_char * 2) - identifier = ''.join((quote_char, identifier, quote_char)) + identifier = f"{quote_char}{identifier}{quote_char}" further_identifiers = [identifier] else: if dot == 0 or dot >= len(identifier) - 1: identifier = identifier.replace(quote_char, quote_char * 2) - identifier = ''.join((quote_char, identifier, quote_char)) + identifier = f"{quote_char}{identifier}{quote_char}" further_identifiers = [identifier] else: first_identifier = identifier[:dot] next_identifier = identifier[dot + 1:] further_identifiers = _identifier_parse(next_identifier, quote_char) first_identifier = first_identifier.replace(quote_char, quote_char * 2) - first_identifier = ''.join((quote_char, first_identifier, quote_char)) + first_identifier = f"{quote_char}{first_identifier}{quote_char}" further_identifiers.insert(0, first_identifier) return further_identifiers @@ -123,14 +123,14 @@ def _identifier_parse(identifier, quote_char): def pg_quote_identifier(identifier, id_type): identifier_fragments = _identifier_parse(identifier, quote_char='"') if len(identifier_fragments) > _PG_IDENTIFIER_TO_DOT_LEVEL[id_type]: - raise SQLParseError('PostgreSQL does not support %s with more than %i dots' % (id_type, _PG_IDENTIFIER_TO_DOT_LEVEL[id_type])) + raise SQLParseError(f'PostgreSQL does not support {id_type} with more than {_PG_IDENTIFIER_TO_DOT_LEVEL[id_type]} dots') return '.'.join(identifier_fragments) def mysql_quote_identifier(identifier, id_type): identifier_fragments = _identifier_parse(identifier, quote_char='`') if (len(identifier_fragments) - 1) > _MYSQL_IDENTIFIER_TO_DOT_LEVEL[id_type]: - raise SQLParseError('MySQL does not support %s with more than %i dots' % (id_type, _MYSQL_IDENTIFIER_TO_DOT_LEVEL[id_type])) + raise SQLParseError(f'MySQL does not support {id_type} with more than {_MYSQL_IDENTIFIER_TO_DOT_LEVEL[id_type]} dots') special_cased_fragments = [] for fragment in identifier_fragments: @@ -185,5 +185,4 @@ def check_input(module, *args): dangerous_elements.append(elem) if dangerous_elements: - module.fail_json(msg="Passed input '%s' is " - "potentially dangerous" % ', '.join(dangerous_elements)) + module.fail_json(msg=f"Passed input '{', '.join(dangerous_elements)}' is potentially dangerous") diff --git a/plugins/module_utils/deps.py b/plugins/module_utils/deps.py index 2cca370d97..a24cd63838 100644 --- a/plugins/module_utils/deps.py +++ b/plugins/module_utils/deps.py @@ -53,7 +53,7 @@ class _Dependency(object): module.fail_json(msg=self.message, exception=self.trace) def __str__(self): - return "".format(self.name, self._states[self.state]) + return f"" @contextmanager diff --git a/plugins/module_utils/dimensiondata.py b/plugins/module_utils/dimensiondata.py index 4f482aad18..a0430b445e 100644 --- a/plugins/module_utils/dimensiondata.py +++ b/plugins/module_utils/dimensiondata.py @@ -73,7 +73,7 @@ class DimensionDataModule(object): # Region and location are common to all Dimension Data modules. region = self.module.params['region'] - self.region = 'dd-{0}'.format(region) + self.region = f'dd-{region}' self.location = self.module.params['location'] libcloud.security.VERIFY_SSL_CERT = self.module.params['validate_certs'] @@ -140,7 +140,7 @@ class DimensionDataModule(object): if not user_id or not key: home = expanduser('~') config = configparser.RawConfigParser() - config.read("%s/.dimensiondata" % home) + config.read(f"{home}/.dimensiondata") try: user_id = config.get("dimensiondatacloud", "MCP_USER") @@ -190,7 +190,7 @@ class DimensionDataModule(object): if network_domain: return network_domain - raise UnknownNetworkError("Network '%s' could not be found" % locator) + raise UnknownNetworkError(f"Network '{locator}' could not be found") def get_vlan(self, locator, location, network_domain): """ @@ -212,7 +212,7 @@ class DimensionDataModule(object): if vlan: return vlan - raise UnknownVLANError("VLAN '%s' could not be found" % locator) + raise UnknownVLANError(f"VLAN '{locator}' could not be found") @staticmethod def argument_spec(**additional_argument_spec): diff --git a/plugins/module_utils/gandi_livedns_api.py b/plugins/module_utils/gandi_livedns_api.py index bda4a05ead..135fc6188c 100644 --- a/plugins/module_utils/gandi_livedns_api.py +++ b/plugins/module_utils/gandi_livedns_api.py @@ -6,7 +6,7 @@ from __future__ import annotations import json -from ansible.module_utils.common.text.converters import to_native, to_text +from ansible.module_utils.common.text.converters import to_text from ansible.module_utils.urls import fetch_url @@ -42,7 +42,7 @@ class GandiLiveDNSAPI(object): error = errors[0] name = error.get('name') if name: - s += '{0} :'.format(name) + s += f'{name} :' description = error.get('description') if description: s += description @@ -50,9 +50,9 @@ class GandiLiveDNSAPI(object): def _gandi_api_call(self, api_call, method='GET', payload=None, error_on_404=True): authorization_header = ( - 'Bearer {0}'.format(self.personal_access_token) + f'Bearer {self.personal_access_token}' if self.personal_access_token - else 'Apikey {0}'.format(self.api_key) + else f'Apikey {self.api_key}' ) headers = {'Authorization': authorization_header, 'Content-Type': 'application/json'} @@ -61,7 +61,7 @@ class GandiLiveDNSAPI(object): try: data = json.dumps(payload) except Exception as e: - self.module.fail_json(msg="Failed to encode payload as JSON: %s " % to_native(e)) + self.module.fail_json(msg=f"Failed to encode payload as JSON: {e} ") resp, info = fetch_url(self.module, self.api_endpoint + api_call, @@ -73,7 +73,7 @@ class GandiLiveDNSAPI(object): if info['status'] >= 400 and (info['status'] != 404 or error_on_404): err_s = self.error_strings.get(info['status'], '') - error_msg = "API Error {0}: {1}".format(err_s, self._build_error_message(self.module, info)) + error_msg = f"API Error {err_s}: {self._build_error_message(self.module, info)}" result = None try: @@ -85,7 +85,7 @@ class GandiLiveDNSAPI(object): try: result = json.loads(to_text(content, errors='surrogate_or_strict')) except (getattr(json, 'JSONDecodeError', ValueError)) as e: - error_msg += "; Failed to parse API response with error {0}: {1}".format(to_native(e), content) + error_msg += f"; Failed to parse API response with error {e}: {content}" if error_msg: self.module.fail_json(msg=error_msg) @@ -114,11 +114,11 @@ class GandiLiveDNSAPI(object): return [self.build_result(r, domain) for r in results] def get_records(self, record, type, domain): - url = '/domains/%s/records' % (domain) + url = f'/domains/{domain}/records' if record: - url += '/%s' % (record) + url += f'/{record}' if type: - url += '/%s' % (type) + url += f'/{type}' records, status = self._gandi_api_call(url, error_on_404=False) @@ -137,7 +137,7 @@ class GandiLiveDNSAPI(object): return records def create_record(self, record, type, values, ttl, domain): - url = '/domains/%s/records' % (domain) + url = f'/domains/{domain}/records' new_record = { 'rrset_name': record, 'rrset_type': type, @@ -152,7 +152,7 @@ class GandiLiveDNSAPI(object): return None def update_record(self, record, type, values, ttl, domain): - url = '/domains/%s/records/%s/%s' % (domain, record, type) + url = f'/domains/{domain}/records/{record}/{type}' new_record = { 'rrset_values': values, 'rrset_ttl': ttl, @@ -161,7 +161,7 @@ class GandiLiveDNSAPI(object): return record def delete_record(self, record, type, domain): - url = '/domains/%s/records/%s/%s' % (domain, record, type) + url = f'/domains/{domain}/records/{record}/{type}' self._gandi_api_call(url, method='DELETE') diff --git a/plugins/module_utils/gitlab.py b/plugins/module_utils/gitlab.py index bc2ef9381c..1d95ec34e7 100644 --- a/plugins/module_utils/gitlab.py +++ b/plugins/module_utils/gitlab.py @@ -7,7 +7,6 @@ from __future__ import annotations from ansible.module_utils.basic import missing_required_lib -from ansible.module_utils.common.text.converters import to_native from ansible_collections.community.general.plugins.module_utils.version import LooseVersion @@ -62,7 +61,7 @@ def find_project(gitlab_instance, identifier): except Exception as e: current_user = gitlab_instance.user try: - project = gitlab_instance.projects.get(current_user.username + '/' + identifier) + project = gitlab_instance.projects.get(f"{current_user.username}/{identifier}") except Exception as e: return None @@ -86,11 +85,10 @@ def ensure_gitlab_package(module, min_version=None): ) gitlab_version = gitlab.__version__ if min_version is not None and LooseVersion(gitlab_version) < LooseVersion(min_version): - module.fail_json( - msg="This module requires python-gitlab Python module >= %s " - "(installed version: %s). Please upgrade python-gitlab to version %s or above." - % (min_version, gitlab_version, min_version) - ) + module.fail_json(msg=( + f"This module requires python-gitlab Python module >= {min_version} (installed version: " + f"{gitlab_version}). Please upgrade python-gitlab to version {min_version} or above." + )) def gitlab_authentication(module, min_version=None): @@ -120,10 +118,12 @@ def gitlab_authentication(module, min_version=None): oauth_token=gitlab_oauth_token, job_token=gitlab_job_token, api_version=4) gitlab_instance.auth() except (gitlab.exceptions.GitlabAuthenticationError, gitlab.exceptions.GitlabGetError) as e: - module.fail_json(msg="Failed to connect to GitLab server: %s" % to_native(e)) + module.fail_json(msg=f"Failed to connect to GitLab server: {e}") except (gitlab.exceptions.GitlabHttpError) as e: - module.fail_json(msg="Failed to connect to GitLab server: %s. \ - GitLab remove Session API now that private tokens are removed from user API endpoints since version 10.2." % to_native(e)) + module.fail_json(msg=( + f"Failed to connect to GitLab server: {e}. GitLab remove Session API now " + "that private tokens are removed from user API endpoints since version 10.2." + )) return gitlab_instance diff --git a/plugins/module_utils/homebrew.py b/plugins/module_utils/homebrew.py index 10bf7c14fa..6c01535a55 100644 --- a/plugins/module_utils/homebrew.py +++ b/plugins/module_utils/homebrew.py @@ -12,32 +12,28 @@ import re def _create_regex_group_complement(s): lines = (line.strip() for line in s.split("\n") if line.strip()) chars = filter(None, (line.split("#")[0].strip() for line in lines)) - group = r"[^" + r"".join(chars) + r"]" + group = rf"[^{''.join(chars)}]" return re.compile(group) class HomebrewValidate(object): # class regexes ------------------------------------------------ {{{ - VALID_PATH_CHARS = r""" + VALID_PATH_CHARS = rf""" \w # alphanumeric characters (i.e., [a-zA-Z0-9_]) \s # spaces : # colons - {sep} # the OS-specific path separator + {os.path.sep} # the OS-specific path separator . # dots \- # dashes - """.format( - sep=os.path.sep - ) + """ - VALID_BREW_PATH_CHARS = r""" + VALID_BREW_PATH_CHARS = rf""" \w # alphanumeric characters (i.e., [a-zA-Z0-9_]) \s # spaces - {sep} # the OS-specific path separator + {os.path.sep} # the OS-specific path separator . # dots \- # dashes - """.format( - sep=os.path.sep - ) + """ VALID_PACKAGE_CHARS = r""" \w # alphanumeric characters (i.e., [a-zA-Z0-9_]) @@ -123,17 +119,17 @@ def parse_brew_path(module): """ path = module.params["path"] if not HomebrewValidate.valid_path(path): - module.fail_json(msg="Invalid path: {0}".format(path)) + module.fail_json(msg=f"Invalid path: {path}") if isinstance(path, str): paths = path.split(":") elif isinstance(path, list): paths = path else: - module.fail_json(msg="Invalid path: {0}".format(path)) + module.fail_json(msg=f"Invalid path: {path}") brew_path = module.get_bin_path("brew", required=True, opt_dirs=paths) if not HomebrewValidate.valid_brew_path(brew_path): - module.fail_json(msg="Invalid brew path: {0}".format(brew_path)) + module.fail_json(msg=f"Invalid brew path: {brew_path}") return brew_path diff --git a/plugins/module_utils/hwc_utils.py b/plugins/module_utils/hwc_utils.py index 7c64e765dc..dee53cd787 100644 --- a/plugins/module_utils/hwc_utils.py +++ b/plugins/module_utils/hwc_utils.py @@ -30,7 +30,7 @@ class HwcModuleException(Exception): self._message = message def __str__(self): - return "[HwcClientException] message=%s" % self._message + return f"[HwcClientException] message={self._message}" class HwcClientException(Exception): @@ -41,9 +41,8 @@ class HwcClientException(Exception): self._message = message def __str__(self): - msg = " code=%s," % str(self._code) if self._code != 0 else "" - return "[HwcClientException]%s message=%s" % ( - msg, self._message) + msg = f" code={self._code!s}," if self._code != 0 else "" + return f"[HwcClientException]{msg} message={self._message}" class HwcClientException404(HwcClientException): @@ -51,7 +50,7 @@ class HwcClientException404(HwcClientException): super(HwcClientException404, self).__init__(404, message) def __str__(self): - return "[HwcClientException404] message=%s" % self._message + return f"[HwcClientException404] message={self._message}" def session_method_wrapper(f): @@ -61,7 +60,7 @@ def session_method_wrapper(f): r = f(self, url, *args, **kwargs) except Exception as ex: raise HwcClientException( - 0, "Sending request failed, error=%s" % ex) + 0, f"Sending request failed, error={ex}") result = None if r.content: @@ -69,7 +68,7 @@ def session_method_wrapper(f): result = r.json() except Exception as ex: raise HwcClientException( - 0, "Parsing response to json failed, error: %s" % ex) + 0, f"Parsing response to json failed, error: {ex}") code = r.status_code if code not in [200, 201, 202, 203, 204, 205, 206, 207, 208, 226]: @@ -98,7 +97,7 @@ class _ServiceClient(object): self._client = client self._endpoint = endpoint self._default_header = { - 'User-Agent': "Huawei-Ansible-MM-%s" % product, + 'User-Agent': f"Huawei-Ansible-MM-{product}", 'Accept': 'application/json', } @@ -186,7 +185,7 @@ class Config(object): raise_exc=False) def _get_service_endpoint(self, client, service_type, region): - k = "%s.%s" % (service_type, region if region else "") + k = f"{service_type}.{region if region else ''}" if k in self._endpoints: return self._endpoints.get(k) @@ -197,11 +196,11 @@ class Config(object): region_name=region, interface="public") except Exception as ex: raise HwcClientException( - 0, "Getting endpoint failed, error=%s" % ex) + 0, f"Getting endpoint failed, error={ex}") if url == "": raise HwcClientException( - 0, "Cannot find the endpoint for %s" % service_type) + 0, f"Cannot find the endpoint for {service_type}") if url[-1] != "/": url += "/" @@ -340,7 +339,7 @@ def wait_to_finish(target, pending, refresh, timeout, min_interval=1, delay=3): if not_found_times > 10: raise HwcModuleException( - "not found the object for %d times" % not_found_times) + f"not found the object for {not_found_times} times") else: not_found_times = 0 @@ -349,7 +348,7 @@ def wait_to_finish(target, pending, refresh, timeout, min_interval=1, delay=3): if pending and status not in pending: raise HwcModuleException( - "unexpected status(%s) occurred" % status) + f"unexpected status({status}) occurred") if not is_last_time: wait *= 2 @@ -360,7 +359,7 @@ def wait_to_finish(target, pending, refresh, timeout, min_interval=1, delay=3): time.sleep(wait) - raise HwcModuleException("async wait timeout after %d seconds" % timeout) + raise HwcModuleException(f"async wait timeout after {timeout} seconds") def navigate_value(data, index, array_index=None): @@ -379,7 +378,7 @@ def navigate_value(data, index, array_index=None): i = index[n] if i not in d: raise HwcModuleException( - "navigate value failed: key(%s) is not exist in dict" % i) + f"navigate value failed: key({i}) is not exist in dict") d = d[i] if not array_index: diff --git a/plugins/module_utils/identity/keycloak/keycloak_clientsecret.py b/plugins/module_utils/identity/keycloak/keycloak_clientsecret.py index 7608935aaf..24751847bb 100644 --- a/plugins/module_utils/identity/keycloak/keycloak_clientsecret.py +++ b/plugins/module_utils/identity/keycloak/keycloak_clientsecret.py @@ -67,7 +67,7 @@ def keycloak_clientsecret_module_resolve_params(module, kc): if client is None: module.fail_json( - msg='Client does not exist {client_id}'.format(client_id=client_id) + msg=f'Client does not exist {client_id}' ) id = client['id'] diff --git a/plugins/module_utils/ilo_redfish_utils.py b/plugins/module_utils/ilo_redfish_utils.py index b06c388b23..c49094a077 100644 --- a/plugins/module_utils/ilo_redfish_utils.py +++ b/plugins/module_utils/ilo_redfish_utils.py @@ -20,8 +20,7 @@ class iLORedfishUtils(RedfishUtils): properties = ['Description', 'Id', 'Name', 'UserName'] # Changed self.sessions_uri to Hardcoded string. - response = self.get_request( - self.root_uri + self.service_root + "SessionService/Sessions/") + response = self.get_request(f"{self.root_uri}{self.service_root}SessionService/Sessions/") if not response['ret']: return response result['ret'] = True @@ -83,7 +82,7 @@ class iLORedfishUtils(RedfishUtils): if not res_dhv6['ret']: return res_dhv6 - datetime_uri = self.manager_uri + "DateTime" + datetime_uri = f"{self.manager_uri}DateTime" listofips = mgr_attributes['mgr_attr_value'].split(" ") if len(listofips) > 2: @@ -102,12 +101,12 @@ class iLORedfishUtils(RedfishUtils): if not response1['ret']: return response1 - return {'ret': True, 'changed': True, 'msg': "Modified %s" % mgr_attributes['mgr_attr_name']} + return {'ret': True, 'changed': True, 'msg': f"Modified {mgr_attributes['mgr_attr_name']}"} def set_time_zone(self, attr): key = attr['mgr_attr_name'] - uri = self.manager_uri + "DateTime/" + uri = f"{self.manager_uri}DateTime/" response = self.get_request(self.root_uri + uri) if not response['ret']: return response @@ -115,7 +114,7 @@ class iLORedfishUtils(RedfishUtils): data = response["data"] if key not in data: - return {'ret': False, 'changed': False, 'msg': "Key %s not found" % key} + return {'ret': False, 'changed': False, 'msg': f"Key {key} not found"} timezones = data["TimeZoneList"] index = "" @@ -129,7 +128,7 @@ class iLORedfishUtils(RedfishUtils): if not response['ret']: return response - return {'ret': True, 'changed': True, 'msg': "Modified %s" % attr['mgr_attr_name']} + return {'ret': True, 'changed': True, 'msg': f"Modified {attr['mgr_attr_name']}"} def set_dns_server(self, attr): key = attr['mgr_attr_name'] @@ -161,7 +160,7 @@ class iLORedfishUtils(RedfishUtils): if not response['ret']: return response - return {'ret': True, 'changed': True, 'msg': "Modified %s" % attr['mgr_attr_name']} + return {'ret': True, 'changed': True, 'msg': f"Modified {attr['mgr_attr_name']}"} def set_domain_name(self, attr): key = attr['mgr_attr_name'] @@ -206,7 +205,7 @@ class iLORedfishUtils(RedfishUtils): response = self.patch_request(self.root_uri + ethuri, payload) if not response['ret']: return response - return {'ret': True, 'changed': True, 'msg': "Modified %s" % attr['mgr_attr_name']} + return {'ret': True, 'changed': True, 'msg': f"Modified {attr['mgr_attr_name']}"} def set_wins_registration(self, mgrattr): Key = mgrattr['mgr_attr_name'] @@ -227,7 +226,7 @@ class iLORedfishUtils(RedfishUtils): response = self.patch_request(self.root_uri + ethuri, payload) if not response['ret']: return response - return {'ret': True, 'changed': True, 'msg': "Modified %s" % mgrattr['mgr_attr_name']} + return {'ret': True, 'changed': True, 'msg': f"Modified {mgrattr['mgr_attr_name']}"} def get_server_poststate(self): # Get server details @@ -302,5 +301,5 @@ class iLORedfishUtils(RedfishUtils): return { "ret": False, "changed": False, - "msg": "Server Reboot has failed, server state: {state} ".format(state=state) + "msg": f"Server Reboot has failed, server state: {state} " } diff --git a/plugins/module_utils/ipa.py b/plugins/module_utils/ipa.py index 21b0df3537..96010d503b 100644 --- a/plugins/module_utils/ipa.py +++ b/plugins/module_utils/ipa.py @@ -51,16 +51,16 @@ class IPAClient(object): self.use_gssapi = False def get_base_url(self): - return '%s://%s/ipa' % (self.protocol, self.host) + return f'{self.protocol}://{self.host}/ipa' def get_json_url(self): - return '%s/session/json' % self.get_base_url() + return f'{self.get_base_url()}/session/json' def login(self, username, password): if 'KRB5CCNAME' in os.environ and HAS_GSSAPI: self.use_gssapi = True elif 'KRB5_CLIENT_KTNAME' in os.environ and HAS_GSSAPI: - ccache = "MEMORY:" + str(uuid.uuid4()) + ccache = f"MEMORY:{uuid.uuid4()!s}" os.environ['KRB5CCNAME'] = ccache self.use_gssapi = True else: @@ -71,8 +71,8 @@ class IPAClient(object): 'GSSAPI. To use GSSAPI, please set the ' 'KRB5_CLIENT_KTNAME or KRB5CCNAME (or both) ' ' environment variables.') - url = '%s/session/login_password' % self.get_base_url() - data = 'user=%s&password=%s' % (quote(username, safe=''), quote(password, safe='')) + url = f'{self.get_base_url()}/session/login_password' + data = f"user={quote(username, safe='')}&password={quote(password, safe='')}" headers = {'referer': self.get_base_url(), 'Content-Type': 'application/x-www-form-urlencoded', 'Accept': 'text/plain'} @@ -97,7 +97,7 @@ class IPAClient(object): err_string = e.get('message') else: err_string = e - self.module.fail_json(msg='%s: %s' % (msg, err_string)) + self.module.fail_json(msg=f'{msg}: {err_string}') def get_ipa_version(self): response = self.ping()['summary'] @@ -114,7 +114,7 @@ class IPAClient(object): def _post_json(self, method, name, item=None): if item is None: item = {} - url = '%s/session/json' % self.get_base_url() + url = f'{self.get_base_url()}/session/json' data = dict(method=method) # TODO: We should probably handle this a little better. @@ -132,13 +132,13 @@ class IPAClient(object): if status_code not in [200, 201, 204]: self._fail(method, info['msg']) except Exception as e: - self._fail('post %s' % method, to_native(e)) + self._fail(f'post {method}', to_native(e)) charset = resp.headers.get_content_charset('latin-1') resp = json.loads(to_text(resp.read(), encoding=charset)) err = resp.get('error') if err is not None: - self._fail('response %s' % method, err) + self._fail(f'response {method}', err) if 'result' in resp: result = resp.get('result') diff --git a/plugins/module_utils/known_hosts.py b/plugins/module_utils/known_hosts.py index 80802f616e..ec20b8d88b 100644 --- a/plugins/module_utils/known_hosts.py +++ b/plugins/module_utils/known_hosts.py @@ -146,28 +146,28 @@ def add_host_key(module, fqdn, port=22, key_type="rsa", create_dir=False): try: os.makedirs(user_ssh_dir, int('700', 8)) except Exception: - module.fail_json(msg="failed to create host key directory: %s" % user_ssh_dir) + module.fail_json(msg=f"failed to create host key directory: {user_ssh_dir}") else: - module.fail_json(msg="%s does not exist" % user_ssh_dir) + module.fail_json(msg=f"{user_ssh_dir} does not exist") elif not os.path.isdir(user_ssh_dir): - module.fail_json(msg="%s is not a directory" % user_ssh_dir) + module.fail_json(msg=f"{user_ssh_dir} is not a directory") if port: - this_cmd = "%s -t %s -p %s %s" % (keyscan_cmd, key_type, port, fqdn) + this_cmd = f"{keyscan_cmd} -t {key_type} -p {port} {fqdn}" else: - this_cmd = "%s -t %s %s" % (keyscan_cmd, key_type, fqdn) + this_cmd = f"{keyscan_cmd} -t {key_type} {fqdn}" rc, out, err = module.run_command(this_cmd) # ssh-keyscan gives a 0 exit code and prints nothing on timeout if rc != 0 or not out: msg = 'failed to retrieve hostkey' if not out: - msg += '. "%s" returned no matches.' % this_cmd + msg += f'. "{this_cmd}" returned no matches.' else: - msg += ' using command "%s". [stdout]: %s' % (this_cmd, out) + msg += f' using command "{this_cmd}". [stdout]: {out}' if err: - msg += ' [stderr]: %s' % err + msg += f' [stderr]: {err}' module.fail_json(msg=msg) diff --git a/plugins/module_utils/ldap.py b/plugins/module_utils/ldap.py index 8c20fd7370..e0ee5940e2 100644 --- a/plugins/module_utils/ldap.py +++ b/plugins/module_utils/ldap.py @@ -91,7 +91,7 @@ class LdapGeneric(object): if len(explode_dn) > 1: try: escaped_value = ldap.filter.escape_filter_chars(explode_dn[0]) - filterstr = "(%s)" % escaped_value + filterstr = f"({escaped_value})" dns = self.connection.search_s(','.join(explode_dn[1:]), ldap.SCOPE_ONELEVEL, filterstr) if len(dns) == 1: diff --git a/plugins/module_utils/linode.py b/plugins/module_utils/linode.py index 77b074e708..966b4352fc 100644 --- a/plugins/module_utils/linode.py +++ b/plugins/module_utils/linode.py @@ -18,4 +18,4 @@ def get_user_agent(module): from ansible.module_utils.ansible_release import __version__ as ansible_version except ImportError: ansible_version = 'unknown' - return 'Ansible-%s/%s' % (module, ansible_version) + return f'Ansible-{module}/{ansible_version}' diff --git a/plugins/module_utils/lxd.py b/plugins/module_utils/lxd.py index 7a7c868aa9..cc8e05c0f0 100644 --- a/plugins/module_utils/lxd.py +++ b/plugins/module_utils/lxd.py @@ -78,7 +78,7 @@ class LXDClient(object): def do(self, method, url, body_json=None, ok_error_codes=None, timeout=None, wait_for_container=None): resp_json = self._send_request(method, url, body_json=body_json, ok_error_codes=ok_error_codes, timeout=timeout) if resp_json['type'] == 'async': - url = '{0}/wait'.format(resp_json['operation']) + url = f"{resp_json['operation']}/wait" resp_json = self._send_request('GET', url) if wait_for_container: while resp_json['metadata']['status'] == 'Running': diff --git a/plugins/module_utils/manageiq.py b/plugins/module_utils/manageiq.py index 9b65239a5f..477fc9a326 100644 --- a/plugins/module_utils/manageiq.py +++ b/plugins/module_utils/manageiq.py @@ -93,12 +93,12 @@ class ManageIQ(object): ca_bundle_path = params['ca_cert'] self._module = module - self._api_url = url + '/api' + self._api_url = f"{url}/api" self._auth = dict(user=username, password=password, token=token) try: self._client = ManageIQClient(self._api_url, self._auth, verify_ssl=verify_ssl, ca_bundle_path=ca_bundle_path) except Exception as e: - self.module.fail_json(msg="failed to open connection (%s): %s" % (url, str(e))) + self.module.fail_json(msg=f"failed to open connection ({url}): {e}") @property def module(self): @@ -138,7 +138,7 @@ class ManageIQ(object): except ValueError: return None except Exception as e: - self.module.fail_json(msg="failed to find resource {error}".format(error=e)) + self.module.fail_json(msg=f"failed to find resource {e}") return vars(entity) def find_collection_resource_or_fail(self, collection_name, **params): @@ -151,8 +151,7 @@ class ManageIQ(object): if resource: return resource else: - msg = "{collection_name} where {params} does not exist in manageiq".format( - collection_name=collection_name, params=str(params)) + msg = f"{collection_name} where {params!s} does not exist in manageiq" self.module.fail_json(msg=msg) def policies(self, resource_id, resource_type, resource_name): @@ -174,8 +173,7 @@ class ManageIQ(object): if resource: return resource["id"] else: - msg = "{resource_name} {resource_type} does not exist in manageiq".format( - resource_name=resource_name, resource_type=resource_type) + msg = f"{resource_name} {resource_type} does not exist in manageiq" self.module.fail_json(msg=msg) @@ -193,10 +191,7 @@ class ManageIQPolicies(object): self.resource_type = resource_type self.resource_id = resource_id - self.resource_url = '{api_url}/{resource_type}/{resource_id}'.format( - api_url=self.api_url, - resource_type=resource_type, - resource_id=resource_id) + self.resource_url = f'{self.api_url}/{resource_type}/{resource_id}' def query_profile_href(self, profile): """ Add or Update the policy_profile href field @@ -215,9 +210,7 @@ class ManageIQPolicies(object): try: response = self.client.get(url.format(resource_url=self.resource_url)) except Exception as e: - msg = "Failed to query {resource_type} policies: {error}".format( - resource_type=self.resource_type, - error=e) + msg = f"Failed to query {self.resource_type} policies: {e}" self.module.fail_json(msg=msg) resources = response.get('resources', []) @@ -235,9 +228,7 @@ class ManageIQPolicies(object): try: response = self.client.get(url.format(api_url=self.api_url, profile_id=profile_id)) except Exception as e: - msg = "Failed to query {resource_type} policies: {error}".format( - resource_type=self.resource_type, - error=e) + msg = f"Failed to query {self.resource_type} policies: {e}" self.module.fail_json(msg=msg) resources = response.get('policies', []) @@ -316,34 +307,26 @@ class ManageIQPolicies(object): if not profiles_to_post: return dict( changed=False, - msg="Profiles {profiles} already {action}ed, nothing to do".format( - action=action, - profiles=profiles)) + msg=f"Profiles {profiles} already {action}ed, nothing to do") # try to assign or unassign profiles to resource - url = '{resource_url}/policy_profiles'.format(resource_url=self.resource_url) + url = f'{self.resource_url}/policy_profiles' try: response = self.client.post(url, action=action, resources=profiles_to_post) except Exception as e: - msg = "Failed to {action} profile: {error}".format( - action=action, - error=e) + msg = f"Failed to {action} profile: {e}" self.module.fail_json(msg=msg) # check all entities in result to be successful for result in response['results']: if not result['success']: - msg = "Failed to {action}: {message}".format( - action=action, - message=result['message']) + msg = f"Failed to {action}: {result['message']}" self.module.fail_json(msg=msg) # successfully changed all needed profiles return dict( changed=True, - msg="Successfully {action}ed profiles: {profiles}".format( - action=action, - profiles=profiles)) + msg=f"Successfully {action}ed profiles: {profiles}") class ManageIQTags(object): @@ -360,17 +343,12 @@ class ManageIQTags(object): self.resource_type = resource_type self.resource_id = resource_id - self.resource_url = '{api_url}/{resource_type}/{resource_id}'.format( - api_url=self.api_url, - resource_type=resource_type, - resource_id=resource_id) + self.resource_url = f'{self.api_url}/{resource_type}/{resource_id}' def full_tag_name(self, tag): """ Returns the full tag name in manageiq """ - return '/managed/{tag_category}/{tag_name}'.format( - tag_category=tag['category'], - tag_name=tag['name']) + return f"/managed/{tag['category']}/{tag['name']}" def clean_tag_object(self, tag): """ Clean a tag object to have human readable form of: @@ -397,9 +375,7 @@ class ManageIQTags(object): try: response = self.client.get(url.format(resource_url=self.resource_url)) except Exception as e: - msg = "Failed to query {resource_type} tags: {error}".format( - resource_type=self.resource_type, - error=e) + msg = f"Failed to query {self.resource_type} tags: {e}" self.module.fail_json(msg=msg) resources = response.get('resources', []) @@ -442,27 +418,23 @@ class ManageIQTags(object): if not tags_to_post: return dict( changed=False, - msg="Tags already {action}ed, nothing to do".format(action=action)) + msg=f"Tags already {action}ed, nothing to do") # try to assign or unassign tags to resource - url = '{resource_url}/tags'.format(resource_url=self.resource_url) + url = f'{self.resource_url}/tags' try: response = self.client.post(url, action=action, resources=tags) except Exception as e: - msg = "Failed to {action} tag: {error}".format( - action=action, - error=e) + msg = f"Failed to {action} tag: {e}" self.module.fail_json(msg=msg) # check all entities in result to be successful for result in response['results']: if not result['success']: - msg = "Failed to {action}: {message}".format( - action=action, - message=result['message']) + msg = f"Failed to {action}: {result['message']}" self.module.fail_json(msg=msg) # successfully changed all needed tags return dict( changed=True, - msg="Successfully {action}ed tags".format(action=action)) + msg=f"Successfully {action}ed tags") diff --git a/plugins/module_utils/memset.py b/plugins/module_utils/memset.py index ac2348704f..cbfbc9108a 100644 --- a/plugins/module_utils/memset.py +++ b/plugins/module_utils/memset.py @@ -55,7 +55,7 @@ def memset_api_call(api_key, api_method, payload=None): data = urlencode(payload) headers = {'Content-Type': 'application/x-www-form-urlencoded'} api_uri_base = 'https://api.memset.com/v1/json/' - api_uri = '{0}{1}/' . format(api_uri_base, api_method) + api_uri = f'{api_uri_base}{api_method}/' try: resp = open_url(api_uri, data=data, headers=headers, method="POST", force_basic_auth=True, url_username=api_key) @@ -72,13 +72,13 @@ def memset_api_call(api_key, api_method, payload=None): response.status_code = errorcode if response.status_code is not None: - msg = "Memset API returned a {0} response ({1}, {2})." . format(response.status_code, response.json()['error_type'], response.json()['error']) + msg = f"Memset API returned a {response.status_code} response ({response.json()['error_type']}, {response.json()['error']})." else: - msg = "Memset API returned an error ({0}, {1})." . format(response.json()['error_type'], response.json()['error']) + msg = f"Memset API returned an error ({response.json()['error_type']}, {response.json()['error']})." except urllib_error.URLError as e: has_failed = True - msg = "An URLError occurred ({0})." . format(type(e)) - response.stderr = "{0}" . format(e) + msg = f"An URLError occurred ({type(e)})." + response.stderr = f"{e}" if msg is None: msg = response.json() diff --git a/plugins/module_utils/mh/base.py b/plugins/module_utils/mh/base.py index c2e6bafd7c..688d65fc35 100644 --- a/plugins/module_utils/mh/base.py +++ b/plugins/module_utils/mh/base.py @@ -40,7 +40,7 @@ class ModuleHelperBase(object): def __getattr__(self, attr): if attr in self._delegated_to_module: return getattr(self.module, attr) - raise AttributeError("ModuleHelperBase has no attribute '%s'" % (attr, )) + raise AttributeError(f"ModuleHelperBase has no attribute '{attr}'") def __init_module__(self): pass diff --git a/plugins/module_utils/mh/deco.py b/plugins/module_utils/mh/deco.py index 1a887418d7..0be576ccfa 100644 --- a/plugins/module_utils/mh/deco.py +++ b/plugins/module_utils/mh/deco.py @@ -38,7 +38,7 @@ def module_fails_on_exception(func): @wraps(func) def wrapper(self, *args, **kwargs): def fix_key(k): - return k if k not in conflict_list else "_" + k + return k if k not in conflict_list else f"_{k}" def fix_var_conflicts(output): result = {fix_key(k): v for k, v in output.items()} @@ -56,7 +56,7 @@ def module_fails_on_exception(func): except Exception as e: # patchy solution to resolve conflict with output variables output = fix_var_conflicts(self.output) - msg = "Module failed with exception: {0}".format(str(e).strip()) + msg = f"Module failed with exception: {str(e).strip()}" self.module.fail_json(msg=msg, exception=traceback.format_exc(), output=self.output, vars=self.vars.output(), **output) return wrapper diff --git a/plugins/module_utils/mh/exceptions.py b/plugins/module_utils/mh/exceptions.py index 4e203576f9..94bb7d7fff 100644 --- a/plugins/module_utils/mh/exceptions.py +++ b/plugins/module_utils/mh/exceptions.py @@ -10,7 +10,7 @@ from ansible.module_utils.common.text.converters import to_native class ModuleHelperException(Exception): def __init__(self, msg, update_output=None, *args, **kwargs): - self.msg = to_native(msg or "Module failed with exception: {0}".format(self)) + self.msg = to_native(msg or f"Module failed with exception: {self}") if update_output is None: update_output = {} self.update_output = update_output diff --git a/plugins/module_utils/mh/mixins/deprecate_attrs.py b/plugins/module_utils/mh/mixins/deprecate_attrs.py index 70262d9489..166e365782 100644 --- a/plugins/module_utils/mh/mixins/deprecate_attrs.py +++ b/plugins/module_utils/mh/mixins/deprecate_attrs.py @@ -15,7 +15,7 @@ class DeprecateAttrsMixin(object): if target is None: target = self if not hasattr(target, attr): - raise ValueError("Target {0} has no attribute {1}".format(target, attr)) + raise ValueError(f"Target {target} has no attribute {attr}") if module is None: if isinstance(target, AnsibleModule): module = target @@ -57,4 +57,4 @@ class DeprecateAttrsMixin(object): # override attribute prop = property(_getter) setattr(target, attr, prop) - setattr(target, "_{0}_setter".format(attr), prop.setter(_setter)) + setattr(target, f"_{attr}_setter", prop.setter(_setter)) diff --git a/plugins/module_utils/mh/mixins/state.py b/plugins/module_utils/mh/mixins/state.py index 1eb82672ed..a04c3b1386 100644 --- a/plugins/module_utils/mh/mixins/state.py +++ b/plugins/module_utils/mh/mixins/state.py @@ -15,7 +15,7 @@ class StateMixin(object): return self.default_state if state is None else state def _method(self, state): - return "{0}_{1}".format(self.state_param, state) + return f"{self.state_param}_{state}" def __run__(self): state = self._state() @@ -35,4 +35,4 @@ class StateMixin(object): return func() def __state_fallback__(self): - raise ValueError("Cannot find method: {0}".format(self._method(self._state()))) + raise ValueError(f"Cannot find method: {self._method(self._state())}") diff --git a/plugins/module_utils/net_tools/pritunl/api.py b/plugins/module_utils/net_tools/pritunl/api.py index c2c6ef79e8..7d6bd7fe86 100644 --- a/plugins/module_utils/net_tools/pritunl/api.py +++ b/plugins/module_utils/net_tools/pritunl/api.py @@ -62,7 +62,7 @@ def _delete_pritunl_organization( api_token=api_token, api_secret=api_secret, method="DELETE", - path="/organization/%s" % (organization_id), + path=f"/organization/{organization_id}", validate_certs=validate_certs, ) @@ -90,7 +90,7 @@ def _get_pritunl_users( api_secret=api_secret, base_url=base_url, method="GET", - path="/user/%s" % organization_id, + path=f"/user/{organization_id}", validate_certs=validate_certs, ) @@ -103,7 +103,7 @@ def _delete_pritunl_user( api_secret=api_secret, base_url=base_url, method="DELETE", - path="/user/%s/%s" % (organization_id, user_id), + path=f"/user/{organization_id}/{user_id}", validate_certs=validate_certs, ) @@ -116,7 +116,7 @@ def _post_pritunl_user( api_secret=api_secret, base_url=base_url, method="POST", - path="/user/%s" % organization_id, + path=f"/user/{organization_id}", headers={"Content-Type": "application/json"}, data=json.dumps(user_data), validate_certs=validate_certs, @@ -137,7 +137,7 @@ def _put_pritunl_user( api_secret=api_secret, base_url=base_url, method="PUT", - path="/user/%s/%s" % (organization_id, user_id), + path=f"/user/{organization_id}/{user_id}", headers={"Content-Type": "application/json"}, data=json.dumps(user_data), validate_certs=validate_certs, @@ -221,7 +221,7 @@ def post_pritunl_organization( if response.getcode() != 200: raise PritunlException( - "Could not add organization %s to Pritunl" % (organization_name) + f"Could not add organization {organization_name} to Pritunl" ) # The user PUT request returns the updated user object return json.loads(response.read()) @@ -249,8 +249,7 @@ def post_pritunl_user( if response.getcode() != 200: raise PritunlException( - "Could not remove user %s from organization %s from Pritunl" - % (user_id, organization_id) + f"Could not remove user {user_id} from organization {organization_id} from Pritunl" ) # user POST request returns an array of a single item, # so return this item instead of the list @@ -268,8 +267,7 @@ def post_pritunl_user( if response.getcode() != 200: raise PritunlException( - "Could not update user %s from organization %s from Pritunl" - % (user_id, organization_id) + f"Could not update user {user_id} from organization {organization_id} from Pritunl" ) # The user PUT request returns the updated user object return json.loads(response.read()) @@ -288,7 +286,7 @@ def delete_pritunl_organization( if response.getcode() != 200: raise PritunlException( - "Could not remove organization %s from Pritunl" % (organization_id) + f"Could not remove organization {organization_id} from Pritunl" ) return json.loads(response.read()) @@ -308,8 +306,7 @@ def delete_pritunl_user( if response.getcode() != 200: raise PritunlException( - "Could not remove user %s from organization %s from Pritunl" - % (user_id, organization_id) + f"Could not remove user {user_id} from organization {organization_id} from Pritunl" ) return json.loads(response.read()) @@ -332,9 +329,7 @@ def pritunl_auth_request( auth_timestamp = str(int(time.time())) auth_nonce = uuid.uuid4().hex - auth_string = "&".join( - [api_token, auth_timestamp, auth_nonce, method.upper(), path] - ) + auth_string = f"{api_token}&{auth_timestamp}&{auth_nonce}&{method.upper()}&{path}" auth_signature = base64.b64encode( hmac.new( @@ -353,7 +348,7 @@ def pritunl_auth_request( auth_headers.update(headers) try: - uri = "%s%s" % (base_url, path) + uri = f"{base_url}{path}" return open_url( uri, diff --git a/plugins/module_utils/ocapi_utils.py b/plugins/module_utils/ocapi_utils.py index 147009399f..fd606d9bcc 100644 --- a/plugins/module_utils/ocapi_utils.py +++ b/plugins/module_utils/ocapi_utils.py @@ -13,7 +13,6 @@ from urllib.parse import urlparse from ansible.module_utils.urls import open_url from ansible.module_utils.common.text.converters import to_native -from ansible.module_utils.common.text.converters import to_text GET_HEADERS = {'accept': 'application/json'} @@ -57,16 +56,14 @@ class OcapiUtils(object): headers = {k.lower(): v for (k, v) in resp.info().items()} except HTTPError as e: return {'ret': False, - 'msg': "HTTP Error %s on GET request to '%s'" - % (e.code, uri), + 'msg': f"HTTP Error {e.code} on GET request to '{uri}'", 'status': e.code} except URLError as e: - return {'ret': False, 'msg': "URL Error on GET request to '%s': '%s'" - % (uri, e.reason)} + return {'ret': False, 'msg': f"URL Error on GET request to '{uri}': '{e.reason}'"} # Almost all errors should be caught above, but just in case except Exception as e: return {'ret': False, - 'msg': "Failed GET request to '%s': '%s'" % (uri, to_text(e))} + 'msg': f"Failed GET request to '{uri}': '{e}'"} return {'ret': True, 'data': data, 'headers': headers} def delete_request(self, uri, etag=None): @@ -87,16 +84,14 @@ class OcapiUtils(object): headers = {k.lower(): v for (k, v) in resp.info().items()} except HTTPError as e: return {'ret': False, - 'msg': "HTTP Error %s on DELETE request to '%s'" - % (e.code, uri), + 'msg': f"HTTP Error {e.code} on DELETE request to '{uri}'", 'status': e.code} except URLError as e: - return {'ret': False, 'msg': "URL Error on DELETE request to '%s': '%s'" - % (uri, e.reason)} + return {'ret': False, 'msg': f"URL Error on DELETE request to '{uri}': '{e.reason}'"} # Almost all errors should be caught above, but just in case except Exception as e: return {'ret': False, - 'msg': "Failed DELETE request to '%s': '%s'" % (uri, to_text(e))} + 'msg': f"Failed DELETE request to '{uri}': '{e}'"} return {'ret': True, 'data': data, 'headers': headers} def put_request(self, uri, payload, etag=None): @@ -114,16 +109,14 @@ class OcapiUtils(object): headers = {k.lower(): v for (k, v) in resp.info().items()} except HTTPError as e: return {'ret': False, - 'msg': "HTTP Error %s on PUT request to '%s'" - % (e.code, uri), + 'msg': f"HTTP Error {e.code} on PUT request to '{uri}'", 'status': e.code} except URLError as e: - return {'ret': False, 'msg': "URL Error on PUT request to '%s': '%s'" - % (uri, e.reason)} + return {'ret': False, 'msg': f"URL Error on PUT request to '{uri}': '{e.reason}'"} # Almost all errors should be caught above, but just in case except Exception as e: return {'ret': False, - 'msg': "Failed PUT request to '%s': '%s'" % (uri, to_text(e))} + 'msg': f"Failed PUT request to '{uri}': '{e}'"} return {'ret': True, 'headers': headers, 'resp': resp} def post_request(self, uri, payload, content_type="application/json", timeout=None): @@ -145,16 +138,14 @@ class OcapiUtils(object): headers = {k.lower(): v for (k, v) in resp.info().items()} except HTTPError as e: return {'ret': False, - 'msg': "HTTP Error %s on POST request to '%s'" - % (e.code, uri), + 'msg': f"HTTP Error {e.code} on POST request to '{uri}'", 'status': e.code} except URLError as e: - return {'ret': False, 'msg': "URL Error on POST request to '%s': '%s'" - % (uri, e.reason)} + return {'ret': False, 'msg': f"URL Error on POST request to '{uri}': '{e.reason}'"} # Almost all errors should be caught above, but just in case except Exception as e: return {'ret': False, - 'msg': "Failed POST request to '%s': '%s'" % (uri, to_text(e))} + 'msg': f"Failed POST request to '{uri}': '{e}'"} return {'ret': True, 'headers': headers, 'resp': resp} def get_uri_with_slot_number_query_param(self, uri): @@ -166,7 +157,7 @@ class OcapiUtils(object): """ if self.proxy_slot_number is not None: parsed_url = urlparse(uri) - return parsed_url._replace(query="slotnumber=" + str(self.proxy_slot_number)).geturl() + return parsed_url._replace(query=f"slotnumber={self.proxy_slot_number}").geturl() else: return uri @@ -201,7 +192,7 @@ class OcapiUtils(object): elif command.startswith("PowerMode"): return self.manage_power_mode(command) else: - return {'ret': False, 'msg': 'Invalid command: ' + command} + return {'ret': False, 'msg': f"Invalid command: {command}"} return {'ret': True} @@ -240,7 +231,7 @@ class OcapiUtils(object): return response data = response['data'] if key not in data: - return {'ret': False, 'msg': "Key %s not found" % key} + return {'ret': False, 'msg': f"Key {key} not found"} if 'ID' not in data[key]: return {'ret': False, 'msg': 'IndicatorLED for resource has no ID.'} @@ -283,7 +274,7 @@ class OcapiUtils(object): return response data = response['data'] if key not in data: - return {'ret': False, 'msg': "Key %s not found" % key} + return {'ret': False, 'msg': f"Key {key} not found"} if 'ID' not in data[key]: return {'ret': False, 'msg': 'PowerState for resource has no ID.'} @@ -305,7 +296,7 @@ class OcapiUtils(object): if response['ret'] is False: return response else: - return {'ret': False, 'msg': 'Invalid command: ' + command} + return {'ret': False, 'msg': f"Invalid command: {command}"} return {'ret': True} @@ -322,14 +313,14 @@ class OcapiUtils(object): this method sends the file as binary. """ boundary = str(uuid.uuid4()) # Generate a random boundary - body = "--" + boundary + '\r\n' - body += 'Content-Disposition: form-data; name="FirmwareFile"; filename="%s"\r\n' % to_native(os.path.basename(filename)) + body = f"--{boundary}\r\n" + body += f'Content-Disposition: form-data; name="FirmwareFile"; filename="{to_native(os.path.basename(filename))}"\r\n' body += 'Content-Type: application/octet-stream\r\n\r\n' body_bytes = bytearray(body, 'utf-8') with open(filename, 'rb') as f: body_bytes += f.read() - body_bytes += bytearray("\r\n--%s--" % boundary, 'utf-8') - return ("multipart/form-data; boundary=%s" % boundary, + body_bytes += bytearray(f"\r\n--{boundary}--", 'utf-8') + return (f"multipart/form-data; boundary={boundary}", body_bytes) def upload_firmware_image(self, update_image_path): @@ -339,7 +330,7 @@ class OcapiUtils(object): """ if not (os.path.exists(update_image_path) and os.path.isfile(update_image_path)): return {'ret': False, 'msg': 'File does not exist.'} - url = self.root_uri + "OperatingSystem" + url = f"{self.root_uri}OperatingSystem" url = self.get_uri_with_slot_number_query_param(url) content_type, b_form_data = self.prepare_multipart_firmware_upload(update_image_path) diff --git a/plugins/module_utils/oneandone.py b/plugins/module_utils/oneandone.py index 4d98a7d80c..1c9cb73d73 100644 --- a/plugins/module_utils/oneandone.py +++ b/plugins/module_utils/oneandone.py @@ -209,7 +209,7 @@ def wait_for_resource_creation_completion(oneandone_conn, (resource_type != OneAndOneResources.server and resource_state.lower() == 'active')): return elif resource_state.lower() == 'failed': - raise Exception('%s creation failed for %s' % (resource_type, resource_id)) + raise Exception(f'{resource_type} creation failed for {resource_id}') elif resource_state.lower() in ('active', 'enabled', 'deploying', @@ -217,10 +217,10 @@ def wait_for_resource_creation_completion(oneandone_conn, continue else: raise Exception( - 'Unknown %s state %s' % (resource_type, resource_state)) + f'Unknown {resource_type} state {resource_state}') raise Exception( - 'Timed out waiting for %s completion for %s' % (resource_type, resource_id)) + f'Timed out waiting for {resource_type} completion for {resource_id}') def wait_for_resource_deletion_completion(oneandone_conn, @@ -246,7 +246,7 @@ def wait_for_resource_deletion_completion(oneandone_conn, _type = 'PRIVATENETWORK' else: raise Exception( - 'Unsupported wait_for delete operation for %s resource' % resource_type) + f'Unsupported wait_for delete operation for {resource_type} resource') for log in logs: if (log['resource']['id'] == resource_id and @@ -255,4 +255,4 @@ def wait_for_resource_deletion_completion(oneandone_conn, log['status']['state'] == 'OK'): return raise Exception( - 'Timed out waiting for %s deletion for %s' % (resource_type, resource_id)) + f'Timed out waiting for {resource_type} deletion for {resource_id}') diff --git a/plugins/module_utils/oneview.py b/plugins/module_utils/oneview.py index b740450244..1f57355f58 100644 --- a/plugins/module_utils/oneview.py +++ b/plugins/module_utils/oneview.py @@ -395,11 +395,11 @@ class OneViewModuleBase(object, metaclass=abc.ABCMeta): resource1 = first_resource resource2 = second_resource - debug_resources = "resource1 = {0}, resource2 = {1}".format(resource1, resource2) + debug_resources = f"resource1 = {resource1}, resource2 = {resource2}" # The first resource is True / Not Null and the second resource is False / Null if resource1 and not resource2: - self.module.log("resource1 and not resource2. " + debug_resources) + self.module.log(f"resource1 and not resource2. {debug_resources}") return False # Checks all keys in first dict against the second dict @@ -449,15 +449,15 @@ class OneViewModuleBase(object, metaclass=abc.ABCMeta): resource1 = first_resource resource2 = second_resource - debug_resources = "resource1 = {0}, resource2 = {1}".format(resource1, resource2) + debug_resources = f"resource1 = {resource1}, resource2 = {resource2}" # The second list is null / empty / False if not resource2: - self.module.log("resource 2 is null. " + debug_resources) + self.module.log(f"resource 2 is null. {debug_resources}") return False if len(resource1) != len(resource2): - self.module.log("resources have different length. " + debug_resources) + self.module.log(f"resources have different length. {debug_resources}") return False resource1 = sorted(resource1, key=_str_sorted) @@ -467,15 +467,15 @@ class OneViewModuleBase(object, metaclass=abc.ABCMeta): if isinstance(val, Mapping): # change comparison function to compare dictionaries if not self.compare(val, resource2[i]): - self.module.log("resources are different. " + debug_resources) + self.module.log(f"resources are different. {debug_resources}") return False elif isinstance(val, list): # recursive call if not self.compare_list(val, resource2[i]): - self.module.log("lists are different. " + debug_resources) + self.module.log(f"lists are different. {debug_resources}") return False elif _standardize_value(val) != _standardize_value(resource2[i]): - self.module.log("values are different. " + debug_resources) + self.module.log(f"values are different. {debug_resources}") return False # no differences found diff --git a/plugins/module_utils/opennebula.py b/plugins/module_utils/opennebula.py index 24500cb8c1..ce9ec76b0d 100644 --- a/plugins/module_utils/opennebula.py +++ b/plugins/module_utils/opennebula.py @@ -46,16 +46,16 @@ def render(to_render): if value is None: continue if isinstance(value, dict): - yield '{0:}=[{1:}]'.format(key, ','.join(recurse(value))) + yield f"{key}=[{','.join(recurse(value))}]" continue if isinstance(value, list): for item in value: - yield '{0:}=[{1:}]'.format(key, ','.join(recurse(item))) + yield f"{key}=[{','.join(recurse(item))}]" continue if isinstance(value, str): yield '{0:}="{1:}"'.format(key, value.replace('\\', '\\\\').replace('"', '\\"')) continue - yield '{0:}="{1:}"'.format(key, value) + yield f'{key}="{value}"' return '\n'.join(recurse(to_render)) @@ -124,7 +124,7 @@ class OpenNebulaModule: else: self.fail("Either api_password or the environment variable ONE_PASSWORD must be provided") - session = "%s:%s" % (username, password) + session = f"{username}:{password}" if not self.module.params.get("validate_certs") and "PYTHONHTTPSVERIFY" not in environ: return OneServer(url, session=session, context=no_ssl_validation_context) @@ -312,11 +312,11 @@ class OpenNebulaModule: current_state = state() if current_state in invalid_states: - self.fail('invalid %s state %s' % (element_name, state_name(current_state))) + self.fail(f'invalid {element_name} state {state_name(current_state)}') if transition_states: if current_state not in transition_states: - self.fail('invalid %s transition state %s' % (element_name, state_name(current_state))) + self.fail(f'invalid {element_name} transition state {state_name(current_state)}') if current_state in target_states: return True @@ -334,7 +334,7 @@ class OpenNebulaModule: try: self.run(self.one, self.module, self.result) except OneException as e: - self.fail(msg="OpenNebula Exception: %s" % e) + self.fail(msg=f"OpenNebula Exception: {e}") def run(self, one, module, result): """ diff --git a/plugins/module_utils/pkg_req.py b/plugins/module_utils/pkg_req.py index d749e5f86b..13c824440f 100644 --- a/plugins/module_utils/pkg_req.py +++ b/plugins/module_utils/pkg_req.py @@ -47,7 +47,7 @@ class PackageRequirement: return req.name, req except Exception as e: - raise ValueError("Invalid package specification for '{0}': {1}".format(name, e)) from e + raise ValueError(f"Invalid package specification for '{name}': {e}") from e def matches_version(self, version): """ @@ -68,4 +68,4 @@ class PackageRequirement: return ver in self.requirement.specifier except InvalidVersion as e: - raise ValueError("Invalid version '{0}': {1}".format(version, e)) from e + raise ValueError(f"Invalid version '{version}': {e}") from e diff --git a/plugins/module_utils/python_runner.py b/plugins/module_utils/python_runner.py index d60d75f97b..7d9b94f50e 100644 --- a/plugins/module_utils/python_runner.py +++ b/plugins/module_utils/python_runner.py @@ -25,7 +25,7 @@ class PythonRunner(CmdRunner): path_prefix.append(os.path.join(venv, "bin")) if environ_update is None: environ_update = {} - environ_update["PATH"] = "%s:%s" % (":".join(path_prefix), os.environ["PATH"]) + environ_update["PATH"] = f"{':'.join(path_prefix)}:{os.environ['PATH']}" environ_update["VIRTUAL_ENV"] = venv python_cmd = [self.python] + _ensure_list(command) diff --git a/plugins/module_utils/redis.py b/plugins/module_utils/redis.py index 9d87ca83f8..d3de8e63e9 100644 --- a/plugins/module_utils/redis.py +++ b/plugins/module_utils/redis.py @@ -100,5 +100,5 @@ class RedisAnsible(object): try: return Redis(**redis_auth_params(self.module)) except Exception as e: - self.module.fail_json(msg='{0}'.format(str(e))) + self.module.fail_json(msg=f'{e}') return None diff --git a/plugins/module_utils/rundeck.py b/plugins/module_utils/rundeck.py index 4e109407b3..7b9f56339a 100644 --- a/plugins/module_utils/rundeck.py +++ b/plugins/module_utils/rundeck.py @@ -53,11 +53,7 @@ def api_request(module, endpoint, data=None, method="GET", content_type="applica response, info = fetch_url( module=module, - url="%s/api/%s/%s" % ( - module.params["url"], - module.params["api_version"], - endpoint - ), + url=f"{module.params['url']}/api/{module.params['api_version']}/{endpoint}", data=json.dumps(data), method=method, headers={ diff --git a/plugins/module_utils/saslprep.py b/plugins/module_utils/saslprep.py index f7394ce008..02a0cc87f4 100644 --- a/plugins/module_utils/saslprep.py +++ b/plugins/module_utils/saslprep.py @@ -105,35 +105,31 @@ def prohibited_output_profile(string): for c in string: # RFC4013 2.3. Prohibited Output: if in_table_c12(c): - raise ValueError('%s: prohibited non-ASCII space characters ' - 'that cannot be replaced (C.1.2).' % RFC) + raise ValueError(f'{RFC}: prohibited non-ASCII space characters that cannot be replaced (C.1.2).') if in_table_c21_c22(c): - raise ValueError('%s: prohibited control characters (C.2.1).' % RFC) + raise ValueError(f'{RFC}: prohibited control characters (C.2.1).') if in_table_c3(c): - raise ValueError('%s: prohibited private Use characters (C.3).' % RFC) + raise ValueError(f'{RFC}: prohibited private Use characters (C.3).') if in_table_c4(c): - raise ValueError('%s: prohibited non-character code points (C.4).' % RFC) + raise ValueError(f'{RFC}: prohibited non-character code points (C.4).') if in_table_c5(c): - raise ValueError('%s: prohibited surrogate code points (C.5).' % RFC) + raise ValueError(f'{RFC}: prohibited surrogate code points (C.5).') if in_table_c6(c): - raise ValueError('%s: prohibited inappropriate for plain text ' - 'characters (C.6).' % RFC) + raise ValueError(f'{RFC}: prohibited inappropriate for plain text characters (C.6).') if in_table_c7(c): - raise ValueError('%s: prohibited inappropriate for canonical ' - 'representation characters (C.7).' % RFC) + raise ValueError(f'{RFC}: prohibited inappropriate for canonical representation characters (C.7).') if in_table_c8(c): - raise ValueError('%s: prohibited change display properties / ' - 'deprecated characters (C.8).' % RFC) + raise ValueError(f'{RFC}: prohibited change display properties / deprecated characters (C.8).') if in_table_c9(c): - raise ValueError('%s: prohibited tagging characters (C.9).' % RFC) + raise ValueError(f'{RFC}: prohibited tagging characters (C.9).') # RFC4013, 2.4. Bidirectional Characters: if is_prohibited_bidi_ch(c): - raise ValueError('%s: prohibited bidi characters (%s).' % (RFC, bidi_table)) + raise ValueError(f'{RFC}: prohibited bidi characters ({bidi_table}).') # RFC4013, 2.5. Unassigned Code Points: if in_table_a1(c): - raise ValueError('%s: prohibited unassigned code points (A.1).' % RFC) + raise ValueError(f'{RFC}: prohibited unassigned code points (A.1).') def saslprep(string): @@ -155,7 +151,7 @@ def saslprep(string): # comprised of characters from the Unicode [Unicode] character set." # Validate the string is a Unicode string if not is_unicode_str(string): - raise TypeError('input must be of type str, not %s' % type(string)) + raise TypeError(f'input must be of type str, not {type(string)}') # RFC4013: 2.1. Mapping. string = mapping_profile(string) diff --git a/plugins/module_utils/snap.py b/plugins/module_utils/snap.py index 3ca28441a1..d672a7b519 100644 --- a/plugins/module_utils/snap.py +++ b/plugins/module_utils/snap.py @@ -35,7 +35,7 @@ def snap_runner(module, **kwargs): _set=cmd_runner_fmt.as_fixed("set"), get=cmd_runner_fmt.as_fixed(["get", "-d"]), classic=cmd_runner_fmt.as_bool("--classic"), - channel=cmd_runner_fmt.as_func(lambda v: [] if v == 'stable' else ['--channel', '{0}'.format(v)]), + channel=cmd_runner_fmt.as_func(lambda v: [] if v == 'stable' else ['--channel', f'{v}']), options=cmd_runner_fmt.as_list(), info=cmd_runner_fmt.as_fixed("info"), dangerous=cmd_runner_fmt.as_bool("--dangerous"), diff --git a/plugins/module_utils/source_control/bitbucket.py b/plugins/module_utils/source_control/bitbucket.py index dde3f7dd26..a3d3fa5f2f 100644 --- a/plugins/module_utils/source_control/bitbucket.py +++ b/plugins/module_utils/source_control/bitbucket.py @@ -54,14 +54,14 @@ class BitbucketHelper: if info['status'] == 200: self.access_token = content['access_token'] else: - self.module.fail_json(msg='Failed to retrieve access token: {0}'.format(info)) + self.module.fail_json(msg=f'Failed to retrieve access token: {info}') def request(self, api_url, method, data=None, headers=None): headers = headers or {} if self.access_token: headers.update({ - 'Authorization': 'Bearer {0}'.format(self.access_token), + 'Authorization': f'Bearer {self.access_token}', }) elif self.module.params['user'] and self.module.params['password']: headers.update({ diff --git a/plugins/module_utils/ssh.py b/plugins/module_utils/ssh.py index f9b8b531d6..851efcbe86 100644 --- a/plugins/module_utils/ssh.py +++ b/plugins/module_utils/ssh.py @@ -13,7 +13,7 @@ import os def determine_config_file(user, config_file): if user: - config_file = os.path.join(os.path.expanduser('~%s' % user), '.ssh', 'config') + config_file = os.path.join(os.path.expanduser(f'~{user}'), '.ssh', 'config') elif config_file is None: config_file = '/etc/ssh/ssh_config' return config_file diff --git a/plugins/module_utils/storage/hpe3par/hpe3par.py b/plugins/module_utils/storage/hpe3par/hpe3par.py index 96558fad4f..da88db1ce6 100644 --- a/plugins/module_utils/storage/hpe3par/hpe3par.py +++ b/plugins/module_utils/storage/hpe3par/hpe3par.py @@ -20,7 +20,7 @@ def convert_to_binary_multiple(size_with_unit): if float(size) < 0: return -1 if not valid_unit: - raise ValueError("%s does not have a valid unit. The unit must be one of %s" % (size_with_unit, valid_units)) + raise ValueError(f"{size_with_unit} does not have a valid unit. The unit must be one of {valid_units}") size = size_with_unit.replace(" ", "").split('iB')[0] size_kib = basic.human_to_bytes(size) diff --git a/plugins/module_utils/univention_umc.py b/plugins/module_utils/univention_umc.py index 4270c5199e..1475a91542 100644 --- a/plugins/module_utils/univention_umc.py +++ b/plugins/module_utils/univention_umc.py @@ -89,7 +89,7 @@ def uldap(): def construct(): try: secret_file = open('/etc/ldap.secret', 'r') - bind_dn = 'cn=admin,{0}'.format(base_dn()) + bind_dn = f'cn=admin,{base_dn()}' except IOError: # pragma: no cover secret_file = open('/etc/machine.secret', 'r') bind_dn = config_registry()["ldap/hostdn"] @@ -186,7 +186,7 @@ def module_by_name(module_name_): univention.admin.modules.init(uldap(), position_base_dn(), module) return module - return _singleton('module/%s' % module_name_, construct) + return _singleton(f'module/{module_name_}', construct) def get_umc_admin_objects(): diff --git a/plugins/module_utils/utm_utils.py b/plugins/module_utils/utm_utils.py index c86442efe7..0bb2086b8c 100644 --- a/plugins/module_utils/utm_utils.py +++ b/plugins/module_utils/utm_utils.py @@ -71,8 +71,9 @@ class UTM: """ self.info_only = info_only self.module = module - self.request_url = module.params.get('utm_protocol') + "://" + module.params.get('utm_host') + ":" + to_native( - module.params.get('utm_port')) + "/api/objects/" + endpoint + "/" + self.request_url = ( + f"{module.params.get('utm_protocol')}://{module.params.get('utm_host')}:{module.params.get('utm_port')}/api/objects/{endpoint}/" + ) """ The change_relevant_keys will be checked for changes to determine whether the object needs to be updated @@ -82,9 +83,8 @@ class UTM: self.module.params['url_password'] = module.params.get('utm_token') if all(elem in self.change_relevant_keys for elem in module.params.keys()): raise UTMModuleConfigurationError( - "The keys " + to_native( - self.change_relevant_keys) + " to check are not in the modules keys:\n" + to_native( - list(module.params.keys()))) + f"The keys {self.change_relevant_keys} to check are not in the modules keys:\n{list(module.params.keys())}" + ) def execute(self): try: diff --git a/plugins/module_utils/vardict.py b/plugins/module_utils/vardict.py index cee21083b5..ccea7d5bb6 100644 --- a/plugins/module_utils/vardict.py +++ b/plugins/module_utils/vardict.py @@ -98,8 +98,9 @@ class _Variable(object): return def __str__(self): - return "".format( - self.value, self.initial_value, self.diff, self.output, self.change, self.verbosity + return ( + f"" ) @@ -163,7 +164,7 @@ class VarDict(object): ValueError: Raised if trying to set a variable with a reserved name. """ if name in self.reserved_names: - raise ValueError("Name {0} is reserved".format(name)) + raise ValueError(f"Name {name} is reserved") if name in self.__vars__: var = self._var(name) var.set_meta(**kwargs) diff --git a/plugins/module_utils/vexata.py b/plugins/module_utils/vexata.py index 00dff7c41e..f117e7759f 100644 --- a/plugins/module_utils/vexata.py +++ b/plugins/module_utils/vexata.py @@ -12,7 +12,6 @@ try: except ImportError: HAS_VEXATAPI = False -from ansible.module_utils.common.text.converters import to_native from ansible.module_utils.basic import env_fallback VXOS_VERSION = None @@ -58,7 +57,7 @@ def get_array(module): else: module.fail_json(msg='Test connection to array failed.') except Exception as e: - module.fail_json(msg='Vexata API access failed: {0}'.format(to_native(e))) + module.fail_json(msg=f'Vexata API access failed: {e}') def argument_spec(): diff --git a/plugins/module_utils/wdc_redfish_utils.py b/plugins/module_utils/wdc_redfish_utils.py index 3880626f90..564be3829e 100644 --- a/plugins/module_utils/wdc_redfish_utils.py +++ b/plugins/module_utils/wdc_redfish_utils.py @@ -64,7 +64,7 @@ class WdcRedfishUtils(RedfishUtils): A URI is considered good if we can GET uri/redfish/v1. """ for root_uri in root_uris: - uri = root_uri + "/redfish/v1" + uri = f"{root_uri}/redfish/v1" response = self.get_request(uri) if response['ret']: self.root_uri = root_uri @@ -86,7 +86,7 @@ class WdcRedfishUtils(RedfishUtils): :return: True/False if the enclosure is multi-tenant or not and return enclosure generation; None if unable to determine. """ - response = self.get_request(self.root_uri + self.service_root + "Chassis/Enclosure") + response = self.get_request(f"{self.root_uri}{self.service_root}Chassis/Enclosure") if response['ret'] is False: return None pattern = r".*-[A,B]" @@ -114,7 +114,7 @@ class WdcRedfishUtils(RedfishUtils): # Simple update status URI is not provided via GET /redfish/v1/UpdateService # So we have to hard code it. - self.simple_update_status_uri = "{0}/Status".format(self.simple_update_uri) + self.simple_update_status_uri = f"{self.simple_update_uri}/Status" # FWActivate URI if 'Oem' not in data['Actions']: @@ -267,9 +267,7 @@ class WdcRedfishUtils(RedfishUtils): parsed_url = urlparse(update_opts["update_image_uri"]) if update_creds: original_netloc = parsed_url.netloc - parsed_url = parsed_url._replace(netloc="{0}:{1}@{2}".format(update_creds.get("username"), - update_creds.get("password"), - original_netloc)) + parsed_url = parsed_url._replace(netloc=f"{update_creds.get('username')}:{update_creds.get('password')}@{original_netloc}") update_opts["update_image_uri"] = urlunparse(parsed_url) del update_opts["update_creds"] @@ -294,9 +292,7 @@ class WdcRedfishUtils(RedfishUtils): ]: return { 'ret': False, - 'msg': 'Target is not ready for FW update. Current status: {0} ({1})'.format( - status_code, status_description - )} + 'msg': f'Target is not ready for FW update. Current status: {status_code} ({status_description})'} # Check the FW version in the bundle file, and compare it to what is already on the IOMs @@ -314,20 +310,14 @@ class WdcRedfishUtils(RedfishUtils): if is_enclosure_multi_tenant != is_bundle_multi_tenant: return { 'ret': False, - 'msg': 'Enclosure multi-tenant is {0} but bundle multi-tenant is {1}'.format( - is_enclosure_multi_tenant, - is_bundle_multi_tenant, - ) + 'msg': f'Enclosure multi-tenant is {is_enclosure_multi_tenant} but bundle multi-tenant is {is_bundle_multi_tenant}' } # Verify that the bundle is compliant with the target enclosure if enclosure_gen != bundle_gen: return { 'ret': False, - 'msg': 'Enclosure generation is {0} but bundle is of {1}'.format( - enclosure_gen, - bundle_gen, - ) + 'msg': f'Enclosure generation is {enclosure_gen} but bundle is of {bundle_gen}' } # Version number installed on IOMs @@ -355,7 +345,7 @@ class WdcRedfishUtils(RedfishUtils): return { 'ret': True, 'changed': False, - 'msg': 'Version {0} already installed'.format(bundle_firmware_version) + 'msg': f'Version {bundle_firmware_version} already installed' } # Version numbers don't match the bundle -- proceed with update (unless we are in check mode) @@ -425,9 +415,7 @@ class WdcRedfishUtils(RedfishUtils): if status_code != self.UPDATE_STATUS_CODE_FW_UPDATE_COMPLETED_WAITING_FOR_ACTIVATION: return { 'ret': False, - 'msg': 'Target is not ready for FW activation after update. Current status: {0} ({1})'.format( - status_code, status_description - )} + 'msg': f'Target is not ready for FW activation after update. Current status: {status_code} ({status_description})'} self.firmware_activate(update_opts) return {'ret': True, 'changed': True, @@ -447,7 +435,7 @@ class WdcRedfishUtils(RedfishUtils): # The other will return an error with message "IOM Module A/B cannot be read" which_iom_is_this = None for iom_letter in ['A', 'B']: - iom_uri = "Chassis/IOModule{0}FRU".format(iom_letter) + iom_uri = f"Chassis/IOModule{iom_letter}FRU" response = self.get_request(self.root_uri + self.service_root + iom_uri) if response['ret'] is False: continue @@ -505,7 +493,7 @@ class WdcRedfishUtils(RedfishUtils): result['ret'] = True data = response['data'] if key not in data: - return {'ret': False, 'msg': "Key %s not found" % key} + return {'ret': False, 'msg': f"Key {key} not found"} current_led_status = data[key] if current_led_status == current_led_status_map[command]: return {'ret': True, 'changed': False} diff --git a/plugins/module_utils/xfconf.py b/plugins/module_utils/xfconf.py index b00090ba3c..8febbf450d 100644 --- a/plugins/module_utils/xfconf.py +++ b/plugins/module_utils/xfconf.py @@ -14,7 +14,7 @@ def _values_fmt(values, value_types): for value, value_type in zip(values, value_types): if value_type == 'bool': value = 'true' if boolean(value) else 'false' - result.extend(['--type', '{0}'.format(value_type), '--set', '{0}'.format(value)]) + result.extend(['--type', f'{value_type}', '--set', f'{value}']) return result