extensible stylesheet language - bfhamrhein/skripten/xml/xsltfolien.pdfxsl extensible stylesheet...

Post on 16-Aug-2020

8 Views

Category:

Documents

0 Downloads

Preview:

Click to see full reader

TRANSCRIPT

XSL

eXtensible Stylesheet Language

Die Stylesheet Sprache für XML

XSL ist ein World Wide Web Standard

• XSL ist ein vom World Wide Web Consortium empfohlener Standard

• W3C Recommendation von XSLT2.0 und XPath2.0Januar 2007

• W3C Proposed Recommendation der gesamten XSL, inklusive XSL Formatting Objects

August 2001

CSS �� XSL

W3C hat mit der Festlegung des XSL Standards begonnen, bevor derjenige von CSS festgelegt war.

Wozu gibt es zwei Style Sheet Sprachen?

CSS XSL

Verwendung mit HTML? ja neinVerwendung mit XML? ja jaTransformations-Sprache? nein jaSyntax CSS XML

CSS - Style Sheet für HTML-Files

• HTML benutzt vordefinierte (und darum allgemein bekannte) Tags:

<h1> Titel-Element<p> neuer Abschnitt,

...

• Im CSS wird definiert, wie die verschiedenen Elemente darzustellen sind (Fonts, Farben, ...)

h1 { font-family: sans-serif;

font-size: 48pt }

p { font-size: 8pt;

color: blue }

XSL – Style Sheet für XML

• XML benutzt keine vordefinierten Tags: <table> kann eine HTML Tabelle oder auch ein Möbelstück sein.

• Im XML-Dokument steht nicht, wie die Daten dargestellt werden sollen.

• Es braucht einen Mechanismus, welcher beschreibt, wie die Daten eines XML-Dokumentes dargestellt werden sollen.

XSL bietet diesen Mechanismus

XSL erzeugt beliebige Formate

XML(Daten)

C++

WordXML

XML

PostScript(XSL-FO)

Java

TeXPDF

(XSL-FO)

(X)HTML

XSL: Drei Teile / Drei Sprachen

Drei Teile

• eine Methode, um XML Dokumente zu transformieren,

• eine Methode, um XML Teile und Patterns zu adressieren

• eine Methode, um XML Dokumente zu formatieren

Drei Sprachen

• XSLT, die Sprache um XML umzuwandeln• XPath, die Sprache zum Adressieren und

Selektieren von XML-Knoten• XSL Formatting Objects (XSL FO), die Sprache

um formatierte Ausgabe zu beschreiben.

XSLT

XSL Transformations

XSL Transformations

• XSLT ist der wichtigste Teil des XSL Standard. XSLT wird benutzt, um XML Dokumente in andere (XML, HTML, ...) Dokumente umzuformen.

• XSLT kann auch neue (nicht im XML-Dokument enthaltene) Daten-Elemente in das Ausgabe-Dokument einfügen (zum Beispiel Formatier-Befehle), Elemente umsortieren oder weglassen.

• XSLT kann die XML-Knoten (zum Beispiel auch abhängig vom Wert des Elementes) verschieden behandeln (formatieren).

Wie funktioniert XSLT?

XSL

(Templates)

XML

(Daten)

AusgabeDokument

Wie funktioniert XSLT?

• XSLT benutzt im Transformations-Prozess die Sprache XPath, um die zu einem Template passenden Knoten herauszufiltern.

• Sobald im XML-Dokument ein passender Knoten (match) gefunden wird, formt XSLT diesen Knoten mit Hilfe der angegebenen Regeln (Template) um, und schreibt das Resultat ins Ausgabe-Dokument.

• Alle Text-Knoten des XML-Dokumentes, welche nicht zu einer Regel (einem Template) passen, werden unmodifiziert in das Ausgabe-Dokument kopiert.

Das Beispiel Dokument: People.xml

<?xml version="1.0"?><people>

<person><name>

<firstName>Alan</firstName><lastName>Turing</lastName>

</name><born date="1912" addressRef="gbl"/><died date="1954" addressRef="gbc"/><profession>computer scientist</profession><profession>mathematician</profession><profession>cryptographer</profession><hobby>philosophy</hobby><hobby>biology</hobby>

</person>...

XML Dokument mit Stylesheet Verbinden

<?xml version="1.0"?><?xml-stylesheet type="text/xsl"

href="http://www.abc.ch/mystyle.xsl"?><people>

<person><name>

<firstName >Alan</firstName><lastName>Turing</lastName>

</name>...

xsl:template

XSL benutzt Templates (Regeln), um zu bestimmen, wie die XML-Knoten umgeformt werden sollen.

Ein "match"-Attribut wird benutzt, um ein Knoten einem Template zuzuordnen.

<xsl:template match= Knoten >

Action

</xsl:template>

XSL: "hello world"

<?xml version="1.0" encoding="UTF-8"?>

<xsl:stylesheet version="2.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text" encoding="UTF-8"/>

<xsl:template match="people">hello world

</xsl:template>

</xsl:stylesheet>

hello world

XSL: "hello world"

<?xml version="1.0" encoding="UTF-8"?>

<xsl:stylesheet version="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text"/>

<xsl:template match="people">

hello world

</xsl:template>

<xsl:template match="person">

I am here

</xsl:template>

</xsl:stylesheet>

hello world

XSL: "hello world"

<?xml version="1.0" encoding="UTF-8"?>

<xsl:stylesheet version="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text"/>

<xsl:template match="person">

I am here

</xsl:template>

</xsl:stylesheet>

I am here

I am here

I am here

I am here

Great Britain London Germany UlmUSA Queens, NY Switzerland BaselGreat Britain Cambridge USA Princeton

Die wichtigsten xsl Befehle

<xsl: ... >

xsl:apply-templates

Der Befehl xsl:apply-templates sucht im XML den angegebene Pfad, eine Regel dazu und führt diese aus.

Welches Kind als nächstes behandelt werden soll, kann explizit ausgewählt werden durch ein select-Attribut <xsl:apply-templates select="person"/>

Der Befehl<xsl:apply-templates/>

sucht alle Kind (-Elemente) des aktuellen Knotens und führt deren Templates aus.

xsl:apply-templates

<?xml version="1.0" encoding="UTF-8"?>

<xsl:stylesheet version="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output method="text"/>

<xsl:template match="people">

<xsl:apply-templates select="person"/>

</xsl:template>

<xsl:template match="person">

I am here

</xsl:template>

</xsl:stylesheet>

I am hereI am hereI am hereI am here

xsl:call-template

<?xml version="1.0" encoding="UTF-8"?><xsl:stylesheet version="1.0“ xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:template match="people">

<xsl:call-template name="templ1"/>

</xsl:template>

<xsl:template name=" templ1"><xsl:apply-templates select="person"/>

</xsl:template>

<xsl:template match="person">I am here</xsl:template>

</xsl:stylesheet> I am hereI am hereI am hereI am here

xsl:for-each

Das gleiche Resultat erhalten wir durch

I am hereI am hereI am hereI am here

<xsl:template match="people">

<xsl:for-each select="person">

I am here

</xsl:for-each>

</xsl:template>

xsl:value-of

Das XSL <xsl:value-of> Element kann benutzt werden, um den Wert bestimmter Knoten auszugeben.

Beispiele:

<xsl:value-of select="lastName"/><xsl:value-of select="firstName"/><xsl:value-of select="hobby" separator=", " />

<xsl:template match="people"><html>

<head><title> Famous Scientists</title></head><body><h4> Famous Scientists</h4>

<xsl:apply-templates select="person"/></body>

</html></xsl:template>

<xsl:template match="person"><p/> <xsl:apply-templates select="name"/>

</xsl:template>

<xsl:template match="name"><xsl:value-of select="lastName"/><xsl:text> </xsl:text><xsl:value-of select="firstName"/>

</xsl:template>

Adressieren von Attributen

<xsl:template match="person"><b><xsl:apply-templates select="name"/></b><xsl:text> </xsl:text><small>

( <xsl:value-of select="born/@date"/> -<xsl: value-of select="died/@date"/>)

</small><p/>

</xsl:template>

Es ist möglich, für dieselben Knoten mehrere, verschiedene Templates zu definieren, die dann kontextabhängig angewandt werden.

Der Aufruf des Templates sowie das Template selber erhalten ein mode Attribute.

Damit können zum Beispiel Inhaltsverzeichnisse, Querverweise oder verschiedene Darstellungen der gleichen Datenelemente erzeugt werden.

Templates mit Modes

<xsl:template match="people"><html> <body>

<h4>Table of Contents</h4><ul><xsl:apply-templates select="person" mode="toc"/></ul><xsl:apply-templates select="person"/>

</body></html></xsl:template>

<xsl:template match="person" mode="toc"><li/><xsl:value-of select="name/lastName"/>

</xsl:template>

<xsl:template match="person"><p>

<b><xsl:apply-templates select="name"/></b><small> (<xsl:value-of select="born/@date"/> -<xsl:value-of select="died/@date"/>)</small>

</p></xsl:template>

Templates mit Modes

Der erste Durchgang wird durch<xsl:template match="person" mode="toc">

gebildet, der zweite durch<xsl:template match="person">

xsl:if

Mit Hilfe einer if-Anweisung können Knoten unterschiedlich behandelt werden

<xsl:if test="name/lastName = 'Euler' ">

<xsl:if test="born/@date > 1900 ">

<xsl:template match="person">

<xsl:if test="born/@date > 1900 ">

<xsl:apply-templates select="name"/>

</xsl:if>

</xsl:template>

XSL Test Operation

Die Bedingungen können mit and oder or verbunden werden.

<xsl:template match="person">

<xsl:if test="born/@date > 1850 andname/firstName != 'Alan' ">

<xsl:apply-templates select="name"/>

</xsl:if>

</xsl:template>

Richard Feynman

Albert Einstein

xsl:choose

Es gibt in XSL kein if-else Konstrukt. Anstatt eines if-else gibt es ein xsl:choose. Verzweigungen werden aus xsl:when und xsl:otherwise zusammengesetzt.

<xsl:choose><xsl:when test="...">

...</xsl:when><xsl:otherwise>

...</xsl:otherwise>

</xsl:choose>

<xsl:template match="person"><xsl:choose>

<xsl:when test="profession='mathematician' "><font color="blue">

<xsl:apply-templates select="hobby"/></font>

</xsl:when><xsl:otherwise>

<xsl:apply-templates select="hobby"/></xsl:otherwise>

</xsl:choose></xsl:template>

XSL Auswahl Operation

xsl:sort

Um eine Sequenz von Knoten während der Transformation (nach einem gewählten Schlüssel) zu sortieren, gibt es das sort Element:

<xsl:sort select="name/lastName"/>

xsl:sort kann entweder innerhalb eines <xsl:apply-templates> oder eines <xsl:for-each> Elements vorkommen.

Das select-Attribut gibt an, nach welchem Schlüssel sortiert werden soll.

<xsl:apply-templates select="person"><xsl:sort select="name/lastName" order="ascending"/>

</xsl:apply-templates>

XSL Sortier Operation

<xsl:sort> als Kind von <xsl:apply-templates>:

xsl:variable

In XSL können auch Konstanten definiert werden:

<xsl:variable name="ntext">value_of_variable

</xsl:variable>

Der Wert der Konstanten ntext kann mit $ntext gelesen werden:

<xsl:value-of select="$ntext"/>

Der Wert von ntext kann nicht verändert werden!

xsl:variable

Berechnen einer gewichteten Summe

<xsl:variable name="tmp"><tmpPrice>

<xsl:for-each select="book"><item>

<xsl:value-of select="price * quantity"/></item>

</xsl:for-each></tmpPrice>

</xsl:variable><xsl:value-of select="sum($tmp/tmpPrice/item)"/>

xsl:param

Beim Aufruf von Templates können Parameter übergeben werden

<xsl:apply-templates select="title"><xsl:with-param name="p1">

<xsl:value-of select="irgendein Wert"/></xsl:with-param>

</xsl:apply-templates>

Verwendung im Template:<xsl:template match="title">

<xsl:param name="p1"/>... verwenden von $p1 ...

</xsl:template>

xsl:for-each-group

<xsl:template match="people"><xsl:for-each-group select="address"

group-by="country"><xsl:value-of select="country"/>:<xsl:value-of select="current-group()/city"

separator=", "/><br/></xsl:for-each-group>

</xsl:template>

xsl:include / xsl:import

<xsl:import href= "URI" >und

<xsl:include href= "URI" > fügen das unter der angegebenen Adresse gefundene

Stylesheet ein.

<xsl:include href="ss.xsl"/>

<xsl:include href="http://www.sowieso.ch/ss.xsl"/>

Default Template Regeln

Was geschieht mit den Knoten, wenn es im Stylesheet dafür kein Template

gibt?

Text- und Attribut-Knoten

Von Text- und Attribut-Knoten wird der Wert des Textes (des Attributes) in das Ausgabe-Dokument kopiert.

Als XSL-Template sieht dies wie folgt aus:

<xsl:template match= " text() | @* "><xsl:value-of select="."/>

</xsl:template>

Root- und Element-Knoten

Vom Root- und von allen Element-Knoten werden per Default die Template-Regeln aller Kindknoten aufgerufen.

Als XSL-Template sieht dies wie folgt aus:

<xsl:template match= " / | * "><xsl:apply-templates/>

</xsl:template>

Kommentare / Verarbeitungsanweisung

Kommentare und Processing Instructions werden per Default ignoriert.

Als XSL-Template sieht dies wie folgt aus:

<xsl:template

match= "processing-instructions() | comment()" />

Es gibt keine Adressierung (keinen XPath Ausdruck) für Namespace-Knoten.

Template Drivenvs.

Data Driven

Schwach strukturierte XML Dokumente

Reports, Briefe, Webseiten, ....

<?xml version='1.0'?>

<book-review>

<title>This Book</title> by <author>This

Author</author>, by <publisher>The

Publisher</publisher> on <date>date</date>,

indeed a good book. However, the book titled

<title>Book</title> by the same publisher is

very bad. The reviewer ...

</book-review>

Data-Driven Template

<xsl:stylesheet version="1.0"

xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:template match="/">

<html><body>

<xsl:apply-templates/>

</body></html>

</xsl:template>

<xsl:template match="book-review">

<p> <xsl:apply-templates/> </p>

</xsl:template>

. . .

XPath

www.w3.org/TR/xpath

Adressierung

Die Templates im Stylesheet können nur dann richtig (an der richtigen Stelle) angewandt werden, wenn die Adressierung (match) korrekt ist.

XSL muss beliebige Knoten des XML-Dokumentes adressieren (identifizieren) können.

Dafür benutzt XSL die Sprache XPath.

XPath Beispiele

name alle <name> Kinder des aktuellen Knotens

name/firstName alle <firstName> Kinder aller <name> Kinder des aktuellen Knotens

/ der Root Knoten des Dokumentes

. der aktuelle Knoten

.. der Vorgänger (Parent) des aktuellen Knotens

//name alle <name> Elemente des Dokumentes

.//name alle <name> Nachfolger (direkt und indirekt) des aktuellen Knotens

XPath Syntax

• Die XPath-Syntax sieht ähnlich aus wie die übliche Filesystem-Adressierung.

• Das Pattern matching ist abhängig vom Kontext: Ein XPath Ausdruck kann verschiedene Knoten bezeichnen, abhängig von der Stelle im Dokument, in welchem er steht.

• XPath findet alle passenden Knoten. Sollen nur gewisse Knoten aus dem Pfad selektiert werden, kann der Pfad (durch Prädikate) eingeschränkt werden.

XPath Syntax

• Ein XPath ist absolut, falls er mit einem Slash (" / ") anfängt: /person

• Ein Pfad ist zusammengesetzt auf einer Reihe von Schritten, welche durch "/" getrennt sind:

people/person/born

• Attribute werden durch "@" markiert.born/@addressRef

• Pfade können kombiniert werden durch "|" (Auswahl)

name/firstName | profession | hobby

XPath: Wildcards

Pfade können Wildcards enthalten: *, @* und node().

* selektiert alle Elemente@* selektiert alle Attributenode() selektiert alle Knoten

Beispiele//* alle Elemente im Dokument/* alle Kinder von Rootstr/*/title alle <title> Enkel von str//*/@id alle Attribute mit Namen id

XPath Prädikate

XPath kann auch filtern. Dazu wird im select-Attribut zum Pfad ein Prädikat mit angegeben

<xsl:apply-templatesselect="person [name/firstName != 'Alan' ]"/>

Mögliche Filter-Operatoren sind:= gleich

!= ungleich&lt; kleiner als> grösser als

XPath Beispiele: Prädikate

born[ @addressRef = 'gbc' ]alle <born> Kinder, welche ein addressRef Attribut

mit Wert "gbc" haben

died[ @addressRef ] alle <died> Kinder, welche ein addressRef Attribut

haben

person [born/@date &gt; 1900 ]/namealle Namen von Personen, welche später als 1900

geboren sind

name[last()]das letzte <name> Kind des aktuellen Knotens

XPath Schritte

Jeder Schritt im Pfad ist ein Bezeichner, ein Wildcard oder ein Prädikat.

<xsl:template match="person"><xsl:apply-templates select="*[@date]"/>

</xsl:template>

<xsl:template match="born | died"><xsl:value-of select="../* /lastName"/>, <xsl:value-of select="name(.) "/>: <xsl:value-of select="@date"/><xsl:variable name="var" select="@addressRef"/><xsl:apply-templates select="//*[@id=$var]/city"/><br/>

</xsl:template>

Weitere Beispiele

//name/*alle Kinder von name

//name/*[@*]alle Kinder von name, die ein Attribut haben

//name/*[*]alle Kinder von name, welche keine Blätter sind

//*[@*]alle Elemente, die ein Attribut haben

//person[*/@id]/name

alle name Kinder von person Elementen, die ein Kind mit einem id Attribut haben

//*[@*]/*alle Kinder von Elementen, die ein Attribut haben

XPath Adressierung-Achsen

Es gibt für viele XPath-Adressen zwei Schreibweisen: die ausführliche und die abgekürzte. Bisher haben wir immer die abgekürzte Schreibweise benutzt.

Abkürzung für:attribute @child (default)parent ..self .descendant-or-self //

self

parent

ancestor

preceding

descendant

following

child

descendant-or-self

Adressierungs-Achsen

following-sibling

preceding-sibling

ancestor-or-self

XPath: child, self, parent

Child ist die Default-Richtung im Pfad. child:: kann immer weggelassen werden:

Statt self::* wird üblicherweise die abgekürzte Schreibweise ( . ) benutzt:

parent::* findet den (direkten) Vorgänger eines Knotens und kann abgekürzt werden durch ..

/child::people/child::person/child::profession

= /people/person/profession

XPath Funktionen

Die wichtigsten XPath Funktionen

Konvertierungsfunktionen

boolean( obj )number( obj )string( obj )

Negierungboolean not (value)

String Funktionen

concat(), substring(), contains(), Konkatenation, Substring bilden, Substring-Test

number string-length(string)

boolean matches (string, pattern)true, falls der gegebene String das Pattern erfüllt.

string replace (s1, pattern, s2)im String s1 werden alle Teile, welche das Pattern erfüllen, durch s2 ersetzt

Numerische Funktionen

abs(), avg(), max(), min() Absolutwert, Durchschnitt, Maximum, Minimum

round(), floor(), ceiling()Runden, Abrunden, Aufrunden

Grundoperationen+, -, *, mod, div

Numerische Funktionen (2)

<xsl:value-of select="sum(//number)"/>die Summe der Werte, welche in allen <number>-Knoten vorkommen.

<xsl:value-of select="sum(//book/quantity)"/>

berechnet die Anzahl vorhandene Bücher

format-number( -50.883, '#.0')ergibt den Wert -50.9

Funktionen auf Sequenzen

person[3], person[last()]filtert die dritte (letzte) Person heraus

position() gibt die Position des Knotens im Kontext zurück.

count()zählt die Anzahl Knoten der Knoten-Menge set.

count(//person) ergibt 4, count(//address) ergibt 6

Funktionen auf Sequenzen (2)

boolean empty(items)

ergibt true, falls items eine leere sequenz

remove(), insert-before(), reverse(),

subsequence(), …

Funktionen auf Sequenzen zum Löschen, Einfügen, Umdrehen und Zerteilen der Sequenzen.

Datum und Zeit

current-date(), current-time()aktuelle Zeit, aktuelles Datum

format-date(date, pictureString) …

Beispiel:format-date(current-date(), ' [D]-[M]-[Y] ')

For-Ausdrücke

for $x in E1 return result

evaluiert result für jedes Element der Sequenz E1

sum(for $x in book return $x/price * $x/quantity)

summiert die price * quantity Werte aller order Elemente

Einlesen von XML-Dokumenten

Die Funktion

document($srcval )lädt das an der Adresse (URI) srcval gefundene Dokument.

Durch Definition einer Variable „input“ kann so auf die Elemente des Files „Daten.xml“ zugegriffen werden.

<xsl:variable name="input"select="document('Daten.xml')/person"/>

xsl:key, key()

Durch xsl:key kann eine Indexierung (Schlüssel) von Elementen angelegt werden.

Alle ../born/@date-Attribute von name-Elementen:

<xsl:key name="myKey1" match="name"use="../born/@date"/>

Alle Anfangsbuchstaben von hobby-Elementen:

<xsl:key name="myKey2" match="hobby"use="substring(.,1,1)"/>

xsl:key, key()

Die XPath Funktion key() gibt dann die entsprechenden Elemente zurück.

<xsl:apply-templates select="key('myKey1','1912')"/>

gibt alle name-Knoten mit Geburtstjahr 1912 zurück.

<xsl:apply-templates select="key('myKey2','p')"/>

gibt alle hobby-Knoten mit Anfangsbuchstabe "p" zurück.

People Beispiel: address ID auflösen

Schlüssel definieren<xsl:key name="addrKey" match="address"

use="@id"/>

Schlüssel benutzen<xsl:template match="person">

<xsl:apply-templatesselect="key('addrKey', born/@addressRef)"/>

</xsl:template>

xsl:function

<xsl:stylesheet "version="2.0"

xmlns:xsl="http://www.w3.org/1999/XSL/Transform

xmlns:cs="http://www.isbe.ch/catalogFunctions"

xmlns:xs='http://www.w3.org/2001/XMLSchema'>

<!-- function definition -->

<xsl:function name="cs:substring"><xsl:param name="str" as="xs:string"/><xsl:param name="n" as="xs:integer"/><xsl:sequence select= "if( string-length($str) &gt;=$n )

then substring($str,1,$n) else error() "/></xsl:function>

Exkurs: XQuery

Übungen

top related