Ansible中使用if条件为gather_facts赋值True/False不生效问题
问题原因
Ansible的play级别gather_facts是布尔类型参数,会在play加载阶段完成类型转换。你通过Jinja模板输出的"true"/"false"本质是字符串类型,按照YAML解析规则,所有非空字符串都会被判定为布尔值True,所以无论模板输出什么内容,gather_facts都会被识别为开启状态。
而connection参数本身接受字符串类型的取值,所以模板返回的字符串可以直接生效,不存在类型转换异常的问题。
解决方法
方法1:添加bool过滤器转换模板输出类型
只需要在原Jinja表达式末尾添加|bool过滤器,将输出的字符串转换为对应的布尔值即可,修改后的play配置如下:
--- - hosts: "{{ run_on_node|default('mysql_cluster_sql[0]')}}" connection: "{% if migrated is defined and migrated == 'yes' %}local{% else %}ssh{% endif %}" gather_facts: "{% if migrated is defined and migrated == 'yes' %}false{% else %}true{% endif %}" | bool tasks: - debug: var=ansible_all_ipv4_addresses - debug: var=ansible_default_ipv4.address
方法2:用setup模块手动控制事实收集(兼容性更好)
如果需要兼容旧版本Ansible,或者有更复杂的事实收集判断逻辑,可以直接关闭play级别的事实收集,在任务列表开头通过setup模块按需执行收集操作:
--- - hosts: "{{ run_on_node|default('mysql_cluster_sql[0]')}}" connection: "{% if migrated is defined and migrated == 'yes' %}local{% else %}ssh{% endif %}" gather_facts: false tasks: - name: 收集主机事实 ansible.builtin.setup: when: not (migrated is defined and migrated == 'yes') - debug: var=ansible_all_ipv4_addresses - debug: var=ansible_default_ipv4.address
内容的提问来源于stack exchange,提问作者Shubham Saroj
相关产品推荐
相关产品推荐

