xsl:import

(Auszug aus "XSLT 2.0 & XPath 2.0" von Frank Bongers, Kapitel 6.)

A | B | C | D | E | F | G | H | I | J | K | L | M | N | O | P | Q | R | S | T | U | V | W | X | Y | Z

 

Das Toplevel-Element xsl:import importiert den Inhalt eines externens XSL-Stylesheetmoduls in das aktuelle Stylesheet oder Stylesheetmodul und fügt auf diese Weise extern liegende Template-Regeln und Deklarationen den lokalen des importierenden Stylesheets hinzu.

Klassifizierung Deklaration
Funktionsgruppe Stylesheetstruktur
Einführung XSLT 1.0

Position im Stylesheet und erlaubte Inhalte:

Die Deklaration xsl:import ist nur als Toplevel-Element gestattet. Es muss dabei in Dokumentreihenfolge allen anderen Toplevel-Elementen vorangehen, auch eventuell vorhandenen xsl:include-Deklarationen. Beliebig viele xsl:import-Anweisungen dürfen aufeinander folgen. Das Element selbst ist stets leer.

Attribute:

Es gelten die Standardattribute. Zusätzlich besitzt xsl:import ein obligatorisches Attribut href.

href

Wert

uri-reference

Verwendung

Obligatorisch

Einführung

XSLT 1.0

Das href-Attribut enthält den URI des zu importierenden externen Stylesheets. Handelt es sich um einen relativen URI, so wird er in Bezug auf den Basis-URI des importierenden Moduls aufgelöst. Die Unterstützung von Fragment Identifiern ist Anwendungen freigestellt, jedoch nicht vorgeschrieben, sodass nicht vorhersagbar ist, ob und wie in XML-Dokumente eingebettete (also über ID-Referenz angesprochene) Stylesheets importiert werden können.

Verwendungszweck:

xsl:import importiert die Deklarationen und Template-Regeln externer XSLT-Stylesheets in ein Hauptstylesheet (principal sty­lesheet module). Für den folgenden Verarbeitungsprozess gilt die Gesamtheit aller lokalen und importierten Template-Regeln. Es ist somit möglich, bestimmte, öfter verwendete Regeln als externe Module in separate Stylesheets auszulagern und bei Bedarf in beliebige Rumpfstylesheets zu importieren.

Die importierten Stylesheetinhalte (Template-Regeln und Deklarationen) behal­ten jeweils ihren Basis-URI sowie auf sie bezogene Namensraumdeklarationen innerhalb der importierten Stylesheetmodule. Analog bleiben Namensraumde­klarationen des Hauptstylesheets auf dieses beschränkt und erstrecken sich nicht auf importierte Module.

Hinweis – Erstellung kompatibler Stylesheets
Soll ein Stylesheet erstellt werden, das sowohl unter XSLT 1.0 als auch unter XSLT 2.0 ausgeführt werden soll, so ist es empfehlenswert, zwei unterschiedliche Hauptmodule (principal stylesheet modules) zu schreiben, die den Versionsstand version="1.0" respektive version="2.0" angeben und lediglich als Einstiegsmodule dienen. Mittels xsl:import bzw. xsl:include können von dort aus nun die jeweils gewünschten Module geladen werden (auch verschiedene). Jedes der Module kann nun einen individuellen Versionsstand besitzen, der auf »1.0« oder »2.0« steht, je nachdem, ob XSLT 2.0-Instruktionen enthalten sind oder nicht.

Die Rangordnung der Importe – Importpräzedenz
Die importierten Regeln und Deklarationen besitzen einen niedrigeren Rang als die lokal im importie­renden Stylesheet vorhandenen Regeln und Deklarationen. Aus diesem Grund wird beispielsweise im Konfliktfall zwischen Template-Regeln mit identischem match-Pattern den lokalen Regeln Vorrang eingeräumt. Formal wird diese Regelung als Importpräzedenz bezeichnet – eine importierte Template-Regel besitzt eine niedrigere Importpräzedenz.

Importkaskade
Ein importiertes Stylesheet darf selbst ein oder mehrere weitere Stylesheets durch eigene xsl:import-Deklarationen importieren. Die so indirekt ins Hauptstylesheet importierten Regeln haben alle jeweils eine niedrigere Präzedenz als die des importierenden Stylesheets.

Import mehrerer Stylesheets
Wird durch mehrere aufeinander folgende xsl:import-Anweisungen eine Reihe von externen Stylesheets importiert, so besitzt das durch die erste Anweisung in Dokumentreihenfolge importierte Stylesheet (und durch dieses seinerseits importierte Stylesheets) die niedrigste Importpräzedenz.

Das zuletzt importierte Modul (und wiederum durch dieses importierte Style­­sheets) hat dagegen die höchste Präzedenz unter allen importierten Stylesheets, jedoch stets eine niedrigere als lokal vorhandene Regeln.

Es ist kein Fehler, wenn ein Stylesheet mehrmals auch auf verschiedenen Hier­rachie-Ebenen importiert wird. Es darf sich jedoch niemals – direkt oder indi­rekt – ein Stylesheetmodul selbst importieren, da in diesem Fall ein nicht auflösbarer Zirkelbezug entstünde und der Prozessor die Verarbeitung abbrechen würde. (Der Umstand wird daher als statischer Fehler ERR XTSE0210 gewertet).

Verhalten in Bezug auf Template-Regeln xsl:template
Existieren im zusam­mengefassten Stylesheet mehrere in Bezug auf ihr match-Attribut oder ihren Namen identische Template-Regeln, so wird diejenige mit der höchsten Import­präzedenz instanziiert. Das jeweils importierende Style­sheet kann eine impor­tierte, auf Grund einer höherrangigen, lokalen Regel stillgelegte Template-Regel mit Hilfe der Instruktion xsl:apply-imports (gegebenenfalls auch mit xsl:next-match) aktivieren. Diese tritt in der lokalen Template-Regel einfach anstelle von xsl:apply-templates.

Verhalten in Bezug auf weitere Toplevel-Elemente

  • Attributsets xsl:attribute-set
    Attributsets gleichen expandier­ten Namens addieren sich zu einem Gesamtset, wobei im Falle konkurrierender Attributdeklarationen diejenige mit der höchsten Importpräzedenz gilt.
  • Zahlenformatdeklarationen xsl:decimal-format
    Gleichnamige xsl:decimal-format-Deklarationen aller Module werden jeweils addiert, desgleichen die unbenannten Deklarationen. Bei widersprüchlichen Werten eines Formatproper­ties bekommt jeweils der Wert aus der Deklaration mit der höchsten Importpräzedenz den Vor­rang. Ein Konflikt zweier Properties aus Deklarationen gleicher Importpräzedenz stellt allerdings einen statischen Fehler dar (ERR XTSE1290).

Achtung – Abweichung zu XSLT 1.0:
In XSLT 1.0 dürfen durch Import von Stylesheetmodulen keine Dopplungen bei Zahlenformatdeklarationen auftreten, ungeachtet von Import­präzedenzen. Gleichfalls dürfen auch nicht mehrere (unbenannte) Defaultdeklarationen vorliegen.

  • Schlüsseldeklarationen xsl:key
    Es werden grundsätzlich die Schlüsselde­klarationen aller importierten Module verwendet – Importpräzedenzen spie­len keine Rolle.
  • Globale Parameter und Variable xsl:param und xsl:variable
    Globale Parameter und Variable gleichen Namens sind erlaubt, solange sie verschie­dene Importpräzedenz besitzen. Eine Referenz auf sie wird jedoch in Bezug auf die Variable bzw. den Parameter mit der höchsten Präzedenz ausgewer­tet. Mit anderen Worten: Gleichnamige Variable niedrigerer Präzedenz wer­den durch solche mit höherer Präzedenz »überschattet«.
  • Namespace-Aliasing mit xsl:namespace-alias
    Liegen in Stylesheetmo­dulen mehrere xsl:namespace-alias-Deklarationen vor, die sich auf das gleiche Namensraumpräfix beziehen, so wird diejenige mit der höchsten Importpräzedenz verwendet. Liegen gleichartige Deklarationen mit identi­scher Importpräzedenz vor, so kann dies als Fehler gewertet werden.
  • Whitespacebehandlung durch xsl:preserve-space und xsl:strip-space
    Im Fall von Widersprüchen zwischen xsl:preserve-space- und xsl:strip-space-Deklarationen hat diejenige mit der höheren Importprä­zedenz den Vorrang. Bei gleicher Importpräzedenz gilt diejenige Regel mit dem spezifischer formulierten NameTest, also der höheren Priorität. Übli­cherweise werden Whitespace-Nodes in Elementen, für die gleichrangige xsl:preserve-space und xsl:strip-space-Anweisungen vorliegen, nicht entfernt.
  • Eigenschaften des Ergebnisdokuments xsl:output
    Gleichnamige benannte sowie unbenannte xsl:output-Deklarationen aller Module wer­den jeweils addiert. Bei widersprüchlichen Werten hat jeweils die Deklara­tion mit der höchsten Importpräzedenz den Vorrang.

Vergleich: xsl:import vs. xsl:include
Ähnlich xsl:import kann auch die Anweisung xsl:include zum Zusammenfassen mehrerer Styles­heets verwendet werden. Die Deklaration xsl:include kennt jedoch das Prin­zip der Importpräzedenz nicht, sondern fügt den Inhalt des inkludierten Styles­heets gleichrangig dort ein, wo die Deklaration steht. Dies muss jedoch, anders als bei xsl:import, nicht zwangsläufig am Anfang des Hauptstylesheets sein. (Welche Template-Regel bei dergestalt sich ergebenden Dubletten gilt, hängt von der durch den Ort der Inklusion bestimmten letztendlichen Dokumentreihenfolge ab. Ein Prozessor gibt im entsprechenden Fall meist der letzten Regel den Vorrang.)

Beispiele:

Beispiel 1 – Direkter Import zweier Stylesheets:

Hauptstylesheet:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
  <!-- importiert Modul 1 ins Hauptstylesheet: -->
  <xsl:import href="importbeispiel_1.xsl"/>
  <!-- importiert Modul 2 ins Hauptstylesheet: -->
  <xsl:import href="importbeispiel_2.xsl"/>
  <xsl:template match="/">
    <importbeispiel>
      <xsl:apply-templates/>
    </importbeispiel>
  </xsl:template>
  <xsl:template match="a">
    <ausgabe>
      <!-- Verarbeitung des Elements <a> -->
      <xsl:apply-templates/>
    </ausgabe>
  </xsl:template>
</xsl:stylesheet>

Das Hauptstylesheet enthält zwei Importanweisungen für externe Stylesheets und eine Template-Regel zur Verarbeitung eines Elements <a>.

Erstes importiertes Stylesheet (Modul 1):

<!-- importbeispiel_1.xsl -->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
  <xsl:template match="a">
    <extern1>
      <!-- Verarbeitung des Elements <a> -->
      <xsl:apply-templates/>
    </extern1>
  </xsl:template>
  <xsl:template match="b">
    <extern1>
      <!-- Verarbeitung des Elements <b> -->
      <xsl:apply-templates/>
    </extern1>
  </xsl:template>
  <xsl:template match="c">
    <extern1>
      <!-- Verarbeitung des Elements <c> -->
      <xsl:apply-templates/>
    </extern1>
  </xsl:template>
</xsl:stylesheet>

Das zuerst importierte Stylesheet Modul 1 besitzt gleichfalls eine Template-Regel für das Element <a> und zusätzlich eine weitere Regel für die Elemente <b> und <c>. Die Regeln fügen um den Inhalt entsprechender Elemente jeweils ein Literal Result Element <extern1> ein. Die Regel zu <a> ist jedoch, da importiert, niederrangiger als die des Hauptstylesheets und tritt nicht in Kraft.

Zweites importiertes Stylesheet (Modul 2):

<!-- importbeispiel_2.xsl -->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
  <xsl:template match="b">
    <extern2>
      <!-- Verarbeitung des Elements <b> -->
      <xsl:apply-templates/>
    </extern2>
  </xsl:template>
  <xsl:template match="d">
    <extern2>
      <!-- Verarbeitung des Elements <d> -->
      <xsl:apply-templates/>
    </extern2>
  </xsl:template>
</xsl:stylesheet>

Das zweite importierte Stylesheet Modul 2 besitzt, wie das zuerst importierte Modul 1, eine Tem­plate-Regel für Element <b> und zusätzlich eine Regel für Element <d> (für das bisher noch keine Regel existierte). Das in diesem Fall eingefügte Literal Result Element nennt sich <extern2>. Da Modul 2 nach Modul 1 importiert wird, gelten zu Modul 1 gleichnamige Regeln als höherrangig (dies betrifft die Regel zu <b>, wo Modul 2 die Regel aus Modul 1 überschreibt).

Quelldokument:

<?xml version="1.0" encoding="ISO-8859-1"?>
<beispiel>
  <a>Inhalt a</a>
  <b>Inhalt b</b>
  <c>Inhalt c</c>
  <d>Inhalt d</d>
</beispiel>

Ergebnisdokument:

<?xml version="1.0" encoding="utf-8"?>
<importbeispiel>
  <ausgabe>Inhalt a</ausgabe>
  <extern2>Inhalt b</extern2>
  <extern1>Inhalt c</extern1>
  <extern2>Inhalt d</extern2>
</importbeispiel>

Die Verarbeitung des Quelldokuments erfolgt für Element <a> durch das Hauptstylesheet, da die entsprechende Regel des ersten importierten Style­­sheets die geringere Importpräzedenz besitzt. Element <b> wird durch das zweite importierte Stylesheet verarbeitet, da dieses Vorang vor dem ersten importierten Stylesheet besitzt. Für Elemente <c> und <d> gibt es keine Kon­flikte, hier wird im ersten Fall eine Regel aus Modul 1, im zweiten eine aus Modul 2 eingesetzt.

Beispiel 2 – »Huckepack«-Import zweier Stylesheets:

Hauptstylesheet:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
  <!-- importiert Modul 1 ins Hauptstylesheet: -->
  <xsl:import href="importbeispiel_1b.xsl"/> 
  <xsl:template match="/">
    <importbeispiel>
      <xsl:apply-templates/>
    </importbeispiel>
  </xsl:template>
  <xsl:template match="a">
    <ausgabe>
      <!-- Verarbeitung des Elements <a> -->
      <xsl:apply-imports/>
    </ausgabe>
  </xsl:template>
</xsl:stylesheet>

Das Hauptstylesheet ist gegenüber dem vorigen Beispiel leicht modifiziert, insofern, als es nur ein einziges Stylesheet importbeispiel_1b.xsl importiert. Dieses importiert seinerseits das zweite Stylesheet.

Erstes importiertes Stylesheet (Modul 1b):

<!-- importbeispiel_1b.xsl -->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
  <!-- importiert Modul 2 in Modul 1: -->
  <xsl:import href="importbeispiel_2.xsl"/>
  <xsl:template match="a">
    <extern1>
      <!-- Verarbeitung des Elements <a> -->
      <xsl:apply-templates/>
    </extern1>
  </xsl:template>
  <xsl:template match="b">
    <extern1>
      <!-- Verarbeitung des Elements <b> -->
      <xsl:apply-templates/>
    </extern1>
  </xsl:template>
  <xsl:template match="c">
    <extern1>
      <!-- Verarbeitung des Elements <c> -->
      <xsl:apply-templates/>
    </extern1>
  </xsl:template>
</xsl:stylesheet>

Das Stylesheet importbeispiel_1b.xsl importiert seinerseits das zweite Style­sheet Modul 2 – das im vorigen Beispiel bereits verwendete importbeispiel_2.xsl. ­Dieses bleibt für dieses Beispiel, ebenso wie das zugrunde liegende Quelldokument, unverändert.

Durch die nun veränderten Importpräzedenzen wirkt sich die Modifikation jedoch im Ergebnisdokument aus: da die Regel für <b> in Modul 2 nun nicht mehr direkt ins Hauptstylesheet (und zwar nach der aus Modul 1), sondern in diesem Fall in Modul 1 importiert wird, gilt sie als niederrangiger als die gleichnamige Regel aus Modul 1. In diesem Kontext tritt daher die Regel aus Modul 2 nicht in Kraft, wie im Ergebnisdokument zu sehen.

Ergebnisdokument:

<?xml version="1.0" encoding="utf-8"?>
<importbeispiel>
  <ausgabe>Inhalt a</ausgabe>
  <extern1>Inhalt b</extern1>
  <extern1>Inhalt c</extern1>
  <extern2>Inhalt d</extern2>
</importbeispiel>

Das Element <b> wird nun durch das vom Hauptstylesheet direkt importierte Stylesheetmodul verarbeitet – die entsprechende Regel aus dem von diesem wiederum importierten Stylesheet besitzt die geringere Präzedenz. Ansonsten verhalten sich Beispiel 1 und 2 identisch.

Beispiel 1b – Aktivierung einer Template-Regel durch xsl:apply-imports:

Eine importierte Regel kann zusätzlich zu einer lokalen Regel verarbeitet wer­den, wenn anstelle der Instruktion xsl:apply-templates die Instruktion xsl:apply-imports verwendet wird. Hierfür wird die Template-Regel für Ele­ment <a> im Hauptstylesheet von Beispiel 1 dergestalt modifiziert, dass der Elementinhalt durch ein Literal Result Element <ausgabe> umgeben wird:

<xsl:template match="a">
  <!-- Verarbeitung des Elements <a> -->
  <ausgabe>
    <!-- ... unter Einbeziehung importierter Regeln: -->
    <xsl:apply-imports/>
  </ausgabe>
</xsl:template>

Es ergibt sich im Ergebnisdokument in diesem Fall folgende Veränderung:

<?xml version="1.0" encoding="utf-8"?>
<importbeispiel>
  <ausgabe>
    <extern1>Inhalt a</extern1>
  </ausgabe>
  <extern2>Inhalt b</extern2>
  <extern1>Inhalt c</extern1>
  <extern2>Inhalt d</extern2>
</importbeispiel>

Hier wird zuerst die lokale Template-Regel für <a> ausgeführt und der Elementknoten <ausgabe> erzeugt.

Die Anweisung xsl:apply-imports führt dazu, dass nach weiteren importierten Regeln gerin­gerer Importpräzedenz gesucht wird und diese anschließend ebenfalls ausgeführt werden: Das Resultat entspricht quasi dem Ineinanderschachteln der Templatebodies der lokalen und der importierten Regel.

Hinweis zum Aktivieren importierter Template-Regeln
Das Aktivieren stillgelegter importierter Template-Regeln durch xsl:apply-imports ist nur direkt aus dem importierenden Stylesheet (oder Modul) heraus möglich, nicht aus einem parallel importierten Modul. So ist es durch eine Modifikation der Stylesheets von Beispiel 1 nicht reali­sierbar, die Template-Regel für <b> aus dem ersten importierten Stylesheet aus der entsprechenden höherrangigen Regel des zweiten Stylesheets heraus zu aktivieren – im Fall von Beispiel 2 ist dies dagegen möglich (siehe Beispiel 2b)!

Beispiel 2b – Aktivierung einer Template-Regel durch xsl:apply-imports:

Importiert ein durch ein Hauptstylesheet importiertes Stylesheetmodul seinerseits ein weiteres Modul, so kann es dessen, auf Grund geringerer Importpräferenz stillgelegte, Stylesheetregeln aktivieren.

Die Regel für Element <b> in import_beispiel_1b.xsl wird also geringfügig modifiziert:

<!-- import_beispiel1b.xsl -->
<xsl:template match="b">
  <extern1>
    <!-- statt xsl:apply-templates: -->
    <xsl:apply-imports/>
  </extern1>
</xsl:template>

Das Ergebnisdokument von Beispiel 2 verändert sich in diesem Fall folgender­maßen (da jetzt ja die Regel aus Modul 2 zusätzlich aktiviert wird):

<?xml version="1.0" encoding="utf-8"?>
<importbeispiel>
  <ausgabe>Inhalt a</ausgabe>
  <extern1>
    <extern2>Inhalt b</extern2>
  </extern1>
  <extern1>Inhalt c</extern1>
  <extern2>Inhalt d</extern2>
</importbeispiel>

Analog zum vorigen Beispiel tritt die Regel des »huckepack« importierten Modul 2 zusätz­lich nach der Instanziierung derjenigen aus Modul 1 in Kraft.

Elementdefinition:

XSLT 1.0:

<!-- Category: top-level-element -->
<xsl:import 
     href = uri-reference 
/>

XSLT 2.0:

<!-- Category: declaration -->
<xsl:import
     href = uri-reference
/>
Tipp der data2type-Redaktion:
Zum Thema XSLT bieten wir auch folgende Schulungen zur Vertiefung und professionellen Fortbildung an:

Copyright © Galileo Press, Bonn 2008
Für Ihren privaten Gebrauch dürfen Sie die Online-Version ausdrucken.
Ansonsten unterliegt dieses Kapitel aus dem Buch "XSLT 2.0 & XPath 2.0 ― Das umfassende Handbuch" 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.


Galileo Press, Rheinwerkallee 4, 53227 Bonn