Я использую Java 11 (AdoptOpenJDK 11.0.5 2019-10-15) на Windows 10. Я анализирую некоторые устаревшие файлы X HTML 1.1, которые принимают следующую общую форму:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" http://www.w3.org/MarkUp/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
<head>
<title>XHTML 1.1 Skeleton</title>
</head>
<body>
</body>
</html>
Я использую простой не проверяющий парсер:
DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
documentBuilderFactory.setNamespaceAware(true);
DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
final Document document;
try (InputStream inputStream = new BufferedInputStream(getClass().getResourceAsStream("xhtml-1.1-test.xhtml"))) {
document = documentBuilder.parse(inputStream);
}
По какой-то причине он добавляет дополнительные атрибуты, такие как xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
и xml:space="preserve"
повсюду:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" version="-//W3C//DTD XHTML 1.1//EN" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xml:lang="en">
<head xmlns="http://www.w3.org/1999/xhtml" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<title xmlns="http://www.w3.org/1999/xhtml" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">XHTML 1.1 Skeleton</title>
</head>
<body xmlns="http://www.w3.org/1999/xhtml" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xml:space="preserve"></body>
</html>
Я знаю, что DTD могут предоставлять значения атрибутов по умолчанию, но я не понимаю, почему был добавлен атрибут xmlns:xsi
, когда в этом пространстве имен отсутствуют элементы или атрибуты.
Кроме того xml:space="preserve"
, кажется, вообще неверен; я думаю, что только элементы вроде <pre>
должны иметь набор xml:space="preserve"
. ( Обновление: Спецификация HTML5 указывает, что HTML по умолчанию сохраняет пространство и что xml:space
не должно быть сериализовано в HTML, так что, возможно, это было частью рассуждения здесь. Я улучшу свой сериализатор HTML, чтобы он игнорировал атрибут xml:space
, что частично устранит эту проблему.)
Также обратите внимание на version="-//W3C//DTD XHTML 1.1//EN"
; это то, что мне не нужно или не нужно.
Я что-то не так делаю? Есть ли способ настроить парсер так, чтобы он не включал этот ненужный код?
Интересно, что это не проблема со строгим X HTML 1.0.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "https://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
<head>
<title>XHTML 1.0 Skeleton</title>
</head>
<body>
</body>
</html>
При разборе это дает то, что можно ожидать:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "https://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
<head>
<title>XHTML 1.0 Skeleton</title>
</head>
<body>
</body>
</html>
Но это проблема с -//W3C//DTD XHTML 1.1 plus MathML 2.0 plus SVG 1.1//EN
. Так что, похоже, это просто проблема X HTML 1.1.
Обновление: У меня есть несколько потенциально полезных новостей: если я создаю новый документ без DTD и импортирую все дерево документов в новый документ все это бессмысленно (что, очевидно, исходит из подразумеваемых атрибутов в DTD) исчезает, потому что у целевого документа вообще нет DTD. (См. Как принудительно удалить атрибуты с подразумеваемыми значениями по умолчанию из DTD в Java XML DOM .) Но это очень неэффективно; было бы неплохо вообще отключить это при разборе.