#html-parser #tokenizer #html #html5 #whatwg #tokenize #parser

html5gum

符合WHATWG规范的HTML标记解析器和标签汤解析器

14个版本

0.5.7 2023年7月26日
0.5.3 2023年6月10日
0.5.2 2022年6月20日
0.4.0 2022年1月29日
0.2.1 2021年11月27日

#101解析器实现

Download history 8258/week @ 2024-03-14 17806/week @ 2024-03-21 13157/week @ 2024-03-28 3792/week @ 2024-04-04 3348/week @ 2024-04-11 2673/week @ 2024-04-18 2377/week @ 2024-04-25 3207/week @ 2024-05-02 1729/week @ 2024-05-09 1784/week @ 2024-05-16 1693/week @ 2024-05-23 1684/week @ 2024-05-30 2127/week @ 2024-06-06 2019/week @ 2024-06-13 1741/week @ 2024-06-20 1413/week @ 2024-06-27

7,613 每月下载量
5 软件包中(直接使用4个)

MIT 许可协议

280KB
6.5K SLoC

html5gum

docs.rs crates.io

html5gum 是一个符合WHATWG规范的HTML标记解析器。

use std::fmt::Write;
use html5gum::{Tokenizer, Token};

let html = "<title   >hello world</title>";
let mut new_html = String::new();

for token in Tokenizer::new(html).infallible() {
    match token {
        Token::StartTag(tag) => {
            write!(new_html, "<{}>", String::from_utf8_lossy(&tag.name)).unwrap();
        }
        Token::String(hello_world) => {
            write!(new_html, "{}", String::from_utf8_lossy(&hello_world)).unwrap();
        }
        Token::EndTag(tag) => {
            write!(new_html, "</{}>", String::from_utf8_lossy(&tag.name)).unwrap();
        }
        _ => panic!("unexpected input"),
    }
}

assert_eq!(new_html, "<title>hello world</title>");

标记解析器做什么和不做什么

html5gum 完全实现了 WHATWG HTML规范中的13.2.5,即能够对HTML文档进行标记化并通过 html5lib的标记解析器测试套件。由于它只是一个标记解析器,这意味着

  • html5gum 实现字符集检测。 此实现接受和返回字节,但假定UTF-8。它可以优雅地处理无效的UTF-8。
  • html5gum 纠正错误嵌套的标签。
  • html5gum 识别隐式自闭合元素,如 <img>,作为标记解析器,它将简单地发出一个开始标记。然而,它确实会发出一个自闭合标签 <img .. />
  • html5gum 不实现DOM,遗憾的是,在HTML规范中,构建DOM(“树构建”)会影响标记化操作。例如,请参阅 此示例代码 以了解这会导致哪些问题。
  • html5gum 通常不 符合WHATWG规范中的浏览器级HTML 解析器。这在未来可能会改变,请参阅 问题21

考虑到这些注意事项,html5gum几乎可以解析标记浏览器能够解析的任何内容。

Emitter特性

html5gum的一个显著特点是,您可以提供自己的标记数据结构,并通过实现Emitter特性来挂钩标记创建。这允许您

  • 将所有针对HTML标签的分配重写为使用自定义分配器或数据结构。

  • 有效地过滤掉不感兴趣的数据类别,而无需为其分配内存。例如,如果标记之间的任何纯文本对您来说都不感兴趣,您可以实现相应的特质方法作为空操作,从而避免创建纯文本标记的任何开销。

请参阅custom_emitter示例,了解实际效果。

其他特性

  • 无不安全Rust
  • 唯一的依赖项是jetscii,可以通过crate特性禁用(见Cargo.toml

其他HTML解析器

html5gum的创建是为了高效地解析HTML标签杂烩。之前的选项是

  • 使用quick-xmlxmlparser,并进行一些修改,以使任何一个都能处理坏HTML。对于某些(相当大)的HTML输入,这效果很好(尤其是quick-xml可以配置为对解析错误非常宽容)且解析速度极快。但它们都不能解析所有的HTML。

    对于我的用例,html5gumquick-xml慢约2倍。

  • 使用html5ever自己的标记器,以尽可能减少树构建的开销。这虽然可行,但在我自己的用例中性能较差(比quick-xml慢10-15倍)。

  • 使用lol-html,其性能可能至少与html5gum一样好,但它提供了一个基于闭包的API,我没有成功地在我的用例中使其工作。

词源

为什么这个库叫html5gum

  • G.U.M: Giant Unreadable Match-statement

  • <在此处插入“像吃5 gum一样解析HTML”的meme图片>

许可证

在MIT许可证下发布,请参阅./LICENSE

依赖项