Conditions

前言

差點漏了這個幾乎最重要機能condition

這個玩意就跟shell script中的if迴圈一樣重要

When

在ansible中最常見的條件就是用when這個基本上就跟if [...];then一樣,不過更加直觀一點

基本用法

不囉唆先上個範例

1
2
3
4
5
#隨便來個tasks

- name: 在系統為Arch Linux時跑shell內的指令
shell: yay -Syu --noconfirm
when: ansible_facts['os_family'] == 'Archlinux'

這裡when的後面放的是讀取機器的ansible_facts內的os_family變數,當它等於Archlinux的時候執行這個Tasks

複合條件

基本上就是A and B時條件成立或是A or B的時候會觸發條件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# 當條件是 A and B都滿足的時候

- name: 當Node是Archlinux以及hostname為Test的時候觸發
shell: yay -S brave-bin --noconfirm
when: (ansible_facts['os_family'] == 'Archlinux') and (ansible_facts['hostname'] == 'Test')

# 或是以下寫法

- name: 當Node是Archlinux以及hostname為Test的時候觸發
shell: yay -S brave-bin --noconfirm
when:
- ansible_facts['os_family'] == 'Archlinux'
- ansible_facts['hostname'] == 'Test'

# 當條件變成A or B的時候

- name: 當Node是Ubuntu或是Debiant的時候觸發
shell: yay -S brave-bin --noconfirm
when: (ansible_facts['os_family'] == 'Ubuntu') or (ansible_facts['os_family'] == 'Debian')

看起來很簡單吧,基本上這都是利用ansible_facts的系統資訊做的判斷

利用register做變數進行判斷

若是想要利用某一些輸出的資訊來進行判斷的時候就可以利用register來進行

1
2
3
4
5
6
7
8
9
10
11
# 系統更新完後,若有更新Kernel就提示
- name: System Update via yay
become_user: ansible-user
shell: yay -Syu --noconfirm
register: out
changed_when: "'nothing to do'is not in out.stdout"

- name: Kernel Updated
debug:
msg: Kernel Update!! Needs to Reboot!!
when: "'linuix' is in out.stdout"

這個比較複雜一點,並且有用到一個沒講過的changed_when這個意思是滿足這個條件的才標示為changed
相對應的語法跟When一樣

可以看得出範例中我把前一個tasks的輸出registerout
然後在changed_when內定義了在輸出(out.stdout)中沒有nothing to do字串的時候就把這個tasks定義為changed
這樣可以在沒有更新任何東西的時候就顯示OK(因為沒有更新東西會出現nothing to do字串)

然後下一個tasks內定義,當linux出現在out.stdout的時候就顯示Kernel Update!! Needs to Reboot!!字串提醒事後要重開機(當然…也可以直接就改module為shell讓機器直接重開機)

結論

其實還有很多高級用法,例如自定義facts, 或是failed_when等奇奇怪怪的可以拿來組合成各種判斷,只要不是在when條件內使用"{{ }}"變數定義就好
我個人的習慣是喜歡在最前面先用vars_files filter掉os_family這樣可以減少後面編寫的時候when的複雜化,畢竟越簡單的組件寫的時候越簡易不會出錯…