1、ansible的基本命令格式
    ansible <host-pattern> [options]
    #host 必选项,表示Inventory文件中指定的主机或者主机组,可以为ip、hostname、Iventory中的group组名,还可以使用.*等通配符
    #option可选项,常见可选项如下
    -m name 或 --module=name :       指定执行使用的模块名
    -u username 或 --user=username : 指定远程主机以什么用户执行命令
    -s  或 --sudo :                  相当于linux中切换到root用户执行命令
    -U sudo_username 或 --sudo-user=sudo_username : 表示切换到指定的用户sudo_username执行命令
    -b 或 --become :                                替换旧版中的-s和--sudo命令
    -become-user  :                                  替换旧版中的--sudo-user命令
    #旧版
    ansible all -m ping -u hadoop                                 #以hadoop用户执行所有主机是否ping得通
    ansible all -m ping -u hadoop --sudo                          #以hadoop用户sudo 切换到root用户执行ping命令
    ansible all -m ping -u hadoop --sudo --sudo-user  master      #以hadoop用户sudo 切换到master用户去执行ping命令
    #新版
    ansible all -m ping -u hadoop -b                           #切换至root用户执行ping命令
    ansible all -m ping -u hadoop -b --become-user master      #以hadoop用户sudo切换到master用户执行ping命令
    ansible web1 -m ping                                      #检查web1服务器组中的所有服务器是否都存活
    ansible web1 -m  copy -a "src=/etc/fstab  dest=/tmp/fstab owner=root group=root mode = 644 backup=yes " #复制本地文件到远程

2、ansible-playbook的基本命令格式
    ansible-playbook test.yml   
    #ansible后面跟事先编辑好的playbook.yml文件
    其实可以看成将一系列ansible命令按照一定的条件组织好,形成一个命令集,存放到yml文件中,再使用ansible-playbook命令统一批量执行。

3、ansible-galaxy命令格式 
#类似于github和pip功能,可以从galaxy中下载和上传roles 
(1)ansible-galaxy [init|info|install|list|remove]  [--help] [options]
    #init:初始化本地的Roles配置,以备上传到galaxy中
    #info:列出指定Roles的详细信息
    #install:从galax中下载并安装指定的Roles到本地
    #list: 列出本地已下载的所有Roles
    #remove: 删除已经下载的Roles
(2)--help 显示init、info、install……的具体用法
    ansible init  --help
    usage : ansible-galaxy init [options] role_name
    options可选参数如下:
    #-f, --force 强制覆盖本地已经存在的Role
    #-h, --help  显示帮助信息
    #-c, --ignore-certs  忽略SSL授权认证的错误
    #-p init_path , --init-path=init_path 设置Role的下载存放地址,默认为当前目录
    #--offline , 直接离线安装,不需要在线下载
    #-s api_server , --server=api_server , 设置下载服务器的目标地址,默认是http://galaxy.ansible.com
    #-v , --verbose , 详细信息模式
    #--version , 显示版本号
(3) 案例:
    ansible-galaxy --ignore-errors install azavea.git   #默认保存在/etc/ansible/roles目录下
    
4、ansible-pull基本命令格式
    ansible-pull [options] [playbook.yml] 
    通过ansible-pull命令与git、crontab共同使用,可以通过crontab定期拉去指定的git版本到本地,并以指定模式自动运行预先制定好的指令
    */20 * * * *  root /usr/local/bin/ansible-pull -o -C 2.1.0 -d /src/www/king-gw/  -i /etc/ansible/hosts - U git://git.kingifa.com/king-gw-ansiblepull >> /var/log/ansible-pull.log 2>&1

5、ansible-doc基本命令格式
    ansible-doc [options] [module...]
    Ansible模块文档说明,ansible中的每一个模块(ping 就是一个模块)都有详细的介绍
    ansible-doc ping    #显示ping模块的详细说明
    ansible-doc -l         #列出所有模块

6、ansible-vault基本命令格式
    ansible-vault [create|encrypt|decrypt|edit|rekey|view]    [--help]    [options]  filename
    valut:街道,拱顶,保险库 , ansible-vault主要用来加密和解密yml文件,加密后的yml文件里面就是一串乱码,必须解密后才能正常查看
    ansible-vault encrypt a.yml    #加密文件,
    ansible-vault decrypt a.yml    #解密文件

7、ansible-console
    通过该命令可以直接进入ansible的交互式命令行终端模式,类似于shell命令行,常用于集中处理一批临时命令,复杂程度低于使用ansible-playbooks
    提示符:root@all (4)[f:5]   #当前用户名@当前所在Inventory中定义的组 组中主机(ip地址)的数量 f:5 表示fork线程数为5
    cd web1 #可以切换地址组,
    forks 2 #设置线程数  
    list    #列出组中的所有主机ip地址
    
8、Inventory文件的配置
    Inventory文件是用来管理主机的配置文件,其中记录了很多不同组,每个组中我们可以添加不同的主机IP地址,通过该文件我们就可以批量化地管理多台主机了
    Inventory文件默认存放路径为/etc/ansible/hosts中,在使用ansible命令是可以通过参数-i 或者 --inventory-file来读取指定的inventory文件
    ansible -i /etc/ansible/hosts  webs -m  ping -u hadoop # 读取指定的Inventory文件
    如果系统中只有一个Inventory文件,我们就不需要特别指定,会默认去/etc/ansible/hosts目录中读取。
    另外一台主机可以同时属于多个不同的组
(1)    定义主机和组
    [websevers]             # 定义一个组
    192.168.1.80            #组内可以为ip地址,也可以为主机名
    web1.magedu.com
    web2.mageud.com:2222     #如果目标主机的ssh端口不是默认的22,就需要在主机名或ip地址后面指定SSH端口号
    web[10:20].magedu.com   #[10:20]通配符代表从10~20之间的所有数字, 这一行包含了11台主机
    web[a:f].mageud.com        #[a:f]代表从a~f中所有的字母,这一行包含了6台主机
    
(2)定义主机变量
    为单个主机服务器添加特有的配置,直接在对应的主机后面,添加变量
    [webservers]
    weba.magedu.com http_port=808 maxRequestPerChild=801 #表示这台主机上的http服务的端口不是默认的8080,而是808 ,以及最大链接数为801个

(3)定义组变量
    为某一个组中所有的主机赋予统一变量
    [webservers]
    weba.magedu.com
    webb.magedu.com
    webc.magedu.com
        
    [webservers:vars]    #给webservers组定义主变量
    ntp_server=ntp.magedu.com    #将webservers组中的所有主机ntp_sserver的值为ntp.magedu.com
    nfs_server=nfs.magedu.com    #将webservers组中的所有主机nfs_sserver的值为nfs.magedu.com
(4)    组中还可以嵌套组
    Inventory中,组还可以包含其他组,并且也可以向组中的主机指定变量。

(5)多重变量定义
    变量除了可以在Inventory中定义,还以独立于Inventory文件之外单独到存在yaml格式的配置文件中。

9、正则表达式
    在使用ansible命令,指定作用组或者单个主机时可以使用正则表达式
    ansible webservers -m service -a "name=httpd status=restarted" #重启webservers组中所有主机的httpd服务
    ansible all   -m ping   #检查所有主机是否存活
    ansible "*"   -m ping     #all和*号的功能相同,但是*需要用""号引起来
    ansible 192.168.1.*     -m ping      #检查192.168.1.0/24网络的所有主机是否存活
    ansible web1:web2        -m ping      #同时检查web1和web2两个组的所有主机是否存活,并集,同时对多个主机或多个组执行命令,用":"冒号分割
    ansible web1:!web2         -m ping     #表示表示在web1组中但是不在web2中的所有主机执行命令, 差集
    ansible web1:&web2      -m ping     #即在web1组也在web2组中的主机,交集
    ansbile *.magedu.com     -m ping     #对所有以.magedu.com结尾的主机执行命令
    ansible one*.com:webservers -m ping    #对所有以one开头以com结尾的主机,与webservers组取并集
    ansible webservers[0:1] -m ping     #根据下标取组中对应的主机
    ansible webservers[-1]  -m ping     #取组中倒数第一个主机
    ansible webservers[1:]    -m ping     #取组中第2个到到最后一个主机
    ansible "~(beta|web|green)\.example\.(com|org)" -m ping #支持正则表达式,正则表达式以~开头
    ansible "~192\.168\.[0-9]{\2}.[0-9]\2{,}" -m ping         #检测Inventory中所有以192.168开头的服务器是否存活
    
10、ansible命令详解Ad-Hoc命令集
    ansible命令执行的完整流程:
    ansible webservers -s -m command -a "hostname"  -vvv    #以root用户在每台主机上执行hostname命令,返回webservers组中的每台主机的名字,并显示详细的执行过程。
    (1)首先当前主机与远程主机建立SSH链接,
    (2)然后在远程主机的$HOME/.ansible/tmp/目录下建立临时文件夹用来存放远程执行脚本,
    (3)将/tmp/目录下的临时脚本移动到$HOME/.ansible/tmp/ansible-tmp-数字/command Python脚本中,
    (4)切换成root用户,执行python脚本,并返回结果
    (4)然后再删除临时目录$HOME/.ansible/tmp/ansible-tmp-数字 。
    
(2)ansible 10.21.40.61 -B 5 -P 2 -T 2  -m command -a "sleep 20" -u root
    对服务器10.21.40.61以root用户执行sleep 20 ,执行最大连接超时时长为2s,设置为后台模式执行命令,没隔2s输出一次进度,如果5s还没有执行完毕就终止改任务
    ansible命令的其他options可选项
    -B num ,--backgroud=num   后台执行命令,超过num秒任务没有执行完毕就自动终止
    -P num ,--poll=num           定期返回后台任务的进度,每隔num秒返回一次任务进度
    -T sec ,--timeout=sec     指定远程链接最长超时时间
    -u name,--user=name       指定远程主机以name用户执行命令
    -k , --ask-pass SSH       认证密码
    -K , --ask-sudo-pass sudo 用户密码 (--sudo时使用)
    -s , --sudo               切换成root用户执行命令
    -a "arguments", --args "arguments" 执行命令command模块的参数
    -m name , --module-name=name 指定执行使用的模块
    -t directory , -tree=directory 输出信息至directory目录下,结果文件以远程主机的主机名命名
    -f num , --forks=num      指定ansible命令执行的并发线程数,默认为5
    -l subset ,--limit=subset 限定运行命令的主机,只有limit指定的主机才会执行命令
    
(3)ansible web1 -m command -a "df -lh"
    ansible web1 -a "df -lh"    #默认使用command模块,查看web1组中的所有主机的磁盘使用情况
    ansible web1 -m shell -a "free -m"  #使用shell模块批量查看web1组中所有主机内存使用情况
    ansible apps -m yum -a "name=redhat-lsb state=present"  #为apps组中所有主机安装redhat-lsb 用来查看每台主机的系统版本号
    ansible apps -m command -a "lsb-release -a"      
    ansible apps -m yum -a "name=ntp state=present"         #为appls组中所有主机按照ntp服务并设置为开机自启动
    ansible apps -m command -a "name=ntpd state=started enable=yes"
    
11、Ad-Hoc组管理和特点主机变更
    架构规划:前端Proxy 、 Web servers 和后端的数据库DB。
    [proxy]
    192.168.37.159
    
    [app]
    192.168.37.130
    192.168.37.160
    
    [nosql]
    192.168.37.142
    
    [db]
    192.168.37.142
(0)构建简单的web服务架构
    proxy组:安装Nginx服务用来转发用户的各种请求到后端的WebServers响应
    app组:  安装Nginx+PHP+Django服务,用来响应用户的request请求
    nosql组:安装redis服务,用来缓冲查询数据库的压力
    db组:   安装MariaDB服务,查询数据库返回结果
    
(1)首先给proxy组安装Nginx服务,并检查服务是否安装成功
    ansible proxy -m yum -a "name=nginx state=present"  #state=present表示新建 
    ansible proxy -m command -a "nginx -v"
    
(2)然后Web Servers组安庄Nginx、PHP、Django服务
    ansible app -m yum -a "name=nginx state=present"        #安装nginx、php服务
    ansible app -m yum -a "name=php  state=present"
    ansible app -m yum -a "name=MySQL-python state=present" #安装MySql-python 和Python-setuptools依赖包
    ansible app -m yum -a "name=python-setuptools state=present"
    ansible app -m pip -a "name=django start=present"        #使用pip安装django服务,django依赖Python 2.7.0+版本
    ansible app -m command -a "python -c 'import django; print django.get_version()'"  #检查django是否安装成功
    
(3)最后配置后端Nosql和Database服务
    ansible nosql -m yum -a "name=redis state=present"     
    ansible nosql -m command -a "redic-cli --version"
        
    安装MariaDB(继Mysql后又一大流行数据库)    
    添加yum源,修改/etc/yum.repos.d/mariadb.repo添加内容
    [mariadb]
    name=MariaDB
    baseurl=http://yum.mariadb.org/10.1/centos6-x86
    gpgkey=https://yum.mariadb.org/RPM-GPG-KEY-MariaDB
    gpgcheck=1
    
    ansible db -m yum -a "name=MariaDB-Server state=present"    #安装MariaDB-Server服务
    ansible db -m yum -a "name=MariaDB-client state=present"    #安装MariaDB-Client服务
    ansible db -m command -a "iptables -A INPUT -s 192.168.37.0/24 -p tcp -m tcp --dport 3306 -j ACCEPT" #开启防火墙3306端口
    
(4)Ad-Hoc限定主机执行命令
    ansible app -m command -a "service ntpd start " --limit "192.168.37.158"  #只启动app组中192.168.37.158这台服务器的ntpd服务
    ansible 192.168.37.158 -m command -a "service ntpd start" 
    ansible "192.168.37.158:192.168.37.161" -m command -a "service ntpd start"    #指定多台主机执行命令,用冒号分割,需要用引号将所有地址引起来
    ansible 192.168.37.*  -m command -a "service ntpd start"    #指定多台主机变更

12、ansible管理系统用户    
(1)linux用户管理
    批量新增用户;新增用户dba , 使用bash shell, 附加组为admins,dbagroup ,家目录为/home/dba/
    ansible db  -m  user -a "name=dba shell=/bin/bash groups=admins,dbagroup append=yes home=/home/dba/  state=present"
    user模块的属性
    name    用户名
    shell      设置用户shell
    groups     设置用户附加组群,使用逗号分隔多个群组,如果参数为空,即groups="" ,则删除用户所有附加组
    append    当为yes表示增量添加group,即用户附加组群变多了,当为no时全量变更,抛弃原来的组群,只设置为groups属性中的组
    state    为present时新建用户 , 为absent时删除用户
    remove  结合state=absent使用,删除用户相当于userdel --remove
    home    设置用户的家目录
    expires    设置用户过期时间
    password 设置用户密码,后面跟的密码必须是加密过后的密码
    update_pssword  当为always:只有密码不同才会更新密码,当为on_create 只为新用户设置密码
    
(2)修改用户属组,将用户dba的所属组质变为dbagroup,删除admins组权限
    ansible db -m user -a "name=bda groups=dbagroup append=no"
    
(3)修改用户属性,将用户dba的过期时间设置为2016/6/1 18:00:00,UNIXTIME=1464775200
    ansible db -m user -a "name=dba expires=1464775200" 
    
(4)删除用户,将用户dba删除
    ansible db -m user -a "name=dba remove=yes state=absent"

(5)变更用户密码:设置用户tom的密码为redhat123
    ansible db -m user -a "name=tom shell=/bin/bash  password=EKEVWEJRO123 update_pssword=always"
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     
(6)通过使用mysql_user模块为mysql数据库增加用户xiao,初始密码为xiao123
    ansible db -m mysql_user -a "login_host=localhost login_password=root123 login_user=root name=xiao password="xiao123" priv=zabbox.*:ALL state=present"

13、Playbook基础语法
(1)playbook的正式内容:
    注:缩进空格和tab不能混用,k/v的值可以同行写也可以换行写,同行使用":"隔开,换行写需要以"-"分隔,一个name对应一个task
    创建一个名为hello.yml的文件
    ---                            #必须以三个减号作为首行
    - hosts: webservers            #定义第一个play1,并指定要执行命令的远程主机组或者单个主机
      vars:                        #定义了两个变量,后期可以调用
         http_port: 80
         max_client: 200
      remote_user: root            #设置远程主机以root用户执行命令
      tasks:                    #定义一系列接下来要执行的任务,任务列表
        - name: ensure the apache server is the latest version    #任务1:确保apache服务器的本班时最新的
          yum: name=httpd state=latest                            #       使用yum模块执行任务,后面是yum模块的参数        
        - name: write the apache config file                    #任务2:编辑apache服务器的配置文件
          template: src=/srv/httpd.j2 dest=/etc/httpd.conf        #       使用template模块                            
        - name: ensure apache is running                        #任务3:启动apache服务
          service: name=httpd  state=started                    #        使service模块启动httpd服务
          notify: restart apache                                #调用并执行定义好的handler中的task
      
      handlers:                                                #定义一个handlers,且本质也是一个task的列表,可以通过notify和任务名来调用集合中的某个task,notiy的task才会执行,没有notify的task不会执行
        - name: restart apache server 
          service: name=httpd state=restart 
        - name: stop apache server 
          service: name=httpd state=stop 
    - hosts: app                #定义第二个paly2, 针对app主机组,一个playbook可以包含多个play        
      remote_user: root
      tasks:
        - name:"安装apache server"
          command: yum install --quite -y httpd httpd-devel
        - name: "复制文件"
          command:cp /tmp/httpd.conf /etc/httpd/conf/httpd.conf
          command: cp /tmp/httpd-vhosts.conf /etc/httpd/conf/httpd-vhosts.conf
        - name: "启动Apache,并设置为开机自启动"
          command: service httpd start
          command: chkconfig httpd on

执行hello.yml文件:
    ansible-playbook hello.yml
    
(2)playbook循环语句:
    ---
    - hosts: all
      sudo: yes    #远程主机以root用户执行命令
      tasks:
        - name: "安装Apache server"
          yum: name={{item}} state=present
          with_items:   #wtih_items要与模块名yum左对齐
             - httpd
             - httpd-devel
        - name:"复制配置文件"
          copy: src={{item.src}}  dest={{item.dest}} owner=root group=root mode=644
          with_items:                                                            #该命令是将当前主机上的文件远程拷贝到其他机器的指定路径下
            - {src:"/tmp/httpd.conf", dest:"/etc/httpd/conf/httpd.conf"}        #src表示ansible所在本地服务器上的路径, dest为远程主机的路径
            - {src:"/etc/httpd-vhosts.conf", dest:"/etc/httpd/conf/httpd-vhosts.conf"}
        - name: "检查Apache运行状态,并设置开机自启动"
          service: name=httpd state=started enable=yes

(3)ansible-playbook常用的参数 [options]
    --limit          用来限定哪些主机会执行playbook中的命令
    --list-hosts     返回在执行playbook时,哪些主机将会受到影响
    --remote_user   用来执行远程主机以什么用户执行命令
    --ask-sudo-pass 用来传递sudo密码到远程主机,来保证sudo命令可以正常运行,使用--ask-sudo-pass(-K)选项交互式输入sudo密码
    --sudo          可以强制所有play都使用sudo用户执行
    --sudo-user     可以指定sudo可以执行那个用户的权限
    --check         在运行playbook之前,使用该命令--check(-C)来检测playbook都会改变哪些内容,显示的结果跟真正执行时一模一样,但不会真的对被管理的服务器产生实际影响。
    --force-handlers 当playbook中某一个task执行时出现了错误,那么ansible会停止所有任务,而且handlers也不会被触发,如果们需要不管是否出现问题都要触发handlers,那么就可以用该选项来强制触发handlers
    
(4)playbook定义变量,设置Handlers
    在playbook中可以创建一个变量文件vars.yml来存放所有需要的变量。
    不仅变量可以定义在文件中,Handler、Tasks也可以独立定义在文件中.
    ---
    - hosts: all
      vars_files: vars.yml        #通过vars_files关键字来引用文件中的变量
    pre_task和post_task用来指定在主任务运行之前和之后要运行的任务
    例如:在安装其他服务之前,我们需要确保apt缓存始终是最新的,因此我们通过apt模块来更新apt缓存,同时设置有效期为3600s
    pre_tasks:
        - name: update apt cache if needed
          apt: update_cache=yes  cache_valid_time=3600 
            
            
(5)输出打印一行信息:
    ********************************************
    ansible all -m debug -a "msg='hello world'" 
    ansible all -m debug -a msg=hello -u root
    playbook模式
    - name:   打印出环境变量
      debug: msg=" The variable is {{JAVA_HOME}}"
    ********************************************
    
(6)在文件中独立定义变量时,首行时三个减号,变量定义定格写,不需要缩进,
    创建vars.yml 文件用来存放变量
    ---
    name: xiaowei
    age:12
    sex: male
    在playbook中通过vars_files: vars.yml 来引用里面的变量
    创建hello.yml文件
    ---
    - hosts: all
      vars_files: vars.yml
      tasks:
        - name : 打印信息
          debug: msg=" the name is {{name}}, age is {{age}}"
    ansible-playbook  hello.yml

(7)在Inventory文件中定义变量
    Inventory文件默认路径为/etc/ansible/hosts, 可以在主机名的后面或者是组名的下方定义变量,如下:
    [shanghai]           #为某一台主机单独指定变量
    app1.example.com  proxy_state=present
    app2.example.com  proxy_state=present
    
    [shanghai:vars]     #为整个主机组指定变量
    dns_hosts=static.example.com
    version=2.1.0
    
(8)定义变量的另一种方式
    由于ansible在执行命令的时候回默认去/etc/ansible/host_vars/和/etc/ansible/group_vars目录下去读取变量
    因此可以在这两个目录下创建于host主机同名的变量定义文件,或者创建与组同名的变量定义文件
    如果我们需要给主机app1.example.com定义变量文件,那么就可以到/etc/ansible/host_vars/目录下创建一个名为app1.example.com的文件
    在里面以YAML格式定义变量
    如果要给shanghai整个组定义变量文件,那么就可以到/etc/ansible/group_vars/目录下创建一个shanghai的空白文件,
    在里面以YAML格式定义变量:
    ---
    foo: bar
    name: xiaowei 
    
(9)Facts,收集系统信息
    在运行任何一个playbook之前,ansible都会去收集playbook指定的主机的信息,这些信息包括:
    远程主机CPU信息、IP地址、磁盘空间、网络接口、操作系统信息
    这些信息对于运行playbook至关重要,我们可以根据这些信息决定是否要运行playbook,我们也可以将这些信息写入到配置文件中
    ansible localhost -m setup >> setup.txt    #用setup模块获取对应主机上的所有可用的Facts信息
    结果:
    localhost | SUCCESS => {
    "ansible_facts": {
        "ansible_all_ipv4_addresses": [
            "192.168.122.128"
        ], 
        "ansible_all_ipv6_addresses": [
            "fe80::20c:29ff:feff:7eb7"
        ], 
        "ansible_apparmor": {
            "status": "disabled"
        }, 
        "ansible_architecture": "x86_64", 
        "ansible_bios_date": "05/19/2017", 
        "ansible_bios_version": "6.00", 
        "ansible_cmdline": {
            "BOOT_IMAGE": "/vmlinuz-3.10.0-123.el7.x86_64", 
            "LANG": "en_US.UTF-8", 
            "crashkernel": "auto", 
            "quiet": true, 
            "rhgb": true, 
            "ro": true, 
            "root": "UUID=b6943379-8c8a-4dbe-af80-b3f2af2d6fa9", 
            "vconsole.font": "latarcyrheb-sun16", 
            "vconsole.keymap": "us"
        }
        
        常用的Facts变量有: ansible_os_family、ansible_hostname、ansible_memtotal_mb……

14、流程控制if、then、when
(1)flie模块:主要用来
    path参数     :必须参数,用于指定要操作的文件或目录,在之前版本的ansible中,使用dest参数或者name参数指定要操作的文件或目录,为了兼容之前的版本,使用dest或name也可以。
    state参数     :设置path=/testdir/a/b,但是ansible不知道这个路径是代表一个文件还是一个目录,所以要通过state来指定,state=directory(创建目录)、touch(创建文件)、link(创建软连接)、hard(创建硬链接)、absent(删除文件或目录)
    src参数     :当state设置为link或者hard时,表示我们想要创建一个软链或者硬链,所以,我们必须指明软链或硬链链接的哪个文件,通过src参数即可指定链接源。
    force参数     : 当state=link的时候,可配合此参数强制创建链接文件,当force=yes时,表示强制创建链接文件。不过强制创建链接文件分为三种情况。情况一:当要创建的链接文件指向的源文件并不存在时,使用此参数,可以先强制创建出链接文件。情况二:当要创建链接文件的目录中已经存在与链接文件同名的文件时,将force设置为yes,会将同名文件覆盖为链接文件,相当于删除同名文件,创建链接文件。情况三:当要创建链接文件的目录中已经存在与链接文件同名的文件,并且链接文件指向的源文件也不存在,这时会强制替换同名文件为链接文件。
    owner参数     :用于指定被操作文件的属主,属主对应的用户必须在远程主机中存在,否则会报错。
    group参数     :用于指定被操作文件的属组,属组对应的组必须在远程主机中存在,否则会报错。
    mode参数    :用于指定被操作文件的权限,比如,如果想要将文件权限设置为”rw-r-x---“,则可以使用mode=650进行设置,或者使用mode=0650,效果也是相同的。如果想要设置特殊权限,比如为二进制文件设置suid,则可以使用mode=4700。
    recurse参数    :当要操作的文件为目录,将recurse设置为yes,可以递归的修改目录中文件的属性

- name: 创建文件
      file: path=/home/hadoop/words.txt  state=touch owner=hadoop group=hadoop mode=0650
      
(2)when条件判断
    ansible在进行条件判断时会使用到一些Jinja2的语法、以及Python的一些内置函数
    很多任务只有在特定条件下执行,这就需要用到when条件表达式了
    还以通过注册器保存命令运行的结果,并对其进行判断
    ---
    - hosts: all
      tasks:
        - name: 只为数据库服务器安装mysql
          yum:  name=mysql-server state=present
          when: ({{is_db_server}} is defined) and {{is_db_server}}    #只在一个服务器上设置一个is_db_server的布尔值变量,用来表示这是一台数据库服务器
        - name: 当软件主版本号为4才更新软件
          yum: name=redis state=present
          when: {{redis_version}}.split(".")[0]=='4'
        - name: 查看一个应用的运行状态,
          command: appname --state
          register: appstate_result                 #定义一个注册变量,将该task的任务执行的结果放到这个注册变量appstate_result中
        - name: 根据上app软件运行的状态,决定是否要执行本task
          command: do something else as you like
          when: "ready" in appstate_result.stdout  #只有当上一个task的执行结果中包含有ready时才会执行当前命令
        - name: 如果当前PHP的版本号为7.0,就执行PHP降级任务
          shell: php --version
          register: php_version_result
        - name: PHP降级
          shell: yum -y downgrade php*
          when: '7.0' in php_version_result.stdout
        - name: 如果远程主机中没有host文件,就远程拷贝一个过去
          stat: path=/etc/hosts
          register: host_file_result
        - name: 拷贝host文件
          copy: src=/path/to/local/hosts_file  dest=/path/to/remote/hosts_file
          when: host_file_result.stat.exists =- false
          
(3)changed_when 、failed_when条件判断
    #使用PHP composer来安装项目依赖,无论是否安装或升级的某些软件,ansible任务返回的结果都会是changed,表示主机已经改变。
    #所以我们需要通过changed_when语句来设置,只有当软件被安装成功了或升级成功了,任务才会返回changed
    ---
    - hosts: all
      tasks:
        - name: isntasll dependencies via composer         
          cammand: /user/local/bin/composer global require phpunit/phpunit --prefer-dist
          register: composer_result
          changed_when: "Nothing to install or update" not in composer_result.stdout    #只有当满足这个条件时,才通知Ansible显示主机Changed
        - name: 通过CLI导入Jenkins任务
          shell: java -jar /opt/jenkins-cli.jar  -s htttp://localhost:8080/create-job "my job"
          register: import_result
          failed_when:  import_result and "already exsits" not in import_result            #只有当满足这个条件时,才通知Ansible显示任务执行失败
        - name: 忽略错误
          command: do something as will
          ignore_errors: true        #不管这个任务是否会报错,都算它执行成功
          
(4)delegate_to 任务委托
    在执行任务的时候,如果对于某一个task,我们只想它在某一台服务器上运行,而不是所有的服务器都运行,这时候就需要用到delegate_to了
    ---
    - hosts: webservers
      tasks:
        - name: remove server form load balancer
          command: remove-from-lb
          delegate_to: 127.0.0.1                 #只在本地主机上执行这个task,其他主机上都不执行
          
        - name: remove server form load balancer
          local_action: command remove-from-lb     # local_action 与 delegate_to等价
          
(5) wait_for 任务暂停
    ---
    - hosts: all
      task:
        - name: wait for webserver to start  #等待web1服务器的80端口打开后,才执行本task
          local_action:
            module: wait_for
            host: web1
            port: 80
            delay: 10
            timeout: 300
            state: started
    该任务会每个10s检查一下web1服务器上的80端口是否开启,如果超过300s还没有开启就返回失败信息
    
(6)tags标签
    可以给某一个task、某一个role、某一个play、或者整个playbook都打上标签,然后再执行的时候,使用--tags选项来指定执行哪些task,用--skip-tags来指定不执行哪些tasks
    ansible-playbook hello.yml --tags "helloworld" 
    ansible-playbook hello.yml --skip-tags "helloworld" 
    案例:
    ---
    - hosts: all
      tags: hello
      roles:
        - role: tomcat
        - tags: [tomcat , app]        #第一种添加tags的方式,用一个列表将所有tags包含在里面
      tasks:
        - name: notif on  completion
          local_action:
            module: osx_say
            msg: hi,nihao
            voice: zarvox
          tags:                        #第二种添加tags的方式,换行用"-"分隔tags
            - notification
            - say

(7)block块
    block块将一系列的task形成一个整体,可以对这个整体执行异常处理语句
    ---
    - hosts: all
      tasks:
        # install and configure apache on redhat/centos hosts
        - block:        #把三个task合并成一个整体,如果操作系统是redhat,就执行这些task,而不用逐个判断
            - yum: name=httpd state=present
            - template: src=httpd.conf.j2 dest=/etc/httpd/conf/httpd.conf
            - service: name=httpd state=started enable=yes
          when: {{ansible_os_family}} == "Redhat"
          sudo: yes
          
        # install and configure apache on debian/ubuntu hosts
        - block:
            - apt: name=apache2 state=present
            - template: src=htttpd.conf.j2 dest=/etc/apache2/apache.conf
            - service: name=apache2 state=started  enable=yes
          when: {{ansible_os_family}} == "Debian"
          sudo: yes 
          
    block块中异常处理:
      tasks:
        - block:
            - name: shell script to connect the app to a monitoring service
              script: monitoring-connect.sh
              rescue:    
                - name: 只有脚本运行出错时,才执行rescue中的语句
                  debug: msg="there was a error in this block"
              always:
                - name: 无论脚本执行结果如何,都要执行always中的语句
                  debug: msg="this always executes"
    #当块中的任意代码出了问题就会执行rescue中的语句,相当于java中的try catch语句,而always相当于finally语句            
            
15、Playbook的高级技巧使用
(1)copy模块的使用:
    copy模块实现复制本地文件到远程主机,copy模块包含如下选项:
    backup:    在覆盖之前将原文件备份,备份文件包含时间信息。有两个选项:yes|no 
    content:    用于替代"src",可以直接设定指定文件的值 
    dest:        必选项。要将源文件复制到的远程主机的绝对路径,如果源文件是一个目录,那么该路径也必须是个目录 
    directory_mode:递归的设定目录的权限,默认为系统默认权限
    force:        如果目标主机包含该文件,但内容不同,如果设置为yes,则强制覆盖,如果为no,则只有当目标主机的目标位置不存在该文件时,才复制。默认为yes
    others:    所有的file模块里的选项都可以在这里使用
    src:        要复制到远程主机的文件在本地的地址,可以是绝对路径,也可以是相对路径。如果路径是一个目录,它将递归复制。在这种情况下,如果路径使用"/"来结尾,则只复制目录里的内容,如果没有使用"/"来结尾,则包含目录在内的整个内容全部复制,类似于rsync。         
    ansible web1 -m copy -a "src=/etc/ansible/script.sh dest=/tmp/ owner=appuser group=appuser mode=0755"     
    ###复制本地脚本到远程主机server6下并定义用户和组以及权限755 
    
(2)include用法:
    创建一个 install_MysqlAndPhp.yml文件 ,用来存放公共执行模块
    install_MysqlAndPhp.yml:
    ---                              # 这个yml文件可以看做是一个task任务列表,专门用来安装msyql和php
    - yum: name=mysql state=present
    - yum: name=php-fpm state=present
    
    再创建一个install_lamp.yml文件,通过include语句来调用install_MysqlAndPhp.yml文件中的内容
    ---
    - host: all
      remote_user: root
      gather_facts:    no
      tasks:                                # 在tasks关键字中使用include,
        - include: install_MysqlAndPhp.yml    # include语句可以看做是一个task,所以与任务install_httpd左对齐
        
        - name: install_httpd
          yum: name=httpd state=present
        
    在handlers关键字中使用include
    创建test_include.yml文件
    ---
    - hosts: all
      remote_user: root
      gather_facts: no
      tasks:
        - name: create_file
          file: path=/opt/tmp  state=touch 
          notify: test_include_module    #handlers中的任务,要被tasks中的任务调用,所以notify语句要与file模块左对齐,由create_file这个task去notify在handlers中的test_include_moudle这个任务
          
      handlers:        # handlers 也可以看做是一种任务列表,所以与tasks左对齐
        - name: test_include_module
          include: include.yml            #在handlers关键字中调用include语句
          
    创建include.yml
    ---
    - debug: msg="hello world"
    - debug: msg="hello world2"
    - debug: msg="hello world3"
        
(3)Roles角色:    
    roles的默认目录可以在/etc/ansible/ansible.cfg配置文件中找到
    roles_path = /etc/ansible/roles/
    roles目录下用来存放各个角色,每一个角色对应个子文件夹,
    而每个角色文件夹中又包含:files、templates、tasks、handlers、vars、defaults、meta    (7个子文件夹)
    files/         :存放由copy或script模块等调用的文件;
    templates/    :template模块查找所需要模板文件的目录;
    tasks/        :至少应该包含一个名为main.yml的文件;其它的文件需要在此文件中通过include进行包含,所有包含在其中的任务将会被执行;
    handlers/    :至少应该包含一个名为main.yml的文件;其它的文件需要在此文件中通过include进行包含,所有包含在其中的handlers将会被执行;
    vars/        :至少应该包含一个名为main.yml的文件;其它的文件需要在此文件中通过include进行包含,所有包含在其中的变量将在roles中生效;
    meta/        :至少应该包含一个名为main.yml的文件,定义当前角色的特殊设定及其依赖关系;其它的文件需要在此文件中通过include进行包含;注意,角色和角色之间有依赖关系,如安装NT,先装nginx后装tomcat,一般不需定义,执行我们自己定义好安装顺序即可
    default/    :设定默认变量时使用此目录中的main.yml文件;
        
(4)案例:目录结构如下:
    myfile.yml
    myapache.yml
    roles        
        |---- apache
        |        |---- handlers
        |        |        |---- main.yml
        |        |---- tasks
        |                |---- main.yml
        |                |---- restart.yml
        |---- example
                |---- files
                |        |---- Magedu.ppt
                |        |---- Stanley.ppt
                |
                |---- tasks
                        |---- main.yml
                        |---- file.yml
    在roles目录下有两个子目录:apache和example分别对于两个role
    案例一:更新webservers组中的httpd服务的配置文件,然后重启服务
    1)编辑/roles/apache/handlers/main.yml:
    ---
    - name: restart_apache
      service: name=apache state=start
      
    2)编辑/roles/apache/tasks/restart.yml
    ---
    - name: transfer apache config file
      file: src=httpd.conf dest=/opt/apache/httpd.conf  #更新httpd服务的配置文件,然后再重启httpd服务
      notify: restart_apache    #调用handlers中写好的重启apache httpd服务的任务
     
    3)编辑/roles/apache/tasks/main.yml
    ---
    - include: restart.yml
    
    4)编辑与roles目录统计的myapahce.yml
    ---
    - hosts: webservers
      remote_user: root
      roles:
        - role: apache             #所有task、handlers全部都被分解到roles下各个目录的文件中
        
    5)执行apache.yml文件
    ansible-playbook  myapahce.yml
    
    案例二:files文件传输
    1)编辑与roles目录同级的myfile.yml文件
    ---
    - hosts: 192.168.122.128
      remote_user: root
      gather_facts: no
      roles:
        - role: example
    
    2)编辑roles/example/task/file.yml
    ---
    - name:  file change example
      copy: path={{item.src}} dest={{item.dest}} owner=hadoop group=hadoop 
      with_items:
        - src:Magedu.ppt            #由于Magedu.ppt和Stanley.ppt这两个文件存放在roles/files目录,因此传输时只需要指定相对files目录的路径既可,规范用户了存放文件的位置。
          dest:/opt/tmp/magedu.ppt
          
        - src:Stanley.ppt
          dest:/opt/tmp/Stanley.ppt
          
    3)编辑roles/example/task/main.yml
    ---
    - include file.yml
    
    4)执行与roles同级file.yml
    ansible-playbook myfile.yml    #注:这个被执行myfile.yml文件的名字是什么,位置在哪里可以任意指定

Ansible 学习笔记(一)相关推荐

  1. Linux红帽认证工程师(RHCE)考试笔记(Ansible学习笔记)

    写在前面: 笔记是因为考红帽所以整理的,大都是老师的笔记,主要是常用模块整理,后面有些类似考试的实战题目,不是教程,教程建议大家到下面的学习网站,这篇博客适合温习用,层次有些乱,嘻嘻,生活加油,天天开 ...

  2. ansible学习笔记

    ansible是基于模块化的,通过调用特定的模块,完成特定的任务 基于Python语言实现,由Paramiko.PyYAML和Jinja2三个关键模块实现 部署简单,agentless(无需部署客户端 ...

  3. ansible 学习笔记

    一.基础知识: 1. 简介 ansible基于python开发,集合了众多运维工具的优点,实现了批量系统配置.批量程序部署.批量运行命令等功能.ansible是基于模块工作的,本身没有批量部署的能力. ...

  4. Ansible学习笔记——vault加密

    这里写自定义目录标题 语法及常用操作 使用加密文件中的变量来创建用户 语法及常用操作 1. 创建文件:需要输入文件的密码 [student@workstation ~]$ ansible-vault ...

  5. ansible2.7学习笔记系列

    写在前面:ansible的资料网上很多,本人也是参考网上资料,做总结,如有错误,麻烦指出,谢谢. 所谓学习笔记,就是不断成长的过程,也许一段时间后有更深入理解了,就会继续更新笔记. 笔记定位:目前写的 ...

  6. CCNP学习笔记(6)

    一.交换机 1.二层交换 特性: ①基于MAC地址转发数据帧 ②硬件工作 ③处理数据效率高,数据传输延时低 ④转发广播 2.三层交换 特性: ①提供路由功能 ②提高安全性 ③流量管理 3.网络方案中交 ...

  7. Docker学习笔记 之 Docker安装配置使用

    简介 Docker是一个开源的引擎,可以轻松的为任何应用创建一个轻量级的.可移植的.自给自足的容器.开发者在笔记本上编译测试通过的容器可以批量地在生产环境中部署,包括VMs(虚拟机).bare met ...

  8. Linux入门怎么学?262页linux学习笔记,零基础也能轻松入门

    #种一棵树最好的时间是十年前,其次是现在 很多程序员一开始在学习上找不到方向,但我想在渡过了一段时间的新手期之后这类问题大多都会变得不再那么明显,工作的方向也会逐渐变得清晰起来. 但是没过多久,能了解 ...

  9. Reliable Cloud Infrastructure: Design and Process学习笔记

    最后更新2022/03/16 忘记更新对应的学习笔记,补上.这一科有9节,加上0章简介 简介 google cloud的好多功能有点相似,这科内容是介绍应该选什么产品,怎么选择,怎么规划,怎么设计等等 ...

最新文章

  1. 2022-2028年中国锅仔片行业研究及前瞻分析报告
  2. 浅谈Redis与MySQL的耦合性以及利用管道完成MySQL到Redis的高效迁移
  3. 分别使用 XHR、jQuery 和 Fetch 实现 AJAX
  4. Ubuntu下如何正确安装FFmpeg
  5. 闰秒对数据库和linux的影响
  6. Chrome Cookie SameSite 属性设置
  7. datax oracle mysql_从 MySQL 到 Lindorm时序引擎 的数据迁移
  8. 2018年9月5日第一贴
  9. 在华为云ECS上手工通过Docker部署tomcat
  10. 新一批国产游戏版号下发:共53款 腾讯、网易在列
  11. java socket 缓冲_关于socket的发送缓冲区网上有诸多的讨论,这里个人小结一下,希望对以后有些帮助。首先,看下面一段代码,...
  12. javascript中的错误处理机制
  13. php框架 路由_PHP框架开发之Route路由简单实现
  14. jquery-pager的使用
  15. LINUX下载编译libreadline
  16. 各主板黑苹果dsdt补丁_台式机微星(MSI)主板黑苹果EFI引导文件分享amp;2020.12.3
  17. 非华为电脑多屏协同_升级版多屏协同,实现多窗口,华为电脑管家11.0版
  18. Kotlin-Android世界的一股清流
  19. 腾讯版天眼查3年VIP免费领取!下手要快
  20. 金钱数字转换为大写中文

热门文章

  1. 数据结构和算法_零基础入门01
  2. IrfanView - 图片浏览、编辑、批处理神器
  3. vscode写php高亮,vscode如何设置代码高亮_编程开发工具
  4. “时间的朋友“跨年演讲对技术人的一点启发
  5. oracle第3名到第6名,ORACLE的rownum用法讲解
  6. 记一次简单的公众号分析
  7. 【go.js 常用api管理】
  8. tryParse的用法。
  9. 全球及中国高端功率MOSFET行业市场调查及投资价值预测报告2022-2028年
  10. Ubuntu下端口被占用问题