无法将 Ansible 事实设置为整数

TSG*_*TSG 8 ansible ansible-facts

我正在尝试提取主要发行版版本(以ansible_facts字符串形式保存)并将其存储为整数以供以后使用<>与整数进行比较。当我这样做时:

- set_fact:
    distromajor: "{{ ansible_facts['distribution_major_version'] | int }}"
Run Code Online (Sandbox Code Playgroud)

我发现distromajorHold"7"而不是7.
所以后来比较失败。事实上,我让它发挥作用的唯一方法就是像这样进行比较:

(distromajor|int >=6) and (distromajor|int <= 8)
Run Code Online (Sandbox Code Playgroud)

这是预期的行为吗?
为什么我不能将发行版主要版本保存为 int?

最接近的SO问题没有解释为什么后来的整数比较失败而没有distromajor在比较时将变量重新转换为整数。

Vla*_*tka 9

问:这是预期的行为吗?

答:是的。这是 Ansible 中的预期行为。


问:为什么我不能将发行版主要版本保存为 int?

答:Ansible 认为您不能(待办事项:需要参考源代码)。在YAML中,存在三个基本原语:

  • 映射(哈希/字典)
  • 序列(数组/列表)
  • 标量(字符串/数字)

如您所见,标量既是字符串又是数字。但是,出于某种我不知道的原因,Ansible 决定任何"{{ scalar }}"表达式只能返回stringboolean。例如,

    - set_fact:
        distromajor: "{{ ansible_facts['distribution_major_version']|int }}"
    - debug:
        var: distromajor
    - debug:
        msg: "{{ distromajor|type_debug }}"
Run Code Online (Sandbox Code Playgroud)

尽管显式转换为整数,但仍给出一个字符串,正如您已经发现的那样

  distromajor: '20'
  msg: AnsibleUnsafeText
Run Code Online (Sandbox Code Playgroud)

更新。

如果你想将变量保留为整数,请将其放入字典中。例如,

  my_dict_yaml: |
    distromajor: {{ ansible_distribution_major_version }}
  my_dict: "{{ my_dict_yaml|from_yaml }}"
Run Code Online (Sandbox Code Playgroud)

给出

  my_dict:
    distromajor: 20
  my_dict.distromajor|type_debug: int
Run Code Online (Sandbox Code Playgroud)

用于测试的完整剧本示例

- hosts: localhost

  vars:

    my_dict_yaml: |
      distromajor: {{ ansible_distribution_major_version }}
    my_dict: "{{ my_dict_yaml|from_yaml }}"

  tasks:

    - setup:
        gather_subset: distribution_major_version
    - debug:
        var: ansible_distribution_major_version
    - debug:
        var: ansible_distribution_major_version|type_debug

    - debug:
        var: my_dict
    - debug:
        var: my_dict.distromajor|type_debug
Run Code Online (Sandbox Code Playgroud)