Reputation: 13
I'm tring to use a value in a specific tag as variable name. But while converting xml system gives Undeclared variable in XPath expression Exception.
My Xml file is
<request>
<entityType>individual</entityType>
</request>
And Xslt file is
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:math="http://www.w3.org/2005/xpath-functions/math"
exclude-result-prefixes="xs math"
version="3.0">
<xsl:param name="individual" static="yes" as="xs:string" select="'1'"/>
<xsl:param name="legal" static="yes" as="xs:string" select="'2'"/>
<xsl:template match="/*">
<xsl:param name="entity" as="xs:string" select="concat('$',entityType)"/>
<xsl:variable name="input" as="xs:string">
<xsl:evaluate xpath="$entity"/>
</xsl:variable>
<HTML><TITLE><xsl:value-of select="$input"/></TITLE></HTML>
</xsl:template>
</xsl:stylesheet>
i expect the result as
<HTML><TITLE>1</TITLE></HTML>
But I get "Static error in XPath expression supplied to xsl:evaluate: Undeclared variable in XPath expression" message.
Upvotes: 1
Views: 138
Reputation: 167716
If you read https://www.w3.org/TR/xslt-30/#dynamic-xpath then you will find it clearly states "Variables declared in the stylesheet in xsl:variable
or xsl:param
elements are not in-scope within the target expression.". You will have to use xsl:with-param
inside the xsl:evaluate
and/or with-params
on the xsl:evaluate
to declare the parameters you need.
<xsl:evaluate xpath="$entity" with-params="map{ QName('', 'individual') : $individual }"/>
As pointed out in your comment, you want to map certain string color values to integer color values, that might be possible in XSLT 3 with a map e.g. with an input of
<colors>
<color>red</color>
<color>green</color>
</colors>
and an XSLT 3.0 of e.g.
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="3.0"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
exclude-result-prefixes="#all"
expand-text="yes">
<xsl:param name="color-map"
as="map(xs:string, xs:integer)"
select="map {
'red' : 1,
'green' : 2
}"/>
<xsl:template match="color">
<xsl:copy>{$color-map(.)}</xsl:copy>
</xsl:template>
<xsl:mode on-no-match="shallow-copy"/>
</xsl:stylesheet>
you would get a result of e.g.
<colors>
<color>1</color>
<color>2</color>
</colors>
Upvotes: 1
Reputation: 163595
@MartinHonnen is correct in his explanation of why this doesn't work, but standing back from it, I wonder what you are actually trying to achieve? What is suppposed to happen if the source XML document contains a value other than "individual" or "legal"? If these are the only two values that the stylesheet can correctly process, surely there is an easier way of mapping these to the integers 1 and 2?
I don't really know what your problem is, but I suspect that xsl:evaluate
is not the right solution to it.
Upvotes: 2