Ansible16:Playbook高级用法
目录
- 本地执行
- 任务委托
- 任务暂停
- 滚动执行
- 只执行一次
- 设置环境变量
- 交互式提示
本地执行
如果希望在控制主机本地运行一个特定的任务,可以使用local_action语句。
假设我们需要配置的远程主机刚刚启动,如果我们直接运行playbook,可能会因为sshd服务尚未开始监听而导致失败,我们可以在控制主机上使用如下示例来等待被控端sshd端口监听:
- name: wait for ssh server to be runningwait_forport: 22 host: "{{ inventory_hostname }}" search_regex: OpenSSHconnection: local
任务委托
在有些时候,我们希望运行与选定的主机或主机组相关联的task,但是这个task又不需要在选定的主机或主机组上执行,而需要在另一台服务器上执行。
这种特性适用于以下场景:
- 在告警系统中启用基于主机的告警
- 向负载均衡器中添加或移除一台主机
- 在dns上添加或修改针对某个主机的解析
- 在存储节点上创建一个存储以用于主机挂载
- 使用一个外部程序来检测主机上的服务是否正常
可以使用delegate_to语句来在另一台主机上运行task:
- name: enable alerts for web servershosts: webserverstasks:- name: enable alertsnagios: action=enable_alerts service=web host="{{ inventory_hostname }}"delegate_to: nagios.example.com
如果delegate_to: 127.0.0.1的时候,等价于local_action
任务暂停
有些情况下,一些任务的运行需要等待一些状态的恢复,比如某一台主机或者应用刚刚重启,我们需要需要等待它上面的某个端口开启,此时就需要将正在运行的任务暂停,直到其状态满足要求。
Ansible提供了wait_for模块以实现任务暂停的需求
wait_for模块常用参数:
- connect_timeout:在下一个任务执行之前等待连接的超时时间
- delay:等待一个端口或者文件或者连接到指定的状态时,默认超时时间为300秒,在这等待的300s的时间里,wait_for模块会一直轮询指定的对象是否到达指定的状态,delay即为多长时间轮询一次状态。
- host:wait_for模块等待的主机的地址,默认为127.0.0.1
- port:wait_for模块待待的主机的端口
- path:文件路径,只有当这个文件存在时,下一任务才开始执行,即等待该文件创建完成
- state:等待的状态,即等待的文件或端口或者连接状态达到指定的状态时,下一个任务开始执行。当等的对象为端口时,状态有started,stoped,即端口已经监听或者端口已经关闭;当等待的对象为文件时,状态有present或者started,absent,即文件已创建或者删除;当等待的对象为一个连接时,状态有drained,即连接已建立。默认为started
- timeout:wait_for的等待的超时时间,默认为300秒
示例:
#等待8080端口已正常监听,才开始下一个任务,直到超时
- wait_for: port: 8080 state: started #等待8000端口正常监听,每隔10s检查一次,直至等待超时
- wait_for: port: 8000 delay: 10 #等待8000端口直至有连接建立
- wait_for: host: 0.0.0.0 port: 8000 delay: 10 state: drained#等待8000端口有连接建立,如果连接来自10.2.1.2或者10.2.1.3,则忽略。
- wait_for: host: 0.0.0.0 port: 8000 state: drained exclude_hosts: 10.2.1.2,10.2.1.3 #等待/tmp/foo文件已创建
- wait_for: path: /tmp/foo #等待/tmp/foo文件已创建,而且该文件中需要包含completed字符串
- wait_for: path: /tmp/foo search_regex: completed #等待/var/lock/file.lock被删除
- wait_for: path: /var/lock/file.lock state: absent #等待指定的进程被销毁
- wait_for: path: /proc/3466/status state: absent #等待openssh启动,10s检查一次
- wait_for: port: 22 host: "{{ ansible_ssh_host | default(inventory_hostname) }}" search_regex: OpenSSH delay: 10
滚动执行
默认情况下,ansible会并行的在所有选定的主机或主机组上执行每一个task,但有的时候,我们会希望能够逐台运行。最典型的例子就是对负载均衡器后面的应用服务器进行更新时。通常来讲,我们会将应用服务器逐台从负载均衡器上摘除,更新,然后再添加回去。我们可以在play中使用serial语句来告诉ansible限制并行执行play的主机数量。
下面是一个在amazon EC2的负载均衡器中移除主机,更新软件包,再添加回负载均衡的配置示例:
- name: upgrade pkgs on servers behind load balancerhosts: myhostsserial: 1tasks:- name: get the ec2 instance id and elastic load balancer idec2_facts:- name: take the host out of the elastic load balancer idlocal_action: ec2_elbargs:instance_id: "{{ ansible_ec2_instance_id }}"state: absent- name: upgrade pkgsapt: update_cache: yes upgrade: yes- name: put the host back n the elastic load balancerlocal_action: ec2_elbargs:instance_id: "{{ ansible_ec2_instance_id }}"state: presentec2_elbs: "{{ items }}"with_items: ec2_elbs
在上述示例中,serial的值为1,即表示在某一个时间段内,play只在一台主机上执行。如果为2,则同时有2台主机运行play。
一般来讲,当task失败时,ansible会停止执行失败的那台主机上的任务,但是继续对其他 主机执行。在负载均衡的场景中,我们会更希望ansible在所有主机执行失败之前就让play停止,否则很可能会面临所有主机都从负载均衡器上摘除并且都执行失败导致服务不可用的场景。这个时候,我们可以使用serial语句配合max_fail_percentage语句使用。max_fail_percentage
表示当最大失败主机的比例达到多少时,ansible就让整个play失败。示例如下:
- name: upgrade pkgs on fservers behind load balancerhosts: myhostsserial: 1max_fail_percentage: 25tasks:......
假如负载均衡后面有4台主机,并且有一台主机执行失败,这时ansible还会继续运行,要让Play停止运行,则必须超过25%,所以如果想一台失败就停止执行,我们可以将max_fail_percentage的值设为24。如果我们希望只要有执行失败,就放弃执行,我们可以将max_fail_percentage的值设为0。
只执行一次
某些时候,我们希望某个task只执行一次,即使它被绑定到了多个主机上。例如在一个负载均衡器后面有多台应用服务器,我们希望执行一个数据库迁移,只需要在一个应用服务器上执行操作即可。
可以使用run_once语句来处理:
- name: run the database migrateionscommand: /opt/run_migrateionsrun_once: true
还可以与local_action配合使用,如下:
- name: run the task locally, only oncecommand: /opt/my-custom-commandconnection: localrun_once: true
还可以与delegate_to配合使用,让这个只执行一次的任务在指定的机器上运行:
- name: run the task locally, only oncecommand: /opt/my-custom-commandrun_once: truedelegate_to: app.a1-61-105.dev.unp
设置环境变量
我们在命令行下执行某些命令的时候,这些命令可能会需要依赖环境变量。比如在安装某些包的时候,可能需要通过代理才能完成完装。或者某个脚本可能需要调用某个环境变量才能完成运行。
ansible 支持通过environment
关键字来定义一些环境变量。
在如下场景中可能需要用到环境变量:
- 运行shell的时候,需要设置path变量
- 需要加载一些库,这些库不在系统的标准库路径当中
下面是一个简单示例:
---
- name: upload a remote file to aws s3hosts: testtasks:- name: install pipyum:name: python-pipstate: installed- name: install the aws toolspip:name: awsclistate: present- name upload file to s3shell aws s3 put-object --bucket=my-test-bucket --key={{ ansible_hostname }}/fstab --body=/etc/fstab --region=eu-west-1environment:AWS_ACCESS_KEY_ID: xxxxxxAWS_SECRET_ACCESS_KEY: xxxxxx
事实上,environment也可以存储在变量当中:
- hosts: allremote_user: rootvars:proxy_env:http_proxy: http://proxy.example.com:8080https_proxy: http://proxy.bos.example.com:8080tasks:- apt: name=cobbler state=installedenvironment: proxy_env
交互式提示
在少数情况下,ansible任务运行的过程中需要用户输入一些数据,这些数据要么比较秘密不方便,或者数据是动态的,不同的用户有不同的需求,比如输入用户自己的账户和密码或者输入不同的版本号会触发不同的后续操作等。ansible的vars_prompt关键字就是用来处理上述这种与用户交互的情况的。
- hosts: allremote_user: rootvars_prompt:- name: share_userprompt: "what is your network username?"private: yes- name: share_passprompt: "what is your network password"private: yestasks:- debug:var: share_user- debug:var: share_pass
vars_prompt常用选项说明:
- private: 默认为yes,表示用户输入的值在命令行不可见
- default:定义默认值,当用户未输入时则使用默认值
- confirm:如果设置为yes,则会要求用户输入两次,适合输入密码的情况
转载于:https://www.cnblogs.com/breezey/p/10996651.html
Ansible16:Playbook高级用法相关推荐
- ansible高级用法(压测脚本)
记录一个ansible高级用法与shell结合_kali_yao的博客-CSDN博客_ansible shell 注:由于ansible的远程原则必须要key(也就是ssh远程测试),所以在配置文件中 ...
- vim的高级用法配置以及在系统中如何获取帮助
vim的高级用法配置以及在系统中如何获取帮助 1 vim的三种模式 1.1 使用方法 1.2 vim模式 2 vim工作的基本配置 2.1 临时设定(set设定) 2.2 永久设定方式 3 搜索 4 ...
- Cacti Weathermap 高级用法 (二)
成都长宽Weathermap实际运用的效果图示例: 这是一个CNC出口的质量监控图. 途中cnc节点(红色)是一个展示图例,TEL节点根据存活状态显示为绿色 TEL节点上面P:47.2ms 是一个,这 ...
- JAVA正则表达式高级用法(分组与捕获)
2019独角兽企业重金招聘Python工程师标准>>> 正则表达式在字符串处理中经常使用,关于正则简单的用法相信有一点程序基础的人都懂得一些,这里就不介绍简单基础了.这里主要讲解一下 ...
- GUN sed高级用法,sed脚本编写
这里举一些sed常用的高级用法例子经供参考: 一下操作都针对file.txt文件作修改 [root@QX-××× ~]# cat file.txt libgcc-4.4.7-4.el6.x86_64 ...
- java return用法_Java枚举的高级用法之多键值的映射使用
枚举Enum单映射使用 做Java的各位仁兄姐妹都知道,Java通过HashMap,以及枚举提供了方便的K-V映射功能,例如 枚举单映射使用 但是如果遇到多个键值映射,例如K-K-V的形式怎么办呢?可 ...
- (转)python requests 高级用法 -- 包括SSL 证书错误的解决方案
(转)python requests 高级用法 -- 包括SSL 证书错误的解决方案 参考文章: (1)(转)python requests 高级用法 -- 包括SSL 证书错误的解决方案 (2)ht ...
- Python 内置函数sorted()在高级用法
对于Python内置函数sorted(),先拿来跟list(列表)中的成员函数list.sort()进行下对比.在本质上,list的排序和内建函数sorted的排序是差不多的,连参数都基本上是一样的. ...
- class() 高级用法 -- lua
class() 高级用法 class() 除了定义纯 Lua 类之外,还可以从 C++ 对象继承类.比如需要创建一个工具栏,并在添加按钮时自动排列已有的按钮,那么我们可以使用如下的代码:-- 从 CC ...
最新文章
- 什么是Activity 和 Activity分类
- 我们这旮都是黑社会[转]
- 开发人员怎么看实施人员
- 自己动手写处理器之第一阶段(3)——MIPS32指令集架构简单介绍
- 模板之家php mysql_PHP+APACHE+MYSQL安装方法
- 开机出现 Invalid Partition Table 怎么办
- 雷电模拟器 脚本_精灵盛典辅助雷电模拟器使用教程
- Linux查看和注销用户
- Error:Execution failed for task ':clean'. Unable to delete directory :\build\intermediates (转)...
- 焦作机器人编程比赛_焦作市山阳区东环小学在第二十届全国中小学电脑制作活动“机器人竞赛”焦作选拔赛中创佳绩...
- Matplotlib调整字体大小
- Android模拟点击屏幕,实现按键精灵点击屏幕功能
- 点分十进制ip地址转为十进制数字地址-python3实现
- Web前端工程师学习路线
- Linux_29_Linux-Vsftpd
- CBNetworking AFN的封装,别出心裁
- Adapterdemo
- 使用计算机时注意的,使用计算机时注意几点预防“鼠标手”
- AutoCAD关于选择的一些技巧(如何高效地框选)
- 告别2022,重新出发