Как заставить HTML5 работать с DOMDocument?

Я пытаюсь проанализировать HTML-код с помощью DOMDocument, сделать что-то вроде изменений в нем, а затем собрать его обратно в строку, которую я отправляю на выход.

Но есть несколько проблем, связанных с анализом, что означает, что то, что я отправляю в DOMDocument, не всегда возвращается в той же форме :)

Вот список:

using ->loadHTML:

formats my document regardless of the preserveWhitespace and formatOutput settings (loosing whitespaces on preformatted text) gives me errors when I have html5 tags like <header>, <footer> etc. But they can be supressed, so I can live with this. produces inconsistent markup - for example if I add a <link ... /> element (with a self-closing tag), after parsing/saveHTML the output will be <link .. >

using ->loadXML:

encodes entities like > from <style> or <script> tags: body > div becomes body &gt; div all tags are closed the same way, for example <meta ... /> becomes <meta...></meta>; but this can be fixed with an regex.

Я не пробовал HTML5lib, но я предпочел DOMDocument вместо пользовательского парсера по соображениям производительности

Update:

Таким образом, как упоминается Honeymonster, использование CDATA решает основную проблему с loadXML.

Можно ли как-нибудь предотвратить самозакрытие всех пустых тегов HTML, кроме определенного набора, без использования регулярных выражений?

Прямо сейчас у меня есть:

$html = $dom->saveXML($node);

$html = preg_replace_callback('#<(\w+)([^>]*)\s*/>#s', function($matches){

       // ignore only these tags
       $xhtml_tags = array('br', 'hr', 'input', 'frame', 'img', 'area', 'link', 'col', 'base', 'basefont', 'param' ,'meta');

       // if a element that is not in the above list is empty,
       // it should close like   `<element></element>` (for eg. empty `<title>`)
       return in_array($matches[1], $xhtml_tags) ? "<{$matches[1]}{$matches[2]} />" : "<{$matches[1]}{$matches[2]}></{$matches[1]}>";
}, $html);

который работает, но он также будет выполнять замены в контенте CDATA, который я не хочу ...

Ответы на вопрос(5)

Ваш ответ на вопрос