skip to Main Content

Declared YUM task as below:

---
- hosts: all
  vars:
  tasks:

  - name: install package
    yum:
        name: ntp
        state: present

Ran following command:

ansible-playbook test.yml -i localhost, --connection=local -vvvv

Receiving error message:

TASK [install package] ***************************************************************************************************************************************************
task path: /home/osuser/dod/test.yml:6
Using module file /usr/lib/python2.7/site-packages/ansible/modules/system/setup.py
<localhost> ESTABLISH LOCAL CONNECTION FOR USER: osuser
<localhost> EXEC /bin/sh -c '/usr/bin/python && sleep 0'
Running svr4pkg as the backend for the yum action plugin
Using module file /usr/lib/python2.7/site-packages/ansible/modules/packaging/os/svr4pkg.py
<localhost> EXEC /bin/sh -c '/usr/bin/python && sleep 0'
fatal: [localhost]: FAILED! => {
    "ansible_facts": {
        "pkg_mgr": "svr4pkg"
    },
    "changed": false,
    "invocation": {
        "module_args": {
            "category": false,
            "name": "ntp",
            "proxy": null,
            "response_file": null,
            "src": null,
            "state": "present",
            "zone": "all"
        }
    },
    "msg": "src is required when state=present",
    "name": "ntp"

Note the following message in debug:

Running svr4pkg as the backend for the yum action plugin

Ansible decided to use “srv4pkg” module (which requires src parameter) as backend of yum.

Workaround:
Set use_backend: yum parameter on yum module… if possible ! (I cannot modify the yaml file in my real usage).

Running Ansible 2.7.15 on CentOS 7.6.. with yum installed so there is absolutely no reason svr4pkg as a back-end (which is not supported/documented by yum module).

However, as it seems to be defined as an ansible_fact, I have done following test (result is filtered):

ansible -i localhost, all -m setup -k
SUCCESS => {
    "ansible_facts": {
        "ansible_distribution": "CentOS",
        "ansible_distribution_file_parsed": true,
        "ansible_distribution_file_path": "/etc/redhat-release",
        "ansible_distribution_file_variety": "RedHat",
        "ansible_distribution_major_version": "7",
        "ansible_distribution_release": "Core",
        "ansible_distribution_version": "7.6.1810",
        "ansible_os_family": "RedHat",
        "ansible_pkg_mgr": "svr4pkg",
        "ansible_python_version": "2.7.5",
        "module_setup": true
    },
    "changed": false
}

Any clue of the reason and how to enforce ansible_pkg_mgr ?

2

Answers


  1. Chosen as BEST ANSWER

    It seems that this distribution is shipped with yum and svr4pkg as we can see below:

    $ ll /usr/bin/yum
    -rwxr-xr-x. 1 root root 801 Nov  5  2018 /usr/bin/yum
    $ ll /usr/sbin/pkgadd
    -rwxr-xr-x. 1 root root 207342 Jul  2 16:12 /usr/sbin/pkgadd
    

    So the last available package manager resolved is kept and take precedence /usr/lib/python2.7/site-packages/ansible/module_utils/facts/system/pkg_mgr.py

    # A list of dicts.  If there is a platform with more than one
    # package manager, put the preferred one last.  If there is an
    # ansible module, use that as the value for the 'name' key.
    PKG_MGRS = [{'path': '/usr/bin/yum', 'name': 'yum'},
                {'path': '/usr/bin/dnf', 'name': 'dnf'},
                {'path': '/usr/bin/apt-get', 'name': 'apt'},
                {'path': '/usr/sbin/pkgadd', 'name': 'svr4pkg'},
                [...]
    
        def collect(self, module=None, collected_facts=None):
            facts_dict = {}
            collected_facts = collected_facts or {}
    
            pkg_mgr_name = 'unknown'
            for pkg in PKG_MGRS:
                if os.path.exists(pkg['path']):
                    pkg_mgr_name = pkg['name']
    
            # Handle distro family defaults when more than one package manager is
            # installed, the ansible_fact entry should be the default package
            # manager provided by the distro.
            if collected_facts['ansible_os_family'] == "RedHat":
                if pkg_mgr_name not in ('yum', 'dnf'):
                    pkg_mgr_name = self._check_rh_versions(pkg_mgr_name, collected_facts)
    
            [...]
    
            facts_dict['pkg_mgr'] = pkg_mgr_name
            return facts_dict
    

    So it seems to be an unmanaged case on ansible.

    However, I still have no idea on how to enforce the right value !


  2. Fixed by upgrading to Ansible 2.8+.

    See https://github.com/ansible/ansible/issues/49184 when multiple package managers are available on system.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search