Ansible 变量
定义变量规则
- 变量名由字母、数字、下划线组成,且必须以字母开头。
- 不能使用 Ansible 内置关键字作为变量名。
变量作用域与优先级
Ansible 变量可分为三个范围,优先级从高到低依次为:
- Global 范围(高):从命令行或 Ansible 配置中设置的变量。
- Play 范围(中):在 Play 及相关结构中设置的变量。
- Host 范围(低):在 Inventory、Facts 或 Register 中设置的变量,包括主机组和个别主机上定义的变量。
若变量重复定义,优先级高的将覆盖优先级低的。
定义变量的多种方式
Ansible 支持多种定义变量的方式,包括:
- 将模块执行结果注册为变量(
register
) - 直接定义字典类型的变量
- 在 Role 文件中定义变量
- 通过命令行传递变量
- 使用
with_items
迭代将多个任务结果赋值给一个变量 - 在 Inventory 中定义主机或主机组变量
- 使用内置变量
- 使用事实变量(Facts)
变量定义示例
使用 vars
定义变量
- name: test
hosts: node1
vars:
- aa: 11
- bb: 22
- cc:
a1: c31
a2: c32
tasks:
- name: create debug1
debug:
msg: "{{ aa }}"
- name: create debug2
debug:
msg: "{{ bb }}"
- name: create debug3
debug:
msg: "{{ cc.a1 }}"
- name: create debug4
debug:
msg: "{{ cc.a2 }}"
使用 vars_files
引入外部变量文件
- name: test1234
hosts: node1
vars_files: /home/student/ansible/var.yml
tasks:
- name: debug1
debug:
msg: "{{ aa }}"
- name: debug2
debug:
msg: "{{ bb }}"
- name: debug3
debug:
msg: "{{ cc.a1 }}"
- name: debug4
debug:
msg: "{{ cc.a2 }}"
使用 register
注册变量
使⽤register选项,可以将当前task的输出结果赋值给⼀个变量。
- name: test a playbook
hosts: node1
tasks:
- name: shell
shell: "cat /tmp/zz"
register: zz
- name: create debug
debug:
var: zz
输出示例:
"zz": {
"changed": true,
"cmd": "cat /tmp/zz",
"delta": "0:00:00.005195",
"end": "2020-07-29 10:06:17.704232",
"failed": false,
"rc": 0,
"start": "2020-07-29 10:06:17.699037",
"stderr": "",
"stderr_lines": [],
"stdout": "zz",
"stdout_lines": ["zz"]
}
也可以提取特定字段:
- name: create debug
debug:
msg: "{{ zz.rc }}"
使用 set_fact
定义变量
set_fact和register的功能很相似,也是将值赋值给变量。它更像shell中变量的赋值⽅式,可以将某个变量的值赋值给另⼀个变量,也可以将字符串赋值给变量
通过’ansible node1 -m setup’ 可以查询node1主机所有的事实变量
- name: test a playbook
hosts: node1
tasks:
- name: hostname
debug:
msg: "{{ ansible_fqdn }}"
#输出示例
"msg": "node1.example.com"
使用事实变量(Facts)
- name: abc
hosts: node1
tasks:
- name: test
debug:
msg: "The IPv4 address of {{ ansible_nodename }} is {{ ansible_ens160.ipv4.address }}"
#输出示例
"msg": "the ipv4 address of node1.example.com is 172.16.30.10"
通过命令行传递变量
- name: test4
hosts: node1
tasks:
- name: create debug
debug:
msg: "My name is {{ name1 }}"
- name: create debug2
debug:
msg: "My name is {{ name2 }}"
执行命令:
ansible-playbook d.yml -e 'name1=tom name2=marry'
#输出示例
"msg": "my name is tom"
"msg": "my name is marry"
在 Inventory 中定义变量
编辑 /host/student/ansible/inventory
:
node1
node2
[net]
node1
node2
[net:vars]
vars1='hello'
vars2='hi'
Playbook 示例:
- name: test5
hosts: node1
tasks:
- name: create debug1
debug:
msg: "say {{ vars1 }}"
- name: create debug2
debug:
msg: "say {{ vars2 }}"
#输出示例
"msg": "say hello"
"msg": "say hi"
使用 group_vars
和 host_vars
在 /home/student/ansible/
下创建 host_vars
目录,并为主机定义变量:
# /home/student/ansible/host_vars/node1
vars1: groupvars1
vars2: groupvars2
或使用 YAML 文件:
# /host/student/ansible/host_vars/node1.yml
vars1: abc
vars2: bcd
Playbook
- name: test
hosts: node1
tasks:
- name: create debug
debug:
msg: my name is {{vars1}}
- name: create debug2
debug:
msg: my name is {{vars2}}
#输出示例
"msg": "my name is groupvars1"
"msg": "my name is groupvars2"
删除/etc/ansible/host_vars/node1 保留/etc/ansible/host_vars/node1.yml,再次执行playbook
#输出示例
"msg": "my name is abc"
"msg": "my name is bcd"
若同时存在
node1和
node1.yml,则
node1 的优先级更高。
内置变量示例
ansible_version(ansible版本)
- name: test
hosts: node1
tasks:
- name: create debug
debug:
msg: "{{ ansible_version }}"
输出:
{
"full": "2.9.18",
"major": 2,
"minor": 9,
"revision": 18,
"string": "2.9.18"
}
inventory_hostname(当前主机的主机名称)
- name: test
hosts: node1
tasks:
- name: create debug
debug:
msg: "{{ inventory_hostname }}"
输出:
"msg": "node1"
play_hosts(当前play所操作的所有主机的主机名列表)
- name: test
hosts: net
tasks:
- name: create debug
debug:
msg: "{{ play_hosts }}"
输出:
"msg": [
"node1",
"node2"
]
"msg": [
"node1",
"node2"
]
groups(获取到清单中”所有分组”的”分组信息”)
- name: test
hosts: node1
tasks:
- name: create debug
debug:
msg: "{{ groups }}"
输出:
"msg": {
"all": [
"node1",
"node2"
],
"net": [
"node1",
"node2"
],
"ungrouped": []
}
group_names(获取到当前主机所在分组的组名)
- name: test
hosts: node1
tasks:
- name: create debug
debug:
msg: "{{ group_names }}"
输出:
"msg": [
"net"
]
inventory_diransible主机中清单文件的存放路径
- name: test
hosts: node1
tasks:
- name: create debug
debug:
msg: "{{ inventory_dir }}"
输出:
"msg": "/home/student/ansible"
使用 with_items
迭代赋值
- name: test
hosts: node1
tasks:
- name: abc
shell:
cmd: echo "{{ item }}"
with_items:
- haha
- heihei
- hehe
register: hi_var
- name: debug1
debug:
var: hi_var.results[0].stdout
- name: debug2
debug:
var: hi_var.results[1].stdout
- name: debug3
debug:
var: hi_var.results[2].stdout
输出:
"hi_var.results[0].stdout": "haha"
"hi_var.results[1].stdout": "heihei"
"hi_var.results[2].stdout": "hehe"
- name: abc
shell:
cmd: echo "{{item}}"
with_items:
- haha
- heihei
- hehe
register: hi_var
- name: debug1
debug:
msg: "{{hi_var}}"
输出:
"msg": {
"changed": true,
"msg": "All items completed",
"results": [
{
"ansible_loop_var": "item",
"changed": true,
"cmd": "echo \"haha\"",
"delta": "0:00:00.003206",
"end": "2021-04-09 00:36:52.433624",
"failed": false,
"invocation": {
"module_args": {
"_raw_params": "echo \"haha\"",
"_uses_shell": true,
"argv": null,
"chdir": null,
"creates": null,
"executable": null,
"removes": null,
"stdin": null,
"stdin_add_newline": true,
"strip_empty_ends": true,
"warn": true
}
},
"item": "haha",
"rc": 0,
"start": "2021-04-09 00:36:52.430418",
"stderr": "",
"stderr_lines": [],
"stdout": "haha",
"stdout_lines": [
"haha"
]
},
{
"ansible_loop_var": "item",
"changed": true,
"cmd": "echo \"heihei\"",
"delta": "0:00:00.002276",
"end": "2021-04-09 00:36:52.676159",
"failed": false,
"invocation": {
"module_args": {
"_raw_params": "echo \"heihei\"",
"_uses_shell": true,
"argv": null,
"chdir": null,
"creates": null,
"executable": null,
"removes": null,
"stdin": null,
"stdin_add_newline": true,
"strip_empty_ends": true,
"warn": true
}
},
"item": "heihei",
"rc": 0,
"start": "2021-04-09 00:36:52.673883",
"stderr": "",
"stderr_lines": [],
"stdout": "heihei",
"stdout_lines": [
"heihei"
]
},
{
"ansible_loop_var": "item",
"changed": true,
"cmd": "echo \"hehe\"",
"delta": "0:00:00.002589",
"end": "2021-04-09 00:36:52.920442",
"failed": false,
"invocation": {
"module_args": {
"_raw_params": "echo \"hehe\"",
"_uses_shell": true,
"argv": null,
"chdir": null,
"creates": null,
"executable": null,
"removes": null,
"stdin": null,
"stdin_add_newline": true,
"strip_empty_ends": true,
"warn": true
}
},
"item": "hehe",
"rc": 0,
"start": "2021-04-09 00:36:52.917853",
"stderr": "",
"stderr_lines": [],
"stdout": "hehe",
"stdout_lines": [
"hehe"
]
}
]
}
Ansible Vault 管理机密
Ansible Vault 用于加密敏感数据(如密码、API 密钥等),避免以明文形式存储。
使用ansible vault,可通过一个名为ansible-vault的命令行工具创建、编辑、加密、解密和查看文件。Ansible vault可以加密任何由ansible使用的结构化数据文件。这可能包括清单变量、playbook中含有的变量文件、在执行playbook时作为参数传递的变量文件,或者ansible角色中定义的变量。
创建加密文件
ansible-vault create test.yml
输入密码:redhat
确认密码:redhat
要创建新的加密文件,使用ansible-vault create filename命令,默认使用vi编辑
查看加密文件
ansible-vault view test.yml
Vault password: #输入设置的密码redhat
---
- name: test1
hosts: node1
tasks:
- name: create user2
user:
name: user2
state: present
编辑加密文件
ansible-vault edit test.yml
加密现有文件
ansible-vault encrypt a.yml
输入密码:redhat
确认密码:redhat
解密文件
# 直接解密,永久解密
ansible-vault decrypt test.yml
# 解密并另存为其他文件(原文件仍加密)
ansible-vault decrypt a.yml --output=a-secret.yml
使用密码文件加密/解密
# 加密
ansible-vault encrypt e.yml --vault-id secret.txt
# 执行 Playbook
ansible-playbook e.yml --vault-id secret.txt
修改加密文件的密码
ansible-vault rekey filename #命令可以修改
ansible-vault rekey a.yml
输入旧密码
输入新密码
确认新密码
执行加密的 Playbook
# 使用提示输入密码
ansible-playbook --vault-id @prompt a.yml
# 使用交互式输入密码
ansible-playbook --ask-vault-pass a.yml
# 检查模式(Dry-run)
ansible-playbook --ask-vault-pass a.yml -C
Ansible 变量参考手册
一、 事实变量 (Facts)
这些变量通过 ansible.builtin.setup
模块收集自受控节点(Managed Node)。使用 ansible node1 -m setup
命令可以获取。
变量分类 | 变量名 | 描述 | 示例/备注 |
---|---|---|---|
网络信息 | ansible_default_ipv4.address |
主IPv4地址 | 获取默认路由所使用的IP地址 |
ansible_<interface>.ipv4.address |
指定网卡的IPv4地址 | 将 <interface> 替换为实际网卡名,如 ansible_eth0.ipv4.address |
|
系统信息 | ansible_fqdn |
完全合格域名 (FQDN) | node1.example.com |
ansible_hostname |
主机名称 (短名称) | node1 |
|
ansible_memtotal_mb |
总内存大小 (单位: MB) | 1024 (表示 1GB 内存) |
|
ansible_bios_version |
BIOS 版本号 | xx.xx.xx |
|
存储信息 | ansible_devices.vda.size |
vda 硬盘的总容量 | 通常表示第一块虚拟磁盘 |
ansible_devices.vdb.size |
vdb 硬盘的总容量 | 通常表示第二块虚拟磁盘 | |
ansible_lvm.vgs |
逻辑卷管理器 (LVM) 中的卷组信息 | 返回一个字典结构,包含所有VG的详细信息 |
二、 内置变量 (Magic Variables)
这些变量由Ansible自动提供,无需收集,主要用于获取清单(Inventory)信息。
变量名 | 描述 | 示例/用途 |
---|---|---|
groups |
一个包含所有清单分组及其主机列表的字典。 | groups['web'] 返回 [web1, web2] |
groups.all |
一个列表,包含所有清单中的主机。 | groups.all 返回 [node1, node2, web1, db1] |
group_names |
当前正在执行任务的主机所属的组名列表。 | 在Playbook中用于条件判断: when: "'db' in group_names" |
inventory_hostname |
当前正在执行任务的主机在Ansible清单中定义的名字。 | 可能不同于 ansible_hostname (系统实际主机名),特别是当你使用了别名时。 |