两个playbook分别用于安装LAMP环境和LNMP环境
cat lamp.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- yum:
name: mysql
state: present
- yum:
name: php-fpm
state: present
- yum:
name: httpd
state: present
cat lnmp.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- yum:
name: mysql
state: present
- yum:
name: php-fpm
state: present
- yum:
name: nginx
state: present
重构上面两段代码,提取出相同的部分
cat install_MysqlAndPhp.yml
- yum:
name: mysql
state: present
- yum:
name: php-fpm
state: present
cat lamp.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: install_MysqlAndPhp.yml
- yum:
name: httpd
state: present
cat lnmp.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: install_MysqlAndPhp.yml
- yum:
name: nginx
state: present
1. include
1.1 在 handlers使用include
cat test_include.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- file:
path: /opt/ttt
state: touch
notify: test include handlers
handlers:
- name: test include handlers
include: include_handler.yml
cat include_handler.yml
- debug:
msg: "task1 of handlers"
- debug:
msg: "task2 of handlers"
- debug:
msg: "task3 of handlers"
include引用playbook,执行lamp.yml时,会先执行lamp相关的任务,然后再执行lnmp.yml中的任务
cat lamp.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: install_MysqlAndPhp.yml
- yum:
name: httpd
state: present
- include: lnmp.yml
1.2 include传入参数
cat test_include1.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: in.yml
test_var1=hello
test_var2=test
cat in.yml
- debug:
msg: "{{ test_var1 }}"
- debug:
msg: "{{ test_var2 }}"
使用 vars关键字,以key: value变量的方式传入参数变量
tasks:
- include: in.yml
vars:
test_var1: hello
test_var2: test
cat test_include1.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: in.yml
vars:
users:
bob:
gender: male
lucy:
gender: female
cat in.yml
- debug:
msg: "{{ item.key}} is {{ item.value.gender }}"
loop: "{{ users | dict2items }}"
1.3 include中打标签
cat test_include1.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: in1.yml
tags: t1
- include: in2.yml
tags: t2
cat in1.yml
- debug:
msg: "task1 in in1.yml"
- debug:
msg: "task2 in in1.yml"
cat in2.yml
- debug:
msg: "task1 in in2.yml"
- debug:
msg: "task2 in in2.yml"
1.4 对include进行循环操作
cat test_include1.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: in3.yml
when: 2 > 1
- include: in3.yml
loop:
- 1
- 2
- 3
cat in3.yml
- debug:
msg: "task1 in in3.yml"
- debug:
msg: "task2 in in3.yml"
在A.yml中include了B.yml,并且循环调用了B.yml中的两个任务,在B.yml中,输出了item的信息
cat A.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: B.yml
loop:
- 1
- 2
- 3
cat B.yml
- debug:
msg: "{{item}}--task1 in B.yml"
- debug:
msg: "{{item}}--task2 in B.yml"
“双层循环”:B.yml中循环调用了debug模块,而在A.yml中,又循环的调用了B.yml
cat A.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include: B.yml
loop:
- 1
- 2
cat B.yml
- debug:
msg: "{{item}}--task in B.yml"
loop:
- a
- b
- c
loop_control的loop_var
在A文件中循环调用了B文件,并且在循环时使用了loop_control的loop_var选项,将 loop_var选项的值设置为"outer_item",这表示,将外层循环的item值存放在了"outer_item"变量中,在B文件中的 debug任务中,同时输出了"outer_item"变量和"item"变量的值
cat A.yml
---
- hosts: test70
remote_user: root
gather_facts: nog
tasks:
- include: B.yml
loop:
- 1
- 2
loop_control:
loop_var: outer_item
cat B.yml
- debug:
msg: "{{outer_item}}--{{item}}--task in B.yml"
loop:
- a
- b
- c
2. include_tasks
cat intest.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task1"
- include_tasks: in.yml
- debug:
msg: "test task2"
# cat in.yml
- debug:
msg: "task1 in in.yml"
- debug:
msg: "task2 in in.yml"
2.7版本开始,"include_tasks"模块加入了file参数和apply参数,file参数可以用来指定要包含的任务列表文件
- include_tasks:
file: in.yml
等价于
- include_tasks: in.yml
在使用tags时,“include_tasks” 与"include"并不相同,标签只会对"include_tasks"任务本身生效,而不会对其中包含的任务生效
cat intest.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task1"
- include_tasks:
file: in.yml
tags: t1
- debug:
msg: "test task2"
如果想要tags对"include_tasks"中包含的所有任务都生效,该怎么实现呢?这时,就需要使用到"include_tasks"模块的apply参数
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include_tasks:
file: in.yml
apply:
tags:
- t1
执行上例playbook以后,并没有如预想的一样调用in.yml中的任务,就连"include_tasks"任务自身也没有被调用
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- include_tasks:
file: in.yml
apply:
tags:
- t1
tags: always
in.yml中的任务并未"always"执行,而"include_tasks"任务本身却"always"执 行了,所以,可以得出结论,上例中的always标签只是针对"include_tasks"任务自身而言的,之所以 为"include_tasks"任务添加always标签,就是为了让apply参数中的t1标签能够针对包含的所有任务生效,always标签并不会 对被包含的所有任务生效
cat intest.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task"
tags: t0
- include_tasks:
file: in.yml
apply:
tags:
- t1
tags: always
apply参数中的tags用于给in.yml中的任务统一打标签,"include_tasks"对应的tags用于 给"include_tasks"任务自身打标签,同时,如果想要apply参数中的tags能够生效,"include_tasks"的标签中必须包含 always标签
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task"
tags: t0
- include_tasks:
file: in.yml
apply:
tags: t1,always
tags: always
3. import_tasks
cat intest1.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task"
- import_tasks: in.yml
cat in.yml
- debug:
msg: "task1 in in.yml"
- debug:
msg: "task2 in in.yml
import_tasks和include_tasks不同之处在于,import_tasks是静态的,include_tasks是动态的。
静态的意思就是被include的文件在playbook被加载时就展开了(是预处理的)。
动态的意思就是被include的文件在playbook运行时才会被展开(是实时处理的)。
由于include_tasks是动态的,所以,被include的文件的文件名可以使用任何变量替换。
由于import_tasks是静态的,所以,被include的文件的文件名不能使用动态的变量替换。
cat intest3.yml
---
- hosts: test70
remote_user: root
gather_facts: no
vars:
file_name: in.yml
tasks:
- import_tasks: "{{file_name}}"
- include_tasks: "{{file_name}}
set_fact的方式定义了file_name变量
cat intest3.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- set_fact:
file_name: in.yml
- import_tasks: "{{file_name}}"
- include_tasks: "{{file_name}}"
使用了set_fact的方式定义了file_name变量,尝试执行上例playbook,会发现报错。
当使用静态的import时,请确保文件名中使用到的变量被定义在vars中、vars_files中、或者extra-vars中,静态的import不支持其他方式传入的变量。
想要对包含的任务列表进行循环操作,则只能使用"include_tasks"关键字,不能使用"import_tasks"关键字,"import_tasks"并不支持循环操作,
也就是说,使用"loop"关键字或"with_items"关键字对include文件进行循环操作时,只能配合"include_tasks"才能正常运行。
当使用when关键字对include文件添加了条件判断时,只有条件满足后,include文件中的任务列表才会被执行,其实,when关键字对"include_tasks"和"import_tasks"的实际操作有着本质区别,区别如下:
当对"include_tasks"使用when进行条件判断时,when对应的条件只会应用于"include_tasks"任务本身,当执行被包含的任务时,不会对这些被包含的任务重新进行条件判断。
当对"import_tasks"使用when进行条件判断时,when对应的条件会应用于被include的文件中的每一个任务,当执行被包含的任务时,会对每一个被包含的任务进行同样的条件判断。
cat intest4.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- name: '----------set testvar to 0'
set_fact:
testnum: 0
- debug:
msg: '-----include_tasks-----enter the in1.yml-----'
- include_tasks: in1.yml
when: testnum == 0
- name: '----------set testvar to 0'
set_fact:
testnum: 0
- debug:
msg: '-----import_tasks-----enter the in1.yml-----'
- import_tasks: in1.yml
when: testnum == 0
# cat in1.yml
- set_fact:
testnum: 1
- debug:
msg: "task1 in in1.yml"
4. import_playbook
cat intest6.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task in intest6.yml"
- import_playbook: intest7.yml
cat intest7.yml
---
- hosts: test70
remote_user: root
gather_facts: no
tasks:
- debug:
msg: "test task in intest7.yml"
————Blueicex 2020/3/30 10:08 [email protected]