如何使用jq更新json文档中的单个值?

时间:2015-06-24 18:56:33

标签: json jq

如果我忽视了一些非常明显的东西,那就是我的意思;我刚刚找到jq并尝试使用它来更新一个JSON值而不会影响周围的数据。

我想将curl结果导入jq,更新一个值,并将更新的JSON传递给curl -X PUT。像

这样的东西
curl http://example.com/shipping.json | jq '.' field: value | curl -X PUT http://example.com/shipping.json

到目前为止,我已使用sed一起攻击它,但在查看|=jq运算符的几个示例后,我确信我不需要这些

以下是JSON示例 - 我如何使用jq设置"local": false,同时保留其余的JSON?

{
  "shipping": {
    "local": true,
    "us": true,
    "us_rate": {
      "amount": "0.00",
      "currency": "USD",
      "symbol": "$"
    }
  }
}

3 个答案:

答案 0 :(得分:76)

使用=运算符设置对象的值。另一方面,|=用于更新值。这是一个微妙但重要的区别。过滤器的上下文发生变化。

由于您要将属性设置为常量值,请使用=运算符。

.shipping.local = false

请注意,在为属性设置值时,它不一定必须存在。您可以通过这种方式轻松添加新值。

.shipping.local = false | .shipping.canada = false | .shipping.mexico = true

答案 1 :(得分:22)

更新值(将.foo.bar设置为“新值”):

jq '.foo.bar = "new value"' file.json

使用变量更新值(将.foo.bar设置为“ hello”):

variable="hello"; jq --arg variable "$variable" '.foo.bar = $variable' file.json

答案 2 :(得分:0)

与运算符| =类似的功能是map。 映射将适合避免对数组使用先前的过滤器...

想象您的数据是一个数组(在此示例中很常见)

[
  {
    "shipping": {
      "local": true,
      "us": true,
      "us_rate": {
        "amount": "1.00",
        "currency": "USD",
        "symbol": "$"
      }
    }
  },
  {
    "shipping": {
      "local": true,
      "us": true,
      "us_rate": {
        "amount": "1.00",
        "currency": "USD",
        "symbol": "$"
      }
    }
  }
]

因此,有必要将代码中的数组视为:

http://example.com/shipping.json | jq '.[] | .shipping.local = "new place"' | curl -X PUT http://example.com/shipping.json

或使用专为在每个数组元素中工作的map函数

http://example.com/shipping.json | jq 'map(.shipping.local = "new place")' | curl -X PUT http://example.com/shipping.json

观察

为了便于学习,您在jq用法上也犯了一些错误,只需考虑它确实在程序中“读取”了第一个参数,因此所有所需的命令都应包含在第一个字符串中调用程序后。