14

I'm automatically securing SSL keys like this:

- name: Find ssl keys
  find: paths="/etc/ssl/" patterns="*.key" recurse=yes
  register: secure_ssl_keys_result

- name: Secure ssl keys
  file: path={{ item.path }} user=root group=root mode=600
  with_items: secure_ssl_keys_result.files

Now, for every item, there is a huge log message with the whole content of the item:

ok: [127.0.0.1] => (item={u'uid': 0, u'woth': False, u'mtime': 1454939377.264, u'inode': 400377, u'isgid': False, u'size': 3243, u'roth': False, u'isuid': False, u'isreg': True, u'gid': 0, u'ischr': False, u'wusr': True, u'xoth': False, u'rusr': True, u'nlink': 1, u'issock': False, u'rgrp': False, u'path': u'/etc/ssl/foo.key', u'xusr': False, u'atime': 1454939377.264, u'isdir': False, u'ctime': 1454939657.116, u'isblk': False, u'xgrp': False, u'dev': 65025, u'wgrp': False, u'isfifo': False, u'mode': u'0600', u'islnk': False})

This is incredibly unreadable, as I only want to know the path of the item that is being processed (and maybe changed). With a big number of keys, this get's out of hand really quick.

How can I change this play in a way that only the item.path is being printed out for each item?

I have already tried no_log: True, but this completely omits the output of course.

  • Maybe you could write a [Jinja Filter](docs.ansible.com/ansible/playbooks_filters.html) set no_log: true and return the value of item.path with debug module – Henrik Pingel Feb 16 '16 at 10:08
23

Ansible 2.2 has loop_control.label for this.

- name: Secure ssl keys
  file: path={{ item.path }} user=root group=root mode=600
  with_items: secure_ssl_keys_result.files
  loop_control:
    label: "{{ item.path }}"
5

Method 1

Use

secure_ssl_keys_result.files|map(attribute='path')|list

It will return a list of paths:

['/etc/ssl../', '/etc/ssl/.../']

Your whole task would become:

- name: Secure ssl keys
  file: path={{ item }} user=root group=root mode=600
  with_items: secure_ssl_keys_result.files|map(attribute='path')|list

Beware that you can only select a single attribute, it is not possible to use attribute=['path', 'mode'] or similar.

Method 2

I thought of using extract to be able to fetch multiple keys (because it is sometimes necessary to have a second key for a when condition), but didn't manage to do it, as I would need to map the list of dicts, then map the list of keys over the specific dict, which doesn't seem possible, as map only accepts a function name but not a function definition/chained functions. I would be grateful for an suggestion here!

A great idea from the comments (Thanks, Uditha Desilva!):

- name: Secure ssl keys file: path={{ item.0 }} mode=600 owner={{ item.1 }}
  with_together: 
  - secure_ssl_keys_result.files|map(attribute='path')|list 
  - secure_ssl_keys_result.files|map(attribute='uid')|list 

Method 3

Alternatively, a custom filter like this could be used (that's what I did before I found out about map):

from ansible import errors
import re

def cleandict(items, keepkeys):
    try:
        newitems = []
        if not isinstance(items, list):
          items = [items]
        if not isinstance(keepkeys, list):
          keepkeys = [keepkeys]
        for dictionary in items:
          newdictionary = {}
          for keepkey in keepkeys:
            newdictionary[keepkey] = dictionary.get(keepkey)
          newitems.append(newdictionary)  
        return newitems
    except Exception, e:
        raise errors.AnsibleFilterError('split plugin error: %s' % str(e) )
        #raise errors.AnsibleFilterError('split plugin error: %s, string=%s' % str(e),str(items) )

class FilterModule(object):
    ''' A filter to split a string into a list. '''
    def filters(self):
        return {
            'cleandict' : cleandict
        }

ansible.cfg:

filter_plugins = ~/.ansible/plugins/filter_plugins/:/usr/share/ansible_plugins/filter_plugins
  • 1
    Regarding your method 2, it would seem viable to use "with_together", even if it isn't super-efficient (unfortunately comments can't use code tags so this will look odd): - name: Secure ssl keys file: path={{ item[0] }} mode=600 owner={{ item[1] }} with_together: - secure_ssl_keys_result.files|map(attribute='path')|list - secure_ssl_keys_result.files|map(attribute='uid')|list – Uditha Desilva Mar 2 '16 at 11:04
1

You can't. It's either all or nothing (via no_log: True)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.