【问题标题】:Is there such a thing as a valid HTML5 fragment?是否存在有效的 HTML5 片段之类的东西?
【发布时间】:2010-11-09 12:14:10
【问题描述】:

如果不知道文档的其余部分是什么样子,我显然无法确定 HTML 片段是否有效(至少,我需要一个 doctype 才能知道我正在验证哪些规则)。但鉴于以下 HTML5 片段:

<article><header></article>My header</header><p>My text</p></article>

我当然可以确定它是无效,而无需查看文档的其余部分。那么,是否存在诸如“临时有效”的 HTML 或“如果它适合有效文档中的某个位置则有效”之类的东西?

除了下面的伪代码之外,还有更多内容吗?

def is_valid_fragment(fragment):
 tmp = "<!doctype html><html><head><title></title></head><body>" + fragment + "</body></html>"
 return my_HTML5_validator.is_valid_html5_document(tmp)

【问题讨论】:

  • 您的伪代码不适用于&lt;li&gt;item&lt;/li&gt;,因为它不能直接出现在正文中。您也可能对 DOM 规范中 DocumentFragment 的定义感兴趣。它代表文档树的一部分并且需要良好的格式,所以abc&lt;br/&gt;&lt;br/&gt; 是有效的片段,但&lt; 不是。我在 XML 或 HTML 规范中找不到片段的定义

标签: validation html fragment


【解决方案1】:

您当然可以谈论well-formedXML 文档,并且您可以从任何单个元素及其子元素构造一个文档。因此,您可以谈论具有良好格式的单根 XHTML5 片段。您可以通过将其作为文档序列处理或将其包装在一些合成容器元素中来处理多根片段(如&lt;img/&gt;&lt;img/&gt;) - 因为我们只是在谈论格式正确,这没关系。

但是,HTML5 仍然允许 SGML 自关闭标签,如&lt;hr&gt; 等,其自关闭性只能通过诉诸 doctype 来确定。例如,&lt;div&gt;&lt;hr&gt;&lt;/div&gt; 可以,但&lt;div&gt;&lt;tr&gt;&lt;/div&gt; 不行。如果您处理的是 DOM 节点而不是文本作为输入,这将不成问题,但如果您有文本,则需要一个对 HTML 有足够了解的解析器才能处理这些元素。不过,除此之外,一些直接从 XML 中提取的非常简单的规则就足以处理格式良好的问题。

如果您想超越格式良好并查看validity 的某些方面,我认为您仍然可以使用 XML 在单根片段级别上做到这一点。正如规范所说:

如果 XML 文档具有关联的文档类型声明并且文档符合其中表达的约束条件,则它是有效的。

DTD 可以将任何元素命名为根,然后该机制负责检查该元素与其子元素及其子元素等之间的关系,以及构成有效性的各种其他约束。

同样,您可以将这个想法直接转换为 HTML。不过,我不知道您如何处理多根片段。请记住,某些整个文档的约束(例如 ID 是唯一的)可能会保留在片段中,但一旦片段插入其中,则不会保留在其他有效的文档中。

【讨论】:

    【解决方案2】:

    根据您打算对此验证执行的操作,我认为您应该记住,浏览器非常容忍格式错误的 HTML!

    您在示例中给出的无效 HTML 字符串在(如果不是全部的话)浏览器中可以正常工作:

    const serializedHTML = "<article><header></article>My header</header><p>My text</p></article>"
    const range = document.createRange()
    const fragment = range.createContextualFragment(serializedHTML)
    console.log(fragment)

    上面sn-p中定义的片段内容会产生如下的DOM树:

    <article>
      <header></header>
    </article>
    "My header"
    <p>My text</p>
    

    【讨论】:

      【解决方案3】:

      一种粗略的方法是检查通过另一个元素的 innerHTML 传递片段是否会通过执行类似于以下代码的操作来更改文本。

      <html>
      <head>
      </head>
      <script>
      function validateHTML(htmlFragment) {
         var testDiv = document.getElementById('testDiv')
         testDiv.innerHTML = htmlFragment
         var res = htmlFragment==testDiv.innerHTML
         testDiv.innerHTML = ""
         return res
      }
      </script>
      <body>
      <div id=testDiv style='display:none'></div>
      
      <textarea id=txtElem onKeyUp="this.style.backgroundColor = validateHTML(this.value) ? '' : '#f00'"></textarea>
      
      </body>
      </html>
      

      【讨论】:

        【解决方案4】:

        你可以检查它是否格式正确。

        【讨论】:

        • 你可以通过解释如何做来改进这个答案。
        猜你喜欢
        • 1970-01-01
        • 2023-03-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-09-21
        • 1970-01-01
        相关资源
        最近更新 更多