Instalación de varios paquetes en varios sistemas operativos con Ansible

Instalación de varios paquetes en varios sistemas operativos con Ansible

Tengo un host con 2 servidores: uno tiene CentOS y el otro Ubuntu instalado.

Decidí instalar Apache, nginx y php-fpm en ambos servidores y escribí 3 manuales.

  1. ubuntu.yml (/home/ansible/playbook):
---
- name: Ubuntu Playbook
  hosts: ubun
  become: true
  vars:
   - packages:
     - nginx
     - apache2
     - php-fpm 
  tasks:
   - name: Update apt package
   apt:
   name: "*"
   state: latest
   update_cache: yes
   - name: Install Packages
     apt:
       pkg: "{{ packages }}"
       state: latest
       update_cache: yes
   - name: Apache Service Start
     service:
       name: nginx
       state: restarted
       enabled: yes
  1. centos.yml (/home/ansible/playbook):
---
- name: CentOS Playbook
  hosts: cent
  become: true
  vars:
   packages:
   - epel-release
   - httpd
   - nginx
   - php-fpm
  tasks:
   - name: Update yum package
     yum:
       name: "*"
       state: latest
       update_cache: yes
   - name: Install Packages
     yum:
       name: "{{ packages }}"
       state: latest
       update_cache: yes
   - name: Apache Service Start
     service:
       name: nginx
       state: restarted
       enabled: yes
  1. base.yml (/home/ansible/playbook):
---
- name: Base Playbook
  hosts: aws
  become: true
  tasks:
    - name: Performing Tasks for CentOS
      when: ansible_facts['distribution'] == 'CentOS'
      include_tasks: centos.yml
    - name: Performing Tasks for Ubuntu
      when: ansible_facts['distribution'] == 'Ubuntu'
      include_tasks: ubuntu.yml

Mis 3 grupos de Ansible son:

  • [aws] que contiene tanto el servidor

  • [cent] que contiene el servidor CentOS

  • [ubun] que contiene el servidor Ubuntu

Intenté ejecutar en seco centos.ymly ubuntu.ymlpor separado y funcionó, pero cuando intento ejecutar en seco base.ymlaparece el siguiente error:

    FAILED! => {"reason": "unexpected parameter type in action: <class 'ansible.parsing.yaml.objects.AnsibleSequence'>\n\nThe error appears to be in '/home/ansible/playbook/centos.yml': line 2, column 3, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n---\n- name: CentOS Playbook\n  ^ here\n"}

    FAILED! => {"reason": "unexpected parameter type in action: <class 'ansible.parsing.yaml.objects.AnsibleSequence'>\n\nThe error appears to be in '/home/ansible/playbook/ubuntu.yml': line 2, column 3, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n---\n- name: Ubuntu Playbook\n  ^ here\n"}

Ya intenté reemplazar import_taskscon include_taskspero aparece el mismo error.

Respuesta1

Mi solución es fusionarlos en una sola obra, ya que hacen lo mismo.

---
- name: php-fpm play
  hosts: aws
  become: true
  vars:
  - repo:
      Debian:
      - apt # already installed, but need something here
      RedHat:
      - epel-release
  - packages:
      Debian:
      - apache2
      #- nginx # cannot have 2 listening on port 80
      - php-fpm
      RedHat:
      - httpd
      #- nginx
      - php-fpm
  - services:
      Debian: apache2
      RedHat: httpd

  tasks:
     # TODO move update * task to different play

   - name: Install repo
     # Seperate package transaction for EPEL
     # so it is available in the next task
     package:
       name: "{{ repo[ansible_os_family] }}"

   - name: Install Web Server Packages
     # Keyed by OS family fact to also support RHEL and Debian
     package:
       name: "{{ packages[ansible_os_family] }}"
       state: latest

   - name: Web Service Start
     service:
       name: "{{ services[ansible_os_family] }}"
       state: restarted
       enabled: yes

No se pueden tener varios servidores escuchando en los puertos 80 y 443. Comenté nginx, ya que una tarea estaba mal etiquetada como "Inicio del servicio Apache". Si desea que uno de estos actúe como proxy para el otro o algo así, deberá implementar un archivo de configuración para cambiar los puertos.

Usó la package:acción que delega al administrador de paquetes real. Permite que una tarea de instalación de paquetes se ejecute en diferentes sistemas operativos. No puedo hacerlo update_cachede esa manera, pero yum no lo necesita al agregar repositorios como lo hace apt.

La estructura de Vars depende de los valores específicos de la familia del sistema operativo. Esto permite indexar los nombres de paquetes y servicios por hechos. Familia de sistemas operativos, por lo que también funciona en RHEL y Debian además de CentOS y Ubuntu.

La sangría estaba mal. Los parámetros de los módulos deben tener una sangría un nivel por debajo de las directivas de nivel de tarea como name:.

No se puede include_tasksreproducir una obra completa, eso solo funciona con import_playbook. include_tasksEs más fácil cuando tienes roles que tienen un directorio de tareas para dichos archivos. (Las tareas a nivel de juego existen, pero estoy a favor de que los roles lo hagan todo).


Todavía hay más trabajo para que esto sea útil.

Cuando necesita usar templatepara instalar la configuración, EL coloca las configuraciones en /etc/httpd/, mientras que Debian está en /etc/apache2/.

Muchas funciones de servidor web son de código abierto, puedes consultarlas si quieres ideas. ControlarGalaxia.

Considere trasladar sus tareas a roles, permita la reutilización.

Respuesta2

Es mejor si tomas un rol como ejemplo, aquí tienes el código arreglado:

---

- hosts: aws
  remote_user: myuser
  become: true
  tasks:
  - name: Performing Tasks for CentOS
    include_tasks: centos.yml
    when: ansible_facts['distribution'] == 'CentOS'
  - name: Performing Tasks for Ubuntu
    include_tasks: ubuntu.yml
    when: ansible_facts['distribution'] == 'Ubuntu'

Tareas de centos.yml:

---

- name: installing httpd
  yum: pkg=httpd state=present

Tareas de ubuntu.yml:


- name: installing apache2
  apt: pkg=apache2 state=present

En los archivos de tareas, solo necesita las tareas, sin hosts, tareas, etc.

información relacionada