ansible笔记():初识ansible playbook

假设,我们想要在test70主机上安装nginx并启动,我们可以在ansible主机中执行如下3条命令

ansible test70 -m yum_repository -a 'name=aliEpel description="alibaba EPEL" baseurl=http://mirrors.aliyun.com/epel/7/$basearch'
ansible test70 -m yum -a 'name=nginx disable_gpg_check=yes enablerepo=aliEpel'
ansible test70 -m service -a "name=nginx state=started" 我们通过上述3条命令,先确定配置了对应的yum源,然后使用yum模块安装了nginx,最后使用service模块启动了nginx,最终达到了我们的目的。 但是在实际的工作环境中,我们可能需要经常在新主机上安装nginx,难道每次有新的服务器加入工作环境,我们都要修改上述3条命令中的主机名并且重新将每一条命令执行一遍吗?这样似乎有些麻烦,肯定有更好的办法,没错,我们可以将上述命令写成脚本,每次修改一些变量,然后执行脚本就行了,这样似乎方便了不少,而ansible天生就提供了这种类似"脚本"的功能,在ansible中,类似"脚本"的文件被称作"剧本",'剧本'的英文名称为'playbook',我们只需要将要做的事情编写成playbook,把不同的模块按照顺序编排在剧本中,ansible就会按照剧本一步一步的执行,最终达到我们的目的,虽然playbook的功能与脚本类似,但是剧本并不是简单的将ad-hoc命令按照顺序堆砌在一个可执行文件中,编写剧本需要遵循YAML语法,如果你没有接触过YAML语法,不用害怕,坚持看完后面的示例,熟悉一些固定套路以后,你也可以自己编写playbook。 那么怎样编写playbook呢?我们先从一个简单的示例开始 首先,我们需要创建一个YAML格式的playbook文件。 playbook文件以".yaml"或者".yml"作为文件名后缀,此处我们创建一个名为"test.yml"的剧本文件。 在编写剧本之前,我们先来回顾两个简单的ad-hoc命令,比如如下两条命令: [root@node1 data]# ansible test211 -m ping
[root@node1 data]# ansible test211 -m file -a "path=/data/test211 state=directory" 上述命令表示使用ping模块去ping主机test70,然后再用file模块在test70主机上创建目录,那么,如果把上述命令转换成playbook的表现形式,该如何书写呢?示例如下 (此处先进行示例,后文会说明怎样执行playbook) ---
- hosts: test211
remote_user: root
tasks:
- name: ping the host
ping:
- name: make directory test
file:
path: /data/testfile
state: directory 如上所示,第一行使用三个横杠作为开始,在YAML语法中,"---"表示文档开始。 第二行使用"- "作为开头(注意:横杠后面有空格),如果你了解过YAML语法,那么你一定知道YAML使用"- "表示一个块序列的节点,如果你不了解YAML语法,不用在此处纠结,先这么写,写的多了,自然会理解,从上例可以看出,"- "后面使用hosts关键字指定了要操作的主机,hosts关键字对应的值为test70,表示我们要在test70主机上进行操作,"hosts: test70"是一个键值对,注意,在YAML语法中使用冒号映射键值对时,'冒号'后面必须有'空格',这也是语法,没有为什么,记住就好,如果你想要一次性在多台主机上进行操作,可以同时写多个主机,每台主机使用逗号隔开,比如'hosts: test70,test61',如果你在清单中对主机进行了分组,也可以使用组名。 第三行,使用remote_user关键字可以指定在进行远程操作时使用哪个用户进行操作,'remote_user: root'表示test70的root用户进行操作,上图中,remote_user关键字与hosts关键字对齐,表示它们是平级的,之前的文章中提到过,在YAML语法中进行缩进时,不能使用tab键进行缩进,必须使用空格,所以,为了兼容使用tab键进行缩进的使用习惯,可以将vim编辑器设置为自动将tab转成空格。 第四行,使用tasks关键字指明要进行操作的任务列表,之后的行都属于tasks键值对中的值。 之后的行都属于tasks任务列表中的任务,可以看出,整个任务列表一共有两个任务组成,每个任务都以"- "开头,每个任务都有自己的名字,任务名使用name关键字进行指定,第一个任务使用ping模块,使用ping模块时没有指定任何参数。第二个任务使用file模块,使用file模块时,指定了path参数与state参数的值。 好了,test.yml已经编写完成了,但是,我们还没有运行这个剧本,运行剧本需要使用'ansible-playbook'命令,示例如下 [root@node1 data]# ansible-playbook test.yml PLAY [test211] ********************************************************************************************************************************************************************************************************************************************************************************************************************************************************** TASK [Gathering Facts] **************************************************************************************************************************************************************************************************************************************************************************************************************************************************
ok: [test211] TASK [ping the host] ****************************************************************************************************************************************************************************************************************************************************************************************************************************************************
ok: [test211] TASK [make directory test] **********************************************************************************************************************************************************************************************************************************************************************************************************************************************
changed: [test211] PLAY RECAP **************************************************************************************************************************************************************************************************************************************************************************************************************************************************************
test211 : ok= changed= unreachable= failed= 如上图所示,playbook执行后返回了一些信息,这些信息是这次剧本运行的概况。 'PLAY [test211]'表示这次运行的playbook中有一个'play'是针对test211这台主机运行的,一个'playbook'是由一个或多个'play'组成的,这样说可能不太容易理解,那么我们打个比方,一个'剧本'是由一个或多个'桥段'组成的,每个桥段都有不同的场景、人物、故事,所有的桥段组合在一起,组成一个完整的剧本,剧本就是playbook,桥段就是play,而上例中,整个剧本中只有一个桥段,也就是说,上例的playbook中,我们只写了一个play,在下文中我们会举例说明怎样书写多个play,到时候你会更加明白到底什么是所谓的'play',当然,'桥段'只是我自己为了方便理解给'play'起的中文名,官方名称只叫"play"。 从上述信息可以看出,仅有的这个play是针对test211运行的,这个play一共包含三个任务,第一个任务的名字叫做'Gathering Facts',第二个任务的名字叫做'Ping the host',第三个任务的名字叫做'make directory test',看到此处你会发现,我们在playbook中明明只写了两个任务,为什么最后执行时却有三个任务呢?这是因为,每个play在执行时,都会先执行一个默认任务,这个默认任务就是'Gathering Facts','Gathering Facts'任务会收集当前play对应的目标主机的相关信息,收集完这些基础信息后,才会执行我们指定的任务,由于上例中,hosts的值只有test211一个主机,所以这个play只针对test211运行,所以'Gathering Facts'这个任务只收集了test211的相关信息,执行完默认任务后,开始执行'Ping the host'任务和'make directory test'任务,由于在执行playbook之前,/testdir/test目录已经存在于test211主机中,所以'make directory test'任务返回的信息是绿色的,如果对应的目录并不存在,'make directory test'任务返回的信息应该是黄色的,这是因为幂等性的缘故,前文已经解释过,此处不再赘述。 当playbook中的所有play执行完毕后,在返回信息的'PLAY RECAP'中可以对所有目标主机的执行情况进行'回顾',由于我们的目标主机只有test211一台,所以只看到了test211的执行概括信息。 我们已经执行了一个playbook,这个playbook中只有一个play,我们也可以在这个playbook中多写几个play,示例如下: ---
- hosts: test211
remote_user: root
tasks:
- name: pint the host
ping:
- name: make directory test211
file:
path: /data/test211
state: directory - hosts: test212,test215
remote_user: root
tasks:
- name: touch file
file:
path: /touchfile
state: touch - hosts:
test212
test215
remote_user: root
tasks:
- name: create user jack
user:
name: jack 如上所示,上例中有多个play,第一个play针对test211执行,这个play会执行两个任务。 第二个play针对test212和test215执行,第二个play只包含一个任务,即在对应的目标主机上创建/touchfile文件 第三个play针对test212和test215执行,细心如你一定发现了,当你需要在play中指定多个主机时,有两种语法可以使用,第二个play和第三个play中的语法都可以指定多个主机,第三个play也只包含一个任务,即在test212和test215主机上创建jack用户。 多个play写完以后,我们来运行一下剧本试试 如下所示,每个play执行时都会显示当前play对应的目标主机,并且每个play执行时都会先执行默认的facts任务,收集对应目标主机的信息,当所有play都执行完毕后,会出现'PLAY RECP',相当于一个小的报告信息,看到这里,你应该已经理解了到底什么是所谓的'play'了吧。 [root@node1 data]# ansible-playbook test2.yml PLAY [test211] **************************************************************** TASK [Gathering Facts] ********************************************************
ok: [test211] TASK [pint the host] **********************************************************
ok: [test211] TASK [make directory test211] *************************************************
ok: [test211] PLAY [test212,test215] ******************************************************** TASK [Gathering Facts] ********************************************************
ok: [test215]
ok: [test212] TASK [touch file] *************************************************************
changed: [test212]
changed: [test215] PLAY [test212 test215] ******************************************************** TASK [Gathering Facts] ********************************************************
ok: [test215]
ok: [test212] TASK [create user jack] *******************************************************
changed: [test215]
changed: [test212] PLAY RECAP ********************************************************************
test211 : ok= changed= unreachable= failed=
test212 : ok= changed= unreachable= failed=
test215 : ok= changed= unreachable= failed= 如果你并不是很熟悉YAML语法,你可以不用过于深究YAML语法,只需要死记硬背,记住某些"固定套路"即可编写playbook,写的多了,自然会对这些语法有所理解 如果你的playbook写完了,但是你不能确定playbook文件中是否存在语法错误,那么你可以使用如下命令对playbook进行语法检查 [root@node1 data]# ansible-playbook --syntax-check /data/test2.yml 执行上述命令后,如果只返回了playbook的名称,就表示没有语法错误。 除了对playbook进行语法测试,我们还能够'模拟执行'playbook,'模拟执行'并不是真正的执行,只是'假装'执行一下,playbook中的任务并不会真正在目标主机中运行,所以你可以放心大胆的进行模拟,使用如下命令即可模拟运行playbook,模拟运行功能可以帮助我们'预估'playbook是否能够正常执行。 [root@node1 data]# ansible-playbook --check test2.yml 注意:使用上述命令进行'模拟'时,一些任务可能会报错,这可能是因为报错的任务在执行时需要依赖之前的其他任务的完成结果,但是因为是'模拟'执行,所以之前的任务并不会真正的执行,既然之前的任务没有真正的执行,自然不会产生对应的结果,所以后面的任务就报错了,也就是说,我们并不能完全以'模拟'的反馈结果作为playbook是否能够正常运行的判断依据,只能通过'模拟'大概的'预估'一下而已。

ansible笔记(10):初识ansible playbook的更多相关文章

  1. ansible笔记(11):初识ansible playbook(二)

    ansible笔记():初识ansible playbook(二) 有前文作为基础,如下示例是非常容易理解的: --- - hosts: test211 remote_user: root tasks ...

  2. ansible笔记(12):handlers的用法

    ansible笔记():handlers的用法 这篇文章会介绍playbook中handlers的用法. 在开始介绍之前,我们先来描述一个工作场景: 当我们修改了某些程序的配置文件以后,有可能需要重启 ...

  3. ansible笔记(4):常用模块之文件操作

    前文中,我们已经介绍了怎样使用模块,而且我们知道,ansible有很多模块,每个模块都有自己的功能,"模块"涉及到的方向比较多,所以对于个人来说,并没有必要了解所有的模块,我们只需 ...

  4. ansible笔记(3):ansible模块的基本使用

    ansible笔记():ansible模块的基本使用 在前文的基础上,我们已经知道,当我们使用ansible完成实际任务时,需要依靠ansible的各个模块,比如,我们想要去ping某主机,则需要使用 ...

  5. ansible笔记(1)在centos中安装ansible

    ansible笔记():ansible的基本概念 一些基础概念 ansible是什么? 它是一个"配置管理工具",它是一个"自动化运维工具",如果你没有使用过任 ...

  6. Ansible笔记(1)---基本概念

    一.ansible的作用以及工作结构 1.1.ansible简介: ansible是新出现的自动化运维工具,基于Python开发,集合了众多运维工具(puppet.cfengine.chef.func ...

  7. ansible笔记(7):常用模块之系统类模块

    ansible笔记():常用模块之系统类模块 cron模块 cron模块可以帮助我们管理远程主机中的计划任务,功能相当于crontab命令. 在了解cron模块的参数之前,先写出一些计划任务的示例,示 ...

  8. ansible笔记(8):常用模块之系统类模块(二)

    ansible笔记():常用模块之系统类模块(二) user模块 user模块可以帮助我们管理远程主机上的用户,比如创建用户.修改用户.删除用户.为用户创建密钥对等操作. 此处我们介绍一些user模块 ...

  9. ansible笔记(9):常用模块之包管理模块

    ansible笔记():常用模块之包管理模块 yum_repository模块 yum_repository模块可以帮助我们管理远程主机上的yum仓库. 此处我们介绍一些yum_repository模 ...

随机推荐

  1. java读大文件最快性能【转】

    java读大文件最快性能 完全引用自: 几种读大文件方法的效率对比测试 据说1.88g只要5秒左右,未亲测. /** * 读大文件 * BufferedReader + char[] * @throw ...

  2. HDU 6374(拼三角形 **)

    题意是在给定的线段长中挑选出能拼成三角形的最长的三条边,输出三角形的周长.先对所有边排序,从大到小,满足两较短边之和大于第三边就输出,若从未输出过就输出 -1 #include <iostrea ...

  3. SpringBoot系列: 单元测试

    SpringBoot 项目单元测试也很方便, Web项目中单元测试应该覆盖:1. Service 层2. Controller 层 本文前半部分讲解是一些测试基础配置. 对于Service和Contr ...

  4. C# 获取程序运行时路径

    Ø  前言 开发中,很多时候都需要获取程序运行时路径,比如:反射.文件操作等..NET Framework 已经封装了这些功能,可以很方便的使用. C# 中有很多类都可以获取程序运行时路径,我们没必要 ...

  5. seleniums私房菜系列一 ---- selenium简介

    一.Selenium是什么? Selenium是ThroughtWorks公司一个强大的开源Web功能测试工具系列,本系列现在主要包括以下4款: 1.Selenium Core:支持DHTML的测试案 ...

  6. 默认约束(DEFAULT)

    默认值 当插入记录时,如果没有明确为字段赋值,则自动赋予默认值. mysql> CREATE TABLE tb8( -> id SMALLINT UNSIGNED AUTO_INCREME ...

  7. tensorflow faster rann

    github 上大神的代码 https://github.com/endernewton/tf-faster-rcnn.git 在自己跑的过程中的问题: 1. 数据集的问题: 作者实现了 voc,co ...

  8. es6写法

    我们在日常开发中,如果我们使用es5则可以直接在浏览器里面写JavaScript脚本.一点问题也没有. 但是在写es6语法的JavaScript代码的时候,我们就需要引入babel翻译器了. 例如: ...

  9. websocket和socketio的总结

    1.WebSocket是什么? WebScoket是一种让客户端和服务器之间能进行双向实时通信的技术.它是HTML最新标准HTML5的一个协议规范,本质上是个基于TCP的协议,它通过HTTP/HTTP ...

  10. jstl和EL表达式混合使用

    EL表达式里判断字符串,或者... ${(wrt.acceptName eq '刘立荣') || (wrt.acceptName eq '卢伟冰') } <tr> <td heigh ...