Ansible set_facts by localhost json 文件并复制到远程主机
Ansible set_facts by localhost json file and copy to remote hosts
我正在尝试将 json 文件从我的本地主机复制到远程主机,并使用 json“版本”键值作为目标文件名中的参数。
JSON:
{"name": "test", "version": 3}
YML:
---
- name: Get json file version
hosts: locahost
become: true
tasks:
- name: Register licenses file
command: "cat conf/licenses.json"
register: result
- name: Save the json data
set_fact:
jsondata: "{{ result.stdout | from_json }}"
- name: Save licenses file version
set_fact:
file_version: "{{ jsondata | json_query(jmesquery) }}"
vars:
jmesquery: 'version'
- name: Deploy Licenses File
hosts: hosts
become: true
tasks:
- name: Copy licenses file
copy:
src: "conf/licenses.json"
dest: "/tmp/licenses_{{ file_version }}.json"
当我 运行 上面的剧本时,部署许可证文件密钥找不到 file_version 事实,即使我可以看到它已成功保存在 Get json文件版本密钥。
设置file_version事实:
ok: [localhost] => {
"ansible_facts": {
"file_version": "1"
},
"changed": false
}
错误:
The task includes an option with an undefined variable. The error was: 'file_version' is undefined
我认为事实保存在给定的主机粒度上,而不是每个剧本启动的全局事实。
我目前的解决方法是将密钥组合到一个任务中,然后它就可以正常工作,但我更喜欢一次获取版本,而不是为每个远程主机重复一次。
要访问另一台主机的事实,您始终可以使用 hostvars
special variable。
因此,在您的情况下:
dest: "/tmp/licenses_{{ hostvars.localhost.file_version }}.json"
现在,您实际上不需要两场比赛那么复杂,并且完全可以做到:
- name: Deploy Licenses File
hosts: hosts
become: true
tasks:
- name: Copy licenses file
copy:
src: "{{ _licence_file }}"
dest: "/tmp/licenses_{{ file_version }}.json"
vars:
_licence_file: conf/licenses.json
file_version: >-
{{ (lookup('file', _licence_file) | from_json).version }}
第一个游戏仅在 localhost 运行。因此,在第一个游戏中声明的变量仅对 localhost 可用。这是第二个playhost无法使用变量的原因
The error was: 'file_version' is undefined
运行一次任务在所有主机的第一个块中播放。这样变量将在第二个游戏中对所有主机可用。例如,下面的简化剧本可以完成这项工作
- hosts: all
tasks:
- block:
- include_vars:
file: licenses.json
name: jsondata
- set_fact:
file_version: "{{ jsondata.version }}"
run_once: true
- hosts: hosts
tasks:
- copy:
src: licenses.json
dest: "/tmp/licenses_{{ file_version }}.json"
在远程主机创建文件
shell> ssh admin@test_11 cat /tmp/licenses_3.json
{"name": "test", "version": 3}
代码可以进一步简化。下面的单人游戏也可以做到这一点
- hosts: hosts
tasks:
- include_vars:
file: licenses.json
name: jsondata
run_once: true
- copy:
src: licenses.json
dest: "/tmp/licenses_{{ jsondata.version }}.json"
我正在尝试将 json 文件从我的本地主机复制到远程主机,并使用 json“版本”键值作为目标文件名中的参数。
JSON:
{"name": "test", "version": 3}
YML:
---
- name: Get json file version
hosts: locahost
become: true
tasks:
- name: Register licenses file
command: "cat conf/licenses.json"
register: result
- name: Save the json data
set_fact:
jsondata: "{{ result.stdout | from_json }}"
- name: Save licenses file version
set_fact:
file_version: "{{ jsondata | json_query(jmesquery) }}"
vars:
jmesquery: 'version'
- name: Deploy Licenses File
hosts: hosts
become: true
tasks:
- name: Copy licenses file
copy:
src: "conf/licenses.json"
dest: "/tmp/licenses_{{ file_version }}.json"
当我 运行 上面的剧本时,部署许可证文件密钥找不到 file_version 事实,即使我可以看到它已成功保存在 Get json文件版本密钥。
设置file_version事实:
ok: [localhost] => {
"ansible_facts": {
"file_version": "1"
},
"changed": false
}
错误:
The task includes an option with an undefined variable. The error was: 'file_version' is undefined
我认为事实保存在给定的主机粒度上,而不是每个剧本启动的全局事实。
我目前的解决方法是将密钥组合到一个任务中,然后它就可以正常工作,但我更喜欢一次获取版本,而不是为每个远程主机重复一次。
要访问另一台主机的事实,您始终可以使用 hostvars
special variable。
因此,在您的情况下:
dest: "/tmp/licenses_{{ hostvars.localhost.file_version }}.json"
现在,您实际上不需要两场比赛那么复杂,并且完全可以做到:
- name: Deploy Licenses File
hosts: hosts
become: true
tasks:
- name: Copy licenses file
copy:
src: "{{ _licence_file }}"
dest: "/tmp/licenses_{{ file_version }}.json"
vars:
_licence_file: conf/licenses.json
file_version: >-
{{ (lookup('file', _licence_file) | from_json).version }}
第一个游戏仅在 localhost 运行。因此,在第一个游戏中声明的变量仅对 localhost 可用。这是第二个playhost无法使用变量的原因
The error was: 'file_version' is undefined
运行一次任务在所有主机的第一个块中播放。这样变量将在第二个游戏中对所有主机可用。例如,下面的简化剧本可以完成这项工作
- hosts: all
tasks:
- block:
- include_vars:
file: licenses.json
name: jsondata
- set_fact:
file_version: "{{ jsondata.version }}"
run_once: true
- hosts: hosts
tasks:
- copy:
src: licenses.json
dest: "/tmp/licenses_{{ file_version }}.json"
在远程主机创建文件
shell> ssh admin@test_11 cat /tmp/licenses_3.json
{"name": "test", "version": 3}
代码可以进一步简化。下面的单人游戏也可以做到这一点
- hosts: hosts
tasks:
- include_vars:
file: licenses.json
name: jsondata
run_once: true
- copy:
src: licenses.json
dest: "/tmp/licenses_{{ jsondata.version }}.json"