Re: Generic XSLT stylesheet to generate pages....Ideas
Hi Edward, > I am trying to come up with a generic XSLT stylesheet which takes in > XTML (Page definition), XML (Data), XSLT(standard call_templates for > page components) and generates either HTML/XHTML in one go. > Alternatively the XHTML(Page definition) could be read in without > the XML(Data) to produce an XSLT stylesheet which when applied to > the XML (Data) produces XHTML/HTML in a second step. My gut feeling > in to produce the resultant XHTML in go since one is effectively > merging XML documents to produce a resultant XML document. One way of doing this is to have the page definition XHTML contain elements that indicate where you want the XML data to be inserted. The placeholder elements can be more or less complex as you require, but the more complex they are, the more likely that you're reinventing XSLT and you may as well use a simplified stylesheet rather than a separate page definition. For example, a simple page definition (template.xhtml) might look like: <html xmlns="http://www.w3.org/1999/xhtml" xmlns:ins="http://interpulse.co.uk/template"> <head> <title>Test Page</title> </head> <body> <p> Username: <ins:username /> </p> </body> </html> With a XML document (data.xml) being: <info> <username>Edward Bedell</username> </info> A stylesheet could accept one or the other of these as inputs, or even just use itself as the source, but it should store both the template and the data as global variables and apply templates to the template.xsl document. For example: <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ins="http://interpulse.co.uk/template"> <xsl:variable name="template" select="document('template.xsl')" /> <xsl:variable name="data" select="document('data.xml')" /> <xsl:template match="/"> <xsl:apply-templates select="$template/*" /> </xsl:template> ... </xsl:stylesheet> The majority of the result is created by copying the XHTML elements from the template document. For this, you need an identity template that matches all the nodes in your document and just copies them: <xsl:template match="node()|@*"> <xsl:copy> <xsl:apply-templates select="@*|node()" /> </xsl:copy> </xsl:template> The exceptions to this processing are the templates in your namespace, which are placeholders indicating where information from the data document should be inserted in the template page. For this example, the ins:username element means that the value of the username element child of the info element in the data document should be inserted. So you should have a template matching that instruction and doing what it says: <xsl:template match="ins:username"> <xsl:value-of select="$data/info/username" /> </xsl:template> You can keep adding these templates - one per placeholder or instruction that you place in the page template. You can do it the other way you suggested as well - use the page definition to create a stylesheet that you then use to process the XML document - but it's slightly more complicated because you have to mess around with namespace aliases and so on. However, it does have the advantage over the above method that it means your placeholder/instruction elements can contain XPaths, since you aren't limited by the fact that you can't evaluate an XPath on the fly using XSLT. I believe that creating a stylesheet from a page definition in this way is a form of literate programming... Cheers, Jeni --- Jeni Tennison http://www.jenitennison.com/ XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list
PURCHASE STYLUS STUDIO ONLINE TODAY!
Purchasing Stylus Studio from our online shop is Easy, Secure and Value Priced!
Download The World's Best XML IDE!
Accelerate XML development with our award-winning XML IDE - Download a free trial today!
Subscribe in XML format