https://docs.ansible.com/ansible/latest/user_guide/playbooks_reuse_roles.html
角色(roles)其实就是把原本的playbook文件拆分成目录结构, 通过分析目录结构加载任务参数。
一、目录结构
webservers.yml
fooservers.yml
roles/
common/
tasks/
handlers/
files/
templates/
vars/
defaults/
meta/
webservers/
tasks/
defaults/
meta/
目录的级别结构是固定的。
webservers.yml, fooservers.yml 是playbook调用的主文件,文件里加载roles目录下的role。
roles 目录是固定的。
common, webservers 是role的名称, 下面各自定义各自role的内容。
role下面的目录名称是固定的。
tasks
: 定义任务。
handlers
: 定义handlers。
files
: 存放需要copy的文件。
templates
: 存放模板文件。
vars
: 变量文件。
defaults
: 默认变量。
meta
: 元数据。
需要了解的:
-
其中除了
files
以外, 其他目录里的文件固定位main.yml, ansible-playbook会通过这个文件加载信息。 -
在同一个role中,任何copy文件、templates、include都可以直接加载所需要的task、file、vars, 而不需要写路径。如:
在tasks
任务里调用files
里的文件直接相对路径即可。
比如:src=nginx-1.17.8.tar.gz
就可以, 不需要添加路径。 -
defaults
与vars
里面都是放置变量, 只不过变量的优先级不同, 一般情况下也用不到defaults
目录。
优先级可以参考这里:
https://www.yxingxing.net/articles/2020/02/14/1581649499754.html#b3_solo_h3_5 。 -
不需要的目录可以不写。
二、使用
介绍
使用roles
子句加载role。
有加载顺序,在上面的role先执行。如:
- hosts: webserver
roles:
- common
- webserver
- dbserver
先执行common, 然后webserver, dbserver。
每个role里面的meta
都是先执行。然后执行task
。
roles的加载方式有3中, 前两种都是正常的在roles
子句下面的列表。
第三种是在task
子句里使用include_role
,import_role
子句。
roles[]
.<role_name>
就是上面的方式。
这种方式用于-
后面不需要加载其他子句的情况。roles[]
.role: <role_name>
,在需要其他子句的情况下
比如下面需要vars
子句添加变量。common还是原来的样子,webserver与dbserver变了。
- hosts: webserver
roles:
- common
- role: webserver
vars:
dir: '/usr/local/nginx'
version: '1.17.8'
- role: dbserver
vars:
dir: '/usr/local/mariadb'
tasks[]
.include_role
- hosts: webserver
tasks:
- include_role:
name: common
- include_role:
name: webserver
vars:
dir: '/usr/local/nginx'
version: '1.17.8'
- include_role:
name: dbserver
vars:
dir: '/usr/local/mariadb'
例子
1、简单的例子
目录结构:
[root@lvs playbook]# tree
.
├── roles
│ └── webserver
│ ├── tasks
│ │ └── main.yml
│ └── vars
│ └── main.yml
└── test.yml
4 directories, 3 files
[root@lvs playbook]#
test.yml
role的调用就是在roles
子句下面以列表加载, 加载方式也有两种:
1、直接指定role名称,就是下面这个例子。
2、- role: <role_name>
, 用于在roles
下面还要使用vars
添加变量的情况。
[root@lvs playbook]# cat test.yml
- hosts: webserver
roles:
- webserver
tasks
[root@lvs playbook]# cat roles/webserver/tasks/main.yml
- name: print info
debug: msg="hello {{ user }}"
vars
[root@lvs playbook]# cat roles/webserver/vars/main.yml
user: sst
[root@lvs playbook]#
执行:
[[root@lvs playbook]# ansible-playbook test.yml
PLAY [webserver] *****************************************************************************************************************************
TASK [Gathering Facts] ***********************************************************************************************************************
ok: [172.100.102.92]
ok: [172.100.102.93]
TASK [webserver : print info] ****************************************************************************************************************
ok: [172.100.102.92] => {
"msg": "hello sst"
}
ok: [172.100.102.93] => {
"msg": "hello sst"
}
2、加载role的也可以使用when
task.yml:
- hosts: webserver
roles:
- common
- role: webserver
vars:
dir: '/usr/local/nginx'
version: '1.17.8'
when: version == '1.16'
- role: dbserver
vars:
dir: '/usr/local/mariadb'
上面的common与dbserver在roles目录下只有空目录,只要有目录就不会报错。
[root@lvs playbook]# ansible-playbook test.yml
PLAY [webserver] ********************************************************************************************************************************
TASK [Gathering Facts] **************************************************************************************************************************
ok: [172.100.102.92]
ok: [172.100.102.93]
TASK [webserver : print info] *******************************************************************************************************************
skipping: [172.100.102.92]
skipping: [172.100.102.93]
PLAY RECAP **************************************************************************************************************************************
172.100.102.92 : ok=1 changed=0 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0
172.100.102.93 : ok=1 changed=0 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0