0
votes

I need to evaluate some xpath expressions dynamically and I was comparing XmlPrime and Saxon for options on how to do this. I have seen Saxon supports it:

http://saxon.sourceforge.net/saxon7.9/extensions.html#evaluate http://www.saxonica.com/documentation/index.html#!extensions/functions/saxon-extension-functions

but I can't something similar in the XmlPrime Documentation:

http://www.xmlprime.com/xmlprime/doc/2.6/P_XmlPrime_XdmModule_XsltFunctions.htm

it's there something I'm missing or a workaround to it?

Thxs! Vlax

1

1 Answers

1
votes

As far as I can tell from reading the documentation they don't provide an Evaluate function but they allow you to implement ones using .NET code (which can be embedded using xp:script).

Based on that I implemented a stylesheet for testing:

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
  xmlns:xp="http://www.xmlprime.com/"
  xmlns:xs="http://www.w3.org/2001/XMLSchema"
  xmlns:mf="http://example.com/mf"
  exclude-result-prefixes="xp xs mf">


<xp:script implements-prefix="mf" language="C#"><![CDATA[
public static IEnumerable<System.Xml.XPath.XPathItem> Evaluate(string exp, XPathItem contextItem)
{ 
   XPath path = XPath.Compile(exp);
   return path.Evaluate(contextItem);
}
]]></xp:script>

<xsl:template match="@* | node()" mode="#all">
  <xsl:copy>
    <xsl:apply-templates select="@* , node()" mode="#current"/>
  </xsl:copy>
</xsl:template>

<xsl:template match="exp">
  <xsl:copy>
    <result><xsl:sequence select="mf:Evaluate(., .)"/></result>
  </xsl:copy>
</xsl:template>

<xsl:template match="exp2">
  <xsl:copy>
    <result>
      <xsl:apply-templates select="mf:Evaluate(., /*)" mode="test1"/>
    </result>
  </xsl:copy>
</xsl:template>

</xsl:stylesheet>

That compiles and runs fine (using the command line tool xslt.exe) with XmlPrime 2.8, the current release. So when applied to an XML input sample like

<root>
  <exp>local-name()</exp>
  <exp>count(node())</exp>
  <exp2>*[matches(., '\(\)')]</exp2>
</root>

I get an output like

<?xml version="1.0" encoding="UTF-8"?><root>
  <exp><result>exp</result></exp>
  <exp><result>1</result></exp>
  <exp2><result><exp>local-name()</exp><exp>count(node())</exp></result></exp2>
</root>

You might need to check back with the implementers of XmlPrime whether that approach is a good use of their API, I started with http://www.xmlprime.com/xmlprime/doc/2.8/native-modules.htm to have an example and then looked for XPath evaluation in their API. But I certainly don't have done a careful reading of their documentation nor have I run a test suite to make sure the approach covers all types of XPath expressions and return types.