Python 如何防止lxml添加默认doctype
当html文档中缺少一个doctype时,lxml似乎会添加一个默认doctype 请参阅此演示代码:Python 如何防止lxml添加默认doctype,python,lxml,libxml2,Python,Lxml,Libxml2,当html文档中缺少一个doctype时,lxml似乎会添加一个默认doctype 请参阅此演示代码: import lxml.etree import lxml.html def beautify(html): parser = lxml.etree.HTMLParser( strip_cdata=True, remove_blank_text=True ) d = lxml.html.fromstring(html, parser
import lxml.etree
import lxml.html
def beautify(html):
parser = lxml.etree.HTMLParser(
strip_cdata=True,
remove_blank_text=True
)
d = lxml.html.fromstring(html, parser=parser)
docinfo = d.getroottree().docinfo
return lxml.etree.tostring(
d,
pretty_print=True,
doctype=docinfo.doctype,
encoding='utf8'
)
with_doctype = """
<!DOCTYPE html>
<html>
<head>
<title>With Doctype</title>
</head>
</html>
"""
# This passes!
assert "DOCTYPE" in beautify(with_doctype)
no_doctype = """<html>
<head>
<title>No Doctype</title>
</head>
</html>"""
# This fails!
assert "DOCTYPE" not in beautify(no_doctype)
# because the returned html contains this line
# <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
# which was not present in the source before
导入lxml.etree
导入lxml.html
def美化(html):
parser=lxml.etree.HTMLParser(
strip\u cdata=True,
删除\u blank\u text=True
)
d=lxml.html.fromstring(html,parser=parser)
docinfo=d.getroottree().docinfo
返回lxml.etree.tostring(
D
漂亮的印刷品=真的,
doctype=docinfo.doctype,
编码='utf8'
)
使用“doctype=”“”
带Doctype
"""
#这就过去了!
在美化中断言“DOCTYPE”(使用_DOCTYPE)
否_doctype=“”
没有Doctype
"""
#这失败了!
断言“DOCTYPE”不在美化中(无DOCTYPE)
#因为返回的html包含这一行
#
#这在以前的资料中是不存在的
我如何告诉lxml不要这样做 这个问题最初是在这里提出的: 引用可能有帮助的答案: lxml是基于libxml2的,默认情况下它会这样做,除非您传递选项
HTML\u PARSE\u NODEFDTD
。代码
我不知道您是否可以告诉lxml通过该选项。。libxml有python绑定,您可能可以直接使用它们,但它们看起来非常复杂
编辑:进行了更多的挖掘,该选项确实出现在lxml资源中。这个选项正是你想要的,但我还不确定如何激活它,如果可能的话
目前在lxml中没有办法做到这一点,但我已经创建了一个,它在
HTMLParser
中添加了一个default\u doctype
布尔值
一旦代码被合并,就需要像这样创建解析器:
parser = lxml.etree.HTMLParser(
strip_cdata=True,
remove_blank_text=True,
default_doctype=False,
)
其他一切都保持不变。中没有处理
HTML\u PARSE\u NODEFDTD
选项,因此您可能运气不好。@nwellnhof也许我们可以解决这个问题,并创建一个PR@lxml?不过,这个选项是存在的。我也是。目前还没有解决方案。FWIW,libxml2 Perl绑定,也是。我认为解决这个问题不会太难,但我只是没有足够的cython等方面的经验。所以我自己无法编译它。