You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ode.apache.org by ka...@apache.org on 2008/11/20 23:58:09 UTC
svn commit: r719416 - in /ode/trunk:
bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/
bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/
bpel-obj/src/main/java/org/apache/ode/bpel/elang/xquery10/ bpel-ob...
Author: karthick
Date: Thu Nov 20 14:58:08 2008
New Revision: 719416
URL: http://svn.apache.org/viewvc?rev=719416&view=rev
Log:
Add XQuery-Related Files (for ODE-411).
Added:
ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/
ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/
ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10BpelFunctions.java
ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20.java
ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20Draft.java
ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerImpl.java
ode/trunk/bpel-obj/src/main/java/org/apache/ode/bpel/elang/xquery10/
ode/trunk/bpel-obj/src/main/java/org/apache/ode/bpel/elang/xquery10/o/
ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/
ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.bpel
ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.wsdl
ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/deploy.xml
ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/test.properties
ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/
ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/OXQuery10ExpressionBPEL20.java
ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/
ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10BpelFunctions.java
ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10ExpressionRuntime.java
Added: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10BpelFunctions.java
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10BpelFunctions.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10BpelFunctions.java (added)
+++ ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10BpelFunctions.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,162 @@
+package org.apache.ode.bpel.compiler.v2.xquery10.compiler;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.namespace.QName;
+import javax.xml.xpath.XPathFunction;
+import javax.xml.xpath.XPathFunctionException;
+
+import net.sf.saxon.dom.NodeWrapper;
+import net.sf.saxon.expr.XPathContext;
+import net.sf.saxon.om.Item;
+
+import org.apache.ode.bpel.compiler.v2.xpath20.JaxpFunctionResolver;
+import org.apache.ode.bpel.rtrep.common.Constants;
+import org.apache.ode.utils.Namespaces;
+import org.w3c.dom.Node;
+
+
+/**
+ * XQuery-Friendly definition of BPEL functions, which
+ * delegates calls to the JAXP-based function resolver
+ */
+public class XQuery10BpelFunctions {
+ public static final String USER_DATA_KEY_FUNCTION_RESOLVER = "function-resolver";
+ private static final QName WSBPEL_GET_VARIABLE_PROPERTY = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_GETVARIABLEPROPERTY);
+ private static final QName WSBPEL_GET_VARIABLE_DATA = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_GETVARIABLEDATA);
+ private static final QName WSBPEL_GET_LINK_STATUS = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_GETLINKSTATUS);
+ private static final QName WSBPEL_DO_XSL_TRANSFORM = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_DOXSLTRANSFORM);
+
+ /**
+ * WS-BPEL getVariableProperty function
+ *
+ * @param context context
+ * @param variableName variableName
+ * @param propertyName propertyName
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object getVariableProperty(XPathContext context,
+ String variableName, String propertyName) throws XPathFunctionException {
+ ArrayList<String> arguments = new ArrayList<String>();
+ arguments.add(variableName);
+ arguments.add(propertyName);
+
+ return evaluate(resolveFunction(context, WSBPEL_GET_VARIABLE_PROPERTY),
+ arguments);
+ }
+
+ /**
+ * WS-BPEL getVariableData function
+ *
+ * @param context context
+ * @param variableName variableName
+ * @param partName partName
+ * @param xpath xpath
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object getVariableData(XPathContext context,
+ String variableName, String partName, String xpath)
+ throws XPathFunctionException {
+ ArrayList<String> arguments = new ArrayList<String>();
+ arguments.add(variableName);
+ arguments.add(partName);
+ arguments.add(xpath);
+
+ return evaluate(resolveFunction(context, WSBPEL_GET_VARIABLE_DATA),
+ arguments);
+ }
+
+ /**
+ * WS-BPEL doXslTransform function
+ *
+ * @param context context
+ * @param xslUri xslUri
+ * @param sources sources
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object doXslTransform(XPathContext context, String xslUri,
+ Object sources) throws XPathFunctionException {
+ ArrayList<Object> arguments = new ArrayList<Object>();
+ arguments.add(xslUri);
+ arguments.add(sources);
+
+ return evaluate(resolveFunction(context, WSBPEL_DO_XSL_TRANSFORM),
+ arguments);
+ }
+
+ /**
+ * WS-BPEL getLinkStatus function
+ *
+ * @param context context
+ * @param linkName linkName
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object getLinkStatus(XPathContext context, String linkName)
+ throws XPathFunctionException {
+ ArrayList<String> arguments = new ArrayList<String>();
+ arguments.add(linkName);
+
+ return evaluate(resolveFunction(context, WSBPEL_GET_LINK_STATUS),
+ arguments);
+ }
+
+ /**
+ * Locates the JAXP equivalent function
+ *
+ * @param context context
+ * @param name name
+ *
+ * @return type
+ */
+ private static XPathFunction resolveFunction(XPathContext context,
+ QName name) {
+ JaxpFunctionResolver funcResolver = null;
+ Item item = context.getCurrentIterator().current();
+
+ if (item instanceof NodeWrapper) {
+ Node node = (Node) ((NodeWrapper) item).getUnderlyingNode();
+
+ if (node != null) {
+ funcResolver = (JaxpFunctionResolver) node.getUserData(USER_DATA_KEY_FUNCTION_RESOLVER);
+ }
+ }
+
+ return funcResolver.resolveFunction(name, 0);
+ }
+
+ /**
+ * Evaluates function against arguments passed by XQuery
+ *
+ * @param function function
+ * @param arguments arguments
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ private static Object evaluate(XPathFunction function, List arguments)
+ throws XPathFunctionException {
+ if (function == null) {
+ throw new XPathFunctionException("Unable to locate function in library");
+ }
+
+ return function.evaluate(arguments);
+ }
+}
Added: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20.java
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20.java (added)
+++ ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,29 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.ode.bpel.compiler.v2.xquery10.compiler;
+
+import org.apache.ode.utils.Namespaces;
+
+
+public class XQuery10ExpressionCompilerBPEL20 extends XQuery10ExpressionCompilerImpl {
+
+ public XQuery10ExpressionCompilerBPEL20() {
+ super(Namespaces.WSBPEL2_0_FINAL_EXEC);
+ }
+}
Added: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20Draft.java
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20Draft.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20Draft.java (added)
+++ ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerBPEL20Draft.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.ode.bpel.compiler.v2.xquery10.compiler;
+
+import org.apache.ode.utils.Namespaces;
+
+public class XQuery10ExpressionCompilerBPEL20Draft extends XQuery10ExpressionCompilerImpl {
+
+ public XQuery10ExpressionCompilerBPEL20Draft() {
+ super(Namespaces.WS_BPEL_20_NS);
+ }
+
+}
Added: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerImpl.java
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerImpl.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerImpl.java (added)
+++ ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/xquery10/compiler/XQuery10ExpressionCompilerImpl.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,397 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.ode.bpel.compiler.v2.xquery10.compiler;
+
+import java.net.URI;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import javax.xml.namespace.QName;
+import javax.xml.transform.Source;
+import javax.xml.transform.TransformerFactory;
+import javax.xml.xquery.XQConnection;
+import javax.xml.xquery.XQConstants;
+import javax.xml.xquery.XQDataSource;
+import javax.xml.xquery.XQException;
+import javax.xml.xquery.XQItemType;
+import javax.xml.xquery.XQPreparedExpression;
+import javax.xml.xquery.XQSequence;
+import javax.xml.xquery.XQStaticContext;
+
+import net.sf.saxon.Configuration;
+import net.sf.saxon.om.Validation;
+import net.sf.saxon.xqj.SaxonXQConnection;
+import net.sf.saxon.xqj.SaxonXQDataSource;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.ode.bpel.compiler.WrappedResolverException;
+import org.apache.ode.bpel.compiler.XPathMessages;
+import org.apache.ode.bpel.compiler.api.CompilationException;
+import org.apache.ode.bpel.compiler.bom.Expression;
+import org.apache.ode.bpel.compiler.v2.xpath20.JaxpFunctionResolver;
+import org.apache.ode.bpel.compiler.v2.CompilerContext;
+import org.apache.ode.bpel.compiler.v2.ExpressionCompiler;
+import org.apache.ode.bpel.compiler.v2.xpath10.XslCompilationErrorListener;
+import org.apache.ode.bpel.compiler.v2.xpath20.JaxpVariableResolver;
+import org.apache.ode.bpel.rtrep.common.Constants;
+import org.apache.ode.bpel.rtrep.v2.OConstantVarType;
+import org.apache.ode.bpel.rtrep.v2.OElementVarType;
+import org.apache.ode.bpel.rtrep.v2.OExpression;
+import org.apache.ode.bpel.rtrep.v2.OLValueExpression;
+import org.apache.ode.bpel.rtrep.v2.OMessageVarType;
+import org.apache.ode.bpel.rtrep.v2.OScope;
+import org.apache.ode.bpel.rtrep.v2.OVarType;
+import org.apache.ode.bpel.rtrep.v2.OXsdTypeVarType;
+import org.apache.ode.bpel.rtrep.v2.OMessageVarType.Part;
+import org.apache.ode.bpel.rtrep.v2.xquery10.OXQuery10ExpressionBPEL20;
+import org.apache.ode.utils.DOMUtils;
+import org.apache.ode.utils.NSContext;
+import org.apache.ode.utils.Namespaces;
+import org.apache.ode.utils.msg.MessageBundle;
+import org.apache.ode.utils.xsl.XslTransformHandler;
+import org.apache.xml.utils.XMLChar;
+import org.w3c.dom.Node;
+import org.w3c.dom.NodeList;
+
+/**
+ * XQuery compiler based on the SAXON implementation.
+ */
+public class XQuery10ExpressionCompilerImpl implements ExpressionCompiler {
+
+ protected static final Log __log = LogFactory.getLog(XQuery10ExpressionCompilerImpl.class);
+
+ protected String _bpelNS;
+ protected QName _qnLinkStatus;
+ protected QName _qnVarProp;
+ protected QName _qnVarData;
+ protected QName _qnXslTransform;
+
+ protected final XPathMessages __msgs = MessageBundle.getMessages(XPathMessages.class);
+ protected Map<String, String> _properties = new HashMap<String, String>();
+ protected CompilerContext _compilerContext;
+
+ public XQuery10ExpressionCompilerImpl(String bpelNS) {
+ _bpelNS = bpelNS;
+ _qnLinkStatus = new QName(_bpelNS, Constants.EXT_FUNCTION_GETLINKSTATUS);
+ _qnVarProp = new QName(_bpelNS, Constants.EXT_FUNCTION_GETVARIABLEPROPERTY);
+ _qnVarData = new QName(_bpelNS, Constants.EXT_FUNCTION_GETVARIABLEDATA);
+ _qnXslTransform = new QName(_bpelNS, Constants.EXT_FUNCTION_DOXSLTRANSFORM);
+
+ _properties.put("runtime-class", "org.apache.ode.bpel.rtrep.v2.xquery10.runtime.XQuery10ExpressionRuntime");
+ TransformerFactory trsf = new net.sf.saxon.TransformerFactoryImpl();
+ XslTransformHandler.getInstance().setTransformerFactory(trsf);
+ }
+
+ public void setCompilerContext(CompilerContext compilerContext) {
+ _compilerContext = compilerContext;
+ XslCompilationErrorListener xe = new XslCompilationErrorListener(compilerContext);
+ XslTransformHandler.getInstance().setErrorListener(xe);
+ }
+
+ /**
+ * @see org.apache.ode.bpel.compiler.api.ExpressionCompiler#compileJoinCondition(java.lang.Object)
+ */
+ public OExpression compileJoinCondition(Object source) throws CompilationException {
+ return _compile((Expression) source, true);
+ }
+
+ /**
+ * @see org.apache.ode.bpel.compiler.api.ExpressionCompiler#compile(java.lang.Object)
+ */
+ public OExpression compile(Object source) throws CompilationException {
+ return _compile((Expression) source, false);
+ }
+
+ /**
+ * @see org.apache.ode.bpel.compiler.api.ExpressionCompiler#compileLValue(java.lang.Object)
+ */
+ public OLValueExpression compileLValue(Object source) throws CompilationException {
+ return (OLValueExpression) _compile((Expression) source, false);
+ }
+
+ /**
+ * @see org.apache.ode.bpel.compiler.api.ExpressionCompiler#compile(java.lang.Object)
+ */
+ private OExpression _compile(org.apache.ode.bpel.compiler.bom.Expression xquery, boolean isJoinCondition)
+ throws CompilationException {
+ OXQuery10ExpressionBPEL20 oexp = new OXQuery10ExpressionBPEL20(_compilerContext.getOProcess(), _qnVarData,
+ _qnVarProp, _qnLinkStatus, _qnXslTransform, isJoinCondition);
+ oexp.namespaceCtx = xquery.getNamespaceContext();
+ doJaxpCompile(oexp, xquery);
+ return oexp;
+ }
+
+ private void doJaxpCompile(OXQuery10ExpressionBPEL20 out, Expression source) throws CompilationException {
+ String xqueryStr;
+ Node node = source.getExpression();
+ if (node == null) {
+ throw new IllegalStateException("XQuery string and xpath node are both null");
+ }
+ if (node.getNodeType() != Node.TEXT_NODE &&
+ node.getNodeType() != Node.ELEMENT_NODE &&
+ node.getNodeType() != Node.CDATA_SECTION_NODE) {
+ throw new CompilationException(__msgs.errUnexpectedNodeTypeForXPath(DOMUtils.domToString(node)));
+ }
+ xqueryStr = DOMUtils.domToString(node);
+ xqueryStr = xqueryStr.trim();
+ if (xqueryStr.length() == 0) {
+ throw new CompilationException(__msgs.warnXPath20Syntax(DOMUtils.domToString(node), "empty string"));
+ }
+
+ try {
+ XQDataSource xqds = new SaxonXQDataSource();
+ XQConnection xqconn = xqds.getConnection();
+
+ __log.debug("Compiling expression " + xqueryStr);
+ Configuration configuration = ((SaxonXQConnection) xqconn).getConfiguration();
+ configuration.setAllNodesUntyped(true);
+ configuration.setHostLanguage(Configuration.XQUERY);
+
+ XQStaticContext staticContext = xqconn.getStaticContext();
+ JaxpFunctionResolver funcResolver = new JaxpFunctionResolver(
+ _compilerContext, out, source.getNamespaceContext(), _bpelNS);
+ JaxpVariableResolver variableResolver = new JaxpVariableResolver(
+ _compilerContext, out);
+
+ XQueryDeclarations declarations = new XQueryDeclarations();
+ NSContext nsContext = source.getNamespaceContext();
+ Set<String> prefixes = nsContext.getPrefixes();
+ for (String prefix : prefixes) {
+ String uri = nsContext.getNamespaceURI(prefix);
+ staticContext.declareNamespace(prefix, uri);
+ if ("".equals(prefix)) {
+ declarations.declareDefaultElementNamespace(uri);
+ } else if ("bpws".equals(prefix)) {
+ declarations.declareNamespace("bpws", "java:" + Constants.XQUERY_FUNCTION_HANDLER_COMPILER);
+ } else {
+ declarations.declareNamespace(prefix, uri);
+ }
+ }
+ declarations.declareVariable(
+ getQName(nsContext, Namespaces.ODE_EXTENSION_NS, "pid"),
+ getQName(nsContext, Namespaces.XML_SCHEMA, "integer"));
+ Map<URI, Source> schemaDocuments = _compilerContext.getSchemaSources();
+ for (URI schemaUri : schemaDocuments.keySet()) {
+ Source schemaSource = schemaDocuments.get(schemaUri);
+ // Don't add schema sources, since our Saxon library is not schema-aware.
+ // configuration.addSchemaSource(schemaSource);
+ }
+ configuration.setSchemaValidationMode(Validation.SKIP);
+ List<OScope.Variable> variables = _compilerContext.getAccessibleVariables();
+ Map<QName, QName> variableTypes = new HashMap<QName, QName>();
+ for (String variableName : getVariableNames(xqueryStr)) {
+ OScope.Variable variable = getVariable(variables, variableName);
+ if (variable == null) {
+ continue;
+ }
+ OVarType type = variable.type;
+ QName nameQName = getNameQName(variableName);
+ QName typeQName = getTypeQName(variableName, type);
+ variableTypes.put(nameQName, typeQName);
+ String prefix = typeQName.getPrefix();
+ if (prefix == null || "".equals(prefix.trim())) {
+ prefix = getPrefixForUri(nsContext, typeQName.getNamespaceURI());
+ }
+ // don't declare typed variables, as our engine is not schema-aware
+ // declarations.declareVariable(variable.name, typeQName);
+ declarations.declareVariable(variableName);
+ }
+
+ // Add implicit declarations as prolog to the user-defined XQuery
+ out.xquery = declarations.toString() + xqueryStr;
+
+ // Check the XQuery for compilation errors
+ xqconn.setStaticContext(staticContext);
+ XQPreparedExpression exp = xqconn.prepareExpression(out.xquery);
+
+ // Pre-evaluate variables and functions by executing query
+ node.setUserData(XQuery10BpelFunctions.USER_DATA_KEY_FUNCTION_RESOLVER,
+ funcResolver, null);
+ exp.bindItem(XQConstants.CONTEXT_ITEM,
+ xqconn.createItemFromNode(node, xqconn.createNodeType()));
+ // Bind external variables to dummy runtime values
+ for (QName variable : exp.getAllUnboundExternalVariables()) {
+ QName typeQName = variableTypes.get(variable);
+ Object value = variableResolver.resolveVariable(variable);
+ if (typeQName != null) {
+ if (value.getClass().getName().startsWith("java.lang")) {
+ exp.bindAtomicValue(variable, value.toString(),
+ xqconn.createAtomicType(XQItemType.XQBASETYPE_ANYATOMICTYPE));
+ } else if (value instanceof Node) {
+ exp.bindNode(variable, (Node) value, xqconn.createNodeType());
+ } else if (value instanceof NodeList) {
+ NodeList nodeList = (NodeList) value;
+ ArrayList nodeArray = new ArrayList();
+ for (int i = 0; i < nodeList.getLength(); i++) {
+ nodeArray.add(nodeList.item(i));
+ }
+ XQSequence sequence = xqconn.createSequence(nodeArray.iterator());
+ exp.bindSequence(variable, sequence);
+ }
+ }
+ }
+ exp.executeQuery();
+ } catch (XQException xqe) {
+ __log.debug(xqe);
+ __log.info("Couldn't validate properly expression " + xqueryStr);
+ } catch (WrappedResolverException wre) {
+ if (wre._compilationMsg != null)
+ throw new CompilationException(wre._compilationMsg, wre);
+ if (wre.getCause() instanceof CompilationException)
+ throw (CompilationException) wre.getCause();
+ throw wre;
+ }
+ }
+
+ public Map<String, String> getProperties() {
+ return _properties;
+ }
+
+ private String getQName(NSContext nsContext, String uri, String localPart) {
+ String prefix = getPrefixForUri(nsContext, uri);
+ return (prefix == null ? localPart : (prefix + ":" + localPart));
+ }
+
+ private String getPrefixForUri(NSContext nsContext, String uri) {
+ Set<String> prefixes = nsContext.getPrefixes();
+ for (String prefix : prefixes) {
+ String anUri = (nsContext.getNamespaceURI(prefix));
+ if (anUri != null && anUri.equals(uri)) {
+ return prefix;
+ }
+ }
+ return null;
+ }
+
+ private List<String> getVariableNames(String xquery) {
+ List<String> variableNames = new ArrayList<String>();
+ for (int index = xquery.indexOf("$"); index != -1; index = xquery.indexOf("$")) {
+ StringBuffer variableName = new StringBuffer();
+ for (char ch = xquery.charAt(++index);
+ XMLChar.isNCName(ch);
+ ch = xquery.charAt(++index)) {
+ variableName.append(ch);
+ }
+ variableNames.add(variableName.toString());
+ xquery = xquery.substring(index);
+ }
+ return variableNames;
+ }
+
+ private OScope.Variable getVariable(List<OScope.Variable> variables, String variableName) {
+ String declaredVariable = getVariableDeclaredName(variableName);
+ for (OScope.Variable variable : variables) {
+ if (variable.name.equals(declaredVariable)) {
+ return variable;
+ }
+ }
+ return null;
+ }
+
+ private String getVariableDeclaredName(String variableReference) {
+ int dotIndex = variableReference.indexOf(".");
+ return dotIndex >= 0 ? variableReference.substring(0, dotIndex) : variableReference;
+ }
+
+ private String getVariablePartName(String variableReference) {
+ int dotIndex = variableReference.indexOf(".");
+ return dotIndex >= 0 ? variableReference.substring(dotIndex + 1) : "";
+ }
+
+ private QName getNameQName(String variableName) {
+ String prefix = null, localName = null;;
+ int colonIndex = variableName.indexOf(":");
+ if (colonIndex >= 0) {
+ prefix = variableName.substring(0, colonIndex);
+ localName = variableName.substring(colonIndex + 1);
+ } else {
+ prefix = "";
+ localName = variableName;
+ }
+ return new QName(prefix, localName);
+ }
+
+ private QName getTypeQName(String variableName, OVarType type) {
+ QName typeQName = null;
+ if (type instanceof OConstantVarType) {
+ typeQName = new QName(Namespaces.XML_SCHEMA, "string", "xs");
+ } else if (type instanceof OElementVarType) {
+ typeQName = ((OElementVarType) type).elementType;
+ } else if (type instanceof OMessageVarType) {
+ Part part = ((OMessageVarType) type).parts.get(getVariablePartName(variableName));
+ if (part != null) {
+ typeQName = getTypeQName(variableName, part.type);
+ }
+ } else if (type instanceof OXsdTypeVarType) {
+ typeQName = ((OXsdTypeVarType) type).xsdType;
+ }
+ return typeQName;
+ }
+
+ private class XQueryDeclarations {
+ StringBuffer declarations = new StringBuffer();
+
+ public XQueryDeclarations() {}
+
+ public void declareVariable(String name, QName type) {
+ declareVariable(name, type.getPrefix() + ":" + type.getLocalPart());
+ }
+
+ public void declareVariable(String name, String type) {
+ declarations.append("declare variable ")
+ .append("$")
+ .append(name)
+ .append(" as ")
+ .append(type)
+ .append(" external ")
+ .append(";\n");
+ }
+
+ public void declareVariable(String name) {
+ declarations.append("declare variable ")
+ .append("$")
+ .append(name)
+ .append(" external ")
+ .append(";\n");
+ }
+
+ public void declareNamespace(String prefix, String uri) {
+ declarations.append("declare namespace ")
+ .append(prefix)
+ .append("=")
+ .append("\"" + uri + "\"")
+ .append(";\n");
+ }
+
+ public void declareDefaultElementNamespace(String uri) {
+ declarations.append("declare default element namespace ")
+ .append("\"" + uri + "\"")
+ .append(";\n");
+ }
+
+ public String toString() {
+ return declarations.toString();
+ }
+ }
+}
Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.bpel
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.bpel?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.bpel (added)
+++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.bpel Thu Nov 20 14:58:08 2008
@@ -0,0 +1,107 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+<process name="HelloXQueryWorld"
+ targetNamespace="http://ode/bpel/unit-test"
+ xmlns:bpws="http://docs.oasis-open.org/wsbpel/2.0/process/executable"
+ xmlns="http://docs.oasis-open.org/wsbpel/2.0/process/executable"
+ xmlns:tns="http://ode/bpel/unit-test"
+ xmlns:xsd="http://www.w3.org/2001/XMLSchema"
+ xmlns:types="http://ode/bpel/types"
+ xmlns:test="http://ode/bpel/unit-test.wsdl"
+ xmlns:ode="http://www.apache.org/ode/type/extension"
+ queryLanguage="urn:oasis:names:tc:wsbpel:2.0:sublang:xquery1.0"
+ expressionLanguage="urn:oasis:names:tc:wsbpel:2.0:sublang:xquery1.0">
+
+ <import location="HelloXQueryWorld.wsdl"
+ namespace="http://ode/bpel/unit-test.wsdl"
+ importType="http://schemas.xmlsoap.org/wsdl/"/>
+
+ <partnerLinks>
+ <partnerLink name="HelloXQueryPartnerLink"
+ partnerLinkType="test:HelloXQueryPartnerLinkType"
+ myRole="me" />
+ </partnerLinks>
+
+ <variables>
+ <variable name="myVar" messageType="test:HelloXQueryMessage"/>
+ <variable name="tempVar" element="test:content"/>
+ <variable name="otherVar" type="xsd:string"/>
+ </variables>
+
+ <sequence>
+ <receive
+ name="start"
+ partnerLink="HelloXQueryPartnerLink"
+ portType="test:HelloXQueryPortType"
+ operation="HelloXQuery"
+ variable="myVar"
+ createInstance="yes"/>
+ <assign name="assign1">
+ <copy>
+ <from variable="myVar" part="TestPart"/>
+ <to variable="otherVar"/>
+ </copy>
+ <copy>
+ <from><![CDATA[<test:content>Hello</test:content>]]></from>
+ <to variable="tempVar"/>
+ </copy>
+ <copy>
+ <from>
+ typeswitch ($myVar.TestPart)
+ case $a as xs:string return "test"
+ default return "default"
+ </from>
+ <to variable="otherVar"/>
+ </copy>
+ <copy>
+ <from><![CDATA[
+ typeswitch ($myVar.TestPart)
+ case $a as text() return <test:content/>
+ default return <test:content/>
+ ]]>
+ </from>
+ <to variable="otherVar"/>
+ </copy>
+ <!-- this copy will fail since saxon is not schema-aware
+ <copy>
+ <from>
+ typeswitch ($myVar.TestPart)
+ case $a as element(*, test:content) return "test"
+ default return "default"
+ </from>
+ <to variable="otherVar"/>
+ </copy>
+ -->
+ <copy>
+ <from>
+ for $loopOnce in (1)
+ return
+ concat(bpws:getVariableProperty("myVar", "test:content"), "XQuery World")
+ </from>
+ <to variable="myVar" part="TestPart"/>
+ </copy>
+ </assign>
+ <reply name="end"
+ partnerLink="HelloXQueryPartnerLink"
+ portType="test:HelloXQueryPortType"
+ operation="HelloXQuery"
+ variable="myVar"/>
+ </sequence>
+
+</process>
Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.wsdl
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.wsdl?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.wsdl (added)
+++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/HelloXQueryWorld.wsdl Thu Nov 20 14:58:08 2008
@@ -0,0 +1,91 @@
+<?xml version="1.0" encoding="utf-8" ?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<wsdl:definitions
+ targetNamespace="http://ode/bpel/unit-test.wsdl"
+ xmlns="http://schemas.xmlsoap.org/wsdl/"
+ xmlns:tns="http://ode/bpel/unit-test.wsdl"
+ xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
+ xmlns:xsd="http://www.w3.org/2001/XMLSchema"
+ xmlns:vprop="http://docs.oasis-open.org/wsbpel/2.0/varprop"
+ xmlns:types="http://ode/bpel/types"
+ xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
+ xmlns:bpws="http://docs.oasis-open.org/wsbpel/2.0/process/executable"
+ xmlns:plnk="http://docs.oasis-open.org/wsbpel/2.0/plnktype">
+
+ <wsdl:types>
+ <xsd:schema targetNamespace="http://ode/bpel/types">
+ <xsd:complexType name="ContentCT">
+ <xsd:sequence>
+ <xsd:element name="content" type="xsd:string"/>
+ </xsd:sequence>
+ </xsd:complexType>
+ </xsd:schema>
+ </wsdl:types>
+
+ <wsdl:message name="HelloXQueryMessage">
+ <wsdl:part name="TestPart" type="types:ContentCT"/>
+ </wsdl:message>
+
+ <wsdl:portType name="HelloXQueryPortType">
+ <wsdl:operation name="HelloXQuery">
+ <wsdl:input message="tns:HelloXQueryMessage" name="TestIn"/>
+ <wsdl:output message="tns:HelloXQueryMessage" name="TestOut"/>
+ </wsdl:operation>
+ </wsdl:portType>
+
+ <wsdl:binding name="HelloXQuerySoapBinding" type="tns:HelloXQueryPortType">
+ <soap:binding style="rpc" transport="http://schemas.xmlsoap.org/soap/http"/>
+ <wsdl:operation name="HelloXQuery">
+ <soap:operation soapAction="" style="rpc"/>
+ <wsdl:input>
+ <soap:body
+ namespace="http://ode/bpel/unit-test.wsdl"
+ use="literal"/>
+ </wsdl:input>
+ <wsdl:output>
+ <soap:body
+ namespace="http://ode/bpel/unit-test.wsdl"
+ use="literal"/>
+ </wsdl:output>
+ </wsdl:operation>
+ </wsdl:binding>
+ <wsdl:service name="HelloXQueryService">
+ <wsdl:port name="HelloXQueryPort" binding="tns:HelloXQuerySoapBinding">
+ <soap:address location="http://localhost:8080/ode/processes/HelloXQueryWorld"/>
+ </wsdl:port>
+ </wsdl:service>
+
+ <plnk:partnerLinkType name="HelloXQueryPartnerLinkType">
+ <plnk:role name="me" portType="tns:HelloXQueryPortType"/>
+ <plnk:role name="you" portType="tns:HelloXQueryPortType"/>
+ </plnk:partnerLinkType>
+
+ <vprop:property name="content" type="xsd:string"/>
+ <vprop:propertyAlias propertyName="tns:content" messageType="tns:HelloXQueryMessage" part="TestPart">
+
+ <vprop:query queryLanguage="urn:oasis:names:tc:wsbpel:2.0:sublang:xpath2.0">
+ content
+ </vprop:query>
+
+ </vprop:propertyAlias>
+
+</wsdl:definitions>
+
Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/deploy.xml
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/deploy.xml?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/deploy.xml (added)
+++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/deploy.xml Thu Nov 20 14:58:08 2008
@@ -0,0 +1,29 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+<deploy xmlns="http://www.apache.org/ode/schemas/dd/2007/03"
+ xmlns:pns="http://ode/bpel/unit-test"
+ xmlns:wns="http://ode/bpel/unit-test.wsdl">
+
+ <process name="pns:HelloXQueryWorld">
+ <active>true</active>
+ <provide partnerLink="HelloXQueryPartnerLink">
+ <service name="wns:HelloXQueryService" port="HelloXQueryPort"/>
+ </provide>
+ </process>
+</deploy>
Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/test.properties
URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/test.properties?rev=719416&view=auto
==============================================================================
--- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/test.properties (added)
+++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestXQueryExpression/test.properties Thu Nov 20 14:58:08 2008
@@ -0,0 +1,23 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements. See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.
+# The ASF licenses this file to You under the Apache License, Version 2.0
+# (the "License"); you may not use this file except in compliance with
+# the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+
+namespace=http://ode/bpel/unit-test.wsdl
+service=HelloXQueryService
+operation=HelloXQuery
+request1=<message><TestPart><content>Hello</content></TestPart></message>
+response1=.*HelloXQuery World.*
+
Added: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/OXQuery10ExpressionBPEL20.java
URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/OXQuery10ExpressionBPEL20.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/OXQuery10ExpressionBPEL20.java (added)
+++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/OXQuery10ExpressionBPEL20.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,42 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.ode.bpel.rtrep.v2.xquery10;
+
+import javax.xml.namespace.QName;
+
+import org.apache.ode.bpel.rtrep.v2.OProcess;
+import org.apache.ode.bpel.rtrep.v2.xpath20.OXPath20ExpressionBPEL20;
+
+/**
+ * A representation of an XQuery expression
+ */
+public class OXQuery10ExpressionBPEL20 extends OXPath20ExpressionBPEL20 {
+
+ private static final long serialVersionUID = -1L;
+
+ public String xquery;
+
+ public OXQuery10ExpressionBPEL20(OProcess owner, QName qname_getVariableData,
+ QName qname_getVariableProperty, QName qname_getLinkStatus,
+ QName qname_doXslTransform, boolean isJoinExpression) {
+ super(owner, qname_getVariableData, qname_getVariableProperty, qname_getLinkStatus,
+ qname_doXslTransform, isJoinExpression);
+ }
+}
Added: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10BpelFunctions.java
URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10BpelFunctions.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10BpelFunctions.java (added)
+++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10BpelFunctions.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,162 @@
+package org.apache.ode.bpel.rtrep.v2.xquery10.runtime;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.namespace.QName;
+import javax.xml.xpath.XPathFunction;
+import javax.xml.xpath.XPathFunctionException;
+
+import net.sf.saxon.dom.NodeWrapper;
+import net.sf.saxon.expr.XPathContext;
+import net.sf.saxon.om.Item;
+
+import org.apache.ode.bpel.rtrep.common.Constants;
+import org.apache.ode.bpel.rtrep.v2.xpath20.JaxpFunctionResolver;
+import org.apache.ode.utils.Namespaces;
+import org.w3c.dom.Node;
+
+
+/**
+ * XQuery-Friendly definition of BPEL functions, which
+ * delegates calls to the JAXP-based function resolver
+ */
+public class XQuery10BpelFunctions {
+ public static final String USER_DATA_KEY_FUNCTION_RESOLVER = "function-resolver";
+ private static final QName WSBPEL_GET_VARIABLE_PROPERTY = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_GETVARIABLEPROPERTY);
+ private static final QName WSBPEL_GET_VARIABLE_DATA = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_GETVARIABLEDATA);
+ private static final QName WSBPEL_GET_LINK_STATUS = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_GETLINKSTATUS);
+ private static final QName WSBPEL_DO_XSL_TRANSFORM = new QName(Namespaces.WSBPEL2_0_FINAL_EXEC,
+ Constants.EXT_FUNCTION_DOXSLTRANSFORM);
+
+ /**
+ * WS-BPEL getVariableProperty function
+ *
+ * @param context context
+ * @param variableName variableName
+ * @param propertyName propertyName
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object getVariableProperty(XPathContext context,
+ String variableName, String propertyName) throws XPathFunctionException {
+ ArrayList<String> arguments = new ArrayList<String>();
+ arguments.add(variableName);
+ arguments.add(propertyName);
+
+ return evaluate(resolveFunction(context, WSBPEL_GET_VARIABLE_PROPERTY),
+ arguments);
+ }
+
+ /**
+ * WS-BPEL getVariableData function
+ *
+ * @param context context
+ * @param variableName variableName
+ * @param partName partName
+ * @param xpath xpath
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object getVariableData(XPathContext context,
+ String variableName, String partName, String xpath)
+ throws XPathFunctionException {
+ ArrayList<String> arguments = new ArrayList<String>();
+ arguments.add(variableName);
+ arguments.add(partName);
+ arguments.add(xpath);
+
+ return evaluate(resolveFunction(context, WSBPEL_GET_VARIABLE_DATA),
+ arguments);
+ }
+
+ /**
+ * WS-BPEL doXslTransform function
+ *
+ * @param context context
+ * @param xslUri xslUri
+ * @param sources sources
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object doXslTransform(XPathContext context, String xslUri,
+ Object sources) throws XPathFunctionException {
+ ArrayList<Object> arguments = new ArrayList<Object>();
+ arguments.add(xslUri);
+ arguments.add(sources);
+
+ return evaluate(resolveFunction(context, WSBPEL_DO_XSL_TRANSFORM),
+ arguments);
+ }
+
+ /**
+ * WS-BPEL getLinkStatus function
+ *
+ * @param context context
+ * @param linkName linkName
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ public static Object getLinkStatus(XPathContext context, String linkName)
+ throws XPathFunctionException {
+ ArrayList<String> arguments = new ArrayList<String>();
+ arguments.add(linkName);
+
+ return evaluate(resolveFunction(context, WSBPEL_GET_LINK_STATUS),
+ arguments);
+ }
+
+ /**
+ * Locates the equivalent JAXP function
+ *
+ * @param context context
+ * @param name name
+ *
+ * @return type
+ */
+ private static XPathFunction resolveFunction(XPathContext context,
+ QName name) {
+ JaxpFunctionResolver funcResolver = null;
+ Item item = context.getCurrentIterator().current();
+
+ if (item instanceof NodeWrapper) {
+ Node node = (Node) ((NodeWrapper) item).getUnderlyingNode();
+
+ if (node != null) {
+ funcResolver = (JaxpFunctionResolver) node.getUserData(USER_DATA_KEY_FUNCTION_RESOLVER);
+ }
+ }
+
+ return funcResolver.resolveFunction(name, 0);
+ }
+
+ /**
+ * Evaluates function against arguments passed by XQuery
+ *
+ * @param function function
+ * @param arguments arguments
+ *
+ * @return type
+ *
+ * @throws XPathFunctionException XPathFunctionException
+ */
+ private static Object evaluate(XPathFunction function, List arguments)
+ throws XPathFunctionException {
+ if (function == null) {
+ throw new XPathFunctionException("Unable to locate function in library");
+ }
+
+ return function.evaluate(arguments);
+ }
+}
Added: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10ExpressionRuntime.java
URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10ExpressionRuntime.java?rev=719416&view=auto
==============================================================================
--- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10ExpressionRuntime.java (added)
+++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xquery10/runtime/XQuery10ExpressionRuntime.java Thu Nov 20 14:58:08 2008
@@ -0,0 +1,554 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.ode.bpel.rtrep.v2.xquery10.runtime;
+
+import java.util.ArrayList;
+import java.util.Calendar;
+import java.util.Collections;
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import javax.xml.namespace.QName;
+import javax.xml.transform.TransformerFactory;
+import javax.xml.xpath.XPathConstants;
+import javax.xml.xquery.XQConnection;
+import javax.xml.xquery.XQConstants;
+import javax.xml.xquery.XQDataSource;
+import javax.xml.xquery.XQException;
+import javax.xml.xquery.XQItem;
+import javax.xml.xquery.XQItemType;
+import javax.xml.xquery.XQPreparedExpression;
+import javax.xml.xquery.XQResultSequence;
+import javax.xml.xquery.XQSequence;
+import javax.xml.xquery.XQStaticContext;
+
+import net.sf.saxon.Configuration;
+import net.sf.saxon.om.Validation;
+import net.sf.saxon.trans.DynamicError;
+import net.sf.saxon.value.DurationValue;
+import net.sf.saxon.xqj.SaxonXQConnection;
+import net.sf.saxon.xqj.SaxonXQDataSource;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.ode.bpel.common.FaultException;
+import org.apache.ode.bpel.rtrep.common.ConfigurationException;
+import org.apache.ode.bpel.rtrep.common.Constants;
+import org.apache.ode.bpel.rtrep.v2.EvaluationContext;
+import org.apache.ode.bpel.rtrep.v2.ExpressionLanguageRuntime;
+import org.apache.ode.bpel.rtrep.v2.OExpression;
+import org.apache.ode.bpel.rtrep.v2.xpath20.JaxpFunctionResolver;
+import org.apache.ode.bpel.rtrep.v2.xpath20.JaxpVariableResolver;
+import org.apache.ode.bpel.rtrep.v2.xquery10.OXQuery10ExpressionBPEL20;
+import org.apache.ode.utils.DOMUtils;
+import org.apache.ode.utils.ISO8601DateParser;
+import org.apache.ode.utils.NSContext;
+import org.apache.ode.utils.xsd.Duration;
+import org.apache.ode.utils.xsl.XslTransformHandler;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+import org.w3c.dom.NodeList;
+import org.w3c.dom.Text;
+
+
+/**
+ * XQuery 1.0 Expression Language run-time subsytem. Saxon implementation.
+ */
+@SuppressWarnings("deprecation")
+public class XQuery10ExpressionRuntime implements ExpressionLanguageRuntime {
+ static final short NODE_TYPE = 1;
+ static final short NODESET_TYPE = 2;
+ static final short STRING_TYPE = 3;
+ static final short BOOLEAN_TYPE = 4;
+ static final short NUMBER_TYPE = 5;
+
+ /** Class-level logger. */
+ private static final Log __log = LogFactory.getLog(XQuery10ExpressionRuntime.class);
+
+ /**
+ * Creates a new XQuery10ExpressionRuntime object.
+ */
+ public XQuery10ExpressionRuntime() {
+ }
+
+ /**
+ * Initialize XSL Transformer
+ *
+ * @param properties properties
+ *
+ * @throws ConfigurationException ConfigurationException
+ */
+ public void initialize(Map properties) throws ConfigurationException {
+ TransformerFactory trsf = new net.sf.saxon.TransformerFactoryImpl();
+ XslTransformHandler.getInstance().setTransformerFactory(trsf);
+ }
+
+ /**
+ *
+ * @see org.apache.ode.bpel.explang.ExpressionLanguageRuntime#evaluateAsString(org.apache.ode.bpel.o.OExpression,
+ * org.apache.ode.bpel.explang.EvaluationContext)
+ */
+ public String evaluateAsString(OExpression cexp, EvaluationContext ctx)
+ throws FaultException {
+ return (String) evaluate(cexp, ctx, XPathConstants.STRING);
+ }
+
+ /**
+ *
+ * @see org.apache.ode.bpel.explang.ExpressionLanguageRuntime#evaluateAsBoolean(org.apache.ode.bpel.o.OExpression,
+ * org.apache.ode.bpel.explang.EvaluationContext)
+ */
+ public boolean evaluateAsBoolean(OExpression cexp, EvaluationContext ctx)
+ throws FaultException {
+ return (Boolean) evaluate(cexp, ctx, XPathConstants.BOOLEAN);
+ }
+
+ /**
+ * Evaluate expression and return a number
+ *
+ * @param cexp cexp
+ * @param ctx ctx
+ *
+ * @return type
+ *
+ * @throws FaultException FaultException
+ */
+ public Number evaluateAsNumber(OExpression cexp, EvaluationContext ctx)
+ throws FaultException {
+ return (Number) evaluate(cexp, ctx, XPathConstants.NUMBER);
+ }
+
+ /**
+ *
+ * @see org.apache.ode.bpel.explang.ExpressionLanguageRuntime#evaluate(org.apache.ode.bpel.o.OExpression,
+ * org.apache.ode.bpel.explang.EvaluationContext)
+ */
+ public List evaluate(OExpression cexp, EvaluationContext ctx)
+ throws FaultException {
+ List result;
+ Object someRes = evaluate(cexp, ctx, XPathConstants.NODESET);
+
+ if (someRes instanceof List) {
+ result = (List) someRes;
+ __log.debug("Returned list of size " + result.size());
+
+ if ((result.size() == 1) && !(result.get(0) instanceof Node)) {
+ // Dealing with a Java class
+ Object simpleType = result.get(0);
+
+ // Dates get a separate treatment as we don't want to call toString on them
+ String textVal;
+
+ if (simpleType instanceof Date) {
+ textVal = ISO8601DateParser.format((Date) simpleType);
+ } else if (simpleType instanceof DurationValue) {
+ textVal = ((DurationValue) simpleType).getStringValue();
+ } else {
+ textVal = simpleType.toString();
+ }
+
+ // Wrapping in a document
+ Document d = DOMUtils.newDocument();
+
+ // Giving our node a parent just in case it's an LValue expression
+ Element wrapper = d.createElement("wrapper");
+ Text text = d.createTextNode(textVal);
+ wrapper.appendChild(text);
+ d.appendChild(wrapper);
+ result = Collections.singletonList(text);
+ }
+ } else if (someRes instanceof NodeList) {
+ NodeList retVal = (NodeList) someRes;
+ __log.debug("Returned node list of size " + retVal.getLength());
+ result = new ArrayList(retVal.getLength());
+
+ for (int m = 0; m < retVal.getLength(); ++m) {
+ Node val = retVal.item(m);
+
+ if (val.getNodeType() == Node.DOCUMENT_NODE) {
+ val = ((Document) val).getDocumentElement();
+ }
+
+ result.add(val);
+ }
+ } else {
+ result = null;
+ }
+
+ return result;
+ }
+
+ /**
+ * Evaluate expression and return a node
+ *
+ * @param cexp cexp
+ * @param ctx ctx
+ *
+ * @return type
+ *
+ * @throws FaultException FaultException
+ */
+ public Node evaluateNode(OExpression cexp, EvaluationContext ctx)
+ throws FaultException {
+ List retVal = evaluate(cexp, ctx);
+
+ if (retVal.size() == 0) {
+ throw new FaultException(cexp.getOwner().constants.qnSelectionFailure,
+ "No results for expression: " + cexp);
+ }
+
+ if (retVal.size() > 1) {
+ throw new FaultException(cexp.getOwner().constants.qnSelectionFailure,
+ "Multiple results for expression: " + cexp);
+ }
+
+ return (Node) retVal.get(0);
+ }
+
+ /**
+ * Evaluate expression and return a date
+ *
+ * @param cexp cexp
+ * @param context context
+ *
+ * @return type
+ *
+ * @throws FaultException FaultException
+ */
+ public Calendar evaluateAsDate(OExpression cexp, EvaluationContext context)
+ throws FaultException {
+ List literal = DOMUtils.toList(evaluate(cexp, context,
+ XPathConstants.NODESET));
+
+ if (literal.size() == 0) {
+ throw new FaultException(cexp.getOwner().constants.qnSelectionFailure,
+ "No results for expression: " + cexp);
+ }
+
+ if (literal.size() > 1) {
+ throw new FaultException(cexp.getOwner().constants.qnSelectionFailure,
+ "Multiple results for expression: " + cexp);
+ }
+
+ Object date = literal.get(0);
+
+ if (date instanceof Calendar) {
+ return (Calendar) date;
+ }
+
+ if (date instanceof Date) {
+ Calendar cal = Calendar.getInstance();
+ cal.setTime((Date) date);
+
+ return cal;
+ }
+
+ if (date instanceof Element) {
+ date = ((Element) date).getTextContent();
+ }
+
+ try {
+ return ISO8601DateParser.parseCal(date.toString());
+ } catch (Exception ex) {
+ String errmsg = "Invalid date: " + literal;
+ __log.error(errmsg, ex);
+ throw new FaultException(cexp.getOwner().constants.qnInvalidExpressionValue,
+ errmsg);
+ }
+ }
+
+ /**
+ * Evaluate expression and return duration
+ *
+ * @param cexp cexp
+ * @param context context
+ *
+ * @return type
+ *
+ * @throws FaultException FaultException
+ */
+ public Duration evaluateAsDuration(OExpression cexp,
+ EvaluationContext context) throws FaultException {
+ String literal = this.evaluateAsString(cexp, context);
+
+ try {
+ return new Duration(literal);
+ } catch (Exception ex) {
+ String errmsg = "Invalid duration: " + literal;
+ __log.error(errmsg, ex);
+ throw new FaultException(cexp.getOwner().constants.qnInvalidExpressionValue,
+ errmsg);
+ }
+ }
+
+ /**
+ * Evaluate expression and return opaque type
+ *
+ * @param cexp cexp
+ * @param ctx ctx
+ * @param type type
+ *
+ * @return type
+ *
+ * @throws FaultException FaultException
+ */
+ private Object evaluate(OExpression cexp, EvaluationContext ctx, QName type)
+ throws FaultException {
+ try {
+ OXQuery10ExpressionBPEL20 oxquery10 = ((OXQuery10ExpressionBPEL20) cexp);
+
+ XQDataSource xqds = new SaxonXQDataSource();
+ XQConnection xqconn = xqds.getConnection();
+
+ Configuration configuration = ((SaxonXQConnection) xqconn).getConfiguration();
+ configuration.setAllNodesUntyped(true);
+ configuration.setHostLanguage(Configuration.XQUERY);
+
+ XQStaticContext staticEnv = xqconn.getStaticContext();
+
+ NSContext nsContext = oxquery10.namespaceCtx;
+ Set<String> prefixes = nsContext.getPrefixes();
+ for (String prefix : prefixes) {
+ String uri = nsContext.getNamespaceURI(prefix);
+ staticEnv.declareNamespace(prefix, uri);
+ }
+
+ configuration.setSchemaValidationMode(Validation.SKIP);
+ xqconn.setStaticContext(staticEnv);
+
+ // Prepare expression, for starters
+ String xquery = oxquery10.xquery.replaceFirst(
+ Constants.XQUERY_FUNCTION_HANDLER_COMPILER,
+ Constants.XQUERY_FUNCTION_HANDLER_RUNTIME);
+ XQPreparedExpression exp = xqconn.prepareExpression(xquery);
+
+ JaxpFunctionResolver funcResolver = new JaxpFunctionResolver(ctx,
+ oxquery10);
+ JaxpVariableResolver variableResolver = new JaxpVariableResolver(ctx,
+ oxquery10, configuration);
+ // Bind external variables to runtime values
+ for (QName variable : exp.getAllUnboundExternalVariables()) {
+ // Evaluate referenced variable
+ Object value = variableResolver.resolveVariable(variable);
+
+ // Figure out type of variable
+ XQItemType xqType = getItemType(xqconn, value);
+
+ // Saxon doesn't like binding sequences to variables
+ if (value instanceof NodeList) {
+ // So extract the first item from the node list
+ NodeList nodeList = (NodeList) value;
+ ArrayList nodeArray = new ArrayList();
+ for (int i = 0; i < nodeList.getLength(); i++) {
+ nodeArray.add(nodeList.item(i));
+ }
+ value = xqconn.createSequence(nodeArray.iterator());
+ }
+
+
+ // Bind value with external variable
+ if (value != null && xqType != null) {
+ if (value instanceof XQSequence) {
+ exp.bindSequence(variable, (XQSequence) value);
+ } else {
+ exp.bindObject(variable, value, xqType);
+ }
+ }
+ }
+
+ // Set context node
+ Node contextNode = (ctx.getRootNode() == null)
+ ? DOMUtils.newDocument() : ctx.getRootNode();
+ contextNode.setUserData(XQuery10BpelFunctions.USER_DATA_KEY_FUNCTION_RESOLVER,
+ funcResolver, null);
+ exp.bindItem(XQConstants.CONTEXT_ITEM,
+ xqconn.createItemFromNode(contextNode, xqconn.createNodeType()));
+
+ // Execute query
+ XQResultSequence result = exp.executeQuery();
+
+ // Cast Saxon result to Java result
+ Object evalResult = getResultValue(type, result);
+
+ if ((evalResult != null) && __log.isDebugEnabled()) {
+ __log.debug("Expression " + cexp.toString() +
+ " generated result " + evalResult + " - type=" +
+ evalResult.getClass().getName());
+
+ if (ctx.getRootNode() != null) {
+ __log.debug("Was using context node " +
+ DOMUtils.domToString(ctx.getRootNode()));
+ }
+ }
+
+ return evalResult;
+ } catch (XQException xqe) {
+ // Extracting the real cause from all this wrapping isn't a simple task
+ Throwable cause = (xqe.getCause() != null) ? xqe.getCause() : xqe;
+
+ if (cause instanceof DynamicError) {
+ Throwable th = ((DynamicError) cause).getException();
+
+ if (th != null) {
+ cause = th;
+
+ if (cause.getCause() != null) {
+ cause = cause.getCause();
+ }
+ }
+ }
+ throw new FaultException(cexp.getOwner().constants.qnSubLanguageExecutionFault, cause.getMessage(), cause);
+ } catch (Throwable t) {
+ __log.debug("Could not evaluate expression because of ", t);
+ throw new FaultException(cexp.getOwner().constants.qnSubLanguageExecutionFault, t.getMessage(), t);
+ }
+ }
+
+ /**
+ * Return opaque object embedded in XQuery Item
+ *
+ * @param item item
+ *
+ * @return type
+ *
+ * @throws XQException XQException
+ */
+ private Object getItemValue(XQItem item) throws XQException {
+ XQItemType itemType = item.getItemType();
+ Object itemValue = null;
+
+ switch (itemType.getBaseType()) {
+ case XQItemType.XQBASETYPE_BOOLEAN:
+ itemValue = item.getBoolean();
+
+ break;
+
+ case XQItemType.XQBASETYPE_DECIMAL:
+ itemValue = item.getDouble();
+
+ break;
+
+ case XQItemType.XQBASETYPE_BYTE:
+ itemValue = item.getByte();
+
+ break;
+
+ case XQItemType.XQBASETYPE_FLOAT:
+ itemValue = item.getFloat();
+
+ break;
+
+ case XQItemType.XQBASETYPE_INT:
+ case XQItemType.XQBASETYPE_INTEGER:
+ itemValue = item.getInt();
+
+ break;
+
+ case XQItemType.XQBASETYPE_LONG:
+ itemValue = item.getLong();
+
+ break;
+
+ case XQItemType.XQBASETYPE_ANYTYPE:
+ itemValue = item.getNode();
+
+ break;
+
+ case XQItemType.XQBASETYPE_ANYURI:
+ itemValue = item.getNodeUri();
+
+ break;
+
+ case XQItemType.XQBASETYPE_SHORT:
+ itemValue = item.getShort();
+
+ break;
+
+ case XQItemType.XQBASETYPE_STRING:
+ case XQItemType.XQBASETYPE_ANYATOMICTYPE:
+ itemValue = item.getAtomicValue();
+
+ break;
+ }
+
+ return itemValue;
+ }
+
+ /**
+ * Return XQuery type corresponding to given value
+ *
+ * @param xqconn XQuery connection
+ * @param value value
+ *
+ * @return type
+ *
+ * @throws XQException XQException
+ */
+ private XQItemType getItemType(XQConnection xqconn, Object value) throws XQException {
+ XQItemType xqType = null;
+ if (value instanceof Long) {
+ xqType = xqconn.createAtomicType(XQItemType.XQBASETYPE_LONG);
+ } else if (value instanceof String) {
+ xqType = xqconn.createAtomicType(XQItemType.XQBASETYPE_STRING);
+ } else if (value instanceof NodeList) {
+ NodeList nodeList = (NodeList) value;
+
+ if (nodeList.getLength() == 1) {
+ xqType = xqconn.createNodeType();
+ value = nodeList.item(0);
+ } else {
+ value = null;
+ }
+ }
+ return xqType;
+ }
+
+ /**
+ * Cast XQuery sequence into an opaque list
+ *
+ * @param type type
+ * @param result result
+ *
+ * @return value
+ *
+ * @throws XQException XQException
+ */
+ private Object getResultValue(QName type, XQResultSequence result) throws XQException {
+ Object resultValue = null;
+ if (XPathConstants.NODESET.equals(type)) {
+ List list = new ArrayList();
+
+ while (result.next()) {
+ Object itemValue = getItemValue(result.getItem());
+
+ if (itemValue != null) {
+ list.add(itemValue);
+ }
+ }
+
+ resultValue = list;
+ } else {
+ resultValue = getItemValue(result.getItem());
+ }
+ return resultValue;
+ }
+}