gpt4 book ai didi

ruby - 如何让 Nokogiri 的 SAX 解析器不那么严格?

转载 作者:数据小太阳 更新时间:2023-10-29 08:08:52 26 4
gpt4 key购买 nike

我正在处理非常大的 XML 文件,所以我需要使用 SAX/evented XML 解析器。 Nokogiri::XML::SAX 似乎是一个显而易见的选择,但是,SAX 解析器似乎会因小错误而窒息,即使是常规 XML 解析器也可以轻松恢复的错误。

在下面的示例中,url <property> 的属性有一个 &那真的应该转义到&amp; . Nokogiri::XML 仍然能够解析 <property> 中的元素但是 Nokogiri::XML::SAX 似乎只是放弃并且从不触发 <property> 中元素的事件.

require 'nokogiri'

class Doc < Nokogiri::XML::SAX::Document
include Enumerable

def initialize(xml)
@xml = xml
end

def each(&block)
@on_record = block
parse(@xml)
end

def parse(xml)
parser = Nokogiri::XML::SAX::Parser.new(self)
parser.parse(xml)
end

def end_element(name)
@on_record.call(name) if name == "details"
end

def error(str)
puts str
end
end

xml = <<XML
<?xml version="1.0" encoding="UTF-8"?>
<streeteasy version="1.5">
<properties>
<property url="http://example.com/?foo=bar&yin=yang">
<location>Somewhere</location>
<details>Information goes here</details>
</property>
</properties>
</streeteasy>
XML

puts Doc.new(xml).count # => 0, but should be 1
puts Nokogiri::XML(xml).xpath("//details").count # => 1

上面的脚本应该输出:

1
1

但是,我得到:

EntityRef: expecting ';'
0
1

有没有办法让 Nokogiri 忽略这些小错误?在 Ruby 中是否有更好的 SAX/push/pull/evented XML 解析选项可以忽略此类错误?

最佳答案

改用 Nokogiri 的 HTML SAX 解析器。

改变这一行

parser = Nokogiri::XML::SAX::Parser.new(self)

到这一行

parser = Nokogiri::HTML::SAX::Parser.new(self)

HTML 解析器显然在恢复模式下运行 libxml,并且能够从错误中恢复。这允许该示例输出所需的 1/1,尽管有一些关于非标准“html”标签的提示。

Tag streeteasy invalid
Tag properties invalid
htmlParseEntityRef: expecting ';'
Tag property invalid
Tag location invalid
Tag details invalid
1
1

更新

事实证明这适用于我设计的示例,但是一旦 Nokogiri::HTML::SAX::Parser#parse 被传递给 IO 而不是String 就像 XML 版本一样,它会因错误而窒息。我无法将文件加载到内存中……这违背了使用 SAX 解析器的全部目的。所以,不接受我自己的回答。

关于ruby - 如何让 Nokogiri 的 SAX 解析器不那么严格?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22874615/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com