Groups | Blog | Home
all groups > dotnet xml > june 2004 >

dotnet xml : Xsl extension function and type coersion in .Net?



Mark
6/7/2004 12:21:02 PM
Hi..

I have a c# class that i'm using to implement some extension functions and one of those functions is a simple push/pop stack. I made the c# code fairly generic, taking and returning objects - i.e
public void push (object val
{ stack.Push (val)


public object pop (
{ return stack.Pop()


The thought was that the stack could be used for many purposes even though my first use is for stacking boolean state info (e.g. <xsl:value-of select="ext:push(true())"/> ... <xsl:if test="ext:pop()">Succeeded!</xsl:if>). The odd thing I'm seeing so far is that pushing a boolean (like true() or false()) from xsl seems to work fine (the push() call is getting a System.Boolean as input and pop is returning it) doesn't get properly interpreted on pop() unless I put it in an xsl variable first. Any ideas why that is

To give an example, presum
<xsl:value-of select="ext:push(true())"/

With that presumption
<xsl:if test="ext:pop()">Succeeded!</xsl:if> fail
<xsl:value-of select="string (ext:pop())"/> outputs
<xsl:value-of select="boolean (ext:pop())"/> outputs fals
*but
<xsl:variable name="dummy" select="ext:pop()"/><xsl:if test="$dummy">Succeeded!</xsl:if> work
<xsl:value-of select="string($dummy)"/> outputs tru
<xsl:value-of select="boolean($dummy)"/> outputs tru

Again, if i take the return from the extension function and pop it into a variable, it seems the interpretation as a boolean works fine but if I try to use the return from the extension function directly, it doesn't. Any ideas why that would be

Thank
-Mar
Oleg Tkachenko [MVP]
6/8/2004 11:37:49 AM
[quoted text, click to view]

As stated on MSDN:
"The data types returned from extension objects are one of the four
basic XPath data types of number, string, Boolean, and node set."

You better obey to this rule if you want predictable behaviour.

[quoted text, click to view]

Nitpickingly speaking that's really bad extension functions. They break
XSLT functional and side-effect free nature. Many would say that smells
like abusing extensions to change the language.

[quoted text, click to view]

Yeah, that's not really looks good. But as your function returns object
and there is no object type in XPath/XSLT data model, I think that's
quite reasonable to have such bizarre results.

[quoted text, click to view]
Well, once you bind object to a variable, it's being converted to one of
XPath data types, so it works properly.

--
Oleg Tkachenko [XML MVP]
Mark
6/9/2004 8:11:04 AM
Thanks for replying..

[quoted text, click to view]

Since the inputs originally come from xsl, I am obeying this rule. My C# code is using the generic object declaration so that I can have one routine to handle all invocations. Since the .net xml dom and xsl enginer are implemented in .net languages, they have all of the typing and reflection capabilities in the languages to see that this "object" box has a value of type boolean, string, whatever. I would have hoped that the interface to the extension functions would avail themselves of the reflection capabilities to see what's inside the box (as it were) when handing things in and out

[quoted text, click to view]

Well, yes, but extension functions basically exist to do what's not convenient or practical in vanilla xml

[quoted text, click to view]

See comment above about object just being a generic box and that what's inside does map to core XPath data types. Boxing is a pretty standard feature in C# both for reference passing parameters and for genericizing function definitions
Again, what's in the box *is* standard xpath data types; I'd expected a .Net xsl implementation to recognize this

[quoted text, click to view]

Again, what's inside the object box is always an XPath core datatype. If the xsl implementation can figure out the right interpretation of the value inside the box for <xsl:variable name="dummy" select="ext:pop()"/>, why can't it figure it out with direct usage (i.e. <xsl:value-of select="ext:pop()">)

Thank
-Mar
AddThis Social Bookmark Button