XSLT


XML's power lies in its ability to represent data. However, to do something useful with the XML data, especially if it is document-centric XML, it would typically need to be translated into another format. The technology that enables this translation is the eXtensible Stylesheet Language (XSL). XSL is a language for expressing style sheets. A style sheet is an XML document that describes how to display an XML document of a particular type. XSL is a W3C specification and is broken down into three complementary technologies:

  • XSL Transformations (XSLT). Defines a language for expressing transformation rules from one class of XML document to another. XSLT specifications can be found at www.w3.org/TR/xslt.

  • XML Path Language (XPath). An expression language used by XSLT to access or refer to parts of an XML document. XPath specifications can be found at www.w3.org/TR/xpath.

  • XSL Formatting Objects (XSL-FO). A language for defining formatting, such as fonts and page layout. These are defined as a part of the XSL specification at www.w3.org/TR/xsl.

An XSLT processor, analogous to an XML parser, is an application that applies an XSL style sheet (which itself is an XML document and conforms to the XSL schema) to XML data input. Instead of modifying the original XML data, XSLT produces a result—typically HTML or XML and, in some rare cases, binary. Essentially, XSL uses XSLT to transform an XML source tree into an XML result tree, as Figure 9.5 shows.

click to expand
Figure 9.5: XSLT transformation process

These trees are logical structures that consists of nodes that may be produced by XML. They may be implemented as object models (e.g., DOM), a series of well-balanced parse events (e.g., callbacks received by the SAX ContentHandler), a series of requests (the result of which can describe a tree), or a stream of marked-up characters.

Consider the example where you want to display part of the flutebank.com administrator information from the XML in Listing 9.1. Listing 9.5 shows the XSL a processor would take. Figure 9.6 shows the resulting output from the transformation, as rendered in a browser.


Figure 9.6: XML transformed into HTML

Listing 9.5: The XSL style sheet used to transform the XML from Listing 9.1

start example
 <?xml version="1.0" encoding="UTF-8"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:n1="http://www.flutebank.com/schema" xmlns:contacts="http://www.flutebank.com/ schema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">     <xsl:template match="/">         <html>             <body>                 <h4>Flutebank.com : Support personal contact information</h4>                 <table bgcolor="#AAB0AC" border="1" cellpadding="0" cellspacing="0"                                                                           width="50%">                     <tr>                         <td>                             <h4>Name</h4>                         </td>                         <td>                             <xsl:for-each select="n1:flutebank">                                 <xsl:for-each select="n1:administrator">                                     <xsl:for-each select="n1:firstname">                                         <xsl:apply-templates />                                     </xsl:for-each>                                 </xsl:for-each>                             </xsl:for-each> <xsl:for-each select="n1:flutebank">                                 <xsl:for-each select="n1:administrator">                                     <xsl:for-each select="n1:lastname">                                         <xsl:apply-templates />                                     </xsl:for-each>                                 </xsl:for-each>                             </xsl:for-each>                         </td>                     </tr>                     <tr>                         <td>                             <h4>Phone:</h4>                         </td>                         <td>                             <xsl:for-each select="n1:flutebank">                                 <xsl:for-each select="n1:administrator">                                     <xsl:for-each select="n1:telephone">                                         <xsl:for-each select="n1:desk">                                             <xsl:apply-templates />                                         </xsl:for-each>                                     </xsl:for-each>                                 </xsl:for-each>                             </xsl:for-each>                         </td>                     </tr>                     <<tr>                         <td>                             <h4>Email:</h4>                         </td>                         <td>                             <xsl:for-each select="n1:flutebank">                                 <xsl:for-each select="n1:administrator">                                     <xsl:for-each select="n1:email">                                         <xsl:for-each select="n1:work">                                             <xsl:apply-templates />                                         </xsl:for-each>                                     </xsl:for-each>                                 </xsl:for-each>                             </xsl:for-each>                         </td>                     </tr>                 </table>             </body>         </html>     </xsl:template>     <xsl:template match="n1:administrator">         <xsl:apply-templates />     </xsl:template>     <xsl:template match="n1:cellular">         <xsl:apply-templates />     </xsl:template> </xsl:stylesheet> 
end example

As with XML, this chapter is not intended to be a lesson on XSL or XPath syntax; numerous good sources are available for that. Vendor tools are also available, such as XMLSpy (www.xmlspy.com), that can generate XSL code based on the input XML and desired output, with minimal knowledge of these languages on the part of the user.

So, why is XSLT important? A typical enterprise application that delivers content to users would use data from multiple EIS resources, apply some business rules and processing to the data, and serve the clients. As Figure 9.7a shows, the clients could be other applications, users, or devices, all using the same logical data. To prevent rewriting the application and the presentation tier for every interface, an XSL-based processor that transcodes same document-centric XML into different formats (XML to WML, HTML, XML, XHTML, etc.) using XSL offers a cleaner content delivery mechanism but the same logical data set. The logical tiering for this approach is shown in Figure 9.7b.

click to expand
Figure 9.7a: Transcoding XML into different formats

click to expand
Figure 9.7b: Logical tiering

JAXP and XSLT

JAXP architecture accommodates XSLT by providing the same abstraction and pluggability as it does for SAX and DOM (see Figure 9.1a).

start sidebar

JAXP endorses XLST 1.0 from the W3C at www.w3.org/TR/1999/REC-xslt-19991116.

end sidebar

As Figure 9.8 shows, JAXP is used to instantiate a TransformerFactory, which, in turn, is used to obtain a reference to a Transfomer specific to a style sheet. A Transformer takes a Source and transforms it into a Result. The source can be of any type: a DOMSource,a SAXSource (or the content parsed by a SAX parser), or a StreamSource.

click to expand
Figure 9.8: JAXP and XSLT

The JAXP part that handles transformations is also known as the Transformation API for XML (TrAX) and is contained in the following packages:

  • javax.xml.transform. Defines the core interfaces for transformation.

  • javax.xml.transform.sax. Defines the SAX-relevant interfaces for transformation.

  • javax.xml.transform.dom. Defines the DOM-relevant interfaces for transformation.

  • javax.xml.transform.stream. Defines the Stream-relevant interfaces for transformation.

To put the earlier mention about a source tree and a result tree into perspective, it is interesting to note that if the reference implementation, Xalan, is supplied with a DOMSource, it will use this as its internal tree representation. If the input is a SAXSource or StreamSource, it uses its own internal tree representation as the source tree, called an STree. This is more efficient than a general-purpose DOM, because it contains additional sorting optimizations.

Tables 9.7 through 9.10 show the relevant interfaces in the above packages.

The code to do the transformation would look something like the following:

                String xml = "saxexaple2.xml";                String xsl = "fluteadmin.xsl"; // instantiate the factory                TransformerFactory factory = TransformerFactory.newInstance(); // obtain a transformer from the factory for the XSL                Transformer transformer = factory.newTransformer                                               (new StreamSource(new File(xsl))); // use the transformer to transform the source to a result                transformer.transform(new StreamSource(new File(xml)),                                                      new StreamResult(System.out)); 

Another example would be to transform a DOM into another DOM in memory, using the XSL that is also in memory as a DOM (remember, an XSL document is also an XML document).

Table 9.7: The javax.xml.transform Package

Source

Defines the top level interface to wrap other specific sources.

Result

Defines the top level interface to wrap other specific results.

Templates

A template represents a set of XSL instructions in memory that need to be applied repeatedly to different XML data structures.

Transformer

The processor that applies the transformation.

TransformerFactory

A factory used to obtain a reference to the underlying Transformer.

URIResolver

Like schemas, a style sheet can have references to other style sheets, using an xsl:include or xsl:import statement. This is used to resolve such references and process them.

Table 9.8: The javax.xml.transform.dom Package

DOMSource

An interface to represent a DOM tree (an org.w3c.dom.Node) as the source of the XML data to be transformed

DOMResult

An interface to represent a DOM tree (an org.w3c.dom.Node) as the result of the transformation

                String xml = "saxexaple2.xml";                String xsl = "fluteadmin.xsl"; // create a DOM from the XSL              DocumentBuilderFactory domfactory = DocumentBuilderFactory.newInstance();              domfactory.setNamespaceAware(true);              DocumentBuilder parser = domfactory.newDocumentBuilder();              Document xsldom = parser.parse(xsl); // create a DOM from the source XML              Document xmldom = parser.parse(xml); // create the transfomer and transform the xml              TransformerFactory factory = TransformerFactory.newInstance();              Transformer transformer = factory.newTransformer(new DOMSource(xsldom));              DOMResult result= new DOMResult();              transformer.transform(new DOMSource(xmldom),result); 

Table 9.9: The javax.xml.transform.sax Package

SAXSource

An interface to represent a SAX as the source of the XML data to be transformed. This wraps an org.xml.sax.InputSource and can futher be piped on a java.io.InputStream, java.io.Reader, or URI. (Typically, a string representing a java.net.URL.)

SAXResult

An interface to wrap a SAX ContentHandler invoked sequentially as a result of applying the transformation to the XML

TemplatesHander

A SAX ContentHandler that can be used to generate a Templates object from SAX source events

TransformerHandler

A SAX ContentHandler that can be used to generate a Result object from SAX source events

SAXTransformerFactory

A special kind of TransformerFactory that can be used to configure the SAX parser processing the XSL input

Table 9.10: The javax.xml.transform.stream Package

StreamSource

An interface to act as a pipe on different streams, as sources for the transformation (File, InputStream, Reader, or URL)

StreamResult

An interface to act as a pipe on different streams, as results for the transformation (File, OutputStream, Write, or URL)

Another example would be to use an empty transfomer not associated with a particular style sheet to transform the DOM—for example, from the code above into another form:

 // As a convenience , print out the in memory DOM to // the System.out using a null transform            TransformerFactory factory = TransformerFactory.newInstance();            Transformer nulltransformer = factory.newTransformer();            nulltransformer.transform(new DOMSource(result.getNode()),                                      new StreamResult(System.out)); 

Another example would be to use the transformer to obtain the associated style sheet from an XML document—for example, if the XML has a processing instruction such as:

 <?xml-stylesheet type="text/xsl" href="fluteadmin.xsl"?>:          String xml = "pitransform.xml";          TransformerFactory factory = TransformerFactory.newInstance();          Source xsl = factory.getAssociatedStylesheet (                                               new StreamSource(xml),null, null, null);          Transformer transformer = factory.newTransformer(xsl);          transformer.transform(new StreamSource(xml),new StreamResult(System.out)); 

A common use for transformation involves applying the same style sheet to different or dynamically generated XML data, to produce dynamic output. For example, users request a service from a flutebank.com account service, resulting in the generation of user-specific stock portfolio XML data that needs to be transformed for rendering. In such scenarios, a Templates object should be used instead, to obtain the Transformer. A Templates object is immutable, thread safe, and guaranteed to work across multiple threads. Also, as we shall see with XSLTc, underlying implementations may provide further optimizations to deal with repeated transformations.

                String xml_1 = "pitransform.xml";                String xml_2 = "saxexample2.xml";                String xsl = "fluteadmin.xsl"; // instantiate the factory                TransformerFactory factory = TransformerFactory.newInstance(); // obtain a template from the factory                Templates template = factory.newTemplates(new StreamSource(xsl));                Transformer transformer = template.newTransformer(); // use the transformer to transform the source to a result                transformer.transform(new StreamSource(new File(xml_1)),                                      new StreamResult(System.out));                transformer.transform(new StreamSource(new File(xml_2)),                                      new StreamResult(System.out)); 




Java Web Services Architecture
Java Web Services Architecture (The Morgan Kaufmann Series in Data Management Systems)
ISBN: 1558609008
EAN: 2147483647
Year: 2005
Pages: 210

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net