Ansible 작동 시 조건문과 다른 조건문과 함께 사용하는 방법

다양한 조건에 따라 Ansible 작업을 실행해야 한다면, 당신은 행운아입니다. Ansible의 when 및 다른 조건부를 사용하면 OS를 기반으로 한 조건을 평가하거나 이전 작업에 종속된 작업을 실행할 수 있습니다.

이 튜토리얼에서는 Ansible의 when 및 다른 조건부를 사용하여 작업을 실행하는 방법을 배우게 됩니다. 이를 통해 작업을 실행할 때 문제를 일으키지 않을 수 있습니다.

시작해 봅시다!

사전 요구 사항

이 튜토리얼은 실습 예제로 구성되어 있습니다. 따라하려면 다음 사항이 준비되어 있는지 확인하세요:

  • Ansible 컨트롤러 호스트 – 이 튜토리얼은 Ubuntu 18.04.5 LTS 머신에서 호스트된 Ansible v2.9.24를 사용합니다.
  • A remote computer to run commands.
  • 인벤토리 파일을 설정하고 이미 Ansible 명령 및 플레이북을 실행할 수 있는 하나 이상의 호스트가 구성되어 있어야 합니다. 이 튜토리얼에서는 web이라는 인벤토리 그룹을 사용합니다.

플레이북에서 다중 작업과 함께 Ansible의 when 사용하기

다양한 작업이 플레이북에 있을 때 모두 특정 조건 없이 실행되면 귀찮을 수 있습니다. 여러 작업이 있는 Ansible 플레이북에서 Ansible when 조건을 정의하는 것으로 이 튜토리얼을 시작해 봅시다.

1. Ansible 컨트롤러 호스트에서 터미널을 엽니다.

2. 아래 명령을 실행하여 홈 디렉토리에 디렉토리를 생성하고 원하는 이름으로 지정한 후 해당 디렉토리로 이동합니다.

이 예에서는 디렉토리의 이름을 ansible_when_condition_demo로 지정합니다. 이 디렉토리에는 Ansible 작업 내에서 when 조건을 호출할 Playbook이 포함됩니다.

# ~/ansible_when_condition_demo라는 디렉토리 생성
mkdir ~/ansible_when_condition_demo
# 작업 디렉토리를 ~/ansible_when_condition_demo로 변경
cd ~/ansible_when_condition_demo

3. 선호하는 코드 편집기에서 ~/ansible_when_condition_demo 디렉토리에 YAML 파일을 생성합니다. 이 예에서는 파일 이름을 my_playbook.yml로 지정합니다. 아래 YAML 플레이북 내용을 my_playbook.yml 파일에 복사하여 붙여 넣습니다.

아래 두 작업(Task-1Task-2)에서 when 조건은 각 원격 호스트의 운영 체제를 확인합니다. 그 결과는 각 작업의 ansible_os_family 플레이스홀더 변수로 전달됩니다.

만약 ansible_os_family 플레이스홀더의 값이 RedHat 또는 Debian과 일치하는 경우, Ansible은 Apache를 설치하기 위해 해당 작업 중 하나를 실행합니다.

---
- name: Ansible tasks to work on Ansible When
# Ansible이 실행될 원격 서버 정의
  hosts: web
  remote_user: ubuntu # 원격 호스트를 ubuntu로 사용
  become: true # 고도로 권한이 있는 사용자 (sudo)로 작업 실행
  tasks:

# (작업-1) ansible_os_family == "RedHat"인지 확인하고 해당 조건이 충족되면 원격 노드에 Apache 설치
    - name: Install Apache on CentOS  Server
      yum: name=httpd  state=present
      become: yes
      when: ansible_os_family == "RedHat"

# (작업-2) ansible_os_family == "Debian"인지 확인하고 해당 조건이 충족되면 원격 노드에 Apache 설치
    - name: Install Apache on Ubuntu Server
      apt:name=apache2 state=present
      become: yes
      when: ansible_os_family == "Debian"

4. 이제 아래의 ansible-playbook 명령을 실행하여 플레이북(my_playbook.yml)에 정의된 작업을 기존 인벤토리 파일에 정의된 원격 호스트에서 실행하십시오.

ansible-playbook my_playbook.yml 

아래 스크린샷에서 다음을 확인할 수 있습니다:

  • 첫 번째 TASK는 변경 사항이 필요하지 않음을 나타내는 OK 상태를 반환했습니다.
  • 두 번째 TASKskipping 상태를 반환했습니다. 조건이 충족되지 않으면 작업이 건너뛰어집니다.
  • 세 번째 TASKchanged 상태를 반환했습니다. 이는 원격 호스트가 올바른 상태가 아니었고(Apache가 없음), Apache를 설치하기 위해 수정되었음을 나타냅니다.
Invoking the ansible-playbook using ansible-playbook command

5. 좋아하는 SSH 클라이언트를 사용하여 Ansible 플레이북의 대상이 된 원격 호스트에 SSH 세션을 열어 Apache가 설치되어 실행 중인지 확인합니다.

6. 마지막으로 아래의 service 명령을 실행하여 원격 호스트에서 Apache가 설치되었는지 확인합니다 (status apache2)

service status apache2

아래에서 볼 수 있듯이 원격 머신에 Apache 서비스가 설치되었습니다.

Verifying the Apache service on the remote node

Ansible when 및 루프 사용

이전에 Ansible 작업을 특정 매개변수에 대한 Ansible when에 따라 실행했습니다. 그러나 목록에 정의된 여러 매개변수를 사용하여 조건을 확인해야 할 수 있습니다. 그렇다면 작업에 loop를 추가해 보세요.

이전에 만든 my_playbook.yml 파일을 엽니다 (“플레이북에서 Ansible when와 함께 작업”의 세 번째 단계). my_playbook.yml 파일의 내용을 아래의 코드로 바꿉니다.

코드의 작업 (Task-1)은 loop를 실행하고 when 조건이 항목 값이 5보다 큰지 확인하고 결과를 반환합니다.

---
- name: Ansible tasks to work on Ansible When
# Ansible이 실행될 원격 서버 정의
  hosts: web
  remote_user: ubuntu   # 원격 호스트로 ubuntu 사용
  become: true
  tasks:
  # (작업 -1) 항목 값이 5보다 큰지 확인
    - name: Run with items greater than 5
      ansible.builtin.command: echo {{ item }}
      loop: [ 0, 2, 4, 6, 8, 10 ]
      when: item > 5*

이제 이전과 같이 플레이북을 실행하려면 아래 명령을 실행하세요.

 ansible-playbook my_playbook.yml

다음은 조건이 거짓일 때 skipping 상태와 조건이 참일 때 changed 상태가 반환된 작업입니다.

Checking the when condition for multiple parameters

Ansible when 및 Ansible facts를 사용한 작업

여러 조건을 추가하여 작업을 실행하려면 Ansible factswhen 조건 내에서 어떻게 활용하는지 배워보세요. Ansible facts를 사용하면 OS, IP 주소, 연결된 파일 시스템과 같은 수집된 사실을 기반으로 작업을 실행하기 위한 조건문을 추가할 수 있습니다.

my_playbook.yml 파일의 내용을 아래 코드로 교체하세요.

아래 코드에서 Task-1Task-2 모두 아래 조건 중 하나가 참일 때만 실행됩니다:

  • distributiondistribtion_major_version이 모두 참 값을 반환한 경우.
  • os_family 값이 CentOS와 동일한 경우.
---
- name: Ansible When Single task example
  hosts: web
  remote_user: ubuntu
  become: true
  tasks:
# (Task-1): distribution이 CentOS이고 major Version이 6인 경우 원격 노드를 종료합니다.
    - name: Shut down CentOS 6 systems
      ansible.builtin.command: /sbin/shutdown -t now
      when:
        - ansible_facts['distribution'] == "CentOS"
        - ansible_facts['distribution_major_version'] == "6"
# (Task-2): os_family가 CentOS인 경우 원격 노드를 종료합니다.
    - name: Shut down CentOS flavored systems
      ansible.builtin.command: /sbin/shutdown -t now
      when: ansible_facts['os_family'] == "CentOS"

이전에 한 것처럼 아래 명령어로 플레이북을 실행하세요.

ansible-playbook my_playbook.yml

아래에서 알 수 있듯이 두 작업 모두 skipping 상태를 표시하며 Ubuntu에 있을 때만 작업이 실행됩니다.

Executing the ansible-playbook with Ansible facts in Ansible when

작업 중 Ansible when을 사용하여 등록된 값에 기반한 작업

때로는 플레이북에서 이전 작업의 결과에 따라 작업을 실행하거나 건너뛰고 싶을 때가 있습니다. 예를 들어 이전 작업의 업그레이드 후에 서비스를 구성하고 싶을 수 있습니다. 이 경우 등록된 변수를 사용합니다. 등록된 변수를 사용하면 이전 작업의 결과를 변수로 등록하고 다음 작업에서 입력으로 사용할 수 있습니다.

1. /home/ubuntu/hello라는 빈 디렉토리를 만듭니다.

2. my_playbook.yml 파일의 내용을 다음 코드로 바꿉니다. 이 코드는 다음을 수행합니다:

첫 번째 작업 (Task-1)은 /etc/hosts 디렉토리의 내용(파일 및 하위 디렉토리)을 메모리에 나열하고 그 결과를 register 명령을 통해 contents1 변수에 저장합니다.

두 번째 작업 (Task-2)은 /home/ubuntu/hello 디렉토리의 내용(현재 비어 있음)을 메모리에 나열하고 그 목록을 contents2 변수에 저장합니다.

세 번째 작업 (Task-3)은 contents1 또는 contents2 변수의 등록된 결과 중 하나가 비어 있다면 “디렉토리가 비어 있음” 메시지를 확인하고 출력합니다.

contents1contents2 변수의 stdout 속성은 작업 명령 실행 결과에서 저장된 셸 출력입니다.

---
- name: Ansible When Single task example
  hosts: web
  remote_user: ubuntu
  become: true
  tasks:
# (작업-1): /etc/hosts 디렉토리의 디렉토리 내용 나열
      - name: List contents of directory and Store in content1
        ansible.builtin.command: ls /etc/hosts
        register: contents1
# (작업-2): /home/ubuntu/hello 디렉토리의 디렉토리 내용 나열
      - name: List contents of directory and Store in content2
        ansible.builtin.command: ls /home/ubuntu/hello
        register: contents2
# (작업-3): 디렉토리가 비어 있는 경우 디렉토리 표시
# /etc/hosts 또는 /home/ubuntu/hello 중 하나라도 비어 있는 디렉토리인 경우
      - name: Check contents for emptiness for content1 or content2
        ansible.builtin.debug:
          msg: "Directory is empty"
        when: contents1.stdout == "" or contents2.stdout == ""

3. 마지막으로, 아래의 ansible-playbook 명령을 사용하여 플레이북을 실행합니다.

ansible-playbook my_playbook.yml

아래에서 볼 수 있듯이, contents2 변수에 대한 등록된 결과가 비어 있기 때문에 세 번째 작업에서는 디렉토리가 비어 있음 메시지를 반환합니다.

Running the Ansible playbook for Ansible when based on registered values

Ansible roles에서 Ansible when 작업하기

이 마지막 예제에서는 Ansible roles 내에서 Ansible when이 작동하는 방법을 배우게 됩니다. Ansible roles을 사용하면 표준 구성을 재사용하여 배포를 빠르게 할 수 있습니다. Ansible when 조건이 true인 경우에만 작업이 Ansible roles을 호출하는 방법에 대해 자세히 알아보세요.

1. 아래 명령어를 실행하여 홈 디렉터리에 ~/ansible_role_when_demo라는 디렉터리를 만들고 작업 디렉터리로 변경하세요. ~/ansible_role_when_demo 디렉터리에는 이 예제의 데모 파일이 저장됩니다.

# 홈 디렉터리에 ~/ansible_role_when_demo 디렉터리를 만듭니다
mkdir ~/ansible_role_when_demo
# ~/ansible_role_when_demo 디렉터리로 변경합니다
cd ~/ansible_role_when_demo

2. 다음으로, 아래 명령어를 실행하여 ~/ansible_role_when_demo/roles~/ansible_role_when_demo/roles/java/tasks 디렉터리를 만드세요.

각 디렉터리에는 다음과 같은 내용이 포함됩니다:

  • ~/ansible_role_when_demo/roles 디렉터리에는 배포할 역할이 포함됩니다.

기본적으로 Ansible은 플레이북이 있는 디렉터리 내의 roles/ 디렉터리 또는 /etc/ansible/roles에서 역할을 찾습니다. 다른 경로에 역할을 저장하려면 플레이북에서 - role: 매개변수를 사용하여 경로를 선언하세요.

  • ~/ansible_role_when_demo/roles/java/tasks 폴더에는 역할을 배포하는 데 필요한 main.yml 파일이 포함됩니다.
# ~/ansible_role_when_demo 디렉터리 내에 roles 디렉터리 생성
mkdir -p roles
# 작업 디렉터리를 ~/ansible_role_when_demo/roles로 변경
cd roles 
# 부모 디렉터리(-p 옵션 사용)인 java 및 tasks 하위 디렉터리 생성
mkdir -p java/tasks

이제 main.yml 파일을 ~/ansible_role_when_demo/roles/java/tasks 디렉터리에 생성한 후, 아래의 플레이북 코드를 main.yml 파일에 복사하여 붙여넣으세요.

이 플레이북은 apt 모듈을 사용하여 원격 노드에 Java를 설치합니다.

---
# Java (Open Jdk) 설치
- name: Install Java 1.8
  apt: name=openjdk-8-jdk

4. 원하는 이름으로 다른 YAML 파일을 생성하고 아래 코드를 복사/붙여넣으세요. 이 예에서 파일은 ~/ansible_role_when_demo/java-setup.yml로 지정되어 있습니다.

아래 코드는 Ansible role (java)를 원격 사용자 (ubuntu)에게 배포합니다. 이 배포는 원격 사용자가 Debian OS에서만 관리자 액세스를 갖는 경우에만 수행됩니다.

- name: Java Installation playbook
# 패키지가 배포될 원격 서버 정의
  hosts: myserver
  remote_user: ubuntu   # 원격 사용자를 ubuntu로 설정
  become: true
  tasks:  
  roles:
     - role: java
       # 원격 사용자가 Debian OS에 있는 경우에만 작업 실행
       when: ansible_facts['os_family'] == 'Debian'

5. tree 명령을 실행하여 ~/ansible_role_when_demo 디렉토리에 필요한 모든 폴더 및 파일이 있는지 확인하십시오.

Verifying all of the required folders in the ~/ansible_role_when_demo directory

6. 마지막으로 다음과 같은 ansible-playbook 명령으로 플레이북을 실행하십시오. ansible-playbook java-setup.yml

ansible-playbook java-setup.yml

아래에서 해당 작업이 changed 상태를 반환했으므로 원격 노드에 Debian OS가 있음을 나타냅니다. Ansible 플레이북을 Ansible when과 함께 실행하는 방법

Running the Ansible playbook using Ansible when with Ansible roles

결론

이 자습서에서는 Ansible when 및 기타 조건문 사용 방법을 배웠습니다. 또한 Ansible when 조건을 적용하는 방법, 기본 작업을 수행하는 Ansible facts 및 Ansible roles을 배웠습니다.

이 새로운 지식을 기반으로 어떻게 발전시키겠습니까? 아마도 Ansible 템플릿을 사용하여 Ansible when 조건을 적용하면 여러 서버의 구성을 시간을 절약할 수 있을 것입니다.

Source:
https://adamtheautomator.com/ansible-when/