在 Day03 認識 Inventory 時,筆者就介紹過 INI 與 YAML 兩種 Inventory 格式了。
所以本篇會預設各位已經擁有這兩份檔案
# inventory.ini
[all]
192.0.2.10 ansible_user=ubuntu
192.0.2.11 ansible_user=ubuntu
192.0.2.12 ansible_user=ubuntu
---
# host.yaml
web_servers:
hosts:
vultr:
ansible_host: 192.0.2.10
ansible_port: 22
ansible_user: deploy
ansible_python_interpreter: /usr/bin/python3
ansible-inventory -i 'inventory.ini,host.yaml' --graph
ansible-inventory -i inventories/ --graph
為什麼筆者比較喜歡使用 YAML 的格式呢,舉個例子:
---
# 相信大家會覺得這樣的格式在對於團隊開發上可讀性會比較高
all:
children:
web:
hosts:
web01: { ansible_host: 192.0.2.21 }
web02: { ansible_host: 192.0.2.22 }
db:
hosts:
db01: { ansible_host: 192.0.2.31 }
vars:
ansible_user: ubuntu
💡 Tips:所以筆者建議
group_vars/<group>.yaml
放群組變數;host_vars/<host>.yaml
放主機變數。
# 指定群組或主機
ansible web -i host.yaml -m ping
ansible web[0] -i host.yaml -m ping # 第一台 (若有支援 Index 的話)
# 運算子
ansible 'web:&prod' -i host.yaml -m ping # 交集
ansible 'web:db' -i host.yaml -m ping # 聯集
ansible 'all:!db' -i host.yaml -m ping # 差集 (排除 db)
有!!!我們可以透過 Constructed 來定義好每個主機的 template,白話來說就是先挖個洞,然後根據主機的 hostvars 來自動把這些洞填滿。
---
# inventory-constructed.yaml
plugin: constructed
strict: false
compose:
app_env: "{{ hostvars[inventory_hostname].app_env | default('dev') }}"
groups:
web: "'web' in (hostvars[inventory_hostname].roles | default([]))"
prod: "hostvars[inventory_hostname].app_env | default('dev') == 'prod'"
keyed_groups:
- key: app_env
prefix: env
使用方式:
ansible-inventory -i 'inventory.ini,host.yaml,inventory-constructed.yaml' --graph
aws_ec2
、azure_rm
、gcp_compute
、k8s
等filters
與 keyed_groups
動態分組ansible-inventory
不會連線主機蒐集 facts; Constructed 依賴 inventory 現有變數group_by
進一步分群:---
- hosts: all
gather_facts: true
tasks:
- name: Group by OS family
group_by:
key: "os_{{ ansible_facts['os_family'] | lower }}"
---
# inventory-inspect.yml
- name: Inspect inventory
hosts: all
gather_facts: false
tasks:
- name: Show host summary
debug:
msg:
- "host={{ inventory_hostname }}"
- "ip={{ ansible_host | default('N/A') }}"
- "groups={{ group_names | join(',') }}"
驗證與檢查:
ansible-inventory -i 'inventory.ini,host.yaml' --graph
ansible-playbook -i 'inventory.ini,host.yaml' inventory-inspect.yml --syntax-check
-list
測試inventory.ini
的主機加上 roles=['web']
,再用 Constructed 分出 web
群組group_vars/web.yaml
設定 app_port=8000
,在簡單 Playbook 中印出該值inventory-inspect.yml
顯示每台主機所屬的 env*
群組 (搭配 keyed_groups)明天來講講 Ansible 怎麼做敏感性資料的加密