问题描述
正在使用Ansible playbook为一系列站点配置Apache。playbook需要将每个站点的虚拟主机配置模板复制到指定位置,并使用a2ensite
命令启用每个站点。用户不喜欢在每个任务中重复相同的项目列表。他想知道如何配置playbook以使用相同的项目列表执行这两个任务。
解决方案
请注意以下操作注意版本差异及修改前做好备份。
方案1
可以创建一个单独的任务文件make_site.yml
,将安装和启用站点的任务分开。在playbook中使用include_tasks
指令来引入这个任务文件,并使用with_items
循环遍历项目列表。
以下是具体步骤:
1. 创建一个名为make_site.yml
的文件。
2. 在该文件中定义安装和启用站点的任务。
3. 在playbook中使用include_tasks
指令引入make_site.yml
文件,并使用with_items
循环遍历项目列表。
下面是一个示例:
- include_tasks: make_site.yml
with_items:
- sitea
- siteb
- sitec
- sited
loop_control:
loop_var: site
在上面的示例中,我们使用include_tasks
指令引入了make_site.yml
文件,并使用with_items
循环遍历项目列表。loop_control
指令用于指定循环变量的名称为site
。
在make_site.yml
文件中,我们可以使用{{ site }}
来引用循环变量,并执行相应的安装和启用任务。
方案2
另一种方法是使用文件通配符来遍历项目列表。假设每个站点都有一个配置文件,我们可以使用文件通配符来获取所有配置文件,并使用正则表达式进行处理。
以下是具体步骤:
1. 创建一个目录用于存放模板文件,比如roles/webserver/templates/apache-sites
。
2. 在该目录中创建每个站点的配置文件,比如sitea.conf.j2
、siteb.conf.j2
等。
3. 在roles/webserver/tasks/main.yml
文件中使用文件通配符和正则表达式来遍历配置文件,并执行相应的安装和启用任务。
下面是一个示例:
- block:
- name: Install apache site conf
template: src={{ item }} dest=/etc/apache2/sites-available/{{ item|regex_replace(".*/","")|regex_replace("\.j2$","") }} mode=0644
with_fileglob:
- "roles/webserver/templates/apache-sites/*"
- name: Enable site apache conf
command: a2ensite {{ item|regex_replace(".*/","")|regex_replace("\.conf\.j2$","") }}
args:
creates: /etc/apache2/sites-enabled/{{ item|regex_replace(".*/","")|regex_replace("\.j2$","") }}
with_fileglob:
- "roles/webserver/templates/apache-sites/*"
become: yes
在上面的示例中,我们使用with_fileglob
指令和文件通配符roles/webserver/templates/apache-sites/*
来获取所有配置文件。然后,使用正则表达式regex_replace
来处理文件路径,获取站点名称,并执行相应的安装和启用任务。
这种方法可以方便地添加新的站点,只需要在模板目录中添加一个新的配置文件即可。
请注意,这种方法也可以用于创建其他应用程序的项目列表,甚至可以使用空的虚拟文件来创建列表。