You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ode.apache.org by mr...@apache.org on 2006/10/11 18:37:37 UTC

svn commit: r462845 - in /incubator/ode/trunk: bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/ bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/

Author: mriou
Date: Wed Oct 11 09:37:36 2006
New Revision: 462845

URL: http://svn.apache.org/viewvc?view=rev&rev=462845
Log:
Improved XPath expression compilation. Now we're hooked into Saxon so we'll be properly notified when the expression parsing meets variables and functions.

Added:
    incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/OdeXPathFunctionLibrary.java
    incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/SaxonContext.java
Modified:
    incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/JaxpFunctionResolver.java
    incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/XPath20ExpressionCompilerBPEL20.java
    incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/TestAssign.bpel
    incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/test.properties

Modified: incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/JaxpFunctionResolver.java
URL: http://svn.apache.org/viewvc/incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/JaxpFunctionResolver.java?view=diff&rev=462845&r1=462844&r2=462845
==============================================================================
--- incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/JaxpFunctionResolver.java (original)
+++ incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/JaxpFunctionResolver.java Wed Oct 11 09:37:36 2006
@@ -103,6 +103,7 @@
             if (params.size() < 1 || params.size() > 3)
                 throw new CompilationException(
                         __msgs.errInvalidNumberOfArguments(Constants.EXT_FUNCTION_GETVARIABLEDATA));
+
             String varname = (String)params.get(0);
             String partname = params.size() > 1 ? (String)params.get(1) : null;
             String locationstr = params.size() > 2 ? (String)params.get(2) : null;

Added: incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/OdeXPathFunctionLibrary.java
URL: http://svn.apache.org/viewvc/incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/OdeXPathFunctionLibrary.java?view=auto&rev=462845
==============================================================================
--- incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/OdeXPathFunctionLibrary.java (added)
+++ incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/OdeXPathFunctionLibrary.java Wed Oct 11 09:37:36 2006
@@ -0,0 +1,53 @@
+package org.apache.ode.bpel.elang.xpath20.compiler;
+
+import net.sf.saxon.expr.Expression;
+import net.sf.saxon.trans.XPathException;
+import net.sf.saxon.trans.StaticError;
+import net.sf.saxon.xpath.XPathFunctionCall;
+
+import javax.xml.namespace.QName;
+import javax.xml.xpath.XPathFunction;
+import javax.xml.xpath.XPathFunctionException;
+import java.util.ArrayList;
+
+/**
+ * Overloading the XPathFunctionLibrary to force it to initialize our functions giving
+ * the provided parameters. Otherwise the Saxon implemetation just never gives you
+ * any parameter before runtime.
+ * @author mriou <mriou at apache dot org>
+ */
+public class OdeXPathFunctionLibrary extends net.sf.saxon.xpath.XPathFunctionLibrary {
+
+    private JaxpFunctionResolver _funcResolver;
+
+    public OdeXPathFunctionLibrary(JaxpFunctionResolver funcResolver) {
+        _funcResolver = funcResolver;
+    }
+
+    public Expression bind(int nameCode, String uri, String local, Expression[] staticArgs) throws XPathException {
+        QName name = new QName(uri, local);
+        XPathFunction function = _funcResolver.resolveFunction(name, staticArgs.length);
+        if (function == null) {
+            return null;
+        }
+
+        // Converting the expression array to the simple string
+        ArrayList args = new ArrayList(staticArgs.length);
+        for (Expression expression : staticArgs) {
+            String exprStr = expression.toString();
+            if (exprStr.startsWith("\"")) exprStr = exprStr.substring(1);
+            if (exprStr.endsWith("\"")) exprStr = exprStr.substring(0, exprStr.length() - 1);
+            args.add(exprStr);
+        }
+
+        try {
+            function.evaluate(args);
+        } catch (XPathFunctionException e) {
+            throw new StaticError(e);
+        }
+        XPathFunctionCall fc = new XPathFunctionCall(function);
+        fc.setArguments(staticArgs);
+        return fc;
+    }
+
+}

Added: incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/SaxonContext.java
URL: http://svn.apache.org/viewvc/incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/SaxonContext.java?view=auto&rev=462845
==============================================================================
--- incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/SaxonContext.java (added)
+++ incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/SaxonContext.java Wed Oct 11 09:37:36 2006
@@ -0,0 +1,93 @@
+package org.apache.ode.bpel.elang.xpath20.compiler;
+
+import net.sf.saxon.xpath.StandaloneContext;
+import net.sf.saxon.xpath.XPathFunctionLibrary;
+import net.sf.saxon.trans.Variable;
+import net.sf.saxon.trans.XPathException;
+import net.sf.saxon.trans.StaticError;
+import net.sf.saxon.om.QNameException;
+import net.sf.saxon.om.NameChecker;
+import net.sf.saxon.Configuration;
+import net.sf.saxon.functions.FunctionLibraryList;
+import net.sf.saxon.functions.FunctionLibrary;
+import net.sf.saxon.expr.VariableReference;
+
+import javax.xml.namespace.QName;
+
+import org.apache.ode.utils.Namespaces;
+
+import java.util.List;
+
+/**
+ * Hooks on Saxon StandaloneContext to be notified when the compilation
+ * finds some variables and functions. This allows us to prepare the
+ * OXpathExpression with variable references and all the things needed
+ * at runtime.
+ * @author mriou <mriou at apache dot org>
+ */
+public class SaxonContext extends StandaloneContext {
+
+    private JaxpVariableResolver _varResolver;
+    private JaxpFunctionResolver _funcResolver;
+
+    public SaxonContext(Configuration config, JaxpVariableResolver varResolver,
+                        JaxpFunctionResolver funcResolver) {
+        super(config);
+
+        // We need to remove the default XPathFunctionLibrary to replace it
+        // with our own
+        List libList = ((FunctionLibraryList)getFunctionLibrary()).libraryList;
+        XPathFunctionLibrary xpathLib = null;
+        for (Object lib : libList) {
+            FunctionLibrary flib = (FunctionLibrary) lib;
+            if (flib instanceof XPathFunctionLibrary) xpathLib = (XPathFunctionLibrary) flib;
+        }
+        if (xpathLib != null) libList.remove(xpathLib);
+        OdeXPathFunctionLibrary oxpfl = new OdeXPathFunctionLibrary(funcResolver);
+        oxpfl.setXPathFunctionResolver(funcResolver);
+
+        oxpfl.setXPathFunctionResolver(_funcResolver);
+        ((FunctionLibraryList)getFunctionLibrary()).addFunctionLibrary(oxpfl);
+
+        _varResolver = varResolver;
+        _funcResolver = funcResolver;
+    }
+
+    public Variable declareVariable(String qname, Object initialValue) throws XPathException {
+        String prefix;
+        String localName;
+        final NameChecker checker = getConfiguration().getNameChecker();
+        try {
+            String[] parts = checker.getQNameParts(qname);
+            prefix = parts[0];
+            localName = parts[1];
+        } catch (QNameException err) {
+            throw new StaticError("Invalid QName for variable: " + qname);
+        }
+        String uri = "";
+        if (!("".equals(prefix))) {
+            uri = getURIForPrefix(prefix);
+        }
+
+        _varResolver.resolveVariable(new QName(uri, localName, prefix));
+
+        return super.declareVariable(qname, initialValue);
+    }
+
+    public VariableReference bindVariable(int fingerprint) throws StaticError {
+        String localName = getNamePool().getLocalName(fingerprint);
+        String prefix = getNamePool().getPrefix(fingerprint);
+        String ns = getNamePool().getURI(fingerprint);
+        // The prefix is lost by compilation, hardcoding it from the ns.
+        if (Namespaces.ODE_EXTENSION_NS.equals(ns)) prefix = "ode";
+        if (prefix != null && prefix.length() > 0) prefix = prefix + ":";
+        try {
+            declareVariable(prefix + localName, null);
+        } catch (XPathException e) {
+            throw new StaticError(e);
+        }
+        return super.bindVariable(fingerprint);
+    }
+
+
+}

Modified: incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/XPath20ExpressionCompilerBPEL20.java
URL: http://svn.apache.org/viewvc/incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/XPath20ExpressionCompilerBPEL20.java?view=diff&rev=462845&r1=462844&r2=462845
==============================================================================
--- incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/XPath20ExpressionCompilerBPEL20.java (original)
+++ incubator/ode/trunk/bpel-el-xpath20/src/main/java/org/apache/ode/bpel/elang/xpath20/compiler/XPath20ExpressionCompilerBPEL20.java Wed Oct 11 09:37:36 2006
@@ -43,6 +43,9 @@
 import java.util.HashMap;
 import java.util.Map;
 
+import net.sf.saxon.xpath.XPathEvaluator;
+import net.sf.saxon.xpath.XPathFactoryImpl;
+
 
 /**
  * XPath compiler based on the SAXON implementation.
@@ -126,30 +129,34 @@
         out.xpath = xpathStr;
         try {
             __log.debug("Compiling expression " + xpathStr);
-            XPathFactory xpf = new net.sf.saxon.xpath.XPathFactoryImpl();
-            xpf.setXPathFunctionResolver(new JaxpFunctionResolver(_compilerContext, out, source.getNamespaceContext(), Constants.BPEL20_NS));
+            XPathFactoryImpl xpf = new net.sf.saxon.xpath.XPathFactoryImpl();
+            JaxpFunctionResolver funcResolver = new JaxpFunctionResolver(
+                    _compilerContext, out, source.getNamespaceContext(), Constants.BPEL20_NS);
+            xpf.setXPathFunctionResolver(funcResolver);
             JaxpVariableResolver varResolver = new JaxpVariableResolver(_compilerContext, out);
             xpf.setXPathVariableResolver(varResolver);
 
-            XPath xpe = xpf.newXPath();
+            XPathEvaluator xpe = (XPathEvaluator) xpf.newXPath();
+            xpe.setStaticContext(new SaxonContext(xpf.getConfiguration(), varResolver, funcResolver));
+            xpe.setXPathFunctionResolver(funcResolver);
             xpe.setNamespaceContext(source.getNamespaceContext());
-            XPathExpression expr = xpe.compile(xpathStr);
+            xpe.compile(xpathStr);
+
             // Here we're "faking" an evaluation to parse properly variables and functions and
             // detect all possible mistakes. To do so we're using specific resolvers that always
             // return guessed appropriate values from variable types.
-            expr.evaluate(DOMUtils.newDocument());
+//            expr.evaluate(DOMUtils.newDocument());
 
             // Fishing for predicates
             // TODO Clean that up
-            if (xpathStr.indexOf("[$") > 0) {
-                String rightStr = xpathStr.substring(xpathStr.indexOf("[$") + 2, xpathStr.length());
-                String varStr = rightStr.substring(0, rightStr.indexOf("]"));
-                varResolver.resolveVariable(new QName(null, varStr));
-            }
+//            if (xpathStr.indexOf("[$") > 0) {
+//                String rightStr = xpathStr.substring(xpathStr.indexOf("[$") + 2, xpathStr.length());
+//                String varStr = rightStr.substring(0, rightStr.indexOf("]"));
+//                varResolver.resolveVariable(new QName(null, varStr));
+//            }
         } catch (XPathExpressionException e) {
             System.out.println("Couldn't validate properly expression " + xpathStr);
             __log.info("Couldn't validate properly expression " + xpathStr);
-//            throw new CompilationException(__msgs.warnXPath20Syntax(xpathStr, e.getCause().toString()), e.getCause());
         } catch (WrappedResolverException wre) {
             if (wre._compilationMsg != null) throw new CompilationException(wre._compilationMsg, wre);
             if (wre.getCause() instanceof CompilationException) throw (CompilationException)wre.getCause();

Modified: incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/TestAssign.bpel
URL: http://svn.apache.org/viewvc/incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/TestAssign.bpel?view=diff&rev=462845&r1=462844&r2=462845
==============================================================================
--- incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/TestAssign.bpel (original)
+++ incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/TestAssign.bpel Wed Oct 11 09:37:36 2006
@@ -41,6 +41,8 @@
         <variable name="otherMsgVar" messageType="test:TestAssignMessage"/>
         <variable name="strVar" type="xsd:string"/>
         <variable name="intVar" type="xsd:int"/>
+        <variable name="intVar2" type="xsd:int"/>
+        <variable name="boolVar" type="xsd:boolean"/>
     </variables>
 
     <sequence>
@@ -61,10 +63,22 @@
                 <to variable="intVar"/>
             </copy>
             <copy>
+                <from>$intVar</from>
+                <to>$intVar2</to>
+            </copy>
+            <copy>
+                <from>bpws:getVariableData('intVar')</from>
+                <to>$intVar2</to>
+            </copy>
+            <copy>
                 <from>$intVar + 1</from>
                 <to variable="intVar"/>
             </copy>
             <copy>
+                <from>$intVar = 4</from>
+                <to variable="boolVar"/>
+            </copy>
+            <copy>
                 <from>abs($intVar + number('2'))</from>
                 <to variable="intVar"/>
             </copy>
@@ -73,7 +87,7 @@
                 <to variable="strVar"/>
             </copy>
             <copy>
-                <from>concat($strVar,' World', $intVar)</from>
+                <from>concat($strVar,' World', $intVar, $boolVar,  $intVar2)</from>
                 <to variable="myVar" part="TestPart"/>
             </copy>
             <copy>

Modified: incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/test.properties
URL: http://svn.apache.org/viewvc/incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/test.properties?view=diff&rev=462845&r1=462844&r2=462845
==============================================================================
--- incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/test.properties (original)
+++ incubator/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestAssignActivity1/test.properties Wed Oct 11 09:37:36 2006
@@ -2,4 +2,4 @@
 service=TestAssignService
 operation=testAssign
 request1=<message><TestPart>Hello</TestPart></message>
-response1=.*Hello World6.*
\ No newline at end of file
+response1=.*Hello World6true3.*
\ No newline at end of file