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

如何编写yq递归表达式强制XML转JSON时统一节点为数组?

问题分析与解决方案

原递归表达式的问题

你使用的(... | select(key == "member")) |= [] + .存在两个核心问题:

  • 递归运算符误用:...是递归下降到所有叶子节点(比如one、two这类字符串值),而叶子节点没有key属性,导致select(key == "member")无法正确匹配到member键对应的节点,进而让yq处理逻辑混乱,输出异常格式。
  • 处理逻辑不严谨:即使匹配到目标节点,[] + .仅能实现单个值转数组,但没有考虑节点本身已是数组的场景(虽然当前案例中可以运行,但扩展性差)。

正确的递归表达式

使用..(遍历所有层级的节点,包括映射节点)选中所有键为member的节点,再通过类型判断统一转为数组:

yq --input-format xml '(.. | select(key == "member")) |= if type == "array" then . else [.] end' data.xml

执行效果

针对你的data.xml,执行后输出:

root:
  heading:
    - member:
        - one
    - member:
        - two
        - three

适配任意层级的原理

  • ..会递归遍历XML转YAML后的所有节点,无论层级深浅,只要键名为member就会被选中;
  • 条件判断if type == "array" then . else [.] end确保:
    • 原本就是数组的member保持结构不变;
    • 单个值的member被包裹为数组,实现全层级格式统一。

额外优化:批量处理多节点

如果需要同时处理多个类似节点(比如member、item),可修改选择器:

yq --input-format xml '(.. | select(key == "member" or key == "item")) |= if type == "array" then . else [.] end' data.xml

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.18 10:27:53