Hacker News 中文摘要

RSS订阅

地狱般的YAML文档 -- The YAML Document from Hell

文章摘要

YAML格式虽然标榜人性化,但其过度复杂的语法设计反而降低了易用性。作者通过对比JSON的简洁规范(仅6张流程图)与YAML冗长的技术文档(10章内容4级目录),指出YAML充满设计陷阱,其表面友好性具有欺骗性。文章以激烈口吻批评YAML在追求灵活性时丧失了作为数据格式应有的简洁本质。

文章总结

标题:YAML——来自地狱的配置文件格式

作者:Ruud van Asseldonk
发布日期:2023年1月11日

YAML作为一种数据格式极其复杂。它本意是提供一种对人类友好的格式,但为了实现这一目标,它引入了过多的复杂性,以至于我认为它实际上起到了相反的效果。YAML充满了陷阱,其友好性具有欺骗性。本文将通过一个示例来展示这一点。

YAML的复杂性

JSON非常简单,其规范仅包含六个简单的语法图。而YAML的规范则包含10个章节,章节编号深达四级,甚至还有一个专门的勘误页面。JSON规范自2005年以来基本冻结,而YAML规范仍在不断更新,最新版本为2021年10月发布的1.2.2。YAML 1.2与1.1有显著差异,同一文档在不同版本下可能解析出不同结果。

地狱般的YAML文档示例

以下是一个YAML文档示例,展示了其解析时的各种问题:

yaml server_config: port_mapping: - 22:22 - 80:80 - 443:443 serve: - /robots.txt - /favicon.ico - !.git geoblock_regions: - dk - fi - is - no - se flush_cache: on: [push, memory_pressure] priority: background allow_postgres_versions: - 9.5.25 - 9.6.24 - 10.23 - 12.13

  1. 六十进制数字问题
    22:22在YAML 1.1中会被解析为六十进制数字1342,而在YAML 1.2中则被视为字符串。许多解析器(如PyYAML)仍使用YAML 1.1,导致解析结果不一致。

  2. 标签问题
    !.git中的!是标签,用于将YAML数据类型转换为宿主语言的更丰富类型。加载不受信任的YAML文档可能导致任意代码执行,存在安全隐患。

  3. 挪威问题
    no在YAML 1.1中被解析为布尔值false,而在YAML 1.2中应为字符串。许多解析器为了兼容性,仍保留这一行为。

  4. 非字符串键
    YAML允许键为任何值,包括布尔值。例如,on可能被解析为true,导致键名意外变化。

  5. 意外数字
    未加引号的字符串(如10.23)可能被解析为数字,导致类型错误。

其他问题

  • 语法高亮不可靠:不同工具对YAML的高亮显示不一致,无法依赖其识别潜在问题。
  • 模板化YAML的风险:由于YAML的复杂性和空格敏感性,模板化YAML极易出错,生成JSON是更安全的选择。

替代方案

  1. TOML:支持注释,字符串必须加引号,避免了YAML的许多陷阱,但对深层嵌套数据支持较弱。
  2. 带注释的JSON:扩展JSON以支持注释,但普及度较低。
  3. 生成JSON:使用编程语言(如Python或Nix)生成JSON,既能避免YAML的问题,又能实现抽象和复用。

结论

YAML试图成为比JSON更友好的格式,但其复杂性和不可预测的行为使其难以驾驭。TOML是更安全的替代品,而在必须使用YAML时,生成JSON是更可靠的方法。

评论总结

评论摘要生成失败