Jq更新JSON密钥:基于值的值

时间:2016-08-01 23:52:51

标签: json jq amazon-ecs

我对jq很新,并希望用它来更新带有新值的AWS ECS任务定义。 AWS cli返回以下json响应,我想用 name 属性 CONFIG_URL 修改对象 value “这是atest”。

{
  "family": "contentpublishing-task",
  "volumes": [],
  "containerDefinitions": [
    {
      "environment": [
        {
          "name": "TEST_ENV",
          "value": "TEST"
        },
        {
          "name": "CONFIG_URL",
          "value": "s3://stg-appcfg/config-20160729-1130.json"
        }
      ],
      "name": "contentpublishing",
      "mountPoints": [],
      "image": "contentpublishing:blah",
      "cpu": 512,
      "portMappings": [
        {
          "protocol": "tcp",
          "containerPort": 8081,
          "hostPort": 8080
        }
      ],
      "memory": 256,
      "essential": true,
      "volumesFrom": []
    }
  ]
}

尝试以下查询

 cat test.json | jq 'select(.containerDefinitions[0].environment[].name=="CONFIG_URL").value|="this is atest"' 2>&1 

但是已经返回了以下内容。正如您所看到的,在最外层的json对象中添加了一个附加值键。

{
  "family": "contentpublishing-task",
  "volumes": [],
  "containerDefinitions": [
    {
      "environment": [
        {
          "name": "TEST_ENV",
          "value": "TEST"
        },
        {
          "name": "CONFIG_URL",
          "value": "s3://stg-appcfg/config-20160729-1130.json"
        }
      ],
      "name": "contentpublishing",
      "mountPoints": [],
      "image": "contentpublishing:blah",
      "cpu": 512,
      "portMappings": [
        {
          "protocol": "tcp",
          "containerPort": 8081,
          "hostPort": 8080
        }
      ],
      "memory": 256,
      "essential": true,
      "volumesFrom": []
    }
  ],
  "value": "this is atest"
}

2 个答案:

答案 0 :(得分:2)

在设置值之前,必须先选择相应的环境节点。您的查询不会更改上下文,因此它仍然位于根项目上,因此您最终会将新值添加到根目录。

$ jq --arg update_name "CONFIG_URL" --arg update_value "this is a test" \
'(.containerDefinitions[].environment[] | select(.name == $update_name)).value = $update_value' input.json

答案 1 :(得分:0)

这是一个使用jq Complex assignments

的解决方案
(
  .containerDefinitions[]
| .environment[]
| select(.name == "CONFIG_URL")
| .value
) |= "this is atest"