Verlinkte Dokumente erstellen

(Auszug aus "XSLT Kochbuch" von Sal Mangano)

Problem

Sie möchten XML nach HTML mit Hyperlinks darin konvertieren.

Lösung

Eine typische Vorgehensweise bei der Konvertierung von XML nach HTML besteht aus zwei oder mehreren Durchgängen über das XML, um die Menü- bzw. Indexseiten sowie die Seiten mit dem eigentlichen Inhalt zu erstellen. Die Menüseiten enthalten dann Links auf die Inhaltsseiten. (Hierfür genügt eine XSLT 1.0-Lösung.) Die folgende Lösung generiert Seiten für den Index und eine Zusammenfassung von SalesBySalesPerson.xml:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:saxon="http://icl.com/saxon" extension-element-prefixes="saxon">
  <xsl:output method="html"/>
  <xsl:template match="/">
    <xsl:apply-templates select="*" mode="index"/>
    <xsl:apply-templates select="*" mode="content"/>
  </xsl:template>
  <!-- =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  = -->
  <!--                Erzeuge index.html  (mode = "index")                       -->
  <!-- =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  = -->
  <xsl:template match="salesBySalesperson" mode="index">
    <saxon:output href="index.html">
      <html>
        <head>
          <title>Sales By Salesperson Index</title>
        </head>
        <body bgcolor="#FFFFFF" text="#000000">
          <h1>Sales By Salesperson</h1>
          <xsl:apply-templates mode="index"/>
        </body>
      </html>
    </saxon:output>
  </xsl:template>
  <xsl:template match="salesperson" mode="index">
    <h2>
      <a href="{concat(@name,'.html')}">
        <xsl:value-of select="@name"/>
      </a>
    </h2>
  </xsl:template>
  <!-- =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  = -->
  <!--               Erzeuge @name.html  (mode = "content")                      -->
  <!-- =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  = -->
  <xsl:template match="salesperson" mode="content">
    <saxon:output href="{@name}.html">
      <html>
        <head>
          <title><xsl:value-of select="@name"/> Sales</title>
        </head>
        <body bgcolor="#FFFFFF" text="#000000">
          <h1><xsl:value-of select="@name"/> Sales</h1>
          <ol>
            <xsl:apply-templates mode="content"/>
          </ol>
        </body>
      </html>
    </saxon:output>
  </xsl:template>
  <xsl:template match="product" mode="content">
    <li><xsl:value-of select="@sku"/>&#xa0;&#xa0;&#xa0;&#xa0;&#xa0;&#xa0;$<xsl:value-of select="@totalSales"/></li>
  </xsl:template>
</xsl:stylesheet>

Beachten Sie, wie die Modi die Transformation der XML-Elemente in einen Index- und einen Informationsinhalt für jede HTML-Seite eines Verkäufers trennen. In HTML-Transformationen werden Modi häufig eingesetzt, weil man mit ihnen Daten in einem einzigen Stylesheet auf mehrere Arten darstellen kann.

In diesem Fall soll das Stylesheet auf eine Verwendung im Stapelbetrieb beschränkt sein. Dabei können Sie einen Parameter angeben, um zu kontrollieren, welches Dokument erzeugt wird. Dieser Parameter macht außerdem die nicht-standardgemäße Erweiterung saxon:output überflüssig (die Sie auch dann nicht brauchen, wenn Sie XSLT 2.0 verwenden):

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output method="html"/>
  <!-- Gibt an, welches Dokument ausgegeben wird -->
  <!-- INDEX : erzeugt das Indexdokument -->
  <!-- Verkäufername : erzeugt die Seite für diesen Verkäufer -->
  <xsl:param name="which" select="'INDEX'"/>
  <xsl:template match="/">
    <xsl:choose>
      <xsl:when test="$which='INDEX'">
        <xsl:apply-templates select="*" mode="index"/>
      </xsl:when>
      <xsl:otherwise>
        <xsl:apply-templates select="*/salesperson[@name = $which]" mode="content"/>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>
  <!-- =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  = -->
  <!--            Erzeuge index.html  (mode = "index")                           -->
  <!-- =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  = -->
  <xsl:template match="salesBySalesperson" mode="index">
    <!-- saxon:output entfernt. Der Rest ist gleich. -->
  </xsl:template>
  <!-- ... -->
  <xsl:template match="salesperson" mode="content">
    <!-- saxon:output entfernt. Der Rest ist gleich. -->
  </xsl:template>
  <!-- ... -->
</xsl:stylesheet>

Diese Technik wäre noch ein wenig robuster, falls alle Verkäufer eine ID statt ihren Namen als Parameter verwenden würden.

Diskussion

Diese Lösung erzeugt keinen schicken Inhalt, aber sie illustriert die grundlegende Mechanik bei der Erstellung von verlinkten HTML-Inhalten. Um alle Webseiten mit einem einzigen Stylesheet zu erzeugen, mussten Sie ein nicht-standardisiertes XSLT 1.0-Element (saxon:output) verwenden. Ähnliche Erweiterungen gibt es in den meisten Prozessoren, und XSLT 2.0 kennt hierfür xsl:result-document.

Das Stylesheet produziert relative Links, also genau das, was Sie meistens haben wollen. Wenn Sie jedoch absolute Links benötigen sollten, dann können Sie, anstatt im Code eine URL fest anzugeben, einen Parameter auf oberster Ebene einführen, der auf diese URL gesetzt werden kann:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output method="html"/>
  <xsl:param name="URL" select="http://www.mycompany.com/"/>
  <!-- ausgelassen ... -->
  <xsl:template match="salesperson" mode="index">
    <h2>
      <a href="{$URL}{@name}.html'">
        <xsl:value-of select="@name"/>
      </a>
    </h2>
  </xsl:template>
</xsl:stylesheet>

Siehe auch

Im Rezept Objektorientierte Wiederverwendung und Entwurfsmuster emulieren finden Sie weitergehende Information darüber, wie man mehrere Ausgabedokumente erzeugt.

Der von diesen Transformationen erzeugte Inhalt ist nicht besonders benutzerfreundlich. In den Rezepten HTML-Tabellen erzeugen und Frames erzeugen werden Sie sehen, wie Sie die Ästethik dieser Ergebnisse verbessern können.

  

<< zurück vor >>

 

 

 

Tipp der data2type-Redaktion:
Zum Thema XSLT bieten wir auch folgende Schulungen zur Vertiefung und professionellen Fortbildung an:

Copyright © 2006 O'Reilly Verlag GmbH & Co. KG
Für Ihren privaten Gebrauch dürfen Sie die Online-Version ausdrucken.
Ansonsten unterliegt dieses Kapitel aus dem Buch "XSLT Kochbuch" denselben Bestimmungen, wie die gebundene Ausgabe: Das Werk einschließlich aller seiner Teile ist urheberrechtlich geschützt. Alle Rechte vorbehalten einschließlich der Vervielfältigung, Übersetzung, Mikroverfilmung sowie Einspeicherung und Verarbeitung in elektronischen Systemen.

O'Reilly Verlag GmbH & Co. KG, Balthasarstraße 81, 50670 Köln, kommentar(at)oreilly.de