【问题标题】:Using lxml.html with broken html entities?将 lxml.html 与损坏的 html 实体一起使用?
【发布时间】:2019-06-16 21:00:09
【问题描述】:

我需要处理一个页面,该页面不幸地混合了正确和不正确的 HTML 实体;例如:

<i>Kristj&aacuten V&iacute;ctor</i>

这在 Firefox 67 中最终会得到正确解释:

...但是,如果我们执行“查看源代码”,Firefox 会通过语法颜色指示第一个 HTML 实体有问题:

...确实有,HTML 实体末尾的分号丢失了 - 但是,Firefox 以某种方式找出了它,并呈现了正确的字符。

现在,如果我尝试在 lxml 中使用它:

#!/usr/bin/env python3

import lxml.html as LH
import lxml.html.clean as LHclean

testhtmlstring = "<i>Kristj&aacuten V&iacute;ctor</i>"

myhtml = LH.fromstring( testhtmlstring )
myhtml = LHclean.clean_html( myhtml )
myitem = myhtml.xpath("//i")[0]
myitemstr = myitem.text_content()
print(myitemstr)

...代码在终端(Ubuntu 18.04)中打印出来:

Kristj&aacuten Víctor

...所以,很明显,损坏的 htmlentity 没有转换为正确的字符。

有什么我可以使用的,所以我从 lxml 的输出字符串中得到了正确的字符,即使在 htmlentity 损坏的情况下(如 Firefox 那样)?

【问题讨论】:

    标签: python html html-entities lxml.html


    【解决方案1】:

    HTML 5 标准指定了一个特定的实体子集,可以在没有尾随分号的情况下进行解析,因为these entities were historically defined with the semicolon being optional

    html.unescape() function 明确支持这些,使用该函数作为第二遍来清除此问题:

    >>> from html import unescape
    >>> unescape("Kristj&aacuten Víctor")
    'Kristján Víctor'
    

    如果您安装html5lib,那么您可以通过他们的lxml.html.html5parser module(包装html5lib 自己的html5lib.treebuilders.etree_lxml adapter)让lxml 表现相同:

    >>> from lxml.html import html5parser as etree
    >>> etree.fromstring("Kristj&aacuten Víctor").text
    'Kristján Víctor'
    

    【讨论】:

    • 非常感谢,很大的帮助 - 不知道有一个分号允许的 htmlentities 子集。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-09-27
    • 1970-01-01
    • 2014-09-23
    • 2018-04-09
    • 2017-02-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多