[stable-2.13] arg_spec - Return aliases in validation result and update aliases (#77576) (#77601)

When looking up the `no_log` setting for a parameter that is an alias in
`AnsibleModule._log_invocation()`, the alias value will always be an
empty dictionary since `self.aliases` on the `AnsibleModule` instance is
never updated after initialization. Since the `no_log` setting is on the
canonical parameter not the alias, an incorrect warning is issued if the
parameter matches `PASSWORD_MATCH`.

This PR returns the aliases dictionary as an attribute of the
`ValidationResult` and updates the `aliases` attribute on the
`AnsibleModule` instance.
(cherry picked from commit 1b947eaf92)

Co-authored-by: Sam Doran <github@samdoran.com>
pull/77611/head
Sam Doran 2 years ago committed by GitHub
parent 3e1db5d753
commit 91fb18bf31
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -0,0 +1,2 @@
bugfixes:
- arg_spec - Fix incorrect ``no_log`` warning when a parameter alias is used (https://github.com/ansible/ansible/pull/77576)

@ -502,6 +502,7 @@ class AnsibleModule(object):
self.validation_result = self.validator.validate(self.params)
self.params.update(self.validation_result.validated_parameters)
self.no_log_values.update(self.validation_result._no_log_values)
self.aliases.update(self.validation_result._aliases)
try:
error = self.validation_result.errors[0]

@ -61,6 +61,7 @@ class ValidationResult:
self._validated_parameters = deepcopy(parameters)
self._deprecations = []
self._warnings = []
self._aliases = {}
self.errors = AnsibleValidationErrorMultiple()
"""
:class:`~ansible.module_utils.errors.AnsibleValidationErrorMultiple` containing all
@ -180,12 +181,11 @@ class ArgumentSpecValidator:
alias_warnings = []
alias_deprecations = []
try:
aliases = _handle_aliases(self.argument_spec, result._validated_parameters, alias_warnings, alias_deprecations)
result._aliases.update(_handle_aliases(self.argument_spec, result._validated_parameters, alias_warnings, alias_deprecations))
except (TypeError, ValueError) as e:
aliases = {}
result.errors.append(AliasError(to_native(e)))
legal_inputs = _get_legal_inputs(self.argument_spec, result._validated_parameters, aliases)
legal_inputs = _get_legal_inputs(self.argument_spec, result._validated_parameters, result._aliases)
for option, alias in alias_warnings:
result._warnings.append({'option': option, 'alias': alias})

@ -709,3 +709,16 @@ def test_no_log_none(stdin, capfd):
# makes it into am.no_log_values. Instead we can check for the warning
# emitted by am._log_invocation.
assert len(get_warning_messages()) > 0
@pytest.mark.parametrize("stdin", [{"pass": "testing"}], indirect=["stdin"])
def test_no_log_alias(stdin, capfd):
"""Given module parameters that use an alias for a parameter that matches
PASSWORD_MATCH and has no_log=True set, a warning should not be issued.
"""
arg_spec = {
"other_pass": {"no_log": True, "aliases": ["pass"]},
}
am = basic.AnsibleModule(arg_spec)
assert len(get_warning_messages()) == 0

@ -95,6 +95,11 @@ def test_aliases(arg_spec, parameters, expected, deprecation, warning):
assert isinstance(result, ValidationResult)
assert result.validated_parameters == expected
assert result.error_messages == []
assert result._aliases == {
alias: param
for param, value in arg_spec.items()
for alias in value.get("aliases", [])
}
if deprecation:
assert deprecation == result._deprecations[0]

Loading…
Cancel
Save