如何跳过 YAML 流中有错误的文档?
How do I skip document with errors in YAML stream?
Python 库 pyyaml
似乎不会允许我读取多文档 YAML 流并在解析错误点之后继续。我有两个相关问题:
- 我是不是漏掉了什么,其他 API 会支持这个吗?
- 其他编程语言的解析器是否支持此操作? (如果有,是哪个)
这是一个多文档 YAML 流的示例:
%YAML 1.1
---
# YAML can contain comments like this
name: David
age: 55
---
name: Mei
age: 50 # Including end-of-line
---
name: Juana: ERROR
age: 47
...
---
name: Adebayo
age: 58
...
我想要类似这样的代码来跳过错误的文档,但要弄清楚“无论这个文档有多糟糕,在 ...
和 ---
.[=19 之后都会有新的开始=]
with open('data/multidoc-bad.yaml') as stream:
docs = yaml.load_all(stream)
while True:
try:
doc = next(docs)
print(doc)
except StopIteration:
break
except Exception as err:
print(err)
我想得到:
{'name': 'David', 'age': 55}
{'name': 'Mei', 'age': 50}
mapping values are not allowed here
in "data/multidoc-bad.yaml", line 10, column 12
{'name': 'Adebayo', 'age': 58}
但实际上我听不懂“Adebayo”的最后一行。
我认识到我 可以 自己编写一个小型解析器来读取行并只查找 ...
和 ---
行来分块流。然后在我自己解析后只将单个文档传递给 yaml.loads()
。但看起来这确实是解析器应该为我做的。
Am I just missing something, and some other API will support this?
不,PyYAML 不能这样做。
Do parsers in other programming languages support this operation? (if so, which)
None 我知道的。大多数 YAML 解析器都是 hand-written,有相当一部分是从 PyYAML 翻译过来的。我不知道有一个实现错误恢复的。 (我使用 SnakeYAML、go-yaml、PyYAML、libyaml、YamlDotNet,并编写了 NimYAML 和 AdaYaml。)
But it sure seems like that's what a parser is supposed to do for me.
我认为解析器不支持这个的原因包括
- 如果没有错误恢复,为 YAML 编写兼容的解析器已经非常复杂,
- multi-document 功能很少使用,因此很少投入精力来增强它,
- 这是唯一一个很明显如何实现错误恢复的情况;我认为在 YAML 文档中,几乎不可能实现有用的错误恢复,因此错误恢复不被视为一个明显的功能来实现,
- 解决方法很简单(你自己描述的)。
Python 库 pyyaml
似乎不会允许我读取多文档 YAML 流并在解析错误点之后继续。我有两个相关问题:
- 我是不是漏掉了什么,其他 API 会支持这个吗?
- 其他编程语言的解析器是否支持此操作? (如果有,是哪个)
这是一个多文档 YAML 流的示例:
%YAML 1.1
---
# YAML can contain comments like this
name: David
age: 55
---
name: Mei
age: 50 # Including end-of-line
---
name: Juana: ERROR
age: 47
...
---
name: Adebayo
age: 58
...
我想要类似这样的代码来跳过错误的文档,但要弄清楚“无论这个文档有多糟糕,在 ...
和 ---
.[=19 之后都会有新的开始=]
with open('data/multidoc-bad.yaml') as stream:
docs = yaml.load_all(stream)
while True:
try:
doc = next(docs)
print(doc)
except StopIteration:
break
except Exception as err:
print(err)
我想得到:
{'name': 'David', 'age': 55}
{'name': 'Mei', 'age': 50}
mapping values are not allowed here
in "data/multidoc-bad.yaml", line 10, column 12
{'name': 'Adebayo', 'age': 58}
但实际上我听不懂“Adebayo”的最后一行。
我认识到我 可以 自己编写一个小型解析器来读取行并只查找 ...
和 ---
行来分块流。然后在我自己解析后只将单个文档传递给 yaml.loads()
。但看起来这确实是解析器应该为我做的。
Am I just missing something, and some other API will support this?
不,PyYAML 不能这样做。
Do parsers in other programming languages support this operation? (if so, which)
None 我知道的。大多数 YAML 解析器都是 hand-written,有相当一部分是从 PyYAML 翻译过来的。我不知道有一个实现错误恢复的。 (我使用 SnakeYAML、go-yaml、PyYAML、libyaml、YamlDotNet,并编写了 NimYAML 和 AdaYaml。)
But it sure seems like that's what a parser is supposed to do for me.
我认为解析器不支持这个的原因包括
- 如果没有错误恢复,为 YAML 编写兼容的解析器已经非常复杂,
- multi-document 功能很少使用,因此很少投入精力来增强它,
- 这是唯一一个很明显如何实现错误恢复的情况;我认为在 YAML 文档中,几乎不可能实现有用的错误恢复,因此错误恢复不被视为一个明显的功能来实现,
- 解决方法很简单(你自己描述的)。