如何用 jq 中各自的 shell 变量替换 JSON 字典中的值?
How to replace values in a JSON dictionary with their respective shell variables in jq?
我有以下 JSON 结构:
{
"host1": "$PROJECT1",
"host2": "$PROJECT2",
"host3" : "xyz",
"host4" : "$PROJECT4"
}
以及shell中的以下环境变量:
PROJECT1="randomtext1"
PROJECT2="randomtext2"
PROJECT4="randomtext3"
我想检查每个键的值,如果它们中有“$”字符,请将它们替换为各自的环境变量(shell 中已经存在)以便我的 JSON 模板使用正确的环境变量呈现。
我可以使用 jq 的 --args
选项,但我要渲染的实际 JSON 模板中有很多变量。
我一直在尝试以下方法:
jq 'with_entries(.values as v | env.$v)
基本上将每个值都作为一个变量,然后使用 env 对象中的变量更新它的值,但似乎我错过了一些理解。有直接的方法吗?
编辑
感谢这个问题的答案,我能够实现我更大的目标,其中一部分被问到这个问题
- 迭代对象中的每个值,
- 检查它的值,
- 如果它是一个字符串并且以字符“$”开头
- 使用该值用同名的环境变量更新它。
- 如果是数组
- 使用该值检索同名的环境变量
- 用“,”分隔字符串,returns一个字符串数组
- 用字符串数组更新值
jq 'with_entries(.value |= (if (type=="array") then (env[.[0][1:]] | split(",")) elif (type=="string" and startswith("$")) then (env[.[1:]]) else . end))'
您需要 export
Bash 变量才能被 jq
看到:
export PROJECT1="randomtext1"
export PROJECT2="randomtext2"
export PROJECT4="randomtext3"
那么你可以选择:
jq -n 'with_entries((.value | select(startswith("$"))) |= env[.[1:]])'
并得到:
{
"host1": "randomtext1",
"host2": "randomtext2",
"host3": "xyz",
"host4": "randomtext3"
}
导出大量 shell 变量可能不是一个好主意,并且不能解决数组值变量的问题。因此,考虑将 variable=value 详细信息打印到文件,然后将该文件与模板组合起来可能是个好主意。这很容易做到,互联网上的例子比比皆是,可能在 SO 上也有。例如,您可以像这样使用 printf
:
printf "%s\t" ${BASH_VERSINFO[@]}
3 2 57 1
您可能还会发现 declare -p
有帮助。
另见 https://github.com/stedolan/jq/wiki/Cookbook#arbitrary-strings-as-template-variables
我有以下 JSON 结构:
{
"host1": "$PROJECT1",
"host2": "$PROJECT2",
"host3" : "xyz",
"host4" : "$PROJECT4"
}
以及shell中的以下环境变量:
PROJECT1="randomtext1"
PROJECT2="randomtext2"
PROJECT4="randomtext3"
我想检查每个键的值,如果它们中有“$”字符,请将它们替换为各自的环境变量(shell 中已经存在)以便我的 JSON 模板使用正确的环境变量呈现。
我可以使用 jq 的 --args
选项,但我要渲染的实际 JSON 模板中有很多变量。
我一直在尝试以下方法:
jq 'with_entries(.values as v | env.$v)
基本上将每个值都作为一个变量,然后使用 env 对象中的变量更新它的值,但似乎我错过了一些理解。有直接的方法吗?
编辑
感谢这个问题的答案,我能够实现我更大的目标,其中一部分被问到这个问题
- 迭代对象中的每个值,
- 检查它的值,
- 如果它是一个字符串并且以字符“$”开头
- 使用该值用同名的环境变量更新它。
- 如果是数组
- 使用该值检索同名的环境变量
- 用“,”分隔字符串,returns一个字符串数组
- 用字符串数组更新值
- 如果它是一个字符串并且以字符“$”开头
jq 'with_entries(.value |= (if (type=="array") then (env[.[0][1:]] | split(",")) elif (type=="string" and startswith("$")) then (env[.[1:]]) else . end))'
您需要 export
Bash 变量才能被 jq
看到:
export PROJECT1="randomtext1"
export PROJECT2="randomtext2"
export PROJECT4="randomtext3"
那么你可以选择:
jq -n 'with_entries((.value | select(startswith("$"))) |= env[.[1:]])'
并得到:
{
"host1": "randomtext1",
"host2": "randomtext2",
"host3": "xyz",
"host4": "randomtext3"
}
导出大量 shell 变量可能不是一个好主意,并且不能解决数组值变量的问题。因此,考虑将 variable=value 详细信息打印到文件,然后将该文件与模板组合起来可能是个好主意。这很容易做到,互联网上的例子比比皆是,可能在 SO 上也有。例如,您可以像这样使用 printf
:
printf "%s\t" ${BASH_VERSINFO[@]}
3 2 57 1
您可能还会发现 declare -p
有帮助。
另见 https://github.com/stedolan/jq/wiki/Cookbook#arbitrary-strings-as-template-variables