Json 使用jq递归地选择对象的键名称

Json 使用jq递归地选择对象的键名称,json,recursion,key,yaml,jq,Json,Recursion,Key,Yaml,Jq,我有一个JSON文档,看起来像: simple: 42 normal: description: "NORMAL" combo: one: description: "ONE" two: description: "TWO" arbitrary: foo: 42 我想使用jq表达式生成以下内容: ["normal", "one", "two"] 选择键的条件是其对应的值是具有键说明的对象类型。在这种情况下,键simple和arbitral不符合条件

我有一个JSON文档,看起来像:

simple: 42

normal:
  description: "NORMAL"

combo:
  one:
    description: "ONE"
  two:
    description: "TWO"
  arbitrary:
    foo: 42
我想使用
jq
表达式生成以下内容:

["normal", "one", "two"]
选择键的条件是其对应的值是具有键
说明
对象
类型。在这种情况下,键
simple
arbitral
不符合条件

我很难制作过滤器。查看了
递归/2
项,但自己无法解决


TIA.

我不清楚您提供的YAML是否只是JSON的“视图”,或者您是否真的想从YAML开始。如果您的文档确实是YAML,那么一种方法就是使用工具 (如yaml2json或)将yaml转换为JSON,然后运行jq 如下图所示;另一种是将jq用作文本处理器, 但在这种情况下,您也可以使用awk

yaml2json input.yaml |
  jq -c '[.. | objects | to_entries[] 
          | select(.value | has("description")?) | .key]'
输出 流解析器 这种类型的问题也非常适合jq的流式解析器,它在处理非常大的JSON文本时特别方便。使用
jq--stream
,合适的jq过滤器应该是:

[select(length==2) | .[0] | select(.[-1] == "description") | .[-2]] 

结果的顺序将取决于YAML到JSON转换工具生成的键的顺序。

Perfect。你是对的:我试图用yq解决问题,但没能。您的解决方案是正确的,非常准确,甚至提供了替代方案。杰出的泰!
[select(length==2) | .[0] | select(.[-1] == "description") | .[-2]]