51.Ansible-字典循环-roles角色编排

一、loop字典循环

1、启动多个服务

在 Ansible 中,可以使用 loop 循环来启动多个服务。这里会用到 item 变量,它是在循环过程中依次代表列表中的每个元素。一次循环赋值一次变量

示例代码如下:

- name: 启动多个服务
  hosts: web
  tasks:
    - name: 启动服务
      systemd:
        name: "{{ item }}"
        state: started
      loop:
        - service1
        - service2
        - service3

在上述代码中,loop 列出了需要启动的服务名称列表,item 变量在每次循环中依次取值为 service1service2service3,从而实现启动多个服务的目的。

2、创建多个文件

通过字典循环来创建多个文件,并且可以根据不同的子集属性设置不同的权限。一次循环赋值一次变量

示例代码如下:

[root@Ansible ~/ansible]# cat var.yml 
- hosts: backup 
  tasks:

    - name: create file
      file: 
        path: /root/{{ item.filename }}
        owner: "{{ item.owner }}"
        group: "{{ item.group }}"
        mode: "{{ item.mode }}"
        state: touch
      loop: 
        - { filename: "123", owner: "www", group: "www", mode: "0600"}
        - { filename: "abd", owner: "root", group: "root", mode: "0644" }

在这个例子中,loop 循环遍历一个包含文件名和权限的字典列表。item.filename 用于指定文件的名称,item.mode 用于设置文件的权限。

3、拷贝多个文件

可以使用 loop 循环来实现拷贝多个文件的操作。一次循环赋值一次变量

示例代码如下:

- name: 拷贝多个文件
  hosts: your_hosts
  tasks:
    - name: 拷贝文件
      copy:
        src: "{{ item.src }}"
        dst: "{{ item.dst }}"
      loop:
        - { src: "/source/path/file1.txt", dst: "/root/path/file1.txt" }
        - { src: "/source/path/file2.txt", dst: "/opt/path/file2.txt" }

在这个任务中,loop 循环遍历一个包含源文件路径和目标文件路径的字典列表。item.src 代表源文件路径,item.dst 代表目标文件路径,从而实现多个文件的拷贝。

二、标签(Tags)的使用

标签(Tags)可以用来对任务进行分类和筛选,方便在执行 Playbook 时只运行特定标签的任务。

列出标签

可以使用以下命令列出 Playbook 中的所有标签:

[root@Ansible ~/ansible]# ansible-playbook  var.yml  --list-tags
playbook: var.yml

  play #1 (backup): backup    TAGS: []
      TASK TAGS: [abd]

运行指定标签的任务

使用 -t 选项来指定运行带有特定标签的任务:

  • 给某个任务打tag,单独让它执行
  • 可以给多个任务打相同的tag
ansible-playbook nfs.yml -t hehe

在 Playbook 中,给任务添加标签的方式如下:

  • 测试带标签运行,和不带标签运行的结果
- hosts: backup
  tasks:
    - name: copy file
      copy:
        src: "{{ item.src }}"
        dest: "{{ item.dst }}"

      loop:
        - { src: 12 , dst: /root/ }
        - { src: 34 , dst: /opt/ }
      tags: abd

    - name: l
      command: ls -l /root/
      register:  ll

    - name: ls
      debug:
        msg: "{{ ll.stdout_lines }}"

三、使用 include 组合多个任务

include 可以将多个任务组合在一起,方便管理和复用。同时,changed_when: false 可以用来控制任务是否被标记为已改变。

示例代码如下:

- name: 主Playbook
  hosts: your_hosts
  tasks:
    - name: 包含其他任务
      include: tasks.yml
      changed_when: false

tasks.yml 文件中,可以定义多个任务:

- name: 任务1
  debug:
    msg: "这是任务1"
- name: 任务2
  debug:
    msg: "这是任务2"

在上述示例中,主 Playbook 通过 include 引入了 tasks.yml 文件中的所有任务,并且通过 changed_when: false 确保这些任务不会被标记为已改变(即使它们实际上执行了操作)。这在某些情况下很有用,例如当任务只是查询信息而不改变系统状态,但 Ansible 可能会误判为改变时。

四、include将多个tasks组合

一、操作目的

通过 Ansible 的 include 功能,将多个任务文件组合在一起,根据主机名条件执行不同的任务。

通过 include_tasks 指令,我们可以方便地将多个任务文件进行组合,并根据不同的条件在不同的主机上执行相应的任务,这提高了 Ansible 任务编排的灵活性和可维护性。在实际应用中,可以根据项目的具体需求,进一步扩展和优化这种任务组合方式。

二、具体操作步骤

(一)准备两个任务文件

  1. 创建 vars.yml 文件
   [root@ansible haoshuaicong]# cat vars.yml
   - hosts: all
     tasks:
       - include_tasks: web01.yml 
         when: ansible_hostname == "web01"
       - include_tasks: backup.yml 
         when: ansible_hostname == "backup01"

这个文件定义了任务的基本框架,其中包含了根据主机名条件来包含其他任务文件的逻辑。

  1. 编辑 web01.yml 具体任务内容
   [root@ansible haoshuaicong]# cat web01.yml 
   - name: create nginx.txt
     file:
       path: /root/nginx.txt
       state: touch

该任务的作用是在 /root 目录下创建一个名为 nginx.txt 的空文件。

  1. 编辑 backup.yml 具体任务内容
   [root@ansible haoshuaicong]# cat backup.yml 
   - name: create file
     file:
       path: /root/rsync.txt
       state: touch

此任务是在 /root 目录下创建一个名为 rsync.txt 的空文件。

(二)整合任务文件

创建 all.yml 文件,将前面两个文件整合起来:

  • 使用all全部主机,when判断那个文件需要对应的主机
  • 总的来说,就是all.yml调用其他文件,然后when判断对应主机执行对应任务
[root@ansible haoshuaicong]# vim all.yml
- hosts: all
  - include_tasks: web.yml
    when: ansible_hostname == "web02"
  - include_tasks: mysql.yml
    when: ansible_hostname == "backup"

五、Jinja2 模版

一、Jinja2 模版基础

在 Ansible 中,Jinja2 模版用于动态生成配置文件或其他文本内容。使用 {{ EXPR }} 来输出变量值,这些变量可以是自定义变量,也可以是 Ansible facts(系统事实信息)。Jinja2 模版通常在文件中使用。

二、准备变量文件示例

(一)创建 motd.j2 文件

[root@ansible haoshuaicong]# cat motd.j2
Welcome to {{ ansible_hostname }}
This system total mem is : {{ ansible_memtotal_mb }} MB
This system ip address: {{ ansible_default_ipv4.address }}

此文件通过 Jinja2 模版语法,使用 Ansible facts 变量 ansible_hostname(主机名)、ansible_memtotal_mb(系统总内存,单位为 MB)和 ansible_default_ipv4.address(系统默认的 IPv4 地址)来生成欢迎信息。

(二)将 motd.j2 拷贝到目标主机

  • 必须使用 template模块才能识别变量
[root@ansible haoshuaicong]# cat cp.yml 
- hosts: web01
  tasks:
    - name: copy motd
      template:
        src: motd.j2
        dest: /root/motd.txt
  • 查看web01的/root/motd.txt文件是否识别变量
[root@Ansible ~/ansible]# cat vars.yml
- hosts: backup 
  tasks: 

    - name: cat 
      command: cat /root/motd.txt
      register: cat

    - name: cat2
      debug:
        msg: "{{ cat.stdout_lines }}"


[root@Ansible ~/ansible]# ansible-playbook  vars.yml 
TASK [cat2] ***************************************************************************************************************************
ok: [backup] => {
    "msg": [
        "Welcome to backup01",
        "This system total mem is : 948 MB",
        "This system ip address: 10.0.0.41"
    ]
}

PLAY RECAP ****************************************************************************************************************************
backup                     : ok=4    changed=1    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0   

[root@Ansible ~/ansible]# 

cp.yml 任务文件中,使用 template 模块将 motd.j2 模版文件拷贝到目标主机的 /root/motd.txt 路径下。在拷贝过程中,Ansible 会根据目标主机的实际情况替换模版中的变量。

三、使用 for 循环生成配置文件案例

(一)创建 nginx.conf 配置文件模版

[root@ansible haoshuaicong]# cat nginx.conf 
upstream {{ server_name }} {
{% for n in range(7,9) %}
        server 172.16.1.{{ n }}:{{ up_port }};
{% endfor %}
}

server {
        listen 80;
        server_name {{ server_name }};

        location / {
                root /code;
                index index.html;
                proxy_pass http://{{ server_name }};
                proxy_set_header Host $http_host;
        }
}

这个 nginx.conf 模版文件中,使用 Jinja2 的 for 循环语法动态生成 upstream 部分的服务器列表。range(7, 9) 表示生成从 7 到 8 的数字序列,每个数字将被用于构建服务器地址。同时,还使用了自定义变量 server_nameup_port

(二)调用 nginx.conf 配置文件

  • 必须使用template模块,使用copy模块不识别
[root@ansible haoshuaicong]# cat cp.yml 
- hosts: lnmp
  vars:
    - server_name: www.wp.com
    - up_port: 80

  tasks:
    - name: copy motd
      template:
        src: nginx.conf
        dest: /root/

cp.yml 文件中,通过 vars 部分定义了 server_nameup_port 变量的值。然后使用 template 模块将 nginx.conf 模版文件拷贝到目标主机的 /root 目录下。生成后的 nginx.conf 文件内容如下:

[root@web01 ~]# cat nginx.conf 
upstream www.wp.com {
        server 172.16.1.7:80;
        server 172.16.1.8:80;
}

server {
        listen 80;
        server_name www.wp.com;

        location / {
                root /code;
                index index.html;
                proxy_pass http://www.wp.com;
                proxy_set_header Host $http_host;
        }
}

可以看到,模版中的变量和循环部分都被正确替换和展开。

四、使用 Jinja2 生成 keepalived 配置文件

(一)创建 keep.j2 配置文件模版

[root@ansible haoshuaicong]# cat keep.j2 
global_defs {
    router_id {{ ansible_fqdn }}
}

vrrp_instance VI_1 {
{% if ansible_fqdn == "web01" %}
    state MASTER
    priority 150
{% else %}
    state BACKUP
    priority 100
{% endif %}

    interface eth0
    virtual_router_id 50
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 1111
    }
    virtual_ipaddress {         
        10.0.0.3
    }
}

keep.j2 模版文件中,使用 Jinja2 的 if - else 条件语句根据 ansible_fqdn(主机的完全限定域名)来动态生成 vrrp_instance 的状态和优先级。如果主机的 ansible_fqdnweb01,则状态为 MASTER,优先级为 150;否则为 BACKUP,优先级为 100。

(二)将 keep.j2 配置文件拷贝到目标主机

[root@ansible haoshuaicong]# cat cp.yml 
- hosts: lnmp
  vars:
    - server_name: www.wp.com
    - up_port: 80

  tasks:
    - name: copy motd
      template:
        src: keep.j2
        dest: /root/

同样在 cp.yml 文件中,使用 template 模块将 keep.j2 模版文件拷贝到目标主机的 /root 目录下,以生成符合不同主机条件的 keepalived 配置文件。

五、总结

通过以上示例,可以看到 Jinja2 模版在 Ansible 中强大的动态配置生成能力。通过结合变量、循环和条件语句,可以根据不同的主机环境和需求,灵活地生成各种配置文件,提高了自动化配置管理的效率和灵活性。

六、Jinja2 模版重构rsync

(一)创建 rsyncd.conf.j2 配置文件模版

[root@ansible ansible]# cat rsyncd.conf.j2 
uid = {{ user }}
gid = {{ user }}
port = {{ rsync_port }}
fake super = yes
use chroot = no
max connections = 200
timeout = 600
ignore errors
read only = false
list = false
auth users = rsync_backup
secrets file = /etc/rsync.passwd
log file = /var/log/rsyncd.log
#####################################

[backup]

path = {{ rs_dir }}

(二)使用playbook的jinja2重构rsync

[root@ansible ansible]# cat rs.yml
- hosts: backup
  vars:
    - user: www
    - rsync_port: 873
    - rs_dir: /backup
  tasks:
    - name: Install Rsync Server
      yum:
        name: rsync
        state: present

    - name: Configure Rsync Server
      template:
        src: "{{ item.src }}"
        dest: "{{ item.dest }}"
        mode: "{{ item.mode }}"
      loop:
        - { src: rsyncd.conf.j2, dest: /etc/rsyncd.conf,mode: '0644' }
        - { src: rsync.passwd, dest: /etc/,mode: '0600' }
      notify: Restart Rsync Server

    - name: Create "{{ user }}" group
      group:
        name: "{{ user }}"
        gid: 666

    - name: Create "{{ user }}" user
      user:
        name: "{{ user }}"
        uid: 666
        group: "{{ user }}"
        shell: /sbin/nologin
        create_home: false

    - name: Create "{{ rs_dir }}"
      file:
        path: "{{ rs_dir }}"
        state: directory
        owner: "{{ user }}"
        group: "{{ user }}"

    - name: Start Rsync Server
      systemd:
        name: rsyncd
        state: started
        enabled: yes
  handlers:
    - name: Restart Rsync Server
      systemd:
        name: rsyncd
        state: restarted

七、roles角色

一、roles 角色优点

  • 复用性强:多个项目能共用同一角色配置相同服务,团队成员也可共享,减少重复工作。
  • 结构清晰:按特定目录存放任务、变量等文件,逻辑分明,查找和修改文件轻松。
  • 管理方便:可将复杂任务拆分成小任务块,不同角色按序执行,还能在不同场景复用、组合。
  • 变量灵活:角色有独立变量,避免冲突,还能在调用时覆盖默认值,支持变量继承。
  • 维护简单:需求变化时只改对应角色,不影响其他部分,且利于版本控制,方便回滚 。

总结:就是各个功能模块放到各个目录下。编辑自带的main.yml即可

二、Rsync 服务使用 roles 编排

1.1 创建 rsync 角色

使用 ansible-galaxy init rsync 命令初始化 rsync 角色。

[root@ansible roles]# ansible-galaxy init rsync

1.2 rsync 角色目录结构

  • jinja2带变量的放到templates里面
[root@ansible rsync]# ll
total 0
drwxr-xr-x 2 root root  6 Jan  2 16:38 files
drwxr-xr-x 2 root root 22 Jan  2 16:38 handlers
drwxr-xr-x 2 root root 22 Jan  2 16:38 tasks
drwxr-xr-x 2 root root  6 Jan  2 16:38 templates
drwxr-xr-x 2 root root 22 Jan  2 16:38 vars

1.3 各文件内容

  • tasks/main.yml:包含安装、配置、启动 Rsync 服务以及创建用户和目录等任务。
- name: Install Rsync Server
  yum:
    name: rsync
    state: present

- name: Configure Rsync
  template:
    src: "{{ item.src }}"
    dest: "{{ item.dest }}"
    mode: "{{ item.mode }}"
  loop:
    - { src: rsyncd.conf.j2,dest: /etc/rsyncd.conf,mode: '0644' }
    - { src: rsync.passwd,dest: /etc/,mode: '0600' }
  notify: Restart Rsync Server

- name: Create "{{ user }}" group
  group:
    name: "{{ user }}"
    gid: 666

- name: Create "{{ user }}" user
  user:
    name: "{{ user }}"
    uid: 666
    group: "{{ user }}"
    shell: /sbin/nologin
    create_home: false

- name: Create "{{ rs_dir }}"
  file:
    path: "{{ rs_dir }}"
    state: directory
    owner: "{{ user }}"
    group: "{{ user }}"

- name: Start Rsync Server
  systemd:
    name: rsyncd
    state: started
    enabled: yes
  • vars/main.yml:定义了变量 userrsync_portrs_dir
user: www
rsync_port: 873
rs_dir: /backup
  • handlers/main.yml:定义了重启 Rsync 服务的任务。
- name: Restart Rsync Server
  systemd:
    name: rsyncd
    state: restarted
  • templates/rsyncd.conf.j2:Rsync 服务的配置文件模板。
uid = {{ user }}
gid = {{ user }}
port = {{ rsync_port }}
fake super = yes
use chroot = no
max connections = 200
timeout = 600
ignore errors
read only = false
list = false
auth users = rsync_backup
secrets file = /etc/rsync.passwd
log file = /var/log/rsyncd.log
#####################################

[backup]

path = {{ rs_dir }}

  • templates/rsync.passwd:Rsync 认证密码文件。
rsync_backup:123456

三、NFS 服务使用 roles 重构

2.1 创建 nfs 角色目录

[root@ansible roles]# mkdir nfs
[root@ansible roles]# cd nfs/
[root@ansible nfs]# ls../rsync/
files  handlers  tasks  templates  vars
[root@ansible nfs]# ls../rsync/|xargs mkdir

2.2 nfs 角色目录结构

  • 运行的.yml集合文件要和nfs目录在同一级
[root@ansible nfs]# tree nfs/
nfs/
├── files
├── handlers
│   └── main.yml
├── tasks
│   └── main.yml
├── templates
│   └── exports.j2
└── vars
    └── main.yml

2.3 各文件内容

  • tasks/main.yml:包含安装、配置、启动 NFS 服务以及创建用户和目录等任务。
- name: Install nfs Server
  yum:
    name: nfs-utils
    state: present

- name: Configure nfs Server
  template:
    src: exports.j2
    dest: /etc/exports
  notify: Restart nfs Server

- name: Create "{{ user }}" group
  group:
    name: "{{ user }}"
    gid: 666

- name: Create "{{ user }}" user
  user:
    name: "{{ user }}"
    uid: 666
    group: "{{ user }}"
    shell: /sbin/nologin
    create_home: false

- name: Create "{{ nfs_dir }}"
  file:
    path: "{{ nfs_dir }}"
    state: directory
    owner: "{{ user }}"
    group: "{{ user }}"

- name: Start nfs Server
  systemd:
    name: nfs
    state: started
    enabled: yes
  • vars/main.yml:定义了变量 nfs_dirnfs_ipuser
nfs_dir: /data/wp
nfs_ip: 172.16.1.0/24
user: www
  • templates/exports.j2:NFS 服务的配置文件模板。
{{ nfs_dir }} {{ nfs_ip }}(rw,sync,all_squash,anonuid=666,anongid=666)
  • handlers/main.yml:定义了重启 NFS 服务的任务。
- name: Restart nfs Server
  systemd:
    name: nfs
    state: restarted

2.4 调用 roles

site.yml 文件中调用 rsync 和 nfs 角色。

- hosts: all
  roles:
    - role: rsync
      when: ansible_hostname == "backup"
    - role: nfs
      when: ansible_hostname == "nfs"
暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇