ansible的playbook用法

ansible的playbook用法

  • 核心元素
  • 基础组件
    • Hosts
    • remote_user
    • task列表和action
  • 示例
  • handlers和notify的使用
  • tags
  • Playbook中变量使用
    • 1 ansible setup facts 远程主机的所有变量都可直接调用
    • 2 在/etc/ansible/hosts中定义
    • 3.通过命令行指定变量,优先级最高
    • 4 在playbook中定义
    • 5 在独立的变量YAML文件中定义
    • 6 在role中定义
  • 模板template
    • when条件判断
    • 迭代:with_items
    • template for if

核心元素

Hosts 执行的远程主机列表
Tasks 任务集
Variables 内置变量或自定义变量在playbook中调用
Templates 模板,可替换模板文件中的变量并实现一些简单逻辑的文件
Handlers 和 notity 结合使用,由特定条件触发的操作,满足条件方才执行,否则不执行
tags 标签 指定某条任务执行,用于选择运行playbook中的部分代码。ansible具有幂等性,因此会自动跳过没有变化的部分,即便如此,有些代码为测试其确实没有发生变化的时间依然会非常地长。此时,如果确信其没有变化,就可以通过tags跳过此些代码片断

ansible-playbook -t tagsname useradd.yml

基础组件

Hosts

playbook中的每一个play的目的都是为了让特定主机以某个指定的用户身份执行任务。hosts用于指定要执行指定任务的主机,须事先定义在主机清单中
可以是如下形式:

one.example.com
one.example.com:two.example.com
192.168.1.50
192.168.1.*
Websrvs:dbsrvs 或者,两个组的并集
Websrvs:&dbsrvs 与,两个组的交集
webservers:!phoenix 在websrvs组,但不在dbsrvs组

remote_user

可用于Host和task中。也可以通过指定其通过sudo的方式在远程主机上执行任务,其可用于play全局或某任务;此外,甚至可以在sudo时使用sudo_user指定sudo时切换的用户

- hosts: websrvs
 remote_user: root
 tasks:
 - name: test connection
 ping:
 remote_user: magedu
 sudo: yes 默认sudo为root
 sudo_user:wang sudo为wang

task列表和action

play的主体部分是task list,task list中的各任务按次序逐个在hosts中指定的所有主机上执行,即在所有主机上完成第一个任务后,再开始第二个任务
task的目的是使用指定的参数执行模块,而在模块参数中可以使用变量。模块执行是幂等的,这意味着多次执行是安全的,因为其结果均一致
每个task都应该有其name,用于playbook的执行结果输出,建议其内容能清晰地描述任务执行步骤。如果未提供name,则action的结果将用于输出

tasks:任务列表
两种格式:
(1) action: module arguments
(2) module: arguments 建议使用
注意:shell和command模块后面跟命令,而非key=value
某任务的状态在运行后为changed时,可通过“notify”通知给相应的handlers
任务可以通过"tags“打标签,可在ansible-playbook命令上使用-t指定进行调用
 示例:
 tasks:
- name: disable selinux
 command: /sbin/setenforce 0
如果命令或脚本的退出码不为零,可以使用如下方式替代
 tasks:
 - name: run this command and ignore the result
 shell: /usr/bin/somecommand || /bin/true
或者使用ignore_errors来忽略错误信息
 tasks:
 - name: run this command and ignore the result
 shell: /usr/bin/somecommand
 ignore_errors: True

示例

---
- hosts: all
  remote_user: root
  
  tasks:
    - name: install
      yum: name=httpd
    - name: config
      copy: src=/data/playbook/httpd.conf dest=/etc/httpd/conf/
    - name: service
      service: name=httpd state=started enabled=yes

playbook实现二进制安装mariadb

---
- hosts: all
  remote_user: root

  tasks:
    - name: user
      user: name=mysql system=yes home=/data/mysql create_home=no shell=/sbin/nologin
    - name: unarchive
      unarchive: src=/data/playbook/mariadb-10.2.32-linux-x86_64.tar.gz dest=/usr/local/ owner=root group=root
    - name: mysql link
      file: src=/usr/local/mariadb-10.2.32-linux-x86_64 dest=/usr/local/mysql state=link
    - name: mysql datadir
      shell: mkdir /data/mysql
    - name: mysql datadir owner group
      file: path=/data/mysql owner=mysql group=mysql
    - name: mysql database
      shell: chdir=/usr/local/mysql/ scripts/mysql_install_db --datadir=/data/mysql --user=mysql
    - name: path var
      copy: content='PATH=/usr/local/mysql/bin:$PATH' dest=/etc/profile.d/mysql.sh
    - name: config
      copy: src=/data/playbook/my-huge.cnf dest=/etc/my.cnf
    - name: service file
      shell: cp /usr/local/mysql/support-files/mysql.server /etc/init.d/mysqld
    - name: start service
      shell: service mysqld start

handlers和notify的使用

playbook实现httpd安装,并通过copy服务触发判断是否重启服务

---
- hosts: all
  remote_user: root

  tasks:
    - name: install
      yum: name=httpd
    - name: config
      copy: src=/data/playbook/httpd.conf dest /etc/httpd/conf/
      notify: restart httpd
    - name: service
      service: name=httpd state=started enabled=yes

  handlers:
    - name: restart httpd
      service: name=httpd state=restarted

tags

可以单独执行tags中的语句不执行其他的

---
- hosts: all
  remote_user: root

  tasks:
    - name: install
      yum: name=httpd
    - name: config
      copy: src=/data/playbook/httpd.conf dest=/etc/httpd/conf/    
      tags: conf
    - name: service
      service: name=httpd state=started enabled=yes

ansible-playbook -t conf httpd.yml
ansible-playbook --list-tags httpd.yml
#查看tags列表

Playbook中变量使用

1 ansible setup facts 远程主机的所有变量都可直接调用

ansible 192.168.160.150 -m setup -a 'filter=ansible_*name*'

写playbook时用{ { }}引用变量

---
- hosts: all

  tasks:
    - name: create file
      file: name=/data/{
     {
     ansible_nodename}}.log state=touch

2 在/etc/ansible/hosts中定义

普通变量

vim /etc/ansible/hosts
[websrvs]
192.168.160.140 hostname=node1
192.168.160.150 hostname=node2
---
- hosts: all

  tasks:
    - name: create file
      file: name=/data/{
     {
     hostname}}.log state=touch

公共变量

[websrvs]
192.168.160.140 hostname=node1
192.168.160.150 hostname=node2

[websrvs:vars]
suf=txt
---
- hosts: websrvs

  tasks:
    - name: create file
      file: name=/data/{
     {
     hostname}}.{
     {
     suf}} state=touch

3.通过命令行指定变量,优先级最高

 ansible-playbook –e hostname=file -e suf=pdf var.yml

4 在playbook中定义

---
- hosts: websrvs
  vars:
    - hostname: testfile
    - suf: html
  tasks:
    - name: create file
      file: name=/data/{
     {
     hostname}}.{
     {
     suf}} state=touch                                             

5 在独立的变量YAML文件中定义

vim var.yml

hostname: testnode
suf: yml               
---
- hosts: websrvs
  vars_files: var.yml
  tasks:
    - name: create file
      file: name=/data/{
     {
     hostname}}.{
     {
     suf}} state=touch

6 在role中定义

模板template

template功能:根据模块文件动态生成对应的配置文件
template文件必须存放于templates目录下,且命名为 .j2 结尾
yaml/yml 文件需和templates目录平级,目录结构如下:

 ./
 ├── temnginx.yml
 └── templates
         └── nginx.conf.j2

定义端口为变量

vim templates/httpd.conf.j2
Listen {
     {
      httpd_port }}

在host文件里定义变量值

vim /etc/ansible/hosts
[websrvs]
192.168.160.140 httpd_port=8014
192.168.160.150 httpd_port=8015

利用template 同步httpd配置文件

---
- hosts: all
  remote_user: root

  tasks:
    - name: install
      yum: name=httpd
    - name: config
      template: src=httpd.conf.j2 dest=/etc/httpd/conf/httpd.conf
      tags: conf
    - name: service
      service: name=httpd state=started enabled=yes

when条件判断

tasks: 
 - name: install conf file to centos7
 template: src=nginx.conf.c7.j2 dest=/etc/nginx/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"

迭代:with_items

当有需要重复性执行的任务时,可以使用迭代机制
对迭代项的引用,固定变量名为”item“
要在task中使用with_items给定要迭代的元素列表

---
- hosts: websrvs

  tasks:
    - name: create user
      user: name={
     {
      item }}
      with_items:
        - tom
        - alice
        - jack
        - rose

多个迭代之间用字典来进行嵌套子变量

- hosts: websrvs
  tasks:
    - name: add some groups
      group: name={
     {
      item }} state=present
      with_items:
        - group1
        - group2
        - group3
    - name: add some users
      user: name={
     {
      item.name }} group={
     {
      item.group }} state=present
      with_items:
        - {
      name: 'user1', group: 'group1' }
        - {
      name: 'user2', group: 'group2' }
        - {
      name: 'user3', group: 'group3' }

template for if

在websrvs里生成server.conf文件,利用for循环,以ports为组生成文件内容

---
- hosts: websrvs
  vars:
    ports:
      - 81
      - 82
      - 83
  tasks:
    - name: config
      template: src=server.conf.j2 dest=/data/server.conf
{
     %for port in ports %}
server {
     
    listen {
     {
     port}}
}
{
     %endfor%}

与上面不同的是,这次ports里面的是字典格式,所以下面格式需要写成port.listen_port

---
- hosts: websrvs
  vars:
    ports:
      - listen_port: 81
      - listen_port: 82
      - listen_port: 83
  tasks:
    - name: config
      template: src=server2.conf.j2 dest=/data/server2.conf
{
     %for port in ports %}
server {
     
    listen {
     {
     port.listen_port}}
}
{
     %endfor%}

这里是更为复杂的多参数示例

---
- hosts: websrvs
  vars:
    ports:
      - web1:
        listen_port: 81
        name: web1.li.com
        dir: /data/web1
      - web2:
        listen_port: 82
        name: web2.li.com
        dir: /data/web2
      - web3:
        listen_port: 83
        name: web3.li.com
        dir: /data/web3
  tasks:
    - name: config
      template: src=server3.conf.j2 dest=/data/server3.conf
{
     %for port in ports %}
server {
     
    listen {
     {
     port.listen_port}}
    server_name {
     {
     port.name}}
    root {
     {
     port.dir}}
}
{
     %endfor%}

这里是若部分参数不一致的情况下,用if做条件判断

---
- hosts: websrvs
  vars:
    ports:
      - web1:
        listen_port: 81
        # name: web1.li.com
        dir: /data/web1
      - web2:
        listen_port: 82
        name: web2.li.com
        dir: /data/web2
      - web3:
        listen_port: 83
        #name: web3.li.com
        dir: /data/web3
  tasks:
    - name: config
      template: src=server4.conf.j2 dest=/data/server4.conf
{
     %for port in ports %}
server {
     
    listen {
     {
     port.listen_port}}
{
     %if port.name is defined %}
    server_name {
     {
     port.name}}
{
     %endif%}
    root {
     {
     port.dir}}
}
{
     %endfor%}

你可能感兴趣的:(ansible的playbook用法)