代码之家  ›  专栏  ›  技术社区  ›  mpen

jq:把数组转换成按文件名索引的对象?

  •  1
  • mpen  · 技术社区  · 7 年前

    使用 jq 如何将数组转换为按文件名索引的对象,或将多个文件读取为按文件名索引的一个对象?

    例如

    jq -s 'map(select(.roles[]? | contains ("mysql")))' -C dir/file1.json dir/file2.json
    

    这给了我想要的数据,但我需要知道它们来自哪个文件。

    所以不是

    [
        { "roles": ["mysql"] },
        { "roles": ["mysql", "php"] }
    ]
    

    对于输出,我想要:

    {
        "file1": { "roles": ["mysql"] },
        "file2": { "roles": ["mysql", "php"] }
    }
    

    我也希望去掉“.json”文件扩展名 如果可能的话 ,仅限于basename(dir除外)。


    例子

    文件1.json
    { "roles": ["mysql"] }
    
    文件2.json
    { "roles": ["mysql", "php"] }
    
    文件3.json
    { }
    

    我的真实文件显然也包含其他内容,但对于这个例子来说,这就足够了。文件3只是为了证明有时缺少“角色”。

    换句话说:我试图在“角色”列表中找到包含“mysql”的文件。我需要将文件名和内容组合成一个JSON对象。


    为了进一步简化问题:

    jq 'input_filename' f1 f2
    

    提供我想要的所有文件名,但我不知道如何将它们组合成一个对象或数组。

    鉴于,

    jq -s 'map(input_filename)' f1 f2
    

    给我 相同的 文件名对每个文件重复一次。例如 [ "f1", "f1" ] 而不是 [ "f1", "f2" ]

    2 回复  |  直到 7 年前
        1
  •  1
  •   peak    7 年前

    inputs any .roles

    jq -n '
      [inputs
       | select(.roles and any(.roles[]; contains("mysql")))
       | {(input_filename | gsub(".*/|\\.json$";"")): .}]
      | add' file*.json
    
        2
  •  1
  •   RomanPerekhrest    7 年前

    jq

    jq 'if (.roles[] | contains("mysql")) then {(input_filename | gsub(".*/|\\.json$";"")): .}
        else empty end' ./file1.json ./file2.json | jq -s 'add'
    

    {
      "file1": {
        "roles": [
          "mysql"
        ]
      },
      "file2": {
        "roles": [
          "mysql",
          "php"
        ]
      }
    }