Linux
用 jq 解析 lsblk
我目前正在嘗試使用 jq 解析 lsblk 的輸出並根據某些標準對其進行過濾。
給定以下範例輸出:
{ "blockdevices": [ { "name": "/dev/sda", "fstype": null, "size": "931.5G", "mountpoint": null, "children": [ { "name": "/dev/sda1", "fstype": "ntfs", "size": "50M", "mountpoint": null },{ "name": "/dev/sda2", "fstype": "ntfs", "size": "439.8G", "mountpoint": null },{ "name": "/dev/sda3", "fstype": "vfat", "size": "512M", "mountpoint": "/boot/efi" },{ "name": "/dev/sda4", "fstype": "ext4", "size": "491.2G", "mountpoint": "/" } ] },{ "name": "/dev/sdb", "fstype": "crypto_LUKS", "size": "200GG", "mountpoint": null, "children": [ { "name": "/dev/mapper/d1", "fstype": "btrfs", "size": "200G", "mountpoint":[ null ] } ] },{ "name": "/dev/sdc", "fstype": "crypto_LUKS", "size": "100G", "mountpoint": null, "children": [ { "name": "/dev/mapper/abc2", "fstype": "btrfs", "size": "100GG", "mountpoint": "/mnt/test" } ] } ] }
我想查看所有具有 fstype“crypto_LUKS”的頂級設備。然後,對於這些設備,我想檢查孩子(如果存在)是否有安裝點(不為空)。最後,我想返回與這兩個條件都匹配的頂級設備的名稱。
因此,對於上面的範例,只會返回 1 個匹配項:
/dev/sdc /dev/mapper/d1
.由於
/dev/sdc
子設備的掛載點為空/空,因此不會返回設備。到目前為止我已經得到了這個:
lsblk -Jpo NAME,FSTYPE,SIZE,MOUNTPOINT | jq -r '.blockdevices[] | select(.fstype == "crypto_LUKS") '
但這僅檢查 crypto_LUKS 標準,而不檢查孩子的掛載點。它還列印整個數組條目,而不僅僅是兩個值。
我該如何解決這個問題?
要獲取塊設備的名稱及其每個非空子掛載點作為製表符分隔的列表:
jq -r ' .blockdevices[] | select(.fstype == "crypto_LUKS") as $dev | $dev.children[]? | select(.mountpoint | type == "string") as $mp | [ $dev.name, $mp.name ] | @tsv'
由於“空掛載點”實際上不是
null
單個null
值的數組,因此我正在測試掛載點是否為字元串。鑑於問題中的數據,這將返回
/dev/sdc /dev/mapper/abc2
要獲取滿足條件的塊設備對象(如果這就是“整個數組”的意思):
jq '.blockdevices[] | select(.fstype == "crypto_LUKS" and any(.children[]?; .mountpoint | type == "string"))'
這將返回塊設備對象,該對象具有該
fstype
值crypto_LUKS
並且至少有一個帶有 a是字元串children
的元素。mountpoint
鑑於問題中的數據,這將返回
{ "name": "/dev/sdc", "fstype": "crypto_LUKS", "size": "100G", "mountpoint": null, "children": [ { "name": "/dev/mapper/abc2", "fstype": "btrfs", "size": "100GG", "mountpoint": "/mnt/test" } ] }