Die Transformation von XML-Daten in ein anderes Format, das beispielweise HTML oder PDF sein kann, ist aus der Entwicklung von Web-Applikationen kaum noch wegzudenken. Für diese Aufgabe bietet das World Wide Web Consortium die eXtensible Stylesheet Language (XSL) an. Diese besteht aus den drei Komponenten:
XSL Transformations (XSLT) bildet die eigentliche Programmiersprache zur Beschreibung von XML-Transformationen.
Die XML Path Language (XPath) wird von XSLT genutzt, um auf XML-Dokumente beziehungsweise Teile davon zuzugreifen.
XSL Formatting Objects (XSL-FO) werden genutzt, um Formatierungen zu beschreiben.
Vom Arbeitsprinzip her ist XSLT mit dem UNIX-Werkzeug awk verwandt: Bedingungen (Template Match) oder Funktionen (Template Name) werden nacheinander auf die Eingabe angewendet. Diese hat bei awk Zeilen, bei XSLT liegt sie als Baumstruktur vor. Wie awk kann XSLT nicht auf seine Ausgabe zugreifen.
Beispiel 8.18: if-then-else in XSLT
<xsl:template match="/">
<xsl:choose>
<xsl:when test="$foobar = 'foo'">
<xsl:call-template name="foo"/>
</xsl:when>
<xsl:otherwise>
<xsl:call-template name="bar"/>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
Stylesheets, wie in XSLT geschriebene Programme aus historischen
Gründen heißen, sind ihrerseits XML-Dokumente. Daher ist XSLT
"geschwätzig", das heißt, sogar einfache Sprachkonstrukte erfordern
viel Schreibarbeit.
Beispiel 8.18
zeigt oben den nötigen Code, um ein if-then-else
in XSLT zu realisieren, unten das hierzu äquivalente PHP-Schnipsel in
Beispiel 8.19.
Wie die Document Style Semantics and Specification Language (DSSSL) für SGML ist XSLT eine funktionale Transformationssprache. Sie bringt daher die Nachteile funktionaler Programmiersprachen mit sich, beispielsweise den Umweg über Rekursion für das Ausdrücken von Schleifen oder Variablen, die eher konstant als variabel sind. Außerdem kann man die Vorteile der funktionalen Programmierung, etwa das Rechnen mit Funktionen als Datentypen oder die Programmierung mit Closures, nicht nutzen. Die bietet XSLT nicht.
Ein weiterer Nachteil von XSLT liegt in der Domänenbeschränkung: Während XSLT "alles über XML weiß" und diesbezügliche Funktionen anbietet, weiß es relativ wenig von Dingen, die nichts mit XML zu tun haben. Ohne die Einbeziehung von in anderen Programmiersprachen, beispielsweise Java, geschriebenen Programmen über Callbacks können XSLT-Stylesheets nicht mit der Welt jenseits von XML interagieren. Das Beziehen von Daten aus anderen Quellen wie einer Datenbank oder das Erzeugen von nicht textbasierten Ausgabeformaten wie Grafiken oder PDF ist ohne Fremdhilfe nicht möglich.
PHP 5 bietet, angelehnt an die Programmierschnittstelle des Mozilla-Projektes,
die Klasse XSLTProcessor
(Abbildung 8.4)
für die Ausführung von XSL-Transformationen an. Im Gegensatz zu den
bereits vorgestellten XML-Programmierschnittstellen von PHP 5 ist die
XSLT-Erweiterung in der Standardkonfiguration nicht aktiviert. Sie muss
über --with-xsl bei der Konfiguration des
Build-Prozesses aktiviert werden (siehe Anhang A).
Mit DOMDocument::load() werden in
Beispiel 8.21
zunächst XML-Dokument
(Beispiel 8.1)
und XSL-Stylesheet
(Beispiel 8.20) in
je ein Objekt der Klasse DOMDocument geladen. Mit den
Methoden importStylesheet() und transformToDoc()
wird das XSL-Stylesheet-Objekt einem XSLT-Prozessor-Objekt zugewiesen sowie
das Eingabedokument in ein neues Objekt der Klasse DOMDocument
transformiert.
Beispiel 8.20: XSL Stylesheet für den Buchkatalog
<?xml version="1.0" encoding="iso-8859-1"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="html" />
<xsl:template match="/">
<html>
<body>
<ul>
<xsl:for-each select="books/book">
<li>
<xsl:value-of select="author" /><br />
<xsl:value-of select="title" /><br />
ISBN: <xsl:value-of select="isbn" /><br />
</li>
</xsl:for-each>
</ul>
</body>
</html>
</xsl:template>
</xsl:stylesheet>
Beispiel 8.21: Transformation des Buchkatalogs von XML nach HTML mit XSLT
<?php
$document = DOMDocument::load('books.xml');
$stylesheet = DOMDocument::load('books.xsl');
$processor = new XSLTProcessor;
$processor->importStylesheet($stylesheet);
print $processor->transformToDoc($document)->saveXML();
?><?xml version="1.0" standalone="yes"?>
<html>
<body>
<ul>
<li>
Sebastian Bergmann<br/>
Professionelle Softwareentwicklung mit PHP 5<br/>
ISBN: 3-89864-229-1<br/>
</li>
<li>
Hakan Kücükyilmaz<br/>
PHP 5<br/>
ISBN: 3-89864-236-4<br/>
</li>
</ul>
</body>
</html>
Alternativ stehen die Methoden transformToUri() und
transformToXml() zur Verfügung, die das
Transformationsergebnis in einer Datei abspeichern oder als
String zurückliefern.
Die Parameter des XSL-Stylesheets können über die Methoden
getParameter(), setParameter() und
removeParameter() kontrolliert werden.
Über die XSL-Funktion php:function können beliebige
PHP-Funktionen aus einem XSL-Stylesheet heraus aufgerufen werden.
Dieser muss hierfür mit xmlns:php="http://php.net/xsl" den
entsprechenden Namespace deklarieren
(Beispiel 8.22).
Über die Methode registerPHPFunctions() des
XSLT-Prozessor-Objektes wird die Unterstützung für die Ausführung
von PHP-Funktionen in XSL-Stylesheets aktiviert
(Beispiel 8.23).
Beispiel 8.22: Verwendung einer PHP-Funktion in einem XSL-Stylesheet
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:php="http://php.net/xsl" version='1.0'>
<xsl:template match="/">
<xsl:value-of select="php:function('str_rot13', 'CUC 5')"/>
</xsl:template>
</xsl:stylesheet>
Beispiel 8.23: Transformation mit einem XSL-Stylesheet, das eine PHP-Funktion verwendet
<?php
$stylesheet = DOMDocument::load('php_function.xsl');
$processor = new XSLTProcessor;
$processor->registerPHPFunctions();
$processor->importStylesheet($stylesheet);
$result = $processor->transformToDoc(new DOMDocument);
print $result->saveXML();
?>PHP 5