当我用 Ruby 解析 YAML 时,它会更改我的锚点名称
When I parse YAML with Ruby, it changes my anchor name
我有一个像这样的 YAML 文件:
- axis: &kadeployversion
type: user-defined
name: kadeployversion
values:
- kadeploy3
- kadeploy3-dev
我用 Ruby 编辑了这个文件,像这样:
require 'yaml'
jjb = YAML.load_file(fileToParse)
jjb[0]['type']='test'
File.open(fileToParse, 'w+'){
|f| f.write jjb.to_yaml
}
但是当我阅读我的新文件时,我有这个:
- axis: &12345678
type: test
name: kadeployversion
values:
- kadeploy3
- kadeploy3-dev
有效,但我想保留我原来的锚名称,否则它会变得不可读。有什么想法吗?
您可以使用 mid-level parsing API:
stream = Psych.parse_stream(yaml)
document = stream.children[0]
mapping = document.children[0]
index = mapping.children.index {|x|
x.is_a?(Psych::Nodes::Scalar) && x.value == 'type'
}
mapping.children[index + 1].value = "new type"
puts stream.to_yaml
说明
使用标准 load/dump 这是不可能的,因为标签信息丢失了。再次转储已解析的 YAML 时发生的情况相当于:
a = [3]
puts({"version"=>a, "axis"=>a}.to_yaml)
###
---
version: &1
- 3
axis: *1
应用任意 ID 来标记对象。
但你并非倒霉!通过下降到 psych mid-level parsing API,此数据已存在,您可以使用它。
yaml = <<EOS
version: &kadeployversion
- 3
axis: *kadeployversion
type: something
EOS
puts Psych.parse_stream(yaml).to_yaml
###
version: &kadeployversion
- 3
axis: *kadeployversion
type: something
parse_stream
returns 是一个 AST 而不是普通的 ruby 对象,所以现在的技巧是更新那个 AST,这比你之前的更难,也可能更脆弱试。如果您 pp
parse_stream
的 return 值,则结构很容易理解,您可以编写一些代码,如顶部的答案。
我有一个像这样的 YAML 文件:
- axis: &kadeployversion
type: user-defined
name: kadeployversion
values:
- kadeploy3
- kadeploy3-dev
我用 Ruby 编辑了这个文件,像这样:
require 'yaml'
jjb = YAML.load_file(fileToParse)
jjb[0]['type']='test'
File.open(fileToParse, 'w+'){
|f| f.write jjb.to_yaml
}
但是当我阅读我的新文件时,我有这个:
- axis: &12345678
type: test
name: kadeployversion
values:
- kadeploy3
- kadeploy3-dev
有效,但我想保留我原来的锚名称,否则它会变得不可读。有什么想法吗?
您可以使用 mid-level parsing API:
stream = Psych.parse_stream(yaml)
document = stream.children[0]
mapping = document.children[0]
index = mapping.children.index {|x|
x.is_a?(Psych::Nodes::Scalar) && x.value == 'type'
}
mapping.children[index + 1].value = "new type"
puts stream.to_yaml
说明
使用标准 load/dump 这是不可能的,因为标签信息丢失了。再次转储已解析的 YAML 时发生的情况相当于:
a = [3]
puts({"version"=>a, "axis"=>a}.to_yaml)
###
---
version: &1
- 3
axis: *1
应用任意 ID 来标记对象。
但你并非倒霉!通过下降到 psych mid-level parsing API,此数据已存在,您可以使用它。
yaml = <<EOS
version: &kadeployversion
- 3
axis: *kadeployversion
type: something
EOS
puts Psych.parse_stream(yaml).to_yaml
###
version: &kadeployversion
- 3
axis: *kadeployversion
type: something
parse_stream
returns 是一个 AST 而不是普通的 ruby 对象,所以现在的技巧是更新那个 AST,这比你之前的更难,也可能更脆弱试。如果您 pp
parse_stream
的 return 值,则结构很容易理解,您可以编写一些代码,如顶部的答案。