公司计划在年底做一次大型市场促销活动,全面冲刺下交易额,为明年的上市做准备。公司要求各业务组对年底大促做准备,运维部要求所有业务容量进行三倍的扩容,并搭建出多套环境可以共开发和测试人员做测试,运维老大为了在年底有所表现,要求运维部门同学尽快实现,当你接到这个任务时,有没有更快的解决方案?

一、简单介绍

1、定义:

      ansible是新出现的自动化运维工具,基于Python开发,集合了众多运维工具(puppet、chef、func、fabric)的优点,实现了批量系统配置、批量程序部署、批量运行命令等功能。

  ansible是基于 paramiko(框架) 开发的,并且基于模块化工作,本身没有批量部署的能力。真正具有批量部署的是ansible所运行的模块,ansible只是提供一种框架。ansible不需要在远程主机上安装client/agents,因为它们是基于ssh来和远程主机通讯的。ansible目前已经已经被红帽官方收购,是自动化运维工具中大家认可度最高的,并且上手容易,学习简单。是每位运维工程师必须掌握的技能之一。

2、ansible 特点

1)部署简单,只需在主控端部署Ansible环境,被控端无需做任何操作,没有agent;

2) 默认使用SSH协议对设备进行管理;

3) 有大量常规运维操作模块,可实现日常绝大部分操作。

4) 配置简单、功能强大、扩展性强;

5) 支持API及自定义模块,可通过Python轻松扩展;

6) 通过Playbooks(剧本)来定制强大的配置、状态管理;

7) 轻量级,无需在客户端安装agent,更新时,只需在操作机上进行一次更新即可;

8) 提供一个功能强大、操作性强的Web管理界面和REST API接口——AWX平台。

9)模块化:调用特定的模块,完成特定任务。

10)无需代理不依赖PKI(无需ssl)

11)幂等性:一个任务执行1遍和执行n遍效果一样,不因重复执行带来意外情况

12)可使用任何编程语言写模块

13)安全,基于OpenSSH

14)有Paramiko,PyYAML,Jinja2(模板语言)三个关键模块

3、ansible架构

上图为ansible的基本架构,从上图可以了解到其由以下部分组成:

  • 核心:ansible
  • 核心模块(Core Modules):这些都是ansible自带的模块
  • 扩展模块(Custom Modules):如果核心模块不足以完成某种功能,可以添加扩展模块
  • 插件(Plugins):完成模块功能的补充
  • 剧本(Playbooks):ansible的任务配置文件,将多个任务定义在剧本中,由ansible自动执行
  • 连接插件(Connectior Plugins):ansible基于连接插件连接到各个主机上,虽然ansible是使用ssh连接到各个主机的,但是它还支持其他的连接方法,所以需要有连接插件
  • 主机群(Host Inventory):定义ansible管理的主机

4、工作原理:

 Ansible主要组成部分

  1. ANSIBLE PLAYBOOKS:任务剧本(任务集),编排定义Ansible任务集的配置文件,由Ansible顺序依次执行,通常是JSON格式的YML文件
  2. INVENTORY:Ansible管理主机的清单/etc/anaible/hosts
  3. MODULES:Ansible执行命令的功能模块,多数为内置核心模块,也可自定义
  4. PLUGINS:模块功能的补充,如连接类型插件、循环插件、变量插件、过滤插件等,该功能不常用
  5. API:供第三方程序调用的应用程序编程接口
  6. ANSIBLE:组合INVENTORY、API、MODULES、PLUGINS的绿框,可以理解为是ansible命令工具,其为核心执行工具
  7. Ansible命令执行来源:
  1. USER,普通用户,即SYSTEM ADMINISTRATOR
  2. CMDB(配置管理数据库) API 调用
  3. PUBLIC/PRIVATE CLOUD API调用
  4. USER-> Ansible Playbook -> Ansibile

8. 利用ansible实现管理的方式:

  1. 1Ad-Hoc ansible命令,主要用于临时命令使用场景
  2. 2Ansible-playbook 主要用于长期规划好的,大型项目的场景,需要有前提的规划9)Ansible-playbook(剧本)执行过程:
  3. 3、将已有编排好的任务集写入Ansible-Playbook
  4. 4、通过ansible-playbook命令分拆任务集至逐条ansible命令,按预定规则逐条执行

9. Ansible主要操作对象:

  1. HOSTS主机
  2. NETWORKING网络设备

注意事项

  1. 执行ansible的主机一般称为主控端,中控,master或堡垒机
  2. 主控端Python版本需要2.6或以上
  3. 被控端Python版本小于2.4需要安装python-simplejson
  4. 被控端如开启SELinux需要安装libselinux-python
  5. windows不能做为主控端

5、ansible 任务执行模式

Ansible系统由控制主机对被管节点的操作方式可分为两类,即ad-hoc和playbook:

  ·ad-hoc(点对点)模式:使用单个模块,支持批量执行单条命令。 ad-hoc 命令是一种可以快速输入的命令,而且不需要保存起来的命令。就相当于bash中的一句话shell。

  ·playbook(剧本)模式:是Ansible主要管理方式,也是Ansible功能强大的关键所在。playbook通过多个task集合完成一类功能,如Web服务的安装部署、数据库服务器的批量备份等。可以简单地把playbook理解为通过组合多条ad-hoc操作作的配置文件。

6、Ansible命令执行过程

  1. ansible命令执行过程
  2.  
  3. 1)加载自己的配置文件 默认/etc/ansible/ansible.cfg
  4.  
  5. 2)查找对应的主机配置文件,找到要执行的主机或者组
  6.  
  7. 3)加载自己对应的模块文件,如command
  8.  
  9. 4)通过ansible将模块或命令生成对应的临时py文件,并将该文件传输至远程服务器端对应执行用户的家目录的.ansible/tmp/XXX/XXX.PY文件
  10.  
  11. 5)给文件+x执行
  12.  
  13. 6)执行并返回结果
  14.  
  15. 7)删除临时py文件,sleep 0退出
  16.  
  17. 执行状态:
  18. 绿色:执行成功并且不需要做改变的操作
  19. 黄色:执行成功并且对目标主机做变更
  20. 红色:执行失败

实战一:安装ansible 及指令讲解

1、安装ansible

ansible安装常用两种方式,yum安装和pip程序安装

这里提供二种安装方式,任选一种即可

(1)使用yum 安装

yum install ansible –y

(2)使用pip :pip是安装Python包的管理器,类似yum

pip install ansible   如果没pip,需先安装pip.yum可直接安装:

yum install python-pip

pip install ansible

确认安装: ansible --version  查询版本

2、Ansible配置文件

Ansible 配置文件/etc/ansible/ansible.cfg (一般保持默认)

  1. [defaults]
  2. #inventory = /etc/ansible/hosts # 主机列表配置文件
  3. #library = /usr/share/my_modules/ # 库文件存放目录
  4. #remote_tmp = $HOME/.ansible/tmp #临时py命令文件存放在远程主机目录
  5. #local_tmp = $HOME/.ansible/tmp # 本机的临时命令执行目录
  6. #forks = 5 # 默认并发数
  7. #sudo_user = root # 默认sudo用户
  8. #ask_sudo_pass = True #每次执行ansible命令是否询问ssh密码
  9. #ask_pass = True
  10. #remote_port = 22
  11. #host_key_checking = False # 检查对应服务器的host_key,建议取消注释
  12. #log_path=/var/log/ansible.log #日志文件
  13. #module_name = command #默认模块

① sudo_user:

这是设置默认执行命令的用户,也可以在playbook中重新设置这个参数。配置实例如下:

  sudo_user = root

② remote_port:

这是指定连接被管节点的管理端口,默认是22。除非设置了特殊的SSH端口,不然这个参数一般是 不需要修改的。配置实例如下:

  remote_port = 22

③ host_key_checking:

这是设置是否检查SSH主机的密钥。可以设置为True或False,关闭后第一次连接没有提示配置实例

  host_key_checking = False

④ timeout:

这是设置SSH连接的超时间隔,单位是秒。配置实例如下:

  timeout = 60

log_path:Ansible系统默认是不记录日志的,如果想把Ansible系统的输出记录到日志文件中,需要设置log_path 来指定一个存储Ansible日志的文件。配置实例如下:

  log_path = /var/log/ansible.log

  另外需要注意,执行Ansible的用户需要有写入日志的权限,模块将会调用被管节点的syslog来记录

3、配置文件、程序及命令:

配置文件

  1. /etc/ansible/ansible.cfg 主配置文件,配置ansible工作特性
  2. /etc/ansible/hosts 主机清单
  3. /etc/ansible/roles/ 存放角色的目录

程序

  1. /usr/bin/ansible 主程序,临时命令执行工具
  2. /usr/bin/ansible-doc 查看配置文档,模块功能查看工具
  3. /usr/bin/ansible-galaxy 下载/上传优秀代码或Roles模块的官网平台
  4. /usr/bin/ansible-playbook 定制自动化任务,编排剧本工具/usr/bin/ansible-pull 远程执行命令的工具
  5. /usr/bin/ansible-vault 文件加密工具
  6. /usr/bin/ansible-console 基于Console界面与用户交互的执行工具

ansible系列命令
ansible

ansible-doc

ansible-playbook   定制任务,编排剧本

ansible-galaxy

  1. 连接 https://galaxy.ansible.com 下载相应的roles
  2. 列出所有已安装的galaxy
  3. ansible-galaxy list
  4. 安装galaxy
  5. ansible-galaxy install geerlingguy.redis
  6. 删除galaxy
  7. ansible-galaxy remove geerlingguy.redis

ansible-vault

  1. 功能:管理加密解密yml文件
  2. ansible-vault [create|decrypt|edit|encrypt|rekey|view]
  3. ansible-vault encrypt hello.yml 加密
  4. ansible-vault decrypt hello.yml 解密
  5. ansible-vault view hello.yml 查看
  6. ansible-vault edit hello.yml 编辑加密文件
  7. ansible-vault rekey hello.yml 修改口令
  8. ansible-vault create new.yml 创建新文件

ansible-console:  2.0+新增,可交互执行命令,支持tab

  1. root@test (2)[f:10] $
  2. 执行用户@当前操作的主机组 (当前组的主机数量)[f:并发数]$
  3. 设置并发数: forks n 例如: forks 10
  4. 切换组: cd 主机组 例如: cd web
  5. 列出当前组主机列表: list
  6. 列出所有的内置命令: ?或help
  7. 示例:
  8. root@all (2)[f:5]$ list
  9. root@all (2)[f:5]$ cd appsrvs
  10. root@appsrvs (2)[f:5]$ list
  11. root@appsrvs (2)[f:5]$ yum name=httpd state=present
  12. root@appsrvs (2)[f:5]$ service name=httpd state=started

ansible-pull        推送命令至远程,效率无限提升,对运维要求较高
ansible-doc: 显示模块帮助
ansible-doc [options] [module...]

  1. -a 显示所有模块的文档
  2. -l, --list 列出可用模块
  3. -s, --snippet显示指定模块的playbook片段

示例:

  1. ansible-doc l 列出所有模块
  2. ansible-doc ping 查看指定模块帮助用法
  3. ansible-doc s ping 查看指定模块帮助用法

 ansible通过ssh实现配置管理、应用部署、任务执行等功能,建议配置ansible端能基于
密钥认证的方式联系各被管理节点
 ansible <host-pattern> [-m module_name] [-a args]

  1. --version 显示版本
  2. -m module 指定模块,默认为command
  3. -v 详细过程 vv -vvv更详细
  4. --list-hosts 显示主机列表,可简写 --list
  5. -k, --ask-pass 提示输入ssh连接密码,默认Key验证
  6. -K, --ask-become-pass 提示输入sudo时的口令
  7. -C, --check 检查,并不执行
  8. -T, --timeout=TIMEOUT 执行命令的超时时间,默认10s
  9. -u, --user=REMOTE_USER 执行远程执行的用户
  10. -b, --become 代替旧版的sudo 切换
  11. --become-user=USERNAME 指定sudorunas用户,默认为root

4、ansible的Host-pattern

匹配主机的列表

All :表示所有Inventory中的所有主机

  • ansible all -m ping

* :通配符

  • ansible “*” -m ping  #其中*代表的意思就是all,所有的IP地址
  • ansible 192.168.1.* -m ping   #匹配1.*的IP地址
  • ansible “*srvs” -m ping

或关系

  • ansible “websrvs:appsrvs” -m ping    #或关系,取IP地址的并集
  • ansible “192.168.1.10:192.168.1.20” -m ping
  • ansible的Host-pattern

逻辑与

  • ansible “websrvs:&dbsrvs” -m ping    #与关系,取IP地址的交集
  • 在websrvs组并且在dbsrvs组中的主机

逻辑非

  • ansible ‘websrvs:!dbsrvs’ -m ping     #在websrvs中,取dbsrvs的反
  • 在websrvs组,但不在dbsrvs组中的主机
  • 注意:此处为单引号

综合逻辑

  • ansible ‘websrvs:dbsrvs:&appsrvs:!ftpsrvs’ -m ping

正则表达式

  • ansible “websrvs:&dbsrvs” -m ping
  • ansible “~(web|db).*\.magedu\.com” -m ping

5、ansible 使用前配置

(1)Ansible配置公私钥

配置ansible 使用公钥验证

虽然ansible支持其他主机认证方式,但是我们最常用的的还是基于秘钥的认证:

① 首先生成秘钥

ssh-keygen -t rsa -P " " -f /root/.ssh/id_rsa

② 然后向主机分发秘钥:

ssh-copy-id root@   #@后面跟主机名或者IP地址3、如果出现以下情况:

# ssh-copy-id -i root/.ssh/id_rsa.pub 10.1.6.72

-bash: ssh-copy-id: command not found

请尝试: yum -y install openssh-clientsansible

(2)直接执行脚本批量将本地公钥传递到对方主机:

  1. vim iplist.txt 将对方的主机IP地址写入
  2. 192.168.34.102
  3. 192.168.34.103
  4. 192.168.34.105
  1. #!/bin/bash 书写批量执行脚本
  2. user=root
  3. password=centos
  4. ssh-keygen -t rsa -P "" -f /root/.ssh/id_rsa
  5.  
  6. while read ip ;do
  7. expect <<EOF
  8. set timeout 10
  9. spawn ssh-copy-id -i /root/.ssh/id_rsa.pub $user@$ip
  10. expect {
  11. "yes/no" { send "yes\n";exp_continue }
  12. "password" { send "$password\n" }
  13. }
  14. expect eof
  15. EOF
  16. done < iplist.txt

实战二:ad-hoc(点对点)常用模块

1、设置hosts 远程被控制主机

  1. vim /etc/ansible/hosts 在最底部写入两个组的内容,分别写入远程主机的IP地址
  2.  
  3. [webs]
  4. 192.168.34.102
  5. 192.168.34.103
  6.  
  7. [apps]
  8. 192.168.34.103
  9. 192.168.34.105

定义hosts 有3类:

① Ex 1:未分组的主机,在任何组头之前指定

② Ex 2:有组的主机,一组属于"webservers"组的主机

③ Ex 3:和数据库有关的,"dbservers"组中的数据库服务器集合

在最底部写入远程主机的IP地址:

2、ping 模块,主机连通性测试

  1. [root@ansibale~]#ansible all -m ping 尝试ping对方主机地址,由于是基于key验证,此时已经不需要输入密码。
  2. 192.168.34.102 | SUCCESS => {
  3. "ansible_facts": {
  4. "discovered_interpreter_python": "/usr/bin/python"
  5. },
  6. "changed": false,
  7. "ping": "pong"
  8. }
  9. 192.168.34.103 | SUCCESS => {
  10. "ansible_facts": {
  11. "discovered_interpreter_python": "/usr/bin/python"
  12. },
  13. "changed": false,
  14. "ping": "pong"
  15. }
  16. 192.168.34.105 | SUCCESS => {
  17. "ansible_facts": {
  18. "discovered_interpreter_python": "/usr/bin/python"
  19. },
  20. "changed": false,
  21. "ping": "pong"
  22. }

3、Command 模块

(1)介绍

命令模块接受命令名称,后面是空格分隔的列表参数。给定的命令将在所有选定的节点上执行,(此时command模块是默认模块,可忽略-m选项)。

不会通过shell进行处理,比如$HOME和操作如"小于"<",">", "|", ";","&"' 工作(需要使用(shell)模块实现这些功能)。

(2)选项

  1. chdir # 在执行命令之前,先切换到该目录
  2. creates # 一个文件名,当这个文件存在,则该命令不执行,可以用来做判断
  3. removes # 一个文件名,这个文件不存在,则该命令不执行,与creates相反的判断
  4. executable # 切换shell来执行命令,需要使用命令的绝对路径(不常用,常用下面shell 模块)
  5. free_form # 要执行的Linux指令,一般使用Ansible的-a参数代替(不常用,常用下面shell 模块)

(3)实例

ansible webs -m command -a 'chdir=/data ls'

  1. [root@ansibaledata]#ansible webs -m command -a "chdir=/data ls" 可以切换到data目录下执行ls命令
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. f1
  4.  
  5. 192.168.34.102 | CHANGED | rc=0 >>
  6. f2
  7. lost+found

ansible webs -m command -a 'creates=/data/f1 touch /data/f2'

  1. [root@ansibaledata]#ansible webs -m command -a "creates=/data/f1 touch /data/f1" #在webs组主机里,如果两个主机data下都有f1,就不会在data下创建f1
  2. [WARNING]: Consider using the file module with state=touch rather than running 'touch'. If you need to use command
  3. because file is insufficient you can add 'warn: false' to this command task or set 'command_warnings=False' in
  4. ansible.cfg to get rid of this message.
  5.  
  6. 192.168.34.102 | CHANGED | rc=0 >>
  7.  
  8. 192.168.34.103 | SUCCESS | rc=0 >>
  9. skipped, since /data/f1 exists
  10.  
  11. [root@ansibaledata]#ansible webs -m command -a "chdir=/data ls" #IP102的主机data下没有f1,就会创建f1.
  12. 192.168.34.102 | CHANGED | rc=0 >>
  13. f1
  14. f2
  15. lost+found
  16.  
  17. 192.168.34.103 | CHANGED | rc=0 >>
  18. f1

ansible webs -m command -a 'removes=/data/f1 touch /data/f2'   data下有f1文件就会创建f2文件

  1. [root@ansibaledata]#ansible webs -a "removes=/data/f1 touch /data/f2" #如果有f1文件就会进行创建f2
  2. [WARNING]: Consider using the file module with state=touch rather than running 'touch'. If you need to use command
  3. because file is insufficient you can add 'warn: false' to this command task or set 'command_warnings=False' in
  4. ansible.cfg to get rid of this message.
  5.  
  6. 192.168.34.102 | CHANGED | rc=0 >>
  7.  
  8. 192.168.34.103 | CHANGED | rc=0 >>
  9.  
  10. [root@ansibaledata]#ansible webs -a "chdir=/data/ ls" 查询之前有f1,此时已经查到创建f2的结果
  11. 192.168.34.102 | CHANGED | rc=0 >>
  12. f1
  13. f2
  14.  
  15. 192.168.34.103 | CHANGED | rc=0 >>
  16. f1
  17. f2

4、shell 模块

shell模块在远程主机上调用shell解释器运行命令,支持shell的各种功能,例如管道、echo等

在配置文件中将模块进行修改,就不需要输入-m shell选项,修改位置:

  1. vim /etc/ansible/ansible.cfg
  2.  
  3. module_name = shell

(1)实例:

ansible webs -m shell -a 'cat /etc/passwd |grep root'

  1. [root@ansibaledata]#ansible webs -m shell -a "getent passwd | grep root"
  2. 192.168.34.102 | CHANGED | rc=0 >>
  3. root:x:0:0:root:/root:/bin/bash
  4. operator:x:11:0:operator:/root:/sbin/nologin
  5.  
  6. 192.168.34.103 | CHANGED | rc=0 >>
  7. root:x:0:0:root:/root:/bin/bash
  8. operator:x:11:0:operator:/root:/sbin/nologin
  9.  
  10. [root@ansibaledata]#ansible webs -a "getent passwd | grep root" 由于是默认的shell模块,不需要加-m shell
  11. 192.168.34.102 | CHANGED | rc=0 >>
  12. root:x:0:0:root:/root:/bin/bash
  13. operator:x:11:0:operator:/root:/sbin/nologin
  14.  
  15. 192.168.34.103 | CHANGED | rc=0 >>
  16. root:x:0:0:root:/root:/bin/bash
  17. operator:x:11:0:operator:/root:/sbin/nologin

5、script 模块

在指定节点运行服务端的脚本

(1)示例,书写脚本:

[root@Ansible ~]#vim test.sh

#/bin/bash

touch /data/test  #创建/data/test

df -h  >> /data/test   #将df内容追加到/data/test文件中

ansible webs -m script -a '/data/test.sh' 在远程被控制的机器执行脚本

ansible webs -m command -a "chdir=/data ls" 查看文件生成

ansible webs -m shell -a "cat /data/test 查看文件内容正确

  1. [root@ansibaledata]#ansible webs -m script -a "/data/test.sh" 通过脚本创建文件及追加文件内容
  2. 192.168.34.102 | CHANGED => {
  3. "changed": true,
  4. "rc": 0,
  5. "stderr": "Shared connection to 192.168.34.102 closed.\r\n",
  6. "stderr_lines": [
  7. "Shared connection to 192.168.34.102 closed."
  8. ],
  9. "stdout": "",
  10. "stdout_lines": []
  11. }
  12. 192.168.34.103 | CHANGED => {
  13. "changed": true,
  14. "rc": 0,
  15. "stderr": "Shared connection to 192.168.34.103 closed.\r\n",
  16. "stderr_lines": [
  17. "Shared connection to 192.168.34.103 closed."
  18. ],
  19. "stdout": "",
  20. "stdout_lines": []
  21. }
  22. [root@ansibaledata]#ansible webs -m command -a "chdir=/data/ cat test" 查询test文件内容
  23. 192.168.34.102 | CHANGED | rc=0 >>
  24. Filesystem Size Used Avail Use% Mounted on
  25. /dev/sda2 96G 913M 91G 1% /
  26. tmpfs 743M 0 743M 0% /dev/shm
  27. /dev/sda1 976M 33M 892M 4% /boot
  28. /dev/sda3 48G 52M 46G 1% /data
  29.  
  30. 192.168.34.103 | CHANGED | rc=0 >>
  31. Filesystem Size Used Avail Use% Mounted on
  32. /dev/sda2 100G 1.2G 99G 2% /
  33. devtmpfs 791M 0 791M 0% /dev
  34. tmpfs 802M 0 802M 0% /dev/shm
  35. tmpfs 802M 9.6M 792M 2% /run
  36. tmpfs 802M 0 802M 0% /sys/fs/cgroup
  37. /dev/sda3 50G 33M 50G 1% /data
  38. /dev/sda1 1014M 127M 888M 13% /boot
  39. tmpfs 161M 0 161M 0% /run/user/0

6、copy模块

copy:复制文件到远程主机,可以改权限等

(1)用法:

① 复制文件

-a "src= dest= "

② 给定内容生成文件

-a "content= dest= "

(2)相关选项如下:

  1. src:源,被复制到远程主机的本地文件,可以是绝对路径,也可以是相对路径。如果路径是一个目录,它将递归复制。在这种情况下,如果路径使用“/”来结尾,则只复制目录里的内容,如果没有使用“/”来结尾,则包含目录在内的整个内容全部复制,类似于rsync
  2. dest:目标,必选项。要将源文件复制到的远程主机的绝对路径,如果源文件是一个目录,那么该路径也必须是个目录
  3. backup:被管理的远程主机已经有文件了,在覆盖之前,将源文件备份,备份文件包含时间信息。有两个选项:yes|no
  4. content:用于替代“src”,可以直接设定指定文件的值
  5. directory_mode:递归设定目录的权限,默认为系统默认权限
  6. force:如果目标主机包含该文件,但内容不同,如果设置为yes,则强制覆盖,如果为no,则只有当目标主机的目标位置不存在该文件时,才复制。默认为yes
  7. others:所有的file模块里的选项都可以在这里使用

示例:

  1. [root@ansibaledata]#ansible all -m copy -a "src=/etc/issue dest=/data/fstab owner=nobody mode=600 backup=yes" src(源)/etc/issue文件复制到dest(目标)的data目录下,起名叫fstab,所有者为nobody,权限为600,如果有此文件,进行备份。
  2. 192.168.34.102 | CHANGED => {
  3. "ansible_facts": {
  4. "discovered_interpreter_python": "/usr/bin/python"
  5. },
  6. "backup_file": "/data/fstab.23704.2019-11-04@15:19:19~",
  7. "changed": true,
  8. "checksum": "5c76e3b565c91e21bee303f15c728c71e6b39540",
  9. "dest": "/data/fstab",
  10. "gid": 0,
  11. "group": "root",
  12. "md5sum": "f078fe086dfc22f64b5dca2e1b95de2c",
  13. "mode": "0600",
  14. "owner": "nobody",
  15. "size": 23,
  16. "src": "/root/.ansible/tmp/ansible-tmp-1572851957.62-86571596767189/source",
  17. "state": "file",
  18. "uid": 99
  19. }
  20. 192.168.34.103 | CHANGED => {
  21. "ansible_facts": {
  22. "discovered_interpreter_python": "/usr/bin/python"
  23. },
  24. "backup_file": "/data/fstab.21512.2019-11-04@23:19:19~",
  25. "changed": true,
  26. "checksum": "5c76e3b565c91e21bee303f15c728c71e6b39540",
  27. "dest": "/data/fstab",
  28. "gid": 0,
  29. "group": "root",
  30. "md5sum": "f078fe086dfc22f64b5dca2e1b95de2c",
  31. "mode": "0600",
  32. "owner": "nobody",
  33. "size": 23,
  34. "src": "/root/.ansible/tmp/ansible-tmp-1572851957.67-211672525698804/source",
  35. "state": "file",
  36. "uid": 99
  37. }
  38. 192.168.34.105 | CHANGED => {
  39. "ansible_facts": {
  40. "discovered_interpreter_python": "/usr/bin/python"
  41. },
  42. "backup_file": "/data/fstab.5430.2019-11-04@15:19:17~",
  43. "changed": true,
  44. "checksum": "5c76e3b565c91e21bee303f15c728c71e6b39540",
  45. "dest": "/data/fstab",
  46. "gid": 0,
  47. "group": "root",
  48. "md5sum": "f078fe086dfc22f64b5dca2e1b95de2c",
  49. "mode": "0600",
  50. "owner": "nobody",
  51. "size": 23,
  52. "src": "/root/.ansible/tmp/ansible-tmp-1572851957.69-65920362365645/source",
  53. "state": "file",
  54. "uid": 99
  55. }
  56. [root@ansibaledata]#ansible all -m shell -a "ls -l /data/" 查看复制后的结果。
  57. 192.168.34.102 | CHANGED | rc=0 >>
  58. total 12
  59. -rw-r--r-- 1 root root 0 Nov 4 14:35 f1
  60. -rw-r--r-- 1 root root 0 Nov 4 14:35 f2
  61. -rw------- 1 nobody root 23 Nov 4 15:19 fstab
  62. -rw------- 1 nobody root 595 Nov 4 15:16 fstab.23704.2019-11-04@15:19:19~ 此文件为备份文件
  63. -rw-r--r-- 1 root root 224 Nov 4 14:58 test
  64.  
  65. 192.168.34.105 | CHANGED | rc=0 >>
  66. total 20
  67. -rw------- 1 nobody root 23 Nov 4 15:19 fstab
  68. -rw------- 1 nobody root 595 Nov 4 15:16 fstab.5430.2019-11-04@15:19:17~ 此文件为备份文件
  69. drwxr-xr-x 7 root root 4096 Oct 29 15:51 fulliso
  70. drwxr-xr-x 4 root root 4096 Oct 29 14:17 iso
  71. -rw-r--r-- 1 root root 1400 Oct 30 20:14 ks7_mini.cfg
  72.  
  73. 192.168.34.103 | CHANGED | rc=0 >>
  74. total 12
  75. -rw-r--r-- 1 root root 0 Nov 4 22:35 f1
  76. -rw-r--r-- 1 root root 0 Nov 4 22:35 f2
  77. -rw------- 1 nobody root 23 Nov 4 23:19 fstab
  78. -rw------- 1 nobody root 595 Nov 4 23:16 fstab.21512.2019-11-04@23:19:19~ 此文件为备份文件
  79. -rw-r--r-- 1 root root 413 Nov 4 22:58 test

copy复制目录: 

  1. [root@ansibaledata]#ansible webs -m copy -a "src=/data dest=/data/newdata" 复制/data/下的目录,并起名叫newdata
  2. 192.168.34.102 | CHANGED => {
  3. "changed": true,
  4. "dest": "/data/newdata/",
  5. "src": "/data"
  6. }
  7. 192.168.34.103 | CHANGED => {
  8. "changed": true,
  9. "dest": "/data/newdata/",
  10. "src": "/data"
  11. }
  12. [root@ansibaledata]#ansible webs -m shell -a "ls -l /data/"
  13. 192.168.34.102 | CHANGED | rc=0 >>
  14. total 16
  15. drwxr-xr-x 3 root root 4096 Nov 4 15:27 newdata
  16. -rw-r--r-- 1 root root 224 Nov 4 14:58 test
  17.  
  18. 192.168.34.103 | CHANGED | rc=0 >>
  19. total 12
  20. drwxr-xr-x 3 root root 18 Nov 4 23:27 newdata
  21. -rw-r--r-- 1 root root 413 Nov 4 22:58 test

content用法:

  1. [root@ansibaledata]#ansible all -m copy -a 'content="[test]\nbaseurl=file:///mnt\ngpgcheck=0" dest=/etc/yum.repos.d/test.repo' 对被控制端进行新建yum源,并起名叫test.repo
  2. [root@ansibaledata]#ansible all -m shell -a "ls /etc/yum.repos.d/" 查看新建的yum源文件
  3. 192.168.34.103 | CHANGED | rc=0 >>
  4. test.repo
  5.  
  6. 192.168.34.102 | CHANGED | rc=0 >>
  7. test.repo
  8.  
  9. 192.168.34.105 | CHANGED | rc=0 >>
  10. base.repo
  11. test.repo
  12.  
  13. [root@ansibaledata]#ansible all -m shell -a "cat /etc/yum.repos.d/test.repo" 查询新建的yum源文件内容
  14. 192.168.34.102 | CHANGED | rc=0 >>
  15. [test]
  16. baseurl=file:///mnt
  17. gpgcheck=0
  18.  
  19. 192.168.34.103 | CHANGED | rc=0 >>
  20. [test]
  21. baseurl=file:///mnt
  22. gpgcheck=0
  23.  
  24. 192.168.34.105 | CHANGED | rc=0 >>
  25. [test]
  26. baseurl=file:///mnt
  27. gpgcheck=0

7、fetch 模块

(1)介绍

从远程某主机获取文件到本地

dest:用来存放文件的目录,例如存放目录为backup,源文件名称为/etc/profile

  在主机pythonserver中,那么保存为/backup/pythonserver/etc/profile

Src:在远程拉取的文件,并且必须是一个file,不能是目录

注意:从远程获取到本地的文件,会保存到以远程主机的IP 为名的目录中,且保存目录结构

示例:

  1. [root@ansibaledata]#ansible webs -m fetch -a "src=/etc/hosts dest=/data" 将远处的/etc/hosts文件复制到本机的/data/目录下
  2. [root@ansibaledata]#ll 复制的文件目录以IP地址形式显示
  3. total 48
  4. -rw-r---w- 1 root root 90 Nov 3 22:05 1
  5. drwxr-xr-x 3 root root 17 Nov 4 15:43 192.168.34.102
  6. drwxr-xr-x 3 root root 17 Nov 4 15:43 192.168.34.103
  7. [root@ansibaledata]#tree 查看复制过来的文件
  8. .
  9. ├── 1
  10. ├── 192.168.34.102
  11.    └── etc
  12.    └── hosts
  13. ├── 192.168.34.103
  14.    └── etc
  15.    └── hosts
  1. [root@ansibaledata]#ansible webs -m shell -a "tar -cvf /root/data.tar /data" 可以将data目录下的文件打包到root下起名叫data.tar 打包之后就可以用fetch复制此打包文件。
  2. [WARNING]: Consider using the unarchive module rather than running 'tar'. If you need to use command because
  3. unarchive is insufficient you can add 'warn: false' to this command task or set 'command_warnings=False' in
  4. ansible.cfg to get rid of this message.
  5.  
  6. [root@ansibaledata]#ansible webs -m shell -a "ls -l /root/" 查看root下的打包文件
  7. 192.168.34.102 | CHANGED | rc=0 >>
  8. total 68
  9. -rw-------. 1 root root 1125 Nov 2 23:04 anaconda-ks.cfg
  10. -rw-r--r-- 1 root root 30720 Nov 4 15:50 data.tar
  11. -rw-r--r--. 1 root root 16911 Nov 2 23:04 install.log
  12. -rw-r--r--. 1 root root 5820 Nov 2 23:03 install.log.syslog
  13. -rw-r--r-- 1 root root 420 Nov 4 14:56 test
  14.  
  15. 192.168.34.103 | CHANGED | rc=0 >>
  16. total 44
  17. -rw-------. 1 root root 1636 Nov 3 07:08 anaconda-ks.cfg
  18. -rw-r--r-- 1 root root 30720 Nov 4 23:50 data.tar
  19. -rw-------. 1 root root 1385 Nov 3 07:08 original-ks.cfg
  20. -rw-r--r-- 1 root root 740 Nov 4 22:56 test

8、file 模块

设置文件属性

创建目录:-a "path= state=directory"

创建链接文件:-a "path= src= state=link"

删除文件:-a "path= state=absent"

(1)选项

(2)实例:

① ansible webs -m file -a "path=/data/f4 state=directory" 在被控制端,创建f4 目录

  1. force:需要在两种情况下强制创建软链接,一种是源文件不存在,但之后会建立的情况下;另一种是目标软链接已存在,需要先取消之前的软链,然后创建新的软链,有两个选项:yes|no
  2. group:定义文件/目录的属组 mode:定义文件/目录的权限
  3. owner:定义文件/目录的属主 path:必选项,定义文件/目录的路径
  4. recurse:递归设置文件的属性,只对目录有效 src:被链接的源文件路径,只应用于state=link的情况
  5. dest:被链接到的路径,只应用于state=link的情况
  6. state=:
  7.   directory:如果目录不存在,就创建目录
  8.   file:即使文件不存在,也不会被创建
  9.   link:创建软链接
  10.   hard:创建硬链接
  11.   touch:如果文件不存在,则会创建一个新的文件,如果文件或目录已存在,则更新其最后修改时间
  12.   absent:删除目录、文件或者取消链接文件

ansible webs -m command -a "chdir=/data ls" 查看/data 目录

  1. [root@ansibaledata]#ansible webs -m file -a "path=/data/f4 state=directory" data目录下新建f4目录
  2. [root@ansibaledata]#ansible webs -m command -a "chdir=/data ls -l" 查询新建的结果
  3. 192.168.34.102 | CHANGED | rc=0 >>
  4. total 20
  5. -rw-r--r-- 1 root root 0 Nov 4 14:35 f1
  6. -rw-r--r-- 1 root root 0 Nov 4 14:35 f2
  7. drwxr-xr-x 2 root root 4096 Nov 4 16:12 f4 新建的f4目录
  8.  
  9. 192.168.34.103 | CHANGED | rc=0 >>
  10. total 12
  11. -rw-r--r-- 1 root root 0 Nov 4 22:35 f1
  12. -rw-r--r-- 1 root root 0 Nov 4 22:35 f2
  13. drwxr-xr-x 2 root root 6 Nov 5 00:12 f4 新建的f4目录

(3)示例:

删除目录下的文件

ansible webs -m file -a "path=/data/f4 state=absent" 删除data目录下的f4

ansible webs -m file -a "path=/data/ state=absent"  删除data目录下的文件

  1. [root@ansibaledata]#ansible webs -m file -a "path=/data/f4 state=absent" 删除data目录下的f4
  2. [root@ansibaledata]#ansible webs -m command -a "chdir=/data ls -l" 查看此时data目录下已经没有f4目录
  3. 192.168.34.102 | CHANGED | rc=0 >>
  4. total 16
  5. -rw-r--r-- 1 root root 0 Nov 4 14:35 f1
  6. -rw-r--r-- 1 root root 0 Nov 4 14:35 f2
  7.  
  8. 192.168.34.103 | CHANGED | rc=0 >>
  9. total 12
  10. -rw-r--r-- 1 root root 0 Nov 4 22:35 f1
  11. -rw-r--r-- 1 root root 0 Nov 4 22:35 f2

(4)示例;

创建软链接和硬链接

ansible webs -m file -a "src=/data/fstab path=/data/fstab.link state=link"    将/data/fstab 创建软链接为/data/fstab.link

ansible webs -m file -a "src=/data/fstab path=/data/fstab1.link state=hard" 将/data/fstab创建硬链接为/data/fstab1.link

1、创建软链接:

  1. [root@ansibaledata]#ansible webs -m file -a "src=/data/fstab path=/data/fstab.link state=link"
  2. 192.168.34.102 | CHANGED => {
  3. [root@ansibaledata]#ansible webs -m shell -a "ls -l /data/"
  4. 192.168.34.102 | CHANGED | rc=0 >>
  5. total 16
  6.  
  7. lrwxrwxrwx 1 root root 11 Nov 4 16:24 fstab.link -> /data/fstab 创建成功的软链接
  8.  
  9. 192.168.34.103 | CHANGED | rc=0 >>
  10. total 12
  11.  
  12. lrwxrwxrwx 1 root root 11 Nov 5 00:24 fstab.link -> /data/fstab 创建成功的软链接

2、创建硬链接: 

  1. [root@ansibaledata]#ansible webs -m file -a "src=/data/fstab path=/data/fstab1.link state=hard"
  2. [root@ansibaledata]#ansible webs -m shell -a "ls -l /data/"
  3. 192.168.34.102 | CHANGED | rc=0 >>
  4. total 20
  5. -rw------- 2 nobody root 23 Nov 4 15:19 fstab
  6. -rw------- 2 nobody root 23 Nov 4 15:19 fstab1.link
  7.  
  8. 192.168.34.103 | CHANGED | rc=0 >>
  9. total 16
  10. -rw------- 2 nobody root 23 Nov 4 23:19 fstab
  11. -rw------- 2 nobody root 23 Nov 4 23:19 fstab1.link

9、hostname:管理主机名

示例:

ansible 192.168.34.102 -m hostname -a "name=centos102" 修改为centos102

ansible 192.168.34.102 -a "hostname" 查看当前修改后的主机名

  1. [root@ansibaledata]#ansible 192.168.34.102 -m hostname -a "name=centos102"
  2. 192.168.34.102 | CHANGED => {
  3. "ansible_facts": {
  4. "ansible_domain": "",
  5. "ansible_fqdn": "centos102",
  6. "ansible_hostname": "centos102",
  7. "ansible_nodename": "centos102",
  8. "discovered_interpreter_python": "/usr/bin/python"
  9. },
  10. "changed": true,
  11. "name": "centos102"
  12. }
  13. [root@ansibaledata]#ansible 192.168.34.102 -a "hostname"
  14. 192.168.34.102 | CHANGED | rc=0 >>
  15. centos102  

10、cron 模块

管理cron计划任务;-a "": 设置管理节点生成定时任务

(1)选项:

  1. action:
  2. cron backup= #如果设置,创建一个crontab备份 【yes|no】
  3. cron_file= #如果指定, 使用这个文件cron.d,而不是单个用户
  4. crontab
  5.   day= #日应该运行的工作( 1-31, *, */2, )
  6.   hour= # 小时 ( 0-23, *, */2, )
  7.   minute= #分钟( 0-59, *, */2, )
  8.   month= #月( 1-12, *, /2, )
  9.   weekday # 周 ( 0-6 for Sunday-Saturday,, )
  10.   job= #指明运行的命令是什么
  11.   name= #定时任务描述
  12.   reboot # 任务在重启时运行,不建议使用,建议使用special_time
  13.   special_time #特殊的时间范围,参数:reboot(重启时),annually(每年),monthly(每月),weekly(每周),daily(每天),hourly(每小时)
  14.   state #指定状态,present表示添加定时任务,也是默认设置,absent表示删除定时任务
  15.   user #以哪个用户的身份执行 

(1)示例:

开启计划任务:

  1. [root@ansibaledata]#ansible webs -m cron -a "minute=*/5 weekday=0,6 job="/usr/sbin/update 192.168.34.101 &> /dev/null" name=synctime" 只在周六周日每五分钟将时间与192.168.34.101进行同步,起名叫synctime
  2. [root@ansibaledata]#ansible webs -a "crontab -l"查询当前执行的任务结果。

禁用计划任务:

  1. [root@ansibaledata]#ansible webs -m cron -a "minute=*/5 weekday=0,6 job="/usr/sbin/update 192.168.34.101 &> /dev/null" name=synctime disabled=ture" 只在周六周日每五分钟将时间与192.168.34.101进行同步计划任务进行禁用
  2. [root@ansibaledata]#ansible webs -a "crontab -l"查询当前执行的任务结果。

(2)示例:

在远程主机上,定义每5分钟,清空一次防火墙

① ansible web -m cron -a "name='Clear the iptable' minute=*/5 job='/sbin/iptables -F'"

ansible web -m shell -a "crontab -l" 查看

  1. [root@ansibaledata]#ansible webs -m cron -a "name='Clean the iptable' minute=*/5 job='/sbin/iptables -F &> /dev/full'"
  2. 192.168.34.102 | CHANGED => {
  3. "ansible_facts": {
  4. "discovered_interpreter_python": "/usr/bin/python"
  5. },
  6. "changed": true,
  7. "envs": [],
  8. "jobs": [
  9. "Clean the iptable"
  10. ]
  11. }
  12. 192.168.34.103 | CHANGED => {
  13. "ansible_facts": {
  14. "discovered_interpreter_python": "/usr/bin/python"
  15. },
  16. "changed": true,
  17. "envs": [],
  18. "jobs": [
  19. "Clean the iptable"
  20. ]
  21. }
  22. [root@ansibaledata]#ansible webs -a "crontab -l"
  23. 192.168.34.102 | CHANGED | rc=0 >>
  24. #Ansible: Clean the iptable
  25. */5 * * * * /sbin/iptables -F
  26.  
  27. 192.168.34.103 | CHANGED | rc=0 >>
  28. #Ansible: Clean the iptable
  29. */5 * * * * /sbin/iptables -F

(3)启动当前的计划任务 

  1. [root@ansibaledata]#ansible webs -m cron -a "name='Clean the iptable' minute=*/5 job='/sbin/iptables -F disabled=false'" 开启当前的计划任务,起名叫Clean the iptable
  2. 192.168.34.102 | CHANGED => {
  3. "ansible_facts": {
  4. "discovered_interpreter_python": "/usr/bin/python"
  5. },
  6. "changed": true,
  7. "envs": [],
  8. "jobs": [
  9. "Clean the iptable"
  10. ]
  11. }
  12. 192.168.34.103 | CHANGED => {
  13. "ansible_facts": {
  14. "discovered_interpreter_python": "/usr/bin/python"
  15. },
  16. "changed": true,
  17. "envs": [],
  18. "jobs": [
  19. "Clean the iptable"
  20. ]
  21. }
  22. [root@ansibaledata]#ansible webs -a "crontab -l"
  23. 192.168.34.102 | CHANGED | rc=0 >>
  24. #Ansible: Clean the iptable
  25. */5 * * * * /sbin/iptables -F disabled=false 开启结果
  26.  
  27. 192.168.34.103 | CHANGED | rc=0 >>
  28. #Ansible: Clean the iptable
  29. */5 * * * * /sbin/iptables -F disabled=false

(4)删除计划任务:

  1. [root@ansibaledata]#ansible webs -m cron -a "name='Clean the iptable' state=absent" 删除计划任务,只需要将对应的计划任务名称删掉即可。
  2. 192.168.34.102 | CHANGED => {
  3. "ansible_facts": {
  4. "discovered_interpreter_python": "/usr/bin/python"
  5. },
  6. "changed": true,
  7. "envs": [],
  8. "jobs": []
  9. }
  10. 192.168.34.103 | CHANGED => {
  11. "ansible_facts": {
  12. "discovered_interpreter_python": "/usr/bin/python"
  13. },
  14. "changed": true,
  15. "envs": [],
  16. "jobs": []
  17. }
  18. [root@ansibaledata]#ansible webs -a "crontab -l" 查询结果,此时已经没有计划任务
  19. 192.168.34.102 | CHANGED | rc=0 >>
  20.  
  21. 192.168.34.103 | CHANGED | rc=0 >>

11、yum 模块

(1)选项

  1. conf_file #设定远程yum安装时所依赖的配置文件。如配置文件没有在默认的位置。
  2. disable_gpg_check #是否禁止GPG checking,只用于`present‘ or `latest’。
  3. disablerepo #临时禁止使用yum库。 只用于安装或更新时。
  4. enablerepo #临时使用的yum库。只用于安装或更新时。
  5. name= #所安装的包的名称
  6. state= #present安装, latest安装最新的, absent 卸载软件。
  7. update_cache #强制更新yum的缓存。

(2)示例

①i安装dstat 包,忽略gpg_check

ansible webs -m yum -a "name=dstat "

卸载dstat 包

ansible webs -m yum -a "name=dstat state=absent"

安装多个包:

ansible webs  -m yum -a "name=httpd,vsftpd,memacahe"

卸载多个包;

ansible webs  -m yum -a "name=httpd,vsftpd,memacahe,state=absent"

  1. [root@ansibaledata]#ansible webs -m yum -a "name=dstat" 安装dstat
  2. 192.168.34.102 | CHANGED => {
  3. "ansible_facts": {
  4. "discovered_interpreter_python": "/usr/bin/python"
  5. },
  6. "changed": true,
  7. "changes": {
  8. "installed": [
  9. "dstat"
  10. ]
  11. },
  12. "msg": "Repository 'base' is missing name in configuration, using id\n",
  13. "rc": 0,
  14. "results": [
  15. "Loaded plugins: fastestmirror, security\nSetting up Install Process\nLoading mirror speeds from cached hostfile\nResolving Dependencies\n--> Running transaction check\n---> Package dstat.noarch 0:0.7.0-3.el6 will be installed\n--> Finished Dependency Resolution\n\nDependencies Resolved\n\n================================================================================\n Package Arch Version Repository Size\n================================================================================\nInstalling:\n dstat noarch 0.7.0-3.el6 base 146 k\n\nTransaction Summary\n================================================================================\nInstall 1 Package(s)\n\nTotal download size: 146 k\nInstalled size: 665 k\nDownloading Packages:\nRunning rpm_check_debug\nRunning Transaction Test\nTransaction Test Succeeded\nRunning Transaction\n\r Installing : dstat-0.7.0-3.el6.noarch 1/1 \n\r Verifying : dstat-0.7.0-3.el6.noarch 1/1 \n\nInstalled:\n dstat.noarch 0:0.7.0-3.el6 \n\nComplete!\n"
  16. ]
  17. }
  18. 192.168.34.103 | CHANGED => {
  19. "ansible_facts": {
  20. "discovered_interpreter_python": "/usr/bin/python"
  21. },
  22. "changed": true,
  23. "changes": {
  24. "installed": [
  25. "dstat"
  26. ]
  27. },
  28. "msg": "Repository 'base' is missing name in configuration, using id\n",
  29. "rc": 0,
  30. "results": [
  31. "Loaded plugins: fastestmirror\nLoading mirror speeds from cached hostfile\nResolving Dependencies\n--> Running transaction check\n---> Package dstat.noarch 0:0.7.2-12.el7 will be installed\n--> Finished Dependency Resolution\n\nDependencies Resolved\n\n================================================================================\n Package Arch Version Repository Size\n================================================================================\nInstalling:\n dstat noarch 0.7.2-12.el7 base 163 k\n\nTransaction Summary\n================================================================================\nInstall 1 Package\n\nTotal download size: 163 k\nInstalled size: 752 k\nDownloading packages:\nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n Installing : dstat-0.7.2-12.el7.noarch 1/1 \n Verifying : dstat-0.7.2-12.el7.noarch 1/1 \n\nInstalled:\n dstat.noarch 0:0.7.2-12.el7 \n\nComplete!\n"
  32. ]
  33. }
  34. [root@ansibaledata]#ansible webs -a "rpm -q dstat" 查看此包是否安装成功
  35. [WARNING]: Consider using the yum, dnf or zypper module rather than running 'rpm'. If you need to use command
  36. because yum, dnf or zypper is insufficient you can add 'warn: false' to this command task or set
  37. 'command_warnings=False' in ansible.cfg to get rid of this message.
  38.  
  39. 192.168.34.102 | CHANGED | rc=0 >>
  40. dstat-0.7.0-3.el6.noarch
  41.  
  42. 192.168.34.103 | CHANGED | rc=0 >>
  43. dstat-0.7.2-12.el7.noarch
  44.  
  45. [root@ansibaledata]#ansible webs -m yum -a "name=dstat state=absent" 卸载dstat
  46. [root@ansibaledata]#ansible webs -a "rpm -q dstat" 查看当前的包是否还存在
  47. [WARNING]: Consider using the yum, dnf or zypper module rather than running 'rpm'. If you need to use command
  48. because yum, dnf or zypper is insufficient you can add 'warn: false' to this command task or set
  49. 'command_warnings=False' in ansible.cfg to get rid of this message.
  50.  
  51. 192.168.34.102 | FAILED | rc=1 >>
  52. package dstat is not installednon-zero return code
  53.  
  54. 192.168.34.103 | FAILED | rc=1 >>
  55. package dstat is not installednon-zero return code

(3)示例:

ansible webs -m yum -a "name=dstat update_cache=yes"  更新缓存

12、service 模块

服务程序管理

(1)选项

  1. arguments #命令行提供额外的参数
  2. enabled #设置开机启动。
  3. name= #服务名称
  4. runlevel #开机启动的级别,一般不用指定。
  5. sleep #在重启服务的过程中,是否等待。如在服务关闭以后等待2秒再启动。
  6. state #started启动服务, stopped停止服务, restarted重启服务, reloaded重载配置

(2)实例

1、远程安装httpd服务

ansible all -m yum -a "name=httpd"

2、远程开启httpd服务:

ansible all -m service -a "name=httpd state=started"  远程操作开启服务

ansible all -m service -a "name=httpd state=enabled" 开机设置启动服务

  1. [root@ansibaledata]#ansible all -m yum -a "name=httpd" 安装http服务
  2. [root@ansibaledata]#ansible all -m service -a "name=httpd state=started" 打开http服务端口
  3. [root@ansibaledata]#ansible all -a "ss -nlt" 查看当前的服务端口
  4. 192.168.34.102 | CHANGED | rc=0 >>
  5. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  6. LISTEN 0 128 :::80 :::*
  7. LISTEN 0 128 :::22 :::*
  8. LISTEN 0 128 *:22 *:*
  9. LISTEN 0 100 ::1:25 :::*
  10. LISTEN 0 100 127.0.0.1:25 *:*
  11.  
  12. 192.168.34.103 | CHANGED | rc=0 >>
  13. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  14. LISTEN 0 128 *:22 *:*
  15. LISTEN 0 100 127.0.0.1:25 *:*
  16. LISTEN 0 128 :::80 :::*
  17. LISTEN 0 128 :::22 :::*
  18. LISTEN 0 100 ::1:25 :::*
  19.  
  20. 192.168.34.105 | CHANGED | rc=0 >>
  21. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  22. LISTEN 0 128 127.0.0.1:6010 *:*
  23. LISTEN 0 128 ::1:6010 :::*
  24. LISTEN 0 128 :::111 :::*
  25. LISTEN 0 128 *:111 *:*
  26. LISTEN 0 128 :::80 :::*
  27. LISTEN 0 128 *:44404 *:*
  28. LISTEN 0 128 :::58453 :::*
  29. LISTEN 0 128 :::22 :::*
  30. LISTEN 0 128 *:22 *:*
  31. LISTEN 0 64 :::23 :::*
  32. LISTEN 0 128 127.0.0.1:631 *:*
  33. LISTEN 0 128 ::1:631 :::*
  34. LISTEN 0 100 ::1:25 :::*
  35. LISTEN 0 100 127.0.0.1:25 *:*

(3)远程关闭服务:

ansible all -m service -a "name=httpd state=stopped"

  1. [root@ansibaledata]#ansible all -m service -a "name=httpd state=stopped" 关闭http服务
  2. [root@ansibaledata]#ansible all -a "ss -nlt" 查此时的80端口已经没有了
  3. 192.168.34.102 | CHANGED | rc=0 >>
  4. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  5. LISTEN 0 128 :::22 :::*
  6. LISTEN 0 128 *:22 *:*
  7. LISTEN 0 100 ::1:25 :::*
  8. LISTEN 0 100 127.0.0.1:25 *:*
  9.  
  10. 192.168.34.103 | CHANGED | rc=0 >>
  11. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  12. LISTEN 0 128 *:22 *:*
  13. LISTEN 0 100 127.0.0.1:25 *:*
  14. LISTEN 0 128 :::22 :::*
  15. LISTEN 0 100 ::1:25 :::*
  16.  
  17. 192.168.34.105 | CHANGED | rc=0 >>
  18. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  19. LISTEN 0 128 127.0.0.1:6010 *:*
  20. LISTEN 0 128 ::1:6010 :::*
  21. LISTEN 0 128 :::111 :::*
  22. LISTEN 0 128 *:111 *:*
  23. LISTEN 0 128 *:44404 *:*
  24. LISTEN 0 128 :::58453 :::*
  25. LISTEN 0 128 :::22 :::*
  26. LISTEN 0 128 *:22 *:*
  27. LISTEN 0 64 :::23 :::*
  28. LISTEN 0 128 127.0.0.1:631 *:*
  29. LISTEN 0 128 ::1:631 :::*
  30. LISTEN 0 100 ::1:25 :::*
  31. LISTEN 0 100 127.0.0.1:25 *:*

13、user 模块

用户模块,管理用户帐号

(1)选项

  1. comment # 用户的描述信息
  2. createhome # 是否创建家目录
  3. force # 在使用state=absent是, 行为与userdel -force一致.
  4. group # 指定基本组
  5. groups # 指定附加组,如果指定为(groups=)表示删除所有组
  6. home # 指定用户家目录
  7. move_home # 如果设置为home=时, 试图将用户主目录移动到指定的目录
  8. name # 指定用户名
  9. non_unique # 该选项允许改变非唯一的用户ID值
  10. password # 指定用户密码,若指定的是明文密码,是不能用的,需用md5加密过后的密码
  11. remove # 在使用state=absent时, 行为是与userdel -remove一致
  12. shell # 指定默认shell
  13. state # 设置帐号状态,不指定为创建,指定值为absent表示删除
  14. system # 当创建一个用户,设置这个用户是系统用户。这个设置不能更改现有用户
  15. uid # 指定用户的uid
  16. update_password # 更新用户密码

示例:

  1. ansible all -m user -a 'name=test comment="test user" uid=200 home=/data/testhome group=root groups=bin,nobody shell=/sbin/nologin'  创建一个test用户的详细信息
  1. ansible all -m user -a "name=test state=absent" 删除用户信息,但是不会删除用户家目录的文件信息
  1. ansible all -a "getent passwd test"  查看当前创建的用户信息
  2. ansiable all -a "name=test state=absent remove=yes"  跟上后面的remove=yes就会删除家目录信息
  1. [root@ansibaledata]#ansible all -m user -a 'name=test comment="test user" uid=200 home=/data/testhome group=root groups=bin,nobody shell=/sbin/nologin' 创建一个test用户的详细信息
  2.  
  3. [root@ansibaledata]#ansible all -a "getent passwd test"
  4. 192.168.34.102 | CHANGED | rc=0 >>
  5. test:x:200:0:test user:/data/testhome:/sbin/nologin
  6.  
  7. 192.168.34.103 | CHANGED | rc=0 >>
  8. test:x:200:0:test user:/data/testhome:/sbin/nologin
  9.  
  10. 192.168.34.105 | CHANGED | rc=0 >>
  11. test:x:200:0:test user:/data/testhome:/sbin/nologin
  12.  
  13. [root@ansibaledata]#ansible all -m user -a "name=test state=absent" 删除用户文件信息
  14. [root@ansibaledata]#ansible all -a "getent passwd test" 查看用户文件信息
  15. 192.168.34.102 | FAILED | rc=2 >>
  16. non-zero return code
  17.  
  18. 192.168.34.103 | FAILED | rc=2 >>
  19. non-zero return code
  20.  
  21. 192.168.34.105 | FAILED | rc=2 >>
  22. non-zero return code

 14、group模块

  1. 1)选项
  2.  
  3. gid # 设置组的GID号
  4. name= # 管理组的名称
  5. state # 指定组状态,默认为创建,设置值为absent为删除
  6. system # 设置值为yes,表示为创建系统组

 (2)示例:

 ansible webs -m group -a "name=testgroup system=yes“  创建系统组
 ansible webs -m group -a "name=testgroup state=absent"  删除组

15、setup 模块

查机器的所有facts信息

(1)介绍

① facts 组件是Ansible 用于采集被管机器设备信息的一个功能,我们可以使用setup 模块查机器的所有facts信息,可以使用filter来查看指定信息。整个facts信息被包装在一个JSON格式的数据结构中,ansible_facts是最上层的值。

② facts就是变量,内建变量 每个主机的各种信息,cpu颗数、内存大小等。会存在facts中的某个变量中。调用后返回很多对应主机的信息,在后面的操作中可以根据不同的信息来做不同的操作。如redhat系列用yum安装,而debian系列用apt来安装软件。

③ setup模块,主要用于获取主机信息,在playbooks里经常会用到的一个参数gather_facts就与该模块相关。

④ setup模块下经常使用的一个参数是filter 参数,查询的是全部信息,很多,filter 相当于匹配筛选。

示例:

(1)查询当前机器的全部信息:

ansible  192.168.34.103  -m setup

(2) 查看当前主机的总内存大小:

ansible all -m setup  -a "filter=ansible_memtotal_mb"  其中filter是过滤的含义。

(3)查看每个主机的centos版本号

ansible all -m setup -a "filter=ansible_distribution_major_version"

实验三:Ansible playbook 的使用

1、介绍

(1)理解

① playbook是ansible用于配置,部署,和管理被控节点的剧本。

② 通过playbook的详细描述,执行其中的一系列tasks,可以让远端主机达到预期的状态。playbook就像Ansible控制器给被控节点列出的的一系列to-do-list,而被控节点必须要完成。

③ 也可以这么理解,playbook 字面意思,即剧本,现实中由演员按照剧本表演,在Ansible中,这次由计算机进行表演,由计算机安装,部署应用,提供对外服务,以及组织计算机处理各种各样的事情

(2)Ansible playbook 使用场景

① 执行一些简单的任务,使用ad-hoc命令可以方便的解决问题,但是有时一个设施过于复杂,需要大量的操作时候,执行的ad-hoc命令是不适合的,这时最好使用playbook。

② 就像执行shell命令与写shell脚本一样,也可以理解为批处理任务,不过playbook有自己的语法格式。

③ 使用playbook你可以方便的重用这些代码,可以移植到不同的机器上面,像函数一样,最大化的利用代码。在你使用Ansible的过程中,你也会发现,你所处理的大部分操作都是编写playbook。可以把常见的应用都编写成playbook,之后管理服务器会变得十分简单。(2)

(2)特性

  1. YAML的可读性好
  2. YAML和脚本语言的交互性好
  3. YAML使用实现语言的数据类型
  4. YAML有一个一致的信息模型
  5. YAML易于实现
  6. YAML可以基于流来处理
  7. YAML表达能力强,扩展性好

2、Ansible playbook 格式

(1)介绍

① playbook由YMAL语言编写。YAML( /ˈjæməl/ )参考了其他多种语言,包括:XML、C语言、Python、Perl以及电子邮件格式RFC2822,Clark Evans在2001年5月在首次发表了这种语言,另外Ingy döt Net与Oren Ben-Kiki也是这语言的共同设计者。

② YMAL格式是类似于JSON的文件格式,便于人理解和阅读,同时便于书写。首先学习了解一下YMAL的格式,对我们后面书写playbook很有帮助。以下为playbook常用到的YMAL格式。

(2)语法介绍

  1. 1、在单一档案中,可用连续三个连字号(---)区分多个档案。另外,还有选择性的连续三个点号( ... )用来表示档案结尾
  2. 2、次行开始正常写Playbook的内容,一般建议写明该Playbook的功能
  3. 3、使用#号注释代码
  4. 4、缩进必须是统一的,不能空格和tab混用
  5. 5、缩进的级别也必须是一致的,同样的缩进代表同样的级别,程序判别配置的级别是通过缩进结合换行来实现的
  6. 6YAML文件内容是区别大小写的,k/v的值均需大小写敏感
  7. 7k/v的值可同行写也可换行写。同行使用:分隔
  8. 8v可是个字符串,也可是另一个列表
  9. 9、一个完整的代码块功能需最少元素需包括 name: task
  10. 10、一个name只能包括一个task
  11. 11YAML文件扩展名通常为ymlyaml

(3)Playbooks 配置文件的基础组件

① hosts:运行指定任务的目标主机;使用hosts指示使用哪个主机或主机组来运行下面的tasks,每个playbook都必须指定hosts,hosts也可以使用通配符格式。主机或主机组在inventory清单中指定,可以使用系统默认的/etc/ansible/hosts,也可以自己编辑,在运行的时候加上-i选项,指定清单的位置即可。在运行清单文件的时候,-list-hosts选项会显示那些主机将会参与执行task的过程中。

② remoute_user: 在远程主机上执行任务的用户;指定远端主机中的哪个用户来登录远端系统,在远端系统执行task的用户,可以任意指定,也可以使用sudo,但是用户必须要有执行相应task的权限。

③ sudo_user:

④ tasks:任务列表;指定远端主机将要执行的一系列动作。tasks的核心为ansible的模块,前面已经提到模块的用法。

  tasks:包含name和要执行的模块name是可选的,只是为了便于用户阅读,不过还是建议加上去,模块是必须的,同时也要给予模块相应的参数

⑤ templates:包含了模板语法的文本文件;

⑥ variables 变量

⑦ handlers:由特定条件触发的任务

(4)注意:shell和command模块后面直接跟命令,而非key=value类的参数列表;

① 某任务的状态在运行后为changed时,可通过"notify"通知给相应的handlers,两个文件名称要一致

② 任务可以通过"tags"打标签,而后可在ansible-playbook命令上使用-t 标签名,指定进行调用;

(5)variables 变量的定义:

① facts:可直接调用;

注意:可使用setup模块直接获取目标主机的facters;

② 用户自定义变量:

(a) ansible-playbook命令的命令行中的

  -e VARS, --extra-vars=VARS

(b) 在playbook中定义变量的方法:

vars:

   - var1: value1

   var2: value2

(6)执行playbook剧本

使用ansible-playbook运行playbook文件,得到如下输出信息,输出内容为JSON格式。并且由不同颜色组成,便于识别。一般而言

 绿色代表执行成功,系统保持原样

 黄色代表系统代表系统状态发生改变

 红色代表执行失败,显示错误输出。

3、playbook剧本书写及运行方式
ansible-playbook <filename.yml> ... [options]
常见选项

  1. --check -C 只检测可能会发生的改变,但不真正执行操作
  2. --list-hosts 列出运行任务的主机
  3. --list-tags 列出tag
  4. --list-tasks 列出task
  5. --limit 主机列表 只针对主机列表中的主机执行
  6. -v -vv -vvv 显示过程

示例

  1. ansible-playbook file.yml --check 只检测
  2. ansible-playbook file.yml
  3. ansible-playbook file.yml --limit websrvs

ansible-playbook示例:

注意:复制的httpd.conf配置文件只能适用于同一版本的httpd配置文件,centos6和centos7不能共用

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4.  
  5. tasks:
  6. - name: create group
  7. group: name=apache system=yes gid=80
  8. - name: create user
  9. user: name=apache group=apache uid=80 shell=/sbin/nonlogin home=/usr/share/httpd system=yes password=$1$TGp21j8c$L3Q8BYFXsCBFt53nmw0t.0
  10. - name: install package
  11. yum: name=httpd
  12. - name: config file
  13. copy: src=/root/playbook/httpd.conf dest=/etc/httpd/conf/ backup=yes
  14. - name: service
  15. service: name=httpd state=started enabled=yes

执行结果:

  1. [root@ansibledata]#ansible-playbook install_httpd.yml 执行此playbook
  2. [root@ansibledata]#ansible webs -a "ss -nlt" 查询当前端口已经开启80端口
  3. 192.168.34.103 | CHANGED | rc=0 >>
  4. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  5. LISTEN 0 128 *:22 *:*
  6. LISTEN 0 100 127.0.0.1:25 *:*
  7. LISTEN 0 128 :::80 :::*
  8. LISTEN 0 128 :::22 :::*
  9. LISTEN 0 100 ::1:25 :::*
  10.  
  11. [root@ansibledata]#ansible webs -a "getent passwd apache" 查询用户账号,已经创建
  12. 192.168.34.103 | CHANGED | rc=0 >>
  13. apache:x:80:80:Apache:/usr/share/httpd:/sbin/nonlogin

(2)在剧本中加入handlers 触发任务

前提背景:如playbook 中有一系列tasks,但有时只需改动少个tasks 就要触发另一个操作;若再把剧本执行一遍,浪费资源和时间;此时可以设置handlers 触发任务

注意:如果执行killall 命令,需要其他机器有该命令才能执行。

vim /data/install_httpd.yml

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4.  
  5. tasks:
  6. - name: create group
  7. group: name=apache system=yes gid=80
  8. - name: create user
  9. user: name=apache group=apache uid=80 shell=/sbin/nonlogin home=/usr/share/httpd system=yes password=$1$TGp21j8c$L3Q8BYFXsCBFt53nmw0t.0
  10. - name: install package
  11. yum: name=httpd
  12. - name: config file
  13. copy: src=/root/playbook/httpd.conf dest=/etc/httpd/conf/ backup=yes
  14. notify:
  15. - restart service
  16. - check httpd
  17. - name: service
  18. service: name=httpd state=started enabled=yes
  19. handlers:
  20. - name: restart service
  21. service: name=httpd state=restarted
  22. - name: check httpd
  23. - shell: /usr/bin/killall -0 httpd &> /tmp/httpd.log

 修改要复制的/data/http.conf配置文件的端口号为81,执行playbook后,就会重启httpd服务,查看当前的端口号就是81

  1. [root@ansibledata]#vim httpd.conf data下要复制的配置文件端口改为81
  2. # prevent Apache from glomming onto all bound IP addresses.
  3. #
  4. #Listen 12.34.56.78:80
  5. Listen 81
  6. [root@ansibledata]#ansible-playbook install_httpd.yml 此时执行playbook,复制过去的端口就是81
  7. [root@ansibledata]#ansible webs -a "ss -nlt" 查看到重启的端口httpd就是81端口
  8. 192.168.34.103 | CHANGED | rc=0 >>
  9. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  10. LISTEN 0 128 *:22 *:*
  11. LISTEN 0 100 127.0.0.1:25 *:*
  12. LISTEN 0 128 :::81 :::*
  13. LISTEN 0 128 :::22 :::*
  14. LISTEN 0 100 ::1:25 :::*

查看当前检测的信号里放置的临时文件没有任何内容,说明执行成功,如果有错误,就会在里边显示错误内容。

(2)tags 标签在playbook中使用:

一个动作可以执行多个标签,也可以多个动作执行多个标签,执行标签动作需要加上-t选项:

ansible-playbook -t config insall.yml  触发一个标签

ansible-playbook -t "config,service" install.yml 触发两个标签

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4.  
  5. tasks:
  6. - name: create group
  7. group: name=apache system=yes gid=80
  8. - name: create user
  9. user: name=apache group=apache uid=80 shell=/sbin/nonlogin home=/usr/share/httpd system=yes password=$1$TGp21j8c$L3Q8BYFXsCBFt53nmw0t.0
  10. - name: install package
  11. yum: name=httpd
  12. - name: config file
  13. copy: src=/data/httpd.conf dest=/etc/httpd/conf/ backup=yes
  14. tags: config,copy 其中一个动作可以标注多个标签,执行configcopy都可以
  15. notify:
  16. - restart service
  17. - check httpd
  18. - name: service
  19. tags: service service标签
  20. service: name=httpd state=started enabled=yes
  21. handlers:
  22. - name: restart service
  23. service: name=httpd state=restarted
  24. - name: check httpd
  25. shell: /usr/bin/killall -0 httpd &> /tmp/httpd.log

我们将要复制的httpd.conf配置文件的端口号改为82,用copy标签执行下面的内容,只会执行下面一个动作,也会执行触发器里边的动作,即nodity和handlers动作

可以看到当前httpd服务启动后的端口号变为82端口。

我们也可以执行多个标签的动作,具体如下操作:

ansible-playbook  -t ""config,service" install.yml

vars变量使用:

(1)变量可以不定义在playbook 中,直接在命令行给出

  1. [root@ansibledata]#vim install_httpd.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6.  
  7. tasks:
  8. - name: install package
  9. yum: name={{ servername }} 使用name变量
  10. - name: service
  11. service: name={{ servername }} state=started enabled=yes

给变量servername赋值,就可以执行相应的动作:其中-e servername=vsftpd 指定当前变量的为vsftpd

ansible-playbook  -e servername=vsftpd install_httpd.yml  将servername赋值为vsftpd,就可以安装此服务,此服务端口为21,已经打开.

执行结果如下:

  1. [root@ansibledata]#ansible-playbook -e name=vsftpd install_httpd.yml
  2. [WARNING]: Found variable using reserved name: name
  3.  
  4. PLAY [webs] **********************************************************************************************************
  5.  
  6. TASK [Gathering Facts] ***********************************************************************************************
  7. ok: [192.168.34.103]
  8.  
  9. TASK [install package] ***********************************************************************************************
  10. ok: [192.168.34.103]
  11.  
  12. TASK [service] *******************************************************************************************************
  13. changed: [192.168.34.103]
  14.  
  15. PLAY RECAP ***********************************************************************************************************
  16. 192.168.34.103 : ok=3 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  17.  
  18. [root@ansibledata]#ansible webs -a "ss -nlt"
  19. 192.168.34.103 | CHANGED | rc=0 >>
  20. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  21. LISTEN 0 128 *:22 *:*
  22. LISTEN 0 100 127.0.0.1:25 *:*
  23. LISTEN 0 128 :::82 :::*
  24. LISTEN 0 32 :::21 21端口打开 :::*
  25. LISTEN 0 128 :::22 :::*
  26. LISTEN 0 100 ::1:25 :::*

(2)赋予两个不同的变量名,servername1为包名,servername2为服务名

  1. [root@ansibledata]#vim install_httpd.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6.  
  7. tasks:
  8. - name: install package
  9. yum: name={{ servername1 }} 赋予一个变量name1,作为包名
  10. - name: service
  11. service: name={{ servername2 }} state=started enabled=yes 启动name2,服务名

将servername1赋予包名,servername2赋予服务名

ansible-playbook  -e "servername1=samba servername2=smb' install_httpd.yml

执行结果如下:

  1. [root@ansibledata]#ansible-playbook -e "servername1=samba servername2=smb" install_httpd.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [install package] ***********************************************************************************************
  9. changed: [192.168.34.103]
  10.  
  11. TASK [service] *******************************************************************************************************
  12. changed: [192.168.34.103]
  13.  
  14. PLAY RECAP ***********************************************************************************************************
  15. 192.168.34.103 : ok=3 changed=2 unreachable=0 failed=0 skipped=0 rescued=0

(3)也可以直接定义在playbook 中:

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4. vars:
  5. - servername1: samba 定义在playbook内容中
  6. - servername2: smb
  7. tasks:
  8. - name: install package
  9. yum: name={{ servername1 }}
  10. - name: service
  11. service: name={{ servername2 }} state=started enabled=yes

执行成功结果:

 

(4)在独立的变量YAML文件中定义(推荐使用此方法)

新建一个vars.yml文件,指定存放要执行的变量,servername: httpd

  1. [root@ansibleplaybook]#vim vars.yml
  2.  
  3. servername: httpd

将写好的变量文件赋予到此playbook内容中

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4. vars_files: 定义一个vars.yml文件
  5. - vars.yml
  6.  
  7. tasks:
  8. - name: install package
  9. yum: name={{ servername }}
  10. - name:
  11. service: name={{ servername }} state=started enabled=yes

执行结果:

  1. [root@ansibleplaybook]#ansible-playbook test.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.102]
  7. ok: [192.168.34.103]
  8.  
  9. TASK [install] *******************************************************************************************************
  10. ok: [192.168.34.103]
  11. ok: [192.168.34.102]
  12.  
  13. TASK [config file] ***************************************************************************************************
  14. ok: [192.168.34.103]
  15. ok: [192.168.34.102]
  16.  
  17. TASK [service] *******************************************************************************************************
  18. ok: [192.168.34.102]
  19. ok: [192.168.34.103]
  20.  
  21. PLAY RECAP ***********************************************************************************************************
  22. 192.168.34.102 : ok=4 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  23. 192.168.34.103 : ok=4 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0

ansible  webs -a "ss -nlt"  可以查看到当前的80端口已经安装好

  1. [root@ansibleplaybook]#ansible webs -a "ss -nlt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:*
  5. LISTEN 0 128 *:22 *:*
  6. LISTEN 0 100 127.0.0.1:25 *:*
  7. LISTEN 0 50 *:445 *:*
  8. LISTEN 0 50 :::139 :::*
  9. LISTEN 0 128 :::80 :::*
  10. LISTEN 0 32 :::21 :::*
  11. LISTEN 0 128 :::22 :::*
  12. LISTEN 0 100 ::1:25 :::*
  13. LISTEN 0 50 :::445 :::*

 (5)  在 在/etc/ansible/hosts中定义变量

1)普通变量:此时在webs组的IP后面追加命名nodename=centos7_1,可以将远程的机器的名称改为centos7_1.

  1. [root@ansibleplaybook]#vim /etc/ansible/hosts
  2. [webs]
  3. 192.168.34.103 nodename=centos7_1

定义yml内容,将hosts的文件名定义到变量中:

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4.  
  5. tasks:
  6. - name: hostname
  7. hostname: name={{ nodename }}

此时执行ansible-playbook test.yml ,就会将远程的主机名称修改,具体如下:

  1. [root@ansibleplaybook]#ansible-playbook test.yml 执行此playbook变量内容
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [hostname] ******************************************************************************************************
  9. changed: [192.168.34.103]
  10.  
  11. PLAY RECAP ***********************************************************************************************************
  12. 192.168.34.103 : ok=2 changed=1
  13. [root@ansibleplaybook]#ansible webs -a "hostname" 查询远程主机的主机名为centos7_1
  14. 192.168.34.103 | CHANGED | rc=0 >>
  15. centos7_1

 2)定义组变量:将主机名之前的内容统一追加一个相同的内容:

  1. vim /etc/ansible/hosts
  2. [webs]
  3. 192.168.34.103 nodename=centos7_1 主机名
  4.  
  5. [webs:vars]
  6. name=baidu.com 添加后缀名

将后缀的变量名称放到后面:

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4.  
  5. tasks:
  6. - name: hostname
  7. hostname: name={{ nodename }}.{{ name }} #定义的变量追加的内容

 执行结果如下:

ansible-playbook  test.yml

  1. [root@ansibleplaybook]#ansible-playbook test.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [hostname] ******************************************************************************************************
  9. changed: [192.168.34.103]
  10.  
  11. PLAY RECAP ***********************************************************************************************************
  12. 192.168.34.103 : ok=2 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  13.  
  14. [root@ansibleplaybook]#ansible webs -a "hostname"
  15. 192.168.34.103 | CHANGED | rc=0 >>
  16. centos7_1.baidu.com # 此时的主机名后缀有baidu.com

4、在剧本中加入模板 templates

(1)介绍

template模板为我们提供了动态配置服务,使用jinja2语言,里面支持多种条件判断、循环、逻辑运算、比较操作等。其实说白了也就是一个文件,和之前配置文件使用copy一样,只是使用copy,不能根据服务器配置不一样进行不同动态的配置。这样就不利于管理。
说明:
1、多数情况下都将template文件放在和playbook文件同级的templates目录下(手动创建),这样playbook文件中可以直接引用,会自动去找这个文件。如果放在别的地方,也可以通过绝对路径去指定。

支持:

  字符串:使用单引号或双引号;

  数字:整数,浮点数;

  列表:[item1, item2, ...]

  元组:(item1, item2, ...)

  字典:{key1:value1, key2:value2, ...}

  布尔型:true/false

  算术运算:+, -, *, /, //, %, **

  比较操作:==, !=, >, >=, <, <=

  逻辑运算:and, or, not

(2)先创建一个模板文件,以.j2 结尾

cp /etc/nginx/nginx.conf /playbook/nginx.conf.j2

vim /playbook/nginx.conf.j2

worker_processes {{ ansible_processor_count*2 }}; #该变量是setup 模块查看CPU核数的变量,此时将CPU核数乘以2

listen {{ nginx_port}}; #自定义在playbook 中的变量

yum install nginx   #安装nginx

"ansible_processor_count": 1  查看当前的CPU核数有几个

(1)书写当前的模板,将本机的源文件复制到目标地址,将CPU个数成倍增涨,并将端口号改为82:

  1. [root@ansibleplaybook]#vim test1.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6.  
  7. tasks:
  8. - name: install
  9. yum: name=nginx
  10. - name: template 定制模板
  11. template: src=nginx.conf.j2 dest=/etc/nginx/nginx.conf 将源文件复制到目标地址
  12. notify: restart
  13. - name: service
  14. service: name=nginx state=started enabled=yes
  15.  
  16. handlers:
  17. - name: restart
  18. service: name=nginx state=restarted enabled=yes

(2)修改templates目录下的nginx.confj2配置文件,将当前的CPU核数乘以四,并将端口号定义变量{{nginx_port}}:

  1. [root@ansibleplaybook]#vim templates/nginx.conf.j2
  2. worker_processes {{ansible_processor_count*4}}; CPU乘以4
  3. server {
  4. listen {{nginx_port}} default_server; 将此IPV4的端口号定义为变量
  5. listen [::]:80 default_server; 下面的是IPV6的端口号

(3)修改/etc/ansible/hosts配置文件的端口号,定义变量,可以修改当前的nginx的端口号:

  1. vim /etc/ansible/hosts
  2. [webs]
  3. 192.168.34.103 nodename=centos7_1 nginx_port=82

执行nginx.yml的剧本:

  1. [root@ansibleplaybook]#ansible-playbook nginx.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [install] *******************************************************************************************************
  9. ok: [192.168.34.103]
  10.  
  11. TASK [template] ******************************************************************************************************
  12. ok: [192.168.34.103]
  13.  
  14. TASK [service] *******************************************************************************************************
  15. ok: [192.168.34.103]
  16.  
  17. PLAY RECAP ***********************************************************************************************************
  18. 192.168.34.103 : ok=4 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0

(4)查询执行结果,此时已有四个CPU运行。

  1. [root@ansibleplaybook]#ansible webs -m shell -a "ps aux | grep nginx" 查询单签的nginx的运行情况
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. root 29927 0.0 0.1 120796 2252 ? Ss 01:51 0:00 nginx: master process /usr/sbin/nginx
  4. nginx 29928 0.0 0.2 121180 3332 ? S 01:51 0:00 nginx: worker process 此时可以查看到有四个CPU
  5. nginx 29929 0.0 0.2 121180 3332 ? S 01:51 0:00 nginx: worker process
  6. nginx 29930 0.0 0.2 121180 3332 ? S 01:51 0:00 nginx: worker process
  7. nginx 29931 0.0 0.1 121180 3128 ? S 01:51 0:00 nginx: worker process
  8. root 29996 0.0 0.0 113176 1216 pts/1 S+ 01:51 0:00 /bin/sh -c ps aux | grep nginx
  9. root 29998 0.0 0.0 112708 956 pts/1 S+ 01:51 0:00 grep nginx

(5)查看82端口号运行情况:

  1. [root@ansibleplaybook]#ansible webs -a "ss -nlt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:*
  5. LISTEN 0 128 *:82 *:* 此时查看到82端口已经打开
  6. LISTEN 0 128 *:22 *:*
  7. LISTEN 0 100 127.0.0.1:25 *:*
  8. LISTEN 0 50 *:445 *:*
  9. LISTEN 0 50 :::139 :::*
  10. LISTEN 0 128 :::80 :::*
  11. LISTEN 0 32 :::21 :::*
  12. LISTEN 0 128 :::86 :::*
  13. LISTEN 0 128 :::22 :::*
  14. LISTEN 0 100 ::1:25 :::*
  15. LISTEN 0 50 :::445 :::*

5、templates之when

when语句参考

条件测试:如果需要根据变量、facts或此前任务的执行结果来做为某task执行与否的前提时要用到条件测试,通过when语句执行,在task中使用jinja2的语法格式、
when语句:
task后添加when子句即可使用条件测试;when语句支持jinja2表达式语法。

"ansible_distribution_major_version": "7"查看当前的系统版本号

1) 将/etc/ansible/hosts配置文件的端口号改为http_port

  1. vim /etc/ansible/hosts
  2. [apps]
  3. 192.168.34.103 http_port=86
  4. 192.168.34.105 http_port=87

2) 将centos6的httpd的配置文件复制到centos7的templates目录下,起名为httpd6.conf.j2  ,准备的是centos6的配置文件

3) 将centos7的httpd的配置文件复制到templates目录下,起名叫httpd7.conf.j2,准备的是centos7的配置文件

  1. [root@centos6~]#scp /etc/httpd/conf/httpd.conf 192.168.34.101:/root/playbook/templates/httpd6.conf.j2
  2. [root@ansibleplaybook]#cp /etc/httpd/conf/httpd.conf templates/httpd7.conf.j2

4) 修改复制后的httpd6.conf.j2和httpd7.conf.j2配置文件的端口:

  1. vim httpd6.conf.j2
  2. Listen {{http_port}}
  3.  
  4. vim httpd7.conf.j2
  5. Listen {{http_port}}

5)书写template模板内的when可以将centos6和centos7的httpd版本不同问题解决,针对不同的系统版本,安装不同版本的系统:

  1. ---
  2. - hosts: apps
  3. remote_user: root
  4.  
  5. tasks:
  6. - name: install
  7. yum: name=httpd
  8. - name: template1
  9. template: src=httpd6.conf.j2 dest=/etc/httpd/conf/httpd.conf
  10. when: ansible_distribution_major_version=="6" #判断当前的操作系统是6版本,安装版本6的httpd服务
  11. notify: restart
  12. - name: template2
  13. template: src=httpd7.conf.j2 dest=/etc/httpd/conf/httpd.conf
  14. when: ansible_distribution_major_version=="7"
  15. notify: restart
  16. - name: service
  17. service: name=httpd state=started enabled=yes
  18.  
  19. handlers:
  20. - name: restart
  21. service: name=httpd state=restarted

6) 查看httpd安装后的结果,此时的86和87端口都已经打开

  1. [root@ansibleplaybook]#ansible apps -a "ss -nlt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:*
  5. LISTEN 0 128 *:80 *:*
  6. LISTEN 0 128 *:22 *:*
  7. LISTEN 0 100 127.0.0.1:25 *:*
  8. LISTEN 0 50 *:445 *:*
  9. LISTEN 0 50 :::139 :::*
  10. LISTEN 0 128 :::80 :::*
  11. LISTEN 0 32 :::21 :::*
  12. LISTEN 0 128 :::86 :::*
  13. LISTEN 0 128 :::22 :::*
  14. LISTEN 0 100 ::1:25 :::*
  15. LISTEN 0 50 :::445 :::*
  16.  
  17. 192.168.34.105 | CHANGED | rc=0 >>
  18. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  19. LISTEN 0 128 127.0.0.1:6010 *:*
  20. LISTEN 0 128 ::1:6010 :::*
  21. LISTEN 0 128 :::55642 :::*
  22. LISTEN 0 128 :::111 :::*
  23. LISTEN 0 128 *:111 *:*
  24. LISTEN 0 128 *:57810 *:*
  25. LISTEN 0 128 :::22 :::*
  26. LISTEN 0 128 *:22 *:*
  27. LISTEN 0 128 :::87 :::*
  28. LISTEN 0 64 :::23 :::*
  29. LISTEN 0 128 127.0.0.1:631 *:*
  30. LISTEN 0 128 ::1:631 :::*
  31. LISTEN 0 100 ::1:25 :::*
  32. LISTEN 0 100 127.0.0.1:25 *:*

6、template之with_items

with_items迭代,当有需要重复性执行的任务时,可以使用迭代机制。
对迭代项的引用,固定变量名为“item”,要在task中使用with_items给定要迭代的元素列表。
列表格式:
  字符串
  字典

 示例一:

在本机新建十个文件,然后将本机的文件复制到其他文件中

  1. [root@ansibleplaybook]#mkdir files
  2. [root@ansibleplaybook]#touch files/file{1..10}

将本地的三个文件复制到对方主机的data目录下,编写playbook:

  1. [root@ansibleplaybook]#vim test_temp.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6.  
  7. tasks:
  8. - name: copy files
  9. copy: src={{item}} dest=/data/ mode=600
  10. with_items:
  11. - file1
  12. - file2
  13. - file3

执行playbook命令,查看执行结果:

  1. [root@ansibleplaybook]#ansible-playbook test_temp.yml 执行命令
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [copy files] ****************************************************************************************************
  9. changed: [192.168.34.103] => (item=file1)
  10. changed: [192.168.34.103] => (item=file2)
  11. changed: [192.168.34.103] => (item=file3)
  12.  
  13. PLAY RECAP ***********************************************************************************************************
  14. 192.168.34.103 : ok=2 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  15.  
  16. [root@ansibleplaybook]#ansible webs -a "ls /data/ -l" 查看对方的主机已经有600权限的三个文件
  17. 192.168.34.103 | CHANGED | rc=0 >>
  18. total 0
  19. -rw------- 1 root root 0 Nov 6 04:14 file1
  20. -rw------- 1 root root 0 Nov 6 04:14 file2
  21. -rw------- 1 root root 0 Nov 6 04:14 file3

示例二:通过嵌套子变量创建用户并加入不同的组

编写playbook:

  1. vim test.yml
  2. ---
  3. - hosts: webs
  4. remote_user: root
  5.  
  6. tasks:
  7. - name: create groups
  8. group: name={{item}} state=present(默认,不需要写)
  9. with_items:
  10. - g1
  11. - g2
  12. - g3
  13. - name: create users state=present(默认,可以不写)
  14. user: name={{item.name}} group={{item.group}}
  15. with_items:
  16. - {name: 'user1',group: 'g1'}
  17. - {name: 'user2',group: 'g2'}
  18. - {name: 'user3',group: 'g3'}

执行剧本并查看执行结果,此时可以看到对方主机已经创建了三个用户:

  1. [root@ansibleplaybook]#ansible-playbook test_temp.yml 执行剧本内容
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [create groups] ************************************************************************************************
  9. changed: [192.168.34.103] => (item=g1)
  10. changed: [192.168.34.103] => (item=g2)
  11. changed: [192.168.34.103] => (item=g3)
  12.  
  13. TASK [create users] **************************************************************************************************
  14. changed: [192.168.34.103] => (item={u'group': u'g1', u'name': u'user1'})
  15. changed: [192.168.34.103] => (item={u'group': u'g2', u'name': u'user2'})
  16. changed: [192.168.34.103] => (item={u'group': u'g3', u'name': u'user3'})
  17.  
  18. PLAY RECAP ***********************************************************************************************************
  19. 192.168.34.103 : ok=3 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  20.  
  21. [root@ansibleplaybook]#ansible webs -a "id user1" 查看执行后的用户,核实是否正确
  22. 192.168.34.103 | CHANGED | rc=0 >>
  23. uid=1002(user1) gid=1002(g1) groups=1002(g1)
  24.  
  25. [root@ansibleplaybook]#ansible webs -a "id user2"
  26. 192.168.34.103 | CHANGED | rc=0 >>
  27. uid=1003(user2) gid=1003(g2) groups=1003(g2)
  28.  
  29. [root@ansibleplaybook]#ansible webs -a "id user3"
  30. 192.168.34.103 | CHANGED | rc=0 >>
  31. uid=1004(user3) gid=1004(g3) groups=1004(g3)

示例三:

同时安装多个包:

  1. [root@ansibleplaybook]#vim test.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6.  
  7. tasks:
  8. - name: install
  9. yum: name=httpd,vsftpd,memcached

执行剧本,并查看当前的已经安装好的包:

  1. [root@ansibleplaybook]#ansible-playbook test.yml 执行剧本
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [install] *******************************************************************************************************
  9. changed: [192.168.34.103]
  10.  
  11. PLAY RECAP ***********************************************************************************************************
  12. 192.168.34.103 : ok=2 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  13.  
  14. [root@ansibleplaybook]#ansible webs -a "rpm -q httpd,vsftp,memcached" 查看此时的包是否被安装
  15. [WARNING]: Consider using the yum, dnf or zypper module rather than running 'rpm'. If you need to use command
  16. because yum, dnf or zypper is insufficient you can add 'warn: false' to this command task or set
  17. 'command_warnings=False' in ansible.cfg to get rid of this message.
  18.  
  19. 192.168.34.103 | FAILED | rc=1 >>
  20. package httpd,vsftp,memcached is not installednon-zero return code

等同于上面的写法:也是同时安装多个软件

  1. [root@ansibleplaybook]#vim test.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6.  
  7. tasks:
  8. - name: install
  9. yum: name={{item}}
  10. with_items:
  11. - httpd
  12. - vsftpd
  13. - memcached 

7、template之for和if

  1. 通过使用forif可以更加灵活的生成配置文件等需求,还可以在里面根据各种条件进行判断,然后生成不同的配置文件、或者服务器配置相关等。

 (1)编写playbook

  1. [root@ansibleplaybook]#vim for_temp.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6. vars:
  7. ports:
  8. - 81
  9. - 82
  10. - 83
  11.  
  12. tasks:
  13. - name: template
  14. template: src=test_for.conf.j2 dest=/data/test_for.conf

(2)模板文件编写 

vim  templates/test_for.conf.j2

  1. {% for i in ports %}
  2. server{
  3. listen {{i}}
  4. }
  5. {% endfor %}

 (3)执行剧本并查看复制到对方主机的文件内容:

  1. [root@ansibleplaybook]#ansible-playbook for_temp.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [template] ******************************************************************************************************
  9. changed: [192.168.34.103]
  10.  
  11. PLAY RECAP ***********************************************************************************************************
  12. 192.168.34.103 : ok=2 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  13.  
  14. [root@ansibleplaybook]#ansible webs -a "cat /data/test_for.conf "
  15. 192.168.34.103 | CHANGED | rc=0 >>
  16. server{
  17. listen 81
  18. }
  19. server{
  20. listen 82
  21. }
  22. server{
  23. listen 83
  24. }

用字典写法将上面的内容输出同样的名称:

  1. [root@ansibleplaybook]#vim for_temp.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6. vars:
  7. ports:
  8. - listen_port: 81
  9. - listen_port: 82
  10. - listen_port: 83
  11.  
  12. tasks:
  13. - name: template
  14. template: src=test_for.conf.j2 dest=/data/test_for.conf

 修改模板内容,和上面的for语句输出内容一致:

  1. [root@ansibleplaybook]#vim templates/test_for.conf.j2
  2.  
  3. {% for i in ports %}
  4. server{
  5. listen {{i.lsiten_port}}
  6. }
  7. {% endfor %}
  8. ~

示例:

编写playbook

  1. [root@ansibleplaybook]#vim for_temp.yml
  2.  
  3. ---
  4. - hosts: webs
  5. remote_user: root
  6. vars:
  7. vhosts:
  8. - host1:
  9. listen_port: 81
  10. host_name: www.a.com
  11. dirname: /data/www1
  12. - host2:
  13. listen_port: 82
  14. host_name: www.b.com
  15. dirname: /data/www2
  16. - host3:
  17. listen_port: 83
  18. host_name: www.c.com
  19. dirname: /data/www3
  20.  
  21. tasks:
  22. - name: template
  23. template: src=test_for.conf.j2 dest=/data/test_for.conf

 编写jianjia2(j.2)文件

  1. [root@ansibleplaybook]#vim templates/test_for.conf.j2
  2.  
  3. {% for i in vhosts %}
  4. server{
  5. listen {{i.listen_port}}
  6. server_name {{i.host_name}}
  7. root {{i.dirname}}
  8. }
  9. {% endfor %}

  执行playbook并查看对方的目录文件

  1. [root@ansibleplaybook]#ansible-playbook for_temp.yml
  2.  
  3. [root@ansibleplaybook]#ansible webs -a "cat /data/test_for.conf"
  4. 192.168.34.103 | CHANGED | rc=0 >>
  5. server{
  6. listen 81
  7. server_name www.a.com
  8. root /data/www1
  9. }
  10. server{
  11. listen 82
  12. server_name www.b.com
  13. root /data/www2
  14. }
  15. server{
  16. listen 83
  17. server_name www.c.com
  18. root /data/www3
  19. }

示例:在for循环中再嵌套if判断,让生成的配置文件更加灵活

编写playbook

  1. ---
  2. - hosts: webs
  3. remote_user: root
  4. vars:
  5. vhosts:
  6. - host1:
  7. listen_port: 81
  8. host_name: www.a.com
  9. dirname: /data/www1
  10. - host2:
  11. listen_port: 82
  12. #host_name: www.b.com 将此行注释掉
  13. dirname: /data/www2
  14. - host3:
  15. listen_port: 83
  16. host_name: www.c.com
  17. dirname: /data/www3
  18.  
  19. tasks:
  20. - name: template
  21. template: src=test_for.conf.j2 dest=/data/test_for.conf

 编写jianjia2文件(j.2) 

  1. [root@ansibleplaybook]#vim templates/test_for.conf.j2
  2.  
  3. {% for i in vhosts %}
  4. server{
  5. listen {{i.listen_port}}
  6. {% if i.host_name is defined %}
  7. server_name {{i.host_name}}
  8. {% endif %}
  9. root {{i.dirname}}
  10. }
  11. {% endfor %}

执行playbook并查看执行结果:

  1. [root@ansibleplaybook]#ansible-playbook for_temp.yml
  2.  
  3. [root@ansibleplaybook]#ansible webs -a "cat /data/test_for.conf"
  4. 192.168.34.103 | CHANGED | rc=0 >>
  5. server{
  6. listen 81
  7. server_name www.a.com
  8. root /data/www1
  9. }
  10. server{
  11. listen 82 此时中间就少了server_name定义的值
  12. root /data/www2
  13. }
  14. server{
  15. listen 83
  16. server_name www.c.com
  17. root /data/www3
  18. }

Roles介绍:

ansible1.2版本引入的新特性,用于层次性、结构化地组织playbookroles能够根据层次型结构自动装载变量文件、tasks以及handlers等。要使用roles只需要在playbook中使用include指令引入即可。简单来讲,roles就是通过分别将变量、文件、任务、模板及处理器放置于单独的目录中,并可以便捷的include它们的一种机制。角色一般用于基于主机构建服务的场景中,但也可以是用于构建守护进程等场景中。主要使用场景代码复用度较高的情况下。

roles目录结构:

 roles目录含义:

  1. roles: <--所有的角色必须放在roles目录下,这个目录可以自定义位置,默认的位置在/etc/ansible/roles
  2. project: <---具体的角色项目名称,比如nginxtomcatphp
  3. files <--用来存放由copy模块或script模块调用的文件。
  4. templates <--用来存放jinjia2模板,template模块会自动在此目录中寻找jinjia2模板文件。
  5. tasks <--此目录应当包含一个main.yml文件,用于定义此角色的任务列表,此文件可以使用include包含其它的位于此目录的task文件。
  6. main.yml
  7. handlers <--此目录应当包含一个main.yml文件,用于定义此角色中触发条件时执行的动作。
  8. main.yml
  9. vars <--此目录应当包含一个main.yml文件,用于定义此角色用到的变量。
  10. main.yml
  11. defaults <--此目录应当包含一个main.yml文件,用于为当前角色设定默认变量。
  12. main.yml
  13. meta <--此目录应当包含一个main.yml文件,用于定义此角色的特殊设定及其依赖关系。
  14. main.yml

(1)创建httpd服务的roles(角色):

新建文件夹,具体文件夹如下:

  1. [root@ansibleplaybook]#mkdir roles
  2. [root@ansibleplaybook]#mkdir roles/{httpd,nginx,mysql}
  3. [root@ansibleplaybook]#mkdir roles/{httpd,nginx,mysql}/{tasks,files,templates,handlers,vars}

复制本地的httpd.conf文件,当做实验备用:

  1. cp /etc/httpd/conf/httpd.conf files/

查看具体的文件结构:

  1. [root@ansibleplaybook]#tree roles/
  2. roles/
  3. ├── httpd
  4.    ├── files
  5.       └── httpd.conf
  6.    ├── handlers
  7.    ├── tasks
  8.       ├── config.yml
  9.       ├── group.yml
  10.       ├── install.yml
  11.       ├── main.yml
  12.       ├── service.yml
  13.       └── user.yml
  14.    ├── templates
  15.    └── vars
  16. ├── mysql
  17.    ├── files
  18.    ├── handlers
  19.    ├── tasks
  20.    ├── templates
  21.    └── vars
  22. └── nginx
  23. ├── files
  24. ├── handlers
  25. ├── tasks
  26. ├── templates
  27. └── vars

编写httpd目录下tasks目录文件内容:

创建将文件复制到对方主机上的文件:

  1. [root@ansibletasks]#vim config.yml
  2.  
  3. - name: config file
  4. copy: src=httpd.conf dest=/etc/httpd/conf backup=yes

创建用户:

  1. [root@ansibletasks]#vim group.yml
  2.  
  3. - name: create group
  4. group: name=apache system=yes gid=80

创建安装配置文件:

  1. [root@ansibletasks]#vim install.yml
  2.  
  3. - name: install package
  4. yum: name=httpd

创建服务的文件:

  1. [root@ansibletasks]#vim service.yml
  2.  
  3. - name: service
  4. service: name=httpd state=started enabled=yes

创建用户文件:

  1. [root@ansibletasks]#cat user.yml
  2. - name: create user
  3. user: name=apache group=apache uid=80 shell=/sbin/nologin home=/usr/share/httpd system=yes

将所有的文件关联起来,并按顺序排列:

  1. [root@ansibletasks]#cat main.yml
  2. - include: group.yml
  3. - include: user.yml
  4. - include: install.yml
  5. - include: config.yml
  6. - include: service.yml

将httpd.conf配置文件的端口修改为9527:

  1. [root@ansibleroles]#vim httpd/files/httpd.conf
  2. Listen 9527

编写playbook剧本,用来调用httpd整个目录下的内容:

  1. [root@ansibleplaybook]#vim httpd_roles.yml
  2.  
  3. - hosts: webs
  4. remote_user: root
  5.  
  6. roles:
  7. - role: httpd

编写一个网站文件,并在屏幕上显示,验证当前的信息:

  1. [root@ansibleroles]#vim httpd/files/index.html
  2.  
  3. <h1>welcome to beijing!</h1>

将创建的index.html数据复制到/var/www/html目录下,相当于是给页面准备一个文件:

  1. [root@ansibleroles]#vim httpd/tasks/data.yml
  2.  
  3. - name: data file
  4. copy: src=index.html dest=/var/www/html/

将创建的数据放到main.yml文件中,按顺序进行执行:

  1. [root@ansibleroles]#vim httpd/tasks/main.yml
  2. - include: group.yml
  3. - include: user.yml
  4. - include: install.yml
  5. - include: config.yml
  6. - include: service.yml
  7. - include: data.yml

查看当前创建的目录文件结构:

  1. [root@ansibleplaybook]#tree roles/httpd
  2. roles/httpd
  3. ├── files
  4.    ├── httpd.conf
  5.    └── index.html
  6. ├── handlers
  7. ├── tasks
  8.    ├── config.yml
  9.    ├── data.yml
  10.    ├── group.yml
  11.    ├── install.yml
  12.    ├── main.yml
  13.    ├── service.yml
  14.    └── user.yml
  15. ├── templates
  16. └── vars

执行playbook

  1. [root@ansibleplaybook]#ansible-playbook httpd_roles.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [httpd : create group] ******************************************************************************************
  9. ok: [192.168.34.103]
  10.  
  11. TASK [httpd : create user] *******************************************************************************************
  12. ok: [192.168.34.103]
  13.  
  14. TASK [httpd : install package] ***************************************************************************************
  15. ok: [192.168.34.103]
  16.  
  17. TASK [httpd : config file] *******************************************************************************************
  18. ok: [192.168.34.103]
  19.  
  20. TASK [httpd : service] ***********************************************************************************************
  21. ok: [192.168.34.103]
  22.  
  23. PLAY RECAP ***********************************************************************************************************
  24. 192.168.34.103 : ok=6 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0

查看httpd端口开启情况:

  1. [root@ansibleplaybook]#ansible webs -a "ss -nlt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:*
  5. LISTEN 0 128 *:82 *:*
  6. LISTEN 0 128 *:22 *:*
  7. LISTEN 0 100 127.0.0.1:25 *:*
  8. LISTEN 0 50 *:445 *:*
  9. LISTEN 0 50 :::139 :::*
  10. LISTEN 0 128 :::80 :::*
  11. LISTEN 0 32 :::21 :::*
  12. LISTEN 0 128 :::22 :::*
  13. LISTEN 0 128 :::9527 :::*
  14. LISTEN 0 100 ::1:25 :::*
  15. LISTEN 0 50 :::445 :::*

查看网页信息打开情况:

(2)创建nginx服务的roles(角色):

1、将之前httpd做实验的子目录文件都复制一份到nginx目录下:

  1. [root@ansibleplaybook]#cd roles/
  2. [root@ansibleroles]#ls
  3. httpd mysql
  4. [root@ansibleroles]#rm -rf nginx/
  5. [root@ansibleroles]#cp -r httpd/ nginx

2、将roles/nginx/tasks/main.yml文件顺序进行修改:

  1. [root@ansibleplaybook]#vim roles/nginx/tasks/main.yml
  2. - include: install.yml
  3. - include: config.yml
  4. - include: service.yml

3、删除多余的tasks目录下的文件:

  1. [root@ansiblenginx]#cd tasks/
  2. [root@ansibletasks]#ls
  3. config.yml data.yml group.yml install.yml main.yml service.yml user.yml
  4. [root@ansibletasks]#rm -rf group.yml user.yml

 4、修改config.yml配置文件,使用template模板形式进行修改:

  1. [root@ansibletasks]#vim config.yml
  2.  
  3. - name: config file
  4. template: src=nginx.conf.j2 dest=/etc/nginx/nginx.conf

 5、将本地已安装好的nginx的nginx.conf配置文件复制到template目录下,起名叫nginx.conf.j2

  1. [root@ansiblenginx]#yum install nginx -y
  2. [root@ansiblenginx]#cp /etc/nginx/nginx.conf templates/nginx.conf.j2

 6、修改nginx/templates/nginx.conf.j2配置文件的CPU内核:

  1. [root@ansibletemplates]#vim nginx.conf.j2
  2.  
  3. # For more information on configuration, see:
  4. # * Official English Documentation: http://nginx.org/en/docs/
  5. # * Official Russian Documentation: http://nginx.org/ru/docs/
  6.  
  7. user nginx;
  8. worker_processes {{ansible_processor_count**3}};

 7、跨角色调用httpd服务文件内容: 

  1. [root@ansiblenginx]#vim tasks/data.yml
  2.  
  3. - name: data
  4. copy: src=roles/httpd/files/index.html dest=/usr/share/nginx/html/

8、将data.yml放入到main.yml文件中、安装的nginx软件名称修改,以及要启动的服务名称修改:

  1. [root@ansiblenginx]#vim tasks/main.yml
  2.  
  3. - include: install.yml
  4. - include: config.yml
  5. - include: service.yml
  6. - include: data.yml
  7.  
  8. [root@ansiblenginx]#vim tasks/install.yml 将安装的nginx文件名修改
  9.  
  10. - name: install package
  11. yum: name=nginx
  12.  
  13. [root@ansiblenginx]#vim tasks/service.yml 将启动的服务名称修改
  14.  
  15. - name: service
  16. service: name=nginx state=started enabled=yes

9、最后在playbook目录下创建nginx_rolee.yml配置文件(跟roles目录平级):

  1. [root@ansibleplaybook]#vim nginx_roles.yml
  2.  
  3. - hosts: webs
  4. remote_user: root
  5.  
  6. roles:
  7. - role: nginx
  8. - role: httpd

10、执行playbook

  1. [root@ansibleplaybook]#ansible-playbook nginx_roles.yml 执行剧本
  2. [root@ansibleplaybook]#ansible webs -a "ss -nlt" 查看当前的端口执行情况:809527端口都已打开
  3. 192.168.34.103 | CHANGED | rc=0 >>
  4. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  5. LISTEN 0 50 *:139 *:*
  6. LISTEN 0 128 *:80 *:*
  7. LISTEN 0 128 *:22 *:*
  8. LISTEN 0 100 127.0.0.1:25 *:*
  9. LISTEN 0 50 *:445 *:*
  10. LISTEN 0 50 :::139 :::*
  11. LISTEN 0 128 :::80 :::*
  12. LISTEN 0 32 :::21 :::*
  13. LISTEN 0 128 :::22 :::*
  14. LISTEN 0 128 :::9527 :::*
  15. LISTEN 0 100 ::1:25 :::*
  16. LISTEN 0 50 :::445 :::*

10、此时用nginx服务默认的80端口已经可以打开网页,已经实现了跨角色调用文件:

 (3)如果触发notify和handlers两个角色,可以修改相关文件,具体如下:

  1. [root@ansibleplaybook]#vim roles/nginx/tasks/config.yml
  2.  
  3. - name: config file
  4. template: src=nginx.conf.j2 dest=/etc/nginx/nginx.conf
  5. notify: restart 此处的名称要和handlers一致
  6. [root@ansibleplaybook]#vim roles/nginx/handlers/main.yml
  7. - name: restart
  8. service: name=nginx state=restarted

为了验证重启效果,此时我们可以将nginx.conf.j2配置文件的端口修改为8080:

  1. [root@ansibleplaybook]#vim roles/nginx/templates/nginx.conf.j2
  2. server {
  3. listen 8080 default_server;

执行playbook

  1. [root@ansibleplaybook]#ansible-playbook nginx_roles.yml
  2. PLAY [webs] **********************************************************************************************************
  3.  
  4. TASK [Gathering Facts] ***********************************************************************************************
  5. ok: [192.168.34.103]
  6.  
  7. TASK [nginx : install package] ***************************************************************************************
  8. ok: [192.168.34.103]
  9.  
  10. TASK [nginx : config file] *******************************************************************************************
  11. changed: [192.168.34.103]
  12.  
  13. TASK [nginx : service] ***********************************************************************************************
  14. ok: [192.168.34.103]
  15.  
  16. TASK [nginx : data] **************************************************************************************************
  17. ok: [192.168.34.103]
  18.  
  19. TASK [httpd : create group] ******************************************************************************************
  20. ok: [192.168.34.103]
  21.  
  22. TASK [httpd : create user] *******************************************************************************************
  23. ok: [192.168.34.103]
  24.  
  25. TASK [httpd : install package] ***************************************************************************************
  26. ok: [192.168.34.103]
  27.  
  28. TASK [httpd : config file] *******************************************************************************************
  29. ok: [192.168.34.103]
  30.  
  31. TASK [httpd : service] ***********************************************************************************************
  32. ok: [192.168.34.103]
  33.  
  34. TASK [httpd : data file] *********************************************************************************************
  35. ok: [192.168.34.103]
  36.  
  37. RUNNING HANDLER [nginx : restart] ************************************************************************************
  38. changed: [192.168.34.103]
  39.  
  40. PLAY RECAP ***********************************************************************************************************
  41. 192.168.34.103 : ok=12 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0

查看当前运行结果,此时的控制的机器nginx端口打开的是8080:

  1. [root@ansibleplaybook]#ansible webs -a "ss -nlt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:*
  5. LISTEN 0 128 *:8080 *:*
  6. LISTEN 0 128 *:22 *:*
  7. LISTEN 0 100 127.0.0.1:25 *:*
  8. LISTEN 0 50 *:445 *:*
  9. LISTEN 0 50 :::139 :::*
  10. LISTEN 0 128 :::80 :::*
  11. LISTEN 0 32 :::21 :::*
  12. LISTEN 0 128 :::22 :::*
  13. LISTEN 0 128 :::9527 :::*
  14. LISTEN 0 100 ::1:25 :::*
  15. LISTEN 0 50 :::445 :::*

下来,我们添加变量格式:

  1. [root@ansibleplaybook]#vim roles/nginx/vars/main.yml
  2.  
  3. username: daemon

 将roles/nginx/templates/nginx.conf.j2配置文件的名称修改:

  1. [root@ansibleplaybook]#vim roles/nginx/templates/nginx.conf.j2
  2.  
  3. # For more information on configuration, see:
  4. # * Official English Documentation: http://nginx.org/en/docs/
  5. # * Official Russian Documentation: http://nginx.org/ru/docs/
  6.  
  7. user {{username}};

 执行playbook

  1. [root@ansibleplaybook]#ansible-playbook nginx_roles.yml
  2.  
  3. PLAY [webs] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7.  
  8. TASK [nginx : install package] ***************************************************************************************
  9. ok: [192.168.34.103]
  10.  
  11. TASK [nginx : config file] *******************************************************************************************
  12. changed: [192.168.34.103]
  13.  
  14. TASK [nginx : service] ***********************************************************************************************
  15. ok: [192.168.34.103]
  16.  
  17. TASK [nginx : data] **************************************************************************************************
  18. ok: [192.168.34.103]
  19.  
  20. TASK [httpd : create group] ******************************************************************************************
  21. ok: [192.168.34.103]
  22.  
  23. TASK [httpd : create user] *******************************************************************************************
  24. ok: [192.168.34.103]
  25.  
  26. TASK [httpd : install package] ***************************************************************************************
  27. ok: [192.168.34.103]
  28.  
  29. TASK [httpd : config file] *******************************************************************************************
  30. ok: [192.168.34.103]
  31.  
  32. TASK [httpd : service] ***********************************************************************************************
  33. ok: [192.168.34.103]
  34.  
  35. TASK [httpd : data file] *********************************************************************************************
  36. ok: [192.168.34.103]
  37.  
  38. RUNNING HANDLER [nginx : restart] ************************************************************************************
  39. changed: [192.168.34.103]
  40.  
  41. PLAY RECAP ***********************************************************************************************************
  42. 192.168.34.103 : ok=12 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0

 查看当前的nginx的名称,此时已经修改为daemon:

  1. [root@ansibleplaybook]#ansible webs -a "ps aux | grep nginx"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. root 25536 0.0 0.1 120796 2092 ? Ss 10:47 0:00 nginx: master process /usr/sbin/nginx
  4. daemon 25537 0.0 0.1 121180 3124 ? S 10:47 0:00 nginx: worker process
  5. root 25602 0.0 0.0 113176 1216 pts/1 S+ 10:48 0:00 /bin/sh -c ps aux | grep nginx
  6. root 25604 0.0 0.0 112708 960 pts/1 R+ 10:48 0:00 grep nginx

(4)实现条件判断调用角色:

  1. [root@ansibleplaybook]#vim roles/httpd/tasks/config.yml
  2.  
  3. - name: config file1
  4. template: src=httpd6.conf.j2 dest=/etc/httpd/conf/httpd.conf backup=yes
  5. when: ansible_distribution_major_version=="6"
  6. - name: config file2
  7. template: src=httpd7.conf.j2 dest=/etc/httpd/conf/httpd.conf backup=yes
  8. when: ansible_distribution_major_version=="7"

将安装好的centos6和centos7的httpd配置文件复制到roles/httpd/templates/目录下,文件名后缀都是以.j2结尾:

  1. [root@centos6~]#scp /etc/httpd/conf/httpd.conf 192.168.34.101:/root/playbook/roles/httpd/templates/httpd6.conf.j2
  2. root@192.168.34.101's password:
  3. httpd.conf 100% 34KB 33.6KB/s 00:00

将centos7的httpd.conf配置文件也放在roles/httpd/templates/目录下,起名以j2结尾:

  1. [root@ansibleplaybook]#cp /etc/httpd/conf/httpd.conf roles/httpd/templates/httpd7.conf.j2

修改当前的http_roles.yml配置文件,里边的apps组才有centos6和7的版本:

  1. [root@ansibleplaybook]#vim http_roles.yml
  2.  
  3. - hosts: apps
  4. remote_user: root
  5.  
  6. roles:
  7. - role: httpd

执行playbook剧本:

  1. [root@ansibleplaybook]#ansible-playbook http_roles.yml
  2.  
  3. PLAY [apps] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7. ok: [192.168.34.105]
  8.  
  9. TASK [httpd : create group] ******************************************************************************************
  10. ok: [192.168.34.103]
  11. ok: [192.168.34.105]
  12.  
  13. TASK [httpd : create user] *******************************************************************************************
  14. ok: [192.168.34.103]
  15. ok: [192.168.34.105]
  16.  
  17. TASK [httpd : install package] ***************************************************************************************
  18. changed: [192.168.34.105]
  19. changed: [192.168.34.103]
  20.  
  21. TASK [httpd : config file1] ******************************************************************************************
  22. skipping: [192.168.34.103]
  23. changed: [192.168.34.105]
  24.  
  25. TASK [httpd : config file2] ******************************************************************************************
  26. skipping: [192.168.34.105]
  27. changed: [192.168.34.103]
  28.  
  29. TASK [httpd : service] ***********************************************************************************************
  30. changed: [192.168.34.103]
  31. changed: [192.168.34.105]
  32.  
  33. TASK [httpd : data file] *********************************************************************************************
  34. ok: [192.168.34.103]
  35. ok: [192.168.34.105]
  36.  
  37. PLAY RECAP ***********************************************************************************************************
  38. 192.168.34.103 : ok=7 changed=3 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0
  39. 192.168.34.105 : ok=7 changed=3 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0

查看安装好后的httpd运行结果:

  1. [root@ansibleplaybook]#ansible apps -a "ss -nltp"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:* users:(("smbd",pid=6721,fd=36))
  5. LISTEN 0 128 *:80 *:* users:(("httpd",pid=27209,fd=3),("httpd",pid=27208,fd=3),("httpd",pid=27207,fd=3),("httpd",pid=27206,fd=3),("httpd",pid=27205,fd=3),("httpd",pid=27204,fd=3))
  6. LISTEN 0 128 *:8080 *:* users:(("nginx",pid=25537,fd=6),("nginx",pid=25536,fd=6))
  7. LISTEN 0 128 *:22 *:* users:(("sshd",pid=6719,fd=3))
  8. LISTEN 0 100 127.0.0.1:25 *:* users:(("master",pid=6818,fd=13))
  9. LISTEN 0 50 *:445 *:* users:(("smbd",pid=6721,fd=35))
  10. LISTEN 0 50 :::139 :::* users:(("smbd",pid=6721,fd=34))
  11. LISTEN 0 128 :::80 :::* users:(("nginx",pid=25537,fd=7),("nginx",pid=25536,fd=7))
  12. LISTEN 0 32 :::21 :::* users:(("vsftpd",pid=6718,fd=4))
  13. LISTEN 0 128 :::22 :::* users:(("sshd",pid=6719,fd=4))
  14. LISTEN 0 100 ::1:25 :::* users:(("master",pid=6818,fd=14))
  15. LISTEN 0 50 :::445 :::* users:(("smbd",pid=6721,fd=33))
  16.  
  17. 192.168.34.105 | CHANGED | rc=0 >>
  18. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  19. LISTEN 0 128 127.0.0.1:6010 *:* users:(("sshd",5804,7))
  20. LISTEN 0 128 ::1:6010 :::* users:(("sshd",5804,6))
  21. LISTEN 0 128 :::43999 :::* users:(("rpc.statd",1781,10))
  22. LISTEN 0 128 :::111 :::* users:(("rpcbind",1674,11))
  23. LISTEN 0 128 *:111 *:* users:(("rpcbind",1674,8))
  24. LISTEN 0 128 *:58740 *:* users:(("rpc.statd",1781,8))
  25. LISTEN 0 128 :::22 :::* users:(("sshd",2079,4))
  26. LISTEN 0 128 *:22 *:* users:(("sshd",2079,3))
  27. LISTEN 0 128 :::87 :::* users:(("httpd",8981,6),("httpd",9097,6),("httpd",9098,6),("httpd",9099,6),("httpd",9100,6),("httpd",9101,6),("httpd",9102,6),("httpd",9103,6),("httpd",9104,6))
  28. LISTEN 0 64 :::23 :::* users:(("xinetd",2103,5))
  29. LISTEN 0 128 127.0.0.1:631 *:* users:(("cupsd",1826,7))
  30. LISTEN 0 128 ::1:631 :::* users:(("cupsd",1826,6))
  31. LISTEN 0 100 ::1:25 :::* users:(("master",2209,13))
  32. LISTEN 0 100 127.0.0.1:25 *:* users:(("master",2209,12))

(5)使用标签实现playbook角色调用:

  1. [root@ansibleplaybook]#vim all_roles.yml
  2.  
  3. - hosts: all
  4. remote_user: root
  5.  
  6. roles:
  7. - {role: httpd,tags: ["httpd","web"]} 将两个服务整体作为一个字典,然后贴上标签:
  8. - {role: nginx,tags: ["nginx","web"]}
  9. - {role: mysql,tags: db}

执行标签的其中一个playbook内容:

  1. [root@ansibleplaybook]#ansible-playbook -t httpd all_roles.yml
  2.  
  3. PLAY [all] ***********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7. ok: [192.168.34.105]
  8.  
  9. TASK [httpd : create group] ******************************************************************************************
  10. ok: [192.168.34.103]
  11. ok: [192.168.34.105]
  12.  
  13. TASK [httpd : create user] *******************************************************************************************
  14. ok: [192.168.34.103]
  15. ok: [192.168.34.105]
  16.  
  17. TASK [httpd : install package] ***************************************************************************************
  18. changed: [192.168.34.103]
  19. changed: [192.168.34.105]
  20.  
  21. TASK [httpd : config file1] ******************************************************************************************
  22. skipping: [192.168.34.103]
  23. changed: [192.168.34.105]
  24.  
  25. TASK [httpd : config file2] ******************************************************************************************
  26. skipping: [192.168.34.105]
  27. changed: [192.168.34.103]
  28.  
  29. TASK [httpd : service] ***********************************************************************************************
  30. changed: [192.168.34.103]
  31. changed: [192.168.34.105]
  32.  
  33. TASK [httpd : data file] *********************************************************************************************
  34. ok: [192.168.34.103]
  35. ok: [192.168.34.105]
  36.  
  37. PLAY RECAP ***********************************************************************************************************
  38. 192.168.34.103 : ok=7 changed=3 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0
  39. 192.168.34.105 : ok=7 changed=3 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0

查看执行后的内容:

  1. [root@ansibleplaybook]#ansible all -a "ss -nlt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:*
  5. LISTEN 0 128 *:22 *:*
  6. LISTEN 0 100 127.0.0.1:25 *:*
  7. LISTEN 0 50 *:445 *:*
  8. LISTEN 0 50 :::139 :::*
  9. LISTEN 0 128 :::80 :::*
  10. LISTEN 0 32 :::21 :::*
  11. LISTEN 0 128 :::22 :::*
  12. LISTEN 0 100 ::1:25 :::*
  13. LISTEN 0 50 :::445 :::*
  14.  
  15. 192.168.34.105 | CHANGED | rc=0 >>
  16. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  17. LISTEN 0 128 127.0.0.1:6010 *:*
  18. LISTEN 0 128 ::1:6010 :::*
  19. LISTEN 0 128 :::43999 :::*
  20. LISTEN 0 128 :::111 :::*
  21. LISTEN 0 128 *:111 *:*
  22. LISTEN 0 128 *:58740 *:*
  23. LISTEN 0 128 :::22 :::*
  24. LISTEN 0 128 *:22 *:*
  25. LISTEN 0 128 :::87 :::*
  26. LISTEN 0 64 :::23 :::*
  27. LISTEN 0 128 127.0.0.1:631 *:*
  28. LISTEN 0 128 ::1:631 :::*
  29. LISTEN 0 100 ::1:25 :::*
  30. LISTEN 0 100 127.0.0.1:25 *:*

执行web标签的playbook,就会将定义标签的httpd和nginx两个文件都执行:

  1. [root@ansibleplaybook]#ansible-playbook -t web all_roles.yml
  2.  
  3. PLAY [apps] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7. ok: [192.168.34.105]
  8.  
  9. TASK [httpd : create group] ******************************************************************************************
  10. ok: [192.168.34.103]
  11. ok: [192.168.34.105]
  12.  
  13. TASK [httpd : create user] *******************************************************************************************
  14. ok: [192.168.34.103]
  15. ok: [192.168.34.105]
  16.  
  17. TASK [httpd : install package] ***************************************************************************************
  18. changed: [192.168.34.103]
  19. changed: [192.168.34.105]
  20.  
  21. TASK [httpd : config file1] ******************************************************************************************
  22. skipping: [192.168.34.103]
  23. changed: [192.168.34.105]
  24.  
  25. TASK [httpd : config file2] ******************************************************************************************
  26. skipping: [192.168.34.105]
  27. changed: [192.168.34.103]
  28.  
  29. TASK [httpd : service] ***********************************************************************************************
  30. changed: [192.168.34.103]
  31. changed: [192.168.34.105]
  32.  
  33. TASK [httpd : data file] *********************************************************************************************
  34. ok: [192.168.34.103]
  35. ok: [192.168.34.105]
  36.  
  37. TASK [nginx : install package] ***************************************************************************************
  38. changed: [192.168.34.105]
  39. changed: [192.168.34.103]
  40.  
  41. TASK [nginx : config file] *******************************************************************************************
  42. changed: [192.168.34.103]
  43. changed: [192.168.34.105]
  44.  
  45. TASK [nginx : service] ***********************************************************************************************
  46. changed: [192.168.34.105]
  47. changed: [192.168.34.103]
  48.  
  49. TASK [nginx : data] **************************************************************************************************
  50. changed: [192.168.34.103]
  51. changed: [192.168.34.105]
  52.  
  53. RUNNING HANDLER [nginx : restart] ************************************************************************************
  54. changed: [192.168.34.103]
  55. changed: [192.168.34.105]
  56.  
  57. PLAY RECAP ***********************************************************************************************************
  58. 192.168.34.103 : ok=12 changed=8 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0
  59. 192.168.34.105 : ok=12 changed=8 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0

 查看执行结果的状态:

  1. [root@ansibleplaybook]#ansible apps -a "ss -nlpt"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  4. LISTEN 0 50 *:139 *:* users:(("smbd",pid=6721,fd=36))
  5. LISTEN 0 128 *:8080 *:* users:(("nginx",pid=38028,fd=6),("nginx",pid=38027,fd=6))
  6. LISTEN 0 128 *:22 *:* users:(("sshd",pid=6719,fd=3))
  7. LISTEN 0 100 127.0.0.1:25 *:* users:(("master",pid=6818,fd=13))
  8. LISTEN 0 50 *:445 *:* users:(("smbd",pid=6721,fd=35))
  9. LISTEN 0 50 :::139 :::* users:(("smbd",pid=6721,fd=34))
  10. LISTEN 0 32 :::21 :::* users:(("vsftpd",pid=6718,fd=4))
  11. LISTEN 0 128 :::22 :::* users:(("sshd",pid=6719,fd=4))
  12. LISTEN 0 100 ::1:25 :::* users:(("master",pid=6818,fd=14))
  13. LISTEN 0 128 :::90 :::* users:(("nginx",pid=38028,fd=7),("nginx",pid=38027,fd=7))
  14. LISTEN 0 50 :::445 :::* users:(("smbd",pid=6721,fd=33))
  15. LISTEN 0 128 :::99 :::* users:(("httpd",pid=37535,fd=4),("httpd",pid=37534,fd=4),("httpd",pid=37533,fd=4),("httpd",pid=37532,fd=4),("httpd",pid=37531,fd=4),("httpd",pid=37530,fd=4))
  16.  
  17. 192.168.34.105 | CHANGED | rc=0 >>
  18. State Recv-Q Send-Q Local Address:Port Peer Address:Port
  19. LISTEN 0 128 127.0.0.1:6010 *:* users:(("sshd",5804,7))
  20. LISTEN 0 128 ::1:6010 :::* users:(("sshd",5804,6))
  21. LISTEN 0 128 :::43999 :::* users:(("rpc.statd",1781,10))
  22. LISTEN 0 128 :::111 :::* users:(("rpcbind",1674,11))
  23. LISTEN 0 128 *:111 *:* users:(("rpcbind",1674,8))
  24. LISTEN 0 128 *:58740 *:* users:(("rpc.statd",1781,8))
  25. LISTEN 0 128 :::8181 :::* users:(("httpd",20990,6),("httpd",21802,6),("httpd",21803,6),("httpd",21804,6),("httpd",21805,6),("httpd",21806,6),("httpd",21807,6),("httpd",21808,6),("httpd",21809,6))
  26. LISTEN 0 128 :::22 :::* users:(("sshd",2079,4))
  27. LISTEN 0 128 *:22 *:* users:(("sshd",2079,3))
  28. LISTEN 0 64 :::23 :::* users:(("xinetd",2103,5))
  29. LISTEN 0 128 127.0.0.1:631 *:* users:(("cupsd",1826,7))
  30. LISTEN 0 128 ::1:631 :::* users:(("cupsd",1826,6))
  31. LISTEN 0 100 ::1:25 :::* users:(("master",2209,13))
  32. LISTEN 0 100 127.0.0.1:25 *:* users:(("master",2209,12))

 

(6)做一个memcached小实验:

目的:是为了定义当前缓存服务器在内存中占比,应该设置多大?

安装memcached:

  1. [root@ansibleplaybook]#yum install memcached -y
  2. [root@ansibleplaybook]#cat /etc/sysconfig/memcached
  3. PORT="11211"
  4. USER="memcached"
  5. MAXCONN="1024"
  6. CACHESIZE="64" 当前的缓存大小
  7. OPTIONS=""

定义memcached角色:

  1. [root@ansibleroles]#cd roles
  2. [root@ansibleroles]#cp httpd/ memcached -r httpd服务复制memcached,在里边进行修改

删除之前指定的httpd相关文件:

  1. [root@ansibletasks]#cd roles/memcached/tasks
  2. [root@ansibletasks]#rm -f data.yml user.yml group.yml 删除不需要的文件
  3. [root@ansiblememcached]#cp /etc/sysconfig/memcached templates/memcached.j2 复制memcachedtemplates目录下,起名叫memcached.j2
  4. [root@ansiblememcached]#vim templates/memcache.j2 修改memcached相关配置
  5.  
  6. PORT="11211"
  7. USER="memcached"
  8. MAXCONN="1024"
  9. CACHESIZE="{{ansible_memtotal_mb//4}}" 将变量进行整除。
  10. OPTIONS=""

修改配置文件:

  1. [root@ansiblememcached]#vim tasks/config.yml
  2.  
  3. - name: config file1
  4. template: src=memcached.j2 dest=/etc/sysconfig/memcached backup=yes

修改main.yml配置文件:

  1. [root@ansiblememcached]#vim tasks/main.yml
  2.  
  3. - include: install.yml
  4. - include: config.yml
  5. - include: service.yml

 修改安装配置文件

  1. [root@ansiblememcached]#vim tasks/install.yml
  2.  
  3. - name: install package
  4. yum: name=memcached

配置启动服务文件:

  1. [root@ansiblememcached]#vim tasks/service.yml
  2.  
  3. - name: service
  4. service: name=memcached state=started enabled=yes

然后在playbook目录下创建一个roles角色playbook剧本:

  1. [root@ansibleplaybook]#vim test_memcached.yml
  2.  
  3. - hosts: apps
  4. remote_user: root
  5.  
  6. roles:
  7. - role: memcached

然后将centos6和centos7的内存大小分别调整为3G和2G,执行playbook:

  1. [root@ansibleplaybook]#ansible-playbook test_memcached.yml
  2.  
  3. PLAY [apps] **********************************************************************************************************
  4.  
  5. TASK [Gathering Facts] ***********************************************************************************************
  6. ok: [192.168.34.103]
  7. ok: [192.168.34.105]
  8.  
  9. TASK [memcached : install package] ***********************************************************************************
  10. ok: [192.168.34.103]
  11. changed: [192.168.34.105]
  12.  
  13. TASK [memcached : config file1] **************************************************************************************
  14. changed: [192.168.34.103]
  15. changed: [192.168.34.105]
  16.  
  17. TASK [memcached : service] *******************************************************************************************
  18. changed: [192.168.34.105]
  19. changed: [192.168.34.103]
  20.  
  21. PLAY RECAP ***********************************************************************************************************
  22. 192.168.34.103 : ok=4 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
  23. 192.168.34.105 : ok=4 changed=3 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0

查看对方的内存大小情况,可以看到,之前的内存大小默认是64,此时已经有所改变:

  1. [root@ansibleplaybook]#ansible apps -a "cat /etc/sysconfig/memcached"
  2. 192.168.34.103 | CHANGED | rc=0 >>
  3. PORT="11211"
  4. USER="memcached"
  5. MAXCONN="1024"
  6. CACHESIZE="496"
  7. OPTIONS=""
  8.  
  9. 192.168.34.105 | CHANGED | rc=0 >>
  10. PORT="11211"
  11. USER="memcached"
  12. MAXCONN="1024"
  13. CACHESIZE="244"
  14. OPTIONS=""

ansible roles总结

  1. 1、编写任务(task)的时候,里面不需要写需要执行的主机,单纯的写某个任务是干什么的即可,装软件的就是装软件的,启动的就是启动的。单独做某一件事即可,最后通过main.yml将这些单独的任务安装执行顺序include进来即可,这样方便维护且一目了然。
  2. 2、定义变量时候直接安装k:v格式将变量写在vars/main.yml文件即可,然后task或者template直接调用即可,会自动去vars/main.yml文件里面去找。
  3. 3、定义handlers时候,直接在handlers/main.yml文件中写需要做什么事情即可,多可的话可以全部写在该文件里面,也可以像task那样分开来写,通过include引入一样的可以。在task调用notify时直接写与handlers名字对应即可(二者必须高度一直)。
  4. 4、模板文件一样放在templates目录下即可,task调用的时候直接写文件名字即可,会自动去到templates里面找。注意:如果是一个角色调用另外一个角色的单个task时候,那么task中如果有些模板或者文件,就得写绝对路径了。

  

  

  

  

  

 

  

  

  

  

  

  

  

  

  

 

 

企业级自动化运维工具应用实战ansible的更多相关文章

  1. 企业级自动化运维工具应用实战-ansible

    背景 公司计划在年底做一次大型市场促销活动,全面冲刺下交易额,为明年的上市做准备.公司要求各业务组对年底大促做准备,运维部要求所有业务容量进行三倍的扩容,并搭建出多套环境可以共开发和测试人员做测试,运 ...

  2. 项目实战10.1—企业级自动化运维工具应用实战-ansible

    实战环境: 公司计划在年底做一次大型市场促销活动,全面冲刺下交易额,为明年的上市做准备.公司要求各业务组对年底大促做准备,运维部要求所有业务容量进行三倍的扩容,并搭建出多套环境可以共开发和测试人员做测 ...

  3. 企业级自动化运维工具---puppet详解

    本文收录在Linux运维企业架构实战系列 1.认识puppet 1.1 引入 puppet是什么,咱们先不用专业的名词解释它,咱们先描述一些工作场景,看明白这些工作场景,自然会知道puppet是什么. ...

  4. 企业级LINUX自动化运维工具Ansible实战课程下载

    什么是Ansible? Ansible是新出现的自动化运维工具,基于Python开发,集合了众多运维工具(puppet.chef.func.fabric)的优点,实现了批量系统配置.批量程序部署.批量 ...

  5. Linux实战教学笔记25:自动化运维工具之ansible (一)

    第二十五节 ansible之文件的批量分发 标签(空格分隔): Linux实战教学笔记-陈思齐 ---本教学笔记是本人学习和工作生涯中的摘记整理而成,此为初稿(尚有诸多不完善之处),为原创作品,允许转 ...

  6. 自动化运维工具-Ansible之3-playbook

    自动化运维工具-Ansible之3-playbook 目录 自动化运维工具-Ansible之3-playbook PlayBook初识 YAML语法 PlayBook部署httpd PlayBook实 ...

  7. 自动化运维工具Ansible详细部署 (转载)

    自动化运维工具Ansible详细部署 标签:ansible 原创作品,允许转载,转载时请务必以超链接形式标明文章 原始出处 .作者信息和本声明.否则将追究法律责任.http://sofar.blog. ...

  8. 自动化运维工具之 Ansible 介绍及安装使用

    一.初识Ansible 介绍: Absible 使用 模块(Modules)来定义配置任务.模块可以用标准脚本语言(Python,Bash,Ruby,等等)编写,这是一个很好的做法,使每个模块幂等.A ...

  9. 自动化运维工具之ansible

    自动化运维工具之ansible   一,ansible简介 ansible是新出现的自动化运维工具,基于Python开发,集合了众多运维工具(puppet.cfengine.chef.func.fab ...

随机推荐

  1. 简单的django登录项目---带views视图函数(脚本文件)---用Bootstrap

    简单的django登录项目 1.首先建立工程,建立工程请参照:https://www.cnblogs.com/effortsing/p/10394511.html 2.在Firstdjango工程项目 ...

  2. laravel原生sql

    转自:https://www.cnblogs.com/zouzhe0/p/6307077.html DB::insert(, ']); $user = DB::]); //我们还 可以看到在执行查询的 ...

  3. django:bootstrap table加载django返回的数据

    bootstrap table加载表格数据有两类方式: 一种通过data属性的方式配置,一种是javascipt方式配置 这里看js配置方式: 1.当数据源为.json文件时 url参数写上json文 ...

  4. Navicat安装及使用

    一.安装Navicat 1.下载安装文件:navicat11.0.17_premium_cs_x86.exe(32位) 2.Oracle 的 Instance Client:instantclient ...

  5. react如何在网页上编辑并运行代码?

    最近想做个能在网站,能在网页上运行代码,并且保存这个组件,看了一下element-react的组件和官方的实例,发现都是可以编辑运行的,因为之前没有这方面的经验,所以看下各位大佬能不能给点意见

  6. 【计算机视觉】Object Proposal之BING理解

    发现: 本论文主要有两大亮点.第一个亮点是发现了在固定窗口的大小下,物体与背景的梯度模式有所不同.如图1所示.图1(a)中绿框代表背景,红框代表物体.如果把这些框都resize成固定大小,比如8X8, ...

  7. opencv-windows安装教程

    一.下载opencv 下载链接: https://opencv.org/releases/ 二.运行exe 运行exe(其实是解压),将压缩包解压到相应目录,如: D:\Program Files ( ...

  8. java如何获取当前日期和时间

    System.currentTimeMillis() 获取标准时间可以通过System.currentTimeMillis()方法获取,此方法不受时区影响,得到的结果是时间戳格式的.例如: 15431 ...

  9. Redis 常用命令学四:集合类型命令

    1.增加和删除命令 127.0.0.1:6379> SADD st a (integer) 1 127.0.0.1:6379> SADD st r f g (integer) 3 127. ...

  10. 将 MathType 公式转换为 Word 自带公式

    以下操作是基于Office 365以及MathType 6.9b平台.有网友留言说第四步没出现「转换为 Office Math」选项,这个我就不清楚了,难道是只有Office 365才支持? 打开Ma ...