550 likes | 731 Views
XSL. eXtensible Stylesheet Language. XML Lecture. Adapted from the work of Prof Mark Baker ACET , University of Reading. Outline. Basic Overview. Applying XLST Stylesheets . Using a XSL Processor. Example XSL - generating HTML. Creating a Stylesheet , Template rules Patterns.
E N D
XSL eXtensibleStylesheetLanguage
XML Lecture • Adapted from the work ofProf Mark Baker ACET, University of Reading
Outline • Basic Overview. • Applying XLST Stylesheets. • Using a XSL Processor. • Example XSL - generating HTML. • Creating a Stylesheet, • Template rules • Patterns. • Some XSL Syntax. • Summary.
XSL • XSL is a family of recommendations for defining XML document transformation and presentation. • It consists of three parts: • XSL Transformations (XSLT) a language for transforming XML, • The XML Path Language (XPath), an expression language used by XSLT to access or refer to parts of an XML document. • XSL Formatting Objects (XSL-FO) an XML vocabulary for specifying formatting semantics. • An XSLT stylesheet specifies the presentation of a class of XML documents by describing how an instance of the class is transformed into an XML document that uses a formatting vocabulary, such as (X)HTML or XSL-FO.
XSL (eXtensibleStylesheet Language) • XSL is a high-level functional language used to transform XML documents into various formats, e.g. XML, HTML etc.. • An XSL program consists of a set of TEMPLATE rules. • Each rule consists of a pattern and a template: • The XSL processor starts from the root element and tries to apply a pattern to that node; • If it succeeds, it executes the corresponding template. • The template, when executed, usually instructs the processor to produce some XML result and to apply the templates, • Recursively on the node's children. • An XSL style sheet is a valid XML document
An XML document <?xml version="1.0" encoding="ISO-8859-1"?> <catalog> <cd country="UK"> <title>Dark Side of the Moon</title> <artist>Pink Floyd</artist> <price>10.90</price> </cd> <cd country="UK"> <title>Space Oddity</title> <artist>David Bowie</artist> <price>9.90</price> </cd> <cd country="USA"> <title>Aretha: Lady Soul</title> <artist>Aretha Franklin</artist> <price>9.90</price> </cd> </catalog>
Applying XSLT Stylesheets to XML Documents • There are three ways of applying an XSLT stylesheet to an XML document: • Directly applying an XSLT processor to the XML document and the XSLT stylesheet, • Calling an XSLT processor from within a (Java) program, • Adding to the XML document a link to the XSL stylesheet and letting the browser do the transformation. • This is what we will use
A link to the stylesheet Letting a Browser Perform the Transformation <?xml version="1.0" encoding="ISO-8859-1"?> <?xml-stylesheet type="text/xsl" href=“catalog.xsl"?> <catalog> <cd country="UK"> <title>Dark Side of the Moon</title> <artist>Pink Floyd</artist> <price>10.90</price> </cd> … </catalog>
The Root of the XSL Document (program) • The Root of the XSL document should be one of the following lines: <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:transform version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> • The namespace allows the XSL processor to distinguish • between XSL tags and tags of the result document
How Does XSLT Work? • An XSL stylesheet is a collection of templates that are applied to source nodes (i.e., nodes of the given XML document). • Each template has a match attribute that specifies to which source nodes the template can be applied. • The current source node is processed by applying a template that matches this node. • Processing always starts at the root (/).
Templates • A template has the form: <xsl:template match="pattern"> ... Template content ... </xsl:template> • The content of a template consists of: • XML elements and text (HTML, etc) that are copied to the result, • XSL elements that are actually instructions. • The pattern syntax is a subset of Xpath.
Single Template XSL program <?xml version="1.0" encoding="ISO-8859-1"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:template match="/"> <html> <body> <h1>Hello World</h1> </body> </html> </xsl:template> </xsl:stylesheet>
<html> <body> <h1>Hello World</h1> </body> </html> Applying a browser to catalog.xml (catalog.xml has a link to catalog.xsl)
Focus on Generating HTML XSL (presentation) XML (content) XSL Processor HTML
Transformation Language • XSL is a transformation language it transforms a document written in one language (XML) into a document of another language (e.g., HTML). XSL Transformation Engine (XSL Parser) XML HTML
Recall XML • Recall that an XML document is composed of ‘elements’. • For a BookCatalogue XML document we have the following elements: BookCatalogue (the ‘root’ element), Book, Title, Author, Date, ISBN, and Publisher.
XSL - all about (Template) “Rules” • Let the XSL processor know when it encounters the root element (e.g., BookCatalogue) do [action1]. • Let the XSL processor know when it encounters the Book element do [action2]. • Let the XSL processor know when it encounters the Title element do [action3]. • And so forth…
XSL - all about (Template) “Rules” • Each template rule has two parts: • A pattern or matching part, that identifies the XML node in the source document to which the action part is to be applied: • Matching information is contained in an attribute. • An action or formatting, styling and processing part that details the transformation and styling of the resulting node
XSL Document Structure xsl:stylesheet template rule for the document (template rule for a child element)* action on the child element action on the document
XSL Document Structure <?xml version=“1.0”?> <xsl:stylesheet> <xsl:template match=“/”> [action] </xsl:template> <xsl:template match=“BookCatalogue”> [action] </xsl:template> <xsl:template match=“Book”> [action] </xsl:template> ... </xsl:stylesheet>
Things to Note • XSL documents are full-fledged XML documents: • As a consequence, if in [action] you want to, say, output an HTML paragraph break you must have both <p> and </p>: • Even though in an HTML document the closing element (</p>) is optional, • Note: an XML all elements must have a closing element. • The root element of all XSL documents is xsl:stylesheet • To indicate that a template rule is to be applied to the XML document you use “/” * Alternatively, <p/>
Template Rules Template rules take the following general form: <xsl:template match=“pattern”> [ action ] </xsl:template>
Template Rules (Example) <xsl:template match=“Book”> <xsl:apply-templates/> </xsl:template> <xsl:template match=“Book”> The XSL processor, as it parses through the XML document and gets to a <Book> element use this template rule.” <xsl:apply-templates/> “Go to each of my children and apply the template rules to them.”
Example - Create XSL for BookCatalogue.xml <?xml version="1.0"?> <!DOCTYPE BookCatalogue SYSTEM “BookCatalogue.dtd"> <BookCatalogue> <Book> <Title>My Life and Times</Title> <Author>Paul McCartney</Author> <Date>July, 1998</Date> <ISBN>94303-12021-43892</ISBN> <Publisher>McMillin Publishing</Publisher> </Book> <Book> <Title>Illusions The Adventures of a Reluctant Messiah</Title> <Author>Richard Bach</Author> <Date>1977</Date> <ISBN>0-440-34319-4</ISBN> <Publisher>Dell Publishing Co.</Publisher> </Book> <Book> <Title>The First and Last Freedom</Title> <Author>J. Krishnamurti</Author> <Date>1954</Date> <ISBN>0-06-064831-7</ISBN> <Publisher>Harper & Row</Publisher> </Book> </BookCatalogue>
First Example • This example will show how the XSL Processor parses an XML document and uses the template rules defined in the XSL document to do something for each thing that is found in the XML document.
Terminology • In BookCatalogue.xml we have (snippet): • <BookCatalogue> • <Book> • <Title>My Life and Times</Title> • <Author>Paul McCartney</Author> • <Date>July, 1998</Date> • <ISBN>94303-12021-43892</ISBN> • <Publisher>McMillin Publishing</Publisher> • </Book> • ... • </BookCatalogue> • “Book is a child element of the BookCatalogue element. • Title, Author, Date, ISBN, and Publisher are children elements of • the Book element.”
Creating a Stylesheet - Step 1 Document / • Draw a tree diagram of your XML document. DocumentType <!DOCTYPE BookCatalogue ...> Element BookCatalogue Element Book Element Book Element Book ... ... Element ISBN Element Publisher Element Author Element Date Element Title Text 94303- 12021-43892 Text McMillin Publishing Text July, 1998 Text My Life ... Text Paul McCartney
Creating a Stylesheet - Step 2 • Create a template rule for every type of node in your tree: • Except for the DOCTYPE node: • The current specification does not allow you to have a template rule for the DOCTYPE node. • e.g., create one template rule for all the <Book> nodes, not one template rule for each of the nodes.
<?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl” > <xsl:template match="/"> <xsl:apply-templates/> </xsl:template> <xsl:template match="BookCatalogue"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Book"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Title"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Author"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Date"> <xsl:apply-templates/> </xsl:template> <xsl:template match="ISBN"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Publisher"> <xsl:apply-templates/> </xsl:template> <xsl:template match="text()"> <xsl:value-of select="."/> </xsl:template> </xsl:stylesheet>
Explanation <xsl:value-of select="."/> “The XSL processor returns the value of the thing that is selected here” In this example the “thing” that is selected is a text node, so the “thing” that is returned is the value of the text node, i.e., the text.
Creating a Stylesheet - Step 3 • For those nodes in the tree that we want to immediately return (i.e., not process any of its children): • remove <xsl:apply-templates/> • remove the template rules for the child nodes - these template rules will never be used, so why have them? • For our example, we want the XSL processor to traverse the entire XML document tree so we do not do this step.
<?xml version="1.0"?> <xsl:stylesheetxmlns:xsl="http://www.w3.org/TR/WD-xsl" > <xsl:template match="/"> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <xsl:apply-templates/> </BODY> </HTML> </xsl:template> <xsl:template match="BookCatalogue"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Book"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Title"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Author"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Date"> <xsl:apply-templates/> </xsl:template> <xsl:template match="ISBN"> <xsl:apply-templates/> </xsl:template> <xsl:template match="Publisher"> <xsl:apply-templates/> </xsl:template> <xsl:template match="text()"> <xsl:value-of select="."/> </xsl:template> </xsl:stylesheet> added these Put an <HTML> wrapper around the content
Creating a Stylesheet - Step 5 • Tell the XSL Processor that when it encounters a <Book> element to output: • “I am at a Book element. Processing its children now.” • Do this for each element. • Before running your XSL document through the XSL Processor, check it for well-formed-ness.
<?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl”> <xsl:template match="/"> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <xsl:apply-templates/> </BODY> </HTML> </xsl:template> <xsl:template match="BookCatalogue"> I am at BookCatalogue. Processing its children now.<br/> <xsl:apply-templates/> </xsl:template> <xsl:template match="Book"> I am at Book. Processing its children now.<br/> <xsl:apply-templates/> </xsl:template> <xsl:template match="Title"> I am at Title. Here's the title:<br/> <xsl:apply-templates/><br/> </xsl:template> <xsl:template match="Author"> I am at Author. Here's the author's name:<br/> <xsl:apply-templates/><br/> </xsl:template> <xsl:template match="Date"> I am at Date. Here's the date:<br/> <xsl:apply-templates/><br/> </xsl:template> <xsl:template match="ISBN"> I am at ISBN. Here's the ISBN:<br/> <xsl:apply-templates/><br/> </xsl:template> <xsl:template match="Publisher"> I am at Publisher. Here's the publisher:<br/> <xsl:apply-templates/><br/> </xsl:template> <xsl:template match="text()"> <xsl:value-of select="."/> </xsl:template> </xsl:stylesheet> BookCatalogue1b.xsl
Default Template Rules • Every XSL document has two default template rules. • These rules are applied when the XSL Processor cannot find a template rule to use from what was written. • Here are the two default template rules: “Match on the document or any element. Return the result of applying the template rules to my children.” <xsl:template match=“/ | *”> <xsl:apply-templates/> </xsl:template> <xsl:template match=“text()”> <xsl:value-of select=“.”/> </xsl:template> “Match on a text node. Return the value of the text node, i.e., the text.”
Multiple Applicable Rules • Suppose that the XSL Processor is processing BookCatalogue and it gets to the <Book> element. • Why does it use <xsl:template match=“Book”> • and not the default template rule <xsl:template match=“/ | *”> after all, both apply! • Answer: given two rules that apply, the more specific rule wins: • “*” is much more general than “Book”. • “*” matches on any element. • “Book” just matches on the Book element.
Example 2 • The XSL Processor, when it encounters a book element output: • ‘<p/>Here is a book:<br/>’ and then the data in its children elements. • This is what we want XSLProcessor to send to BookCatalogue.html. <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> Here is a book: all the data from the first book Here is a book: all the data from the second book Here is a book: all of the data from the third book </BODY> </HTML>
BookCatalogue2.xsl <?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl” > <xsl:template match="BookCatalogue"> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <xsl:apply-templates/> </BODY> </HTML> </xsl:template> <xsl:template match="Book"> <p/>Here is a book:<br/> <xsl:apply-templates/> </xsl:template> </xsl:stylesheet>
Put the Data into an HTML Table <?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl” > <xsl:template match="BookCatalogue”> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <TABLE BORDER="1" WIDTH="100%"> <xsl:apply-templates/> </TABLE> </BODY> </HTML> </xsl:template> <xsl:template match="Book"> <TR> <xsl:apply-templates/> </TR> </xsl:template> <xsl:template match="Title | Author | Date | ISBN | Publisher"> <TD> <xsl:apply-templates/> </TD> </xsl:template> </xsl:stylesheet>
Single Rule Applied to Multiple Elements • Notice in the last example that a single rule is applied to multiple elements: • <xsl:apply-templates select=“pattern”> • The xsl:apply-templates element (without an attribute) tells the XSL Processor to apply the template rules to all children • The xsl:apply-templates element can have an attribute that tells the XSL Processor to process only the child element that matches “pattern”: • This apply-templates rule allows us to specify the order in which the children are processed.
Specify the order of the table contents <?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl” > <xsl:template match="BookCatalogue"> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <TABLE BORDER="1" WIDTH="100%"> <xsl:apply-templates/> </TABLE> </BODY> </HTML> </xsl:template> <xsl:template match="Book"> <TR> <xsl:apply-templates select="Author"/> <xsl:apply-templates select="Title"/> <xsl:apply-templates select="Date"/> <xsl:apply-templates select="Publisher"/> <xsl:apply-templates select="ISBN"/> </TR> </xsl:template> <xsl:template match="Title | Author | Date | ISBN | Publisher"> <TD> <xsl:apply-templates/> </TD> </xsl:template> </xsl:stylesheet> Process the Author element first (in previous examples the Title element was processed first)
<xsl:for-each select=“pattern”> <xsl:for-each select=“Book”> [action] </xsl:for-each> This says that for every Book element, do [action]
For each Book do ... <?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl” > <xsl:template match="BookCatalogue"> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <TABLE BORDER="1" WIDTH="100%"> <xsl:for-each select="Book"> <TR> <xsl:apply-templates/> </TR> </xsl:for-each> </TABLE> </BODY> </HTML> </xsl:template> <xsl:template match="Title | Author | Date | ISBN | Publisher"> <TD> <xsl:apply-templates/> </TD> </xsl:template> </xsl:stylesheet> For each Book create a row and process the Book’s children
Patterns • So far we have seen very simple patterns - simply match against an element name. • XSL provides a rich pattern matching capability. match document <xsl:template match=“/”> “When you start processing the document do ...” <xsl:template match=“Book”> “When you get to a Book element do ...” <xsl:template match=“Title | Author”> “When you get to either a Title element or an Author element do ...” match by name match several names
Patterns match with immediate ancestor <xsl:template match=“Book/Title”> “When you get to a Title element that has a Book element as a parent do ...” <xsl:template match=“BookCatalogue//Title”> “When you get to a Title element that has a BookCatalogue as an ancestor do ...” <xsl:template match=“Book/*”> “When you get to any element that is an immediate child of Book do ....” <xsl:template match=“id(J.K)”> “When you get to an element that has an id “J.K.” do ...” match with an ancestor wildcard match match by id
Patterns (matching by attribute) <xsl:template match=“para”> “When you get to a para element do ...” <xsl:template match=“para[@type]”> “When you get to a para element that has an attribute called type do ...” <xsl:template match=“para[@type =‘opening’]”> “When you get to a para element that has an attribute called type and its value is ‘opening’ do ...” <xsl:template match=“chapter[@num=‘ch1’]/para[@type=‘opening’]”> “When you get to a para element that has an attribute called type whose value is ‘opening’ and the element has a parent called chapter and it has an attribute called num that has a value ‘ch1’ do ...
Patterns (matching by position) <xsl:template match=“Book[first-of-type()]”> “When you get to the first Book element do ...” <xsl:template match=“Book[last-of-type()]”> “When you get to the last Book element do ...” <xsl:template match=“Book[not(last-of-type())]”> “Use this rule for all but the last Book element” Other position qualifiers: not(first-of-type()) first-of-any() “The first child element of any type” not(first-of-any()) last-of-any() not(last-of-any())
Named Attribute Sets • XSL allows you to create a set of attributes and assign a name to it: • What value is this? Reuse! <xsl:attribute-set name=“title-attributes”> <xsl:attribute name=“size”>+1</xsl:attribute> <xsl:attribute name=“color”>blue</xsl:attribute> <xsl:attribute name=“face”>Palatino</xsl:attribute> </xsl:attribute-set>
<?xml version="1.0"?> <xsl:stylesheetxmlns:xsl=“http://www.w3.org/TR/WD-xsl” > <xsl:attribute-set name="title-attributes"> <xsl:attribute name=“size”>+1</xsl:attribute> <xsl:attribute name=“color>blue</xsl:attribute> <xsl:attribute name=“face>Palatino</xsl:attribute> </xsl:attribute-set> <xsl:template match="BookCatalogue”> <HTML> <HEAD> <TITLE>Book Catalogue</TITLE> </HEAD> <BODY> <TABLE BORDER="1" WIDTH="100%"> <xsl:apply-templates/> </TABLE> </BODY> </HTML> </xsl:template> <xsl:template match="Book"> <TR> <xsl:apply-templates/> </TR> </xsl:template> <xsl:template match="Author | Date | ISBN | Publisher"> <TD> <xsl:apply-templates/> </TD> </xsl:template> <xsl:template match="Title"> <TD> <FONT> <xsl:use attribute-set="title-attributes"/> <xsl:apply-templates/> </FONT> </TD> </xsl:template> </xsl:stylesheet> Define the named attribute set Use the named attribute set
Numbering • XSL has the capability to number your elements: <xsl:number/>.<xsl:apply-templates select="Title"/> This will print out a number followed by a period followed by the results of processing the Title element. The number starts at one and increments each time this template rule is instantiated.