Set_fact 是 Ansible 中用于运行时动态定义变量的模块,支持静态赋值、命令结果提取、条件逻辑及主机作用域控制,变量默认仅对当前主机生效。

Set_fact 是 Ansible 中用于在 Playbook 运行时动态定义变量的模块,它让变量值可以在任务执行过程中根据条件、命令结果或逻辑计算生成,而不是写死在 YAML 里。它特别适合需要“先查再用”“按需赋值”的场景,比如获取远程主机信息、拼接路径、判断服务状态后设置开关等。
基础用法:直接赋值或引用其他变量
最简单的用法是给一个新变量赋固定值或已有变量的值:
- 使用
set_fact:后跟键值对,如my_var: "hello" - 支持 Jinja2 表达式,可引用
hostvars、groups、inventory_hostname等内置变量
示例:
- name: 设置静态字符串
set_fact:
app_name: "nginx-web"
<ul><li>name: 拼接主机名和环境
set_fact:
full_id: "{{ inventory_hostname }}-{{ env }}"
结合命令结果动态赋值(常用)
常与 command、shell 或 stat 等模块配合,把执行结果存为变量供后续任务使用:
- 先用
shell获取输出,用register捕获结果 - 再用
set_fact提取stdout或判断逻辑并赋值
示例:检查某目录是否存在,并设标志位
Zynq‑7000 / Zynq UltraScale+ 硬件调试技能。适用于 Xilinx Zynq(Cortex‑A9/A53 + FPGA)Linux 环境,调试 I2C、I2S、UART、GPIO 等外设。包括设备树配置、内核驱动、用户空间调试工具、交叉编译和常见问题排查,支持 PetaLinux 开发。
- name: 检查 /opt/app 目录
stat:
path: /opt/app
register: app_dir_stat
<ul><li><p>name: 设置 exists 标志
set_fact:
app_dir_exists: "{{ app_dir_stat.stat.exists | default(false) }}"</p></li><li><p>name: 仅当目录存在时启动服务
systemd:
name: myapp
state: started
when: app_dir_exists
条件赋值与多分支逻辑
利用 Jinja2 的三元运算符或 selectattr 等过滤器,实现类似 if-else 的动态赋值:
"{{ 'prod' if env == 'production' else 'staging' }}"- 也可用
set_fact配合when实现多任务分支赋值
示例:根据系统类型设置不同软件包名
- name: 设置包名(CentOS vs Ubuntu)
set_fact:
pkg_name: "{{ 'httpd' if ansible_facts['os_family'] == 'RedHat' else 'apache2' }}"
<ul><li>name: 安装 Web 服务
package:
name: "{{ pkg_name }}"
state: present
作用域注意:默认是 host\_vars,不可跨主机共享
set_fact 定义的变量默认只对当前主机生效(即存入 hostvars[inventory_hostname]),不会自动广播到其他主机:
- 若需在另一台主机上使用该变量,必须显式引用,如
{{ hostvars['web01'].app_version }} - 想全局可用?改用
vars(静态)、include_vars(文件加载)或自定义插件
示例:从 db 主机获取版本号,在 app 主机上使用
# 在 db 主机上设置
- name: 获取数据库版本
shell: psql --version | awk '{print $3}'
register: psql_ver_out
when: inventory_hostname == 'db01'
<ul><li>name: 设置全局可见变量(不推荐,仅作说明)
set_fact:
global_db_version: "{{ psql_ver_out.stdout }}"
when: inventory_hostname == 'db01'</li></ul><h1>在 app 主机上引用(需确保 db01 已执行过 set_fact)</h1><ul><li>name: 显示 db 版本
debug:
msg: "DB version is {{ hostvars['db01'].global_db_version }}"
when: inventory_hostname == 'app01'

















