运维自动化之ANSLBLE
本章内容
运维自动化发展历程及技术应用
ansible命令使用
absible常用模块详解
YAML语法
Ansible palybook基础
Playbook变量,tags、handlers使用
Playbook模块 templates
Playbook条件判断when
Playbook字典with_items
Ansible Roles
自动化运维应用场景
文件传输
应用部署(软件升级)
配置管理
任务流编排
常用自动化运维工具
- Ansible:python,Agentless,中小型应用环境
Saltstack:python,一般需部署agent,执行效率更高
Puppet:ruby,功能强大,配置复杂,重型,适合大型环境
Fabric:python,agentless
Chef:ruby,国内应用少
Cfengine
func
Ansible发展史
作者:Michakl DaHaan (Cobbke与Func作者)
ansible的名称来自《安德的游戏》中跨越时空的即时通信工具
2012-03-09发布0.0.1版 2015-10-17,RedHat宣布1.5亿美金收购
官网:https://www.ensible.com/
官方文档:https://www.docs.ansible.com/
Ansible特性
模块化:调用特定的模块,完成特定任务
Paramiko(ptyhon对ssh的实现),PyYAML,jinja2(模块语言)三个关键模块
支持自定义模块,可使用任何编程语言写模块
基于python实现
部署简单,基于python和ssh(默认以安装),agentless,无需代理不依赖PKI(无需ssl)
安全,基于Openssh
幂等性:一个任务执行1遍和执行n遍效果一样,不因重复执行带来意外情况
支持playbook编排任务,YAML格式,编排任务,支持丰富的数据结构
较强大的多层解决方案role
Ansible架构
组合INVENTORY,API,MODULES,PLUGINS的绿框,可以理解为是ansible命令工具,其为核心执行工具
INVENTORY:Ansble管理主机的清单/etc/ananaible/hosts
MODULES:ansible执行命令的功能模块,多为内核模块,也可自定义
PLUGINS:模块功能的补充,如连接类型插件,循环插件,变量插件等,该功能不常用
API:供第三方程序调用的应用程序编程接口
Ansible 命令执行来源
USER普通用户,既SYSTEM ADMINISTRATOR
PLAYBOOK:认为你剧本(任务集),编排定义1Ansible任务集的配置文件,由Ansible顺序依次执行,通常是JSON格式的YAML文件
CMDO(配置管理数据库)API调用
PUBLIC/PRIVATE CLOUD API调用
USER->Ansible Playbook -> Ansible
注意事项
执行ansible的主机一般称为主控端,中控,master或堡垒机
主控端python版本需要2.6或以上
被控端端版本小于2.4需要安装python-simplejson
被控端如开启SElinux需要安装libselinux-python
Windows不能作为主控端 可以当客户端
Ansible安装和入门
Ansible安装
ansible的安装方法有很多种
EPEL源的rpm包安装
yum install ansible
| 编译安装 |
| ------------------------------------------------------------ |
| yum -y install python-jinja2 PyYAML python-paramiko python-babel python- cryto |
tar xf ansible-1.5.4.tar.gz |
cd ansible-1.5.4
python setup.py build
python setup.py install
mkdir /etc/ansible
cp -r examples/* /etc/ansible
Git方式
git clone git://github.com/ansible/ansible.git --recursive
cd ./ansible
source ./hacking/env–setup
pip安装
pip是安装python包的管理器,类似yum
yum install python-pip python-devel
yum install gcc glibc-devel zibl-devel rpm-bulid openssl-devel
pip install --upgrade pip
pip install ansible --upgrade
确认安装
ansible --version
[root@ansible ~]# ansible --version
ansible 2.9.23
config file = /etc/ansible/ansible.cfg
configured module search path = [u'/root/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']
ansible python module location = /usr/lib/python2.7/site-packages/ansible
executable location = /usr/bin/ansible
python version = 2.7.5 (default, Oct 14 2020, 14:45:30) [GCC 4.8.5 20150623 (Red Hat 4.8.5-44)]
centos7安装
Ansible 相关文件
/etv/ansible/ansible.cfg 主配置文件,配置ansible工作特性
/etc/ansible/hosts 主机清单
/etc/ansible/roles/ 存放角色的目录
Ansible主配置文件
ansible 的配置文件/etc/ansible/ansible.cfg
,其中大部分配置内容无需进行修改
[defaults]
#inventory = /etc/ansible/ hosts#主机列表配置文件
#library = /usr/share/ my_modules/#库文件存放目录
#remote_tmp = $HOME/.ansible/tmp#临时py命令文件存放在远程主机目录
#local_tmp = $HOME/.ansible/tmp#本机的临时命令执行目录
#forks = 5#默认并发数
#sudo_user = root #默认sudo用户
#ask_sudo_pass = True #每次执行 ansi1e命令是否询问ssh密码
#ask_pass = True
#remote_port 22
#host_key_checking = False#检查对应服务器的 host_key,建议取消注释
#log_path = /var/log/ ansible.log#日志文件,建议启
#module _name = command#默认模块,可以修改为she11模块
111行[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FNfQDD6H-1637840564484)(D:/Typora/image-20210803094535354.png)]
inventory主机清单
ansible的主要功用在于批量主机操作,为了便捷地使用其中的部分主机,可以在inventory file中将其分组命名默认的inventory file为 /etc/ansible/hosts
inventory file可以有很多个,且也可以通过Dynamic inventory来动态生成
主机清单文件格式
inventory文件遵循INI文件格式,中括号的字符为组名,可以将同一个主机归并到多个不同的组中
此外,当如若目标主机使用了非默认的SSH端口查看ss -ntl
,还可以在名称之后使用冒号加端口来标明
如果主机名称遵循相似的命名模式,还可以使用列表的方式标识各主机
配置文件在vim /etc/ansible/hosts
分成了几个类
Ansible相关工具
/usr/bin/ansible 主程序,临时命令执行工具
/usr/bin/ansible-doc 查看配置文档,模块功能查看工具
/usr/bin/ansible-galaxy 下载/上传优秀代码或Roles模块的官网平台
/usr/bin/ansible-playbook 定制自动化任务,编排剧本工具
/usr/bin/ansible-pull 远程执行命令的工具
/usr/bin/ansible-vault 文件加密工具
/usr/bin/ansible-console 基于Console界面与用户交互的执行工具
利用ansible实现管理的主要方式
Ad-Hoc即利用ansible命令,主要用于临时命令使用场景
Ansible-playbook 主要用于长期规划好的,大型项目的场景,需要有前期的规划过程
ansible-doc
此工具用来显示模块帮助
格式
ansible-doc [options] [module..]
-l --list #列出可用模块
-s --snippet #显示指定模块的playbook片段
范例:
#列出所有模块
ansible -doc -l
#查看指定模块帮助用法
ansible -doc ping
查看指定模块帮助用法
ansible -doc -s ping
ansible
此工具通过ssh协议,实现对远程主机的配置管理,应用部署,任务执行等功能
建议:使用此工具前,先配置ansible主控端能基于密钥认证的方式联系各个被管理节点
范例:利用sshpass批量实现基于key验证
ssh-keygen -f /root/.ssh/id_rsa -p ''
NET=192.168.100
export SSHPASS=123.com
for IP in {1..222};do
sshpass -e ssh-copy-id $NET.$IP
done
格式
ansible <host-pattern> [-m module_name] [-a args]
选项说明:
选项说明
verslon #显示版本
-m module #指定模块,默认为 command
-v #井详细过程 -vv -vvv更详细
--list-hosts #显示主机列表,可简写--1ist
-k, --ask-pass #提示输入ssh连接密码,默认key验证
-C, --check #检查,并不执行
-T,-- tImeout=TIMEOUT #执行命令的超时时间,默认10s
-u,--user= REMOTE_USER#执行远程执行的用户
-b, --become #代替旧版的sudo切换
--become-user= USERNAME#指定sudo的 runas用户,默认为root
-K, --ask-become-pass #提示输入sudo时的口令
小实验 为什么会错误呢 因为第一次没有输入yes
启用起来 就不会爆出来
以及把他们的文件放进去了 为什么还失败了 默认基于key验证 所以就失败了 可以基于用户名密码
绿色代表成功 因为 192.168.10.18的密码和其他两台主机的密码不一样所以连接不成功 pong表示成功的意思
把192.168.10.18的密码改成和其他两位主机一样的密码就可以了
基于key验证就需要把ssh密钥发送给其他客户机
[root@node ~]# ssh-keygen
Generating public/private rsa key pair.
Enter file in which to save the key (/root/.ssh/id_rsa):
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /root/.ssh/id_rsa.
Your public key has been saved in /root/.ssh/id_rsa.pub.
The key fingerprint is:
SHA256:dXk3x4TEsUGdWI7iUBriR2vtgm46O9Iiby+UVHIBg98 root@node
The key's randomart image is:
+---[RSA 2048]----+
| .o.... o . +B=o|
| . ..o. o * o=*.|
| . = . *.oo.oo+|
| o E +.+... .o|
| . . .S. o |
| o . . |
| . . o |
| . = +o |
| +.=++ |
+----[SHA256]-----+
[root@node ~]# ssh-copy-id 192.168.10.16
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub"
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to install the new keys
root@192.168.10.16's password:
Number of key(s) added: 1
Now try logging into the machine, with: "ssh '192.168.10.16'"
and check to make sure that only the key(s) you wanted were added.
[root@node ~]# ssh-copy-id 192.168.10.17
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub"
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to install the new keys
root@192.168.10.17's password:
Number of key(s) added: 1
Now try logging into the machine, with: "ssh '192.168.10.17'"
and check to make sure that only the key(s) you wanted were added.
[root@node ~]# ssh-copy-id 192.168.10.18
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub"
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to install the new keys
root@192.168.10.18's password:
Number of key(s) added: 1
Now try logging into the machine, with: "ssh '192.168.10.18'"
and check to make sure that only the key(s) you wanted were added.
[root@node ~]# ansible all -m ping
192.168.10.18 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
192.168.10.16 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
192.168.10.17 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
查看以管理的机器 也可以是分组名字
[root@node ~]# ansible all --list-hosts
hosts (3):
192.168.10.16
192.168.10.17
192.168.10.18
通配符*
ansible命令执行过程
1.加载自己的配置文件 默认/etc/ansible/ansible.cfg
2.加载自己对应的模块文件,如:command
3.通过ansible将模块或命令生成对应的临时py文件,并将该文件传输至远程服务器的对应执行用户 $HOME/.ansible/tmp/ansible-tmp-数字/XXX.PY文件
4.给文件+x执行
5.执行并返回结果
6.删除临时py文件,退出
ansible的执行状态:
[root@node ~]# grep -A 13 '\[colors\]' /etc/ansible/ansible.cfg
[colors]
#highlight = white
#verbose = blue
#warn = bright purple
#error = red
#debug = dark gray
#deprecate = purple
#skip = cyan
#unreachable = red
#ok = green
#changed = yellow
#diff_add = green
#diff_remove = red
#diff_lines = cyan
- 绿色:执行成功并且不需要做改变的操作
- 黄色:执行成功并且对目标主机做变更
- 红色:执行失败
ansible-galaxy
此工具会连接https://galaxy.ansible.com下载相应的roles(角色)
ansible-pull
此工具会推送ansible的命令至远程,效率无限提升,对运维要求较高
ansible-playbook
此工具用于执行编写好的playbook任务
范例:
ansible-playbook hello.yml
cat hellp.yml
---
#hello word yml file
- hosts: websrvs
remote_user: root
tasks:
- name: hello word
command: /usr/bin/wall hello wold
ansible-vault
此工具可以用于加密解密yml文件
格式
ansible-vault [create|decrypt|edit|encrypt|rekey|view]
范例
ansible-vault encrypt hello.yml #加密
ansible-vault decrypt hello.yml #解密
ansible-vault view hello.yml #查看
ansible-vault edit hello.yml #编辑加密文件
ansible-vault rekey hello.yml #修改口令
ansible-vault create new.yml #创建新文件
ansible-console
此工具可交互执行命令,支持tab,ansible 2.0+新增
执行用户@当前操作的主机组(当前的主机数量)[f:并发量]$
常用子命令:
- 设置并发数:forks n 例如:forks 10
- 切换组: cd 主机组 例如:cd web
- 列出当前主机列表:list
Welcome to the ansible console.
Type help or ? to list commands.
root@all (3)[f:5]$ list
192.168.10.16
192.168.10.17
192.168.10.18
root@all (3)[f:5]$ cd appsrvs
root@appsrvs (3)[f:5]$ list
192.168.10.16
192.168.10.17
192.168.10.18
root@* (3)[f:5]$ cd websrvs
root@websrvs (2)[f:5]$ list
192.168.10.16
192.168.10.17
root@websrvs (2)[f:5]$ cd dbsrvs
root@dbsrvs (1)[f:5]$ list
192.168.10.17
root@dbsrvs (1)[f:5]$ cd
root@* (3)[f:5]$ forks 10
root@* (3)[f:10]$
Ansible常用模块 ansible-doc -s 可以查看模块用法
1.1.0 Command模块
功能:在远程主机执行命令,此为默认模块,可忽略-m选项
注意:此命令不支持$VARNAME < > | ; &等,用shell模块实现
范例:
[root@node ~]# ansible websrvs -m command -a 'cat /etc/centos-release'
#websrvs 指/etc/ansible/hosts 下面的组
192.168.10.17 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
192.168.10.16 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
[root@node ~]# ansible websrvs -m command -a 'chdir=/etc cat centos-release'
192.168.10.17 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
192.168.10.16 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
#跟这个意思一样
#[root@node ~]# cd /etc/ ; cat centos-release
#CentOS Linux release 7.9.2009 (Core)
[root@node etc]# ansible websrvs -m command -a 'chdir=/etc creates=/data/f1.txt cat centos-release'
192.168.10.17 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
192.168.10.16 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
creates的命令是如果这个文件存在将不会执行下一条命令 如果不存在将执行下一条命令
#如果在 IP 17 上有这个文件将不会执行下一条命令
[root@node ~]# ansible websrvs -m command -a 'chdir=/etc creates=/data/f1.txt cat centos-release'
192.168.10.17 | SUCCESS | rc=0 >>
skipped, since /data/f1.txt exists
192.168.10.16 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
removes 的命令是 creates 反过来的意思如果如这个文件的话 会执行下一条命令,如果没有的话将不会执行下一条命令
[root@node ~]# ansible websrvs -m command -a 'chdir=/etc removes=/data/f1.txt cat centos-release'
192.168.10.17 | CHANGED | rc=0 >>
CentOS Linux release 7.3.1611 (Core)
192.168.10.16 | SUCCESS | rc=0 >>
skipped, since /data/f1.txt does not exist
1.1.1 Shell模块
功能和:Command相似,用shell执行命令
范例
ansible wevsrvs -m shell -a 'echo 1234.com | passwd --stdin root '
[root@node ~]# ansible websrvs -m shell -a "echo $HOSTNAME"
192.168.10.16 | CHANGED | rc=0 >>
node
192.168.10.17 | CHANGED | rc=0 >>
node
[root@node ~]# ansible websrvs -m shell -a 'echo $HOSTNAME'
192.168.10.17 | CHANGED | rc=0 >>
localhost.localdomain
192.168.10.16 | CHANGED | rc=0 >>
localhost.localdomain
[root@node ~]# ansible websrvs -m shell -a ' echo hello > /tmp/hello.log'
192.168.10.17 | CHANGED | rc=0 >>
192.168.10.16 | CHANGED | rc=0 >>
[root@node ~]# ansible websrvs -m shell -a ' cat /tmp/hello.log'
192.168.10.17 | CHANGED | rc=0 >>
hello
192.168.10.16 | CHANGED | rc=0 >>
hello
[root@node ~]# ansible websrvs -m shell -a ' chdir=/tmp cat hello.log'
192.168.10.17 | CHANGED | rc=0 >>
hello
192.168.10.16 | CHANGED | rc=0 >>
hello
注意调用bash执行命令 类似cat/tmp/test.md | awk -F “|” ‘{print 1,2}’ &> /tmp/example.txt这些复杂命令,即使使用shell也可能会失败,解决办法:写到脚本时,copy到远程,执行,再把需要的结果拉回执行命令的机器
将默认模块command改为shell vim/etc/ansible/ansible.cfg
module_name = shell
1.1.2Script模块
功能:在远程主机上运行ansible服务器上的脚本
ansible websrvs -m script -a '/data/test.sh'
[root@node ~]# ansible websrvs -m script -a '/data/test.sh'
192.168.10.17 | CHANGED => {
"changed": true,
"rc": 0,
"stderr": "Shared connection to 192.168.10.17 closed.\r\n",
"stderr_lines": [
"Shared connection to 192.168.10.17 closed."
],
"stdout": "My hostname is localhost.localdomain\r\n",
"stdout_lines": [
"My hostname is localhost.localdomain"
]
}
192.168.10.16 | CHANGED => {
"changed": true,
"rc": 0,
"stderr": "Shared connection to 192.168.10.16 closed.\r\n",
"stderr_lines": [
"Shared connection to 192.168.10.16 closed."
],
"stdout": "My hostname is localhost.localdomain\r\n",
"stdout_lines": [
"My hostname is localhost.localdomain"
]
}
假如将这个脚本慢放100秒就会在客户端显示 一百秒之内显示一百秒之外就自动删除了crtl+c也会自动删除
[root@localhost ~]# tree .ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/
.ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/
└── test.sh
0 directories, 1 file
[root@localhost ~]# cat .ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/
cat: .ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/: 是一个目录
[root@localhost ~]# cat .ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/test.sh
#!/bin/bash
echo My hostname is `hostname`
sleep 100
[root@localhost ~]# cat .ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/test.sh
cat: .ansible/tmp/ansible-tmp-1628132275.04-75210-50548140935223/test.sh: 没有那个文件或目录
1.1.4Copy模块
功能:从ansible服务器主控端复制文件到远程主机
#指定内容,直接生成目标文件
ansible websrvs -m copy -a "content='test line1\ntest lin2' dest=/tmp/test.txt "
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"checksum": "4f4d8a96a04e881aa5295348dc1e4d0ebe19802b",
"dest": "/tmp/test.txt",
"gid": 0,
"group": "root",
"md5sum": "c644bb586fa388f2a4f29ed0dcb563f3",
"mode": "0644",
"owner": "root",
"secontext": "unconfined_u:object_r:admin_home_t:s0",
"size": 21,
"src": "/root/.ansible/tmp/ansible-tmp-1628168923.71-75698-249218734635622/source",
"state": "file",
"uid": 0
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"checksum": "4f4d8a96a04e881aa5295348dc1e4d0ebe19802b",
"dest": "/tmp/test.txt",
"gid": 0,
"group": "root",
"md5sum": "c644bb586fa388f2a4f29ed0dcb563f3",
"mode": "0644",
"owner": "root",
"secontext": "unconfined_u:object_r:admin_home_t:s0",
"size": 21,
"src": "/root/.ansible/tmp/ansible-tmp-1628168923.72-75699-4497557374337/source",
"state": "file",
"uid": 0
}
#查看是否生成
[root@node ~]# ansible websrvs -a "chdir=/tmp cat test.txt"
192.168.10.17 | CHANGED | rc=0 >>
test line1
test lin2
192.168.10.16 | CHANGED | rc=0 >>
test line1
test lin2
#将自己的文件传输到起到指定
[root@node ~]# ansible websrvs -m copy -a "src=/etc/centos-release dest=/tmp/os.txt owner=root mode=600"
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"checksum": "0d3186157c40752f89db0e618a5866935b523e7b",
"dest": "/tmp/os.txt",
"gid": 0,
"group": "root",
"md5sum": "902962816d0ec4fbb532949f70a41ae7",
"mode": "0600",
"owner": "root",
"secontext": "unconfined_u:object_r:admin_home_t:s0",
"size": 37,
"src": "/root/.ansible/tmp/ansible-tmp-1628169367.11-75893-7571866854172/source",
"state": "file",
"uid": 0
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"checksum": "0d3186157c40752f89db0e618a5866935b523e7b",
"dest": "/tmp/os.txt",
"gid": 0,
"group": "root",
"md5sum": "902962816d0ec4fbb532949f70a41ae7",
"mode": "0600",
"owner": "root",
"secontext": "unconfined_u:object_r:admin_home_t:s0",
"size": 37,
"src": "/root/.ansible/tmp/ansible-tmp-1628169367.14-75892-217136206457670/source",
"state": "file",
"uid": 0
}
[root@node ~]# ansible websrvs -a "cat /tmp/os.txt"
192.168.10.17 | CHANGED | rc=0 >>
CentOS Linux release 7.9.2009 (Core)
192.168.10.16 | CHANGED | rc=0 >>
CentOS Linux release 7.9.2009 (Core)
[root@node ~]# ansible websrvs -a "ls -l /tmp/os.txt"
192.168.10.17 | CHANGED | rc=0 >>
-rw-------. 1 root root 37 8月 5 21:16 /tmp/os.txt
192.168.10.16 | CHANGED | rc=0 >>
-rw-------. 1 root root 37 8月 5 21:16 /tmp/os.txt
#将目录拷贝过去
[root@node ~]# ansible websrvs -m copy -a "src=/etc/sysconfig dest=/tmp/ owner=root mode=600"
192.168.10.16 | CHANGED => {
"changed": true,
"dest": "/tmp/",
"src": "/etc/sysconfig"
}
192.168.10.17 | CHANGED => {
"changed": true,
"dest": "/tmp/",
"src": "/etc/sysconfig"
}
1.1.5Fetch模块
功能:从远程主机提取文件至ansible的主控端,copy相反,目前不支持目录
范例:
[root@node ~]# tree /data/os/
/data/os/
├── 192.168.10.16
│ └── etc
│ └── redhat-release
├── 192.168.10.17
│ └── etc
│ └── redhat-release
└── 192.168.10.18
└── etc
└── redhat-release
6 directories, 3 files
[root@node ~]# ansible all -m fetch -a 'src=/etc/redhat-release dest=/data/os'
1.1.6File模块
功能:设置文件属性
[root@node ~]# ansible websrvs -m file -a 'path=/data/test.txt state=touch'
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"dest": "/data/test.txt",
"gid": 0,
"group": "root",
"mode": "0644",
"owner": "root",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 0,
"state": "file",
"uid": 0
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"dest": "/data/test.txt",
"gid": 0,
"group": "root",
"mode": "0644",
"owner": "root",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 0,
"state": "file",
"uid": 0
}
[root@node ~]# ansible websrvs -a 'ls -l /data/test.txt'
192.168.10.17 | CHANGED | rc=0 >>
-rw-r--r--. 1 root root 0 8月 5 21:54 /data/test.txt
192.168.10.16 | CHANGED | rc=0 >>
-rw-r--r--. 1 root root 0 8月 5 21:54 /data/test.txt
[root@node ~]# ansible websrvs -m file -a 'path=/data/test.txt group=bin mode=666'
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"gid": 1,
"group": "bin",
"mode": "0666",
"owner": "root",
"path": "/data/test.txt",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 0,
"state": "file",
"uid": 0
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"gid": 1,
"group": "bin",
"mode": "0666",
"owner": "root",
"path": "/data/test.txt",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 0,
"state": "file",
"uid": 0
}
[root@node ~]# ansible websrvs -a 'ls -l /data/test.txt'
192.168.10.17 | CHANGED | rc=0 >>
-rw-rw-rw-. 1 root bin 0 8月 5 21:54 /data/test.txt
192.168.10.16 | CHANGED | rc=0 >>
-rw-rw-rw-. 1 root bin 0 8月 5 21:54 /data/test.txt
1.1.7unarchive模块
功能:解包解压缩
实现有两种用法:
1、将ansible主机上的压缩包传到远程主机后解压缩至特定目录,设置copy=yes
2、将远程主机上的某个压缩包解压压缩至指定路径下,设置copy=no
常见参数:
- copy:默认为yes,当copy=yes,拷贝的文件是从ansible主机复制到远程主机上,如果设置为copy=no,会在远程主机上寻找src源文件
- remote_src:和copy功能一样且互斥,yes表示在远程主机,不在ansible主机,no表示文件在ansible主机上
- src:源路径,可以是ansible主机上的路径,也可以是远程主机上的路劲,如果是远程主机上的路径,则需要设置copy=no
- dest:远程主机上的目标路径
- mode:设置解压缩后的文件权限
范例:
#将本地的tar,gz文件解压到其他机器
[root@node ~]# ansible websrvs -m unarchive -a 'src=/data/etc.tar.gz dest=/data/ owner=root'
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"dest": "/data/",
"extract_results": {
"cmd": [
"/usr/bin/gtar",
"--extract",
"-C",
"/data/",
"-z",
"--owner=root",
"-f",
"/root/.ansible/tmp/ansible-tmp-1628212890.8-78167-6385590959496/source"
],
"err": "",
"out": "",
"rc": 0
},
"gid": 0,
"group": "root",
"handler": "TgzArchive",
"mode": "0755",
"owner": "root",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 17,
"src": "/root/.ansible/tmp/ansible-tmp-1628212890.8-78167-6385590959496/source",
"state": "directory",
"uid": 0
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"dest": "/data/",
"extract_results": {
"cmd": [
"/usr/bin/gtar",
"--extract",
"-C",
"/data/",
"-z",
"--owner=root",
"-f",
"/root/.ansible/tmp/ansible-tmp-1628212890.79-78168-81835740355826/source"
],
"err": "",
"out": "",
"rc": 0
},
"gid": 0,
"group": "root",
"handler": "TgzArchive",
"mode": "0755",
"owner": "root",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 17,
"src": "/root/.ansible/tmp/ansible-tmp-1628212890.79-78168-81835740355826/source",
"state": "directory",
"uid": 0
}
[root@node ~]# ansible websrvs -m unarchive -a 'src=/data/etc.tar.gz dest=/data/ owner=root copy=yes'
#主控端将压缩包传输到客户端
[root@node ~]# ansible websrvs -m copy -a 'src=/data/etc.tar.xz dest=/data/'
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"checksum": "89b230a1bc50d8098bdf6b132a038a3c03ce3eda",
"dest": "/data/etc.tar.xz",
"gid": 0,
"group": "root",
"md5sum": "6cf81d9587c1449f3fdada07470097f5",
"mode": "0644",
"owner": "root",
"secontext": "system_u:object_r:default_t:s0",
"size": 8099436,
"src": "/root/.ansible/tmp/ansible-tmp-1628213207.03-78301-147337025091910/source",
"state": "file",
"uid": 0
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"checksum": "89b230a1bc50d8098bdf6b132a038a3c03ce3eda",
"dest": "/data/etc.tar.xz",
"gid": 0,
"group": "root",
"md5sum": "6cf81d9587c1449f3fdada07470097f5",
"mode": "0644",
"owner": "root",
"secontext": "system_u:object_r:default_t:s0",
"size": 8099436,
"src": "/root/.ansible/tmp/ansible-tmp-1628213207.0-78299-22615467353598/source",
"state": "file",
"uid": 0
}
#进行查看
[root@node ~]# ansible websrvs -a 'ls -l /data/'
192.168.10.16 | CHANGED | rc=0 >>
总用量 7924
drwxr-xr-x. 77 root root 8192 8月 6 09:06 etc
-rw-r--r--. 1 root root 8099436 8月 6 09:26 etc.tar.xz
192.168.10.17 | CHANGED | rc=0 >>
总用量 7924
drwxr-xr-x. 77 root root 8192 8月 6 09:06 etc
-rw-r--r--. 1 root root 8099436 8月 6 09:26 etc.tar.xz
#在主控端进行解包客户端的包 设置权限为700 copy=no 表示是在远程主机上解包
[root@node ~]# ansible websrvs -m unarchive -a 'src=/data/etc.tar.xz dest=/opt/ mode=700 copy=no'
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"dest": "/opt/",
"extract_results": {
"cmd": [
"/usr/bin/gtar",
"--extract",
"-C",
"/opt/",
"-f",
"/data/etc.tar.xz"
],
"err": "",
"out": "",
"rc": 0
},
"gid": 0,
"group": "root",
"handler": "TarArchive",
"mode": "0755",
"owner": "root",
"secontext": "system_u:object_r:usr_t:s0",
"size": 17,
"src": "/data/etc.tar.xz",
"state": "directory",
"uid": 0
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"dest": "/opt/",
"extract_results": {
"cmd": [
"/usr/bin/gtar",
"--extract",
"-C",
"/opt/",
"-f",
"/data/etc.tar.xz"
],
"err": "",
"out": "",
"rc": 0
},
"gid": 0,
"group": "root",
"handler": "TarArchive",
"mode": "0755",
"owner": "root",
"secontext": "system_u:object_r:usr_t:s0",
"size": 17,
"src": "/data/etc.tar.xz",
"state": "directory",
"uid": 0
}
[root@node ~]# ansible websrvs -a 'ls -l/opt/'
192.168.10.16 | FAILED | rc=2 >>
ls:无效选项 -- /
Try 'ls --help' for more information.non-zero return code
192.168.10.17 | FAILED | rc=2 >>
ls:无效选项 -- /
Try 'ls --help' for more information.non-zero return code
[root@node ~]# ansible websrvs -a 'ls -l /opt/'
192.168.10.17 | CHANGED | rc=0 >>
总用量 12
drwx------. 77 root root 8192 8月 6 09:06 etc
192.168.10.16 | CHANGED | rc=0 >>
总用量 12
drwx------. 77 root root 8192 8月 6 09:06 etc
[root@node ~]# ansible websrvs -a 'du -sh /opt/'
192.168.10.17 | CHANGED | rc=0 >>
36M /opt/
192.168.10.16 | CHANGED | rc=0 >>
36M /opt/
1.1.8Archive模块
功能:打包压缩
范例:
[root@node ~]# ansible websrvs -m archive -a 'path=/var/log/ dest=/data/log.tar.bz2 format=bz2 owner=root mode=0600'
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"archived": [
"/var/log/tallylog",
"/var/log/lastlog",
"/var/log/wtmp",
"/var/log/btmp",
"/var/log/messages",
"/var/log/secure",
"/var/log/maillog",
"/var/log/spooler",
"/var/log/vmware-vmsvc.log",
"/var/log/firewalld",
"/var/log/Xorg.9.log",
"/var/log/cron",
"/var/log/wpa_supplicant.log",
"/var/log/boot.log",
"/var/log/dmesg.old",
"/var/log/dmesg",
"/var/log/Xorg.0.log.old",
"/var/log/Xorg.0.log",
"/var/log/vmware-vmusr.log",
"/var/log/yum.log",
"/var/log/audit/audit.log",
"/var/log/gdm/:0.log.3",
"/var/log/gdm/:0.log.2",
"/var/log/gdm/:0.log.1",
"/var/log/gdm/:0.log",
"/var/log/gdm/:0-greeter.log.2",
"/var/log/gdm/:0-greeter.log.1",
"/var/log/gdm/:0-greeter.log",
"/var/log/cups/access_log",
"/var/log/cups/error_log",
"/var/log/cups/page_log",
"/var/log/tuned/tuned.log",
"/var/log/sa/sa24",
"/var/log/sa/sa11",
"/var/log/sa/sa05",
"/var/log/sa/sa06",
"/var/log/anaconda/anaconda.log",
"/var/log/anaconda/syslog",
"/var/log/anaconda/X.log",
"/var/log/anaconda/program.log",
"/var/log/anaconda/packaging.log",
"/var/log/anaconda/storage.log",
"/var/log/anaconda/ifcfg.log",
"/var/log/anaconda/ks-script-D4Gm2a.log",
"/var/log/anaconda/journal.log"
],
"arcroot": "/var/log/",
"changed": true,
"dest": "/data/log.tar.bz2",
"expanded_exclude_paths": [],
"expanded_paths": [
"/var/log/"
],
"gid": 0,
"group": "root",
"missing": [],
"mode": "0600",
"owner": "root",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 390428,
"state": "file",
"uid": 0
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"archived": [
"/var/log/tallylog",
"/var/log/lastlog",
"/var/log/wtmp",
"/var/log/btmp",
"/var/log/messages",
"/var/log/secure",
"/var/log/maillog",
"/var/log/spooler",
"/var/log/boot.log",
"/var/log/dmesg",
"/var/log/vmware-vmsvc.log",
"/var/log/firewalld",
"/var/log/Xorg.9.log",
"/var/log/cron",
"/var/log/wpa_supplicant.log",
"/var/log/Xorg.0.log.old",
"/var/log/Xorg.0.log",
"/var/log/vmware-vmusr.log",
"/var/log/yum.log",
"/var/log/audit/audit.log",
"/var/log/cups/access_log",
"/var/log/cups/error_log",
"/var/log/cups/page_log",
"/var/log/gdm/:0.log.1",
"/var/log/gdm/:0.log",
"/var/log/gdm/:0-greeter.log.1",
"/var/log/gdm/:0-greeter.log",
"/var/log/sa/sa14",
"/var/log/sa/sa05",
"/var/log/sa/sa06",
"/var/log/tuned/tuned.log",
"/var/log/anaconda/anaconda.log",
"/var/log/anaconda/syslog",
"/var/log/anaconda/X.log",
"/var/log/anaconda/program.log",
"/var/log/anaconda/packaging.log",
"/var/log/anaconda/storage.log",
"/var/log/anaconda/ifcfg.log",
"/var/log/anaconda/ks-script-CbRh53.log",
"/var/log/anaconda/journal.log"
],
"arcroot": "/var/log/",
"changed": true,
"dest": "/data/log.tar.bz2",
"expanded_exclude_paths": [],
"expanded_paths": [
"/var/log/"
],
"gid": 0,
"group": "root",
"missing": [],
"mode": "0600",
"owner": "root",
"secontext": "unconfined_u:object_r:default_t:s0",
"size": 352434,
"state": "file",
"uid": 0
}
[root@node ~]# ansible websrvs -a 'ls -l /data/log.tar.bz2 '
192.168.10.17 | CHANGED | rc=0 >>
-rw-------. 1 root root 390428 8月 6 09:35 /data/log.tar.bz2
192.168.10.16 | CHANGED | rc=0 >>
-rw-------. 1 root root 352434 8月 6 09:35 /data/log.tar.bz2
[root@node ~]# ansible websrvs -a 'file /data/log.tar.bz2 '
192.168.10.17 | CHANGED | rc=0 >>
/data/log.tar.bz2: bzip2 compressed data, block size = 900k
192.168.10.16 | CHANGED | rc=0 >>
/data/log.tar.bz2: bzip2 compressed data, block size = 900k
1.1.9Hostname模块
功能:管理主机名
范例:
[root@node ~]# ansible 192.168.10.16 -m hostname -a 'name=centos7.aqi'
192.168.10.16 | CHANGED => {
"ansible_facts": {
"ansible_domain": "aqi",
"ansible_fqdn": "centos7.aqi",
"ansible_hostname": "centos7",
"ansible_nodename": "centos7.aqi",
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"name": "centos7.aqi"
}
[root@node ~]# ansible 192.168.10.16 -a 'hostname'
192.168.10.16 | CHANGED | rc=0 >>
centos7.aqi
1.2.0Cron模块
功能:计划任务
支持时间:minute,day,month,weekday
范例:
1.2.1Yum模块
功能:管理软件包,只支持Rhel,CentOS,fedora,不支持Ubuntu其他版本
范例:
[root@node ~]# ansible all -m yum -a "name=httpd"
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"changes": {
"installed": [
"httpd"
]
},
"msg": "",
"rc": 0,
"results": [
"Loaded plugins: fastestmirror, langpacks\nLoading mirror speeds from cached hostfile\nResolving Dependencies\n--> Running transaction check\n---> Package httpd.x86_64 0:2.4.6-45.el7.centos will be installed\n--> Processing Dependency: httpd-tools = 2.4.6-45.el7.centos for package: httpd-2.4.6-45.el7.centos.x86_64\n--> Processing Dependency: /etc/mime.types for package: httpd-2.4.6-45.el7.centos.x86_64\n--> Processing Dependency: libaprutil-1.so.0()(64bit) for package: httpd-2.4.6-45.el7.centos.x86_64\n--> Processing Dependency: libapr-1.so.0()(64bit) for package: httpd-2.4.6-45.el7.centos.x86_64\n--> Running transaction check\n---> Package apr.x86_64 0:1.4.8-3.el7 will be installed\n---> Package apr-util.x86_64 0:1.5.2-6.el7 will be installed\n---> Package httpd-tools.x86_64 0:2.4.6-45.el7.centos will be installed\n---> Package mailcap.noarch 0:2.1.41-2.el7 will be installed\n--> Finished Dependency Resolution\n\nDependencies Resolved\n\n================================================================================\n Package Arch Version Repository Size\n================================================================================\nInstalling:\n httpd x86_64 2.4.6-45.el7.centos yum 2.7 M\nInstalling for dependencies:\n apr x86_64 1.4.8-3.el7 yum 103 k\n apr-util x86_64 1.5.2-6.el7 yum 92 k\n httpd-tools x86_64 2.4.6-45.el7.centos yum 84 k\n mailcap noarch 2.1.41-2.el7 yum 31 k\n\nTransaction Summary\n================================================================================\nInstall 1 Package (+4 Dependent packages)\n\nTotal download size: 3.0 M\nInstalled size: 10 M\nDownloading packages:\n--------------------------------------------------------------------------------\nTotal 15 MB/s | 3.0 MB 00:00 \nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n Installing : apr-1.4.8-3.el7.x86_64 1/5 \n Installing : apr-util-1.5.2-6.el7.x86_64 2/5 \n Installing : httpd-tools-2.4.6-45.el7.centos.x86_64 3/5 \n Installing : mailcap-2.1.41-2.el7.noarch 4/5 \n Installing : httpd-2.4.6-45.el7.centos.x86_64 5/5 \n Verifying : httpd-tools-2.4.6-45.el7.centos.x86_64 1/5 \n Verifying : mailcap-2.1.41-2.el7.noarch 2/5 \n Verifying : apr-1.4.8-3.el7.x86_64 3/5 \n Verifying : httpd-2.4.6-45.el7.centos.x86_64 4/5 \n Verifying : apr-util-1.5.2-6.el7.x86_64 5/5 \n\nInstalled:\n httpd.x86_64 0:2.4.6-45.el7.centos \n\nDependency Installed:\n apr.x86_64 0:1.4.8-3.el7 apr-util.x86_64 0:1.5.2-6.el7 \n httpd-tools.x86_64 0:2.4.6-45.el7.centos mailcap.noarch 0:2.1.41-2.el7 \n\nComplete!\n"
]
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"changes": {
"installed": [
"httpd"
]
},
"msg": "",
"rc": 0,
"results": [
"Loaded plugins: fastestmirror, langpacks\nLoading mirror speeds from cached hostfile\nResolving Dependencies\n--> Running transaction check\n---> Package httpd.x86_64 0:2.4.6-45.el7.centos will be installed\n--> Finished Dependency Resolution\n\nDependencies Resolved\n\n================================================================================\n Package Arch Version Repository Size\n================================================================================\nInstalling:\n httpd x86_64 2.4.6-45.el7.centos yum 2.7 M\n\nTransaction Summary\n================================================================================\nInstall 1 Package\n\nTotal download size: 2.7 M\nInstalled size: 9.4 M\nDownloading packages:\nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n Installing : httpd-2.4.6-45.el7.centos.x86_64 1/1 \n Verifying : httpd-2.4.6-45.el7.centos.x86_64 1/1 \n\nInstalled:\n httpd.x86_64 0:2.4.6-45.el7.centos \n\nComplete!\n"
]
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"changes": {
"installed": [
"httpd"
]
},
"msg": "",
"rc": 0,
"results": [
"Loaded plugins: fastestmirror, langpacks\nLoading mirror speeds from cached hostfile\n * base: mirrors.aliyun.com\n * extras: mirrors.aliyun.com\n * updates: mirrors.aliyun.com\nResolving Dependencies\n--> Running transaction check\n---> Package httpd.x86_64 0:2.4.6-97.el7.centos will be installed\n--> Processing Dependency: httpd-tools = 2.4.6-97.el7.centos for package: httpd-2.4.6-97.el7.centos.x86_64\n--> Processing Dependency: /etc/mime.types for package: httpd-2.4.6-97.el7.centos.x86_64\n--> Running transaction check\n---> Package httpd-tools.x86_64 0:2.4.6-97.el7.centos will be installed\n---> Package mailcap.noarch 0:2.1.41-2.el7 will be installed\n--> Finished Dependency Resolution\n\nDependencies Resolved\n\n================================================================================\n Package Arch Version Repository Size\n================================================================================\nInstalling:\n httpd x86_64 2.4.6-97.el7.centos updates 2.7 M\nInstalling for dependencies:\n httpd-tools x86_64 2.4.6-97.el7.centos updates 93 k\n mailcap noarch 2.1.41-2.el7 base 31 k\n\nTransaction Summary\n================================================================================\nInstall 1 Package (+2 Dependent packages)\n\nTotal download size: 2.8 M\nInstalled size: 9.6 M\nDownloading packages:\n--------------------------------------------------------------------------------\nTotal 5.8 MB/s | 2.8 MB 00:00 \nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n Installing : httpd-tools-2.4.6-97.el7.centos.x86_64 1/3 \n Installing : mailcap-2.1.41-2.el7.noarch 2/3 \n Installing : httpd-2.4.6-97.el7.centos.x86_64 3/3 \n Verifying : httpd-2.4.6-97.el7.centos.x86_64 1/3 \n Verifying : mailcap-2.1.41-2.el7.noarch 2/3 \n Verifying : httpd-tools-2.4.6-97.el7.centos.x86_64 3/3 \n\nInstalled:\n httpd.x86_64 0:2.4.6-97.el7.centos \n\nDependency Installed:\n httpd-tools.x86_64 0:2.4.6-97.el7.centos mailcap.noarch 0:2.1.41-2.el7 \n\nComplete!\n"
]
}
[root@node ~]# ansible all -a "rpm -qa httpd"
[WARNING]: Consider using the yum, dnf or zypper module rather than running 'rpm'. If
you need to use command because yum, dnf or zypper is insufficient you can add 'warn:
false' to this command task or set 'command_warnings=False' in ansible.cfg to get rid
of this message.
192.168.10.17 | CHANGED | rc=0 >>
httpd-2.4.6-45.el7.centos.x86_64
192.168.10.18 | CHANGED | rc=0 >>
httpd-2.4.6-45.el7.centos.x86_64
192.168.10.16 | CHANGED | rc=0 >>
httpd-2.4.6-97.el7.centos.x86_64
[root@node ~]# ansible all -a "rpm -qi httpd" #查看包是否安装
[WARNING]: Consider using the yum, dnf or zypper module rather than running 'rpm'. If
you need to use command because yum, dnf or zypper is insufficient you can add 'warn:
false' to this command task or set 'command_warnings=False' in ansible.cfg to get rid
of this message.
192.168.10.18 | CHANGED | rc=0 >>
Name : httpd
Version : 2.4.6
Release : 45.el7.centos
Architecture: x86_64
Install Date: 2021年08月05日 星期四 19时28分49秒
Group : System Environment/Daemons
Size : 9807149
License : ASL 2.0
Signature : RSA/SHA256, 2016年11月20日 星期日 10时14分03秒, Key ID 24c6a8a7f4a80eb5
Source RPM : httpd-2.4.6-45.el7.centos.src.rpm
Build Date : 2016年11月14日 星期一 10时06分40秒
Build Host : c1bm.rdu2.centos.org
Relocations : (not relocatable)
Packager : CentOS BuildSystem <http://bugs.centos.org>
Vendor : CentOS
URL : http://httpd.apache.org/
Summary : Apache HTTP Server
Description :
The Apache HTTP Server is a powerful, efficient, and extensible
web server.
192.168.10.17 | CHANGED | rc=0 >>
Name : httpd
Version : 2.4.6
Release : 45.el7.centos
Architecture: x86_64
Install Date: 2021年08月06日 星期五 10时28分51秒
Group : System Environment/Daemons
Size : 9807149
License : ASL 2.0
Signature : RSA/SHA256, 2016年11月21日 星期一 02时14分03秒, Key ID 24c6a8a7f4a80eb5
Source RPM : httpd-2.4.6-45.el7.centos.src.rpm
Build Date : 2016年11月15日 星期二 02时06分40秒
Build Host : c1bm.rdu2.centos.org
Relocations : (not relocatable)
Packager : CentOS BuildSystem <http://bugs.centos.org>
Vendor : CentOS
URL : http://httpd.apache.org/
Summary : Apache HTTP Server
Description :
The Apache HTTP Server is a powerful, efficient, and extensible
web server.
192.168.10.16 | CHANGED | rc=0 >>
Name : httpd
Version : 2.4.6
Release : 97.el7.centos
Architecture: x86_64
Install Date: 2021年08月06日 星期五 10时28分54秒
Group : System Environment/Daemons
Size : 9821064
License : ASL 2.0
Signature : RSA/SHA256, 2020年11月18日 星期三 22时17分43秒, Key ID 24c6a8a7f4a80eb5
Source RPM : httpd-2.4.6-97.el7.centos.src.rpm
Build Date : 2020年11月17日 星期二 00时21分17秒
Build Host : x86-02.bsys.centos.org
Relocations : (not relocatable)
Packager : CentOS BuildSystem <http://bugs.centos.org>
Vendor : CentOS
URL : http://httpd.apache.org/
Summary : Apache HTTP Server
Description :
The Apache HTTP Server is a powerful, efficient, and extensible
web server.
卸载 httpd包 state=absent就是卸载的意思
[root@node ~]# ansible all -m yum -a "name=httpd state=absent"
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"changes": {
"removed": [
"httpd"
]
},
"msg": "",
"rc": 0,
"results": [
"已加载插件:fastestmirror, langpacks\n正在解决依赖关系\n--> 正在检查事务\n---> 软件包 httpd.x86_64.0.2.4.6-45.el7.centos 将被 删除\n--> 解决依赖关系完成\n\n依赖关系解决\n\n================================================================================\n Package 架构 版本 源 大小\n================================================================================\n正在删除:\n httpd x86_64 2.4.6-45.el7.centos @yum 9.4 M\n\n事务概要\n================================================================================\n移除 1 软件包\n\n安装大小:9.4 M\nDownloading packages:\nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n 正在删除 : httpd-2.4.6-45.el7.centos.x86_64 1/1 \n 验证中 : httpd-2.4.6-45.el7.centos.x86_64 1/1 \n\n删除:\n httpd.x86_64 0:2.4.6-45.el7.centos \n\n完毕!\n"
]
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"changes": {
"removed": [
"httpd"
]
},
"msg": "",
"rc": 0,
"results": [
"已加载插件:fastestmirror, langpacks\n正在解决依赖关系\n--> 正在检查事务\n---> 软件包 httpd.x86_64.0.2.4.6-45.el7.centos 将被 删除\n--> 解决依赖关系完成\n\n依赖关系解决\n\n================================================================================\n Package 架构 版本 源 大小\n================================================================================\n正在删除:\n httpd x86_64 2.4.6-45.el7.centos @yum 9.4 M\n\n事务概要\n================================================================================\n移除 1 软件包\n\n安装大小:9.4 M\nDownloading packages:\nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n 正在删除 : httpd-2.4.6-45.el7.centos.x86_64 1/1 \n 验证中 : httpd-2.4.6-45.el7.centos.x86_64 1/1 \n\n删除:\n httpd.x86_64 0:2.4.6-45.el7.centos \n\n完毕!\n"
]
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"changes": {
"removed": [
"httpd"
]
},
"msg": "",
"rc": 0,
"results": [
"已加载插件:fastestmirror, langpacks\n正在解决依赖关系\n--> 正在检查事务\n---> 软件包 httpd.x86_64.0.2.4.6-97.el7.centos 将被 删除\n--> 解决依赖关系完成\n\n依赖关系解决\n\n================================================================================\n Package 架构 版本 源 大小\n================================================================================\n正在删除:\n httpd x86_64 2.4.6-97.el7.centos @updates 9.4 M\n\n事务概要\n================================================================================\n移除 1 软件包\n\n安装大小:9.4 M\nDownloading packages:\nRunning transaction check\nRunning transaction test\nTransaction test succeeded\nRunning transaction\n 正在删除 : httpd-2.4.6-97.el7.centos.x86_64 1/1 \n 验证中 : httpd-2.4.6-97.el7.centos.x86_64 1/1 \n\n删除:\n httpd.x86_64 0:2.4.6-97.el7.centos \n\n完毕!\n"
]
}
1.2.2 Service模块
功能:管理服务
范例:
[root@node ~]# ansible all -m service -a "name=httpd state=started"
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"name": "httpd",
"state": "started",
"status": {
"ActiveEnterTimestampMonotonic": "0",
"ActiveExitTimestampMonotonic": "0",
[root@node ~]# ansible all -a "ss -ntl"
192.168.10.16 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6010 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::80 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6010 :::*
192.168.10.17 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6010 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::80 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6010 :::*
192.168.10.18 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6011 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::80 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6011 :::*
[root@node ~]# ansible all -m service -a "name=httpd state=stopped"
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"name": "httpd",
"state": "stopped",
"status": {
"ActiveEnterTimestamp": "四 2021-08-05 19:39:22 PDT",
"ActiveEnterTimestampMonotonic": "11611676350",
"ActiveExitTimestampMonotonic": "0",
"ActiveState": "active",
"After": "remote-fs.target system.slice tmp.mount systemd-journald.socket nss-lookup.target basic.target -.mount network.target",
"AllowIsolate": "no",
"AssertResult": "yes",
"AssertTimestamp": "四 2021-08-05 19:39:22 PDT",
"AssertTimestampMonotonic": "11611575514",
"Before": "shutdown.target",
"BlockIOAccounting": "no",
"BlockIOWeight": "18446744073709551615",
"CPUAccounting": "no",
"CPUQuotaPerSecUSec": "infinity",
"CPUSchedulingPolicy": "0",
"CPUSchedulingPriority": "0",
"CPUSchedulingResetOnFork": "no",
"CPUShares": "18446744073709551615",
"CanIsolate": "no",
}
[root@node ~]# ansible all -a "ss -ntl"
192.168.10.16 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6010 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6010 :::*
192.168.10.17 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6010 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6010 :::*
192.168.10.18 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6011 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6011 :::*
#将80端口修改成8080
[root@node ~]# ansible all -a "sed -i 's/^Listen 80/Listen 8080/' /etc/httpd/conf/httpd.conf"
[root@localhost ~]# grep ^Listen /etc/httpd/conf/httpd.conf
Listen 80
[root@localhost ~]# grep ^Listen /etc/httpd/conf/httpd.conf
Listen 8080
#重启httpd服务 并且查看是否改变
[root@node ~]# ansible all -m service -a "name=httpd state=restarted" &>/dev/null
[root@node ~]#
[root@node ~]# ansible all -a "ss -ntl"
192.168.10.16 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6010 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::8080 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6010 :::*
192.168.10.17 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6010 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::8080 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6010 :::*
192.168.10.18 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:111 *:*
LISTEN 0 5 192.168.122.1:53 *:*
LISTEN 0 128 *:22 *:*
LISTEN 0 128 127.0.0.1:631 *:*
LISTEN 0 100 127.0.0.1:25 *:*
LISTEN 0 128 127.0.0.1:6011 *:*
LISTEN 0 128 :::111 :::*
LISTEN 0 128 :::8080 :::*
LISTEN 0 128 :::22 :::*
LISTEN 0 128 ::1:631 :::*
LISTEN 0 100 ::1:25 :::*
LISTEN 0 128 ::1:6011 :::*
1.2.3 User模块
功能:管理用户
1.2.4Group模块
1.2.5Lineinfile模块
ansible在使用sed进行替换时,经常会遇到需要转义的问题,而已ansible在遇到特殊符号进行替换时,存在问题,无法正常进行替换。其实在ansible自身提供了两个模块:;ineinfile模块和replace模块,可以方便的进行替换
功能:相当于sed,可以修改文件内容
范例:
[root@node ~]# ansible all -m lineinfile -a "path=/etc/selinux/config regexp='^SELINUX=' line='SELINUX=disabled' "
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"backup": "",
"changed": true,
"msg": "line replaced"
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"backup": "",
"changed": true,
"msg": "line replaced"
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"backup": "",
"changed": true,
"msg": "line replaced"
}
[root@node ~]# ansible all -a "cat /etc/selinux/config "
192.168.10.17 | CHANGED | rc=0 >>
# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
# enforcing - SELinux security policy is enforced.
# permissive - SELinux prints warnings instead of enforcing.
# disabled - No SELinux policy is loaded.
SELINUX=disabled
# SELINUXTYPE= can take one of three two values:
# targeted - Targeted processes are protected,
# minimum - Modification of targeted policy. Only selected processes are protected.
# mls - Multi Level Security protection.
SELINUXTYPE=targeted
192.168.10.18 | CHANGED | rc=0 >>
# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
# enforcing - SELinux security policy is enforced.
# permissive - SELinux prints warnings instead of enforcing.
# disabled - No SELinux policy is loaded.
SELINUX=disabled
# SELINUXTYPE= can take one of three two values:
# targeted - Targeted processes are protected,
# minimum - Modification of targeted policy. Only selected processes are protected.
# mls - Multi Level Security protection.
SELINUXTYPE=targeted
192.168.10.16 | CHANGED | rc=0 >>
# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
# enforcing - SELinux security policy is enforced.
# permissive - SELinux prints warnings instead of enforcing.
# disabled - No SELinux policy is loaded.
SELINUX=disabled
# SELINUXTYPE= can take one of three two values:
# targeted - Targeted processes are protected,
# minimum - Modification of targeted policy. Only selected processes are protected.
# mls - Multi Level Security protection.
SELINUXTYPE=targeted
去掉以#开头的行
[root@node ~]# ansible all -m lineinfile -a 'dest=/etc/fstab state=absent regexp="^#"'
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"backup": "",
"changed": true,
"found": 7,
"msg": "7 line(s) removed"
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"backup": "",
"changed": true,
"found": 7,
"msg": "7 line(s) removed"
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"backup": "",
"changed": true,
"found": 7,
"msg": "7 line(s) removed"
}
[root@node ~]# ansible all -a "cat /etc/fstab "
192.168.10.18 | CHANGED | rc=0 >>
UUID=59e57886-f23a-4fc4-b553-30218a4ecb63 / xfs defaults 0 0
UUID=bb2989b3-5461-4fdd-814a-f5398e452c51 /boot xfs defaults 0 0
UUID=2216e66a-8cda-4840-bac7-b553f4337750 swap swap defaults 0 0
192.168.10.17 | CHANGED | rc=0 >>
/dev/mapper/cl-root / xfs defaults 0 0
UUID=82f03d9d-21a6-4f18-8af2-2f630a0263fc /boot xfs defaults 0 0
/dev/mapper/cl-swap swap swap defaults 0 0
192.168.10.16 | CHANGED | rc=0 >>
/dev/mapper/cl-root / xfs defaults 0 0
UUID=702c12b4-224b-4679-9913-8c66e80cc466 /boot xfs defaults 0 0
/dev/mapper/cl-swap swap swap defaults 0 0
1.26 Replace模块
该模块有点类似于sed命令,主要也是基于正则进行匹配和替换
范例:
以uuid开头的行加上注释
[root@node ~]# ansible all -m replace -a "path=/etc/fstab regexp='^(UUID.*)' replace='#\1'"
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"msg": "1 replacements made"
}
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"msg": "1 replacements made"
}
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"msg": "3 replacements made"
}
[root@node ~]# ansible all -a "cat /etc/fstab "
192.168.10.18 | CHANGED | rc=0 >>
#UUID=59e57886-f23a-4fc4-b553-30218a4ecb63 / xfs defaults 0 0
#UUID=bb2989b3-5461-4fdd-814a-f5398e452c51 /boot xfs defaults 0 0
#UUID=2216e66a-8cda-4840-bac7-b553f4337750 swap swap defaults 0 0
192.168.10.17 | CHANGED | rc=0 >>
/dev/mapper/cl-root / xfs defaults 0 0
#UUID=82f03d9d-21a6-4f18-8af2-2f630a0263fc /boot xfs defaults 0 0
/dev/mapper/cl-swap swap swap defaults 0 0
192.168.10.16 | CHANGED | rc=0 >>
/dev/mapper/cl-root / xfs defaults 0 0
#UUID=702c12b4-224b-4679-9913-8c66e80cc466 /boot xfs defaults 0 0
/dev/mapper/cl-swap swap swap defaults 0 0
去掉以#开头的
[root@node ~]# ansible all -m replace -a "path=/etc/fstab regexp='^#(.*)' replace='\1'"
192.168.10.17 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"msg": "1 replacements made"
}
192.168.10.16 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"msg": "1 replacements made"
}
192.168.10.18 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"msg": "3 replacements made"
}
[root@node ~]# ansible all -a "cat /etc/fstab "
192.168.10.17 | CHANGED | rc=0 >>
/dev/mapper/cl-root / xfs defaults 0 0
UUID=82f03d9d-21a6-4f18-8af2-2f630a0263fc /boot xfs defaults 0 0
/dev/mapper/cl-swap swap swap defaults 0 0
192.168.10.16 | CHANGED | rc=0 >>
/dev/mapper/cl-root / xfs defaults 0 0
UUID=702c12b4-224b-4679-9913-8c66e80cc466 /boot xfs defaults 0 0
/dev/mapper/cl-swap swap swap defaults 0 0
192.168.10.18 | CHANGED | rc=0 >>
UUID=59e57886-f23a-4fc4-b553-30218a4ecb63 / xfs defaults 0 0
UUID=bb2989b3-5461-4fdd-814a-f5398e452c51 /boot xfs defaults 0 0
UUID=2216e66a-8cda-4840-bac7-b553f4337750 swap swap defaults 0 0
1.2.7 Setup模块
功能:setup模块来收集主机的系统信息,这些facts信息可以直接以变量的形式使用,如果主机较多,会影响执行速度,可以使用gather_facts:no
来禁止Ansible收集facts信息
范例:
[root@node ~]# ansible 192.168.10.16 -m setup
[root@node ~]# ansible all -m setup -a 'filter=ansible_distribution_major_version'
192.168.10.17 | SUCCESS => {
"ansible_facts": {
"ansible_distribution_major_version": "7",
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false
}
192.168.10.18 | SUCCESS => {
"ansible_facts": {
"ansible_distribution_major_version": "7",
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false
}
192.168.10.16 | SUCCESS => {
"ansible_facts": {
"ansible_distribution_major_version": "7",
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false
}
[root@node ~]# ansible all -m setup -a "filter=ansible_all_ipv4_addresses"
192.168.10.18 | SUCCESS => {
"ansible_facts": {
"ansible_all_ipv4_addresses": [
"192.168.122.1",
"192.168.10.18"
],
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false
}
192.168.10.17 | SUCCESS => {
"ansible_facts": {
"ansible_all_ipv4_addresses": [
"192.168.122.1",
"192.168.10.17"
],
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false
}
192.168.10.16 | SUCCESS => {
"ansible_facts": {
"ansible_all_ipv4_addresses": [
"192.168.122.1",
"192.168.10.16"
],
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false
}
Playbook
playbook介绍
playbook剧本是由一个或多个“play”组成的列表
play的主要功能在于将预定义的一组主机,装扮成事先通过ansible中的task定义好的角色。Task实际是调用ansible的一个module,将多个play组织在一个playbook中,既可以让他们联合起来,按事先编排的机制执行预定义动作
Playbook文件时采用YAML语言编写的
2.1.1YAML语言
YAML是一个可读性高的用来表达资料序列的格式,YAML参考了其他多种语言,包括:XML、C语言、Python、Perl以及电子邮件格式RFC2822等。Clark Evans在2001年在首次发表了这种语言,另外ingy dot Net于 Oren Ben-Kiki也是这语言的共同设计者,目前很多软件中采有此格式的文件,如:ubuntu、ansible、docker、k8s等
YAML:YAML Ain‘t Markup Language,即YAML不是XML。不过在开发的这种语言时,YAML的意思其实是“Yet Another Markup Language”(仍是一种标记语言)
YAML 官方网站:http://www.yaml.org
2.1.2YAML语言特训给
- YAML的可读性好
- YAML和脚本语言的交互性好
- YANL使用实现语言的数据类型
- YAML有一个一致的信息模式
2.1.3YAML语法简介
- 在单一文件第一行,用连续三个连字符"-"开始,还有选择性的连续三个点号(…)用来表示文件的结尾
- 次行开始正常些Playbook的内容,一般建议写明该Playbook的功能
- 使用#号注释代码
- 缩进必须是统一的,不能空格和tab混用
- 缩进的级别也必须是一致的,同样的缩进代表同样的级别,程序判别配置的级别是通过缩进结合换行来实现的YAML文件内容是区别大小写的,key/value的值均需大小写名敏感
- 多个k/v可同行写也可以换行写,同时使用,分割
- v可是哥字符串,可也是另一个列表
- 一个完整的代码块功能需最少元素需包括name和task
- 一个name只能包括一个task
- YAML文件扩展名通常为yml或yaml
YAML的语法和其他高阶语言类似,并且可以简单表达清单、散列表、标量等数据结构、其结构通过空格来展示,序列里的项用"-"来代表,Map里的键值对用“.”分割,下面介绍常见的数据结构
2.1.3.1 List列表
列表由多个元素组成,且所有元素前均使用“-”大头
范例:
# A list of tasty fruits
- Apple
- Orange
- Strawberry
- Mango
[Apple,Orange,Strawberry,Mango]
2.1.3.2 Dictionary
子典通常由多个key于value构成
范例:
# An employee record
name: Example Developer
job: Developer
skill: Elite
也可以将key:value放置于[]中进行表示,用,分割多个key:value
#An employee record
{name: “Example Developer”,job: "Developer",skill: "Eilte"}
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2XiOoA65-1637840564487)(D:/Typora/image-20210809095459470.png)]
2.1.4 三种常见的数据格式
- XML: Extensible Markup Language,可扩展标记语言,用于数据交换和配置
- JSON: JavaScript Object Notation .JavaScprit对象标记法,主要用来数据交换或配置,不支持注释
- YAML: YAML Aint’t Markup Language YAML 不是一种标记语言,主要用来配置,大小写敏感,不支持tab
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LX08Qmju-1637840564488)(D:/Typora/image-20210809100323012.png)]
可以用工具互相转换,参考网站:
https://www.json2yaml.com/
http://www,bejson.com/json/json2yaml/
2.2Playbook核心元素
- Hosts 执行远程主机列表
- Tasks 任务集
- Variables内置变量或自定义变量在playbook中调用
- Templates模块,可替换模板文件中的变量并实现一些简单逻辑文件
- Hadnlers和notify结合使用,由特定条件触发的操作,满足条件方才执行,否则不执行
- tags标签:只当某条任务执行,用于选择运行playbook中的部分代码。ansible具有幂等性。因此会自动跳过没有变化的部分,即便如此,有些代码为测试其确实没有变化的时间依然会非常地长,此时,如果确信其没有变化,就可以通过tags跳过这些代码片段
2.2.1 hosts组件
Hosts:playbook中的每一个play的母的都是为了让特定主机以某个指定用户身份执行任务,hosts用于指定要执行指定任务的主机。须事先定义在主机清单中
one.example.com
one.example.com:twoexample.com
192.168.10.16
192.166.10.*
websrvs:dbsrvs #或者,两个组的并集
websrvs:&dbsrvs #与,两个组的交集
websrvs:!phoenix #在websrvs组,但不在dbsrvs组
案例:
- hosts: websrvs:appsrvs
2.2.2 remote_user组件
remote_user:可用于Host和task中。也可以通过指定其通过sudo的方式在远程主机上执行任务。其可用于play全局或某任务:此外,甚至可以在速冻时使用sudo_user指定sudo时切换的用户
- host: websrvs
remote_user: root
|
tasks:
- name: test cibbection
ping:
remote_user: laowang
sudo: yes #默认sudo为root
sudo_user:wang #sudo为wang
2.2.3task列表和action组件
play的主体部分时task list,task list中有一个或多个task,各个task按次序逐个在hosts中指定的所有主机上执行,即在所有主机上完成第一个task后,再开始第二个task
task的目的时使用指定的参数执行模块,而在模块参数中可以使用变量,模块执行是幂等的,这意味着多次执行时安全的,因为其结构均一致
每个task都应该有其name,用于playbook的执行结果输出,建议其内容能清晰地描述任务执行步骤。如果未提供name,则action的结果将用于输出
task两种格式:
(1)action:module arguments
(2)module:arguments 建议使用
注意:shell和cimmand模块后面跟命令,而非key=value
---
- hosts:websrvs
remote_user: root
tasks:
- name: install httpd
yum: name=httpd
- name: start httpd
service: name=httpd state=started enabled=yes
2.2.3 其它组件
某任务的状态在运行后为changed时,可通过“notify”通知给相应的handiers
任务可以哦通过“tags”打标签,可在ansible-playbook命令上使用-t指定进行调用
2.2.4 ShellScripts VS Playbook案例
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-UE9optD2-1637840564489)(D:/Typora/image-20210810091150367.png)]
2.3.0 playbook命令
格式
ansible-play <filename.yml> … [options]
常见选项
-C --list #只检查可能会发生的改变,但不真正执行操作
--list-hosts #列出运行任务的主机
--list-tags #列出tag
--list-tasks #列出task
--limic 主机列表 #只针对主机列表中的主机执行
-v -vv -vvv #显示过程
范例
ansible-playbook file.yml --check#只检测
ansible-playbook file.yml
ansible-playbook file.yml --list websrvs
2.4 Playbook初步
利用playbook创建mysql用户
范例:mysql_user.yml
---
- hosts: dbsrvs
remote_user: root
tasks:
- name: create group
group: name=mysql system=yes gid=306
- name: create user
user: name=mysql shell=/sbin/nologin system=yes group=mysql uid=306 home=/tmp/mysql create_home=
***
[root@ansible ansible]# ansible-playbook create_mysql.yml
PLAY [dbsrvs] ******************************************************************
TASK [create group] ************************************************************
changed: [192.168.10.17]
changed: [192.168.10.16]
TASK [create user] *************************************************************
changed: [192.168.10.16]
changed: [192.168.10.17]
PLAY RECAP *********************************************************************
192.168.10.16 : ok=2 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
192.168.10.17 : ok=2 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
[root@ansible ansible]# ansible dbsrvs -a 'getent passwd mysql'
192.168.10.16 | CHANGED | rc=0 >>
mysql:x:306:306::/data/mysql:/sbin/nologin
192.168.10.17 | CHANGED | rc=0 >>
mysql:x:306:306::/data/mysql:/sbin/nologin
[root@ansible ansible]# ansible dbsrvs -a 'id mysql'
192.168.10.16 | CHANGED | rc=0 >>
uid=306(mysql) gid=306(mysql) 组=306(mysql)
192.168.10.17 | CHANGED | rc=0 >>
uid=306(mysql) gid=306(mysql) 组=306(mysql)
2.4.1利用playbook按照nginx
范例:install_nginx.yml
---
install
- hosts: websrvs
remote_user: root
tasks:
- name: add group nginx
user: name=nginx state=present
- name: add user nginx
user: name=nginx state=present group=nginx
- name: install Nginx
yum: name=nginx state=present
- name: html page
copy: src=files/index.html dest=/usr/share/nginx/html/index.html
- name: Start Nginx
service: name=nginx state=started enabled=yes
2.4.2利用playbook安装和卸载httpd
范例:
[root@localhost httpd]# ansible-playbook --syntax-check install_httpd.yml
---
#install httpd
- hosts: websrvs
remote_user: root
gather_facts: no
tasks:
- name: Install httpd
yum: name=httpd state=present
- name: Install configure file
copy: src=files/httpd.conf dest=/etc/httpd/httpd.conf
- name: start service
service: name=httpd state=started enabled=yes
ansible-playbook install_httpd.yml --limit 192.168.10.16
删除httpd
---
- hosts: websrvs
remote_user: root
gather_facts: no
tasks:
- name: remove httpd package
yum: name=httpd state=absent
- name: remove apache user
user: name=apache state=absent
- name: remove config file
file: name=/etc/httpd state=absent
- name: remove web html
file: name=/vat/www/html/index.html state=absent
2.5.1Playbook使用handler和notify
handlers本质是task list,类似于MySql中的触发器触发的行为,其中的task与前述的task没有本质上的不同主要用于关注的资源发生变化时,才会采取一定的操作。而Notify对应的action可用于在每个paly的最后被触发,这样可避免多次有改变发生时每次都执行指定的操作,仅在所有的变法发生完成后一次性地执行指定操作。在notify中列出的操作称为handler,也即notify中调用handler中定义的操作
案例:yum -y install lrzsz
---
#install httpd
- hosts: websrvs
remote_user: root
gather_facts: no
tasks:
- name: Install httpd
yum: name=httpd state=present
- name: Install configure file
copy: src=files/httpd.conf dest=/etc/httpd/httpd.conf
notify: restart httpd
- name: start service
service: name=httpd state=started enabled=yes
handlers:
- name: restart httpd
service: name=httpd state=restarted
2.6.1Playbook中使用tags组件
在playbook文件中,可以利用tags组件,为特定task指定标签,当在执行playbook时,可以只执行特定tags的task,而非整个playbook
案例:
---
#install httpd
- hosts: websrvs
remote_user: root
gather_facts: no
tasks:
- name: Install httpd
yum: name=httpd state=present
- name: Install configure file
copy: src=files/httpd.conf dest=/etc/httpd/httpd.conf
tags: conf
- name: start service
service: name=httpd state=started enabled=yes
ansible-playbook -t conf,service httpd.yml
2.7.1Playbook中使用变量
变量名:仅能由字母、数字和下划线组成、且只能以字母开头
变量定义:
variadble=value
范例:
http_port=80
变量调用方式:
通过{{ variable_name }}调用变量,且变量名前后建议加空格,有时用"{{ variable_name }}"才生效
变量来源:
1.ansible的setup facts远程主机的所有变量都可直接调用
2.通过命令行指定变量,优先级最高
ansible-playbook -e varname=value
3.在playbook文件中定义
vars:
- var1: value1
- var2: value2
范例: 使用setup模块中变量
要求在playbook中使用,不用ansible命令调用(会有问题的)
---
#var.yml
- hosts: websrvs
remote_user: root
tasks:
- name: create log file
file: name=/var/log/{{ ansible_fqdn }}.log state=touch
#var.yml
- hosts: websrvs
remote_user: root
tasks:
- name: create log file
file: name=/data/{{ ansible_nodename }}.log state=touch owner=root mode=600
2.7.2在playbook命令行中定义变量
范例:
[root@ansible ansible]# cat var2.yml
---
- hosts: websrvs
remote_user: root
tasks:
- name: install package
yum: name={{ pkname }} state=present
[root@ansible ansible]# ansible-playbook -e pkname=memcached var2.yml
PLAY [websrvs] *************************************************************************************
TASK [Gathering Facts] *****************************************************************************
ok: [192.168.10.16]
ok: [192.168.10.17]
TASK [install package] ****************************************************************************
changed: [192.168.10.17]
changed: [192.168.10.16]
PLAY RECAP *****************************************************************************************
192.168.10.16 : ok=2 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
192.168.10.17 : ok=2 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
范例
---
- hosts: websrvs
remote_user: root
vars:
- username: user1
- groupname: group1
tasks:
- name: create group
group: name={{ groupname }} state=present
- name: create user
user: name={{ username }} group={{ groupname }} state=present
2.7.3使用变量
可以在一个独立的playbook文件中定义变量,在另一个playbook文件中引用变量文件的变量
比playbook中定义的变量优先级高
vim vars.yml
---
#variadb file
package_name: vsftpd
service_name: vsftpd
vim var4.yml
---
#install app and configure
- hosts: appsrvs
remote_user:root
vars_files:
- vars.yml
tasks:
- name: install package
yum: name={{ pack_name }}
tags: install
- name: start service
service: name={{ service_name }} state=started enabled=yes
handlers:
ansible-playbook var4.yml
2.7.4主机清单文件中定义变量
主机变量:
在inventory主机清单文件中为指定的主机定义变量以便于在playbook中使用
范例:
[wesrvs]
www1.aqlinux.com http_port=80 maxRequestsPerChild=808
www2.aqlinux.com http_port=8080 maxRequestsRerChild=909
组(公共)变量:
在inventory主机清单文件中赋予给指定组内所有主机上的在playbook中可用的变量
[websrvs]
www1.aqlinux.com
www2.aqlinux.com
[websrvs:vars]
ntp_server=ntp.aqlinux.com
nfs_server=nfs.aqlinux.com
范例:
[websrvs]
192.168.10.16 http_port=8080 hname=www1
192.168.10.17 http_port=80 hname=www2
2.8template模块
模块是一个文本文件,可以做为生成文件的模块,并且模块文件中还可嵌套jinjayufa
网站https://jinja.palletsprojects.com/en/2,11x/
2.8.1jinja2语言
jinja2语言使用字面量,有下面形式:
字符串:使用单引号或双引号
数字:整数,浮点数
列表:[ltem1,item2…]
元组:[item1,item2…]
字典:[key1:value1,key2:value2…]
布尔型: true/false
算术运算: +,-,*,/,//,%,**
比较运算符: ==,!=,>,>=,<,<=
逻辑运算:and,or,not
流表达式:For,if,when
字面量
表达式最简单的新式就是字面量,字面量表示诸如字符串和数值的Python对象,如"Hellp Word"双引号或单引号中间的一切都是字符串,无论何时你需要在模板中使用一个字符串(比如函数调用,过滤器或只是包含或继承一个模板的参数)如42,43
数据可以为整数和浮点数,如果有小数点,则为浮点数,否则为整数,在Python里,42和42.0是不一样的
算数运算
jinja允许用计算值,支持下面的运算符
+:把两个对象加到一起。通常对象是素质,但是如果两者是字符串或列表,你可以用这种方式来斜街它们,无论如何这不是首选的连接字符串的方式。连接字符串~运算符。{{1+1}}等于2
-:用第一个数减去第二个数{{3-2}}等于1
/:对两个数做处罚的余数,返回值是一个浮点数、{{1/2}}等于{{0.5}}
//:对两个数做触发返回正整数。{{20//7}}等于2
%:计算整数除法的余数、{{11%7}}等于4
*:用右边的数乘左边的操作数。{{ 2 * 2 }} 会返回4,也可以用于重复一个字符串多次。{{’=’*80}}会打印80整个等号的横条
**:取左操作数的右操作数的次幂。{{2 * * 3}}会返回8
比较操作符
==:比较两个对象是否相等
!=:比较两个对象是否不等
》 如果左边大于右边返回true
》= 如果左边大于等于右边返回true
《如果左边小于右边 返回true
《= 如果左边小于等于右边 返回true
逻辑运算符
对于if语句,在for过滤或if表达式中,它可以用于联合多个表达式
and 如果左操作数和右操作数为真则返回true
or 如果左操作数和右操作数有一个为真则返回true
not 对一个表达式取反
{expr}表达式组
true/false true永远是true, 而false始终是false
2.8.2 template
templaste功能:可以根据和参考模块文件,动态生成相类似的配置文件
template文件必须存放于templates目录下,且命名为.j2结尾
yaml/yml 文件需和template目录平级
案例 vim templnginx.yml
mkdir template
yum -y install nginx
cp /etc/nginx/nginx.conf template/nginx.conf.j2
---
- hosts: websrvs
remote_user: root
tasks:
- name: install nginx
yum: name=nginx
- name: template config to remote hosts
template: src=nginx.conf.j2 dest=/etc/nginx/nginx.conf
- name: start service
service: name=nginx state=started enabled=yes
template算术运算
范例:
vim nginx.conf.j2
worker_processes {{ ansible_processor_vcpus**2 }}
worker_processes {{ ansible_processor_vcpu+2 }}
范例:
cat templnginx.yml
---
- hosts: websrvs
remote_user: root
tasks:
- name: install nginx
yum: name=nginx
- name: template config to remote hosts
template: src=nginx.conf.j2 dest=/etc/nginx/nginx.conf
notify: restart nginx
- name: start service
service: name=nginx state=started enabled=yes
handlers:
- name: restart nginx
service: name=nginx state=restarted
2.8.3 template中使用流程控制for和if
template中也可以使用流程控制for循环和if条件判断,实现动态生成文件功能
2.8.4playbook使用when
when语句,可以实现条件测试。如果需要根据变量,facts或此前任务的执行结果来做为某task执行与否的前提时要用到条件测试,通过在task后添加when子句即可使用条件测试,jinja2的语法格式
范例
---
- hosts: websrvs
remote_user: root
tasks:
- name: "shutdown RedHat flavored systems"
command: /sbin/shutdown -h now
when: ansible_os_family == "RedHat"
范例:
---
- hosts: websrvs
remote——user: root
tasks:
- name: add froup nginx
tags: user
user: name=nginx state=present
- name: add user nginx
user: name=nginx state=present group=nginx
- name: Install nginx
yum: name=nginx state=present
- name: restart nginx
service: name=nginx state=restarted
when: ansible_distribution_major_version == "6"
范例:
---
- hosts: websrvs
remote_user: root
tasks:
- name: install conf file to centos
template: src=nginx.conf.c7.j2 dest=/data/nginx.conf
when: ansible_distribution_major_version =="7"
- name: install conf file to centos6
template: src=nginx.conf.c6.j2 dest=/etc/nginx/nginx.conf
when: ansible_distribution_major_version =="6"
2.8.6playbook使用迭代with_items
迭代:当有需要重复执行任务时,可以使用迭代机制
对迭代项的引用,固定变量名为”item“
要在task中使用with_items给定要迭代的元素列表
列表元素格式:
- 字符串
- 字典
范例
---
- hosts: websrvs
remote_user: root
tasks:
- name: add servsral users
user: name={{ item }} state=present groups=wheel
with_items:
- testuser1
- testuser2
#上面语句的功能等同于下面的语句
- name: add user testuser1
user: name=testuser1 state=present groups=wheel
- name: add user testuser2
user: name=testuser2 state=prenent groups=wheel
#查看是否成功
[root@ansible ansible]# ansible websrvs -a 'getent passwd'
testuser1:x:1003:1003::/home/testuser1:/bin/bash
testuser2:x:1004:1004::/home/testuser2:/bin/bash
[root@ansible ansible]# ansible websrvs -a 'id testuser1'
192.168.10.16 | CHANGED | rc=0 >>
uid=1003(testuser1) gid=1003(testuser1) 组=1003(testuser1),10(wheel)
192.168.10.17 | CHANGED | rc=0 >>
uid=1003(testuser1) gid=1003(testuser1) 组=1003(testuser1),10(wheel)
范例
---
#remove mariadb server
- hosts: websrvs:!192.168.10.17
remote_user: root
tasks:
- name: stop service
shell: /etc/init.d/mysql/stop
- name: delecte files and dir
file: path={{ item }} state=absent
with_items:
- /usr/local/mysql
- /usr/local/mariadb-10.2.27-linux-x86_64
- /etc/init.d/mysqld
- /etc/profile.d/mysql.sh
- /etc/my.cnf
- /data/mysql
- name: delete user
user: name=mysql state=absent remove=yes
范例
---
- hosts: websrvs
remote_user: root
taks
- name: install some packages
yum: name={{ item }} state=present
with_items:
- nginx
- mencached
- php-fpm
范例:
---
- hosts: websrvs
remote_user: root
tasks:
- name: copy file
copy: src={{ item }} dest=/tmp/{{ item }}
with_items:
- file1
- file2
- file3
- name: yum install httpd
yum: name={{ item }} state=present
with_items:
- apr
- apr-util
- httpd
迭代嵌套子变量:在迭代中,还可以嵌套子变量,关联多个变量在一起使用
---
- hosts: websrvs
remote_user: root
tasks:
- name: add some groups
group: name={{ item }} state=present
with_items:
- nginx
- mysql
- apache
- name: add some users
user: name={{ item.name }} group={{ item.group }} state=present
with_items:
- { name: 'nginx',group: 'nginx' }
- { name: 'mysql',group: 'mysql' }
- { name: 'apache',group: 'apache'}
范例:
[root@ansible ansible]# cat with_item2.yml
---
- hosts: websrvs
remote_user: root
tasks:
- name: add some groups
group: name={{ item }} state=present
with_items:
- g1
- g2
- g3
- name: add some users
user: name={{ item.name }} group={{ item.group }} home={{ item.home }} create_home=yes state=present
with_items:
- { name: 'user11', group: 'g1', home: '/data/user1' }
- { name: 'user22', group: 'g2', home: '/data/user2' }
- { name: 'user33', group: 'g3', home: '/data/user3' }
################
[root@ansible ansible]# ansible websrvs -a 'id user11'
192.168.10.16 | CHANGED | rc=0 >>
uid=1005(user11) gid=1005(g1) 组=1005(g1)
192.168.10.17 | CHANGED | rc=0 >>
uid=1005(user11) gid=1005(g1) 组=1005(g1)
[root@ansible ansible]# ansible websrvs -a 'getent passwd user11'
192.168.10.16 | CHANGED | rc=0 >>
user11:x:1005:1005::/data/user1:/bin/bash
192.168.10.17 | CHANGED | rc=0 >>
user11:x:1005:1005::/data/user1:/bin/bash
[root@ansible ansible]# ansible websrvs -a 'ls -l /data'
192.168.10.16 | CHANGED | rc=0 >>
总用量 0
-rw-------. 1 root root 0 8月 15 16:04 bogon.log
drwx------. 3 user11 g1 78 8月 17 09:49 user1
drwx------. 3 user22 g2 78 8月 17 09:49 user2
drwx------. 3 user33 g3 78 8月 17 09:49 user3
192.168.10.17 | CHANGED | rc=0 >>
总用量 0
-rw-------. 1 root root 0 8月 15 16:04 bogon.log
drwx------. 3 user11 g1 78 8月 17 09:49 user1
drwx------. 3 user22 g2 78 8月 17 09:49 user2
drwx------. 3 user33 g3 78 8月 17 09:49 user3
3 roles角色
角色是ansible自1.2版本引入的新特性,用于层次性,结构化地组织playbook。roles能够根据层次性结构自动装载变量。tasks以及handlers等。要使用roles只需要在playbook中使用include指令即可,简单来讲,roles就是通过分别将变量、文件、任务、模块及处理器放置于单独的目录中,并可以便捷地include他们的一种机制。角色一般用于基于主机构建服务的场景中,但也可以构建守护进程等场景中
运维复杂的场景:建议使用roles,代码复用度很高
roles:多个角色的集合,可以将很多个的role,分别放至roles目录下的独立子目录中
roles/
mysql/
httpd/
nginx/
redis/
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-UcbWYOui-1637840564490)(D:/Typora/image-20210817101431550.png)]
每个角色,以特定的层级目录结构进行组织
roles目录结构
playbook.yml
roles/
project/
tasks/
files/
vars/
templates/
handlers/
default/
meta/
Roles各目录作用
roles/project/:项目名称,有以下子目录
- files/:存放由copy或script模块等调用的文件
- templates/: remplate模块查找所需要模板文件的目录
- tasks/:定义task,role的基本元素,至少应该包含一个名为main.yml文件;其它的文件需要在此文件中通过include进行包含
- handlers/: 至少应该包含一个名为main.yml的文件:其它的文件需要在此文件中通过include进行包含
- vars/:定义变量,至少应该包含一个名为main.yml的文件;其他的文件需要在此文件中通过include进行包含
- meta/: 定义当前角色的特殊设定及其依赖关系,至少应该包含一个名为main.yml其他文件需在此文件中通过include进行包含
- default/: 设定默认变量时使用此目录中的main.yml文件,比vars的优先级低
3.2创建role
创建role的步骤
(1)创建以roles命名的目录
(2)在roles目录中分别创建以各角色名称命名的目录,如webservers等
(3)在每个角色命令的目录中分别创建files、handlers、meta、tasks、templates、和vars目录;用不到的目录可以创建为空目录,也可以不创建
(4)在playbook文件中,调用各角色
针对大型项目使用Roles进行编排
范例:roles的目录结构
3.3playbook调用角色
调用角色方法1
---
- hosts: websrvs
remote_user: root
roles:
- mysql
- memcached
- nginx
调用角色方法2
键role用于指定角色名称,后续的k/v用于传递变量的角色
---
- hosts: all
remote_user: root
roles:
- mysql
- { role: nginx, username: nginx }
调用角色方法3
还可以基于条件测试实现角色调用
---
- hosts: all
remote_user: root
roles:
- { role: nginx, username: nginx, when: ansible_distribution_major_version == '7' }
3.4 roles中tags使用
---
- hosts: websrvs
remote_user: root
roles:
- { role: nginx ,tags: [ 'nginx','web' ] ,when: ansible_distribution_major_version =="7" }
- { role: httpd ,tags: [ 'httpd','web'] }
- { role: mysql ,tags: [ 'mysql','db' ] }
- { role: mariadb ,tags: [ 'mariadb','db' ] }
ansible-playbook --tags="nginx.httpd.mysql" nginx-role.yml
创建一个httpd角色
创建所在角色需要得yml文件和必要得启动程序main.yml
创建roles角色这个目录
最好在roles目录下创建
[root@ansible ansible]# ansible-galaxy list
# /root/.ansible/roles
- nginxinc.nginx, 0.20.0
# /usr/share/ansible/roles
# /etc/ansible/roles
***
这里我们在/data/ansible/创建
mkdir roles
mkdir httpd/{tasks,files,handlers} -pv 在roles下创建httpd这个角色所需要得东西
[root@ansible ansible]# tree roles/
roles/
└── httpd
├── files
│ ├── httpd.conf
│ └── index.html
├── handlers
│ └── main.yml
└── tasks
├── config.yml
├── index.yml
├── install.yml
├── main.yml
└── service.yml
vim roles/httpd/tasks/install.yml
- name: install httpd package
yum: name=httpd
vim roles/httpd/tasks/config.yml
- name: config file
copy: src=httpd.conf dest=/etc/httpd/conf/ backup=yes
notify: restart
#这里指定了 handles 所以待会要创建 src源文件从/etc/httpd下拷贝一份到 files下起名为httpd.conf 修改端口号为9527
vim roles/httpd/tasks/index.yml
- name: index.html
copy: src=index.html dest=/var/www/html/
#####设置个网页文件为html 本地的html文件创建在files下
vim roles/httpd/tasks/service.yml
- name: starte service
service: name=httpd state=started enabled=yes
集合上边所说的需要一个handlers文件所以现在要去写一个
vim roles/httpd/handlers/main.yml
- name: restart
service: name=httpd state=restarted
做到这里以及创建快完成了写一个启动的文件
vim roles/httpd/tasks/main.yml
- include: install.yml
- include: config.yml
- include: index.yml
- include: service.yml
在再与roles这个角色目录 同等目录下创建启动httpd的yml文件
vim /data/ansible/role_httpd.yml
---
# httpd role
- hosts: websrvs
remote_user: root
roles:
- httpd
就可以执行此角色了
ansible-playbook role_httpd.yml
在查看被控端是否有9527这个端口 如果有就是启动成功了
[root@ansible ansible]# ansible websrvs -a 'ss -ntl'
192.168.10.17 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port LISTEN 0 128 :::9527 :::*
192.168.10.16 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port LISTEN 0 128 :::9527 :::*
##创建一个memcacheed角色
[root@ansible ansible]# tree roles/memcached/
roles/memcached/
├── tasks
│ ├── config.yml
│ ├── install.yml
│ ├── main.yml
│ └── service.yml
└── templates
└── memcached.j2
创建一个运算集
[root@ansible tasks]# cat main.yml
- include: install.yml
- include: config.yml
- include: service.yml
[root@ansible tasks]# cat install.yml
- name: install
yum: name=memcached
[root@ansible tasks]# cat service.yml
- name: service
service: name=memcached state=started enabled=yes
[root@ansible tasks]# cat config.yml
- name: config file
template: src=memcached.j2 dest=/etc/sysconfig/memcached
[root@ansible tasks]# cat ../templates/memcached.j2
PORT="11211"
USER="memcached"
MAXCONN="1024"
CACHESIZE="{{ansible_memtotal_mb//4}}"
OPTIONS=""
在同级目录(roles)创建一个role_memcached.yml
[root@ansible ansible]# cat role_memcached.yml
---
- hosts: websrvs
roles:
- role: memcached
[root@nb ~]# cat /etc/sysconfig/memcached
PORT="11211"
USER="memcached"
MAXCONN="1024"
CACHESIZE="244"
OPTIONS=""
[root@nb ~]# ss -ntl
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:11211 *:*
ansible学习资料
http://galaxy.ansible.com
https://galaxy.ansible.com/explore#/
http://github.com/
http://ansible.com.cn/
https://github.com/ansible/ansible
install.yml
├── main.yml
└── service.yml
vim roles/httpd/tasks/install.yml
- name: install httpd package
yum: name=httpd
vim roles/httpd/tasks/config.yml - name: config file
copy: src=httpd.conf dest=/etc/httpd/conf/ backup=yes
notify: restart
#这里指定了 handles 所以待会要创建 src源文件从/etc/httpd下拷贝一份到 files下起名为httpd.conf 修改端口号为9527
vim roles/httpd/tasks/index.yml - name: index.html
copy: src=index.html dest=/var/www/html/
#####设置个网页文件为html 本地的html文件创建在files下
vim roles/httpd/tasks/service.yml - name: starte service
service: name=httpd state=started enabled=yes
集合上边所说的需要一个handlers文件所以现在要去写一个
vim roles/httpd/handlers/main.yml - name: restart
service: name=httpd state=restarted
做到这里以及创建快完成了写一个启动的文件
vim roles/httpd/tasks/main.yml - include: install.yml
- include: config.yml
- include: index.yml
- include: service.yml
在再与roles这个角色目录 同等目录下创建启动httpd的yml文件
vim /data/ansible/role_httpd.yml
httpd role
-
hosts: websrvs
remote_user: rootroles:
- httpd
就可以执行此角色了
ansible-playbook role_httpd.yml
在查看被控端是否有9527这个端口 如果有就是启动成功了
[root@ansible ansible]# ansible websrvs -a ‘ss -ntl’
192.168.10.17 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port LISTEN 0 128 :::9527 ::😗
192.168.10.16 | CHANGED | rc=0 >>
State Recv-Q Send-Q Local Address:Port Peer Address:Port LISTEN 0 128 :::9527 ::😗
- httpd
```bash
##创建一个memcacheed角色
[root@ansible ansible]# tree roles/memcached/
roles/memcached/
├── tasks
│ ├── config.yml
│ ├── install.yml
│ ├── main.yml
│ └── service.yml
└── templates
└── memcached.j2
创建一个运算集
[root@ansible tasks]# cat main.yml
- include: install.yml
- include: config.yml
- include: service.yml
[root@ansible tasks]# cat install.yml
- name: install
yum: name=memcached
[root@ansible tasks]# cat service.yml
- name: service
service: name=memcached state=started enabled=yes
[root@ansible tasks]# cat config.yml
- name: config file
template: src=memcached.j2 dest=/etc/sysconfig/memcached
[root@ansible tasks]# cat ../templates/memcached.j2
PORT="11211"
USER="memcached"
MAXCONN="1024"
CACHESIZE="{{ansible_memtotal_mb//4}}"
OPTIONS=""
在同级目录(roles)创建一个role_memcached.yml
[root@ansible ansible]# cat role_memcached.yml
---
- hosts: websrvs
roles:
- role: memcached
[root@nb ~]# cat /etc/sysconfig/memcached
PORT="11211"
USER="memcached"
MAXCONN="1024"
CACHESIZE="244"
OPTIONS=""
[root@nb ~]# ss -ntl
State Recv-Q Send-Q Local Address:Port Peer Address:Port
LISTEN 0 128 *:11211 *:*
ansible学习资料
http://galaxy.ansible.com
https://galaxy.ansible.com/explore#/
http://github.com/
http://ansible.com.cn/
https://github.com/ansible/ansible
https://github.com/ansible-examples