jq:获得两个级别的密钥

时间:2015-11-10 10:05:24

标签: jq

我有一些类似的json数据:

{
  "p": {
    "d": {
      "a" : {
        "r": "foo",
        "g": 1
      },
      "b": {
        "r": "bar",
        "g": 2
      }
    },
    "c": {
      "e": {
        "r": "baz",
        "g": 1
      }
    },
    ...
  }
}

我想要类似的东西:

{
  "d": [ 
    "a",
    "b"
  ],
  "c": [
    "e"
  ]
}

我可以使用jq '.p|keys'在“p”下的第一级获取键列表,使用jq '.p|map(.|keys)'获取第二级的结构和键,但我无法弄清楚如何结合它。

3 个答案:

答案 0 :(得分:9)

使用map_values代替map来映射JSON对象的值,同时保留密钥:

jq '.p | map_values(keys)'

在低于1.5的jq版本中,未定义map_values:相反,您可以使用[]|=

jq '.p | . []|= keys'

答案 1 :(得分:1)

以下是使用 reduce setpath

的解决方案
  .p
| reduce keys[] as $k (
     .
   ; setpath([$k]; .[$k] | keys)
)

答案 2 :(得分:0)

一般情况

顶级键:

curl -s https://crates.io/api/v1/crates/atty | jq '. |= keys'

[
  "categories",
  "crate",
  "keywords",
  "versions"
]

两级键:

curl -s https://crates.io/api/v1/crates/atty | jq '.| map_values(keys)'

{
  "crate": [
    "badges",
    "categories",
    "created_at",
    "description",
    "documentation",
    "downloads",
    "exact_match",
    "homepage",
    "id",
    "keywords",
    "links",
    "max_version",
    "name",
    "newest_version",
    "recent_downloads",
    "repository",
    "updated_at",
    "versions"
  ],
  "versions": [
    0,
    1,
    2,
    3,
    4,
    5,
    6,
    7,
    8,
    9,
    10,
    11,
    12,
    13,
    14,
    15,
    16
  ],
  "keywords": [
    0,
    1,
    2
  ],
  "categories": []
}

方法版本

topLevelJsonKeys() {
 curl -s $1 | jq '. |= keys'
  # EXAMPLE: 
  # topLevelJsonKeys https://crates.io/api/v1/crates/atty
}

topLevelJsonKeys2() {
  curl -s $1 | jq '.| map_values(keys)'
  # EXAMPLE: 
  # topLevelJsonKeys2 https://crates.io/api/v1/crates/atty
}