如何修复错误嵌套/未关闭的HTML标记?

Bai*_*ose 17 html python algorithm xhtml

我需要通过使用正确的嵌套顺序关闭任何打开的标签来清理用户提交的HTML.我一直在寻找算法或Python代码来做到这一点但除了PHP中的一些半生不熟的实现之外没有找到任何东西.

例如,像

<p>
  <ul>
    <li>Foo
Run Code Online (Sandbox Code Playgroud)

<p>
  <ul>
    <li>Foo</li>
  </ul>
</p>
Run Code Online (Sandbox Code Playgroud)

任何帮助,将不胜感激 :)

小智 28

使用BeautifulSoup:

from BeautifulSoup import BeautifulSoup
html = "<p><ul><li>Foo"
soup = BeautifulSoup(html)
print soup.prettify()
Run Code Online (Sandbox Code Playgroud)

得到你

<p>
 <ul>
  <li>
   Foo
  </li>
 </ul>
</p>
Run Code Online (Sandbox Code Playgroud)

据我所知,你无法控制将<li> </ li>标签放在Foo的不同行上.

使用Tidy:

import tidy
html = "<p><ul><li>Foo"
print tidy.parseString(html, show_body_only=True)
Run Code Online (Sandbox Code Playgroud)

得到你

<ul>
<li>Foo</li>
</ul>
Run Code Online (Sandbox Code Playgroud)

不幸的是,我知道无法在示例中保留<p>标记.Tidy将其解释为一个空段而不是一个未闭合的段,这样做

print tidy.parseString(html, show_body_only=True, drop_empty_paras=False)
Run Code Online (Sandbox Code Playgroud)

出来了

<p></p>
<ul>
<li>Foo</li>
</ul>
Run Code Online (Sandbox Code Playgroud)

当然,最终,您的示例中的<p>标记是多余的,因此您可能会失去它.

最后,Tidy还可以进行缩进:

print tidy.parseString(html, show_body_only=True, indent=True)
Run Code Online (Sandbox Code Playgroud)

<ul>
  <li>Foo
  </li>
</ul>
Run Code Online (Sandbox Code Playgroud)

所有这些都有起伏,但希望其中一个足够接近.

  • 整洁的原因是它是一个空元素是因为不允许p元素包含ul元素. (3认同)

Nic*_*cki 10

通过Tidy或其中一个移植的运行它.

尝试手工编码,你想要挖出你的眼睛.


小智 5

使用html5lib,效果很好!像这样。

汤= BeautifulSoup(数据,'html5lib')