我有以下 yaml:
attr_keys:
x:
y: [1, 2, 3]
z: 7
我需要创建一个 bash 脚本来解析 yaml 文件,创建在
attr_keys.x
下找到的所有键值的各种组合,并多次运行脚本,每次传递不同的参数组合。
现在我在解析 yaml 文件时遇到问题。当
attr_keys.x
下只有一个键时没有问题,脚本工作正常。但是,当有多个键时,它就会损坏。
我正在使用
yq
来解析文件:
parameters_keys=$(yq e ".attr_keys.x | keys | .[] " config.yaml)
for parameter_key in "${parameters_keys[@]}"
do
echo "Key: $parameter_key"
done
如果我们考虑以下 yaml:
attr_keys:
x:
y: [1, 2, 3]
上面的脚本打印
Key: y
,这是正确的。按照这种行为,如果我要考虑以下 yaml 文件:
attr_keys:
x:
y: [1, 2, 3]
z: 7
预期输出应该是
Key: y
Key: z
但是我得到:
Key: y
z
显然,多个键被解析为整个字符串并被视为一个大“键”。我需要的是将多个键作为数组或列表或类似的东西处理,关于如何做到这一点有什么建议吗?
我正在使用 yq (https://github.com/mikefarah/yq/) 版本 v4.34.1
我尝试链接 bash 命令:
parameters_keys=$(yq e ".attr_keys.x | keys | .[] " config.yaml)
到
parameters_keys=$(yq e ".attr_keys.x | keys " config.yaml)
和
parameters_keys=$(yq e ".attr_keys.x | keys | [.[]] " config.yaml)
但它们都不起作用。
这不是
yq
命令本身的问题,而是将命令的输出存储到 shell 上下文的方式的问题。 $(..)
执行内部提供的命令并将结果生成到标准输出,该结果由提供的变量捕获。因此,多行输出存储在变量parameters_keys
中,作为单个多行条目,就像多个单词一样。
始终在 bash 中使用“数组”来存储和处理多行命令输出。请参阅 BashFAQ/050 使用
mapfile
或 readarray
等内置函数将它们存储到数组中。例如对于你的情况,可能是
mapfile -t parameters_keys < <(yq '.attr_keys.x | keys | .[]' config.yaml)
然后像以前一样对数组进行迭代。
另请注意,使用 mikefarah/yq 时,无需指定
e
标志,因为自 v4.18.1 起它已被 设为默认值
yq 没有问题,问题出在你的 Bash 脚本上。无论生产者的逻辑如何,
varname=$(…)
始终是一个(可能是多行)字符串。因此,您不能只是将数组逻辑转移到 Bash 中,您必须在 Bash 中自己创建数组,例如通过在换行符处假设项目边界。使用括号:
parameters_keys=($(yq e ".attr_keys.x | keys | .[]" config.yaml))
但是,使用 Bash 内置函数之一(例如
readarray
)来执行此操作更安全:
readarray -t parameters_keys < <(yq e ".attr_keys.x | keys | .[]" config.yaml)
您可以简单地将 yb 与
-K
(仅限按键)选项一起使用。
declare -a keys_array
keys_array=($(./yb -Kf "ex.yml" -k "attr_keys.x"))
for key in "${keys_array[@]}"; do
echo "key: ${key}"
done