1.不用循环
---
- name: test
hosts: webservers
tasks:
- name: apache is running
service:
name: httpd
state: started
- name: vsftpd is running
service:
name: vsftpd
state: started
2.使用循环
- name: test
hosts: webservers
tasks:
- name: apache and vsftpd are running
service:
name: "{{ item }}" #循环变量item
state: started
loop:
- httpd
- vsftpd
3.将变量放入列表
- name: test
hosts: webservers
vars:
web_service:
- httpd
- vsftpd
tasks:
- name: apache and vsftpd are running
service:
name: "{{ item }}"
state: started
loop: "{{ web_service }}"
循环散列或字典列表
- name: User Test
user:
name: "{{ item.name }}"
state: present
groups: "{{ item.groups }}"
loop:
- name: westos
groups: westos
- name: redhat
groups: root
register 和loop 一起使用
---
- name: loop register test
gather_facts: no
hosts: localhost
tasks:
- name: loop echo task
shell: "echo This is my item: {{ item }}"
loop:
- one
- two
register: echo_results #注册变量
- name: Show echo results variable
debug:
var: echo_results#显示变量结果
迭代上面playbook 的结果(即使用上面item 的结果)
---
- name: loop register test
gather_facts: no
hosts: localhost
tasks:
- name: loop echo task
shell: "echo This is my item: {{ item }}"
loop:
- one
- two
register: echo_results
- name: Show echo results variable
debug:
msg: "STDOUT from previous task: {{ item.stdout }}"
loop: "{{ echo_results['results'] }}"
使用布尔值测试
---
- name: Boolean test
hosts: all
vars:
run_my_task: true #只有当变量为true 时,才会执行
tasks:
- name: httpd is installed
yum:
name: httpd
when: run_my_task
测试my_service 变量是否有值,有值则安装
---
- name: Boolean test
hosts: all
vars:
my_service: httpd
tasks:
- name: "{{ my_service }} is installed"
yum:
name: "{{ my_service }}"
when: my_service is defined
条件:
等于(字符串) A == “B”
等于(数字) A == 100
小于<
大于>
小于等于<=
大于等于>=
不等于!=
变量存在xxx is defined
变量不存在xxx is not defined
布尔值true 1、true、yes
布尔值false 0、false、no
第一个变量的值存在,且在第二个变量的列表中A in B
测试多个条件:
or 两个条件一个为真即可
and 两个条件必须都为真
- name: Restart httpd if vsftpd is running
hosts: all
tasks:
- name: Get vsftpd status
command: /usr/bin/systemctl is-active vsftpd #判断状态
ignore_errors: yes #如果vsftpd 没运行或失败,则忽略
register: result #定义变量保存结果
- name: Restart httpd
service:
name: httpd
state: restarted
when: result.rc == 0 #退出码为0,则重启httpd
实施处理程序:
处理程序是响应由其他任务触发的通知的任务,只有在template 任务通知已发生更改时才会触发
---
- name: Test
hosts: webservers
tasks:
- name: Copyt File
template:
src: files/example.conf
dest: /etc/httpd/conf.d/example.conf
notify: #notify 语句指出该任务需要触发一个处理程序
- restart apache #程序名
handlers: #表示处理程序任务列表的开头
- name: restart apache #被任务调用的处理程序名称
service: #处理该程序的模块
name: httpd
state: restarted
ansible 把notify 语句当作数组
vim files/example.conf
<VirtualHost *:80>
DocumentRoot /www
ServerName www.westos.org
</VirtualHost>
<VirtualHost *:80>
DocumentRoot /bbs
ServerName bbs.westos.org
</VirtualHost>
vim notify.yml
---
- name: Test
hosts: webservers
tasks:
- name: Copyt File
template:
src: files/example.conf
dest: /etc/httpd/conf.d/example.conf
notify:
- restart apache
- restart mysql
handlers:
- name: restart apache
service:
name: httpd
state: restarted
- name: restart mysql
service:
name: mariadb
state: restarted
使用处理程序注意:
1.处理程序始终按照play 的handlers 部分指定的顺序运行,不按notify 里的
2.处理程序通常在相关play 中所有其他任务运行完后运行
3.处理程序名称存在于个play 命名空间中(若两个处理程序同名,只会运行一个)
4.如果多个任务通知处理程序,处理程序也只会运行一次
5.如果包含notify 的语句任务没有报告changed 结果,则处理程序不会获得通知
通常playbook 遇到错误会中止执行,但是有时我们想要失败时也继续执行
关键字:ignore_errors
vim ignore.yml
---
- name: Test
hosts: webservers
tasks:
- name: Install package
yum:
name: k8s
state: latest
ignore_errors: yes
通常任务失败,play 会中止,那么收到play 中之前任务通知的处理程序将不会运行,如果要运行,需要使用关键字:force_handlers:yes
cat force.yml
---
- hosts: webservers
force_handlers: yes
tasks:
- name: always notify
command: /bin/true
notify: restart apache
- name: Fail task
yum:
name: k8s
state: latest
handlers:
- name: restart apache
service:
name: httpd
state: restarted
处理程序会在任务报告changed 结果时获得通知,ok 或者failed 都不会
关键字:failed_when
tasks:
- name: Run Script
shell: /usr/local/bin/user.sh
register: command_result
failed_when: "'failure' in command_result.stdout"
fail 模块可以实现此效果
tasks:
- name: Run Script
shell: /usr/local/bin/user.sh
register: command_result
ignore_error: yes
- name: Report failure
fail:
msg: "Authentication failure" #fail 模块可以提供明确消息
when: "'failure' in command_result.stdout"
关键字:changed_when
-name: get time
shell: date
changed_when: false
三种关键字:
block:定义要运行的主要任务
rescue:定义要在block 子句中定义的任务失败时运行的任务
always:定义时中独立运行的任务
示例:故意制造错误
cat error.yml
---
- name: Task Failure
hosts: webservers
vars:
web_pkg: http
db_pkg: mariadb-server
db_service: mariadb
tasks:
- name: Install {{ web_pkg }} packages
yum:
name: "{{ web_pkg }}"
state: present
- name: Install {{ db_pkg }} packages
yum:
name: "{{ db_pkg }}"
state: present
运行报错
ansible-playbook error.yml
TASK [Install http packages] ***************************************************
fatal: [servera.lab.example.com]: FAILED! => {"changed": false, "failures": ["No
package http available."], "msg": "Failed to install some of the specified packages",
"rc": 1, "results": []}
第一个任务失败,第二个任务不运行
1.添加忽略关键字
vim error.yml
......
ignore_errors: yes
2.使用block、rescue、always 将任务分开
cat error.yml
---
- name: Task Failure
hosts: webservers
vars:
web_pkg: http
db_pkg: mariadb-server
db_service: mariadb
tasks:
- name: Set up Web
block:
- name: Install {{ web_pkg }} packages
yum:
name: "{{ web_pkg }}"
state: present
rescue:
- name: Install {{ db_pkg }} packages
yum:
name: "{{ db_pkg }}"
state: present
always:
- name: Start {{ db_service }} service
service:
name: "{{ db_service }}"
state: started
执行结果有报错,但是mariadb 正常启动
再修改,将http 的包改为正确
vim error.yml
.........
web_pkg: httpd
发现rescue 部分被忽略,但是always 总会执行
控制’changed’条件:
cat error.yml
---
- name: Task Failure
hosts: webservers
vars:
web_pkg: httpd
db_pkg: mariadb-server
db_service: mariadb
tasks:
- name: Check Time #添加查看时间任务
command: date
register: command_result
- name: Print Time
debug:
var: command_result.stdout
- name: Set up Web
block:
- name: Install {{ web_pkg }} packages
yum:
name: "{{ web_pkg }}"
state: present
rescue:
- name: Install {{ db_pkg }} packages
yum:
name: "{{ db_pkg }}"
state: present
always:
- name: Start {{ db_service }} service
service:
name: "{{ db_service }}"
state: started
运行发现check time 任务始终是changed
因为任务没有更改受管主机,所以不应该每次都是changed
修改文件
vim error.yml
changed_when: false
再次运行,变为ok
使用failed_when 关键字
vim error.yml
failed_when: web_pkg == "httpd"
运行
ansible-playbook error.yml
TASK [Install httpd packages] **************************************************
fatal: [servera.lab.example.com]: FAILED! => {"changed": false,
"failed_when_result": true, "msg": "Nothing to do", "rc": 0, "results": ["Installed:
httpd"]}
有报错,但是其实已经安装了httpd 包,failed_when 关键字只是改变了任务的执行状态,没有改变任务本身,但是失败的状态可以让rescue 语句块执行