Gom3rye

Ansible- 변수 본문

현대 오토에버 클라우드 스쿨

Ansible- 변수

Gom3rye 2025. 8. 8. 17:40
728x90
반응형

Ansible: 클라우드 구축에 사용하는 인프라 구축 자동화 도구

EC2 ssh경로로 접속할 때는 key 파일의 경로를 설정해두고 써서 비밀번호 입력하지 않아도 된다.

변수와 팩트 사용

변수의 종류와 사용법

그룹 변수

  • 인벤토리에 정의된 호스트 그룹에 적용하는 변수
  • 인벤토리에 선언해야 하고 선언하고자 하는 그룹명과 함께 :vars 라는 문자열을 추가해 변수를 선언
  • 인벤토리 파일 생성(/etc/ansible/hosts)
[web]
tnode1-exp.com
tnode2-exp.com

[db]
tnode3.exp.com

[all:children]
web
db

[all:vars]
user=ansible
  • 유저를 생성하는 플레이북 생성(create-user.yaml)
---
- hosts: all
  tasks:
  - name: Create User {{ user }}
    ansible.builtin.user:
      name: "{{ user }}"
      state: present

→ 플레이북을 실행시키면 에러가 발생하는데 에러 내용을 확인해보면 name에 ansible이 설정된 것을 확인할 수 있다.

  • 에러를 제거하고자 하면 권한 상승을 해주면 된다.
---
- hosts: all
  become: yes
  become_user: root
  tasks:
  - name: Create User {{ user }}
    ansible.builtin.user:
      name: "{{ user }}"
      state: present

호스트 변수

특정 호스트에서만 사용 가능한 변수

호스트 옆에 이름=값 의 형태로 지정한다.

  • 인벤토리 파일 생성(/etc/ansible/hosts)
[web]
tnode1-exp.com
tnode2-exp.com

[db]
tnode3.exp.com **user=ansible1**

[all:children]
web
db

→ /etc/ansible/hosts의 user 변수 지우고 이후 create-user.yaml 파일 실행하면 managed node들에 ansible1 유저 생긴다.

플레이북 변수

플레이북 안에 만드는 변수

  • vars 속성 안에 이름: 값의 형태로 설정한다.
---
- hosts: all
  become: yes
  become_user: root
  vars:
    user: ansible2
  tasks:
  - name: Create User {{ user }}
    ansible.builtin.user:
      name: "{{ user }}"
      state: present

→ 이후 create-user.yaml 파일 실행하면 managed node들에 ansible2 유저 생긴다. (그룹 변수 < 호스트 변수 < 플레이북 변수 (우선순위)

추가 변수

ansible-playbook을 실행할 때 파라미터로 넘겨주는 변수로 가장 우선순위가 높다.

  • playbook을 실행할 때 -e 옵션과 함께 이름=값 의 형태로 설정하면 된다.
# create-user.yaml 파일에
vars:
  user: ansible3
  
로 넣고 
ansible-playbook -e user=ansible4 create-user.yaml
하면 ansible3이 만들어지는게 아니라 ansible4가 만들어진다.

작업 변수

playbook의 태스크 수행 결과를 저장하는 것으로 특정 작업 수행 후 그 결과를 후속 작업에서 사용할 때 주로 이용한다.

  • 클라우드의 시스템에 VM을 생성하는 경우 네트워크나 운영체제 이미지와 같은 가상 자원이 필요하다.
  • 가상 자원을 조회하고 조회된 결과를 가지고 VM을 생성할 때 이러한 작업 변수를 이용한다.
  • register: 변수명 을 입력하면 된다.
  • create-user.yaml 파일 수정
---
- hosts: all
  become: yes
  become_user: root
  tasks:
  - name: Create User {{ user }}
    ansible.builtin.user:
      name: "{{ user }}"
      state: present
    register: result # 변수명이니까 아무거나 써도 된다.

  - ansible.builtin.debug:
      var: result
      
# create-user.yaml 실행
ansible-playbook -e user=gom create-user.yaml
## gom이라는 user는 만들어지고 그 결과를 디버깅해서 보여준다.

Password를 안전하게 보관할 수 있는 Ansible Vault

  • 앤서블을 사용할 때 패스워드나 API 키 등 중요한 데이터에 대한 액세스 권한이 필요할 수 있다.
    • 이런 정보들은 인벤토리 변수나 일반 앤서블 플레이북에 텍스트로 작성할 수 있다.
    • 이 경우 앤서블 파일에 접근 권한이 있는 사용자라면 모두 파일 내용을 볼 수 있게 되는데 이는 보안상의 위험을 야기한다.
    • 앤서블에서는 사용되는 모든 데이터 파일을 암호화하고 암호화된 내용을 해독할 수 있는 Ansible Vault 기능을 제공한다.
    • 파일을 만들 때 ansible-vault create 야믈파일경로 를 이용한다.
  • 실습
    • 패스워드를 저장할 파일 생성: ansible-vault create mysecret.yaml
    • 비밀번호를 2번 입력한 후 키와 값의 형태로 작성
    • 파일의 소유 권한을 확인해보면 소유자만 읽고 쓸 수 있도록 설정되어 있고 cat 명령으로 파일을 열면 암호화된 결과로 내용을 출력한다.
ansible_user: ansible
ansible_password: your_secure_password

ls -al mysecret.yaml
## -rw------- 1 kyla kyla 549 Aug  8 03:17 mysecret.yaml -> 소유자 빼고는 못 보게 되어 있다.

# 원본 확인
ansible-vault view 파일경로
ansivle-vault view mysecret.yaml

  • 기존 텍스트 파일의 내용을 비밀번호로 해서 생성
    • 비밀번호를 저장할 파일을 만들어서 비밀번호 저장 (vault-pass)
      • ansible
    • 암호화 파일 생성: ansible-vault create --vault-pass-file ./vault-pass mysecret1.yaml
    user: ansible
    password: ansible
    

→ 똑같은 값을 가지고 만들더라도 해시값을 이용해서 만들기 때문에 결과가 달라질 수 있다.

  • 기존 파일을 암호화 하는 것도 가능: encrypt 옵션 사용
    • ansible-vault encrypt create-user.yaml
  • 암호된 파일의 내용을 복호화 하는 것도 가능: decrypt 옵션 사용
    • ansible-vault decrypt create-user.yaml --output=create-user-decrypted.yaml
    • cat create-user-decrypted.yaml
  • 비밀번호 변경: ansible-vault rekey 암호화된파일경로
    • ansible-vault rekey mysecret.yaml
  • 암호화된 playbook을 실행할 때는 --vault-id @prompt 옵션과 함께 실행
    • 그냥 실행하면 에러난다.

  • 파일에 암호를 저장해두고 사용하는 것도 가능하다.
    • --vault-password-file=비밀번호파일경로

Facts

관리 호스트에서 자동으로 검색한 변수

  • 플레이, 조건문, 반복문 또는 관리 호스트에서 수집한 값에 의존하는 기타 명령문의 변수처럼 사용 가능한 호스트별 정보가 포함되어 있다.
  • 내용
    • 호스트 이름
    • 커널 버전
    • 네트워크 인터페이스 이름
    • 운영체제 버전
    • CPU 개수
    • 사용 가능한 메모리
    • 스토리지 장치의 크기 및 여유 공간
  • 팩트 사용
    • 팩트는 ansible-facts 라는 변수를 통해 사용할 수 있다.
    • 팩트 출력하기 (fact.yaml)
    ---
    - hosts: itstudy
      tasks:
      - name: Print all facts
        ansible.builtin.debug:
          var: ansible_facts
    
    → OS, python version, dns, processor 등 전부 다 나온다.
    • 특정 팩트만 출력 (specific_fact.yaml)
    ---
    - hosts: itstudy
      tasks:
      - name: Print all facts
        ansible.builtin.debug:
          msg: >
            The Default IP of {{ ansible_facts.fqdn }}
            is {{ ansible_facts.default_ipv4.address }}
    

  • 팩트는 변수로 사용하는 것이 가능하다. (ansible_facts. 대신에 **ansible_**만 써도 된다.)
---
- hosts: itstudy
  tasks:
  - name: Print all facts
    ansible.builtin.debug:
      msg: >
        The Default IP of {{ ansible_fqdn }}
        is {{ ansible_default_ipv4.address }}

제어문 구현

반복문

  • 단순 반복문
    • loop 키워드를 작업에 추가하면 작업을 반복해야 하는 항목의 목록을 값으로 사용한다.
    • 해당하는 값을 사용하려면 item 변수를 이용할 수 있다.
    • playbook 파일 생성(check-services.yaml)
    ---
    - hosts: itstudy
      tasks:
      - name: Check SSH State
        ansible.builtin.service:
          name: ssh
          state: started
      - name: Check rsyslog State
        ansible.builtin.service:
          name: rsyslog
          state: started
    
    • 반복문을 사용하는 것으로 수정(check-services.yaml)
    ---
    - hosts: itstudy
      tasks:
      - name: Check SSH and rsyslog State
        ansible.builtin.service:
          name: "{{ item }}"
          state: started
        loop:
          - ssh
          - rsyslog
    
    • 반복할 내용을 변수로 작성
    ---
    - hosts: itstudy
      vars:
        services:
          - ssh
          - rsyslog
      tasks:
      - name: Check SSH and rsyslog State
        ansible.builtin.service:
          name: "{{ item }}"
          state: started
        loop: "{{ services }}"
    
    • 반복문을 이용한 파일 생성 (make-files.yaml)
    ---
    - hosts: all
      become: yes
      become_user: root
      tasks:
      - name: Create files
        ansible.builtin.file:
          path: "{{ item['log-path'] }}"
          mode: "{{ item['log-mode'] }}"
          state: touch
        loop:
          - log-path: /var/log/test1.log
            log-mode: '0644'
          - log-path: /var/log/test2.log
            log-mode: '0644'
    

조건문

  • When 사용
    • Boolean 변수 이용 (boolean-echo-test.yaml)
    ---
    - hosts: all
      vars:
        run_my_task: true
      tasks:
        - name: echo message
          ansible.builtin.shell: "echo test" 
          when: run_my_task
    
  • 조건 연산자
    • ==, <, >, <=, >=
    • in, not in
    • in 사용
    ---
    - hosts: all
      vars:
        supported_os:
    		  - RedHat
          - CentOS
      tasks:
        - name: Print supported OS
          ansible.builtin.debug: 
    	      msg: "This {{ ansible_facts['distribution'] }} need to use dnf"
    	    when: ansible_facts['distribution'] in supported_os
    
    • or나 and 사용 가능
    ---
    - hosts: all
      vars:
        supported_os:
    		  - RedHat
          - CentOS
      tasks:
        - name: Print supported OS
          ansible.builtin.debug: 
    	      msg: "This {{ ansible_facts['distribution'] }} {{ ansible_facts['distribution_version'] }} need to use dnf"
    	    when: ansible_facts['distribution'] in supported_os or ansible_facts['distribution'] == 'Ubuntu'
    

반복문과 조건문 같이 이용

  • 먼저 작성한 것이 우선권을 가진다.
  • mounts 팩트 값을 순회하면서 size_available 의 값이 300000000이 넘으면 메시지를 출력
---
- hosts: all
  tasks:
    - name: Print Root Directory Size
      ansible.builtin.debug:
        msg: "Directory {{ item.mount }} size is {{ item.size_available }}"
      loop: "{{ ansible_facts['mounts'] }}"
      when: item['mount'] == "/"

핸들러

특정 이벤트가 발생했을 때 호출되는 함수나 코드를 핸들러라고 한다.

  • 핸들러를 호출할 때는 notify 속성에 핸들러 이름을 기재하면 된다.
---
- hosts: all
  tasks:
    - name: restart rsyslog
      ansible.builtin.service:
        name: "ssh"
        state: restarted
      notify:
        - print msg
  handlers:
    - name: print msg
      ansible.builtin.debug:
        msg: "rsyslog is restarted"
728x90
반응형