Author: karthick Date: Wed Oct 29 17:29:15 2008 New Revision: 709057 URL: http://svn.apache.org/viewvc?rev=709057&view=rev Log: This patch resolves the issue raised in https://issues.apache.org/jira/browse/ODE-371.
Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.bpel ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.wsdl ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/deploy.xml ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/test1.properties ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionModifier.java Modified: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/bom/Copy.java ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/AssignGenerator.java ode/trunk/bpel-schemas/src/main/resources/ws-bpel_abstract_common_base.xsd ode/trunk/bpel-schemas/src/main/resources/ws-bpel_executable.xsd ode/trunk/bpel-test/src/test/java/org/apache/ode/test/DataHandling20Test.java ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/ASSIGN.java ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OAssign.java ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OLValueExpression.java ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/JaxpFunctionResolver.java ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionRuntime.java ode/trunk/utils/src/main/java/org/apache/ode/utils/DOMUtils.java Modified: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/bom/Copy.java URL: http://svn.apache.org/viewvc/ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/bom/Copy.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/bom/Copy.java (original) +++ ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/bom/Copy.java Wed Oct 29 17:29:15 2008 @@ -61,4 +61,8 @@ public boolean isIgnoreUninitializedFromVariable() { return getAttribute("ignoreUninitializedFromVariable", "no").equals("yes"); } + + public boolean isInsertMissingToData() { + return getAttribute("insertMissingToData", "no").equals("yes"); + } } Modified: ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/AssignGenerator.java URL: http://svn.apache.org/viewvc/ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/AssignGenerator.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/AssignGenerator.java (original) +++ ode/trunk/bpel-compiler/src/main/java/org/apache/ode/bpel/compiler/v2/AssignGenerator.java Wed Oct 29 17:29:15 2008 @@ -73,6 +73,7 @@ OAssign.Copy ocopy = new OAssign.Copy(_context.getOProcess()); ocopy.keepSrcElementName = scopy.isKeepSrcElement(); ocopy.ignoreMissingFromData = scopy.isIgnoreMissingFromData(); + ocopy.insertMissingToData = scopy.isInsertMissingToData(); ocopy.ignoreUninitializedFromVariable = scopy.isIgnoreUninitializedFromVariable(); ocopy.debugInfo = new DebugInfo(_context.getSourceLocation(), scopy.getLineNo(), source.getExtensibilityElements()); Modified: ode/trunk/bpel-schemas/src/main/resources/ws-bpel_abstract_common_base.xsd URL: http://svn.apache.org/viewvc/ode/trunk/bpel-schemas/src/main/resources/ws-bpel_abstract_common_base.xsd?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/bpel-schemas/src/main/resources/ws-bpel_abstract_common_base.xsd (original) +++ ode/trunk/bpel-schemas/src/main/resources/ws-bpel_abstract_common_base.xsd Wed Oct 29 17:29:15 2008 @@ -591,7 +591,8 @@ <xsd:attribute name="keepSrcElementName" type="tBoolean" use="optional" default="no"/> <xsd:attribute name="ignoreMissingFromData" type="tBoolean" use="optional" default="no"/> <xsd:attribute name="ignoreUninitializedFromVariable" type="tBoolean" use="optional" default="no"/> - </xsd:extension> + <xsd:attribute name="insertMissingToData" type="tBoolean" use="optional" default="no"/> + </xsd:extension> </xsd:complexContent> </xsd:complexType> Modified: ode/trunk/bpel-schemas/src/main/resources/ws-bpel_executable.xsd URL: http://svn.apache.org/viewvc/ode/trunk/bpel-schemas/src/main/resources/ws-bpel_executable.xsd?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/bpel-schemas/src/main/resources/ws-bpel_executable.xsd (original) +++ ode/trunk/bpel-schemas/src/main/resources/ws-bpel_executable.xsd Wed Oct 29 17:29:15 2008 @@ -660,6 +660,7 @@ <xsd:attribute name="keepSrcElementName" type="tBoolean" use="optional" default="no"/> <xsd:attribute name="ignoreMissingFromData" type="tBoolean" use="optional" default="no"/> <xsd:attribute name="ignoreUninitializedFromVariable" type="tBoolean" use="optional" default="no"/> + <xsd:attribute name="insertMissingToData" type="tBoolean" use="optional" default="no"/> </xsd:extension> </xsd:complexContent> </xsd:complexType> Modified: ode/trunk/bpel-test/src/test/java/org/apache/ode/test/DataHandling20Test.java URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/java/org/apache/ode/test/DataHandling20Test.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/bpel-test/src/test/java/org/apache/ode/test/DataHandling20Test.java (original) +++ ode/trunk/bpel-test/src/test/java/org/apache/ode/test/DataHandling20Test.java Wed Oct 29 17:29:15 2008 @@ -76,4 +76,5 @@ @Test public void testAssignMissingData() throws Throwable { go("/bpel/2.0/TestAssignMissingData"); } + } Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.bpel URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.bpel?rev=709057&view=auto ============================================================================== --- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.bpel (added) +++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.bpel Wed Oct 29 17:29:15 2008 @@ -0,0 +1,105 @@ +<!-- + ~ 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 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" + xsi:schemaLocation="http://docs.oasis-open.org/wsbpel/2.0/process/executable ../../../../../../../bpel-schemas/src/main/resources/wsbpel_executable.xsd" + xmlns:tns="http://ode/bpel/unit-test/TestInsertMissingData" + xmlns:prb="http://ode/bpel/unit-test/ProbeService.wsdl" + xmlns:types="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types" + xmlns:foo="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types" + xmlns:xsd="http://www.w3.org/2001/XMLSchema" + xmlns:wns="http://ode/bpel/unit-test/TestInsertMissingData.wsdl" + xmlns:ode="http://www.apache.org/ode/type/extension" + xmlns:fn="http://www.w3.org/2005/xpath-functions" + xmlns="http://docs.oasis-open.org/wsbpel/2.0/process/executable" + targetNamespace="http://ode/bpel/unit-test/TestInsertMissingData" + name="TestInsertMissingData" + queryLanguage="urn:oasis:names:tc:wsbpel:2.0:sublang:xpath2.0" + expressionLanguage="urn:oasis:names:tc:wsbpel:2.0:sublang:xpath2.0" + suppressJoinFailure="yes"> + + <import location="TestInsertMissingData.wsdl" + namespace="http://ode/bpel/unit-test/TestInsertMissingData.wsdl" + importType="http://schemas.xmlsoap.org/wsdl/" /> + <import location="../ProbeService/probeService.wsdl" + namespace="http://ode/bpel/unit-test/ProbeService.wsdl" + importType="http://schemas.xmlsoap.org/wsdl/"/> + + <partnerLinks> + <partnerLink name="request" partnerLinkType="wns:TestInsertMissingDataRequest" myRole="TestInsertMissingDataService"/> + </partnerLinks> + <variables> + <variable name="request" messageType="wns:requestMessage"/> + <variable name="testType" element="types:aTestMessage"/> + <variable name="reply" messageType="wns:replyMessage"/> + </variables> + <sequence> + <receive name="receive1" partnerLink="request" portType="wns:TestInsertMissingDataPT" operation="request" variable="request" createInstance="yes"/> + + <!-- test cases for ignore missing to data --> + <assign name="assign1"> + <copy insertMissingToData="yes"> + <from>$request.requestMessageData/typeIndicators/types:indicatorTwo</from> + <to>$testType/@xsi:nil</to> + </copy> + <copy insertMissingToData="yes"> + <from>$request.requestMessageData/typeIndicators/types:indicatorTwo</from> + <to>$testType/typeIndicators/types:indicatorTwo</to> + </copy> + <copy> + <from>ode:delete($testType/typeIndicators)</from> + <to>$testType</to> + </copy> + <copy insertMissingToData="yes"> + <from>$request.requestMessageData/typeIndicators/types:indicatorTwo</from> + <to>$testType/child::typeIndicators/types:indicatorTwo</to> + </copy> + <copy> + <from>ode:delete($testType/typeIndicators)</from> + <to>$testType</to> + </copy> + <copy insertMissingToData="yes"> + <from>$request.requestMessageData/typeIndicators/types:indicatorTwo</from> + <to>$testType/child::typeIndicators/child::types:indicatorTwo</to> + </copy> + <copy> + <from>ode:delete($testType/typeIndicators)</from> + <to>$testType</to> + </copy> + <copy insertMissingToData="yes"> + <from>$request.requestMessageData/typeIndicators/types:indicatorTwo</from> + <to variable="testType">/typeIndicators/child::types:indicatorTwo</to> + </copy> + </assign> + + <assign name="assign3"> + <copy> + <from>$request.requestMessageData/requestID</from> + <to variable="reply" part="replyID"/> + </copy> + <copy> + <from> + <literal><![CDATA[pass]]></literal> + </from> + <to>$reply.replyText</to> + </copy> + </assign> + + <reply name="reply" partnerLink="request" portType="wns:TestInsertMissingDataPT" operation="request" variable="reply"/> + </sequence> + </process> Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.wsdl URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.wsdl?rev=709057&view=auto ============================================================================== --- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.wsdl (added) +++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/TestInsertMissingData.wsdl Wed Oct 29 17:29:15 2008 @@ -0,0 +1,102 @@ +<!-- + ~ 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/TestInsertMissingData.wsdl" + xmlns:tns="http://ode/bpel/unit-test/TestInsertMissingData.wsdl" + xmlns:typens="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types" + xmlns="http://ode/bpel/unit-test/TestInsertMissingData.wsdl" + xmlns:prb="http://ode/bpel/unit-test/ProbeService.wsdl" + xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" + xmlns:plnk="http://docs.oasis-open.org/wsbpel/2.0/plnktype" + xmlns:xsd="http://www.w3.org/2001/XMLSchema" + xmlns:vprop="http://docs.oasis-open.org/wsbpel/2.0/varprop"> + + <wsdl:types> + + <xsd:schema + targetNamespace="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types" + xmlns="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types" + xmlns:xsd="http://www.w3.org/2001/XMLSchema"> + + <xsd:element name="aTestMessage" type="testMessage"></xsd:element> + <xsd:element name="indicator" type="xsd:string" abstract="true"/> + <xsd:element name="indicatorOne" type="xsd:string" substitutionGroup="indicator"/> + <xsd:element name="indicatorTwo" type="xsd:string" substitutionGroup="indicator"/> + + <xsd:complexType name="typeIndicator"> + <xsd:sequence> + <xsd:element ref="indicatorOne"/> + <xsd:element ref="indicatorTwo"/> + </xsd:sequence> + </xsd:complexType> + <xsd:complexType name="testMessage"> + <xsd:sequence> + <xsd:element name="requestID" type="xsd:string"/> + <xsd:element name="requestText" type="xsd:string"/> + <xsd:element name="typeIndicators" type="typeIndicator"/> + </xsd:sequence> + </xsd:complexType> + + </xsd:schema> + </wsdl:types> + + <wsdl:message name="requestMessage"> + <wsdl:part name="requestMessageData" element="typens:aTestMessage"/> + </wsdl:message> + + <wsdl:message name="replyMessage"> + <wsdl:part name="replyID" type="xsd:string"/> + <wsdl:part name="replyText" type="xsd:string"/> + </wsdl:message> + + <wsdl:portType name="TestInsertMissingDataPT"> + <wsdl:operation name="request"> + <wsdl:input message="requestMessage"/> + <wsdl:output message="replyMessage"/> + </wsdl:operation> + </wsdl:portType> + + <wsdl:binding name="TestInsertMissingDataBinding" type="tns:TestInsertMissingDataPT"> + <wsdl:operation name="request"> + </wsdl:operation> + </wsdl:binding> + <wsdl:service name="TestInsertMissingDataService"> + <wsdl:port name="TestInsertMissingDataPort" binding="tns:TestInsertMissingDataBinding"> + </wsdl:port> + </wsdl:service> + + <plnk:partnerLinkType name="TestInsertMissingDataRequest"> + <plnk:role name="TestInsertMissingDataService" portType="TestInsertMissingDataPT"/> + </plnk:partnerLinkType> + + <plnk:partnerLinkType name="probeRequest"> + <plnk:role name="probeService" portType="prb:probeMessagePT"/> + </plnk:partnerLinkType> + + <vprop:property name="testProbeID" type="xsd:string"/> + <vprop:propertyAlias propertyName="tns:testProbeID" messageType="tns:requestMessage"/> + + <vprop:property name="testPath" type="xsd:string"/> + <vprop:propertyAlias propertyName="tns:testPath" messageType="tns:requestMessage" part="requestMessageData"> + <vprop:query queryLanguage="urn:oasis:names:tc:wsbpel:2.0:sublang:xpath2.0"> + typeIndicators/typens:indicatorTwo + </vprop:query> + </vprop:propertyAlias> + +</wsdl:definitions> Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/deploy.xml URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/deploy.xml?rev=709057&view=auto ============================================================================== --- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/deploy.xml (added) +++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/deploy.xml Wed Oct 29 17:29:15 2008 @@ -0,0 +1,31 @@ +<!-- + ~ 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/TestInsertMissingData" + xmlns:wns="http://ode/bpel/unit-test/TestInsertMissingData.wsdl"> + + + <process name="pns:TestInsertMissingData"> + <active>true</active> + <provide partnerLink="request"> + <service name="wns:TestInsertMissingDataService" port="wns:TestInsertMissingDataPort"/> + </provide> + </process> +</deploy> Added: ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/test1.properties URL: http://svn.apache.org/viewvc/ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/test1.properties?rev=709057&view=auto ============================================================================== --- ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/test1.properties (added) +++ ode/trunk/bpel-test/src/test/resources/bpel/2.0/TestInsertMissingData/test1.properties Wed Oct 29 17:29:15 2008 @@ -0,0 +1,22 @@ +# +# 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/TestInsertMissingData.wsdl +service=TestInsertMissingDataService +operation=request +request1=<message><requestMessageData><ens:aTestMessage xmlns:ens="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types"><requestID>Start InsertMissingData</requestID><requestText>Event InsertMissingData</requestText><typeIndicators xmlns:foo="http://ode/bpel/unit-test/TestInsertMissingData.wsdl.types"><foo:indicatorOne>fail</foo:indicatorOne><foo:indicatorTwo>fail</foo:indicatorTwo></typeIndicators></ens:aTestMessage></requestMessageData></message> +response1=.*<replyID>Start InsertMissingData</replyID><replyText>pass</replyText>.* Modified: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/ASSIGN.java URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/ASSIGN.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/ASSIGN.java (original) +++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/ASSIGN.java Wed Oct 29 17:29:15 2008 @@ -380,6 +380,7 @@ new EvaluationContextProxy(propRef.getVariable(), lvalue)); } else if (ocopy.to instanceof OAssign.LValueExpression) { OAssign.LValueExpression lexpr = (OAssign.LValueExpression) ocopy.to; + lexpr.setInsertMissingToData(ocopy.insertMissingToData); lvaluePtr = evalQuery(lvalue, null, lexpr.expression, new EvaluationContextProxy(lexpr.getVariable(), lvalue)); if (__log.isDebugEnabled()) Modified: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OAssign.java URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OAssign.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OAssign.java (original) +++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OAssign.java Wed Oct 29 17:29:15 2008 @@ -66,6 +66,7 @@ public boolean keepSrcElementName; public boolean ignoreMissingFromData; public boolean ignoreUninitializedFromVariable; + public boolean insertMissingToData; public Copy(OProcess owner) { super(owner); @@ -169,6 +170,13 @@ return expression.getVariable(); } + public boolean isInsertMissingToData() { + return expression.insertMissingData; + } + + public void setInsertMissingToData(boolean insertMissingToData) { + expression.insertMissingData = insertMissingToData; + } } public static class Expression extends OBase implements RValue { private static final long serialVersionUID = 1L; Modified: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OLValueExpression.java URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OLValueExpression.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OLValueExpression.java (original) +++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/OLValueExpression.java Wed Oct 29 17:29:15 2008 @@ -23,6 +23,14 @@ private static final long serialVersionUID = 1L; /** + * Indicates whether the expression, if it is a simple path, must + * be created if missing By a simple path, we mean a path expression whose + * steps are fully-qualified names separated by slashes. In case any of + * the steps in the simple path is non-existent, then we must create it. + */ + public boolean insertMissingData; + + /** * @param owner */ public OLValueExpression(OProcess owner) { Modified: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/JaxpFunctionResolver.java URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/JaxpFunctionResolver.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/JaxpFunctionResolver.java (original) +++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/JaxpFunctionResolver.java Wed Oct 29 17:29:15 2008 @@ -31,6 +31,7 @@ import java.util.Map; import javax.xml.namespace.QName; +import javax.xml.transform.TransformerException; import javax.xml.transform.dom.DOMSource; import javax.xml.transform.stream.StreamResult; import javax.xml.xpath.XPathFunction; @@ -38,6 +39,7 @@ import javax.xml.xpath.XPathFunctionResolver; import net.sf.saxon.dom.NodeWrapper; +import net.sf.saxon.value.IntegerValue; import net.sf.saxon.value.QNameValue; import org.apache.commons.httpclient.URIException; @@ -63,8 +65,6 @@ import org.w3c.dom.Text; import org.xml.sax.SAXException; -import com.sun.jdi.IntegerValue; - /** * @author mriou <mriou at apache dot org> */ @@ -925,6 +925,14 @@ Element deleteElmt = (Element) children.item(positions[target]); clonedElmt.removeChild(deleteElmt); } + // Saxon doesn't like clones with no children, so I'll oblige + if (clonedElmt.getChildNodes().getLength() == 0) { + try { + clonedElmt.appendChild(DOMUtils.toDOMDocument(parentElmt).createTextNode("")); + } catch (TransformerException te) { + throw new XPathFunctionException(te); + } + } return clonedElmt; } } @@ -1142,7 +1150,7 @@ return Integer.parseInt(extractString(arg)); } catch (ClassCastException cce) { if (arg instanceof IntegerValue) { - return ((IntegerValue) arg).intValue(); + return (int) ((IntegerValue) arg).getDoubleValue(); } throw new IllegalArgumentException("Parameter MUST point to an integer, single element or text node.", cce); } catch (NumberFormatException nfe) { Added: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionModifier.java URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionModifier.java?rev=709057&view=auto ============================================================================== --- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionModifier.java (added) +++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionModifier.java Wed Oct 29 17:29:15 2008 @@ -0,0 +1,198 @@ +package org.apache.ode.bpel.rtrep.v2.xpath20; + +import java.util.Iterator; + +import javax.xml.namespace.QName; +import javax.xml.transform.TransformerException; +import javax.xml.xpath.XPathExpression; + +import net.sf.saxon.expr.AxisExpression; +import net.sf.saxon.expr.Expression; +import net.sf.saxon.expr.ItemChecker; +import net.sf.saxon.expr.PathExpression; +import net.sf.saxon.expr.VariableReference; +import net.sf.saxon.om.Axis; +import net.sf.saxon.om.NamePool; +import net.sf.saxon.pattern.NameTest; +import net.sf.saxon.pattern.NodeKindTest; +import net.sf.saxon.pattern.NodeTest; +import net.sf.saxon.xpath.XPathExpressionImpl; + +import org.apache.ode.utils.DOMUtils; +import org.apache.ode.utils.NSContext; +import org.w3c.dom.Attr; +import org.w3c.dom.DOMException; +import org.w3c.dom.Document; +import org.w3c.dom.Element; +import org.w3c.dom.Node; +import org.w3c.dom.NodeList; + + +/** + * A helper utility that modifies XPath Expression in-place. This is meant + * to be reusable across the XPath and XQuery runtimes. + */ +public class XPath20ExpressionModifier { + private NSContext contextUris; + private NamePool namePool; + + /** + * Creates a new XPath20ExpressionModifier object. + * + * @param contextUris + * @param namePool + */ + public XPath20ExpressionModifier(NSContext contextUris, NamePool namePool) { + this.contextUris = contextUris; + this.namePool = namePool; + } + + /** + * Insert nodes into the specified XPath expression wherever + * required To be precise, an node is added to its parent if: + * a) the node is an element... + * b) that corresponds to an step... + * c) that has a child axis... + * d) whose parent had no children with its name... + * e) and all preceding steps are element name tests. + * + * @param xpathExpr + * @param namePool + * + * @throws DOMException + * @throws TransformerException + */ + @SuppressWarnings("unchecked") + public void insertMissingData(XPathExpression xpathExpr, Node contextNode) + throws DOMException, TransformerException { + if ((contextNode == null) || !(contextNode instanceof Element) || + !(xpathExpr instanceof XPathExpressionImpl)) { + return; + } + + Expression expression = ((XPathExpressionImpl) xpathExpr).getInternalExpression(); + Iterator<Expression> subExpressions = (Iterator<Expression>) expression.iterateSubExpressions(); + + if (!subExpressions.hasNext()) { + return; + } + + Expression subExpr = (Expression) subExpressions.next(); + + if (!(subExpr instanceof PathExpression)) { + return; + } + + Document document = DOMUtils.toDOMDocument(contextNode); + PathExpression pathExpr = (PathExpression) subExpr; + Expression step = pathExpr.getFirstStep(); + + while (step != null) { + if (step instanceof AxisExpression) { + AxisExpression axisExpr = (AxisExpression) step; + + NodeTest nodeTest = axisExpr.getNodeTest(); + + if (!(nodeTest instanceof NameTest)) { + break; + } + + NameTest nameTest = (NameTest) nodeTest; + + QName childName = getQualifiedName(nameTest.getFingerprint(), + namePool, contextUris); + + if (Axis.CHILD == axisExpr.getAxis()) { + if (NodeKindTest.ELEMENT.getNodeKindMask() != nameTest.getNodeKindMask()) { + break; + } + + NodeList children = ((Element) contextNode).getElementsByTagNameNS(childName.getNamespaceURI(), + childName.getLocalPart()); + if ((children == null) || (children.getLength() == 0)) { + Node child = document.createElementNS(childName.getNamespaceURI(), + DOMUtils.getQualifiedName(childName)); + contextNode.appendChild(child); + contextNode = child; + } else if (children.getLength() == 1) { + contextNode = children.item(0); + } else { + break; + } + } else if (Axis.ATTRIBUTE == axisExpr.getAxis()) { + if (NodeKindTest.ATTRIBUTE.getNodeKindMask() != nameTest.getNodeKindMask()) { + break; + } + + Attr attribute = ((Element) contextNode).getAttributeNodeNS(childName.getNamespaceURI(), childName.getLocalPart()); + if (attribute == null) { + attribute = document.createAttributeNS(childName.getNamespaceURI(), childName.getLocalPart()); + ((Element) contextNode).setAttributeNode(attribute); + contextNode = attribute; + } else { + break; + } + + } else { + break; + } + + + } else if (step instanceof ItemChecker) { + ItemChecker itemChecker = (ItemChecker) step; + Expression baseExpr = itemChecker.getBaseExpression(); + + if (!(baseExpr instanceof VariableReference)) { + break; + } + } else { + break; + } + + if (pathExpr != null) { + Expression remainingSteps = pathExpr.getRemainingSteps(); + + if (remainingSteps instanceof PathExpression) { + pathExpr = (PathExpression) remainingSteps; + step = pathExpr.getFirstStep(); + } else if (remainingSteps instanceof AxisExpression) { + pathExpr = null; + step = (AxisExpression) remainingSteps; + } + } else { + break; + } + } + } + + /** + * Create the QName by running the given finger print against the + * given context + * + * @param fingerprint + * @param namePool + * @param nsContext + * + * @return The QName corresponding to the finger print + */ + private QName getQualifiedName(int fingerprint, NamePool namePool, + NSContext nsContext) { + String localName = namePool.getLocalName(fingerprint); + String prefix = namePool.getPrefix(fingerprint); + String uri = namePool.getURI(fingerprint); + + // Unfortunately, NSContext.getPrefix(String URI) doesn't always work + // So, we need to find the prefix for the URI the hard way + if ((prefix == null) || "".equals(prefix)) { + for (String nsPrefix : nsContext.getPrefixes()) { + String nsUri = nsContext.getNamespaceURI(nsPrefix); + + if (nsUri.equals(uri)) { + prefix = nsPrefix; + } + } + } + + return new QName(uri, localName, prefix); + } +} Modified: ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionRuntime.java URL: http://svn.apache.org/viewvc/ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionRuntime.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionRuntime.java (original) +++ ode/trunk/runtimes/src/main/java/org/apache/ode/bpel/rtrep/v2/xpath20/XPath20ExpressionRuntime.java Wed Oct 29 17:29:15 2008 @@ -21,6 +21,8 @@ import net.sf.saxon.trans.DynamicError; import net.sf.saxon.value.DurationValue; import net.sf.saxon.xpath.XPathEvaluator; +import net.sf.saxon.xpath.XPathFactoryImpl; + import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.ode.bpel.common.FaultException; @@ -176,6 +178,12 @@ xpe.setNamespaceContext(oxpath20.namespaceCtx); // Just checking that the expression is valid XPathExpression expr = xpe.compile(((OXPath10Expression)cexp).xpath); + Node contextNode = ctx.getRootNode() == null ? DOMUtils.newDocument() : ctx.getRootNode(); + // Create step nodes in XPath in case it is incompletely instantiated + if (oxpath20.insertMissingData) { + XPath20ExpressionModifier modifier = new XPath20ExpressionModifier(oxpath20.namespaceCtx, xpe.getStaticContext().getNamePool()); + modifier.insertMissingData(expr, ctx.getRootNode()); + } Object evalResult = expr.evaluate(ctx.getRootNode() == null ? DOMUtils.newDocument() : ctx.getRootNode(), type); if (evalResult != null && __log.isDebugEnabled()) { Modified: ode/trunk/utils/src/main/java/org/apache/ode/utils/DOMUtils.java URL: http://svn.apache.org/viewvc/ode/trunk/utils/src/main/java/org/apache/ode/utils/DOMUtils.java?rev=709057&r1=709056&r2=709057&view=diff ============================================================================== --- ode/trunk/utils/src/main/java/org/apache/ode/utils/DOMUtils.java (original) +++ ode/trunk/utils/src/main/java/org/apache/ode/utils/DOMUtils.java Wed Oct 29 17:29:15 2008 @@ -1044,4 +1044,12 @@ return ret; } + public static Document getDocument(Node contextNode) { + return (contextNode == null) ? DOMUtils.newDocument() : contextNode.getOwnerDocument(); + } + + public static String getQualifiedName(QName qName) { + String prefix = qName.getPrefix(), localPart = qName.getLocalPart(); + return (prefix == null || "".equals(prefix)) ? localPart : (prefix + ":" + localPart); + } } \ No newline at end of file