diff --git a/changelogs/fragments/75021-dnf-support-non-english-env.yml b/changelogs/fragments/75021-dnf-support-non-english-env.yml new file mode 100644 index 00000000000..55dab8403dc --- /dev/null +++ b/changelogs/fragments/75021-dnf-support-non-english-env.yml @@ -0,0 +1,2 @@ +bugfixes: + - dnf - support non-english environments (https://github.com/ansible/ansible/issues/75021) diff --git a/lib/ansible/modules/dnf.py b/lib/ansible/modules/dnf.py index 770f2ca4e72..635646f5499 100644 --- a/lib/ansible/modules/dnf.py +++ b/lib/ansible/modules/dnf.py @@ -343,19 +343,16 @@ from ansible.module_utils.six import PY2, text_type from ansible.module_utils.compat.version import LooseVersion from ansible.module_utils.basic import AnsibleModule +from ansible.module_utils.common.locale import get_best_parsable_locale from ansible.module_utils.common.respawn import has_respawned, probe_interpreters_for_module, respawn_module from ansible.module_utils.yumdnf import YumDnf, yumdnf_argument_spec -try: - import dnf - import dnf.cli - import dnf.const - import dnf.exceptions - import dnf.subject - import dnf.util - HAS_DNF = True -except ImportError: - HAS_DNF = False + +# NOTE dnf Python bindings import is postponed, see DnfModule._ensure_dnf(), +# because we need AnsibleModule object to use get_best_parsable_locale() +# to set proper locale before importing dnf to be able to scrape +# the output in some cases (FIXME?). +dnf = None class DnfModule(YumDnf): @@ -531,6 +528,21 @@ class DnfModule(YumDnf): return rc def _ensure_dnf(self): + locale = get_best_parsable_locale(self.module) + os.environ['LC_ALL'] = os.environ['LC_MESSAGES'] = os.environ['LANG'] = locale + + global dnf + try: + import dnf + import dnf.cli + import dnf.const + import dnf.exceptions + import dnf.subject + import dnf.util + HAS_DNF = True + except ImportError: + HAS_DNF = False + if HAS_DNF: return @@ -1298,10 +1310,6 @@ class DnfModule(YumDnf): failure_response['msg'] = "Unknown Error occurred: {0}".format(to_native(e)) self.module.fail_json(**failure_response) - @staticmethod - def has_dnf(): - return HAS_DNF - def run(self): """The main function.""" diff --git a/test/integration/targets/dnf/tasks/dnf.yml b/test/integration/targets/dnf/tasks/dnf.yml index 7e6a8d8f489..9cfc44e3947 100644 --- a/test/integration/targets/dnf/tasks/dnf.yml +++ b/test/integration/targets/dnf/tasks/dnf.yml @@ -816,3 +816,21 @@ that: - nonexisting is success - nonexisting.msg == 'Nothing to do' + +# running on RHEL which is --remote where .mo language files are present +# for dnf as opposed to in --docker +- when: ansible_distribution == 'RedHat' + block: + - dnf: + name: langpacks-ja + state: present + + - dnf: + name: nginx-mod* + state: absent + environment: + LANG: ja_JP.UTF-8 + always: + - dnf: + name: langpacks-ja + state: absent