ToolDeck

CSV 转 YAML

将 CSV 数据转换为 YAML 对象数组

加载示例

CSV 输入

YAML 输出

本地运行 · 粘贴密钥安全无忧
YAML 输出将显示在此处…

什么是CSV转YAML转换?

CSV转YAML转换是将逗号分隔的表格数据转化为YAML(YAML Ain't Markup Language)格式的过程。CSV文件的每一行都会成为YAML序列中的一个条目,每个列标题则映射为YAML映射中的一个键。输出结果是一个以缩进表示层级的可读性文档,配置工具和数据流水线无需额外的Schema文件即可直接解析。

YAML于2001年首次提出,并于2009年发布了当前规范(YAML 1.2)。它是Kubernetes清单、Docker Compose文件、Ansible Playbook、GitHub Actions工作流以及众多CI/CD系统的默认配置格式。当源数据存储在电子表格或数据库导出文件中时,将CSV转换为YAML是为这些系统生成配置条目、数据初始化记录或测试输入的最快方式。

一个正确的CSV转YAML转换器必须处理RFC 4180解析规则:包含逗号或换行符的引用字段、转义的双引号以及不同的分隔符。在YAML一侧,看起来像布尔值(yes、no、true、false)、数字或null的字符串必须加上引号,以防止YAML解析器将其强制转换为非预期类型。转换器还应处理Unicode内容并生成有效的UTF-8输出,因为YAML 1.2要求默认使用UTF-8编码。

为什么使用CSV转YAML工具?

手动从电子表格数据编写YAML既繁琐又容易出错。一个错位的缩进或一个未加引号的特殊字符就会产生无效的YAML,导致配置部署或数据导入失败。此转换器解析CSV字段,将标题映射为键,并生成缩进正确、引号处理恰当的YAML输出。

在浏览器中即时转换
粘贴或上传CSV数据,立即获得有效的YAML输出。无需安装CLI工具,无需引入依赖库,无需构建步骤。
🔒
数据隐私保护
所有解析和转换操作均在浏览器中通过JavaScript本地运行。您的CSV数据不会离开本机,不会发送至服务器,也不会被存储或记录。
🎯
生成格式正确的YAML
输出使用正确的缩进,对可能被误解为布尔值或数字的字符串加上引号,生成符合YAML 1.2规范、可通过任何Lint工具或Schema验证器检验的有效输出。
📋
支持各种CSV方言
自动检测逗号、分号、制表符和竖线作为分隔符。支持RFC 4180引用规则,包括转义的双引号、多行字段以及带BOM的UTF-8文件。

CSV转YAML使用场景

Kubernetes与Docker Compose配置
从配置值电子表格生成环境变量块、ConfigMap数据段或Docker Compose服务定义。将YAML输出直接粘贴到清单文件中。
Ansible Playbook数据
将主机、角色和变量的CSV清单转换为YAML格式的变量文件(group_vars、host_vars),Ansible无需任何自定义解析插件即可原生读取。
CI/CD流水线配置
将构建矩阵条目、环境变量或部署目标的电子表格转换为GitHub Actions、GitLab CI或CircleCI的YAML配置块,避免手动输入重复的矩阵定义。
数据库测试数据初始化
Rails、Django等框架使用YAML作为测试数据和初始数据的格式。将CSV数据库导出转换为YAML数据文件,ORM可直接将其加载到测试数据库中。
数据流水线转换
接受YAML输入的ETL流水线可以直接摄取转换后的CSV数据,无需经过JSON中间步骤。dbt、Dagster和Prefect等工具使用YAML定义流水线和配置。
学习YAML语法
YAML新手可以粘贴熟悉的CSV数据,观察表格行如何转化为序列和映射。对比输入与输出有助于理解缩进规则、键值语法和类型处理方式。

CSV转YAML映射参考

CSV文件中的每个结构元素在YAML中都有直接对应的概念。

CSV概念YAML等价物说明
CSV fileYAML documentThe entire file becomes a YAML sequence (array) of mappings
Header rowMapping keysEach column header becomes a key in every mapping entry
Data rowSequence item (- ...)Each row becomes one mapping item in the top-level array
Cell valueScalar valueStrings, numbers, and booleans are inferred by YAML parsers
Empty cellnull or empty stringRendered as null, ~, or an empty value depending on the tool
Comma delimiterIndentation + colonCSV delimiters are replaced by YAML key: value structure

CSV与YAML对比

CSV是一种平面的分隔符分隔格式,不包含类型信息或层级结构。YAML是JSON的超集,使用缩进表示嵌套,支持多种数据类型,并允许注释。具体选择取决于下游工具的要求。

CSV
纯文本格式,每行一条记录。所有值均为字符串。不支持层级结构、嵌套或注释。文件体积小,电子表格、数据库和命令行工具均支持。由RFC 4180定义。适合在约定好列顺序和类型的系统之间批量传输表格数据。
YAML
基于缩进的格式,原生支持字符串、整数、浮点数、布尔值、null、日期、序列(数组)和映射(对象)。支持用#添加行内注释。是Kubernetes、Docker Compose、Ansible、GitHub Actions及大多数现代DevOps工具的主要配置格式。YAML 1.2是JSON的超集,因此任何有效的JSON同样是有效的YAML。

代码示例

以下是Node.js、Python、Go和CLI工具的实用示例。每个示例均读取CSV表头行作为YAML键,将每条数据行映射为序列条目,并对类型不明确的值进行引号处理。

JavaScript (Node.js)
import { parse } from 'csv-parse/sync'
import { stringify } from 'yaml'

const csv = `name,age,city
Alice,30,Berlin
Bob,25,"New York"`

const records = parse(csv, { columns: true, skip_empty_lines: true })
console.log(stringify(records))
// → - name: Alice
// →   age: "30"
// →   city: Berlin
// → - name: Bob
// →   age: "25"
// →   city: New York

// Vanilla JS (no dependencies)
function csvToYaml(csv) {
  const [headerLine, ...dataLines] = csv.trim().split('\n')
  const headers = headerLine.split(',')
  return dataLines.map(line => {
    const values = line.split(',')
    return headers.map((h, i) => `  ${h}: ${values[i] || ''}`).join('\n')
  }).map(block => `- ${block.trimStart()}`).join('\n')
}
Python
import csv, io, yaml

csv_string = """name,age,city
Alice,30,Berlin
Bob,25,New York"""

reader = csv.DictReader(io.StringIO(csv_string))
data = list(reader)

# default_flow_style=False produces block-style YAML
print(yaml.dump(data, default_flow_style=False, sort_keys=False))
# → - age: '30'
# →   city: Berlin
# →   name: Alice
# → - age: '25'
# →   city: New York
# →   name: Bob

# Preserve insertion order with sort_keys=False (Python 3.7+)
# To type-cast numbers: data = [{k: int(v) if v.isdigit() else v ...}]
Go
package main

import (
	"encoding/csv"
	"fmt"
	"gopkg.in/yaml.v3"
	"strings"
)

func main() {
	input := "name,age,city
Alice,30,Berlin
Bob,25,New York"
	r := csv.NewReader(strings.NewReader(input))
	records, _ := r.ReadAll()
	headers := records[0]

	var data []map[string]string
	for _, row := range records[1:] {
		entry := make(map[string]string)
		for i, h := range headers {
			entry[h] = row[i]
		}
		data = append(data, entry)
	}

	out, _ := yaml.Marshal(data)
	fmt.Println(string(out))
	// → - age: "30"
	// →   city: Berlin
	// →   name: Alice
	// → - age: "25"
	// →   city: New York
	// →   name: Bob
}
CLI (yq / Miller)
# Using yq (https://github.com/mikefarah/yq)
# yq reads CSV with --input-format=csv
yq --input-format=csv --output-format=yaml '.' data.csv

# Using Miller (mlr) — converts between CSV, JSON, YAML, and more
mlr --icsv --oyaml cat data.csv

# Python one-liner for quick conversion
python3 -c "
import csv, sys, yaml
data = list(csv.DictReader(sys.stdin))
print(yaml.dump(data, default_flow_style=False, sort_keys=False))
" < data.csv

常见问题

CSV转YAML转换是如何工作的?
转换器读取第一行作为列标题。后续每一行都会生成一个YAML映射(键值对象),所有映射组合成一个YAML序列(数组)。结果是一个对象列表,其中每个键来自标题,每个值来自单元格内容。
CSV中"true"、"yes"或"null"等值如何处理?
YAML解析器会将裸露的true、false、yes、no和null解释为有类型的值而非字符串。转换器会对这些值加上引号,使其在输出中保持为字符串。例如,包含"yes"的CSV单元格在YAML输出中会变为'"yes"',防止配置工具将其误解为布尔值。
可以将YAML转换回CSV吗?
可以,前提是YAML是一个平面的映射序列(包含标量值的对象数组)。含有深层嵌套映射或混合类型的YAML结构无法简洁地表示为CSV行。对于平面结构,yq、Miller(mlr)或Python的yaml和csv模块等工具均可处理反向转换。
CSV转YAML与CSV转JSON有什么区别?
两者都能从平面CSV输入生成结构化数据。JSON使用花括号和方括号,并有严格的引用规则。YAML使用缩进和冒号,支持注释,手动阅读和编辑更为便捷。大多数DevOps工具(Kubernetes、Ansible、Docker Compose)期望YAML格式;大多数Web API和基于JavaScript的工具期望JSON格式。
输出中的数字和日期如何处理?
CSV将所有值视为字符串。YAML解析器会自动将未加引号的数字(42、3.14)和ISO日期(2024-01-15)识别为对应类型。如果需要所有值保持为字符串,转换器可以对每个值加上引号。如果需要类型推断,则保留值不加引号,由YAML解析器进行类型解析。
转换器能处理大型CSV文件吗?
此工具完全在浏览器中运行,性能取决于可用内存和浏览器标签页限制。在现代硬件上,几兆字节(数万行)的文件可以正常转换。对于非常大的文件(100MB以上),建议使用CLI工具,例如Python的csv和yaml模块、Go的encoding/csv配合gopkg.in/yaml.v3,或支持流式处理数据而无需将全部内容加载至内存的Miller(mlr)。
输出的是YAML 1.1还是YAML 1.2?
此工具生成YAML 1.2输出。与YAML 1.1的主要区别在于:1.2版本取消了「挪威问题」(裸露的'no'被解释为布尔值false),并与JSON保持兼容。大多数现代解析器(Go yaml.v3、Python PyYAML的safe_load、Ruby Psych)均支持YAML 1.2。如果您的工具要求1.1兼容性,由于1.2对常见结构向后兼容,输出在绝大多数情况下仍可正常解析。