加载中...

Ansible playbook


一.简介

1.1 playbook命令

格式

ansible-playbook <filename.yml> ... [options]

常见选项

--syntax-check      #语法检查,可缩写为--syntax,相当于bash -n
-C --check             #模拟执行,值检测可能会发生的改变,但不真正执行操作
--list-hosts             #列出运行任务的主机
--list-tags               #贴出tag
--list-tasks              #列出task
--limit 主机列表       #只针对主机列表中的铁定主机执行
-i INVENTORY         #指定主机清单文件,通常一个项对应一个主机清单文件
--start-at-task START_AT_TASK   #从指定task开始执行,而非从头开始,START_AT_TASK为任务的name
-v -vv	-vvv	        #显示过程

范例

[root@master playbook]#cat hello.yaml 
---
- hosts: all
  remote_user: root

  tasks:
    - name: hello
      command: hostname

[root@master playbook]# ansible-playbook hello.yaml

#-C参数只监测不执行
[root@master playbook]# ansible-playbook -C hello.yaml

二.实战应用

2.1nginx_playbok

---
- hosts: all
  remote_user: root

  tasks:
    - name: create new file
      file: name=/data/newfile state=touch
    - name: install package
      yum: name=nginx
    - name: copy conf
      copy: src=/root/ansible/file/index.html dest=/usr/share/nginx/html
    - name: start service
      service: name=nginx state=started enabled=yes

2.2 httpd_palybook

#install httpd
- hosts: all
  remote_user: root
  gather_facts: no

  tasks:
    - name: Instal1 httpd 
      yum: name=httpd
    - name: Modify config list port
      lineinfile:
        path: /etc/httpd/conf/httpd.conf
        regexp: '^Listen'
        line: 'Listen 8080'
    - name: Modify config data1
      lineinfile:
        path: /etc/httpd/conf/httpd.conf
        regexp: '^DocumentRoot "/var/www/html"'
        line: 'DocumentRoot "/data/html"'
    - name: Modify config data2
      lineinfile:
        path: /etc/httpd/conf/httpd.conf
        regexp: '^<Directory "/var/www/html">'
        line: '<Directory "/data/html">'
    - name: Mkdir website dir
      file: path=/data/html state=directory
    - name: Web html
      copy: src=/root/ansible/file/index.html dest=/data/html/
    - name: Start service
      service: name=httpd state=started enabled=yes

三.Playbook中使用handlers和notify

Handlers本质是task list ,类似于MySQL中的触发器触发的行为,其中的task与前述的task并没有本质上的不同,主要用于当关注的资源发生变化时,才会采取一定的操作。而Notify对应的action可用于在每个play的最后被触发,这样可避免多次有改变发生时每次都执行指定的操作,仅在所有的变化发生完 成后一次性地执行指定操作。在notify中列出的操作称为handler,也即notify中调用handler中定义的操作
注意:

  • 如果多个task通知了相同的handlers, 此handlers仅会在所有tasks结束后运行一 次。
  • 只有notify对应的task发生改变了才会通知handlers, 没有改变则不会触发handlers
  • handlers 是在所有前面的tasks都成功执行才会执行,如果前面任何一个task失败,会导致handler跳过执行,可以使用force_handlers: yes 强制执行handler
---
- hosts: all
  remote_user: root 
  gather_facts: no 
  tasks:
    - name: Install httpd
      yum: name=httpd state=present
    - name: Install configure file
      copy: src=files/httpd.conf dest=/etc/httpd/conf/
#当配置文件内容改变时触发下面两个触发器
      notify:
        - restart httpd
        - wall
    - name: ensure apache is running
      service: name=httpd state=started enabled=yes


  handlers:
#定义触发器
    - name: restart httpd
      service: name=httpd state=restarted
    - name: wall
      command: wall "The config file is changed"

四.Playbook中使用tags组件

在playbook文件中,可以利用tags组件,为特定 task 指定标签,当在执行playbook时,可以只执行特定tags的task,而非整个playbook文件

可以一个task对应多个tag,也可以多个task对应一个tag

还有另外3个特殊关键字用于标签, tagged, untagged 和 all,它们分别是仅运行已标记,只有未标记和所有任务。

---
- hosts: all
  remote_user: root
  gather_facts: no

  tasks:
    - name: Install httpd
      yum: name=httpd state=present
    - name: Install configure file
      copy src=files/httpd.conf dest=/etc/httpd/conf
      tags: [conf,file] #写成一行
        - conf              #写为多行
        - file
    - name: start httpd service
      tags: service
      service: name=httpd state=started enable=yes
[root@ansible ~]#ansible-playbook –-list-tags	httpd.yml 
[root@ansible ~]#ansible-playbook –t conf,service	httpd.yml 
[root@ansible ~]#ansible-playbook --skip-tags conf		httpd.yml 
[root@ansible ~]#ansible-playbook httpd.yml --skip-tags untagged

五.## Playbook中使用变量

变量名: 仅能由字母,数字和下划线组成,且只能以数字开头
变量定义:

variable=value
variable: value

调用方式:
通过 {{ variable_name }} 调用变量,且变量名前后建议加空格,有时用”{{ variable_name }}“才生效

变量来源:

  • ansible 的 setup facts 远程主机的所有变量都可直接调用
  • 通过命令行指定变量,优先级最高
ansible-playbook -e varname=value test.yml
  • 在playbook文件中定义
vars:
  var1: value1
  var2: value2
  • 在独立的变量YAML文件中定义
- hosts: all 
  vars_files:
    - vars.yml
  • 在主机清单中定义
主机(普通)变量:主机组中主机单独定义,优先级高于公共变量
组(公共)变量:针对主机组中所有主机定义统一变量
  • 在项目中针对主机和主机组定义
在项目目录创建host_vars和group_vars目录
  • 在role中定义

变量的优先级从高到低如下

-e 选项定义变量 -->playbook中vars_files --> playbook中vars变量定义 -->host_vars/主机名文件 -->主机清单中主机变量-->group_vars/主机组名文件-->group_vars/all文件--> 主机清单组变量

六 使用setup模块中变量

本模块自动在playbook调用,不要用ansible命令调用,生成的系统状态信息, 并存放在facts变量中

facts 包括的信息很多,如: 主机名,IP,CPU,内存,网卡等

facts 变量有以下使用场景

  • 通过facts变量获取被控端CPU的个数信息,从而生成不同的Nginx配置文件
  • 通过facts变量获取被控端内存大小信息,从而生成不同的memcached的配置文件
  • 通过facts变量获取被控端主机名称信息,从而生成不同的Zabbix配置文件
[root@master playbook]# ansible all -m setup -a "filter='ansible_default_ipv4'"
10.46.40.183 | SUCCESS => {
    "ansible_facts": {
        "ansible_default_ipv4": {
            "address": "10.46.40.183", 
            "alias": "eth0", 
            "broadcast": "10.46.255.255", 
            "gateway": "10.46.0.1", 
            "interface": "eth0", 
            "macaddress": "52:54:00:d2:23:85", 
            "mtu": 1454, 
            "netmask": "255.255.0.0", 
            "network": "10.46.0.0", 
            "type": "ether"
        }, 
        "discovered_interpreter_python": "/usr/bin/python"
    }, 
    "changed": false

playbook中使用

- hosts: all

  tasks:
    - name: show eth0 ip address
      debug:
        msg: IP address {{ ansible_eth0.ipv4.address }}
    - name: show eth0 ip address
      debug:
        msg: IP address {{ ansible_eth0.ipv4.address.split('.')[-1] }}

七.register注册变量

在playbook中可以使用register将捕获命令的输出保存在临时变量中,然后使用debug模块进行显示输出

范例: 利用debug 模块输出变量

- hosts: all

  tasks:
    - name: get variable
      shell: hostname
      register: name
    - name: "print variable"
      debug:
        msg: "{{ name }}"                          #输出register注册的name变量的全部信息
        msg: "{{ name.cmd }}"                   #显示命令
        msg: "{{ name.rc }}"                        #显示命令成功与否
        msg: "{{ name.stdout }}"                 #显示命令的输出结果为字符串形式
        msg: "{{ name.stdout_lines }}"        #显示命令的输出结果为列表形式
        msg: "{{ name.stdout_lines[0] }}"     #显示命令的输出结果的列表中的第一个元素
        msg: "{{ name['stdout_lines'] }}"       #显示命令的执行结果为列表形式

文章作者: huhuhahei
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 huhuhahei !
评论
  目录