zoukankan      html  css  js  c++  java
  • Ansible学习笔记

    Ansible简要笔记
    参考http://www.ansible.com.cn/docs

    主流的自动化运维工具:Puppet、saltstack、ansible chef
    Ansible:用Python编写,采用paramiko协议库
    Ansible的组成:
      1.核心引擎:Ansible
      2.核心模块:
      3.自定义模块
      4.插件:实现日志记录、邮件等功能
      5.playbook:记录执行的任务
      6.连接插件:现在主要是ssh,还支持其他(ZeroMQ等)
      7.主机清单:记录需要配置的节点信息(文件hosts)

    Ansible的优点:
      1.语法简单
      2.不要安装客户端
      3.大量内置模块 用 ansible-doc -l | wc -l 统计可用模块

    [root@localhost ~]# ansible-doc -l | wc -l
    1652

    ansible的配置文件:/etc/ansible/ansible.cfg

    CentOS7.4的安装:
    [root@localhost ~]#yum install -y ansible
    [root@localhost ~]# ansible --version
    ansible 2.5.0
    config file = /etc/ansible/ansible.cfg
    configured module search path = [u'/root/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']
    ansible python module location = /usr/lib/python2.7/site-packages/ansible
    executable location = /usr/bin/ansible
    python version = 2.7.5 (default, Aug 4 2017, 00:39:18) [GCC 4.8.5 20150623 (Red Hat 4.8.5-16)]

    修改配置文件:/etc/ansible/ansible.cfg

    #开启日志
    log_path = /var/log/ansible.log
    #如果ansible没有和被管理节点配置无密码登录时,会提示没有在known_hosts中初始化,如果不想出现这样的提示,可以在配置文件中设置
    host_key_checking = False
    其他配置基本不用改

    基本命令使用:

    #查看版本
    [root@localhost ~]# ansible --version
    #查看所有可用的内置模块
    [root@localhost ~]# 
    ansible-doc -l #查看模式使用帮助
    [root@localhost ~]# ansible-doc -s yum

    一、安装

    系统要求:Linux ssh
    安装方法:通过系统自带的源进行安装(yum install ansible)
    Python:python2.6或python2.7
    selinux:如果启用,需要安装libselinux-python
    二、使用前配置(可选)
    配置客户端无密码登陆:
    [root@localhost ~]# ssh-keygen
    [root@localhost ~]# ssh-copy-id root@10.100.14.102
    #########################################################################
    三基本配置文件:
    (一)inventory文件(客户端主机的IP/域名)
    默认文件位置:/etc/ansible/hosts
    几种常见的格式:

    #1.直接写IP地址
    192.168.1.10
    #2.把IP分组
    [webserver]
    192.168.1.11
    192.168.1.12
    #3.对于不是以22端口连接的主机,可以指定IP地址
    [sql]
    192.168.1.20:2222
    #4.主机别名设置
    [jumper]
    jumper ansible_ssh_port=5555 ansible_ssh_host=192.168.1.50
    #5.对于有规律的一组IP地址可以简写
    [dbserver]
    192.168.1.[100:102]
    db[1:3].example.com
    #6.对用非root用户登录或不同登录方式的主机可以指定连接的用户名
    [targets]
    localhost ansible_connection=local
    other1.example.com ansible_connection=ssh ansible_ssh_user=user1
    other2.example.com ansible_connection=ssh ansible_ssh_user=user1
    #7.给主机定义变量
    [apache]
    host1 http_port=80 maxRequestsPerChild=808
    host2 http_port=303 maxRequestsPerChild=909
    #8.给一组主机定义变量
    [atlanta]
    host1
    host2
    [atlanta:vars]
    ntp_server=ntp.atlanta.example.com
    proxy=proxy.atlanta.example.com
    #9.把一个组作为另一个组的子成员
    [group1]
    host1
    host2
    [group2]
    host3
    host3
    [group:children]
    group1
    group2

    此外,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_sudo_exe (new in version 1.8)  sudo 命令路径(适用于1.8及以上版本)
    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以外的名字(实际有可能名为python26).

    与 ansible_python_interpreter 的工作方式相同,可设定如 ruby 或 perl 的路径....

    inventory的升级用法:

    /etc/ansible/hosts是ansible中默认的被管理节点的IP存放的文件路径,如果想自己定义,或者想把不同类型的主机存在不同的文件中,可以在/etc/ansible/ansible.cfg中更改配置文件即可。比如:

    [root@localhost ~]# vim /etc/ansible/ansible.cfg
    inventory      = /root/myhosts/
    [root@localhost ~]# tree /root/myhosts/
    /root/myhosts/
    ├── dbserver
    └── httpd
    
    0 directories, 2 files
    [root@localhost ~]# ansible all --list-hosts
      hosts (2):
        10.100.14.102
        192.168.1.2

    以上的inventory都是静态hosts配置,对于大量的主机在后期添加起来比较麻烦,ansible还支持动态的inventory

    即通过外部拉取主机的IP,inventory的脚本需要支持两个参数,--list(-l),--host(-H)然后返回json格式的主机信息。

    #########################################################################

    (二)playbook配置文件
    hosts     中记录的是客户机的IP地址
    playbook  中记录的是客户机要进行的操作
    Playbooks  的格式是YAML
    palybook的简单实例:

    ---
    - hosts: webservers
      vars:
        http_port: 80
        max_clients: 200
      remote_user: root    #定义连接的用户名
      tasks:
      - name: ensure apache is at the latest version
        yum: pkg=httpd state=latest
      - name: write the apache config file
        template: src=/srv/httpd.j2 dest=/etc/httpd.conf
        notify:
        - restart apache
      - name: ensure apache is running
        service: name=httpd state=started
      handlers:
        - name: restart apache
          service: name=httpd state=restarted

    详细解释:
    1.主机与用户:
    1.2在任务开始之前定义用户
    - hosts: webservers #指定操作对象,webserver是在hosts文件中农定义的一组主机的名字
      remote_user: root #定义连接的用户名
    1.2在每一个任务中定义远程用户
    - hosts: webservers
      remote_user: root
      tasks:
          - name: test connection
      ping:
      remote_user: username
    1.3使用sudo切换用户
    ---
    - hosts: webservers
      remote_user: yourname
      sudo: yes
    或者在任务中使用sudo
    ---
    - hosts: webservers
      remote_user: username
      tasks:
       - service: name=nginx state=started
         sudo: yes
    或者使用sudo切换到其他用户
    - hosts: webservers
      remote_user: yourname
      sudo: yes
      sudo_user: postgres
    2.任务(tasks)
    tasks的格式;
    tasks:
      - name: 注释部分
      模块名称和执行内容
    2.1command模块和shell模块格式
    tasks:
      - name: disable selinux
      command: /sbin/setenforce 0
    异常的处理:
    tasks:
      - name: run this command and ignore the result
        shell: /usr/bin/somecommand || /bin/true
    或者使用ignore_errors: True
    tasks:
      - name: run this command and ignore the result
        shell: /usr/bin/somecommand
        ignore_errors: True
    2.2其他模块的格式:
    tasks:
      - name: make sure apache is running
        service: name=httpd state=running

    3.Handlers的用法:主要用来重启服务
    handlers:
      - name: restart memcached
        service: name=memcached state=restarted
      - name: restart apache
        service: name=apache state=restarted
    playbook的执行
    ansible-playbook playbook.yml
    4.playbook中变量
    4.1变量的命名和其他语言一致
    4.2在playbook中定义变量
    - hosts: webservers
      vars:
      http_port: 80
    4.3变量的引用:注意需要加双引号
    - hosts: app_servers
      vars:
      app_path: "{{ base_path }}/22"

    5.条件选择
    5.1when语句(jinja2)
    用法1:

    tasks:
      - name: "shutdown Debian flavored systems"
        command: /sbin/shutdown -t now
        when: ansible_os_family == "Debian"
    tasks:
      - shell: echo "only on Red Hat 6, derivatives, and later"
        when: ansible_os_family == "RedHat" and ansible_lsb.major_release|int >= 6

    用法2:如果变量不存在,可以使用defined跳过

    tasks:
        - shell: echo "I've got '{{ foo }}' and am not afraid to use it!"
          when: foo is defined
    
        - fail: msg="Bailing out. this play requires 'bar'"
          when: bar is not defined

    用法3:在roles 和 includes 上面应用’when’语句

    - include: tasks/sometasks.yml
      when: "'reticulating splines' in output"
    - hosts: webservers
      roles:
         - { role: debian_stock_config, when: ansible_os_family == 'Debian' }

    ansible中的when

    tasks:
      - command: /bin/false
        register: result
        ignore_errors: True
      - command: /bin/something
        when: result|failed
      - command: /bin/something_else
        when: result|success
      - command: /bin/still/something_else
        when: result|skipped

    5.2变量注册:返回结果保存到一个变量中,比如 

    - name: test play
      hosts: all
    
      tasks:
    
          - shell: cat /etc/motd
            register: motd_contents
    
          - shell: echo "motd contains the word hi"
            when: motd_contents.stdout.find('hi') != -1 

    6.循环

    6.1标准循环

    - name: add several users
      user: name={{ item }} state=present groups=wheel
      with_items:
         - testuser1
         - testuser2
    或者:
    - name: add several users
      user: name={{ item }} state=present groups=wheel
      with_items:"{{somelist}}"
    或者:
    - name: add several users
      user: name={{ item.name }} state=present groups={{ item.groups }}
      with_items:
        - { name: 'testuser1', groups: 'wheel' }
        - { name: 'testuser2', groups: 'root' }

    6.2循环嵌套

    - name: give users access to multiple databases
      mysql_user: name={{ item[0] }} priv={{ item[1] }}.*:ALL append_privs=yes password=foo
      with_nested:
        - [ 'alice', 'bob' ]
        - [ 'clientdb', 'employeedb', 'providerdb' ]
    或者:
    - name: here, 'users' contains the above list of employees
      mysql_user: name={{ item[0] }} priv={{ item[1] }}.*:ALL append_privs=yes password=foo
      with_nested:
        - "{{users}}"
        - [ 'clientdb', 'employeedb', 'providerdb' ]

    6.3对哈希表使用循环

    ---
    users:
      alice:
        name: Alice Appleworth
        telephone: 123-456-7890
      bob:
        name: Bob Bananarama
        telephone: 987-654-3210
    tasks:
      - name: Print phone records
        debug: msg="User {{ item.key }} is {{ item.value.name }} ({{ item.value.telephone }})"
        with_dict: "{{users}}"

    6.4对文件列表使用循环

    ---
    - hosts: all
    
      tasks:
    
        # first ensure our target directory exists
        - file: dest=/etc/fooapp state=directory
    
        # copy each file over that matches the given pattern
        - copy: src={{ item }} dest=/etc/fooapp/ owner=root mode=600
          with_fileglob:
            - /playbooks/files/fooapp/*

    6.5对并行数据集使用循环(不常用)

    ---
    alpha: [ 'a', 'b', 'c', 'd' ]
    numbers:  [ 1, 2, 3, 4 ]
    tasks:
        - debug: msg="{{ item.0 }} and {{ item.1 }}"
          with_together:
            - "{{alpha}}"
            - "{{numbers}}"

    6.6对子元素使用循环

    ---
    users:
      - name: alice
        authorized:
          - /tmp/alice/onekey.pub
          - /tmp/alice/twokey.pub
        mysql:
            password: mysql-password
            hosts:
              - "%"
              - "127.0.0.1"
              - "::1"
              - "localhost"
            privs:
              - "*.*:SELECT"
              - "DB1.*:ALL"
      - name: bob
        authorized:
          - /tmp/bob/id_rsa.pub
        mysql:
            password: other-mysql-password
            hosts:
              - "db1"
            privs:
              - "*.*:SELECT"
              - "DB2.*:ALL"
    - user: name={{ item.name }} state=present generate_ssh_key=yes
      with_items: "{{users}}"
    
    - authorized_key: "user={{ item.0.name }} key='{{ lookup('file', item.1) }}'"
      with_subelements:
         - users
         - authorized          
    - name: Setup MySQL users
      mysql_user: name={{ item.0.user }} password={{ item.0.mysql.password }} host={{ item.1 }} priv={{ item.0.mysql.privs | join('/') }}
      with_subelements:
        - users
        - mysql.hosts

    6.7对整数序列循环(不常用)

    ---
    - hosts: all
    
      tasks:
    
        # create groups
        - group: name=evens state=present
        - group: name=odds state=present
    
        # create some test users
        - user: name={{ item }} state=present groups=evens
          with_sequence: start=0 end=32 format=testuser%02x
    
        # create a series of directories with even numbers for some reason
        - file: dest=/var/stuff/{{ item }} state=directory
          with_sequence: start=4 end=16 stride=2
    
        # a simpler way to use the sequence plugin
        # create 4 groups
        - group: name=group{{ item }} state=present
          with_sequence: count=4

    6.8随机选择(不常用)

    - debug: msg={{ item }}
      with_random_choice:
         - "go through the door"
         - "drink from the goblet"
         - "press the red button"
         - "do nothing"

    6.9Do-Until循环

    - action: shell /usr/bin/foo
      register: result
      until: result.stdout.find("all systems go") != -1
      retries: 5
      delay: 10

    6.10还有很多不常见的用法,具体参考官方文档
    四、文件目录
    目录结构

    production                #  关于生产环境服务器的清单文件
    stage                     #  关于 stage 环境的清单文件
    
    group_vars/
       group1                 #  这里我们给特定的组赋值
       group2                 # ""
    host_vars/
       hostname1              #  如果系统需要特定的变量,把它们放置在这里.
       hostname2              # ""
    
    library/                  #  如果有自定义的模块,放在这里(可选)
    filter_plugins/           #  如果有自定义的过滤插件,放在这里(可选)
    
    site.yml                  # 主 playbook
    webservers.yml            # 服务器的 playbook
    dbservers.yml             # 数据库服务器的 playbook
    
    roles/
        common/               #  这里的结构代表了一个 "role"
            tasks/            #
                main.yml      #  tasks file can include smaller files if warranted
            handlers/         #
                main.yml      #  handlers file
            templates/        #  files for use with the template resource
                ntp.conf.j2   #  templates end in .j2
            files/            #
                bar.txt       #  files for use with the copy resource
                foo.sh        #  script files for use with the script resource
            vars/             #
                main.yml      #  variables associated with this role
            defaults/         #
                main.yml      #  default lower priority variables for this role
            meta/             #
                main.yml      #  role dependencies
    
        webtier/              # same kind of structure as "common" was above, done for the webtier role
        monitoring/           # ""
        fooapp/               # ""

     五 常用命令

  • 相关阅读:
    学习制作操作系统 0
    阅读《C陷阱与缺陷》的知识增量
    CSS 优先级和特指度
    openCV2马拉松第19圈——Harris角点检測(自己实现)
    Cacti监控mysql数据库server实现过程
    ledisdb:支持类redis接口的嵌入式nosql
    03005_SQL查询语句
    通过smtp直接发送邮件
    XML 解析默认去掉命名空间和注释
    C# /VB.NET 创建PDF项目符号列表和多级编号列表
  • 原文地址:https://www.cnblogs.com/gaoyuanzhi/p/8863386.html
Copyright © 2011-2022 走看看