You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用jq将任意嵌套JSON转换为可还原的CSV格式

如何使用jq将包含嵌套结构的任意JSON对象数组转换为CSV格式

目前已有的同类解决方案大多需要提前指定输入输出的特定字段,我需要满足以下要求的通用方案:

  • 输出包含表头行
  • 适配任意JSON输入,包括嵌套数组和对象
  • 支持部分记录缺失其他记录存在的键对应值的场景
  • 不硬编码任何字段名称
  • 支持将生成的CSV还原为原始嵌套JSON结构
  • 使用键路径作为表头名称(点表示法)

点表示法说明

很多使用JSON的产品、工具库都采用这类语法:通过点拼接键片段来访问嵌套属性/子字段。比如键路径a.b.0.c就可以指代如下JSON中的123值:

{
  "a": {
    "b": [
      {
        "c": 123
      }
    ]
  }
}

注意事项:该方法默认属性名中不包含点字符,如果属性名本身带点需要额外设计转义逻辑,本实现为了简化默认按属性名无点的场景处理。


输入示例JSON数组

[
    {
        "a": {
            "b": [
                {
                    "c": 123
                }
            ]
        }
    },
    {
        "a": {
            "b": [
                {
                    "c": "foo \" bar",
                    "d": "qux"
                }
            ]
        }
    },
    {
        "a": {
            "b": [
                {
                    "d": 456
                }
            ]
        }
    }
]

预期输出CSV

表头会包含所有出现过的字段,每一行对应输入数组中的一个对象,示例输出如下:

"a.b.0.c","a.b.0.d"
123,
"foo "" bar","qux"
,456

可用jq命令

直接执行即可得到符合要求的输出:

cat example.json | jq -r '
# 辅助函数:将单个嵌套对象展开为「点路径: 叶子值」的平面对象
def path_values:
  reduce (paths(scalars) as $p | {path: $p | join("."), value: getpath($p)}) as $item ({}; .[$item.path] = $item.value);

# 第一步:遍历所有输入对象,收集所有出现过的点路径去重作为CSV表头
( map(path_values | keys) | add | unique ) as $headers
# 输出表头行
| ( $headers | map(@csv) | join(",") )
# 逐行输出每个对象的对应值
, ( .[]
    | path_values as $pv
    | $headers
    | map( $pv[.] )
    | map( if type == "string" then . else tostring end )
    | @csv
  )
'

实现说明

  1. 先通过paths(scalars)获取每个JSON对象所有叶子节点的路径,拼接为点分隔的字符串,把嵌套结构转为平面对象
  2. 提前遍历所有输入对象,收集全量出现过的点路径去重作为表头,保证不会遗漏后续对象独有的字段
  3. 逐行处理每个输入对象,按照表头顺序填充对应值,不存在的字段自动留空
  4. 原生调用jq的@csv格式化工具,自动处理CSV转义规则,比如双引号转义、特殊字符自动包裹等

内容的提问来源于stack exchange,提问作者opyh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.04 04:27:00