I am newbie in ansible, so excuse me. I didn't find or may be understand related information from ansible docs.
I need to put some ssh keys by blocks in .ssh/autorized_keys of all users in the system (Debian 9) without using the shell in tasks. Ansible 2.7.5
My plan was:
get all users from a passwd file;
select only non system users, for example, it can be users with /bin/bash shell in passwd, or not /usr/sbin/nologin /bin/false;
extract user name and home dir to variables;
put it as variables to a blockinfile module.
I am trying to get all users from the passwd file with a getent module below.
- getent:
database: passwd
key:
register: allusers
# - debug:
# var: allusers
# - debug:
# msg: "{{ ansible_facts.getent_passwd }}"
# - name: Select actual users
# set_fact:
# passwd_user: "{{ item.key }}"
# passwd_hdir: "{{ item.value.4 }}"
# loop: "{{ allusers.ansible_facts.getent_passwd | dict2items }}"
- name: "Show file path only"
debug:
msg:
- "Located user: {{ item.key }}"
- "Home Dir: {{ item.value.4 }}"
loop: "{{ allusers.ansible_facts.getent_passwd | dict2items }}"
Here I got a dict with key: users and value: home dir. But I don't know how to filter it by shell type and how to assign all users and there dirs to var.
- name: "Add ssh keys"
blockinfile:
path: "{{ passwd_hdir }}/.ssh/authorized_keys"
create: yes
owner: "{{ passwd_user }}"
group: "{{ passwd_user }}"
block: "{{ item }}"
with_file:
- "defaults/main.yml" # file in role's dir with ssh-keys
Ass a result I add keys only for one user. How to make a loop from that task with a list of users as loop variable.
P.S.
Second part of my problem it's how to work with variables results: list, string, dict. I think I understand how to convert using filters, but where I can read more about detecting var type, and exract data from it. It's not clear for me: https://docs.ansible.com/ansible/latest/user_guide/playbooks_variables.html
Thank you.
Q: "How to loop a list of users?"
A: Read passwd. The variable getent_passwd will be created automatically by the module getent
- getent:
database: passwd
Create the list of users by selecting records that contain shell /bin/bash
users_sh: "{{ getent_passwd | dict2items |
selectattr('value', 'contains', '/bin/bash') |
map(attribute='key') }}"
Loop the list and use authorized_key to configure authorized_keys
- authorized_key:
user: "{{ item }}"
key: "{{ lookup('file', 'defaults/main.yml') }}"
loop: "{{ users_sh }}"
Example of a complete playbook for testing
- hosts: all
vars:
users_sh: "{{ getent_passwd | dict2items |
selectattr('value', 'contains', '/bin/bash') |
map(attribute='key') }}"
users_nl: "{{ getent_passwd | dict2items |
selectattr('value', 'contains', '/usr/sbin/nologin') |
map(attribute='key') }}"
tasks:
- getent:
database: passwd
- debug:
var: users_sh | to_yaml
- debug:
var: users_nl | to_yaml
- authorized_key:
user: "{{ item }}"
key: "{{ lookup('file', 'defaults/main.yml') }}"
loop: "{{ users_sh }}"
when: not_dry_run | d(false) | bool