管理大项目——清单管理
1. 利用主机模式选择主机
1.1 引用清单主机
先创建一个host_vars目录,在这个目录下创建一个web1文件
[root@localhost playbook]# mkdir /etc/ansible/host_vars/
[root@localhost playbook]# touch /etc/ansible/host_vars/web1编辑清单文件
[root@localhost playbook]# vim /etc/ansible/inventoryweb1 ansible_password=redhat 之前写的是ip,可以直接通过ip就可以ping通。先在改成一个别名,检查是否能够通过别名来ping通
[root@localhost playbook]# vim /etc/ansible/host_vars/web1ansible_host: 192.168.50.136 在这个文件写入主机名192.168.50.136
[root@localhost playbook]# ansible all --list-host 能够取出该主机名hosts (1):web1
[root@localhost playbook]# ansible all -m ping
web1 | SUCCESS => {"ansible_facts": {"discovered_interpreter_python": "/usr/libexec/platform-python"},"changed": false,"ping": "pong"
}
[root@localhost playbook]# ansible web1 -m ping
web1 | SUCCESS => {"ansible_facts": {"discovered_interpreter_python": "/usr/libexec/platform-python"},"changed": false,"ping": "pong"
}
1.2 用playbook运行
[root@localhost playbook]# vim /etc/ansible/host_vars/web1 ansible_host: 192.168.50.136[root@localhost playbook]# vim /etc/ansible/inventoryweb1 ansible_password=redhat[root@localhost playbook]# vim myplay.yml ---
- hosts: web1tasks:- name: 测试ping:
[root@localhost playbook]# ansible-playbook myplay.yml PLAY [web1] **************************************************************************************************************************TASK [Gathering Facts] ***************************************************************************************************************
ok: [web1]TASK [测试] ****************************************************************************************************************************
ok: [web1]PLAY RECAP ***************************************************************************************************************************
web1 : ok=2 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 ok代表运行成功
1.3 使用组指定主机
当使用组的名称来运行时
[root@localhost playbook]# vim /etc/ansible/inventory[test]
web1 ansible_password=redhat[root@localhost playbook]# vim myplay.yml ---
- hosts: testtasks:- name: 测试ping:
[root@localhost playbook]# ansible-playbook myplay.yml PLAY [test] **************************************************************************************************************************TASK [Gathering Facts] ***************************************************************************************************************
ok: [web1]TASK [测试] ****************************************************************************************************************************
ok: [web1]PLAY RECAP ***************************************************************************************************************************
web1 : ok=2 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 ok显示执行成功[root@localhost playbook]# vim /etc/ansible/inventory1.1.1.1 这3个主机不属于任何组
2.2.2.2
3.3.3.3
[test]
web1 ansible_password=redhat[root@localhost playbook]# ansible ungrouped --list-host 使用ungrouped来执行组之外的主机hosts (3):1.1.1.12.2.2.23.3.3.3
1.4 使用通配符匹配多个主机
- 使用 ‘*’ ,则清单中的所有主机都将匹配(星号必须带引号)
[root@localhost playbook]# vim /etc/ansible/inventory[test]
web1 ansible_password=redhat[root@localhost playbook]# vim myplay.yml ---
- hosts: '*' 使用通配符必须加引号,星号与all效果一样tasks:- name: 测试ping:
[root@localhost playbook]# ansible-playbook myplay.yml PLAY [*] *****************************************************************************************************************************TASK [Gathering Facts] ***************************************************************************************************************
ok: [web1]TASK [测试] ****************************************************************************************************************************
ok: [web1]PLAY RECAP ***************************************************************************************************************************
web1 : ok=2 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 ok表示执行成功
一些在主机模式中使用的字符对shell也有意义。通过ansible使用主机模式从命令行运行临时命令时,这可能会有问题。建议大家在命令行中使用单引号括起使用的主机模式,防止它们被shell意外扩展。
类似的,如果在Ansible Playbook中使用了任何特殊通配符或列表字符,必须将主机模式放在单引号里,确保能够正确解析主机模式。
通配符主机模式匹配所有清单名称、主机和主机组。它们不区别名称是DNS名、IP地址还是组,这可能会导致一些意外的匹配。
- 例如 : 在playbook中写’detacenter*'时
---
- hosts: 'datacenter*'
解读:
比如有以下几个组,在我使用‘datacenter*’时,除了三个组里的每一个主机会被匹配到之外,第三个组里的两个主机会匹配到,所以执行一次playbook时,datacenter1和datacenter2会执行2次[datacenter1]
labhost1.example.com
test1.example.com[datacenter2]
labhost2.example.com
test2.example.com[datacenter:children]
datacenter1
datacenter2
1.5 列表
- 如果提供受管主机的逗号分隔列表,则所有这些受管主机都将是目标:
---
- hosts: 主机名,主机名,主机名
- 如果提供组的逗号分隔列表,则属于任何这些组的所有主机都将是目标:
---
- hosts: 组,组,组
- 混合使用受管主机、主机组和通配符:
---
- hosts:'datacenter*,192.168.50.134'
注意:
也可以用冒号(:)取代逗号。不过,逗号是首选的分隔符,特别是将IPv6地址用作受管主机名称时。
- &: 同时具备在两个组里
---
- hosts: abc,&123 指挥匹配在abc组里的同时还在123组里的主机---
- hosts: &123,abc 该符号也可以放在前面---
- hosts: abc,&123,lop 当&前有组时,只匹配同时在与它相邻的两个组里的主机;&放在第一个时,只取往后第二个和第三个组的主机;但在运行playbook时,会执行lop或lop组里的主机
- !: 取反
---
- hosts: 123,abc,!yyp 在执行playbook时,只读取123(组)和abc(组),不会执行yyp(组)
2. 动态清单
- 编写动态清单
[root@localhost playbook]# vim inventory 编写一个静态清单[haha]
1.1.1.1
2.2.2.2[kk]
5.5.5.5
9.9.9.9[root@localhost playbook]# ansible-inventory -i inventory --list 用-i指定一个静态清单,--list查看写成动态清单是什么样子
{"_meta": {"hostvars": {}},"all": {"children": ["haha","kk","ungrouped"]},"haha": {"hosts": ["1.1.1.1","2.2.2.2"]},"kk": {"hosts": ["5.5.5.5","9.9.9.9"]}
}
3. 配置并行
3.1 使用forks在ansible中配置并行
- 默认情况下,Ansible会以每5台主机来运行playbook,直至所有主机运行完任务
- 设置目标时不能太大,否则控制节点会瘫痪
- 查看Ansible所进行的最大同时连接数 ,该数值由Ansible配置文件中的forks参数控制,使用以下方式查看
[root@ansible ~]# ansible-config dump|grep -i fork 第一种方式查看
DEFAULT_FORKS(default) = 5
[root@ansible ~]# ansible-config list|grep -i fork 第二种方式查看
DEFAULT_FORKS:description: Maximum number of forks Ansible will use to execute tasks on target- {name: ANSIBLE_FORKS}- {key: forks, section: defaults}name: Number of task forks[root@ansible ~]# vim /etc/ansible/ansible.cfg 也可以使用配置文件查看
......
#forks = 5
......
3.2 管理滚动更新
默认情况下:
依次在5台主机上执行playbook中的第一个任务,然后依次在5台主机上执行playbook中的第二个任务,直到playbook中所有任务全部完成,然后执行handlers中的任务
serial: 5
先在前5台主机上执行playbook中的所有任务,包括handlers中的任务,然后在另外5台主机上执行playbook中的所有任务,包括handlers中的任务
4. 包含和导入文件
4.1 管理大型playbook
如果playbook很长或很复杂,我们可以将其分成较小的文件以便于管理。可采用模块化方式将多个playbook组合为一个主要playbook,或者将文件中的任务列表插入play。这样可以更轻松地在不同项目中重用play或任务序列。
4.2 包含或导入文件
Ansible可以使用两种操作将内容带入playbook。可以包含内容,也可以导入内容。
包含内容是一个动态操作。在playbook运行期间,Ansible会在内容到达时处理所包含的内容。
导入内容是一个静态操作。在运行开始之前,Ansible在最初解析playbook时预处理导入的内容。
4.3 导入playbook
查看受控机是否安装了阿帕奇,查看服务是否启动
[root@localhost ~]# rpm -qa|grep httpd
[root@localhost ~]# ss -antl
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
LISTEN 0 128 [::]:22 [::]:* 主控机创建一个playbook目录,下面分别编辑安装,启动服务,把两个任务写入一个组里
[root@localhost playbook]# ls
config.yml install.yml main.yml
[root@localhost playbook]# cat config.yml
---
- hosts: alltasks:- name: start apacheservice:name: httpdstate: started
[root@localhost playbook]# cat install.yml
---
- hosts: alltasks:- name: install apacheyum:name: httpdstate: present
[root@localhost playbook]# cat main.yml
- name: import installimport_playbook: install.yml- name: configimport_playbook: config.yml
[root@localhost playbook]# ansible-playbook main.yml PLAY [all] *********************************************************************TASK [Gathering Facts] *********************************************************
ok: [web1]TASK [install apache] **********************************************************
changed: [web1]PLAY [all] *********************************************************************TASK [Gathering Facts] *********************************************************
ok: [web1]TASK [start apache] ************************************************************
changed: [web1]PLAY RECAP *********************************************************************
web1 : ok=4 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 再次查看受控机是否安装阿帕奇,服务是否启动
[root@localhost ~]# rpm -qa|grep httpd
centos-logos-httpd-80.5-2.el8.noarch
httpd-tools-2.4.37-21.module_el8.2.0+382+15b0afa8.x86_64
httpd-filesystem-2.4.37-21.module_el8.2.0+382+15b0afa8.noarch
httpd-2.4.37-21.module_el8.2.0+382+15b0afa8.x86_64
[root@localhost ~]# ss -antl
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
LISTEN 0 128 *:80 *:*
LISTEN 0 128 *:81 *:*
LISTEN 0 128 [::]:22 [::]:*
- 第二种方式
先在受控机上把该配置文件传到主控机
[root@localhost ~]# scp /usr/share/doc/httpd/httpd-vhosts.conf 192.168.50.135:/root/
root@192.168.50.135's password:
httpd-vhosts.conf 100% 1477 707.6KB/s 00:00
查看有无该文件,端口是否启动
[root@localhost ~]# ls /etc/httpd/conf.d/
1 README vhosts.conf
autoindex.conf userdir.conf welcome.conf
[root@localhost ~]# ss -antl
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
LISTEN 0 128 [::]:22 [::]:* 主控机把该配置文件改名
[root@localhost files]# mv httpd-vhosts.conf httpd-vhosts.conf.j2
[root@localhost files]# ls
gl.j2 httpd-vhosts.conf.j2 user.j2
hosts.j2 inventory.j2进入该文件,把其端口改为变量
[root@localhost files]# vim httpd-vhosts.conf.j2
{ port }}>DocumentRoot "/var/www/html/{{ site }}.example.com"ServerName {{ site }}.example.com
编写组合文件
[root@localhost playbook]# vim main.yml - name: import installimport_playbook: install.yml- hosts: allvars: 加入变量port: 80 使用80端口site: testtasks:- name: configtemplate:src: ../files/httpd-vhosts.conf.j2dest: /etc/httpd/conf.d/httpd-vhosts.conf- name: create directoryfile:path: /var/www/html/{{ site }}.example.comstate: directory- name: provides sitecopy:src: ../files/{{ site }}.example.comdest: /var/www/html/- name: serviceimport_playbook: service.yml
~
[root@localhost playbook]# ansible-playbook main.yml PLAY [all] *********************************************************************TASK [Gathering Facts] *********************************************************
ok: [web1]TASK [install apache] **********************************************************
ok: [web1]
[WARNING]: Found variable using reserved name: portPLAY [all] *********************************************************************TASK [Gathering Facts] *********************************************************
ok: [web1]TASK [config] ******************************************************************
changed: [web1]TASK [create directory] ********************************************************
changed: [web1]TASK [provides site] ***********************************************************
changed: [web1]PLAY [all] *********************************************************************TASK [Gathering Facts] *********************************************************
ok: [web1]TASK [start apache] ************************************************************
changed: [web1]PLAY RECAP *********************************************************************
web1 : ok=8 changed=4 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 查看受控机该文件是否传过来,端口是否启动
[root@localhost ~]# ls /etc/httpd/conf.d/
1 README welcome.conf
autoindex.conf userdir.conf
httpd-vhosts.conf vhosts.conf
[root@localhost ~]# ss -antl
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
LISTEN 0 128 [::]:22 [::]:*
LISTEN 0 128 *:80 *:*
LISTEN 0 128 *:81 *:*
4.4 导入和包含任务
4.4.1 导入任务文件
导入任务文件时,在解析该playbook时将直接插入该文件中的任务。由于import_tasks在解析playbook时静态导入任务,因此对其工作方式有一些影响。
- 使用import_tasks功能时,导入时设置的when等条件语句将应用于导入的每个任务
- 无法将循环用于import_tasks功能
- 如果使用变量来指定要导入的文件的名称,则将无法使用主机或组清单变量
[root@localhost tasks]# vim install.yml - name: installyum:name: httpdstate: present
[root@localhost tasks]# vim service.yml- name: serviceservice:name: httpdstate: started
[root@localhost playbook]# vim zu.yml 建一个组文件,里面写入两个任务---
- hosts: alltasks:- import_tasks: ../tasks/install.yml- import_tasks: ../tasks/service.yml
[root@localhost playbook]# ansible-playbook --syntax-check zu.yml 检查语法playbook: zu.yml
4.4.2 包含任务文件
可以使用include_tasks功能将任务文件动态导入playbook内的play中。
[root@localhost playbook]# vim zu.yml ---
- hosts: alltasks:- imclude_tasks: ../tasks/install.yml- imclude_tasks: ../tasks/service.yml
[root@localhost playbook]# ansible-playbook --list-tasks zu.yml playbook: zu.ymlplay #1 (all): all TAGS: []tasks:install TAGS: []service TAGS: []
在play运行并且这部分play到达前,include_tasks功能不会处理playbook中的内容。Playbook内容的处理顺序会影响包含任务功能的工作方式。
- 使用include_tasks功能时,包含时设置的when等条件语句将确定任务是否包含在play中
- 如果运行ansible-playbook --list-tasks以列出playbook中的任务,则不会显示已包含任务文件中的任务。将显示包含任务文件的任务。相比之下,import_tasks功能不会列出导入任务文件的任务,而列出已导入任务文件中的各个任务
- 不能使用ansible-playbook --start-at-task从已包含任务文件中的任务开始执行playbook
- 不能使用notify语句触发已包含任务文件中的处理程序名称。可以在包含整个任务文件的主playbook中触发处理程序,在这种情况下,已包含文件中的所有任务都将运行
4.4.3 任务文件的用例
请参考下面的示例,在这些情景中将任务组作为与playbook独立的外部文件来管理或许有所帮助:
如果新服务器需要全面配置,则管理员可以创建不同的任务集合,分别用于创建用户、安装软件包、配置服务、配置特权、设置对共享文件系统的访问权限、强化服务器、安装安全更新,以及安装监控代理等。每一任务集合可通过单独的自包含任务文件进行管理
如果服务器由开发人员、系统管理员和数据库管理员统一管理,则每个组织可以编写自己的任务文件,再由系统经理进行审核和集成
如果服务器要求特定的配置,它可以整合为按照某一条件来执行的一组任务。换句话说,仅在满足特定标准时才包含任务
如果一组服务器需要运行某一项/组任务,则它/它们可以仅在属于特定主机组的服务器上运行
4.4.4 管理任务文件
为方便管理,可以创建专门用于任务文件的目录,并将所有任务文件保存在该目录中。然后playbook就可以从该目录包含或导入任务文件。这样就可以构建复杂的playbook,同时简化其结构和组件的管理。
4.5 为外部play和任务定义变量
使用Ansible的导入和包含功能将外部文件中的play或任务合并到playbook中极大地增强了在Ansible环境中重用任务和playbook的能力。为了最大限度地提高重用可能性,这些任务和play文件应尽可能通用。变量可用于参数化play和任务元素,以扩大任务和play的应用范围。
[root@localhost tasks]# vim install.yml - name: install {{ pkg_name }} 加入变量yum:name: "{{ pkg_name }}" 加入变量state: present
[root@localhost tasks]# vim service.yml - name: start {{ srv_name }} service 加入变量service:name: "{{ srv_name }}" 加入变量state: started [root@localhost playbook]# vim zu.yml ---
- hosts: alltasks:- import_tasks: ../tasks/install.yml- import_tasks: ../tasks/service.ymlvars:pkg_name: postfix 安装postfixsrv_name: postfix
[root@localhost playbook]# ansible-playbook zu.yml PLAY [all] *********************************************************************TASK [Gathering Facts] *********************************************************
ok: [web1]TASK [install postfix] *********************************************************
changed: [web1]TASK [start postfix service] ***************************************************
changed: [web1]PLAY RECAP *********************************************************************
web1 : ok=3 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 受控机查看是否安装了postfix
[root@localhost ~]# rpm -qa|grep postfix
postfix-3.3.1-12.el8.x86_64
- 方法二
[root@localhost playbook]# vim zu.yml ---
- hosts: allgather_facts: novars:pkg_name: postfixsrv_name: postfixtasks:- name: import tasks installimport_tasks: ../tasks/install.yml- name: import tasks serviceimport_tasks: ../tasks/service.yml受控机查看
[root@localhost ~]# rpm -qa|grep postfix
postfix-3.3.1-12.el8.x86_64
本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!
