如何使用 jq 将 JSON 对象与相同的键组合

如何使用 jq 将 JSON 对象与相同的键组合

我将以下代码片段导出为 JSON:

{
  "daisy": {
    "dev": {
      "app_url": "example.com",
      "owner": "bob",
      "createat": "2022-06-17T15:31:58Z",
    }
  }
}
{
  "daisy": {
    "dev": {
      "appname": "daisy",
      "flavor": [
        "nodejs"
      ],
      "file": "manifests/daisy.yml"
    }
  }
}

我想将这些对象组合成这样:

{
  "daisy": {
    "dev": {
      "app_url": "example.com",
      "owner": "bob",
      "createat": "2022-06-17T15:31:58Z",
      "appname": "daisy",
      "flavor": [
        "nodejs"
      ],
      "file": "manifests/daisy.yml"
    }
  }
}

我怎样才能做到这一点jq

答案1

将两个对象相乘会将它们合并。下面使用reduce通过将现有对象一一合并来连续构建一个新对象。

有两种类似的方法可以做到这一点:

  1. 使用-n和:inputsreduce

    jq -n 'reduce inputs as $item ({}; . *= $item)' file
    

    这使用了inputs函数,该函数一一返回传入的对象。与-n( )结合使用--null-input可禁用输入的普通读取。

  2. 使用-s和:.[]reduce

    jq -s 'reduce .[] as $item ({}; . *= $item)' file
    

    这会将原始数据-s( --slurp) 读取到数组中,并reduce用于迭代该数组。请注意,如果输入很大,这会导致内存效率严重低下并且速度缓慢。

给定您的数据的结果(并通过删除createat行上的逗号来更正它):

{
  "daisy": {
    "dev": {
      "app_url": "example.com",
      "owner": "bob",
      "createat": "2022-06-17T15:31:58Z",
      "appname": "daisy",
      "flavor": [
        "nodejs"
      ],
      "file": "manifests/daisy.yml"
    }
  }
}

请注意,如果两个或多个对象共享相同的键,并且该键引用一个标量或者大批,那么输入中后面的对象将覆盖该值。

相关内容