【发布时间】:2021-06-17 17:07:25
【问题描述】:
对于jq,我想在 JSON 数据中设置一个属性,让jq 输出原始 JSON 和更新后的值。我或多或少地通过反复试验找到了一个解决方案,并且想了解它为什么以及如何工作。
我有以下 JSON 数据:
{
"notifications": [
{
"source": "observer01",
"channel": "error",
"time": "2021-01-01 01:01:01"
},
{
"source": "observer01",
"channel": "info",
"time": "2021-02-02 02:02:02"
}
]
}
我的目标是使用特定的 source 和 channel 更新对象的 time 属性(原始 JSON 更长,notifications 数组中有许多相同格式的对象)。
(在下面的例子中,我想用通道info更新observer01的time属性,所以上面示例数据中的第二个对象。)
我的第一次尝试是以下jq 命令,但没有产生所需的输出:
jq '.notifications[] | select(.source == "observer01" and .channel == "info").time = "NEWTIME"' data.json
产生以下输出:
{
"source": "observer01",
"channel": "error",
"time": "2021-01-01 01:01:01"
},
{
"source": "observer01",
"channel": "info",
"time": "NEWTIME"
}
这只是notifications 数组中的 JSON 对象列表。我知道这很有用,例如将对象通过管道传输到其他命令行工具。
现在让我们试试下面的jq 命令,和上面的一样加上一对括号:
jq '(.notifications[] | select(.source == "observer01" and .channel == "info").time) = "NEWTIME"' data.json
这会产生所需的输出,即带有更新的 time 属性的原始有效 JSON:
{
"notifications": [
{
"source": "observer01",
"channel": "error",
"time": "2021-01-01 01:01:01"
},
{
"source": "observer01",
"channel": "info",
"time": "NEWTIME"
}
]
}
为什么在上述情况下将括号添加到jq 过滤器会产生不同的输出?
【问题讨论】:
标签: json command-line jq