community.general
community.general copied to clipboard
YAML stdout callback plugin doesn't output stdout from command module
SUMMARY
Issue migrated from https://github.com/ansible/ansible/issues/39122
ISSUE TYPE
- Bug Report
(Though maybe this is a feature idea?)
COMPONENT NAME
plugins/callback/yaml.py
ANSIBLE VERSION
ansible 2.5.1
config file = /etc/ansible/ansible.cfg
configured module search path = [u'/Users/jgeerling/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']
ansible python module location = /usr/local/lib/python2.7/site-packages/ansible
executable location = /usr/local/bin/ansible
python version = 2.7.13 (default, Jul 18 2017, 09:17:00) [GCC 4.2.1 Compatible Apple LLVM 8.1.0 (clang-802.0.42)]
CONFIGURATION
17:27:10 ~/Dropbox/VMs/infrastructure/solr/solr $ ansible-config dump --only-changed
ANSIBLE_NOCOWS(/etc/ansible/ansible.cfg) = True
ANSIBLE_PIPELINING(/etc/ansible/ansible.cfg) = True
ANSIBLE_SSH_CONTROL_PATH(/etc/ansible/ansible.cfg) = /tmp/ansible-ssh-%%h-%%p-%%r
DEFAULT_FORKS(/etc/ansible/ansible.cfg) = 20
DEFAULT_HOST_LIST(/etc/ansible/ansible.cfg) = [u'/etc/ansible/hosts']
DEFAULT_LOAD_CALLBACK_PLUGINS(/etc/ansible/ansible.cfg) = True
DEFAULT_ROLES_PATH(/etc/ansible/ansible.cfg) = [u'/Users/jgeerling/Dropbox/VMs/roles']
DEFAULT_STDOUT_CALLBACK(/etc/ansible/ansible.cfg) = yaml
RETRY_FILES_ENABLED(/etc/ansible/ansible.cfg) = False
OS / ENVIRONMENT
N/A
SUMMARY
When using the Ansible default configuration (default
stdout callback plugin), and running command
module commands either via playbook or ad-hoc commands, command output directed at stdout is printed to the console on the machine running Ansible, e.g.:
$ ansible myserver -a "echo 'testing'"
myserver | SUCCESS | rc=0 >>
testing
When using the yaml
callback plugin, stdout output is not printed to the console on the machine running Ansible, e.g.:
$ ansible myserver -a "echo 'testing'"
PLAY [Ansible Ad-Hoc] **************************************************************************************************
TASK [command] *********************************************************************************************************
changed: [myserver]
PLAY RECAP *************************************************************************************************************
myserver : ok=1 changed=1 unreachable=0 failed=0
STEPS TO REPRODUCE
See summary above.
EXPECTED RESULTS
I expected the yaml
callback plugin to behave similar to the default
callback plugin, printing stdout from command module commands to the command line while running playbooks or ad-hoc tasks.
ACTUAL RESULTS
stdout from command module commands is eaten up and never displayed on the CLI. Note that the debug
module does print msg
s and var
s to screen.
Files identified in the description:
If these files are inaccurate, please update the component name
section of the description or use the !component
bot command.
The default
callback does not print the command stdout. The output you see in the above ad-hoc command comes from the minimal
callback (https://github.com/ansible/ansible/blob/devel/lib/ansible/cli/adhoc.py#L143).
For anyone who's come here from the prior issue, I fixed this by forcing a reinstallation of the collections from galaxy.
ansible-galaxy install --force -r requirements.yml
Perhaps there was some corruption on my local, seeing as this started happening after I installed a new role and I think it caused a redownload of a collection.
This happens everywhere for us including on new installs, so it is not an issue of reinstallation for us.
Well, there's no reason why reinstalling should ever "fix" this, since this isn't a bug and nobody implemented this feature. If someone wants to improve / change this, take a look at @sivel's suggestions here: https://github.com/ansible/ansible/issues/39122#issuecomment-383642487
Also, changing the behavior of the YAML callback is not exactly trivial, since this is a breaking change. Having a detection for ad-hoc mode and a new configuration is probably the best solution. (No idea how to detect ad-hoc mode though...)
Can detect if in adhoc by using the playbook name
def v2_playbook_on_start(self, playbook): playbook_name = os.path.basename(playbook._file_name).split('.yml')[0]
playbook_name will be "__adhoc_playbook__" when adhoc is run.
What changes would be needed to the yaml plugin to change this?
Seems like this doesn't work for any ad-hoc command. I tried with other modules as well like setup and shell all are not providing the output in YAML format
Not sure if this is related or not, but I am experiencing same problem with setup
module:
~$ ansible --version
ansible 2.10.6
config file = None
configured module search path = ['~/.ansible/plugins/modules', '/usr/share/ansible/plugins/modules']
ansible python module location = ~/.local/lib/python3.8/site-packages/ansible
executable location = ~/.local/bin/ansible
python version = 3.8.5 (default, Jul 28 2020, 12:59:40) [GCC 9.3.0]
~$ ANSIBLE_LOAD_CALLBACK_PLUGINS=yes ANSIBLE_STDOUT_CALLBACK=community.general.yaml ansible -m setup localhost
[WARNING]: No inventory was parsed, only implicit localhost is available
PLAY [Ansible Ad-Hoc] **************************************************************************************************************************************************
TASK [setup] ***********************************************************************************************************************************************************
ok: [localhost]
PLAY RECAP *************************************************************************************************************************************************************
localhost : ok=1 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
~$ ANSIBLE_LOAD_CALLBACK_PLUGINS=yes ANSIBLE_STDOUT_CALLBACK=minimal ansible -m setup localhost
[WARNING]: No inventory was parsed, only implicit localhost is available
localhost | SUCCESS => {
"ansible_facts": {
....
That's pretty much expected, since almost no callback plugin (except minimal
) automatically dumps all task results if you don't provide -v
. Otherwise the normal playbook output would be severly cluttered :-)
You'll see what I mean if you use the minimal
callback for a regular playbook. It will be a lot less "minimal" than most other callbacks.
(...) almost no callback plugin (except minimal) automatically dumps all task results if you don't provide -v.
That's true for a regular playbook, but it's not true in case of ad-hoc
tasks. For example default
:
$ ANSIBLE_LOAD_CALLBACK_PLUGINS=yes ANSIBLE_STDOUT_CALLBACK=default ansible -m setup localhost | grep -A10 "ansible_date_time"
[WARNING]: No inventory was parsed, only implicit localhost is available
"ansible_date_time": {
"date": "2021-04-15",
"day": "15",
"epoch": "1618484703",
"hour": "12",
"iso8601": "2021-04-15T11:05:03Z",
"iso8601_basic": "20210415T120503978122",
"iso8601_basic_short": "20210415T120503",
"iso8601_micro": "2021-04-15T11:05:03.978122Z",
"minute": "05",
"month": "04",
$ ansible --version | head -n1
ansible 2.10.7
@weakcamel please note that ansible
seems to always replace the default
plugin by minimal
. See https://github.com/ansible/ansible/blob/devel/lib/ansible/cli/adhoc.py#L135-L143 (I'm not sure whether self.callback
can actually be something other than None
.)