Проблема кодирования UTF-8 с XSLT через PHP - PullRequest
2 голосов
/ 08 сентября 2010

Я сталкиваюсь с неприятной проблемой кодирования при преобразовании XML через XSLT через PHP.

Проблема может быть кратко изложена следующим образом: когда я копирую (в кодировке UTF-8) файл XHTML с таблицей стилей XSLT, некоторые символы отображаются неправильно. Когда я просто показываю один и тот же файл XHTML, все символы отображаются правильно.

Следующие файлы иллюстрируют проблему:

XHTML

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
        <title>encoding test</title>
    </head>
    <body>
        <p>This is how we d&#239;&#223;&#960;&#955;&#509; &#145;special characters&#146;</p>
    </body>
</html>

1010 * XSLT * <?xml version="1.0" encoding="UTF-8"?> <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0"> <xsl:output method="xml" encoding="UTF-8"/> <xsl:template match="@*|node()"> <xsl:copy> <xsl:apply-templates select="@*|node()"/> </xsl:copy> </xsl:template> </xsl:stylesheet> PHP

<?php
  $xml_file = 'encoding_test.xml';
  $xsl_file = 'encoding_test.xsl';

  $xml_doc = new DOMDocument('1.0', 'utf-8');
  $xml_doc->load($xml_file);

  $xsl_doc = new DOMDocument('1.0', 'utf-8');
  $xsl_doc->load($xsl_file);

  $xp = new XsltProcessor();
  $xp->importStylesheet($xsl_doc);

  // alllow to bypass XSLT transformation with bypass=true request parameter
  if ($bypass = $_GET['bypass']) {
    echo file_get_contents($xml_file);
  }
  else {
    echo $xp->transformToXML($xml_doc);
  }
?>

Когда этот скрипт вызывается как таковой (например, с помощью http://localhost/encoding_test/encoding_test.php),, все символы в преобразованном документе XHTML выглядят нормально, кроме символов «и» (они открывают и закрывают одинарные кавычки). Я не эксперт по Unicode, но меня поражают две вещи:

  1. все другие символьные объекты интерпретируются правильно (что может означать что-то о UTF-8-ности &#145; и &#146;)
  2. пока, когда файл XHTML отображается неопосредованно (например, http://localhost/encoding_test/encoding_test.php?bypass=true), , все символы отображаются правильно.

Кажется, я объявил кодировку UTF-8 для вывода везде, где мог. Может быть, другие видят, что не так и можно исправить?

Заранее спасибо!

Рон Ван ден Бранден

1 Ответ

10 голосов
/ 08 сентября 2010

&#145; и &#146; не являются видимыми символами Unicode.

Это старые ссылки на символы HTML 1 для одинарных кавычек, но когда вы обрабатываете их с помощью процессора XSLT, процессор не видит одинарные кавычки, а символы Unicode с десятичными кодами 145 и 146, т.е. U + 0090 и U + 0091 .

Эти символы предназначены для частного использования (т. Е. Использование не определено консорциумом Unicode) Управляющие коды C1 .

Решение состоит в том, чтобы использовать правильные символы Unicode &#x2018; и &#x2019;.

1 Фактически это коды, которые соответствуют кодировке Windows-1252 . Они отображаются браузерами, но на самом деле недопустимы в HTML :

ПРИМЕЧАНИЕ. - Вышеуказанное объявление SGML, как и в HTML 2.0, указывает номера символов от 128 до 159 (от 80 до 9F в шестнадцатеричном формате) как UNUSED. Это означает, что числовые ссылки на символы в этом диапазоне (например, ’) являются недопустимыми в HTML. Ни ISO 8859-1, ни ISO 10646 не содержат символов в этом диапазон, зарезервированный для управляющих символов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...