Is it OK to pass XML to an XSL template through a parameter? For example, below I have the template body
call template test1
which passes some XML through the parameter var1
. I then attempt to walk to the node a
using XPATH
<xsl:template name="test1">
<xsl:param name="var1" />
<fo:block>
<xsl:value-of select="$var1/a" />
</fo:block>
</xsl:template>
<xsl:template name="body">
<xsl:call-template name="test1">
<xsl:with-param name="var1" >
<a>foo</a>
</xsl:with-param>
</xsl:call-template>
</xsl:template>
The problem is, this causes my XSL interpreter to fail with an unuseful error message. I'm being forced to use a closed source vendor system for generating documents, so I'm not able to debug. But before I look into it more, I'm looking for confirmation that this is valid usage of XSL.
The
$var1
parameter passed to the template is hardly usable in XSLT 1.0/XPath 1.0 due to the infamous RTF (Result-Tree Fragment) type.From the W3C XSLT 1.0 spec.:
To circumvent this crippling design decision, almost every XSLT processor has its own extension function, usually named
xxx:node-set()
where thexxx
prefix must be bound to a vendor-defined namespace.Solution:
Find exactly what is the name of this extension function offered by your XSLT processor vendor.
Or, if your XSLT processor supports EXSLT, use the
exsl:node-set()
extension function as defined by EXSLT.Here are some vendor-specific namespaces:
MSXML and .NET XslCompiledTransform, XslCompiledTransform:
Xalan (note, the function name is:
xxx:nodeset()
!):Saxon (6.x):
Altova:
All XSLT processors that implement EXSLT:
In case the body of the
<xsl:param>
isn't dynamically constructed, one can avoid thexxx:node-set()
function in the following way:when this transformation is applied on any XML document (not used), the result is the wanted child of the RTF:
Note: XSLT 2.0/XPath 2.0 got rid of the RTF "type" and there one doesn't have any problem accessing temporary trees and navigating them using the full power of XPath 2.0