使用加密变量和文件
当您运行使用加密变量或文件的任务或剧本(playbook)时,必须提供用于解密变量或文件的密码。您可以通过命令行完成此操作,或者在配置选项或环境变量中设置默认密码源。
传递单个密码
如果任务或剧本中所有的加密变量和文件都需要使用同一个密码,您可以使用 --ask-vault-pass 或 --vault-password-file 命令行选项。
提示输入密码
ansible-playbook --ask-vault-pass site.yml
从 /path/to/my/vault-password-file 文件中获取密码
ansible-playbook --vault-password-file /path/to/my/vault-password-file site.yml
从 vault 密码客户端脚本 my-vault-password-client.py 获取密码
ansible-playbook --vault-password-file my-vault-password-client.py
传递 vault ID
您还可以使用 --vault-id 选项来传递带有 vault 标签的单个密码。当在单个清单(inventory)中使用多个 vault 时,这种方法更加清晰。
提示输入 ‘dev’ vault ID 的密码
ansible-playbook --vault-id dev@prompt site.yml
从 dev-password 文件中获取 ‘dev’ vault ID 的密码
ansible-playbook --vault-id dev@dev-password site.yml
从 vault 密码客户端脚本 my-vault-password-client.py 获取 ‘dev’ vault ID 的密码
ansible-playbook --vault-id dev@my-vault-password-client.py
传递多个 vault 密码
如果您的任务或剧本需要多个使用不同 vault ID 加密的变量或文件,您必须使用 --vault-id 选项,通过传递多个 --vault-id 选项来指定 vault ID(如 ‘dev’、‘prod’、‘cloud’、‘db’)以及密码源(提示、文件、脚本)。例如,要使用从文件读取的 ‘dev’ 密码并提示输入 ‘prod’ 密码:
ansible-playbook --vault-id dev@dev-password --vault-id prod@prompt site.yml
默认情况下,vault ID 标签(dev, prod 等)仅作为提示。Ansible 会尝试使用每个密码来解密 vault 内容。标签与加密数据相同的密码将被首先尝试,之后,将按照在命令行中提供的顺序尝试每个 vault 密钥。
如果加密数据没有标签,或者标签与提供的任何标签都不匹配,则将按照指定的顺序尝试密码。在上述示例中,如果 Ansible 不知道使用了哪个 vault ID 进行加密,将首先尝试 ‘dev’ 密码,然后尝试 ‘prod’ 密码。
在不指定 vault ID 的情况下使用 --vault-id
--vault-id 选项也可以在不指定 vault-id 的情况下使用。这种行为等同于 --ask-vault-pass 或 --vault-password-file,因此很少使用。
例如,使用密码文件 dev-password
ansible-playbook --vault-id dev-password site.yml
提示输入密码
ansible-playbook --vault-id @prompt site.yml
从可执行脚本 my-vault-password-client.py 获取密码
ansible-playbook --vault-id my-vault-password-client.py
配置使用加密内容的默认设置
设置默认 vault ID
如果您使用某个 vault ID 的频率高于其他 ID,可以设置配置选项 DEFAULT_VAULT_IDENTITY_LIST 以指定默认的 vault ID 和密码源。当您没有指定 --vault-id 时,Ansible 将使用默认的 vault ID 和源。您可以为此选项设置多个值。设置多个值等同于传递多个 --vault-id 命令行选项。
设置默认密码源
如果您不想在命令行中提供密码文件,或者您使用某个 vault 密码文件的频率高于其他文件,可以设置 DEFAULT_VAULT_PASSWORD_FILE 配置选项或 ANSIBLE_VAULT_PASSWORD_FILE 环境变量来指定要使用的默认文件。例如,如果您设置 ANSIBLE_VAULT_PASSWORD_FILE=~/.vault_pass.txt,Ansible 将自动在该文件中搜索密码。如果您通过 Jenkins 等持续集成系统使用 Ansible,这将非常有用。
您引用的文件可以是包含密码(明文)的文件,也可以是返回密码的脚本(需设置可执行权限)。
加密文件何时变为可见?
通常情况下,您使用 Ansible Vault 加密的内容在执行后仍保持加密状态。但有一个例外:如果您将加密文件作为 src 参数传递给 copy、template、unarchive、script 或 assemble 模块,该文件在目标主机上将不会被加密(假设您在运行 play 时提供了正确的 vault 密码)。这种行为是刻意设计且非常有用的。您可以加密配置文件或模板以避免泄露配置细节,但当您将该配置复制到环境中的服务器时,您希望它是解密状态,以便本地用户和进程可以访问它。
Ansible Vault 加密文件的格式
Ansible Vault 创建 UTF-8 编码的 txt 文件。文件格式包括一个以换行符结尾的页眉。例如:
$ANSIBLE_VAULT;1.1;AES256
或
$ANSIBLE_VAULT;1.2;AES256;vault-id-label
页眉包含最多四个元素,由分号 (;) 分隔。
格式 ID (
$ANSIBLE_VAULT)。目前$ANSIBLE_VAULT是唯一有效的格式 ID。格式 ID 用于识别使用 Ansible Vault 加密的内容 (通过 vault.is_encrypted_file())。vault 格式版本 (
1.X)。目前所有支持的 Ansible 版本在提供带标签的 vault ID 时,默认将使用 ‘1.1’ 或 ‘1.2’。‘1.0’ 格式仅支持读取(并在写入时自动转换为 ‘1.1’ 格式)。格式版本目前仅用于精确字符串比较(版本号目前不进行“大小比较”)。用于加密数据的加密算法 (
AES256)。目前AES256是唯一支持的加密算法。Vault 格式 1.0 使用 ‘AES’,但当前代码始终使用 ‘AES256’。用于加密数据的 vault ID 标签(可选,
vault-id-label)。例如,如果您使用--vault-id dev@prompt加密文件,则 vault-id-label 为dev。
注意:页眉在未来可能会发生变化。格式 ID 和格式版本之后的字段取决于格式版本。未来的 vault 格式版本可能会增加更多的加密算法选项和/或额外的字段。
文件的其余内容是 ‘vaulttext’。vaulttext 是加密密文的文本装甲(text-armored)版本。每行宽 80 个字符,最后一行可能较短。
Ansible Vault 负载格式 1.1 - 1.2
vaulttext 是密文和 SHA256 摘要的拼接,结果经过 ‘hexlify’ 处理。
‘hexlify’ 指的是 Python 标准库 binascii 模块的 hexlify() 方法。
以下内容的 hexlify() 结果:
salt 的 hexlify() 字符串,后跟一个换行符 (
0x0a)加密 HMAC 的 hexlify() 字符串,后跟一个换行符。该 HMAC 是:
一个 RFC2104 风格的 HMAC
输入为:
AES256 加密的密文
一个 PBKDF2 密钥。此密钥、加密密钥和加密 IV 是由以下内容生成的:
以字节为单位的 salt
10000 次迭代
SHA256() 算法
前 32 字节是加密密钥
第二个 32 字节是 HMAC 密钥
剩余的 16 字节是加密 IV
密文的 hexlify() 字符串。密文是:
AES256 加密数据。数据使用以下内容加密:
AES-CTR 流加密
加密密钥
IV
由整数 IV 引导的 128 位计数器块
明文
原始明文
填充至 AES256 块大小。(填充使用的数据基于 RFC5652)