Ansible 2.8 角色 - 使用 vars/main 目录
Posted
技术标签:
【中文标题】Ansible 2.8 角色 - 使用 vars/main 目录【英文标题】:Ansible 2.8 Roles - using the vars/main directory 【发布时间】:2020-02-03 10:37:35 【问题描述】:我正在尝试将我的 Ansible 角色变量拆分为多个文件 - 根据 this answer,应该可以创建一个 vars/main
目录,并且应该自动加载该目录中的所有 .yml 文件。
然而,这似乎并没有发生在我的案例中。
我的目录结构:
vars
└── main
├── gce_settings.yml
├── vsphere_settings.yml
└── vsphere_zone.yml
但是,当我尝试使用在 vsphere_settings.yml 中定义的变量时,Ansible 抱怨该变量未定义:
"msg": "The task includes an option with an undefined variable. The error was: 'vsphere_user' is undefined
如果我将变量声明移动到vars/main.yml
,一切都会按预期进行。但是,当然,我更愿意将我的变量分成多个文件。
我在 Ansible 官方文档中找不到对这个“功能”的任何引用,我不知道如何解决它。谁能指出我正确的方向?
我的 ansible 版本:
ansible 2.8.5
在 Ubuntu 16.04 上
在你问之前:是的,我确实在尝试加载 vars/main/*.yml
时确保 main.yml
不存在...
【问题讨论】:
如果我下面的示例对您不起作用,请发布详细信息。让它mcve. 谢谢你,弗拉基米尔 - 我已经为问题添加了更多细节,并且我还在我的回答中发布了另一个示例(带有重现步骤)。 【参考方案1】:TL;DR 版本:这是 ansible 中的一个错误,由 vars/main
中存在空的 .yml 文件引起。已经有一个 PR 了。看
here 。
实际结果(如 cmets 中所述)实际上取决于文件的处理顺序(默认情况下,我的 Ansible 似乎按字母顺序处理它们 - 但这可能取决于版本或底层操作系统) :
如果先处理空文件,则会收到错误消息:ERROR! failed to combine variables, expected dicts but got a 'NoneType' and a 'AnsibleMapping'
如果空文件在其他文件之后处理,没有错误信息,但是此时已经设置的所有变量都被销毁了
更多细节:因为我不知道如何在 Ansible 中解决这个问题,所以我去代码并开始添加 print
语句以查看发生了什么。
在我的例子中,我在 vars/main
目录中有一些空的 .yml 文件(我计划稍后填充的文件。嗯......看起来当代码遇到这样一个空文件时,它会破坏到目前为止它已经建立的整个字典。
要么我遗漏了一些非常重要的东西,要么这是一个错误......重现步骤:
创建角色 创建vars/main
目录,并用一些 .yml 文件填充它
添加一个空的 .yml 文件(命名以便在其他文件之后对其进行处理)
尝试打印第一个文件中的变量
ansible# tree roles
roles
+-- test
+-- tasks
¦ +-- main.yml
+-- vars
+-- main
+-- correct_vars.yml
4 directories, 2 files
ansible# cat roles/test/vars/main/correct_vars.yml myname: bogd
ansible# ansible-playbook -i inventory.yml test.yml
...
ok: [localhost] =>
"myname": "bogd"
...
ansible# echo > roles/test/vars/main/emptyfile.yml
ansible# ansible-playbook -i inventory.yml test.yml
... ok: [localhost] =>
"myname": "VARIABLE IS NOT DEFINED!"
...
稍后编辑:是的,这是一个错误...见here。
【讨论】:
你应该在你的问题中编辑这个,而不是发布一个答案 @β.εηοιτ.βε - 因为这正式解决了我的问题(“这是一个错误,并且已经有一个 PR”),所以我决定用它来回答。希望这将帮助其他遇到同样问题的人。我将编辑答案并将最终结果(“这是一个错误”)移到顶部,以使事情更清楚。 这是无关的,不是错误。您在问题中所指的是 role vars 您所缺少的是 myrdd 在链接答案中所说的所有路径实际上都与角色文件夹相关。 链接的问题确实是指剧本 - 但它是相同的代码路径和相同的行为(当 new_data 为 None 时,combine_vars 会破坏字典)。而且,事实上,甚至 bcoca 也关闭了一个角色问题 (github.com/ansible/ansible/issues/54915),作为我链接的那个的欺骗。 @β.εηοιτ.βε - 抱歉,我错过了您评论的第二部分。当然,我上面测试的所有内容都与角色文件夹相关(答案应该清楚)。但是当您说“这不是错误”时,您的依据是什么?我错过了什么?因为我已经链接了两个似乎说是bug的github问题...【参考方案2】:下面的例子
$ cat play.yml
- hosts: localhost
roles:
- role1
$ cat roles/role1/tasks/main.yml
- debug:
var: var1
$ cat roles/role1/vars/main/var1.yml
var1: test_var1
给予
"var1": "test_var1"
【讨论】:
谢谢你——的确,事情应该是这样的。看来我偶然发现了一个由空的 .yml 文件引起的错误。详情见我的回答。以上是关于Ansible 2.8 角色 - 使用 vars/main 目录的主要内容,如果未能解决你的问题,请参考以下文章