4.4 Ansible常用模块介绍

Ansible有很多模块,包括云计算、命令行、包管理、系统服务、用户管理等,可以通过官方网站http://docs.ansible.com/modules_by_category.html 查看相应的模块,也可以在命令行下通过ansible-doc-l命令查看模块,或者通过ansible-doc-s模块名查看具体某个模块的使用方法。官网的介绍比较详细,建议查看官网介绍。ansible-doc-l命令的部分显示结果如下所示:

less comes with NO WARRANTY, to the extent permitted by law.

广告:个人专属 VPN,独立 IP,无限流量,多机房切换,还可以屏蔽广告和恶意软件,每月最低仅 5 美元

For information about the terms of redistribution,

see the file named README in the less distribution.

Homepage: http://www.greenwoodsoftware.com/less

a10_server Manage A10 Networks AX/SoftAX/Thunder/vThunder devices

a10_service_group Manage A10 Networks AX/SoftAX/Thunder/vThunder devices

a10_virtual_server Manage A10 Networks AX/SoftAX/Thunder/vThunder devices

acl Sets and retrieves file ACL information.

add_host add a host (and alternatively a group) to the ansible- playbook in-memory inventory

airbrake_deployment Notify airbrake about app deployments

alternatives Manages alternative programs for common commands

apache2_module enables/disables a module of the Apache2 webserver

apt Manages apt-packag

apt_key Add or remove an apt key

apt_repository Add and remove APT repositories

apt_rpm apt_rpm package manager

assemble Assembles a configuration file from fragments

assert Fail with custom message

at Schedule the execution of a command or script file via the at command.

authorized_key Adds or removes an SSH authorized key

azure create or terminate a virtual machine in azure

bigip_facts Collect facts from F5 BIG-IP devices

bigip_monitor_http Manages F5 BIG-IP LTM http monitors

bigip_monitor_tcp Manages F5 BIG-IP LTM tcp monitors

bigip_node Manages F5 BIG-IP LTM nodes

bigip_pool Manages F5 BIG-IP LTM pools

bigip_pool_member Manages F5 BIG-IP LTM pool members

bigpanda Notify BigPanda about deployments

boundary_meter Manage boundary meters

bower Manage bower packages with bower

bzr Deploy software (or files) from bzr branches

campfire Send a message to Campfire

capabilities Manage Linux capabilities

阅读 ‧ 电子书库

注意

Ansible的模块实现的行为是冥等性(idempotence)的,只需要运行一次playbook就可以将需要配置的机器都置为期望状态。这是一个非常赞的特性,因为它意味着向同一台机器多次执行一个playbook是安全的。

Ansible命令行调用模块的语法如下:

ansible 操作目标

-m 模块名

-a 模块参数

下面将分别介绍运维工作中经常会用到13个模块,其他模块在本书中就不再一一介绍了,具体详情建议大家参考官方文档。

·setup模块

·copy模块

·synchronize模块

·file模块

·ping模块

·group模块

·user模块

·shell模块

·script模块

·get_url模块

·yum模块

·cron模块

·service模块

1.setup模块

该模块可用于获取Ansible客户端机器的详细信息,命令如下:

absible webserver(机器组名

) -m setup

命令显示的部分结果如下(完整结果太详细了,这里只截取了部分显示):

192.168.1.206 | success >> {

"ansible_facts": {

"ansible_all_ipv4_addresses": [

"192.168.1.206"

],

"ansible_all_ipv6_addresses": [

"fe80::216:3eff:fe08:ea2b"

],

"ansible_architecture": "x86_64",

"ansible_bios_date": "",

"ansible_bios_version": "",

"ansible_cmdline": {

"KEYTABLE": "us",

"LANG": "en_US.UTF-8",

"SYSFONT": "latarcyrheb-sun16",

"console": "hvc0",

"quiet": true,

"rd_LVM_LV": "VolGroup/lv_root",

"rd_NO_DM": true,

"rd_NO_LUKS": true,

"rd_NO_MD": true,

"rhgb": true,

"ro": true,

"root": "/dev/mapper/VolGroup-lv_root"

},

"ansible_date_time": {

"date": "2015-11-25",

"day": "25",

"epoch": "1448418484",

"hour": "02",

"iso8601": "2015-11-25T02:28:04Z",

"iso8601_micro": "2015-11-25T02:28:04.467675Z",

"minute": "28",

"month": "11",

"second": "04",

"time": "02:28:04",

"tz": "UTC",

"tz_offset": "+0000",

"weekday": "Wednesday",

"year": "2015"

},

2.copy模块

该模块可实现Ansible主机向客户端传送文件的功能,类似于scp,请大家记得提前关闭所有机器的SELinux功能,不然会出现如下报错:

192.168.1.205 | FAILED >> {

"checksum": "d3869c634275c17b9a0561b1f9ac02f685353a53",

"failed": true,

"msg": "Aborting, target uses selinux but python bindings (libselinux-python) aren't installed!"

}

192.168.1.206 | FAILED >> {

"checksum": "d3869c634275c17b9a0561b1f9ac02f685353a53",

"failed": true,

"msg": "Aborting, target uses selinux but python bindings (libselinux-python) aren't installed!"

}

如果出现上述错误,我们该如何修复呢?需要在被控端安装libselinux-python包来进行修复,命令如下所示:

ansible webserver -m command -a "yum -y install libselinux-python"

修复错误以后,再次输入copy模块的命令,如下:

ansible webserver -m copy -a "src=/usr/local/src/test.py dest=/tmp/ owner=root group=root mode=0755 force=yes"

其他参数都比较好理解,这里解释下force参数和backup参数。

·force:如果目标主机包含该文件,但内容不同,则设置为yes后会强制覆盖,设置为no后,只有当目标主机的目标位置不存在该文件时,才复制该文件到目标主机;默认值为yes。

·backup:在覆盖之前备份源文件,备份文件包含时间。该参数有两个选项yes和no。

命令显示结果如下所示:

192.168.1.206 | success >> {

"changed": false,

"checksum": "da39a3ee5e6b4b0d3255bfef95601890afd80709",

"dest": "/tmp/test.py",

"gid": 0,

"group": "root",

"mode": "0755",

"owner": "root",

"path": "/tmp/test.py",

"size": 0,

"state": "file",

"uid": 0

}

192.168.1.205 | success >> {

"changed": false,

"checksum": "da39a3ee5e6b4b0d3255bfef95601890afd80709",

"dest": "/tmp/test.py",

"gid": 0,

"group": "root",

"mode": "0755",

"owner": "root",

"path": "/tmp/test.py",

"size": 0,

"state": "file",

"uid": 0

}

阅读 ‧ 电子书库

注意

copy模块跟rsync命令一样,如果路径使用“/”来结尾,则只复制目录里的内容;如果没有使用“/”来结尾,则包含目录在内的整个内容全部被复制。

3.synchronize模块

由于synchronize模块会调用rsync命令,因此首先要记得提前安装好rsync软件包。

synchronize模块用于将Ansible机器的指定目录推送(push)到客户机器的指定目录下,命令如下:

ansible 192.168.1.206 -m synchronize -a "src=/usr/local/src/ dest=/usr/local/src/ delete=yes compress=yes "

显示结果如下所示:

192.168.1.206 | success >> {

"changed": true,

"cmd": "rsync --delay-updates -F --compress --delete-after --archive --rsh 'ssh -S none -o StrictHostKeyChecking=no' --out-format='<<CHANGED>>%i %n%L' \"/usr/local/src/\" \"root@192.168.1.206:/usr/local/src/\"",

"msg": ".d..t...... ./\n

"rc": 0,

"stdout_lines": [

".d..t...... ./",

"

"

"

]

}

其中,delete=yes用来实现使两边的内容一样(即以push方式为主),实现效果跟rsync--delete效果一样,如果是客户端不存在的文件或目录则增补,如果存在着不同的文件或目录则删除,以保证两边内容一致。

compress=yes用于开启压缩,默认为开启。

另外,由于synchronize模块调用的是rsync命令,因此如果路径使用“/”来结尾,则只复制目录里的内容;如果没有使用“/”来结尾,则包含目录在内的整个内容全部被复制。

4.file模块

file模块主要用来设置文件或目录的属性。

·group:定义文件或目录的属组。

·mode:定义文件或目录的权限。

·owner:定义文件或目录的属主。

·path:必选项,定义文件或目录的路径。

·recurse:递归设置文件的属性,只对目录有效。

·src:被链接的源文件路径,只应用于state=link的情况。

·dest:被链接到的路径,只应用于state=link的情况。

·force:强制创建软链接,有两种情况,一种是源文件不存在,但之后会建立的情况;另一种是要先取消已创建的软链接,再创建新的软链接,有两个选项yes和no。

·state:后面连接文件的各种状态,例如下面的directory、link、hard、file及absent。

·link:创建软链接。

·hard:创建硬链接。

·directory:如果目录不存在,则创建目录。

·file:即使文件不存在,也不会被创建。

·absent:删除目录、文件或链接文件。

·touch:如果文件不存在,则会创建一个新的文件,如果文件或目录已存在,则更新其最后的修改时间,这一点跟Linux的touch命令效果是一样的。

示例一:将客户端机器192.168.1.205的/usr/local/src/test.py软链接到/tmp/test.py下,命令如下:

ansible 192.168.1.205 -m file -a "src=/usr/local/src/test.py dest=/tmp/test.py state=link"

命令显示结果如下:

192.168.1.205 | success >> {

"changed": true,

"dest": "/tmp/test.py",

"gid": 0,

"group": "root",

"mode": "0777",

"owner": "root",

"size": 22,

"src": "/usr/local/src/test.py",

"state": "link",

"uid": 0

}

若要直接在Ansible机器上查看205机器是否存在/tmp/test.py文件,可采用如下命令:

ansible 192.168.1.205 -m command -a 'll /tmp/test.py'

命令显示结果如下:

192.168.1.205 | success | rc=0 >>

lrwxrwxrwx 1 root root 22 Nov 25 09:13 /tmp/test.py -> /usr/local/src/test.py

示例二:将刚刚建立的/tmp/test.py链接文件删除,命令如下:

absible 192.168.1.205 -m file -a "path=/tmp/test.py state=absent"

命令显示结果如下:

192.168.1.205 | success >> {

"changed": true,

"path": "/tmp/test.py",

"state": "absent"

}

现在再查看下是否还存在着/tmp/test.py文件,命令如下:

ansible 192.168.1.205 -m command -a 'll /tmp/test.py'

结果为:

192.168.1.205 | FAILED | rc=2 >>

ls: cannot access /tmp/test.py: No such file or directory

结果报错,显示不存在此文件,说明已经成功将其删除了。

示例三:在webserver组建立/text.txt文件,属主和属组均为root,权限为0755,命令如下:

ansible webserver -m file -a 'path=/text.txt state=touch owner=root group=root mode=0755'

命令显示结果如下所示:

192.168.1.205 | success >> {

"changed": true,

"dest": "/text.txt",

"gid": 0,

"group": "root",

"mode": "0755",

"owner": "root",

"size": 0,

"state": "file",

"uid": 0

}

192.168.1.206 | success >> {

"changed": true,

"dest": "/text.txt",

"gid": 0,

"group": "root",

"mode": "0755",

"owner": "root",

"size": 0,

"state": "file",

"uid": 0

}

示例四:在webserver组建立test目录,属主和属组均为root,权限为0755,命令如下:

ansible webserver -m file -a 'path=/tmp/test state=directory owner=root group=root mode=0755'

命令显示结果如下所示:

192.168.1.205 | success >> {

"changed": true,

"gid": 0,

"group": "root",

"mode": "0755",

"owner": "root",

"path": "/tmp/test",

"size": 4096,

"state": "directory",

"uid": 0

}

192.168.1.206 | success >> {

"changed": true,

"gid": 0,

"group": "root",

"mode": "0755",

"owner": "root",

"path": "/tmp/test",

"size": 4096,

"state": "directory",

"uid": 0

}

5.ping模块

这个模块前文曾多次提及,用于检测与被控端机器的连通性,命令如下:

ansible webserver -m ping

6. group模块

6.group模块

group模块可以在所有节点上创建自己定义的组,比如利用此模块创建一个组名为test、gid为2016的组,命令如下:

ansible webserver -m group -a 'gid=2016 name=test'

命令显示结果如下所示:

192.168.1.206 | success >> {

"changed": true,

"gid": 2016,

"name": "test",

"state": "present",

"system": false

}

192.168.1.205 | success >> {

"changed": true,

"gid": 2016,

"name": "test",

"state": "present",

"system": false

}

现在可以查看下是否已经正常创建这个名为test的组了,执行如下命令:

ansible webserver -m shell -a 'cat /etc/group| grep test'

命令显示结果如下所示:

192.168.1.206 | success | rc=0 >>

test:x:2016:

192.168.1.205 | success | rc=0 >>

test:x:2016:

现在,我们可以看到两台机器都有组名为test、gid为2016的组了。

阅读 ‧ 电子书库

注意

此处用到了Shell模块,而没有使用默认的command模块,是因为Shell模块支持管道符命令,如果此处还是沿用command模块的话是要报错的。

7.user模块

该模块用于创建用户。在指定的节点上创建一个用户名为test、组为test的用户,命令如下:

ansible webserver -m user -a "name=test group=test"

命令显示结果如下:

192.168.1.205 | success >> {

"changed": true,

"comment": "",

"createhome": true,

"group": 100,

"groups": "test",

"home": "/home/test",

"name": "test",

"shell": "/bin/bash",

"state": "present",

"system": false,

"uid": 501

}

192.168.1.206 | success >> {

"changed": true,

"comment": "",

"createhome": true,

"group": 100,

"groups": "test",

"home": "/home/test",

"name": "test",

"shell": "/bin/bash",

"state": "present",

"system": false,

"uid": 503

}

删除此用户test,可用如下命令:

ansible webserver -m user -a "name=test state=absent remove=yes"

命令显示结果如下所示:

192.168.1.205 | success >> {

"changed": true,

"force": false,

"name": "test",

"remove": true,

"state": "absent"

}

192.168.1.206 | success >> {

"changed": true,

"force": false,

"name": "test",

"remove": true,

"state": "absent"

}

8.shell模块

command模块作为Ansible的默认模块,可以运行被控端机器权限范围内的所有Shell命令,前面已多次提到,这里不再重复。而Shell模块是执行被控端机器的Shell脚本文件,跟另一个模块raw的功能类似,并且支持管道符。

比如要执行webserver组机器下的/tmp/echo_hello.sh文件,命令如下:

ansible webserver -m shell -a "/tmp/echo_hello.sh"

显示结果如下:

192.168.1.205 | success | rc=0 >>

hello,world

192.168.1.206 | success | rc=0 >>

hello,world

9.script模块

script模块用于在远程被控端主机上执行本地Ansible机器中的Shell脚本文件,相当于scp+shell的组合命令,比如,要执行本地机器的/root/print_hello.sh,命令如下:

ansible webserver -m script -a "/root/print_hello.sh"

命令显示结果如下所示:

192.168.1.205 | success >> {

"changed": true,

"rc": 0,

"stderr": "OpenSSH_5.3p1, OpenSSL 1.0.1e-fips 11 Feb 2013\ndebug1: Reading configuration data /etc/ssh/ssh_config\r\ndebug1: Applying options for *\r\ndebug1: auto-mux: Trying existing master\r\ndebug1: mux_client_request_session: master session id: 2\r\ndebug1: mux_client_request_session: master session id: 2\r\nShared connection to 192.168.1.205 closed.\r\n",

"stdout": "hello,world\r\n"

}

192.168.1.206 | success >> {

"changed": true,

"rc": 0,

"stderr": "OpenSSH_5.3p1, OpenSSL 1.0.1e-fips 11 Feb 2013\ndebug1: Reading configuration data /etc/ssh/ssh_config\r\ndebug1: Applying options for *\r\ndebug1: auto-mux: Trying existing master\r\ndebug1: mux_client_request_session: master session id: 2\r\ndebug1: mux_client_request_session: master session id: 2\r\nShared connection to 192.168.1.206 closed.\r\n",

"stdout": "hello,world\r\n"

}

10.get_url模块

get_url模块可以实现在远程主机上下载url到本地,这个模块应该在平时的工作中用得比较多,比如,webserver组的被控端机器需要下载http://ftp.linux.ncsu.edu/pub/epel/6/x86_64/epel-release-6-8.noarch.rpm 文件到/tmp目录下,命令如下:

ansible webserver -m get_url -a 'url= http://ftp.linux.ncsu.edu/pub/epel/6/x86_64/epel-release-6-8.noarch.rpm dest=/tmp'

命令显示结果如下所示:

192.168.1.206 | success >> {

"changed": true,

"checksum": "2b2767a5ae0de30b9c7b840f2e34f5dd9deaf19a",

"dest": "/tmp/epel-release-6-8.noarch.rpm",

"gid": 0,

"group": "root",

"md5sum": "2cd0ae668a585a14e07c2ea4f264d79b",

"mode": "0644",

"msg": "OK (14540 bytes)",

"owner": "root",

"sha256sum": "",

"size": 14540,

"src": "/tmp/tmp4lZkbI",

"state": "file",

"uid": 0,

"url": "http://ftp.linux.ncsu.edu/pub/epel/6/x86_64/epel-release-6-8.noarch.rpm"

}

192.168.1.205 | success >> {

"changed": true,

"checksum": "2b2767a5ae0de30b9c7b840f2e34f5dd9deaf19a",

"dest": "/tmp/epel-release-6-8.noarch.rpm",

"gid": 0,

"group": "root",

"md5sum": "2cd0ae668a585a14e07c2ea4f264d79b",

"mode": "0644",

"msg": "OK (14540 bytes)",

"owner": "root",

"sha256sum": "",

"size": 14540,

"src": "/tmp/tmp5j3tu5",

"state": "file",

"uid": 0,

"url": "http://ftp.linux.ncsu.edu/pub/epel/6/x86_64/epel-release-6-8.noarch.rpm"

}

11.yum模块

顾名思义,yum模块是用来管理Linux平台的软件包操作的。

·config_file:yum的配置文件。

·disable_gpg_check:关闭gpg_check。

·disablerepo:不启用某个源。

·enablerepo:启用某个源。

·name:要进行操作的软件包的名字,也可以传递一个url或一个本地的rpm包的路径。

·state:present|absent|latest,state状态对应了3种软件包状态,这里present和latest都表示安装,而absent则表示移除。

若要在指定的被控端机器192.168.1.206上面用Nginx的yum源安装Nginx软件包,可采用如下命令:

ansible 192.168.1.206 -m yum -a 'name=nginx enablerepo=nginx state=present'

显示结果如下:

192.168.1.206 | success >> {

"changed": true,

"msg": "",

"rc": 0,

"results": [

"Loaded plugins: fastestmirror\nSetting up Install Process\nLoading mirror speeds from cached hostfile\n * base: mirrors.163.com\n * extras: mirror.bit.edu.cn\n * updates: centos.ustc.edu.cn\nResolving Dependencies\n--> Running transaction check\n---> Package nginx.x86_64 0:1.8.0-1.el6.ngx will be installed\n--> Finished Dependency Resolution\n\nDependencies Resolved\n\n================================================================================\n Package Arch Version Repository ======================================================================\nInstalling:\n nginx x86_64 1.8.0-1.el6.ngx nginx 352 k\n\nTransaction Summary\n===================================================================\nInstall 1 Package(s)\n\nTotal download size: 352 k\nInstalled size: 872 k\nDownloading Packages:\nRunning rpm_check_debug\nRunning Transaction Test\nTransaction Test Succeeded\nRunning Transaction\n\r Installing : nginx-1.8.0-1.el6.ngx.x86_64 1/1 \n----------------------------------------------------------------------\n\nThanks for using nginx!\n\nPlease find the official documentation for nginx here:\n* http://nginx.org/en/docs/\n\nCommercial subscriptions for nginx are available on:\n* http://nginx.com/products/\n\n----------------------------------------------------------------------\n\r Verifying : nginx-1.8.0-1.el6.ngx.x86_64 1/1 \n\nInstalled:\n nginx.x86_64 0:1.8.0-1.el6.ngx \n\nComplete!\n"

]

}

可以通过如下命令查看软件包是否通过Nginx源安装的:

ansible 192.168.1.206 -m shell -a 'yum list installed | grep nginx'

显示结果如下:

192.168.1.206 | success | rc=0 >>

nginx.x86_64 1.8.0-1.el6.ngx @nginx

其实也可以用命令查看yum模块的帮助文件,它本身就提供了强大的案例参考,命令如下:

ansiable-doc yum

显示结果如下所示(显示结果较多,只摘取了Examples部分的内容):

EXAMPLES:

- name: install the latest version of Apache

yum: name=httpd state=latest

- name: remove the Apache package

yum: name=httpd state=absent

- name: install the latest version of Apache from the testing repo

yum: name=httpd enablerepo=testing state=present

- name: install one specific version of Apache

yum: name=httpd-2.2.29-1.4.amzn1 state=present

- name: upgrade all packages

yum: name=* state=latest

- name: install the nginx rpm from a remote repo

yum: name=http://nginx.org/packages/centos/6/noarch/RPMS/nginx-release-centos-6-0.el6.ngx.noarch.rpm state=present

- name: install nginx rpm from a local file

yum: name=/usr/local/src/nginx-release-centos-6-0.el6.ngx.noarch.rpm state=present

- name: install the 'Development tools' package group

yum: name="@Development tools" state=present

12.cron模块

cron模块,顾名思义就是创建计划任务,可以定义webserver组被控端机器每天凌晨1点过1分ntpdate自动对时,命令如下所示:

ansible webserver -m cron -a '"name=ntpdate time every day" minute="1" hour="1" job="/sbin/ntpdate ntp.api.bz >> /dev/null"'

这里定义的name是标记计划任务,可以通过此标记删除或更改计划任务,命令显示结果如下:

192.168.1.205 | success >> {

"changed": true,

"jobs": [

"ntpdate time every day"

]

}

192.168.1.206 | success >> {

"changed": true,

"jobs": [

"ntpdate time every day"

]

}

详细语法可以参考ansiable-doc cron,这里不再重复命令显示结果。

13.service模块

被控端服务管理,例如开启、关闭、重启服务等。

示例一:在webserver端开启Nginx服务,命令如下:

ansible webserver -m service -a "name=nginx state=started"

示例二:将httpd服务加入webserver端的启动项,命令如下:

ansible mysql -m service -a 'name=mysqld state=started enabled=yes'

其他常用模块,在这里就不一一列举了,大家可以参考Ansible官方文档。