簡體   English   中英

Ansible 和/或 Jinja2 中的子字符串

[英]SubString in Ansible and/or Jinja2

我正在嘗試取消所有掛載點,除非它們是當前列表的一部分:

excluded: ['home', 'cdrom', 'tmpfs', 'sys', 'run', 'dev', 'root']

僅適用於 fstab 的設備示例:

  • /dev/mapper/vgroot-local_home
  • devtmpfs
  • tmpfs

/dev/mapper/vgroot-local_home應該從卸載中排除,因為子字符串home存在於陣列上,並且對於devtmpfs子字符串tmpfs也是如此。 對於tmpfs ,我們有一個完美的匹配。 目標是檢查設備。

在檢查了所有Ansible 過濾器Jinja2 文檔后,我沒有找到解決這個問題的方法。 收集所有 Ansible 事實。

- name: Ensure the mountpoint is on the excluded list
  ansible.posix.mount:
    path: '{{ mount.device }}'
    state: unmounted
  when: {{ ??? }}
  with_items: '{{ ??? }}'
  become: true
  tags: mountpoints

要在 Jinja 中測試一個字符串是否包含子字符串,我們使用in測試,很像 Python:

"somestring" in somevariable

在您的情況下,您想檢查給定字符串是否包含excluded列表中的任何子字符串。 從概念上講,我們想要的是類似於 Python 表達式的東西

if any(x in mount.device for x in excluded)

使用 Jinja 過濾器,我們需要稍微反轉我們的邏輯。 我們可以使用select過濾器從excluded列表中獲取包含在給定目標字符串(例如mount.device )中的字符串列表,如下所示:

excluded|select('in', item)

如果item匹配excluded列表中的任何內容,則上述表達式將生成一個非空列表(在布爾上下文中使用時其計算結果為true )。

在劇本中使用,它看起來像這樣:

- hosts: localhost
  gather_facts: false
  vars:
    excluded: ['home', 'cdrom', 'tmpfs', 'sys', 'run', 'dev', 'root']
    mounts:
      - /dev/mapper/vgroot-local_home
      - devtmpfs
      - tmpfs
      - something/else
  tasks:
    - debug:
        msg: "unmount {{ item }}"
      when: not excluded|select('in', item)
      loop: "{{ mounts }}"

上面的劇本作為輸出產生:

TASK [debug] *******************************************************************
skipping: [localhost] => (item=/dev/mapper/vgroot-local_home) 
skipping: [localhost] => (item=devtmpfs) 
skipping: [localhost] => (item=tmpfs) 
ok: [localhost] => (item=something/else) => {
    "msg": "unmount something/else"
}

也就是說,當當前循環項包含excluded列表中的子字符串時,它會跳過任務。

假設您的目標是“卸載所有文件系統,但設備名稱包含excluded列表中的子字符串的文件系統除外”,您可以編寫:

- name: Unmount filesystems that aren't excluded
  ansible.posix.mount:
    path: '{{ mount.device }}'
    state: unmounted
  when: not excluded|select('in', item.device)
  loop: "{{ ansible_mounts }}"
  become: true
  tags: mountpoints

如果由於匹配路徑而不想排除掛載項,請迭代basename ,例如,如果由於排除列表中的dev而不想排除/dev/mapper/vgroot-local_home

    - debug:
        msg: "Unmount {{ item }}"
      loop: "{{ mounts|map('basename') }}"
      when: not excluded|select('in', item)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM