My goal is to use ansible-vault
with multiple IDs (e.g. dev
and prod
) and retrieve the correct password (for dev
or prod
) from macOS keychain.
I have tried many configuration combinations, but the most promising seems to be what I describe here. Unfortunately, this is, like everything else I have tried, not working.
I have a script called vault-keyring-client.py
, fetched from Github which is executable and stored as ~/.vault/vault-keyring-client.py
.
Also, I set the environment variable ANSIBLE_VAULT_PASSWORD_FILE
to this full path.
The macOS keychain holds two "generic password" entries, one for dev
and one for prod
.
Now, I would expect the following command to work, meaning to output the encrypted string for whatever is input via STDIN
:
ansible-vault encrypt_string --vault-id dev
I have also tried the very similar command
ansible-vault encrypt_string --vault-id dev --encrypt-vault-id dev
to even more clearly indicate what I am trying to do; the result is the same:
I am getting an error claiming that
vault-keyring-client could not find key="default" for user="<my-username>" via backend="macOS Keyring"
According to my understanding ansible-vault
should call the mentioned script (because it is set in ANSIBLE_VAULT_PASSWORD_FILE
) and pass it the parameter --vault-id dev
(because this is what I give it on the CLI). With this, the script should return the password it finds in the keychain.
So my question is: why is ansible-vault
looking for a key (password) called default
in the keychain when I clearly indicate that I want dev
?
The more complete output/error looks as follows:
[WARNING]: Error getting vault password file (None): The vault password file <cwd>/mgm/dev was not found
[WARNING]: Error in vault password file loading (default): Vault password client script ~/.vault/vault-keyring-client.py did not find a secret for vault-id=default: b'vault-keyring-client could not find key="default" for user="<my-username>" via backend="macOS Keyring"\n'
ERROR! Vault password client script ~/.vault/vault-keyring-client.py did not find a secret for vault-id=default: b'vault-keyring-client could not find key="default" for user="<my-username>" via backend="macOS Keyring"\n'
ansible-vault
seems to be looking for a (password) file called dev
in the current working directory (and correctly detects that this does not exist) but then stops respecting the dev
ID and continues to look for something called default
...
I know that not all hope is lost, because the following command actually does work:
ansible-vault encrypt_string --vault-id dev@~/.vault/vault-keyring-client.py
It is just a mouthful to type and I do not see why this should make a/the difference...
BTW: I am using ansible version 2.14.5
.
Your problem is that you are using the env var ANSIBLE_VAULT_PASSWORD_FILE
which declares a single default password (used without vault-id to say this fast...) instead of ANSIBLE_VAULT_IDENTITY_LIST
which is the one dedicated for using several ids.
Just unset the prior and set the latest to the correct list of ids with their respective password files. Since you are using a script, it will receive the id and is able to reply with the correct password. So you basically use the same file for each id:
unset ANSIBLE_VAULT_PASSWORD_FILE
export ANSIBLE_VAULT_IDENTITY_LIST="dev@${HOME}/.vault/vault-keyring-client.py,\
staging@${HOME}/.vault/vault-keyring-client.py,\
prod@${HOME}/.vault/vault-keyring-client.py"