如何通过SaltStack Reactor自动为Minion添加自定义Grains属性
问题描述
我希望Minion完成认证或启动时自动添加Grains属性,已配置Reactor规则:
reactor: - 'salt/auth': - /srv/salt/reactor/grains_add.sls - 'salt/minion/*/start': - /srv/salt/reactor/grains_add.sls
最初的grains_add.sls采用硬编码值设置Grains:
add_custom_grains: local.grains.setvals: - tgt: {{ data['id'] }} - arg: - {"code":"2","code_ename":"tt"}
现在想从Minion的Pillar数据中动态获取code变量来设置Grains,尝试用编排运行器重写了grains_add.sls:
invoke_orchestrate_file: runner.state.orchestrate: - args: - mods: orchestrate.add_granis - pillar: minion_id: {{ data['id'] }}
对应的orchestrate.add_granis文件内容如下:
{% set minion_id = salt.pillar.get('minion_id') %} get_grains: local.grains.item: - tgt: {{ minion_id }} - arg: - code set_grains: local.grains.setvals: - tgt: {{ minion_id }} - arg: - {"code":"2","code_ename":"tt"}
不确定后续操作,SaltStack不像Ansible那样直接传递任务结果到下一个任务,请问如何实现从Minion的Pillar获取code来设置Grains?或者有更优方案?
解决方案
方案一:改进编排文件,直接读取Minion的Pillar
Orchestrate运行在Master上,可以直接指定目标Minion来读取其Pillar数据,无需中间步骤。修改orchestrate.add_granis文件:
{% set minion_id = salt.pillar.get('minion_id') %} # 直接获取目标Minion的Pillar中code的值,支持指定默认值 {% set minion_code = salt.pillar.get('code', tgt=minion_id, default='default_code') %} set_custom_grains: local.grains.setvals: - tgt: {{ minion_id }} - arg: - {"code": "{{ minion_code }}", "code_ename": "tt"}
这里通过salt.pillar.get的tgt参数指定目标Minion,直接读取其Pillar中的code值,然后传入grains.setvals完成设置。
方案二:直接在Reactor中完成,无需编排层
可以跳过Orchestrate,直接在Reactor文件中调用runner读取Pillar并设置Grains,简化流程。修改grains_add.sls:
{% set minion_id = data['id'] %} # 调用pillar.get runner获取目标Minion的code值 {% set minion_code = salt.runner.pillar.get(tgt=minion_id, key='code', default='default_code') %} add_custom_grains: local.grains.setvals: - tgt: {{ minion_id }} - arg: - {"code": "{{ minion_code }}", "code_ename": "tt"}
这种方式无需额外的编排文件,直接在Reactor中完成全部逻辑,更简洁高效。
注意事项
- 确保Minion完成认证后,Master能正常同步到其Pillar数据(
salt/auth事件触发时,Minion刚完成认证,此时Pillar通常已就绪) - 为避免
code值不存在导致报错,建议添加default参数设置默认值 - 如果Pillar是动态生成的,需确保在事件触发时Pillar数据已生成完毕
内容的提问来源于stack exchange,提问作者Tony
相关产品推荐
相关产品推荐

