This is the mail archive of the xsl-list@mulberrytech.com mailing list .


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Generic XSLT stylesheet to generate pages....Ideas please...


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


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]