• ansible 基础


    1 ansible 入门

    1.1 ansible 是什么

    网上各种介绍都有, 由来的,这里不多写了。 
    ansible 是一款运维自动化工具,其主要功能是帮运维实现 IT 工作的自动化、降低人为操作事务、提高业务自动化率、提升运维工作效率,常用于软件部署自动化,配置自动化,管理自动化等等一些功能

    1.2 ansible 主要特点

    • ansible 是非C/S 架构,自身没有client端,只需要安装SSH,python即可。
    • 基于OpenSSH 通信,底层基于 SSH 协议(Windows基于PowerShell)
    • 支持密码和 SSH 认证,可以通过系统账户密码认证或公私钥认证,所以整个过程简单、方便、安全。建议使用公私钥方式认证,因为密码认证方式的密码需要明文写配置文件
    • 支持windows,但windows必须是客户端,服务端必须是Linux 系统。

    2 环境准备

    2.1 环境规划

    主机名 IP 系统版本 软件版本 用途
    ansible-150 10.0.0.150 Centos 7.6 ansible 批量管理机器
    mysql-151 10.0.0.151 Centos 7.6 xxx 被管理机器
    mysql-152 10.0.0.152 Centos 7.6 xxx 被管理机器

    注:关闭了selinux 和 防火墙,配置好了yum和epel源

    2.2 ansible 安装

    #官方文档里面各种安装方式
    https://docs.ansible.com/
    

    安装方式有很多,我这里用的yum安装 

    安装

    [root@ansible-150 ~]# yum -y install ansible
    [root@ansible-150 ~]# ansible --version
    ansible 2.8.2
    

    安装完了, 是不是该研究如何使用ansible了。但是 ansible 是基于ssh 通信的,需要批量管理服务器,是不是需要做用户密码认证或者秘钥对验证。

    2.3 为新系统添加安全认证

    安全认证分为两种: 
    第一种是:ansible 本身支持密码认证,但是密码是明文配置在Inventory 中。考虑到安全性问题,不推荐使用。 
    第二种是:SSHKey 认证(秘钥对验证),推荐使用。安全性相对明文来说,比较高。

    2.3.1 SSHKey 认证

    从安全性考虑角度,我们是该对root 用户做密钥对,还是普通用户。 
    在公司的时候很多情况下不会给你root 用户权限。我帮别人解决过一个问题,别人家公司的服务器规模小,没有专门维护人员,开发担任服务器管理操作,对用户权限和安全这块可能不怎么懂。他们的项目目录、软件目录都是给的777权限,为了开发方便。不久以后就中了挖矿病毒。 

    1. 建立管理用户 

    出于安全的考虑还是用普通用户做密钥对 
    对所有机器建立一个统一的管理用户就叫ansible 用户

    #对150 ,151,152 建立管理用户,用户名叫ansible 。先不要给什么权限,就是一个普通用户
    useradd ansible
    #所有机器设置这个用户密码为123456。我这是为了方便随意设置,实际要满足密码复杂度
    echo 123456 | passwd  --stdin ansible
    
    所有机器把ansible用户加入到wheel组,管理员组
    usermod -aG  wheel  ansible
    
    所有机器运行visudo,所有机器去掉
    shell> visudo
    #把这一行内容的内容#注释去掉 %wheel  ALL=(ALL)       NOPASSWD: ALL
    %wheel  ALL=(ALL)       NOPASSWD: ALL
    允许wheel用户组中的用户在不输入该用户的密码的情况下使用所有命令    

    ansible 用户就是管理用户了

    2. 生成密钥对

    #在ansible-150上操作
    [root@ansible-150 ~]# su - ansible
    [ansible@ansible-150 ~]$ ssh-keygen -t rsa
    

    [ansible@ansible-150 ~]$ cd .ssh/
    [ansible@ansible-150 .ssh]$ pwd
    /home/ansible/.ssh
    [ansible@ansible-150 .ssh]$ ll
    total 8
    -rw------- 1 ansible ansible 1679 Aug  8 14:31 id_rsa
    -rw-r--r-- 1 ansible ansible  401 Aug  8 14:31 id_rsa.pub
    

    密钥对可以比作钥匙和锁 
    id_rsa 是密钥 密钥相当于是锁 
    id_rsa.pub 是公钥 公钥相当于是钥匙,我们需要把钥匙给别人

    3. 分发公钥

    [ansible@ansible-150 .ssh]$ ssh-copy-id ansible@10.0.0.151
    [ansible@ansible-150 .ssh]$ ssh-copy-id ansible@10.0.0.152
    

    4. 验证

    [ansible@ansible-150 .ssh]$ ssh ansible@10.0.0.151
    [ansible@ansible-150 .ssh]$ ssh ansible@10.0.0.152
    #都可以实现免密码登陆
    

    .ssh 文件夹必须是700 ,.ssh 文件夹下面的文件权限必须是600

    2.4 如果机器很多,怎么做比较快

    这时候分两种情况, 
    第一种:机器已近使用了,这时候就需要自己写脚本,做秘钥分发了 
    第二种:机器还未使用,做批量装机的时候,不是可以安装完执行什么命令或者操作

    #ADD USER
    useradd sa -G wheel
    mkdir /home/sa/.ssh/
    cat /home/sa/.ssh/authorized_keys << EOF
    ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDTrrQuMnd2lxyBYISpHVeV92Y5mE+ez5f2qlmjCm4iNUf0DSFmyN1keY4Egvl6w1BI77gJiVR397c+oBgoq3dB2/uL3Ymic9u1kLx3SFFeWbB15cjAMOAW6msO0f+pSinK4fVzXIrifWAiFCQSRRbpLIGc/zo404h0MscpkdjpT7A+p1FUXEszNsjvJKAPu6VYqqmR2C7PyileTpfNRuCGRSZwLp0stURZ51NQc7FxgFmimt6Q40UrCzl2qzOusZYsur6NGl3gxvs0D+FWpnIR2fteDbr9fnnfHCupw0KJ53r/Oj76tLvCuO5ODpe3HLji8jUolvoKVEiXRUnY6W31 ansible@ansible-150
    EOF
    chmod 600 /home/sa/.ssh/*
    chown sa.sa -R /home/sa
    sed -i '108s/#//' /etc/sudoers
    # 最后一个sed 是去掉108行的注释,是去掉%wheel  ALL=(ALL)       NOPASSWD: ALL这个注释
    

    机器初始化的时候一起执行了

    可以无密码通信了,这时候就研究ansible 如何使用了

    3 ansible 目录结构

    用命令查看 ansible 所有文件存放的目录;

    [ansible@ansible-150 ~]$ rpm -ql ansible
    ...
    

    可以分为以下几类目录:

    • 配置文件目录 /etc/ansible

    • 执行文件目录 /usr/bin

    • Lib 库依赖目录/usr/lib/python2.7/site-packages/ansible/

    如下目录需要配置,需熟练掌握 

    1. 配置文件目录/etc/ansible,所有ansible 的配置均存放在该目录下,运维日常所有配置类操作也均基于此目录进行。

    [root@ansible-150 ansible]# tree
    .
    ├── ansible.cfg   #工具功能配置
    ├── hosts  # inventory 主机信息配置
    └── roles  # 角色
    1 directory, 2 files
    [root@ansible-150 ansible]# pwd
    /etc/ansible
    

    2. 执行文件目录/usr/bin,主要功能为:ansible系列命令默认存放目录。ansible所有的可执行文件均存放在该目录下。

    [root@ansible-150 bin]# cd /usr/bin/
    [root@ansible-150 bin]# ll ansible*
    

    3.1 配置文件解析

    nventory 用于定义ansible 的主机列表配置,ansible 的自身配置文件只有一个,即ansible.cfg,ansible 安装好后它默认存放于/etc/ansible/目录下。ansible.cfg配置文件可以存在于多个地方,ansible读取配置文件的顺序是当前命令执行的目录——>用户家目录下的.ansible.cfg——>/etc/ansible.cfg,先找到哪个就使用哪个配置。 
    配置文件ansible.cfg,大多数为注释行默认配置项。很多默认配置即可 

    常用的配置文件解释

    [defaults]
    #inventory=/etc/ansible/hosts                   #被控端的主机列表文件
    #library=/usr/share/my_modules/                 #库文件存放目录
    #remote_tmp=~/.ansible/tmp                      #临时文件远程主机存放目录
    #local_tmp=~/.ansible/tmp                       #临时文件本地存放目录
    #forks = 5                                      #默认开启的并发数
    #poll_interval=15                               #默认轮询时间间隔(单位秒)
    #sudo_user=root                                 #默认sudo用户
    #ask_sudo_pass=True                             #是否需要sudo密码
    #ask_pass=True                                  #是否需要密码
    #transport=smart                                #传输方式
    #remote_port=22                                 #默认远程主机的端口号
    #建议开启修改以下两个配置参数(取消掉注释即可)
    #host_key_checking = False                       #首次连接是否需要检查key认#证,建议设为False,不要认证
    #log_path=/var/log/ansible.log                   #开启ansible日志
    #module_name = command                           #默认执行模块,可以换成shell模块
    [privilege_escalation]
    #become=True                    #是否sudo
    #become_method=sudo             #sudo方式
    #become_user=root               #sudo 后变为root用户
    #become_ask_pass=False          #sudo 后是否验证密码
    

    我实验环境的ansible.cfg

    [root@ansible-150 ~]# egrep -v '^#|^$' /etc/ansible/ansible.cfg 
    [defaults]
    host_key_checking = False
    log_path = /var/log/ansible.log
    [inventory]
    [privilege_escalation]
    become=True
    become_method=sudo
    become_user=root
    [paramiko_connection]
    [ssh_connection]
    [persistent_connection]
    [accelerate]
    [selinux]
    [colors]
    [diff]
    # 记得把/var/log/ansible.log 的权限给ansible
    [root@ansible-150 ~]# chown ansible.ansible /var/log/ansible.log 
    # 按需修改,不要瞎改,不知道去看看官方文档
    

    3.2 Inventory配置文件及详解

    Inventory 是Ansible 管理主机信息的配置文件,相当于系统HOSTS文件的功能,默认存放在/etc/ansible/hosts。为方便批量管理主机,便捷实用其中的主机分组,ansible通过inventory 来定义其主机和组,在使用时通过 -i 指定读取 

    例:

    ansible -i /etc/ansible/hosts dbsrvs -m ping
    

    如果只有一个Inventory 是可不用指定路径,默认读取/etc/ansible/hosts

    3.3 定义主机和组

    Inventory 配置文件遵循 INI 文件风格,中括号中的字符为组名。其支持将同一个主机同时归并到多个不同的组中,分组的功能为 IT 人员维护主机提供了非常大的便利。此外,若目标主机使用了非默认的 SSH 端口,还可以在主机名称之后使用冒号加端口号来标明,以行为单位分隔配置

    /etc/ansible/hosts
    # "#" 开头表示注释行,不生效
    # Inventory 可以直接为IP 地址
    10.0.0.151
    # Inventory 同样支持主机名(hostname)的方式,后跟冒号加数字表示端口号,默认22号端口
    mysql-151:5636
    mysql-151
    # 中括号的内容表示一个分组的开始,紧随其后的主机均属于改组成员,mysql-151 这这台主机属于[dbsrvs]组
    [dbsrvs]
    mysql-151
    mysql-[151:156]   #[151:156] 表示151~156之间的所有数字,即表示mysql-151,mysql-152,mysql-153,.....,mysql-156的所有主机
    mysql-[b:d]       # [b:d] 同理表示b到d之间的所有字母
    

    3.4 定义主机变量

    在日常工作中,通常会遇到非标准化的需求配置,考虑到安全性问题,管理人员有时候可能把Web 服务的80 端口,修改为其他端口号, 而该功能可以直接通过修改Inventory 配置来实现,在定义主机时为其添加主机变量  

    [atlanta]
    host2 http_port=303 maxRequestsPerChild=909  
    # host2 这台主机中,设置了http_port和maxRequestsPerChild 这两个变量
    

    3.5 定义组变量

    可以定义属于整个组的变量

    [atlanta]
    host1
    host2
    
    [atlanta:vars]
    ntp_server=ntp.atlanta.example.com
    proxy=proxy.atlanta.example.com
    
    #[atlanta] 这个是组名,[altanta:vars] 表示要为这个组定义变量,这个组有哪些变量了:ntp_server和proxy
    

    3.6 常用Inventory 参数列表

    Ansible 基于SSH 连接Inventory 中指定的远程主机时,还内置了很多其他参数,用于指定其交互方式

    ansible_ssh_host
          将要连接的远程主机名.与你想要设定的主机的别名不同的话,可通过此变量设置.
    ansible_ssh_port
          ssh端口号.如果不是默认的端口号,通过此变量设置.
    ansible_ssh_user
          默认的 ssh 用户名
    ansible_ssh_pass
          ssh 密码(这种方式并不安全,我们强烈建议使用 --ask-pass 或 SSH 密钥)
    ansible_sudo_pass
          sudo 密码(这种方式并不安全,我们强烈建议使用 --ask-sudo-pass)
    ansible_connection
          与主机的连接类型.比如:local, ssh 或者 paramiko. Ansible 1.2 以前默认使用 paramiko.1.2 以后默认使用 'smart','smart' 方式会根据是否支持 ControlPersist, 来判断'ssh' 方式是否可行.
    ansible_ssh_private_key_file
          ssh 使用的私钥文件.适用于有多个密钥,而你不想使用 SSH 代理的情况.
    ansible_shell_type
          目标系统的shell类型.默认情况下,命令的执行使用 'sh' 语法,可设置为 'csh' 或 'fish'.
    ansible_python_interpreter
          目标主机的 python 路径.适用于的情况: 系统中有多个 Python, 或者命令路径不是"/usr/bin/python",比如  *BSD, 或者 /usr/bin/python
          不是 2.X 版本的 Python.我们不使用 "/usr/bin/env" 机制,因为这要求远程用户的路径设置正确,且要求 "python" 可执行程序名不可为 python以外的名字(实际有可能名为python27).
          与 ansible_python_interpreter 的工作方式相同,可设定如 ruby 或 perl 的路径....
    

    3.7 一份清单文件列子

    一般常用主机清单的例子如下

    /etc/ansible/hosts
    [groupname]
    some_host         ansible_ssh_port=2222     ansible_ssh_user=manager
    aws_host          ansible_ssh_private_key_file=/home/example/.ssh/aws.pem
    freebsd_host      ansible_python_interpreter=/usr/local/bin/python
    ruby_module_host  ansible_ruby_interpreter=/usr/bin/ruby.1.9.3
    
    # [组名]
    主机名或者IP       参数
    

    注:上面很多知识没有, 我只写了常用了,不知道的去看官方文档

    https://docs.ansible.com/ansible/latest/user_guide/intro_inventory.html#inventory-basics-hosts-and-groups
    

    4 ansible 系列命令用法详解与使用场景

    ansible 有哪些相关命令了  

    • ansible
    • ansible-galaxy
    • ansible-pull
    • ansible-doc
    • ansible-playbook
    • ansible-vault
    • ansible-console

     这些相关命令,最常用的还是ansible,ansible-playbook

     上面很多命令我很少用到, 这里就不全部写了,要用去官方文档查一查

    4.1 ansible

    ansible 是远程管理命令

    ansible 语法如下

    [root@ansible-150 ~]# ansible --help
    Usage: ansible <host-pattern> [options]
    ansible    主机表达式            选项参数
    主机表达式可以是Inventory 里面的主机和IP 或者一些表达式来简易表示主机
    选项参数比较多,这时候就需要经常看help 和 该选项的所表达意思
    

    常用参数 

    -m      相应名称的模块被执行,(默认模块为command)
    -a      模块参数信息,-a后面是要执行的命令
    -C      不做任何该变;只是做预测可能发生的变化
    -syntax-checks  行语法检查在剧本上,但是并不执行剧本相当于debug
    

     

    4.1.2 ansible 命令执行结果色彩说明

    绿色:表示没有发生任何改变 
    红色:执行命令操作出现异常 
    黄色:执行命令后,对受控主机产生影响,发生了配置改变

    4.1.3 ansible 使用例子

    先看看我的主机配置文件内容

    [root@ansible-150 ~]# egrep -v "^$|^#" /etc/ansible/hosts 
    [dbsrvs]
    10.0.0.151 ansible_ssh_user=ansible
    10.0.0.152 ansible_ssh_user=ansible
    

    测试连通性

    [ansible@ansible-150 ~]$ ansible all -m ping 
    10.0.0.151 | SUCCESS => {
        "ansible_facts": {
            "discovered_interpreter_python": "/usr/bin/python"
        }, 
        "changed": false, 
        "ping": "pong"
    }
    10.0.0.152 | SUCCESS => {
        "ansible_facts": {
            "discovered_interpreter_python": "/usr/bin/python"
        }, 
        "changed": false, 
        "ping": "pong"
    }
    

     在被控制机器创建一个目录

    [ansible@ansible-150 ~]$ ansible  all -m command -a 'sudo mkdir /opt/xixi'
     [WARNING]: Consider using 'become', 'become_method', and 'become_user' rather than running sudo
    10.0.0.151 | CHANGED | rc=0 >>
    10.0.0.152 | CHANGED | rc=0 >>
    #验证结果
    [ansible@ansible-150 ~]$ ansible  all -m command -a 'ls /opt'
    10.0.0.151 | CHANGED | rc=0 >>
    rh
    xixi
    
    10.0.0.152 | CHANGED | rc=0 >>
    rh
    xixi
    

    4.2 ansible-doc

    ansible-doc 是Ansible 模块文档说明,针对每个模块都有详细的用法说明及应用案例介绍,功能和Linux 系统man 命令类似。该命令使用方式如下:

     

    ansible-doc [options]  [plugin]
    
    plugin 就是模块
    

    ansible-doc 命令跟[options] 参数或 [模块名] ,显示模块用法说明,具体示例如下:  

    #列出支持的模块
    ansible-doc -l
    
    #模块功能说明
    ansible-doc ping
    

    4.3 ansible-playbook

    ansible-playbook 是日常应用中使用频率最高的命令,其工作机制是:通过读取预先编写好的playbook文件实现批量管理。要实现的功能与命令ansible 一样,可以理解为按一定条件组成的ansible 任务集 
    ansible-playbook 命令后跟YML格式的playbook文件,执行事先编排好的任务集

    Playbook 具有编写简单、可定制性高、灵活方便,以及可固化日常所有操作的特点,应熟练掌握

    4.4 ansible-galaxy

    ansible-galaxy的功能可以简单地理解为gitub的功能,通过ansible-galaxy命令,可以根据下载量和关注量等信息,查找和安装优秀的Roles。roles集合其实就是多个playbook文件的集合。 
    Ansible Galaxy是Ansible的官方社区中心,用于共享Ansible角色。一个角色是Ansible构建自动化内容的方式以及让它可复用。角色一般用于基于主机构建服务的场景中,但也可以是用于构建守护进程等场景中。Ansible Galaxy指的是一个网站共享和下载 Ansible 角色,也可以是帮助 roles 更好的工作的命令行工具。

    https://galaxy.ansible.com/
    

    4.5 ansible-inventory

    查看被控制端主机清单的详细信息默认情况下它使用库存脚本,返回JSON格式

    语法:ansible-inventory [options] [host|group]
    参数:ansible-inventory --help 查看
    ansible-inventory --list
    

      

    5 常用模块

    这里只从运维管理角度介绍几个常用的模块 

    5.1 ping 模块

    用途:尝试连接被控制端主机,成功返回pong(ping–pong是一对的)

    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s ping
    

    示例:  

    [ansible@ansible-150 ~]$ ansible all -m ping
    

     参数 all 代表被控制端的所有主机

    5.2 command 模块

    用途:默认ansible使⽤的模块是command,即可以执⾏⼀些shell命令 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s command
    - name: Executes a command on a remote node
      command:
          argv:                  # 允许用户以列表和字符串的形式提供命令,不能同时使用,也不必须提供其中一种
          chdir:                 # 在执行命令之前,先cd到指定的目录下
          creates:               # 用于判断命令是否要执行,如果指定的文件存在(可以使用通配符),则不执行
          free_form:             # 默认的选项,这里只是显示,实际上是没有的
          removes:               # 用于判断命令是否要执行,如果指定的文件存在(可以使用通配符)则执行,不存在,则不执行
          stdin:                 # 将命令的stdin直接设置为指定值
          warn:                  # 设置command的警告信息(在/etc/ansible/ansible.cfg中有配置项)
    

    示例:

    #不加参数执行shell
    [ansible@ansible-150 ~]$ ansible all -a 'ls -a'
    [ansible@ansible-150 ~]$ ansible 10.0.0.151 -m command -a 'chdir=/etc/selinux ls'
    10.0.0.151 | CHANGED | rc=0 >>
    config
    final
    semanage.conf
    targeted
    tmp
    

    注:command不能解析变量(如$HOME)和某些操作符("<", ">", "|", ";"以及"&"),所以明确要使⽤这些不可解析的操作符时,使⽤shell模块来代替command  

    5.3 shell 模块

    用途:shell和command的⽤法基本⼀样,实际上shell模块执⾏命令的⽅式是在远程使⽤/bin/sh来执⾏的,如/bin/sh ping 
    使用方法:

    ansible-doc -s shell
    - name: Execute commands in nodes.
      shell:
          chdir:                 # 在执行命令之前,先cd到指定的目录下
          creates:               # 用于判断命令是否要执行,如果指定的文件存在(可以使用通配符)存在,则不执行
          executable:            # 不再使⽤默认的/bin/sh解析并执⾏命令,⽽是使⽤此处指定的命令解析(例如使⽤expect解析expect脚本。必须为绝对路径)
          free_form:             # 默认的选项,这里只是显示,实际上是没有的
          removes:               # 用于判断命令是否要执行,如果指定的文件存在(可以使用通配符)不存在,则不执行
          stdin:                 # 将命令的stdin直接设置为指定值
          warn:                  # 设置command的警告信息(在/etc/ansible/ansible.cfg中有配置项)
    

    5.4 script 模块

    用途:script模块用于控制远程主机执行脚本,在执行脚本前,ansible会将本地脚本传输到远程主机,然后在执行,在执行脚本的时候,其采用的是远程主机上的shell环境

    [ansible@ansible-150 ~]$ ansible-doc -s script
    - name: Runs a local script on a remote node after transferring it
      script:
          chdir:                 # 在远程执⾏脚本前先切换到此⽬录下
          creates:               # 当此⽂件存在时,不执⾏脚本。可⽤于实现幂等性。
          decrypt:               # 此选项使用vault控制源文件的自动解密(对使用ansible-vault encrypt 文件名.yml 进行加密的文件解密)
          executable:            # 不再使⽤默认的/bin/sh解析并执⾏命令,⽽是使⽤此处指定的命令解析(例如使⽤expect解析expect脚本。必须为绝对路径)
          free_form:             # 本地待执⾏的脚本路径、选项、参数。之所以称为free_form,是因为它是脚本名+选项+参数。
          removes:               # 当此⽂件不存在时,不执⾏脚本。可⽤于实现幂等性。
    

    示例:

    新建一个脚本在ansible管理主机上
    [ansible@ansible-150 ~]$ cat keme.sh 
    #!/bin/bash
    echo "keme is handsome one."
    #没加任何参数
    [ansible@ansible-150 ~]$ ansible all -m script -a 'keme.sh'
    #执行命令前切换到opt目录 加了chdir参数
    [ansible@ansible-150 ~]$ ansible all -m script -a 'chdir=/opt ./keme.sh'
    

    5.5 copy模块

    用途:copy模块的作用就是拷贝文件或者目录,将 ansible 管理主机上的文件拷贝到远程主机中 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s copy
    - name: Copies files to remote locations
      copy:
          backup:                # 拷贝的同时也创建⼀个包含时间戳信息的备份⽂件,默认为no,可以指定为backup=yes做文件备份
          content:               # 当用content代替src参数的时候,可以把content指定的内容直接写到一个文件
          decrypt:               # 此选项使用vault控制源文件的自动解密(对使用ansible-vault encrypt 文件名.yml 进行加密的文件解密)
          dest:                  # ⽬标路径,只能是绝对路径,如果拷贝的⽂件是⽬录,则⽬标路径必须也是⽬录
          directory_mode:        # 当对⽬录做递归拷贝时,设置了directory_mode将会使得只拷贝新建⽂件旧⽂件不会被拷贝。默认未设置.
          follow:                # 是否追踪到链接的源⽂件(follow=yes|on)
          force:                 # 设置为yes(默认)时,将覆盖远程同名⽂件。设置为no时,忽略同名⽂件的拷贝。
          group:                 # 指定文件拷贝到远程主机后的属组,但是远程主机上必须有对应的组,否则会报错
          local_follow:          # 是否遵循本地机器中的文件系统链接(local_follow=yes|on)
          mode:                  # 设置远程⽂件的权限。使⽤数值表⽰时不能省略第⼀位,如0644。也可以使⽤'u+rwx'或'u=rw,g=r,o=r'等⽅式设置
          owner:                 # 设置远程⽂件的所有者
          remote_src:            # 如果yes它会从目标机上搜索src文件(remote_src=yes|on)
          src:                   # 拷贝本地源⽂件到远程,可使⽤绝对路径或相对路径。如果路径是⽬录,且⽬录后加了斜杠"/",则只会拷贝⽬录中的内容到远程,如果⽬录后不加斜杠,则拷贝⽬录本⾝和⽬录内的内容到远程
          unsafe_writes:         # 是否以不安全的方式进行,可能导致数据损坏(unsafe_writes=yes|on)
          validate:              # 复制前是否检验需要复制目的地的路径
    

      

    示例1 本地文件拷贝到被控端:

    #新建一个文件,文件内容如下
    [ansible@ansible-150 ~]$ pwd
    /home/ansible
    [ansible@ansible-150 ~]$ cat kemeaaa.txt 
    xixi xixi xixi
    
    #把/home/ansible/kemeaaa.txt/ 拷贝到被控端主机/opt 下
    [ansible@ansible-150 ~]$ ansible all -m copy -a 'src=/home/ansible/kemeaaa.txt dest=/opt/'
    

    示例2:拷贝之前先备份

    # 修改kemeaaa.txt 内容
    [ansible@ansible-150 ~]$ cat kemeaaa.txt 
    xixi xixi xixi
    keme keme keme
    
    # 加上backup这个参数
    [ansible@ansible-150 ~]$ ansible all -m copy -a 'src=/home/ansible/kemeaaa.txt dest=/opt/ backup=yes'
    

    在上面可以看到backup_file这个参数,后面就是备份的路径(在被控制端主机上查看)

    示例3 : 修改owner、group、mode参数,默认是root 
    拷贝文件对权限和属主属组进行改变

    # 把权限改为ansible 用户
    [ansible@ansible-150 ~]$ ansible all -m copy -a 'src=/home/ansible/kemeaaa.txt dest=/opt/ owner=ansible group=ansible mode=0744'
    # 验证
    [ansible@ansible-150 ~]$ ansible all -m shell -a 'ls -l /opt/kemeaaa.txt'
    

    5.6 fetch 模块

    用途:从被控远端机器上拉取文件(和COPY模块整好相反) 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s fetch
    - name: Fetches a file from remote nodes
      fetch:
          dest:                  # 本地存储拉取⽂件的⽬录。例如dest=/data,src=/etc/fstab,远程主机名host.exp.com,则保存的路径为/data/host.exp.com/etc/fstab。
          fail_on_missing:       # 当设置为yes时,如果拉取的源⽂件不存在,则此任务失败。默认为no.
          flat:                  # 改变拉取后的路径存储⽅式。如果设置为yes,且当dest以"/"结尾时,将直接把源⽂件的basename存储在dest下。显然,应该考虑多个主机拉取时的⽂件覆盖情况。
          src:                   # 远程主机上的源⽂件。只能是⽂件,不⽀持⽬录。在未来的版本中可能会⽀持⽬录递归拉取.
          validate_checksum:     # fetch到⽂件后,检查其md5和源⽂件是否
    

    示例1 :src、dest 
    拉取10.0.0.151 的文件 到 /home/ansible/目录下

    [ansible@ansible-150 ~]$ ansible 10.0.0.151 -m fetch -a 'src=/etc/hostname dest=/home/ansible/'
    

     示例2:flat

    [ansible@ansible-150 ~]$ ansible 10.0.0.152 -m fetch -a 'src=/etc/hostname dest=/home/ansible/ flat=yes'
    

    拉取后没有主机名文件夹标识

    5.7 file 模块

    用途:管理文件、目录的属性,也可以创建文件或者目录 
    使用方法: 
    在file模块中state参数是十分重要的

    [ansible@ansible-150 ~]$ ansible-doc -s file
    [root@ansible ~]# ansible-doc -s file
    - name: Sets attributes of files
      file:
          follow:                       # 是否遵循目的机器中的文件系统链接(可选值为:yes|on)
          force:                        # 当state=link的时候,可配合此参数强制创建链接文件,当force=yes时,表示强制创建链接文件
                                        # 不过强制创建链接文件分为三种情况。情况一:当要创建的链接文件指向的源文件并不存在时,使用此参数,可以先强制创建出链接文件。
                                        # 情况二:当要创建链接文件的目录中已经存在与链接文件同名的文件时,将force设置为yes,会将同名文件覆盖为链接文件,相当于删除同名文件,创建链接文件。
                                        # 情况三:当要创建链接文件的目录中已经存在与链接文件同名的文件,并且链接文件指向的源文件也不存在,这时会强制替换同名文件为链接文件
          group:                        # 设置远程⽂件的所属组
          mode:                         # 设置远程⽂件的权限。使⽤数值表⽰时不能省略第⼀位,如0644。也可以使⽤
          owner:                        # 设置远程⽂件的所有者
          path:                         # 必须的参数,用于指定要操作的文件或者目录
          recurse:                      # 当要操作的文件为目录,将recurse设置为yes,可以递归的修改目录中的文件属性
          src:                          # 当state设置为link或者hard时,表示我们想要创建一个软链接或者硬链接,所以,我们必须指明软链接或硬链链接的哪个文件,通过src参数即可指定链接源
          state:                        # 此参数非常灵活,其对应的值需要根据情况设定。比如,我们想要在远程主机上创建/testdir/a/b目录,那么则需要设置path=/testdir/a/b,
                                        # 但是,我们无法从”/testdir/a/b“这个路径看出b是一个文件还是一个目录,ansible也同样无法单单从一个字符串就知道你要创建文件还是目录,所以,我们需要通过state参数进行说明
                                        # state=directory:表示创建目录,如果path指定的不存在则被创建
                                        # state=touch:创建文件
                                        # state=link:创建软链接文件
                                        # state=hard:创建硬链接文件
                                        # state=absent:删除文件(删除时不用区分目标是文件、目录、还是链接)
          unsafe_writes:                # 是否以不安全的方式进行,可能导致数据损坏(unsafe_writes=yes|on)
    

    5.8 hostname 模块

    用途:管理配置主机名 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s hostname
    - name: Manage hostname
      hostname:
          name:                  # 必选,主机名称
    

    使用这个模块存在一个问题就是一改主机名紧跟着应该是在这个清单里面的机器都会被改掉导致主机名完全相同 
    是有解决方法的,使用变量的方式进行更改
      

    使用hostname模块修改主机名是直接生效的并且是永久生效

    5.9 yum 模块

    用途:使用yum包管理器管理包

    [ansible@ansible-150 ~]$ ansible-doc -s yum
    - name: Manages packages with the `yum' package manager
      yum:
          allow_downgrade:       # 是否允许给现有包的版本进行降级
          autoremove:            # 卸载包并且删除其所有的依赖包,如果这个依赖包被其他包所依赖则不会删除(authorremove=yes)
          bugfix:                # 如果bugfix=yes和state=latest则仅安装已标记为与bug修复相关的更新
          conf_file:             # 指定yum.repo配置文件.
          disable_excludes:      # 禁用YUM配置文件中定义的排除(yum.repo文件中的某个块).
                                 # disable_excludes=all 禁用所有排除
                                 # disable_excludes=main 禁用yum.conf中的[main]中定义的排除
                                 # disable_excludes=repoid 禁用未给定repo id定义的排除
          disable_gpg_check:     # 安装包时禁止gpgcheck,仅在state=present或者latest时生效.
          disable_plugin:        # 禁用yum的Loaded plugins(使用yum repolist all | less 查看所有插件)
          disablerepo:           # 禁止指定的repo源,多个repo源使用逗号分隔
          download_only:         # 只下载指定的安装包,不进行安装.
          enable_plugin:         # 开启yum的Loaded plugins(使用yum repolist all | less 查看所有插件).
          enablerepo:            # 明确使用那个repo源
          exclude:               # 排除那些包不安装,仅在state=present或者latest时生效
          installroot:           # 指定yum安装包的用户,用此用户安装的只允许root和指定用户使用
          list:                  # 类似于yum list.
          name:                  # (必选参数)指定包名,可以指定版本号,多个包可以使用逗号分隔
          releasever:            # Specifies an alternative release from which all packages will be installed.
          security:              # 如果设置为yes和state=latest,则只安装标记为与安全相关的更新
          skip_broken:           # 跳过具有损坏的依赖包
          state:                 # 用于指定软件包的状态 ,默认值为present,表示确保软件包已经安装
                                 # state=present安装状态(默认值)
                                 # state=installed安装状态
                                 # state=latest安装状态(安装最新的版本)
                                 # state=absent卸载状态
                                 # state=removed卸载状态
          update_cache:          # 强制yum检查缓存是否过期,并在需要时重新下载.仅在state=present或者latest时生效.
          update_only:           # 使用最新软件包时,只更新已安装的软件包。不要安装软件包.仅在state=present或者latest时生效
          validate_certs:        # 这仅适用于使用https url作为rpm的源的情况。例如,用于localinstall。如果设置为no,则不会验证SSL证书
    

      

    5.10 cron 模块

    用途:cron模块⽤于设置定时任务,也⽤于管理定时任务中的环境变量 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s cron
    - name: Manage cron.d and crontab entries
      cron:
          backup:                # (yes/on)如果设置了,则会在修改远程cron_file前备份这些文件
          cron_file:             # 自定义cron_file的文件名,使用相对路径则表示在/etc/cron.d/中,必选同时制定user选项
          minute:                # 分(0-59,*,/N),不写时默认为*
          hour:                  # 时(0-23,*,/N),不写时默认为*
          day:                   # 日(1-31,*,/N),不写时默认为*
          month:                 # 月(1-12,*,/N),不写时默认为*
          weekday:               # 周(0-6 for Sunday-Saturday,*),不写时默认为*
          disabled:              # 禁用crontab中的某个任务,要求state=present
          env:                   # (yes/on)设置一个环境变量,将添加在crontab的顶端,使用name=value定义变量名和值.
          job:                   # 需要执行的命令,如果设置了env,则表示环境变量的值,此时job="xxxx"等价于value="xxxx"
          name:                  # 描述crontab的字符串,但如果设置的是env,则name为环境变量的名称,要求state=absent,注意,若没有设置name,且state=present,则总会创建一条新的job条目,即使cron_file中已经存在同样的条目.
          reboot:                # 如果任务应该在重新启动时运行。不赞成使用此选项。用户应该使用special_time.
          special_time:          # 定时任务的别称,用于定义何时运行job条目.有效值有reboot/hourly/daily/weekly/monthly/yearly/annually
          state:                 # job或者env的状态是present(默认)还是absent,present用于创建,absent用于删除
          user:                  # 指定那个用户的crontab任务将要被修改,默认root.
    

    5.11 service 模块

    用途:service 模块可以帮助我们管理远程主机上的服务。比如,启动或停止远程主机中的 nginx 服务 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s service
    - name: Manage services
      service:
          arguments:             # 服务命令行参数传递
          enabled:               # 设置服务为开机自启(yes/no),默认为no
          name:                  # (必选项)指定服务名.
          pattern:               # 如果服务没有做出相应,可以通过这个参数指定使用ps或者其他方式查看服务的状态.
          runlevel:              # 设置服务启动级别
          sleep:                 # 如果服务正在"重新启动",那么在停止和开始命令之间设置休眠时间.
          state:                 # started和stoped分别是启动和停止服务,它们是幂等操作,多次启动或者停止服务都是一样的,也就是说对于运行中的服务不会再次启动操作,同理停止也是一样的;
                                 # restarted重启服务,restarted总是重读配置文件如果服务是未运⾏状态,则reloaded会启动服务(state和enabled两者⾄少要给⼀个)
    

    5.12 systemd 模块

    用途:systemd 模块可以帮助我们使用systemd管理远程主机上的服务。比如,启动或停止远程主机中的 nginx 服务

    [ansible@ansible-150 ~]$ ansible-doc -s systemd
    - name: Manage services
      systemd:
          daemon_reload:         # 在执行任何其他操作之前运行守护进程重新加载,以确保systemd已经读取其他更改.
          enabled:               # 设置服务为开机自启(yes/no),默认为no
          force:                 # 是否覆盖现有符号链接(yes/on).
          masked:                # 是否将服务设置为masked状态(yes/no),被mask的服务是无法启动的
          name:                  # 指定服务名称.
          no_block:              # 不要同步等待操作请求完成(yes/no)
          state:                 # started和stoped分别是启动和停止服务,它们是幂等操作,多次启动或者停止服务都是一样的,也就是说对于运行中的服务不会再次启动操作,同理停止也是一样的;
    

    5.13 user 模块

    用途:user 模块可以帮助我们管理远程主机上的用户,比如创建用户、修改用户、删除用户、为用户创建密钥对等操作 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s user
    - name: Manage user accounts
      user:
          append:                # 如果用户原本就存在多个附加组,那么当使用 groups 参数设置附加组时,当前设置会覆盖原来的附加组设置
                                 # 如果不想覆盖原来的附加组设置,需要结合 append 参数,将 append 设置为 yes,表示追加附加组到现有的附加组设置,append 默认值为 no.
          comment:               # 设置用户的描述信息
          create_home:           # 创建家⽬录,或者已有的⽤户但家⽬录不存在也会创建。设置为no则不创建家⽬录
          expires:               # 此参数用于指定用户的过期时间,相当于设置 /etc/shadow 文件中的的第8列
                                 # 比如,你想要设置用户的过期日期为2018年12月31日,那么你首先要获取到2018年12月31日的 unix 时间戳,使用命令 “date -d 2018-12-31 +%s” 获取到的时间戳为1546185600,
                                 # 所以,当设置 expires=1546185600 时,表示用户的过期时间为2018年12月31日0点0分,
                                 # 设置成功后,查看远程主机的 /etc/shadow 文件,对应用户的第8八列的值将变成17895(表示1970年1月1日到2018年12月31日的天数,unix 时间戳的值会自动转换为天数,我们不用手动的进行换算,
                                 # 目前此参数只支持在 Linux 和 FreeBSD 系统中使用。
          force:                 # 强制删除用户、用户目录,只在state=absent中生效,相当于userdel --force命令
          generate_ssh_key:      # 是否为相关用户生成SSH密钥。这将“不会”覆盖现有SSH密钥.
          group:                 # 设置⽤户的primary group(主组).
          groups:                # 将⽤户加⼊到辅助组列表中。如果设置"groups=",则会将此⽤户从所有辅助组中移除
          home:                  # 指定要创建的家⽬录路径
          move_home:             # 如果设置为yes,则"home="则表⽰将家⽬录移动到此选项指定的路径下
          name:                  # (必选项)要创建、修改、移除的⽤户名.
          non_unique:            # 当与 -u 选项一起使用时,该选项允许将用户ID更改为非唯一值
          password:              # 设置⽤户密码。此处只能使⽤加密密码作为值.
          password_lock:         # 锁定用户的密码(等价于usermod -L命令)这个选项并不总是意味着用户不能通过其他方法登录。这个选项没有禁用用户,只锁定密码.
          remove:                # 配合'state=absent'时,等价于'userdel --remove',即删除家⽬录和邮件列表
          seuser:                # 在启用selinux的系统上设置seuser类型.
          shell:                 # 设置⽤户的shell
          ssh_key_bits:          # 当 generate_ssh_key 参数的值为 yes 时,使用此参数指定要创建的SSH密钥中的位数.
          ssh_key_comment:       # 当 generate_ssh_key 参数的值为 yes 时,在创建证书时,使用此参数设置公钥中的注释信息。但是如果同名的密钥对已经存在,则并不会修改原来的注释信息,即不做任何操作。
                                 # 当不指定此参数时,默认的注释信息为”ansible-generated on 远程主机的主机名.
          ssh_key_file:          # 当 generate_ssh_key 参数的值为 yes 时,使用此参数自定义生成 ssh 私钥的路径和名称,对应公钥会在同路径下生成,公钥名以私钥名开头,以”.pub”结尾.
          ssh_key_passphrase:    # 当 generate_ssh_key 参数的值为 yes 时,在创建证书时,使用此参数设置私钥的密码。但是如果同名的密钥对已经存在,则并不会修改原来的密码,即不做任何操作.
          ssh_key_type:          # 当 generate_ssh_key参数的值为yes时,在创建证书时,使用此参数设置密钥对的类型。默认密钥类型为 rsa,但是如果同名的密钥对已经存在,并不会对同名密钥做任何操作.
          state:                 # 创建⽤户(present)还是删除⽤户(absent)。默认为present.
          system:                # 设置为yes表⽰创建⼀个系统⽤户,只能⽤于创建,不能⽤于修改已有⽤户为系统⽤户
          uid:                   # 设置用户的UID
          update_password:       # user是幂等模块,"always"将总是修改密码。"on_create"将只在创建⽤户时设置密码
    

      

    5.14 group 模块

    用途:添加或删除组 
    使用方法:

    [ansible@ansible-150 ~]$ ansible-doc -s group
    - name: Add or remove groups
      group:
          gid:                   # 用于指定组的gid
          name:                  # (必选项) 用于指定要操作的组名称
          state:                 # 用于指定组的状态,两个值可选,present,absent,默认为 present,设置为absent 表示删除组。
          system:                # 如果是yes,表示指定的组是系统组
    

    5.15 小结

    上面很多都是模块帮助参数使用说明,自己多试试,就知道模块怎么试用了,还是多看模块帮助信息。

    6 使用 playbooks 剧本

    Playbooks是Ansible的配置,部署和编排语言。他们可以描述您希望远程系统实施的策略,或者描述一般IT流程中的一系列步骤。

    6.1 Playbook 语法

    Playbook 采用 YAML 语法编写,该语言在被开发是,它的意思是:Yet Another Markup Language (仍是一种标记语言)。结合ansible 中 要用到的YAML 语法点。对YAML 语法简洁总结如下。 
    看官方文档的一个简易的列子:一个playbook 的列子verify-apache.yml

    ---
    # 选择的主机
    - hosts: webservers
    #vars 这个是变量
      vars:
        http_port: 80
        max_clients: 200
    # remote_user 远端的执行权限
      remote_user: root
    # 创建一个任务tasks
      tasks:
      - name: ensure apache is at the latest version
    # 利用yum模块才操作
        yum:
          name: httpd
          state: latest
      - name: write the apache config file
        template:
          src: /srv/httpd.j2
          dest: /etc/httpd.conf
      # 触发重启 apache 服务器
        notify:
        - restart apache
      - name: ensure apache is running
        service:
          name: httpd
          state: started
      # 这里的handlers 和上面的notify 的触发是配对的。这就是handlers的作用。相当于tag
      handlers:
        - name: restart apache
          service:
            name: httpd
            state: restarted
    

    总的来说,Playbook 语法的一些特性:

    1. 需要以”—”三个减号开始,且需顶行手写。

    2. 次行开始正常写Playbook 内容。

    3. 使用 # 号注释代码。

    4. 缩进必须是统一的,不能将空格和Tab混用。

    5. 缩进的级别必须是一致的,同样的缩进代表同样的级别,程序判别配置的级别是通过缩进结合换行来实现的。

    6. YAML 文件内容 和Linux 系统大小写判断方式保持一致,是区别大小写的,k/v的值均需要大小写敏感。

    7. k/v 的值可同行也可换行写。同行使用 “:” 分隔,换行写需要以”-” 分隔

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

    9. 一个 name 只能包括一个 task 。

    6.1.2 写简单的Playbook

    上面都是语法说明,自己写一些做简单的列子做练习把 
    示例1:allping.yml

    #建一个目录用来做练习
    [ansible@ansible-150 ansible]$ sudo mkdir learn
    [ansible@ansible-150 ansible]$ cd learn/
    [ansible@ansible-150 learn]$ pwd
    /etc/ansible/learn
    [ansible@ansible-150 learn]$ sudo vim allping.yml
    ---
    - hosts: all
      remote_user: root
      tasks:
        - name: test connection
          ping:
    # 执行编写的剧本
    [ansible@ansible-150 learn]$ ansible-playbook allping.yml 
    

    示例2:install_apache.yml

    # 在管理主机安装上httpd 和 httpd-devel 要httpd.conf和httpd-vhosts.conf 文件
    [ansible@ansible-150 learn]$ sudo yum -y install httpd httpd-devel
    
    # 修改管理主机的httpd.conf和httpd-vhosts.conf 默认没有httpd-vhosts.conf 自己随便创建的
    # 注配置文件内容无实际意义,为了实验效果
    [ansible@ansible-150 conf]$ pwd
    /etc/httpd/conf
    [ansible@ansible-150 conf]$ sudo cp httpd.conf /tmp/
    [ansible@ansible-150 conf]$ sudo cp httpd-vhosts.conf /tmp/
    # 编写install_apache.yml 剧本
    [ansible@ansible-150 conf]$ cd /etc/ansible/learn/
    [ansible@ansible-150 learn]$ sudo vim install_apache.yml
    ---
    - hosts: all
      sudo: yes
      tasks:
      - name: install apache
        yum: name={{ item }} state=present
        with_items:
          - httpd
          - httpd-devel
      - name: copy config file
        copy:
          src: "{{ item.src }}"
          dest: "{{ item.dest }}"
          owner: root
          group: root
          mode: 0644
        with_items:
          - {
          src: "/tmp/httpd.conf",
          dest: "/etc/httpd/conf/httpd.conf" }
          - {
          src: "/tmp/httpd-vhosts.conf",
          dest: "/etc/httpd/conf/httpd-vhosts.conf" }
      - name: 检查 Apache 运行状态,并设置开机启动
        service: name=httpd state=started enabled=yes
    # 写好了剧本是不是要对剧本进行debug 测试,测试剧本是否可用
    # 第一语法检测,第二模拟检测
    [ansible@ansible-150 learn]$ ansible-playbook --syntax-check install_apache.yml 
    [ansible@ansible-150 learn]$ ansible-playbook -C  install_apache.yml 
    

    上面检测都没问题了,该给被控制主机安装apache了

     

    [ansible@ansible-150 learn]$ ansible-playbook install_apache.yml
    # 验证是否安装成功,并启动了
    [ansible@ansible-150 learn]$ ansible all -m shell -a 'ss -ntulp | grep httpd'
    
    # 查看配置文件是否拷贝成功了
    [ansible@ansible-150 learn]$ ansible all -m shell -a 'ls -a /etc/httpd/conf/'
    

    注:上面有警告信息,可以自己根据警告信息,自己调试自己的剧本(playbook)和ansible.cfg 的配置文件

    第 1 行,”—” ,这个是yaml 语法中注释的用法,就想shell 脚本中的 ”#“ 
    第 2 行:”- hosts: all” ,告诉 Ansible 具体要在哪些主机上运行我的剧本,在本例中是all,即所有主机。 
    第 3 行,”sudo: yes”,告诉 Ansible 通过sudo 来运行相应命令,这样所有命令将会以root 身份执行。 
    第 4 行: “tasks: ” 指定一系列将要运行的任务 
    每一个任务 “- name: xxxx” 开头。 
    “- name: ” 字段并不是一个模块不会执行任务实质性的操作,它只是给 “task” 一个易于识别的名称。即使把 “- name” 对应的行删除,也不会有任何问题。 
    在示例2中:使用yum模块来安装apache 
    在第一个 “- name” 任务当中,每个"- name”都可以使用 with_items 来定义变量,并通过"{{ 变量名 }}" 的形式来直接使用,2.11版本应该使用另一种方法,注意警告信息。使用yum 模块的state=present 选项来确保软件被安装,或者使用state=absent来确保软件被删除。

    在第二个 “- name” 当中,使用copy 模块来讲”src” 定义的源文件(必须是Ansible 所在服务器上的本地文件)复制到 “dest” 定义的目的地址(此地址为远程主机上的地址)去。在传递文件的同时,还定义了文件的属主,属组和权限。在这个 “- name” 中,我们用数组的形式给变量复制,使用了 { var1: value , var2: value } 的格式来赋值,变量的个数可以任意多,不同变量间以逗号分隔,使用 {{ item.var1 }} 的形式来调用变量,本示例中为 {{ item.src }}

    第三个 “- name” 使用了同样的结构,调用了 service 模块, 以保证服务的正常开启

    6.2 amsob-playbook 小技巧

    6.2.1 playbook 语法检测和调试

    写完一个playbook 一定要进行语法检测,看看自己哪里写的不对,好及时修改,警告信息也可以注意一下。

    语法检测

    ansible-playbook --syntax-check playbook_file.yml
    

    调试  

    ansible-playbook -C playbook_file.yml
    

    在正式运行playbook 之前,使用--check或-C 选项来检测playbook 都会改变哪些内容,调试显示的结果跟真正执行时一模一样,但不会真的被管理的服务器产生实际影响  

    6.3 限定playbook 执行范围

    当playbook 指定的一批主机有个别主机需进行变更时,可以不需要去修改Playbook文件本身,而是通过一些选项就可以直接限定和查看Ansible 命令的执行范围。

    --limit 
    如果允许上面的install_apache.yum 的剧本,会发现所有被ansible 管理的主机都会被操作。 
    可以通过修改剧本 “- hosts: ” 字段来指定哪些主机将会应用 Playbook 的操作。

    • 指定一台主机: ip或者主机名
    • 指定多台主机: 10.0.0.151,10.0.0.152 逗号分隔,指定多台主机
    • 指定一组主机:写上组名 .(这个组名是/etc/ansibles/hosts里面定义的那个组名) 

    当然,也可以直接通过ansible-playbook 命令来指定主机:

    例如:只指定10.0.0.151 执行
    ansible-playbook install_apache.yml  --list 10.0.0.151
    

    这样,即便playbook中设定 “- hosts: all” ,但也只对10.0.0.151 生效  

    --list-hosts 
    如果要知道在执行playbook是,哪些主机将会受影响,则使用--list-hosts 选项

    ansible-playbook install_apache.yml  --list-hosts
    

    6.4 用户与权限设置

    --remote-user 
    在playbook中,如果在 hosts 字段下没有定义users 关键字,那么Ansible将会使用你在Inventory 文件(/etc/ansible/hosts)中定义的用户,如果Inventory 文件中也没定义用户,ansible 将默认使用系统用户身份来通过ssh连接远程主机,在管理控制主机运行playbook内容。 
    也可以直接在ansible-playbook 中使用--remote-user选项来指定用户。

    ansible-playbook install_apache.yml --remote-user=keme
    

    --ask-sudo-pass 
    在某些情况下,需要传递sudo 密码到远程主机,来保证sudo命令的正常运行时,可以以使用--ask-sudo-pass(-K) 选项来交互式输入密码

    --sudo 
    使用--sudo 选项,可以强制所有 playbook 都使用sudo用户,同时使用 --sudo-user选项指定sudo 可以执行那个用户的权限。如果不指定,则默认以root 身份运行 
    比如当前 用户 ansible 想以 keme 的身份运行 playbook ,命令如下:

    [ansible@ansible-150 learn]$ ansible-palybook install_apache.yml --sudo --sudo-user=keme --ask-sudo-pass
    

    执行过程中,会要求用户输入keme 的密码 

    6.5 ansible-playbook :其他常用选项

    ansible-playbook 命令还有一些其他选项:

    --inventory=PATH (-i PATH):指定inventory 文件,默认文件是/etc/ansible/hosts
    --verbose (-v):显示详细输出,也可以使用-vvvv 显示精确到每分钟的输出
    --extra-vars=VARS (-e VARS) : 定义在playbook使用的变量,格式为: "key=value,key=value"
    --forks=NUM (-f NUM): 指定并发执行的任务数,默认为5,根据服务器性能,调大这个值可提高ansible执行效率0
    --conection=TYPE (-c TYPE) : 指定远程主机的方式,默认为SSH,设为local时,则只在本地执行playbook,建议不做修改
    --check (-C) :检测模式,playbook中定的所有任务将在每台远程主机上进行检测,并不真正执行。
    

    7 安全管理优化

    • 使用安全加密的通信方式,例如:秘钥对;

    在centos/redhat 中ssh 服务的主配置文件 /etc/ssh/sshd_config 中设置
    PasswordAuthentication no #禁止 ssh 使用密码认证连接。如此一来就杜绝了所有针对密码的暴力破解攻击。
    PermitRootLogin no        #禁止 root 用户远程登录。建议只使用普通用户进行远程登录,并使用sudo命令来行使大部分 root 权限。如果实在需要使用 root 用户进行交互式管理,可以使用普通用远程连接到主机,然后通过 su 命令切换到root用户,这样做更加安全
    # 明确指定允许或禁止的远程登录用户。使用AllowUser和 DenyUsers 来指定哪些用户可以登录,哪些用户不能登录。比如,只允许用户 keme 登录,可以设置为AllowUsers keme; 允许除了 xixi 以为的其他用户登录,可以设置为:DenyUsers xixi
    Port 2636 # 使用非默认端口。ssh 的默认端口为22,将其改为任意不与其他服务冲突的端口(建议采用1024以上的端口号)将会使系统更为安全。在ssh配置文件中设置Port 2636,即可修改ssh默认端口为2849.
    
    • 禁止 root 用户远程登录并充分利用 sudo;  
    #充分利用visudo命令或者 vim  /etc/sudoers
    #sudo的目的:为非根用户授予根用户的权限;
    root    ALL=(ALL)       ALL
    %wheel  ALL=(ALL)       ALL
    
    授权用户/组    主机名=(允许转换至的用户)   NOPASSWD:命令动作
    # 假如无需密码直接运行命令的,应该加NOPASSWD:参数,不需要时方可省略,
    
    • 移除非必需的软件,只开放需要用的端口;
    • 遵守权限最小化原则; 

    用户权限管理和文件权限管理,主机上的用户,应用以及进程都应该只允许访问它们本身需要访问的信息和资源

    • 及时更新操作系统和软件;
    • 使用合理过的、有针对性的防火墙;
    • 监测系统登录情况,封掉可以的 IP 地址;
    • 系统登录日志审计;

    8 总结

    上面的写的东西,都是基础, 没写到很高深的东西 ,比如roles , includes ,jinjia2,tags,等等 。 
    如果你有个东西不会,就要去官方文档快速看一下怎么使用,

     

    多去官方文档搜索,比瞎搜索靠谱多了。 
    官方文档: 
    https://docs.ansible.com/ansible/latest/user_guide/index.html

  • 相关阅读:
    使用反射获取对象的步骤
    金融IT的算法要求
    Java编译与反编译命令记录
    常用搜索博客/网站
    Java核心-03 谈谈final、finally、 finalize有什么不同?
    Java核心-02 Exception和Error有什么区别?
    PHP函数技巧篇
    IO
    Markdown 简单使用教程
    FZu Problem 2233 ~APTX4869 (并查集 + sort)
  • 原文地址:https://www.cnblogs.com/keme/p/11351611.html
Copyright © 2020-2023  润新知