I have been developing an Ansible playbook for a couple of weeks, therefore, my experience with such technology is relatively short. Part of my strategy includes using a custom ansible_ssh_user
for provisioning hosts throughout the inventory, however, such user will need its own SSH key pair, which would involve some sort of a plan for holding/storing its correspondent private key. On a production environment, this playbook would be cloned/pulled and run inside a certain playbook node whose role is to provision the rest of the infrastructure.
At first, I was thinking to just put that private key inside the playbook git repository, but I am having second thoughts about it nonetheless, mostly because of somewhat obvious security reasons and common sense around it, hence the reason I need to consult you about this matter.
With this set on the table, here are the follow-up questions:
ansible uses a user to connect to the target machine. So if your user is ubuntu ( -u ubuntu in ansible flags) the key will be ~ubuntu/. ssh/authorized_keys on target machine).
By default, Ansible assumes you are using SSH keys to connect to remote machines. SSH keys are encouraged, but you can use password authentication if needed with the --ask-pass option.
It's a bad idea to store any kind of plaintext secret in revision control, SSH private keys included. Instead, use ansible-vault to store the private key.
ansible-vault
can operate on any file type. Just encrypt the file with
ansible-vault encrypt /path/to/local/private_key
then install the key:
- name: Install a private SSH key vars: source_key: /path/to/local/private_key dest_key: /path/to/remote/private_key tasks: - name: Ensure .ssh directory exists. file: dest: "{{ dest_key | dirname }}" mode: 0700 owner: user state: directory - name: Install ssh key copy: src: "{{ source_key }}" dest: "{{ dest_key }}" mode: 0600 owner: user
Earlier versions of ansible-vault would only operate on variables defined in var files, so you had to do something like this:
ssh_key: | -----BEGIN RSA PRIVATE KEY----- ... -----END RSA PRIVATE KEY----- key_file: /home/user/.ssh/id_rsa
Encrypt with ansible-vault:
ansible-vault encrypt /path/to/var_file
And install the key:
- name: Ensure .ssh directory exists. file: dest: "{{ key_file | dirname }}" mode: 0700 owner: user state: directory - name: Install ssh key copy: content: "{{ ssh_key }}" dest: "{{ key_file }}" mode: 0600 owner: user
Thanks to all those below who improved the answer with their comments.
Since you are provisioning from scratch, you should generate the private/public key pair on the playbook node and then distribute the public key via the authorized_keys
module. This would eliminate the need to store a secret anywhere except on the host where it is needed. Here is a playbook to achieve this, which would be executed on the playbook node:
--- - hosts: 127.0.0.1 sudo: yes gather_facts: no tasks: - name: create ansible_ssh_user locally user: name=ansible_ssh_user generate_ssh_key=yes ssh_key_bits=2048 ssh_key_file=.ssh/id_rsa - name: copy the generated public key to an accessible location for the next play shell: cp ~ansible_ssh_user/.ssh/id_rsa.pub /tmp/ansible_ssh_user.pub - hosts: all sudo: yes gather_facts: no tasks: - name: create ansible_ssh_user user: name=ansible_ssh_user groups=group1,group2 - name: Add RSA public key to the remote host authorized_key: user=ansible_ssh_user key="{{ lookup('file', '/tmp/ansible_ssh_user.pub') }}" - hosts: 127.0.0.1 sudo: yes gather_facts: no tasks: - name: remove public key from /tmp shell: rm /tmp/ansible_ssh_user.pub ...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With