Brc's blog
首页
前端
后端
运维
  • 工作笔记
  • 分类
  • 标签
  • 归档
关于

Brc

努力中
首页
前端
后端
运维
  • 工作笔记
  • 分类
  • 标签
  • 归档
关于
  • Linux基础

  • Linux进阶

    • shell

    • nginx

    • keepalived

    • LVS

    • ansible

      • Ansible基础快速入门
      • Ansible Playbook
      • Ansible Variables
      • Ansible Facts Variables
      • Ansible Task Control
      • Ansible Advanced
        • Ansible Jinja2
          • 什么是jinja2
          • Ansible如何使用jinja2
          • jinja模板基本语法
          • jinja模板逻辑关系
          • jinja模板示例
          • 案例1-Jinja2管理Nginx
          • 案例2-Jinja2管理Keepalived
        • Ansible Roles
          • Roles基本概述
          • Roles目录结构
          • Roles依赖关系
          • Roles案例实战
          • 案例-Roles部署NFS
      • python调用ansible模块
    • docker

    • mysql

  • 其他

  • 运维
  • Linux进阶
  • ansible
Brc
2022-01-06
目录

Ansible Advanced

# Ansible Jinja2

# 什么是jinja2

Jinja2是Python的全功能模板引擎

Ansible需要使用Jinja2模板来修改被管理主机的配置文件。

  • 场景:给10台主机装上Nginx服务,但是要求每台主机的端口都不一样,如何解决?

# Ansible如何使用jinja2

ansible使用jinja2模板需要借助template模块实现,那template模块是用来做什么的?

template模块和copy模块完全一样,都是拷贝文件至远程主机,区别在于template模块会解析要拷贝的文件中变量的值,而copy则是原封不动的将文件拷贝至被控端。

# jinja模板基本语法

  1. 要想在配置文件中使用jinj2,playbook中的tasks必须使用template模块;
  2. 配置文件里面使用变量,用双大括号括起来;

# jinja模板逻辑关系

  1. 循环表达式

    {% for i in EXPR %}...{% endfor %}
    
    1
  2. 判断表达式

    {% if EXPR %}...{% elif EXPR %}...{% endif %}
    
    1
  3. 注释

    {# COMMENT #}
    
    1

# jinja模板示例

  1. 使用Playbook推送文件

    [root@manager playbook]# cat jinja2.yml
    - hosts: webservers
      tasks:
        - name: Copy template File /etc/motd
          template: src=./motd.j2 dest=/etc/motd
    
    1
    2
    3
    4
    5
  2. 准备motd.j2文件

    [root@manager playbook]# cat motd.j2
    Welcome to {{ ansible_hostname }}
    This system total Memory is: {{ ansible_memtotal_mb }} MB
    This system free Memory is: {{ ansible_memfree_mb }} MB
    
    1
    2
    3
    4
  3. 执行playbook

    [root@manager playbook]# ansible-playbook jinja2.yml
    PLAY [webservers] ********************************************************************
    
    TASK [Copy template File /etc/motd] **************************************************
    changed: [10.0.0.13]
    changed: [10.0.0.12]
    
    PLAY RECAP ***************************************************************************
    10.0.0.12                  : ok=1    changed=1    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    10.0.0.13                  : ok=1    changed=1    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
  4. 检查执行后的状态

    [root@manager playbook]# ssh root@10.0.0.12
    Welcome to slave-1
    This system total Memory is: 972 MB
    This system free Memory is: 379 MB
    
    [root@manager playbook]# ssh root@10.0.0.13
    Welcome to slave-2
    This system total Memory is: 972 MB
    This system free Memory is: 379 MB
    
    1
    2
    3
    4
    5
    6
    7
    8
    9

上面的例子展示了如何使用facts变量,当playbook被执行后,ansible_hostname和ansible_memtotal_mb将会被替换成被管理主机上搜集的facts变量的值

# 案例1-Jinja2管理Nginx

  • ansible使用jinja2的for循环表达式渲染出nginx负载均衡的配置文件。
  1. 使用Playbook推送文件

    [root@manager playbook]# cat proxy.yml
    - hosts: webservers
      vars:
        http_port: 80
        server_name: www.bi.com
    
      tasks:
        - name: Copy template Nginx Configure
          template: src=./blog.conf.j2 dest=/etc/nginx/conf.d/blog.bi.com.conf
          notify: Reload Nginx Server
    
      handlers:
        - name: Reload Nginx Server
          service: name=nginx state=reloaded
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
  2. 准备blog.conf.j2配置文件

    [root@manager playbook]# cat blog.conf.j2
    upstream ansible_php {
    {% for i in groups['webservers'] %}
        server {{i}}:80;
    {% endfor %}
    }
    
    server {
        listen 80;
        server_name ansible.bi.com;
    
        location / {
            proxy_pass http://ansible_php;
            proxy_set_header Host $http_hosts;
        }
    }
    
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
  3. 执行playbook

    [root@manager playbook]# ansible-playbook proxy.yml
    PLAY [webservers] ********************************************************************
    
    TASK [Copy template Nginx Configure] *************************************************
    changed: [10.0.0.12]
    changed: [10.0.0.13]
    
    RUNNING HANDLER [Reload Nginx Server] ************************************************
    changed: [10.0.0.13]
    changed: [10.0.0.12]
    
    PLAY RECAP ***************************************************************************
    10.0.0.12                  : ok=2    changed=2    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    10.0.0.13                  : ok=2    changed=2    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
  4. 检查jinja模板渲染出来的配置文件

    [root@slave-1 ~]# cat /etc/nginx/conf.d/blog.bi.com.conf
    upstream ansible_php {
        #设置变量,并进行循环赋值,渲染配置
        server 10.0.0.12:80;
        server 10.0.0.13:80;
    }
    
    server {
        listen 80;
        server_name ansible.bi.com;
    
        location / {
            proxy_pass http://ansible_php;
            proxy_set_header Host $http_hosts;
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16

# 案例2-Jinja2管理Keepalived

  • ansible使用jinja2的if判断表达式渲染出keepalived的Master和Slave的配置文件。
  1. 使用playbook推送keeplaived配置文件

    [root@manager playbook]# cat keepalived.yml
    - hosts: lb
      tasks:
        - name: Copy template Keepalived Configure
          template: src=./keepalived.j2 dest=/etc/keepalived/keepalived.conf
          notify: Restart Keepalived Server
    
      handlers:
        - name: Restart Keepalived Server
          service: name=keepalived state=restarted
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
  2. 准备keepalived.j2配置文件

    [root@manager playbook]# cat keepalived.j2
    global_defs {
        router_id {{ ansible_fqdn }}
    }
    vrrp_instance VI_1 {
    {% if ansible_fqdn == 'lb01' %}
    #如果主机名为lb01则使用如下配置
        state MASTER
        priority 150
    {% elif ansible_fqdn == 'lb02' %}
    #如果主机名为lb02则使用如下配置
        state Backup
        priority 100
    {% endif %}
        #相同配置
        interface eth0
        virtual_router_id 51
        advert_int 1
        authentication {
            auth_type PASS
            auth_pass 1111
        }
        virtual_ipaddress {
            172.16.1.3
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
  3. 执行playbook

    [root@manager playbook]# ansible-playbook keepalived.yml
    PLAY [lb] ********************************************************************
    
    TASK [Copy template Keepalived Configure] *************************************************
    changed: [10.0.0.5]
    changed: [10.0.0.6]
    
    RUNNING HANDLER [Reload Keepalived Server] ************************************************
    changed: [10.0.0.5]
    changed: [10.0.0.6]
    
    PLAY RECAP ***************************************************************************
    10.0.0.5                  : ok=2    changed=2    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    10.0.0.6                  : ok=2    changed=2    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
  4. 检查lb01 Master的keepalived配置文件

    [root@lb01 ~]# cat /etc/keepalived/keepalived.conf
    global_defs {
        router_id lb01
    }
    vrrp_instance VI_1 {
    #如果主机名为lb01则使用如下配置
        state MASTER
        priority 150
        #相同配置
        interface eth0
        virtual_router_id 51
        advert_int 1
        authentication {
            auth_type PASS
            auth_pass 1111
        }
        virtual_ipaddress {
            172.16.1.3
        }
    }
    
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
  5. 检查lb02 Backup的keepalived配置文件

    [root@lb02 ~]# cat /etc/keepalived/keepalived.conf
    global_defs {
        router_id lb02
    }
    vrrp_instance VI_1 {
    #如果主机名为lb02则使用如下配置
        state Backup
        priority 150
        #相同配置
        interface eth0
        virtual_router_id 51
        advert_int 1
        authentication {
            auth_type PASS
            auth_pass 1111
        }
        virtual_ipaddress {
            172.16.1.3
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20

# Ansible Roles

# Roles基本概述

使用Roles组织playbook才是最好的方式。

Roles基于一个已知的文件结构,去自动的加载vars、tasks以及handlers以便playbook更好的调用。

roles相比playbook的结构更加的清晰有层次,但roles显然要比playbook更加复杂难理解!

比如:我们无论安装什么软件都会安装时间同步服务,那么每个playbook都要编写时间同步服务的task。此时我们可以将时间同步服务task任务编写好,等到需要使用的时候进行调用就行了。

# Roles目录结构

roles官方目录结构,必须按如下方式定义。在每个目录中必须有main.yml文件,这些属于强制要求。

[root@manager ~]# cd /etc/ansible/roles
[root@manager roles]# mkdir {nfs,rsync,web}/{vars,tasks,templates,handlers,files,meta} -p
[root@manager roles]# tree
[root@manager roles]# tree
.
├── nfs #角色名称
│   ├── files #存放文件
│   ├── handlers #触发任务
│   ├── meta #依赖关系
│   ├── tasks #具体任务
│   ├── templates #模板文件
│   └── vars #定义变量
1
2
3
4
5
6
7
8
9
10
11
12

# Roles依赖关系

  • roles允许在使用时自动引入其他role,role依赖关系存储在meta/main.yml文件中。

    • 例如: 安装wordpress项目时:
      • 需要先确保nginx与php-fpm的role都能正常运行
      • 然后在wordpress的role中定义,依赖关系
      • 依赖的role有nginx以及php-fpm
    #wordpress依赖nginx与php-fpm的role
    [root@manager playbook]# cat /root/roles/wordpress/meta/main.yml
    dependencies:
      - { role: nginx }
      - { role: php-fpm }
    
    1
    2
    3
    4
    5

wordpress的role会先执行nginx、php-fpm的role,最后在执行wordpress本身

# Roles案例实战

  • Roles三步走:
    • 创建roles目录结构,手动创建或使用ansible-galaxy init testroles
    • 编写roles的功能,也就是tasks
    • 最后playbook引用roles编写好的tasks

# 案例-Roles部署NFS

  1. 目录结构如下

    [root@manager roles]# tree /etc/ansible/roles
    ├── group_vars
    │   └── all
    ├── hosts
    ├── nfs
    │   ├── files
    │   ├── handlers
    │   │   └── main.yml
    │   ├── meta
    │   ├── tasks
    │   │   └── main.yml
    │   └── templates
    │       └── exports.j2
    └── site.yml
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
  2. 定义roles主机清单

    [root@manager roles]# cat /etc/ansible/roles/hosts
    [nfs]
    10.0.0.12
    
    1
    2
    3
  3. 查看nfs角色的tasks任务

    [root@manager roles]# cat /etc/ansible/roles/nfs/tasks/main.yml
    - name: Installed NFS Server
      yum:
        name: nfs-utils
        state: present
    
    - name: Configure NFS Server
      template:
        src: exports.j2
        dest: /etc/exports
      notify: Restart NFS Server
    
    - name: Init NFS Server
      file:
        path: "{{ nfs_share_directory }}"
        state: directory
        owner: "{{ user }}"
        group: "{{ group }}"
    
    - name: Systemd NFS Server
      systemd:
        name: nfs
        state: started
        enabled: yes
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
  4. 查看nfs角色的handlers

    [root@manager roles]# cat /etc/ansible/roles/nfs/handlers/main.yml
    - name: Restart NFS Server
      systemd:
        name: nfs
        state: restarted
    
    1
    2
    3
    4
    5
  5. 查看nfs角色的files目录

    [root@manager roles]# cat /etc/ansible/roles/nfs/templates/exports.j2
    {{ nfs_share_directory }} {{ nfs_share_ip_pool }}(rw,sync,anonuid={{ user_id }},anongid={{ group_id }})
    
    1
    2
  6. nfs对应的变量定义

    [root@manager roles]# cat /etc/ansible/roles/group_vars/all
    # all
    user: www
    group: www
    # nfs
    nfs_share_directory: /ansible_data
    nfs_share_ip_pool: 10.0.0.0/24
    user_id: 666
    group_id: 666
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
  7. 在playbook中使用role,指定nfs主机组,执行nfs服务的roles

    [root@manager roles]# cat /etc/ansible/roles/site.yml
    - hosts: nfs
      roles:
        - nfs
    
    
    [root@manager roles]# ansible-playbook -i hosts site.yml
    PLAY [nfs] ***************************************************************************
    
    TASK [nfs : Installed NFS Server] ****************************************************
    ok: [10.0.0.12]
    
    TASK [nfs : Configure NFS Server] ****************************************************
    ok: [10.0.0.12]
    
    TASK [nfs : Init NFS Server] *********************************************************
    changed: [10.0.0.12]
    
    TASK [nfs : Systemd NFS Server] ******************************************************
    ok: [10.0.0.12]
    
    PLAY RECAP ***************************************************************************
    10.0.0.12                  : ok=4    changed=1    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0
    
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
#ansible#playbook
Last Updated: 2022/04/01, 21:59:48
Ansible Task Control
python调用ansible模块

← Ansible Task Control python调用ansible模块→

最近更新
01
谷歌云创建GKE集群
07-26
02
ElastiCacheForRedis启用密码
07-26
03
upload-to-gcs
06-29
更多文章>
Theme by Vdoing | Copyright © 2021-2024 Brc | MIT License | 浙ICP备19031881号-4
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式