JQ 在几个文件中拆分 JSON
JQ Split JSON in several files
我是新手。并试图根据内容在几个文件中保留或拆分一个 JSON 。
目标组的“名称”是“root_rgs”,我想将它放在不同的文件中。
{
"root_rgs": [
"PROM_FD_ARCNA",
"PROM_JOB_ICMP"
],
"targets": [
"HCC02155",
"HCC09350",
"HCC09321",
"HCCEFACTORYWWW",
"HCC9723"
]
}
{
"root_rgs": [
"PROM_FD_ARCNA",
"PROM_JOB_WIN"
],
"targets": [
"LABTNSARWID236",
"LABTNSARWID692",
"VM00006"
]
}
{
"root_rgs": [
"PROM_FD_MTZ",
"PROM_JOB_ICMP"
],
"targets": [
"TEIARWIN205",
"TEIARWDB150",
"TEIARWCXWA212"
]
}
是否可以生成如下内容:
ARCNA_ICMP.json
{
TARGETS:
"HCC02155",
"HCC09350",
"HCC09321",
"HCCEFACTORYWWW",
"HCC9723"
}
ARCNA_WIN.json
{
TARGETS:
"LABTNSARWID236",
"LABTNSARWID692",
"VM00006"
}
等等...
希望能说清楚,谢谢大家!
jq 本身不能写入文件,既不能写入一个文件,也不能写入多个文件。然而,调用 jq 的 shell 可以。因此,任何解决方案都需要通过将任务分成多个部分来协调这两个级别,并由两个级别之一(或任何第三方工具)执行每个级别。
一种直接的方法是使用 jq 将流分离成文档并准备它们已经携带文件的名称和内容,然后在 shell 中迭代该输出。然后,对于每个迭代步骤,可以再次使用 jq 来提取该数据并让 shell 将内容保存到文件中。
jq -c '{
name: "\(.root_rgs | map(split("_")[-1]) | join("_")).json",
content: {targets}
}' input.json | while read -r json; do
jq '.content' <<< "$json" > "$(jq -r '.name' <<< "$json")"
done
另一种方法是让 jq 生成一个可在 shell 中执行的脚本。这会将必须调用 jq 的次数从 2n+1 减少到仅 1,如果输入文件包含许多文档,这可能很重要。
jq -r '"cat"
+ " >\(.root_rgs | map(split("_")[-1]) | join("_")).json"
+ " <<<\({targets} | tojson | @sh)"
' input.json | bash
这会为输入流中的每个文档生成一行 cat >FILENAME <<<'JSON'
形式的行,它指示 shell 到 cat
到文件的输入,而输入又提供为一个 Here String,它被 bash
理解,命令最终被传送到它。
另一种可能性是将一次 jq 调用与一次实用程序调用结合起来,例如 awk
来写入文件:
jq -cr '(.root_rgs | "\(.[0]|sub("PROM_FD_";""))\(.[1]|sub("PROM_JOB";""))"),
{TARGETS: .targets}' input.json |
awk 'NR%2==1 {fn = ".json"; next} {print [=10=] >> fn}'
当然,生成的文件通常不会打印得很好。
警告:以上附加到现有文件。实际上,处理此类文件的替代方法可能更可取。
我是新手。并试图根据内容在几个文件中保留或拆分一个 JSON 。 目标组的“名称”是“root_rgs”,我想将它放在不同的文件中。
{
"root_rgs": [
"PROM_FD_ARCNA",
"PROM_JOB_ICMP"
],
"targets": [
"HCC02155",
"HCC09350",
"HCC09321",
"HCCEFACTORYWWW",
"HCC9723"
]
}
{
"root_rgs": [
"PROM_FD_ARCNA",
"PROM_JOB_WIN"
],
"targets": [
"LABTNSARWID236",
"LABTNSARWID692",
"VM00006"
]
}
{
"root_rgs": [
"PROM_FD_MTZ",
"PROM_JOB_ICMP"
],
"targets": [
"TEIARWIN205",
"TEIARWDB150",
"TEIARWCXWA212"
]
}
是否可以生成如下内容:
ARCNA_ICMP.json
{
TARGETS:
"HCC02155",
"HCC09350",
"HCC09321",
"HCCEFACTORYWWW",
"HCC9723"
}
ARCNA_WIN.json
{
TARGETS:
"LABTNSARWID236",
"LABTNSARWID692",
"VM00006"
}
等等...
希望能说清楚,谢谢大家!
jq 本身不能写入文件,既不能写入一个文件,也不能写入多个文件。然而,调用 jq 的 shell 可以。因此,任何解决方案都需要通过将任务分成多个部分来协调这两个级别,并由两个级别之一(或任何第三方工具)执行每个级别。
一种直接的方法是使用 jq 将流分离成文档并准备它们已经携带文件的名称和内容,然后在 shell 中迭代该输出。然后,对于每个迭代步骤,可以再次使用 jq 来提取该数据并让 shell 将内容保存到文件中。
jq -c '{
name: "\(.root_rgs | map(split("_")[-1]) | join("_")).json",
content: {targets}
}' input.json | while read -r json; do
jq '.content' <<< "$json" > "$(jq -r '.name' <<< "$json")"
done
另一种方法是让 jq 生成一个可在 shell 中执行的脚本。这会将必须调用 jq 的次数从 2n+1 减少到仅 1,如果输入文件包含许多文档,这可能很重要。
jq -r '"cat"
+ " >\(.root_rgs | map(split("_")[-1]) | join("_")).json"
+ " <<<\({targets} | tojson | @sh)"
' input.json | bash
这会为输入流中的每个文档生成一行 cat >FILENAME <<<'JSON'
形式的行,它指示 shell 到 cat
到文件的输入,而输入又提供为一个 Here String,它被 bash
理解,命令最终被传送到它。
另一种可能性是将一次 jq 调用与一次实用程序调用结合起来,例如 awk
来写入文件:
jq -cr '(.root_rgs | "\(.[0]|sub("PROM_FD_";""))\(.[1]|sub("PROM_JOB";""))"),
{TARGETS: .targets}' input.json |
awk 'NR%2==1 {fn = ".json"; next} {print [=10=] >> fn}'
当然,生成的文件通常不会打印得很好。
警告:以上附加到现有文件。实际上,处理此类文件的替代方法可能更可取。