更多内容请点击:

Linux学习从入门到打死也不放弃,完全笔记整理(持续更新,求收藏,求点赞~~~~) 

https://blog.51cto.com/13683480/2095439


第20章,运维自动化之ansible

 

本章内容:

               运维自动化发展历程及技术应用

               ansible 命令使用

               ansible 常用模块使用

               YAML语法简介

               ansible playbook基础

               playbook 变量,tags,handlers使用

               playbook模板templates

               playbook 条件判断 when

               playbook 字典 with_items

               ansible roles

 

云计算,运维自动化发展历程及技术应用

               IaaS: Intrastructure as a Service 基础设施即服务

                             提供给消费者的服务时对多有计算机基础设施的利用,包括处理CPU,内存,存储

                             和其他基本的计算资源,用户能够部署和运行任意软件,包括操作系统和应用程序。

                             消费者不管理或控制任何云计算基础设施,但能控制操作系统的选择,存储空间,部署

                             的应用,也有可能获得有限制的网络组件,例如路由器、防火墙、负载均衡器等,的控制

                             

               PaaS:Platform as a Service 平台即服务

                             提供给消费者的服务是把客户采用提供的开发语言和工具(如java,python,.net等)

                             开发的或收购的应用程序部署到供应商的云计算基础设施上去。客户不需要管理或者控制底层

                            的云基础设施,包括网络,服务器,操作系统,存储等,但客户能控制部署的应用程序,也可能

                             控制运行应用程序的托管环境配置

                             

               SaaS:Software as a Serveice 软件即服务

                             提供给客户的服务时运营商运行在云计算基础设施上的应用程序,用户可以在各种

                             设备上通过客户端界面访问,如浏览器,消费者不需要管理或控制任何云计算基础设施,

                             包括网络,服务器,操作系统,存储等;

                             

 

常用自动化运维工具

               ansible:python                 Agentless中小型应用环境,通过ssh实现,无需部署代理程序

               Saltstack:python        一般需部署agent,执行效率更高

               Puppet:ruby                      功能强大,配置复杂,适合大型环境

               Fabric:python                    agentless

               chef:ruby                        

               cfengine

               func

               

ansible特性:----------------------------------------------------------------------

                      模块化:调用特定的模块,完成特定任务

                     有Paramiko(基于ssh的python实现),pyYAML,jinja2 三个关键模块

                     支持自定义模块

                     基于python语言实现

                     部署简单,基于python和ssh,

                     安全,基于openssh

                     支持playbook 编排任务

                     具有幂等性,一个任务执行1遍和执行n遍效果一样,不因重复执行带来意外情况

                     无需代理,不依赖PKI(无需ssl)

                     可使用任务编程语言写模块

                      YAML格式,编排任务,支持丰富的数据结构

                     交强大的多层解决方案

               

ansible主要组成部分:

               invenroty:                 ansible管理主机的清单,存放于/etc/ancible/hosts

               modules:               ansible执行命令的功能模块,多数为内置核心模块,也可以自定义

               ansible playbook:      任务剧本,编排定义ansible任务集合的配置文件,由ansible顺序

                                                  执行,通常是JSON格式的YML文件

               plugins:                      模块功能的补充,如连接类型插件,循环插件,变量插件,过滤插件等

               API:                           供第三方程序调用的应用程序编程接口

               ansible: 组合Inventory api modules plugins  的绿框,可以理解为是ansible的命令工具

                                    其为核心执行工具

                                    

               ansible命令执行来源:

                            USER  普通用户,即system administrator

                             CMDB(配置管理数据库)API调用

                            Public/private  cloud  API调用

                            user -> ansible  playbook -> ansible

                    

               利用ansible实现管理的方式:

                            ad-hoc 即ansible命令,用户临时命令使用场景

                            ansible-playbook  主要用于长期规划好的,大型项目的场景,需要由前提的规划

                    

               absible-playbook 执行过程:

                             将已有编排好的任务集写入ansible-palybook

                            通过ansible-playbook 命令分拆任务逐条ansible命令,按预定规则逐条执行

                    

               ansible主要操作对象:

                            host主机

                             network网路设备

                             

               注意事项:     

                            执行ansible的主机一般称为主控端,中控,master或堡垒机

                            主控端python版本需要2.6或以上

                            被控端python版本小于2.4需要安装python-simplejson

                            被控端如开启selinux,需要安装libselinex-python

                             windows不能作为主控端

                             

ansible安装:

               1     rpm包安装,epel源

                                   yum install  ansible

               

               2     编译安装:

                                   yum -y  install python-jinja2 PyYAML python-paramiko python-babel  python-crypto

                                   tar xf  ansible-1.5.4.tar.gz

                                   cd  ansible-1.5.4

                                   python  setup.py build

                                   python  setup.py install

                                   mkdir  /etc/ansible

                                   cp -r  examples/* /etc/ansible                     

 

               3     git方式:

                                   git clone  git://github.com/ansible/ansible.git --recursive

                                   cd ./ansible

                                   source ./hacking/env-setup              

 

               4     pip安装: pip是安装Python包的管理器,类似yum

                                   yum install  python-pip python-devel

                                   yum install  gcc glibc-devel zibl-devel rpm-bulid openssl-devel

                                   pip install  --upgrade  pip

                                   pip install  ansible --upgrade

 

               5     确认安装版本:

                                   ansible  --version

                             

相关文件:

               配置文件:

                             /etc/ansible/ansible.cfg        主配置文件,配置ansible工作特性

                            /etc/ansible/hosts                       主机清单

                             /etc/ansible/roles/                存放roles的目录

                             

               程序:     

                            /usr/bin/ansible                   主程序,临时命令执行工具

                             /usr/bin/ansible-doc            查看配置文档,模块功能查看工具

                             /usr/bin/ansible-galaxy        下载、上传优秀代码或roles模块的官网平台

                             /usr/bin/ansible-playbook 定制自动化任务,编排剧本工具

                             /usr/bin/ansible-pull           远程执行命令的工具

                             /usr/bin/ansible-vault          文件机密工具

                             /usr/bin/ansible-console      基于console界面与用户交互的执行工具

                             

               主机清单:

                            Inventory  :主机清单

                            默认的Inventory file为:    /etc/ansible/hosts

                            inventory  file可以有多个,且也可以通过dynamic inventory 来动态生成

 

主机清单:Inventory

               /etc/ansible/hosts文件格式:

               inventory文件遵循INI文件风格,中括号中的字符为组名。可以将同一个主机同时

               归并到多个不同的组中;此外,如果目标主机使用了非默认的ssh端口,还可以在主机名

               之后使用 :端口号 来标明

               

               例如:

                             [webservers]

                             192.168.65.128

                             192.168.65.132

                             www.test1.com

                             www.test2.com

                                           

                             [dbservers]

                             192.168.65.150:2222

                             192.168.65.160

                             db1.test.com

                             db2.test.com

                                           

               注意:     如果使用name来标明主机,那么就必须提供能供解析的name-server,或者修改

                            本地host文件。/etc/hosts

                                    

               如果主机名称遵循相似的命名模式,还可以使用列表的方式标识各主机

               例如:

                             [webs]

                            www.test[1:100].com             1-100

                            ca.test[a:f].com              a-f

               

               

ansible配置文件:

               /etc/ansible/ansible.cfg        一般保持默认

               [defaults]

               #inventory                   =  /etc/ansible/hosts      主机列表配置文件

               #library                =  /usr/share/my_modules/ 库文件存放目录

               #remote_tmp              =  $HOME/.ansible/tmp      临时py命令文件存放的远程主机目录

               #local_tmp                   =  $HOME/.ansible/tmp        本机的临时命令执行目录

               #forks                          =  5                                      默认并发数

               #sudo_user                  = root                                  默认sudo用户

               #ask_sudo_pass           =  True                  每次执行ansible命令是否询问ssh密码

               #ask_pass                    = True                 

               #remote_port              =  22

               #host_key_checking     = False    检查对应服务器的host_key,建议取消注释

               #log_path      =  /var/log/ansible.log 日志文件

 

               

ansible-doc    显示模块帮助

               ansible-doc [options][modules]

                            -a                  显示所有模块的文档

                            -l --list 列出可用模块

                            -s --snippet  显示指定模块的playbook片段

                             

               示例:

                            ansible-doc -l  

                            ansible-doc  ping

                            ansible-doc -s  ping

                    

ansible命令:---------------------------------------------------------------------

               

               通过ssh实现配置管理,应用部署,任务执行等功能,建议配置ansible端能基于秘钥

               认证的方式联系各被管理节点

               

               ansible [-m module_name] [-a  'args']

                            --version              显示版本

                            -m module          指定模块,默认为command

                            -v -vv -vvv   显示详细过程

                            -list-hosts     显示主机列表,可简写  --list

                            -k --ask-pass      提示连接密码,默认key验证

                            -K --ask-become-pass  提示输入sudo密码

                            -C --check           检查,并不执行

                            -T --timeout=      执行命令的超时时间,默认10s

                            -u  --user=REMOTE_USER    执行远程命令执行的用户

                            -b --bacome       代替旧版的sudo  切换

 

               示例:

                            ansible centos6 -m  shell -u hello -k -a 'ls -l /data/f1'

                            ansible all -m command  -u wang  --become-user=root -a 'ls /root'  -b –k  -K            

                             

               host-pattern          匹配主机的列表

                             

                            all   表示所有inventory中的所有主机

                                   ansible all  -m ping

                             

                            *             通配符,任意长度任意字符

                                   ansible "*"  -m ping

                                   ansible  192.168.65.* -m ping

                                   ansible  1*      -m ping

                                   ansible "c*"  -m ping

                                           如单独使用或者使用时字符串较短 如1-2个字符,建议使用""

                                           否则容易语法错误

                             

                            :           或

                                   ansible  "centos6:centos7" -m ping

                                   ansible  "centos6:192.168.65.132" -m ping

                                   ansible  "centos6:192.168.65.132:centos7" -m  ping

 

                            :&           逻辑与

                                   ansible  "webs:&dbs" -m ping

                                           表示在webs组里,并且在dbs组里的主机

                                           

                            :!            逻辑非

                                   ansible  'webs:!centos6' -m shell -a 'echo  hello'

                                           表示在webs组中,但不在centos6中的主机

                                           

                            注意:    :&  用"" ''  都可以

                                           :!     只能使用''

                                           

                            综合逻辑:

                                   ansible  'webs:dbs:¢os6:!centos7' -m  ping

 

                            正则表达式:

                                   ansible  '~centos(6|7)' -m ping

                                   ansible  '~(web|db).*\.magedu\.com' -m  ping

                                    

               

ansible命令的执行过程:

               1     加载自己的配置文件 默认/etc/ansible/ansible.cfg

               2     加载自己对应的模块文件,如shell、 copy

               3     通过ansible将模块或命令生成对应的临时py文件,并将该文件传输至远程服务器

                     的对应执行用户$HOME/.ansible/tmp/ansible-tmp-数字/xxx.Py文件

               4     给文件+x  执行权限

               5     执行并返回结果

               6     删除临时py文件,sleep 0 退出

               

               执行状态:

                            绿色:    执行成功并且不需要做改变的操作

                            ×××:    执行成功并且对目标主机做变更

                            红色:    执行失败

                             

ansible 常用模块:------------------------------------------------------------------

               

               command:默认模块,可忽略 -m 选项,在远程主机上执行命令,

                            ansible webs -a 'rpm  -q httpd'

                            ansible webs -m  command -a 'rm -f /data/*'

                                    常用选项:

                                           chdir=/DIR                    cd到/DIR目录下执行

                                           creates=filename   如果filename文件存在,将不执行         不存在-->  执行

                                           removes=filename 如果filename文件不存在,将不执行       存在_-->  执行

                                    

               注意:command模块不支持 $name  < > | ; & 等特殊用法,用shell模块实现

               

               shell:     和command 相似,用shell执行命令,支持 $name < > | ; &  等特殊用法

                            ansible webs -m  shell -a 'echo magedu | passwd --stdin hello'

                            调用bash执行命令

                            但是类似 cat /tmp/stanley.md |awk -F'|' '{print $1 $2}'  &>/tmp/example.txt

                             这样的复杂命令就算使用shell模块也可能失败,而且存在引号冲突问题,

                             解决办法:写到脚本中,copy到远程,执行,再把需要的结果拉回执行命令的机器

                                    常用选项:     

                                           chdir

                                           creates

                                           removes

                                           

               script:运行脚本

                            ansible webs -m  script -a f1.sh

                                    常用选项:     chdir

                                                         creates

                                                         removes

                                                         --some-arguments 1234      提供运行参数

                                                         

               copy:      从本地复制文件到远程主机

                            常用选项:   

                                           backup=yes|no      如果目标存在,是否备份

                                           src=                源文件,本地

                                           dest=                     目标路径,远程主机

                                           group=                  所属组

                                           owner=                 所有者

                                           mode=                  设置权限

 

                            ansible webs -m copy  -a 'src=/etc/fstab dest=f2 backup=yes'

                                           ansible webs -m shell -a 'ls /root'

                                           如果不指明路径,默认复制到家目录下

                            ansible dbs -m copy  -a 'src=/root/f2 dest=/data/cat backup=yes mode=000'

                             

               fetch:    从远程主机复制文件到本地主机,与copy相反

                             只能复制单个文件,目录可先tar在fetch

                            选项:

                                           src=

                                           dest=

                            会在dest目录下生成多个主机名命名的目录,且会将源文件的路径一并生成

                            如:

                                           ansible dbs -m fetch -a 'src=/etc/passwd dest=/data/bak'   

                                           [root@Centos6 /data]#tree

                                           .

                                          └──  bak

                                                  ├── 192.168.65.150

                                                  │   └── etc

                                                  │       └──  passwd

                                                  └── 192.168.65.160

                                                         └── etc

                                                                └── passwd

 

                                          5  directories, 2 files

               

               file:       设置文件属性

                            选项:            

                                           path=  dest= name=         等价,指明文件路径

                                          state      

                                                          =derictory              如果不存在则创建目录

                                                         =file                如果不存在默认不创建

                                                         =touch                  默认,创建文件或目录

                                                         =absent                 递归删除        

                                                         =link                      软链接

                                                         =hard                    硬链接

                                           group=                                所属组

                                           owner=                               所有者

                                           src=                              源,创建链接文件需指明

                                           mod=                                  权限        

                             

                            示例:

                            创建文件:

                                           ansible dbs -m file -a 'path=/data/f1 state=touch'

                            创建目录:

                                           ansible dbs -m file -a 'path=/data/dir1  state=directory'

                            删除文件或目录

                                           ansible dbs -m file -a 'path=/data/dir1  state=absent'

                            创建链接

                                           ansible dbs -m file -a 'src=/data/f1 path=/data/f1.link  state=touch'

                             

                             注意:不支持通配符*操作,一次只能操作一个文件或目录

               

               hostname:    管理主机名

                            ansible  192.168.65.150 -m hostname -a 'name=NAME'

                             

               yum:       管理程序包

                            常用选项:   

                                                  name=                  包名

                                                  state=

                                                         present installed latest         安装

                                                         absent    removed                      卸载

                                                         list= installed   name

                                                         disable_gpg_check=yes|no 禁用gpgcheck  默认no

                                                         update_cache=yes|no          是否清楚缓存默认no

                                                         

                            安装程序包:

                                           ansible dbs -m yum -a 'name=vsftpd,httpd'

                            卸载程序包

                                           ansible dbs -m yum -a 'name=vsftpd,httpd  state=absent'

                            查看包列表:

                                           ansible dbs -m yum -a 'list=NAME or intalled'

                            rpm包直接使用yum安装:

                                           ansible dbs -m copy -a 'src=rpmfile dest=/path/'

                                           ansible dbs -m yum -a 'name=/path/rpmfile  disable_gpg_check=yes'

                                           

                             

               cron:     计划任务

                            时间格式选项:minute hour day month weekday

                            选项:    job=                     作业内容

                                           name=                  作业标签

                                           user=                    用户

                                           disabled=true|false        yes|no    禁用或者启用

                                           state=                    默认present 启用

                                                         absent    删除

                             

                            示例:

                            新建计划任务:

                                           ansible dbs -m cron -a 'minute=* job="wall hello there"  name=wall'

                            禁用计划任务

                                           ansible dbs -m cron -a 'disabled=yes job="wall hello there"  name=wall'

                            启用:

                                           disabled=no或false

                            删除:

                                           ansible dbs -m cron -a 'job="wall hello there" name=wall  state=absent'

        

               

               service:服务管理

                            常用选项:

                                           name=                  服务名

                                           state=                           

                                                         reloaded

                                                         restarted

                                                         running

                                                         started

                                                         stopped

                                           enabled=yes|no    开机启动

                             

                            示例:

                             启动并设置开机启动服务

                                           ansible dbs -m service -a 'name=httpd state=started  enabled=yes'

                            关闭:

                                           ansible dbs -m service -a 'name=httpd state=stopped  enabled=no'

                                           

               user:       用户管理模块

                            常用选项:

                                           create_home=no           不创建家目录,默认yes

                                           comment=""                 描述信息

                                           group=                         主组

                                           groups=                       附加组

                                           home=                         手工设置家目录位子

                                           name=                         用户名

                                           password=                   密码

                                           shell=                           shell类型

                                           system=yes|no              是否是系统该用户

                                           uid=                             uid

                                           state=absent                删除用户,默认present

                                           remove=yes                 删除家目录,state=absent时使用

                            示例:

                            新建账号:

                                           ansible dbs -m user -a 'name=lily uid=1080 home=/data/home/ comment="a  beauty girl" groups=root'

                            删除账号:

                                           ansible dbs -m user -a 'name=lily state=absent  remove=yes'

 

               group: 组管理模块

                            常用选项:

                                          gid=                      gid

                                           name=                  组名

                                           state=absent  删除 默认present

                                           system=yes|no      是否系统账号,默认no

                                           

 

ansible系列命令:----------------------------------------------------------------

                            ansible  

                             ansible-doc

                            ansible-playbook  

                             ansible-vault

                             ansible-console

                            ansible-galaxy  

                            ansible-pull                       

ansible-galaxy:

               连接https://galaxy.ansible.com 下载相应的roles

               查看已安装的galaxy

                            ansible-galaxy list  [role_name]

                            ansible-galaxy list  "Stouts grafana"

               安装roles

                            ansible-galaxy  install "Stouts grafana"

               删除roles

                            ansible-galaxy  remove "Stouts grafana"

 

 

ansible-pull:

               推送命令至远程,效率无限提升,对运维要求较高

               

 

ansible-playbook:

               类似shell,用来解释执行编写playbook文件,通常是yml后缀,如:

               ansible-playbook hello.yml

                            [root@Centos6 ~]#cat hello.yml

                             ---

                            - hosts:  dbs

                              remote_user: root

                             

                              tasks:

                                   - name:  hello

                                     command: /usr/bin/wall hello  there

        

 

ansible-vault:

               功能:加密解密yml文件

               ansible-vault  [create|encrypt|decrypt|edit|view|rekey]

                            ansible-vault  encrypt hello.yml 加密

                            ansible-vault view  hello.yml         可以查看加密文件,需要输入密码

                            ansible-vault  decrypt hello.yml 解密

                            ansible-vault edit  hello.yml               编辑加密文件

                            ansible-vault rekey  hello.yml             修改口令

                            ansible-vault create  new.yml             创建新文件

                    

                    

ansible-console:2.0+新增,可交互执行命令,支持tab

               

               工作台介绍:

                            [root@Centos6 ~]#ansible-console

                            Welcome to the  ansible console.

                            Type help or ? to list commands.

 

                            root@all (5)[f:5]$

                            执行用户@当前操作的主机组(当前组的主机数量)[f:并发数]$

               

               设置并发数:              forks n          例如:forks  10

               切换组:                     cd 主机组            例如:cd webs

               列出当前组主机列表:list

               列出所有的内置命令:?或help

               退出:                            exit

               

               示例:

                            root@dbs (2)[f:5]$ shell ls /data

                            root@dbs (2)[f:5]$ yum name=htop state=present

 

 

palybook:------------------------------------------------------------------------

 

playbook示例: 安装并启动httpd服务

---

- hosts: dbs

   remote_user: root

 

   tasks:

    -  name: install package

       yum: name=httpd

    -  name: tempalte conf6

       template: src=httpd.conf6.j2  dest=/etc/httpd/conf/httpd.conf

       when: ansible_distribution_major_version == "6"

       notify: reload conf

    -  name: tempalte conf7

       template: src=httpd.conf7.j2  dest=/etc/httpd/conf/httpd.conf

       when: ansible_distribution_major_version == "7"

       notify: reload conf

    -  name: test web6

       when: ansible_distribution_major_version == "6"

       shell: echo "welcome to web  centos6" > /var/www/html/index.html

    -  name: test web7                                                                           

       when: ansible_distribution_major_version == "7"

       shell: echo "welcome to web centos7" >  /var/www/html/index.html

    -  name: start service

       service: name=httpd state=started

    -  name: testnet

       shell: ping -c2 -w2 172.20.0.1

       tags: testnet

   

   handlers:

    -  name: reload conf

       service: name=httpd state=reloaded           

               

               

palybook:

               一组ansible指令的集合,类似shell脚本

               采用YAML语言编写

               一般使用.yml 后缀 如:hello.yml

               通过ansible-playbook解释执行,如ansible-playbook hello.yml

                             

YAML语言:

                     可读性好

                     和脚本语言的交互性好

                     使用实现语言的数据模型

                     有一个一致的信息模型

                     易于实现

                     可以基于流来处理

                     表达能力强,扩展性好

                     官方地址:http://www.yaml.org

               

YAML语法简介:

               在单一档案中,可用连续三个连字号(---)区分多个档案。另外,还有选择性的

               连续三个点号(...)来表示档案结尾

               次行开始正常些playbook的内容,一般建议写明该playbook的功能

               使用#号注释代码

               缩进必须是统一的,不能空格和tab混用

               缩进的级别必须一致,同样的缩进表示同样的级别,程序判断配置的级别是通过缩进

               结合换行来实现

               k/v(键值对)的值可同行写也可以换行些,同行使用: 分隔

               v可以是个字符串,也可以是另一个列表

               一个完整的代码块功能需要最少元素包括name:task

               一个name只能包括一个task

               文件后缀通常为yml或yaml

                             

 

YAML列表:

               list:列表,其所有元素均使用 - 打头

               列表的每一项可以有多行,如

                            - name:

                              yum:

                              notify:

                              when:

                             

YAML字典:

               dictionary:字典,通常由多个key与value构成

               如:        

                     - {  name: install httpd,yum: name=httpd }

                             

playbook核心元素:

               hosts:           执行的远程主机列表

               remote_user:指定用户身份

               tasks:           任务集

               varniables:内置变量或自定义变量在playbook中调用

               templates:    模板,可以替换模板文件中的变量并实现一些简单逻辑的文件

               handlers:      和notify结合使用,如果notify:A当前task执行发生修改操作,

                                    则触发执行handlers中定义的A操作

               tags:            标签,指定某条任务执行,用于选择运行playbook中的部分代码。

                                    如:

                            ansible-playbook -t  install httpd.yml

                             

               注意:     多个task可以使用同一个tags

                                                  

                                    

hosts:   列表必须事先定义在主机清单中

               可以使用 *,:,:&,:!来定义列表

               如:

                            webs:dbs

                            webs:!dbs

               

remote_user:

               指明执行命令的用户身份

               且支持在task中以sudo方式执行

               例如:

                     - host:  webs

                       remote_user: root

                       tasks:

                         - name: test ping

                              ping:

                              remote_user: hello

                              sudu: yes                        

                              sudu_user: lily    如不知指明,默认sudo为root

                                           

task列表和action:

               play的主体部分是task list,task  list 中的各任务按次序逐个在host中指定

               的所有主机上执行,即在所有主机上完成第一个任务后在开始第二个。在运行自上

               而下某playbook时,如果中途发生错误,多有已执行任务都会回滚,因此,在更正

               playbook后重新执行一次即可

                             

               task的目的是使用指定的参数执行模块,而在模块参数中可以使用变量,模块执行是

               幂等的,这意味着多次执行是安全的,因为其结果均一致

                             

               每个task都应该有其name,用于playbook的执行结果输出

               如果未提供name,则action的结果将用于输出

                             

               格式:

                     1     action: module  arguments

                     2     module:  arguments

                                    

               某任务的状态在运行后卫changed时,可通过notify通知给相应的handlers任务。

                             

               任务可通过tags打标签,而后可在ansible-playbook命令中使用 -t 选项指定执行

                             

               如果命令或脚本的退出码不为零,可以使用下方方式使整个playbook继续执行,而不是回滚

                              tasks:

                              - name: test

                                   shell: false  ||/bin/true

                            或者:

                            tasks:

                              - name: test

                                   shell:  false

                                   ignore_error:  true

 

运行playbook:

               ansible-playbook name.yml

               常用选项:

                            --check|-C           只检测可能发生的改变,不真正执行

                            --list-hosts   列出运行任务的主机

                            --limit                  主机列表,只针对主机列表中的主机执行

                            -v -vv -vvv   显示详细信息

                            -t tags          只执行tags标记的task

 

               

playbook变量:

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

               变量来源:

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

                            ansible all -m setup  list

                             

                            ansible webs -m  setup |grep cpu

                                           "ansible_processor_vcpus": 1,              cpu数量

                             

                            ansible    all -m setup|grep  distribution

                                           ansible_distribution_major_version     主版本号

                            ansible all -m setup  |grep os_family

                                           "ansible_os_family": "RedHat",             版本体系

                            ansible all -m setup  |grep memtotal

                                           "ansible_memtotal_mb": 980,                    内存大小

                                           

                    

                     2     在/etc/ansible/hosts中定义

                             普通变量:主机组中主机单独定义,优先级高于公共变量

                                    [websrvs]

                                    192.168.99.101 http_port=8080 hname=www1

                                    192.168.99.102 http_port=80  hname=www2

                             公共(组)变量:针对主机组中所有主机定义统一变量:

                                   [websvrs:vars]

                                    http_port=808

                                   mark=“_”

                                    [websrvs]

                                    192.168.99.101 http_port=8080 hname=www1

                                    192.168.99.102 http_port=80 hname=www2

                    

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

                                    ansible-playbook -e varname=VALUE

                                    

                     4     在playbook中定义

                                    vars:

                                   - var1:  value1

                                   - var2:  value2

 

                     5     在role中定义

                    

                     6     使用专用变量文件:

                                    vars.yml

                                   var1:  httpd

                                   var2:  vsftpd

 

                                    test.yml

                                    ---

                                   - host:  webs

                                     remote_user: root

                                     vars_files:

                                          -  vars.yml

 

               ansible变量优先级:

                            命令行 -e --> playbook定义的变量  -->主机清单中定义的变量

 

               变量定义:

                             key=value1

                             http_port=80

               

               变量调用方式:

                            通过{{ variable_name }}调用变量,且变量名前后必须有空格,有时用

                                   "{{  variable_name }}" 才生效

                             

                            示例:

                                          vim  testvar.yml

                                           ---

                                          -  hosts: dbs

                                            remote_user: root

                                            vars:

                                                  - var1: httpd

                                                  - var2: vsftpd

                                            tasks:

                                                  - name: status

                                                    service: name={{ var1 }} state=reloaded

                                                  - name: rpm status

                                                    shell: rpm -q "{{ var2 }}"    

 

                                           ansible-playbook -e 'var1=dhcp var2=tftp'  testvar.yml

 

                     在配置文件中指定变量

                     ansible websvrs –m hostname  –a ‘name={{ hname }}{{ mark }}{{ http_port  }}’

                     在命令行执行变量

                     ansible websvrs –e  http_port=8000 –m hostname –a ‘name={{ hname }}{{ mark  }}{{ http_port }}’

                    

                    

 

templates:

               文本文件,嵌套有脚本

                            使用jinja2语言,使用字面量,有下面形式:

                                           字符串:使用单引号或双引号

                                           数字:整数,浮点数

                                           列表:[item1,item2..]

                                           元组:(item1,item2,...)

                                           字典:{key1:value1,key2:value2,..}

                                           布尔型:true/false

                            算术运算:+,-,*,/,//,%,**

                            比较操作:==,!=,>,>=,<,<=

                            逻辑运算:and or not

                            流表达式: for if when

                             

               

               根据模块文件动态生成对应的配置文件

               mkdir ansible/templates    

               在playbook同级的目录中建立templates目录,模板文件必须位于templates目录下,后缀为.j2

               使用时src就可以使用默认路径,src=文件名,

               template模块只能在playbook使用,不能在ansible命令行使用

               

               使用template同步配置文件,在.j2  文件中支持使用ansible setup模块中的所有变量

               且支持算术运算

               例如:

                            Listen {{ ansible_memtotal_mb//7 }}

                            Listen {{ ansible_memtotal_mb+6 }}

 

               注意:不支持两个变量之间的算术运算:

                     例如:

                     Listen {{  ansible_memtotal_mb//ansible_distribution_major_version  }}

                     Listen {{  ansible_memtotal_mb+ansible_distribution_major_version  }}

 

 

when: 

               when语句使用jinja2表达式语法

               用在playbook中,只有当when:语句为真时,此task才执行

               例如:

                     - name: tempalte  conf7

                       template: src=httpd.conf7.j2  dest=/etc/httpd/conf/httpd.conf

                       when: ansible_distribution_major_version ==  "7"

                    

               

with_items: 迭代

               当有需要重复性执行的任务时,可以使用迭代机制

               对迭代项的引用,固定变量名为"item"

               要在task中使用with_items给定要迭代的元素列表

               列表格式

                            字符串

                            字典

               

               示例:            

                            [root@Centos6  ~/ansible]#vim createuser.yml                       

                             ---

                            - hosts: dbs  

                              remote_user: root

                              tasks:                                                                                       

                                   - name:  create user

                                     user: name={{ item  }} 

                                     tags: create

                                     with_items:

                                          -  user1

                                          -  user2

                                          -  user3

                                   - name:  delete user

                                     user: name={{ item  }} state=absent remove=yes

                                     tags: delete

                                     with_items:

                                          -  user1

                                          -  user2

                                          -  user3

 

               示例2:

                            vim  test_item1.yml

                             ---

                            - hosts: dbs  

                              remote_user: root

                              tasks:

                                   - name: touch  some file

                                     file: name=/data/{{  item }} state=touch

                                     with_items:

                                          -  file1

                                          -  file2

                                          -  file3

                                     tags: touch

                                   - name:  delete some files

                                     file: name=/data/{{  item }} state=absent

                                     with_items:

                                          -  file1

                                          -  file2

                                          -  file3

                                     tags: del     

 

 

               item 嵌套:

               例如:     要求新建3个目录dir1,dir2,dir3

                            并且新建3个空文件,file1,file2,file3分别位于对应的目录

                            vim  test_items2.yml

                             ---

                            - hosts:  dbs

                              remote_user: root

                              tasks:

                                   - name:  mkdir

                                     file: name=/data/{{  item }} state=directory

                                     with_items:

                                          -  dir1

                                          -  dir2

                                          -  dir3

                                   - name: touch  file

                                     file: name=/data/{{  item.dir }}/{{ item.file }} state=touch

                                     with_items:

                                          -  { dir: dir1,file: file1 }

                                          -  { dir: dir2,file: file2 }

                                          -  { dir: dir3,file: file3 }

                                    

playbook中的for和if:

        说明:     使用jinja2 语法:

                     仅适合.j2 文件

                                   {% for p in  ports %}

                                    代码段

                                   {% endfor  %}

                    

                                   {% if p is  defined %}

                                    代码段

                                   {% endif  %}

                    

                     类似shell中的for使用,其中p可以任意指定, ports 代表变量,需要与playbook主

                     脚本中的vars:下的变量一致

                     if 为真  代码段执行,反之不执行 defined :被定义

        

        示例1:

                     yml         vim for1.yml

                                    ---

                                   - hosts:  dbs

                                     remote_user: root

                                     vars:

                                          -  ports:

                                                  - 1001

                                                  - 1002

                                                  - 1003

                                     tasks:

                                          -  name: copy file

                                            template: src=for1.j2  dest=/data/for1.conf

                                    

                     j2            vim  templates/for1.j2

                                   {% for p in  ports %}

                                   server  {

                                          listen  {{ p }}

                                    }

                                   {%  endfor%}

                    

                     结果:    [root@2-centos6 /data]#cat for1.conf

                                   server  {

                                          listen  1001

                                    }

                                   server  {

                                          listen  1002

                                    }

                                   server  {

                                          listen  1003

                                    }

        

        示例2:

                     yml         vim for2.yml

                                    ---

                                   - hosts:  dbs

                                     remote_user: root

                                     vars:

                                          -  infos:

                                            - group: boy

                                                  name: tom

                                                  age: 18

                                                  likes: read

                                            - group: girl

                                                  name: lily

                                                  age: 19

                                                  likes: boy

                                            - group: man

                                                  name: big dog

                                                  age: 35

                                                  likes: girl

                                            - group: women

                                                  name: cherry

                                                  age: 41

                                                  likes: monny

                                     tasks:

                                          -  name: copy file

                                            template: src=for2.j2  dest=/data/for2.conf

                    

                     j2            vim  tempaltes/for2.conf

                                   {% for p in  infos %}

                                   group: {{ p.group }}

                                           the  winner is:

                                                         name: {{ p.name }}

                                                         age: {{ p.age }}

                                                         likes: {{ p.likes }}

                                   {% endfor  %}

 

                     结果:    [root@2-centos6 /data]#cat for2.conf

                                   group:  boy

                                          the  winner is:

                                                         name: tom

                                                         age: 18

                                                         likes: read

                                   group:  girl

                                          the  winner is:

                                                         name: lily

                                                         age: 19

                                                         likes: boy

                                   group:  man

                                          the  winner is:

                                                         name: big dog

                                                         age: 35

                                                         likes: girl

                                   group:  women

                                          the  winner is:

                                                         name: cherry

                                                         age: 41

                                                         likes: monny

 

 

        示例3:

                     yml:     vim  for3.yml

                                    ---

                                   - hosts:  dbs

                                     remote_user: root

                                     vars:

                                          -  webs:

                                                  - addr: 10.magedu.com

                                                    port: 810

                                                  - addr: 20.magedu.com

                                                    port: 820

                                                    rootdir:  /data/root20/

                                                  - addr: 30.magedu.com

                                                    port: 830

                                                    rootdir:  /data/root30/

                                     tasks:

                                          -  name: copy file

                                            template: src=for3.j2  dest=/data/for3.conf

 

                     j2:           vim templates/for3.j2  

                                   website  list:

                                   {% for p in  webs %}

                                                  website: {{ p.addr }}

                                                  port: {{ p.port }}

                                   {% if p.rootdir is defined %}

                                                  rootdir: {{ p.rootdir }}

                                   {%  endif%}

 

                                   {%  endfor%}

 

                     结果:    [root@2-centos6 /data]#cat for3.conf

                                   website  list:

                                                  website: 10.magedu.com

                                                 port: 810

 

                                                  website: 20.magedu.com

                                                  port: 820

                                                  rootdir: /data/root20/

 

                                                  website: 30.magedu.com

                                                  port: 830

                                                  rootdir: /data/root30/

                                    

 

roles:---------------------------------------------------------------------------

               将原本playbook中的各个tasks,handlers,vars,拆分成单独的小模块

               而playbook主文件:

                             main.yml中使用

                                   -  include:(旧)

                                   -  import_tasks: (新)

                            调用模块                                    

               

               目录编排:

                            [root@Centos6  ~/ansible/roles]#tree

                             .

                            └── nginx              

                                   ├──  files          

                                   ├──  handlers   

                                   ├──  tasks

                                   ├──  templates

                                   └──  vars

               

                      roles下新建目录即为项目名称:需包含以下子目录

                     files/:             存放copy或script模块等调用的文件

                     templates/:  template模块查找所需要的模板文件的目录

                     tasks/:    定义task,role的基本元素,至少应该包含一个名为main.yml的文件,

                                           其他的文件需要在此文件中通过include包含

                     handlers/:     至少应该包含一个名为main.yml的文件,其他的文件需要在此文件中通过include包含

                     vars/:             定义变量。至少应该包含一个名为main.yml的文件

                                           其他的文件需要在此文件中通过include包含

                     meta/:             定义当前角色的特殊设定及其依赖关系,至少应该包含一个名为main.yml的文件

                                           其它文件需在此文件中通过include进行包含

                     default/:       设定默认变量时使用此目录中的main.yml文件

                    

 

创建role的步骤:

               1     创建以roles命名的目录

               2     在roles目录中分别创建以各角色名称命名的目录,如nginx

               3     在每个角色命名的目录中分别创建files,handlers,meta,tasks,templates和vars目录

                      如用不到的空目录,也不可不用创建

               4     角色编辑

               5     在playbook文件中,调用各角色

 

 

role创建示例:

                     [root@Centos6  ~/ansible/roles]#tree

                     .

                     └──  nginx

                            ├──  files

                            │   └──  f1

                            ├──  handlers

                            │   └──  main.yml

                            ├──  tasks

                            │   ├──  copyfile.yml

                            │   ├──  groupadd.yml

                            │   ├──  main.yml

                            │   ├──  start.yml

                            │   ├──  templ.yml

                            │   ├──  useradd.yml

                            │   └──  yum.yml

                            ├──  templates

                            │   └── nginx.conf.j2

                            └──  vars

 

role创建:

cd roles/nginx

               cd tasks/

                            vim  groupadd.yml

                            - name: create group  nginx

                              group: name=nginx system=yes  gid=80

                             

                            vim  useradd.yml

                            - name: add user  nginx

                           user: name=nginx uid=80 system=yes  shell=/sbin/nologin

 

                            vim  yum.yml

                            - name: install  package

                              yum: name=nginx                 

 

                            vim  templ.yml

                            - name: copy  conf

                              template: src=nginx.conf.j2 dest=

                              when: ansible_distribution_major_version ==  "6"

                              notify: reload conf

 

                            vim  copyfile.yml

                            - name: copy  file

                              copy: src=f1  dest=/var/lib/nginx

 

                            vim  start.yml

                            - name: start  service

                              service: name=nginx state=started  enabled=yes

 

                            vim  main.yml

                            - import_tasks:  groupadd.yml

                            - import_tasks:  useradd.yml

                            - import_tasks:  yum.yml

                            - import_tasks:  templ.yml

                            - import_tasks:  copyfile.yml

                            - import_tasks:  start.yml     

        

               cd handlers/

                            vim  mian.yml

                            - name: reload  conf

                              service: name=nginx state=reloaded    

        

               cp /etc/nginx/nginx.conf templates/nginx.conf.j2

               vim templates/nginx.conf.j2

                            worker_processes  {{ ansible_processor_vcpus*10 }};

 

               touch files/f1

 

 

role调用:调用roles的playbook 要与roles目录在一个目录中       

               vim nginx.role.yml

               ---

               - hosts: dbs

                 remote_user:  root

                 roles:

                     - role:  nginx

        

引用另外一个role中的单个任务,如下,使用完整路径引用即可

                     vim  main.yml

                     - include:  group.yml

                     - include:  user.yml

                     - include:  yum.yml

                     - include:  templ.yml

                     - include:  start.yml

                    

                     - include:  roles/httpd/tasks/copyfile.yml     

        

role调用中的tags使用:

 

                     vim  some_role.yml

                     - hosts:  webs

                       remote_user: root

                       roles:

                            - { role: nginx,tags: ['web','nginx'] }

                            - { role: httpd,tags: ['web','httpd'],when:  ansible_distribution_major_version == "7" }

                            - { role: app,tags: ['app'] }

 

                     ansible-playbook -t web  some_role.yml  挑标签执行

 

        

推荐资料:     

        http://galaxy.ansible.com

    https://galaxy.ansible.com/explore#/

    http://github.com/

    http://ansible.com.cn/

    https://github.com/ansible/ansible

    https://github.com/ansible/ansible-examples

 

笔记整理完成时间:2018年5月31日20:33:43