How to Get Started with Ansible Vault

Arpit ZelawatArpit Zelawat
4 min read

Goal: With this short blog, my aim is to give the reader all the information he needs to successfully implement Ansible Vault in his DevOps project.

Assumption: This blog assumes that you already have a working knowledge of ansible concepts, such as roles, variables, inventory, playbooks etc.

What is Ansible Vault?

According the official documentation:

Ansible Vault encrypts variables and files so you can protect sensitive content such as passwords or keys rather than leaving it visible as plaintext in playbooks or roles.

Let me expand on the 'encrypted variable and files' part. You can keep all your sensitive information inside a single encrypted file, or you can encrypt individual variables/strings, and use them right inside your playbook or vars files.

Choosing between encrypted variables or encrypted files

Encrypted Files

Pros:

  • Easy to manage/share a file

  • Easy to exclude encrypted files using .gitignore

  • Easy to change rekey / change password.

Cons:

  • Every time you need to update the contents of your encrypted file, you have to decrypt it, make your changes, and the encrypt it again.

  • Updating your encrypted files, creates unnecessary changes to your git repository.

Encrypted Variables

Pros:

  • Easy to update. You don't have to update a file containing other variables, but just your intended variable.

  • Doesn't create unnecessary changes to your git repository.

Cons:

  • Difficult to rekey / change password. If you have 20 encrypted variables, then you have to re-encrypt all 20 variables to change your password.

  • Impossible to exclude them out of your git repository. Encrypted variables are used within your playbook/vars files. Excluding these files means excluding your playbook/vars from the repository.

Personally, I prefer encrypted files as they are easy to manage and can be excluded from the repository, even though, they are a hassle to update.

The ansible-vault command line tool

Here's an oversimplified syntax of the ansible-vault command line tool:

ansible-vault <password source> <command>

There are three ways to provide password to the ansible-vault tool:

  • A password prompt using the --ask-vault-pass option.

  • A password file provided by the --vault-password-file path/to/password/file option.

  • Third party secrets manager

There are 7 commands for the tool, namely create, decrypt, edit, view, encrypt, encrypt_string, and rekey. Lets look at them.

Create an encrypted variable

Just execute one of the following commands to create an encrypted variable:

ansible-vault encrypt_string --ask-vault-pass 'mysupersecretpassword' --name 'password_vars'

Or 

ansible-vault encrypt_string --vault-password-file path/to/password/file 'mysupersecretpassword' --name 'password_vars'

You'll get an output similar to this:

password: !vault |
          $ANSIBLE_VAULT;1.1;AES256
          35633434356139363131363933356438316561666431313862383231393364633564343862636330
          6136366435313165626637326238326432316264383562620a356664393361373230326339323934
          32653462343235633738336332623437393434333137333634363437346234356635363734623030
          3761363238656131330a386536393665653034636337343733376437316536306666376638616432
          3761

You can use this encrypted string directly in your YAML files.

Create an encrypted file

This command will create new file named vault.yml :

ansible-vault create vault.yml

This command will encrypt an existing file named vault.yml :

ansible-vault encrypt vault.yml

View an encrypted file

ansible-vault --ask-vault-pass view vault.yml

Edit an encrypted file

ansible-vault --ask-vault-pass edit vault.yml

Set environment variable $EDITOR to nano if you don't want to use vi.

Decrypt a file

ansible-vault --ask-vault-pass decrypt vault.yml

Change password for a file

ansible-vault rekey vault.yml

Using ansible vault in an ansible playbook

Let's implement what we have learned so far using an example.

In this example we'll try to ping a server using an ansible playbook. But since the server's IP address and user name is sensitive information, we'll keep them encrypted. We'll keep the IP address in an encrypted file and the username as an encrypted variable.

Lets start by creating a password file:

echo 'my_vault_password' > .vault_pass

Make sure you don't upload the password in a git repository:

echo '.vault_pass' >> .gitignore

There are two ways to use this vault password file:

  1. Passing it as an argument --vault-password-file

     ansible-vault view --vault-password-file .vault_pass vault.yml
    
  2. Setting path to this file in environment variable

     export ANSIBLE_VAULT_PASSWORD_FILE=path/to/.vault_pass
    

To encrypt the username ubuntu:

ansible-vault encrypt_string --vault-password-file .vault_pass 'ubuntu' --name 'vault_ansible_user'

You'll get an output similar to the one below. Save it.

vault_ansible_user: !vault |
          $ANSIBLE_VAULT;1.1;AES256
          64653062636463306663313065646238616638623039316562643765363635653065623031643463
          3636386430323964626135366563313162623263656434650a386538343233333764383236626266
          62313635383962383461663861313663613932643666333234333666393134303964626463346539
          3237666531393736660a323031346264613339613037366232343263386530663365366139653333
          6331

Now, let's create an encrypted file vault.yml to store our server's IP address.

ansible-vault create --vault-password-file .vault_pass vault.yml

Paste the following content inside the editor:

---
vault_ansible_host: 1.1.1.1

Next, we'll define the inventory.yml file.

---
server:
  hosts:
    server01:
      ansible_host: "{{ vault_ansible_host }}"
      ansible_user: vault_ansible_user: !vault |
          $ANSIBLE_VAULT;1.1;AES256
          35633434356139363131363933356438316561666431313862383231393364633564343862636330
          6136366435313165626637326238326432316264383562620a356664393361373230326339323934
          32653462343235633738336332623437393434333137333634363437346234356635363734623030
          3761363238656131330a386536393665653034636337343733376437316536306666376638616432
          3761

Finally, we'll write our playbook.yml.

---
- name: Playbook
  hosts: server
  vars_files:
    - vault.yml
  tasks:
    - name: ping task
      ansible.builtin.ping:

Here's my directory structure:

.
├── .vault_pass
├── inventory.yml
├── playbook.yml
└── vault.yml

To run the playbook, execute the following command:

ansible-playbook --vault-password-file .vault_pass -i inventory/hosts.yml playbook.yml

This is how to use ansible vault. For more information, please refer the official documentation. Thank you!

0
Subscribe to my newsletter

Read articles from Arpit Zelawat directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Arpit Zelawat
Arpit Zelawat

Hi! My name is Arpit, and I'm a Software Engineer turned Product Manager. I use this platform to share my learnings in various different fields of interest.