Отметим также, что спецификация языка XSLT определяет функциональность элемента xsl:output
как возможную, но не обязательную. Процессоры обязаны манипулировать логическими моделями XML-документов, но при этом они не обязаны поддерживать сериализацию и уметь выводить преобразованный XML-документ как последовательность байт. Конечно же, абсолютное большинство процессоров поддерживает такую возможность, но при всем том она остается не более чем возможностью.
Поэтому из соображений переносимости можно лишь только надеяться, что документ будет выведен так, как было задумано. Не следует исключать возможности, что в определённых условиях процессор не сможет контролировать процесс вывода документа.
Типичным примером такой ситуации может быть использование процессора совместно с другими компонентами, которые обмениваются с процессором документами в виде DOM-структур, но сами загружают и выводят документы. В этом примере компоненты, занимающиеся выводом преобразованного документа, могут спокойным образом игнорировать все то, что было указано в элементе xsl:output
или в атрибутах disable-output-escaping
других элементов преобразования. Более того, они даже не будут знать, что было там указано, поскольку эти значения не касаются процесса преобразования как такового — они относятся к выводу, контролировать который процессор в данном случае не может.
Отсюда следует однозначный вывод: не нужно чересчур злоупотреблять возможностями xsl:output
и disable-output-escaping
.
Замена специальных символов
Как мы уже знаем, в XML есть несколько специальных символов, которые, как правило, заменяются процессором при выводе документа на соответствующие символьные или встроенные сущности. К примеру, для того, чтобы вывод был корректным XML-документом, процессор обязан заменять символы " <
" и " &
" на встроенные ( <
и &
) или символьные ( <
и &
) сущности.
Между тем довольно часто бывает необходимым выводить в выходящем документе символы разметки.
Пример
Пусть входящий документ содержит описание товара, заданное в секции CDATA:
big and grey animal!]]>
Если мы будем преобразовывать этот документ с использованием шаблона
то в выходящем документе специальные символы будут заменены:
An elephant
This is a big and grey animal!
Для того чтобы избежать замены, можно воспользоваться атрибутом disable-output-escaping
(отменить замену символов) элементов xsl:value-of
и xsl:text. Этот атрибут может принимать значения "yes"
и "no"
("no" — значение по умолчанию). Значение "yes"
означает, что процессор при выводе текста, создаваемого xsl:text
или xsl:value-of
не должен заменять специальные символы. Если бы в предыдущем примере мы использовали преобразование.
Листинг 8.56. Преобразование, содержащее disable-output-escaping
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
то на выходе мы бы получили документ
An elephant
This is a big and grey animal!
Атрибут disable-output-escaping
налагает ряд ограничений на использование текстовых узлов, генерируемых элементами xsl:text
и xsl:value-of
: эти узлы не могут входить в качестве текстового содержимого в узлы атрибутов, комментариев или инструкций по обработке. Кроме того, дерево, содержащее текстовые узлы, для которых была отменена замена специальных символов, не может быть приведено к строке или числу. И в том и в другом случае процессор может либо выдать ошибку преобразования, либо проигнорировать отмену замены специальных символов.
Атрибут disable-output-escaping
имеет также и более концептуальное ограничение. Процессор сможет отменить замену символов только в том случае, когда он сам будет контролировать процесс вывода. Как мы уже обсуждали в предыдущем разделе, ситуации, когда процесс вывода не будет выполняться самим процессором, не такая уж и редкость. Поэтому следует использовать disable-output-escaping
только в тех случаях, когда другой альтернативы нет или когда имеется полная уверенность, что этот метод будет работать.
Атрибут disable-output-escaping
работает с методами вывода "xml"
и "html"
, но не оказывает никакого влияния на метод "text"
, поскольку при этом методе все специальные символы и так выводятся без замены.
Кодировки в XSLT-преобразованиях
Несмотря на то, что в логических деревьях, которыми манипулирует XSLT, текстовые узлы представляются в кодировке Unicode, очень часто в обрабатываемых документах бывает необходимо использовать также другие кодировки. К примеру, большинство русскоязычных документов хранятся в кодировках UTF-8 и KOI8-R.
Читать дальше