500 likes | 742 Views
XSLT – en introduktion. Digitalisering av kulturarvet. Idag. Vad är XSLT? Hur fungerar XSLT? XPath och noder XSLT:s notation Templates, repetitioner och villkor TEI. XSL-språk. XSLT Ett språk för att transformera XML-dokument X-PATH Ett språk för att navigera i XML-dokument
E N D
XSLT – en introduktion Digitalisering av kulturarvet david.gunnarsson@hb.se
Idag • Vad är XSLT? • Hur fungerar XSLT? • XPath och noder • XSLT:s notation • Templates, repetitioner och villkor • TEI
XSL-språk • XSLT • Ett språk för att transformera XML-dokument • X-PATH • Ett språk för att navigera i XML-dokument • XSL-FO • Ett språk för att formatera XML-dokument
Vad är XSLT? • Står för eXstensible Stylesheet Language for Transformation • Ett programmeringsspråk för att transformera XML-dokument • En W3C-standard • XSLT transforms an XML source-tree into an XML result-tree
Den röda tråden… DATA LOGIK GRÄNSSNITT XML XSLT XHTML(+CSS)
XML, XSLT, XHTML och CSS XML XSLT CSS Omvandling XHTML
Hur fungerar XSLT? <?xml version="1.0" encoding="iso-8859-1"?> <!DOCTYPE boksamling SYSTEM "boksamling.dtd"> <?xml-stylesheet type="text/xsl" href="boksamling.xsl"?> <boksamling> <bok/> </boksamling>
En post i XML-filen <bok> <forfattare> <fNamn>Sue</fNamn> <eNamn>Grafton</eNamn> </forfattare> <titel>L som i laglös</titel> <kategori>Deckare</kategori> <pris valuta="gbp">20</pris> </bok>
XSLT-kod <?xml version="1.0" encoding="ISO-8859-1" ?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns="http://www.w3.org/1999/xhtml"> <xsl:output method="html" indent="yes"/> <xsl:template match="/"> <xsl:apply-templates select="boksamling"/> </xsl:template> <xsl:template match="boksamling"> <xsl:apply-templates select="bok"/> </xsl:template> <xsl:template match="bok"> Författare: <xsl:value-of select="forfattare/fNamn"/> <xsl:text> </xsl:text> <xsl:value-of select="forfattare/eNamn"/><br /> Titel: <xsl:value-of select="titel"/><br /> Kategori: <xsl:value-of select="kategori"/><hr /> </xsl:template> </xsl:stylesheet>
XPath • Ett språk för att navigera i XML-dokument • En syntax för att definiera delar av ett XML-dokument • En W3C-standard • XSLT använder XPath för att navigera i XML-dokument
XPath - noder • XML-dokument behandlas som träd bestående av noder • Typer av noder • Element • Attributes • Text • Namespaces • Processing instruction • Comment <!-- kommentar --> • Document node (dokumentets rotelement)
XPath - noder <?xml version="1.0" encoding="iso-8859-1"?> <boksamling> <bok> <forfattare> <fNamn>Sue</fNamn> <eNamn>Grafton</eNamn> </forfattare> <titel>L som i laglös</titel> <kategori>Deckare</kategori> <pris valuta="gbp">20</pris> </bok> </boksamling>
XPath – Relationer mellan noder • Varje element och attribut har en och endast en förälder • Elementnoder har noll till många barn • Noder med samma förälder kallas syskon • Det första syskonet är äldst, det näst första är näst äldst och så vidare… • En förfader är en förälders förälder • En ättling är ett barns barn
XPath – Peka ut noder • Nodnamn – Pekar ut samtliga barn till noden • / - Pekar ut från rotelementet • // - Pekar ut noder i dokumentet från den aktuella nod som matchar utpekningen • . – Pekar ut aktuell nod • .. – Pekar ut föräldern till aktuell nod • @ - Pekar ut attribut
XPath – Peka ut noder • boksamling – Pekar ut samtliga barn till noden boksamling • /boksamling – Pekar ut rotelementet boksamling • boksamling/bok – Pekar ut alla bok-element som är barn till boksamling • //bok – pekar ut samtliga bok-element, oavsett var de befinner sig i hierarkin • boksamling//titel – Pekar ut samtliga titel-element som är ättlingar till boksamling, oavsett var de befinner sig i hierarkin • //@currency – Pekar ut samtliga attributnoder med namnet currency
Exempel: template-anrop <xsl:template match="boksamling"> <xsl:apply-templates select="bok/forfattare/eNamn"/> </xsl:template> • Gör att vi är säkra på att rätt eNamn hämtas, dvs det som är barn till forfattare som i sin tur är barn till bok
En annan variant <xsl:template match="boksamling"> <xsl:apply-templates select="bok//eNamn"/> </xsl:template> • Gör att vi är säkra på att rätt eNamn hämtas, dvs det som är ättling till bok
En tredje variant <xsl:template match="boksamling"> <xsl:apply-templates select="//forfattare/eNamn"/> </xsl:template> • Gör att vi är säkra på att rätt eNamn hämtas, dvs det som är barn till forfattare
En fjärde variant <xsl:template match="boksamling"> <xsl:apply-templates select="//eNamn"/> </xsl:template> • Fungerar om eNamn finns på endast en nivå i trädet • Skulle eNamn finnas på flera nivåer förväxlar tolken noderna med varandra • Att ha samma namn på noder på olika nivå i XML-trädet är dock ingen optimal lösning
Exempel: anropat template <xsl:template match="eNamn"> <xsl:value-of select="."/> <xsl:value-of select="../fNamn"/> <xsl:value-of select="../../titel"/> <xsl:value-of select="../../kategori"/> </xsl:template>
Operatorer • A=A (A är ekvivalent med A) • A!=B (A är inte ekvivalent med B) • A>B (A är större än B) • A<C (A är mindre än C) • A>=D (A är större än eller lika med D) • A<=E (A är mindre än eller lika med E) • Ett uttryck av detta slaget är antingen sant (true) eller falskt (false)
Operatorer • A=A and B!=C • Sant om och endast om A är ekvivalent med A och B inte är ekvivalent med C • A=A or B=C • Sant om A är ekvivalent med A eller om B är ekvivalent med C • Om första påståendet är sant kollas inte fler påståenden • not (A=B) • Sant om och endast om A inte är ekvivalent med B
Aritmetiska operatorer • + addition 5+2 • - subtraktion 7-2 • * multiplikation 8*3 • div division 6 div 3 • mod modulus 9 mod 2
XSLT • Förändra en icke presentabel fil till en webbsida • Formatera ett dokument till PDF eller liknande • Förändra en XML-vokabulär till en annan • Extrahera specifik information från ett dokument och formatera på ett annat sätt
XSLT:s notation • Alla element i XSLT innehåller prefixet xsl: <xsl:choose> </xsl:choose> <xsl:sort select="name"/> <xsl:value-of select="name"/>
Operatorer i XSLT • A=A A är ekvivalent med A • A!=B A är inte ekvivalent med B • 8 > 6 8 är större än 6 • 6 < 8 6 är mindre än 8 • A >= B A är större än eller lika med B • B <= A B är mindre än eller lika med A
Operatorer i XSLT • AND, OR och AND…! • pris < 10 and kategori = 'Deckare’ • pris < 10 or kategori = 'Deckare’ • pris < 10 and kategori != 'Deckare’
Templates • Innehåller regler som appliceras vid matchning av en specificerad nod • Syntax: <xsl:template name=”namn" match=”mönster" mode=”form" priority=”siffra"> … </xsl:template> • Samtliga attribut är valfria, men minst ett av attributen name och match måste återfinnas
Exempel, templates <xsl:template match="boksamling"> <xsl:apply-templates select="bok/forfattare/eNamn"/> </xsl:template> <xsl:template match="eNamn"> <xsl:value-of select="."/> <xsl:value-of select="../fNamn"/> <xsl:value-of select="../../titel"/> <xsl:value-of select="../../kategori"/> </xsl:template>
Exempel, templates med villkor <xsl:template match="boksamling"> <xsl:apply-templates select="bok/forfattare[eNamn='Grafton']"/> </xsl:template> <xsl:template match="forfattare"> <xsl:value-of select="eNamn"/> <xsl:value-of select="fNamn"/> <xsl:value-of select="../titel"/> <xsl:value-of select="../kategori"/> </xsl:template>
Repetitioner i XSLT: for-each <xsl:for-each select=“X-PATH-uttryck”> …kod som utförs på varje nod som överensstämmer med X-PATH-uttrycket </xsl:for-each>
Exempel: for-each <xsl:template match="/"> <xsl:for-each select="boksamling/bok"> <xsl:value-of select="forfattare/eNamn"/> <xsl:value-of select="forfattare/fNamn"/> <xsl:value-of select="titel"/> <xsl:value-of select="kategori"/> </xsl:for-each> </xsl:template>
Exempel: for-each med villkor <xsl:template match="/"> <xsl:for-each select ="boksamling/bok/forfattare[eNamn ='Grafton']"> <xsl:value-of select="eNamn"/> <xsl:value-of select="fNamn"/> <xsl:value-of select="../titel"/> <xsl:value-of select="../kategori"/> </xsl:for-each> </xsl:template>
Styrstrukturer i XSLT om (villkor a) utför a annars om (villkor b) utför b annars utför c
Med if <xsl:if test=”villkor a"> …kod som utförs om villkor a är sant </xsl:if> <xsl:if test=”villkor b"> …kod som utförs om villkor b är sant </xsl:if> <xsl:if test=”villkor c"> …kod som utförs om villkor c är sant </xsl:if>
Exempel: if <xsl:if test="pris < 10 and kategori != 'Deckare'"> <xsl:value-of select="forfattare/eNamn"/>:  <xsl:value-of select="titel"/> </xsl:if>
Med choose <xsl:choose> <xsl:when test=”villkor a"> ...kod som utförs om villkor a är sant </xsl:when> <xsl:when test=”villkor b"> ...kod som utförs om villkor b är sant </xsl:when> <xsl:otherwise> …kod som utförs om varken villkor a eller b är sant </xsl:otherwise> </xsl:choose>
Exempel: choose <xsl:choose> <xsl:when test="kategori='Deckare'"> <xsl:value-of select="titel"/>,  är en deckare </xsl:when> <xsl:otherwise> <xsl:value-of select="titel"/>,  är inte en deckare </xsl:otherwise> </xsl:choose>
TEI och XSLT • På samma sätt som en XML-fil kan transformeras med XSLT kan text uppmärkt med TEI transformeras • Även här används XPath för navigering
Den TEI-uppmärkta texten <?xml version="1.0" encoding="ISO-8859-1" standalone="no"?> <!DOCTYPE TEI.2 SYSTEM "http://www.adm.hb.se/~mg/dig/XMLLab/teilitex.dtd"> <?xml-stylesheet type="text/xsl" href="tei.xsl"?> <TEI.2> <teiHeader> <fileDesc> <titleStmt> <title>The Life and Opinions of Tristram Shandy, Gentleman, by Laurence Sterne: Electronic edition</title> … </TEI.2>
Ett XSLT-skal <?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="text"/> <xsl:template match="/"> <html> <head> </head> <body> </body> </html> </xsl:template> </xsl:stylesheet>
Lite innehåll… <html> <head> <title><xsl:value-of select="TEI.2/teiHeader/fileDesc/ titleStmt/title"/></title> </head> <body> <h1><xsl:value-of select="TEI.2/teiHeader/fileDesc/ titleStmt/title"/></h1> </body> </html>
Hämta allt med for-each <h1> <xsl:value-of select="TEI.2/teiHeader/fileDesc/ titleStmt/title"/> </h1> <xsl:for-each select="/TEI.2//*"> <p> <xsl:value-of select="."/> </p> </xsl:for-each>
OK, men det ser ju inte så lyckat ut… • /TEI.2//* matchar alla noder som befinner sig i TEI.2 • <xsl:value-of select="."/> skriver ut värdet på den nod som XSLT-processorn pekar på • Om en nod har fler än ett barn kommer innehållet i denna nod (plus dess barn) att skrivas ut lika många gånger som antalet barn
Templates <body> <xsl:apply-templates/> </body> • Skriver ut allt • Ytterligare templates och mer styrning behövs
Placering av nytt template <xsl:template match="/"> <html> <head> <title> <xsl:value-of select="TEI.2/teiHeader/fileDesc/titleStmt/title"/> </title> </head> <body> <xsl:apply-templates/> </body> </html> </xsl:template> <xsl:template match="div"> </xsl:template>
Två templates infogas… <xsl:template match="div"> <div style="border: 3px double black; padding: 50px; width: 750px;"> <xsl:apply-templates/> </div> </xsl:template> <xsl:template match="p"> <p> <xsl:apply-templates/> </p> </xsl:template>
Varför skrivs headern ut igen? <body> <xsl:apply-templates/> </body> • Skriver ut allt (inklusive teiHeader-noden) • Detta åtgärdas med hjälp av select
Uteslutning av överflödig headerinformation <body> <h1><xsl:value-of select ="TEI.2/teiHeader/fileDesc/ titleStmt/title"/></h1> <xsl:apply-templates select="TEI.2/text/body"/> </body>
Att titta på över sommaren • http://www.w3schools.com/xsl/ • http://www.w3.org/TR/xslt • Ray, Eric T. (2003). Learning XML. 2. ed. Sebastopol: OReilly. 399 s. • Kompendiet Digitalisering av text