Reputation: 77
I ran into a behavior related to types in XSLT/XPath that I can't explain. Here's a snippet of XSLT that shows the problem (it's not a very useful XSLT, of course, but it represents a pretty minimal demonstration my question):
<?xml version="1.0"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:template match="/">
<xsl:variable name="root">
<xsl:sequence select="root(.)"/>
</xsl:variable>
<xsl:if test="root(.) is $root">
Match
</xsl:if>
</xsl:template>
</xsl:stylesheet>
You will see that "Match" is not displayed. However, if you add as="node()"
to the <xsl:variable name="root">
then "Match" is displayed.
Can anyone explain help me understand why?
You can plug this XSLT into http://xslttest.appspot.com to explore the problem. Any input XML will work (e.g., <?xml version="1.0"?><foo/>
).
Thanks, Josh.
Upvotes: 3
Views: 136
Reputation: 5432
To know the difference between a sequence and a variable you may go through the following link.
To summarize, xsl:variable
without an as
attribute creates a new document(having its own root node).
Using as
attribute helps creating an atomic value or a sequence. Here, the variable wouldn't be a root node but will refer to the sequence(s) it contains.
When you use:
<xsl:variable name="root">
<xsl:sequence select="root(.)"/>
</xsl:variable>
With the condition <xsl:if test="root(.) is $root">
, you are testing whether the root of the input XML document is same as the root of the variable root
, which is false
.
And when you use:
<xsl:variable name="root" as="node()">
The condition, root(.) is $root
evaluates to true
as both the input document root and the sequence generated by variable root
are same.
And of course, as mentioned by michael.hor257k
this stylesheet shall be versioned 2.0
.
EDIT:
Declaring variable in the following way would also make the condition true()
<xsl:variable name="root" select="root(.)"/>
Upvotes: 2