Announcement Announcement Module
Collapse
No announcement yet.
How to continue the process if the xpath splitter expression evaluation fails Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • How to continue the process if the xpath splitter expression evaluation fails

    I have configured the cascade of splitters as shown below:
    HTML Code:
    <int:chain  input-channel="PQCaseInquiry-AWD-GROUP-MEMBER-PROVIDER-PQCALLISSLOOKUP-Execute"  output-channel="Aggregate-Cases-Channel" >
    <int-xml:xpath-splitter >
            <int-xml:xpath-expression expression="//folder"/>
            </int-xml:xpath-splitter>
            
            <!-- split the cases -->
           <int-xml:xpath-splitter >
            <int-xml:xpath-expression expression="//case"/>
            </int-xml:xpath-splitter>
              
            <int-jdbc:stored-proc-outbound-gateway
                           ............................        
    </int-jdbc:stored-proc-outbound-gateway>
          
              </int:chain>
    For any reason if the second xpath splitter fails in evaluating(//case) the expression i.e if no case is found, still I want to continue with another folder(//folder) split by the first xpath splitter. Can anybody help on this? Thanks in advance.

  • #2
    If you use an Excecutor or QueueChannel between the splitters (rather than having them in a chain), each split will be handed off to a new thread so they won't affect each other. A queue channel (with a poller on the second splitter) would maintain the the order.

    If the flow starts with JDBC and you want it all to run in a single transaction, you can't do that, though.

    In that case, you would have to add a gateway between the splitters, and put an error channel on the gateway to handle the error on each split.

    Code:
    <service activator ref="gateway" input-channel="fromFirstSplitter">
    <gateway service-interface="SomeInterfaceWithAMethodThatReturnsVoid" default-request-channel="toSecondSplitter" error-channel="errors"/>
    On the error channel you can log the error, or simply use nullChannel to ignore the error.

    Comment


    • #3
      Thanks Gary for your response. As per your suggestion, I have placed one splitter in one chain and the other one as a separate so that they won't exist in a single chain.
      I have added the queue channels and the poller as shown below:
      <int:chain input-channel="Build-Response-After-PQCLKUP-Response-Aggregation" output-channel="queueChannel" >
      <int:service-activator ref="msgHandler" method="buildMessageFromExtSysResponse" />

      <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Format-response-StageOne}" />
      <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Format-response-StageTwo}" />

      <int:header-enricher default-overwrite="true" should-skip-nulls="true" >
      <int:header name="${headerNames.originalPayload}" expression="payload" />
      </int:header-enricher>

      <!-- Split the Folders-->
      <int-xml:xpath-splitter >
      <int-xml:xpath-expression expression="//folder"/>
      </int-xml:xpath-splitter>

      <int:header-enricher default-overwrite="true" should-skip-nulls="true" >
      <int:header name="folderInfo" expression="payload" />
      </int:header-enricher>

      </int:chain>

      <int:channel id="queueChannel">
      <int:queue capacity="25"/>
      </int:channel>

      <int-xml:xpath-splitter input-channel="queueChannel" output-channel="pollerChannel" >
      <int-xml:xpath-expression expression="//case"/>
      </int-xml:xpath-splitter>


      <int:channel id="pollerChannel">
      <int:queue capacity="25"/>

      </int:channel>



      <int:chain input-channel="pollerChannel" output-channel="Aggregate-Cases-Channel" >
      <intoller fixed-delay="1" />
      <int:header-enricher default-overwrite="true" should-skip-nulls="true" >
      <int:header name="${headerNames.originalPayload}" expression="payload" />
      </int:header-enricher>

      <int-jdbc:stored-proc-outbound-gateway
      auto-startup="true"
      data-source="routingDataSource"
      stored-procedure-name="${PQCaseInquiry.storedProcedureName.pqcallis slookup}"
      skip-undeclared-results="true"
      ignore-column-meta-data="true"
      use-payload-as-parameter-source = "false"
      expect-single-result="true" >

      <int-jdbc:sql-parameter-definition name="P_CDATTIM" direction="IN" type="VARCHAR" />
      <int-jdbc:sql-parameter-definition name="P_CRECORDCD" direction="IN" type="VARCHAR" />
      <int-jdbc:sql-parameter-definition name="P_CCRNODE" direction="IN" type="VARCHAR" />

      <int-jdbcarameter name="P_CDATTIM" expression="#xpath(payload, '//CRDATTIM')" />
      <int-jdbcarameter name="P_CRECORDCD" expression="#xpath(payload, '//RECORDCD')" />
      <int-jdbcarameter name="P_CCRNODE" expression="#xpath(payload, '//CRNODE')" />

      <int-jdbc:returning-resultset name="rowMapper" row-mapper="com.dsths.cs.awd.utils.ResultSetRowMapper"/>
      </int-jdbc:stored-proc-outbound-gateway>

      <int:service-activator ref="msgHandler" method="buildMessageFromExtSysResponse" />
      <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Merge-All-Issues}" />

      </int:chain>
      But with the above code, I am getting the following exception:
      HTML Code:
      Caused by: java.lang.IllegalArgumentException: No poller has been defined for endpoint 'org.springframework.integration.config.ConsumerEndpointFactoryBean#29', and no default poller is available within the context.
          at org.springframework.util.Assert.notNull(Assert.java:112)
          at org.springframework.integration.config.ConsumerEndpointFactoryBean.initializeEndpoint(ConsumerEndpointFactoryBean.java:226)
      I am using the queue channel and the poller for the first time. Could you please help me out by correcting my code?

      Comment


      • #4
        <int-xml:xpath-splitter input-channel="queueChannel" output-channel="pollerChannel" >
        Should have <poller>, too

        Comment


        • #5
          Thanks Artem for the response.
          I have added the poller directly in Xpath splitter code as below:
          HTML Code:
          <int-xml:xpath-splitter input-channel="queueChannel"  output-channel="pollerChannel" >
                  <int-xml:xpath-expression expression="//case"/>
                  <int:poller  fixed-delay="1" />
                  </int-xml:xpath-splitter>
          Now, I am getting the following exception:
          HTML Code:
          Invalid content was found starting with element 'int:poller'. No child element is expected at this point.

          Comment


          • #6
            <poller> element should be before <xpath-expression>

            Comment


            • #7
              Thanks Artem for quick reply.
              The above suggestion worked fine for poller configuration. But, unfortunately still my core problem is not solved. If the xpath splitter fails in splitting the xml for any reason, it is going to error channel. In my case if the xpath splitter finds no //case, then it should look for one more //folder and then try to split the //case. but it is not happening. Do I need to do anything extra apart from the above queue channel and poller configuration?
              HTML Code:
              16:55:55,875 WARN  [org.springframework.integration.core.MessagingTemplate$TemporaryReplyChannel.send] Reply message being sent, but the receiving thread has already received a reply:[Payload=org.springframework.integration.MessagingException: failed to split Message payload][Headers={timestamp=1400498755875, id=8ece3229-7538-2f92-df9c-bcfaaa14da5d}]
              16:55:56,884 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
              java.lang.IllegalArgumentException: Adding text to an XML document must not be null
                  at org.dom4j.DocumentFactory.createText(DocumentFactory.java:136)
                  at org.dom4j.tree.AbstractElement.addText(AbstractElement.java:740)
                  at com.dsths.cs.awd.jobs.PQMessageHandler.handleError(PQMessageHandler.java:359)
                  at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                  at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
                  at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)

              Comment


              • #8
                You should configure "error-channel" (e.g. to "nullChannel") for the <poller> of the second <splitter>.

                Comment


                • #9
                  Artem,
                  Still getting the same issue though I have added the error-channel="nullChannel" for the poller of the second splitter . I have added the the following code:
                  Code:
                  <int-xml:xpath-splitter input-channel="queueChannel"  output-channel="pollerChannel" >
                          <int:poller  fixed-delay="1" error-channel="nullChannel" />
                          <int-xml:xpath-expression expression="//case"/>
                          </int-xml:xpath-splitter>
                  Exception details:
                  HTML Code:
                  java.lang.IllegalArgumentException: failed to split message with XPath expression: org.springframewo[email protected]148c47e
                      at org.springframework.integration.xml.splitter.XPathMessageSplitter.splitNode(XPathMessageSplitter.java:138)
                      at org.springframework.integration.xml.splitter.XPathMessageSplitter.splitDocument(XPathMessageSplitter.java:124)
                  Any ideas on what's wrong here?

                  Comment


                  • #10
                    Show more StackTrace, please. And would be better, if you switch on DEBUG for "org.springframework.integration" package, to determine the message flow around the issue

                    Comment


                    • #11
                      The following is the log after split failure:
                      HTML Code:
                      19:24:23,464 WARN  [org.springframework.integration.core.MessagingTemplate$TemporaryReplyChannel.send] Reply message being sent, but the receiving thread has already received a reply:[Payload=org.springframework.integration.MessagingException: failed to split Message payload][Headers={timestamp=1400507663464, id=df4a3e16-1b1e-3be9-b08f-1171dcc8f9b2}]
                      19:24:24,467 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:25,470 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:26,473 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:27,476 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:28,479 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:29,482 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:30,485 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:30,687 DEBUG [com.dsths.cs.awd.junits.PQCaseInquiryTest.testPQCaseInquiryAWD_MEMBER_search] ********** Exception occured.....
                      java.lang.IllegalArgumentException: Adding text to an XML document must not be null
                          at org.dom4j.DocumentFactory.createText(DocumentFactory.java:136)
                          at org.dom4j.tree.AbstractElement.addText(AbstractElement.java:740)
                          at com.dsths.cs.awd.jobs.PQMessageHandler.handleError(PQMessageHandler.java:359)
                          at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                          at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
                          at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
                          at java.lang.reflect.Method.invoke(Method.java:597)
                          at org.springframework.expression.spel.support.ReflectiveMethodExecutor.execute(ReflectiveMethodExecutor.java:69)
                          at org.springframework.expression.spel.ast.MethodReference$MethodValueRef.getValue(MethodReference.java:97)
                          at org.springframework.expression.spel.ast.CompoundExpression.getValueInternal(CompoundExpression.java:82)
                          at org.springframework.expression.spel.ast.SpelNodeImpl.getTypedValue(SpelNodeImpl.java:102)
                          at org.springframework.expression.spel.standard.SpelExpression.getValue(SpelExpression.java:103)
                          at org.springframework.integration.util.AbstractExpressionEvaluator.evaluateExpression(AbstractExpressionEvaluator.java:144)
                          at org.springframework.integration.util.MessagingMethodInvokerHelper.processInternal(MessagingMethodInvokerHelper.java:268)
                          at org.springframework.integration.util.MessagingMethodInvokerHelper.process(MessagingMethodInvokerHelper.java:142)
                          at org.springframework.integration.handler.MethodInvokingMessageProcessor.processMessage(MethodInvokingMessageProcessor.java:73)
                          at org.springframework.integration.handler.ServiceActivatingHandler.handleRequestMessage(ServiceActivatingHandler.java:67)
                          at org.springframework.integration.handler.AbstractReplyProducingMessageHandler.handleMessageInternal(AbstractReplyProducingMessageHandler.java:142)
                          at org.springframework.integration.handler.AbstractMessageHandler.handleMessage(AbstractMessageHandler.java:73)
                          at org.springframework.integration.handler.MessageHandlerChain.handleMessageInternal(MessageHandlerChain.java:131)
                          at org.springframework.integration.handler.AbstractMessageHandler.handleMessage(AbstractMessageHandler.java:73)
                          at org.springframework.integration.dispatcher.UnicastingDispatcher.doDispatch(UnicastingDispatcher.java:115)
                          at org.springframework.integration.dispatcher.UnicastingDispatcher.dispatch(UnicastingDispatcher.java:102)
                          at org.springframework.integration.channel.AbstractSubscribableChannel.doSend(AbstractSubscribableChannel.java:77)
                          at org.springframework.integration.channel.AbstractMessageChannel.send(AbstractMessageChannel.java:178)
                          at org.springframework.integration.channel.AbstractMessageChannel.send(AbstractMessageChannel.java:149)
                          at org.springframework.integration.core.MessagingTemplate.doSend(MessagingTemplate.java:330)
                          at org.springframework.integration.core.MessagingTemplate.doSendAndReceive(MessagingTemplate.java:361)
                          at org.springframework.integration.core.MessagingTemplate.sendAndReceive(MessagingTemplate.java:274)
                          at org.springframework.integration.gateway.MessagingGatewaySupport.doSendAndReceive(MessagingGatewaySupport.java:250)
                          at org.springframework.integration.gateway.MessagingGatewaySupport.sendAndReceiveMessage(MessagingGatewaySupport.java:208)
                          at org.springframework.integration.gateway.GatewayProxyFactoryBean.invokeGatewayMethod(GatewayProxyFactoryBean.java:323)
                          at org.springframework.integration.gateway.GatewayProxyFactoryBean.doInvoke(GatewayProxyFactoryBean.java:286)
                          at org.springframework.integration.gateway.GatewayProxyFactoryBean.invoke(GatewayProxyFactoryBean.java:277)
                          at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
                          at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:204)
                          at $Proxy54.pqCaseInquiryAWD(Unknown Source)
                          at com.dsths.cs.awd.junits.PQCaseInquiryTest.testPQCaseInquiryAWD_MEMBER_search(PQCaseInquiryTest.java:68)
                          at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                          at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
                          at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
                          at java.lang.reflect.Method.invoke(Method.java:597)
                          at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
                          at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
                          at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
                          at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
                          at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:74)
                          at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:83)
                          at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:72)
                          at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:231)
                          at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:88)
                          at org.junit.runners.ParentRunner$3.run(ParentRunner.java:193)
                          at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:52)
                          at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:191)
                          at org.junit.runners.ParentRunner.access$000(ParentRunner.java:42)
                          at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:184)
                          at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
                          at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:71)
                          at org.junit.runners.ParentRunner.run(ParentRunner.java:236)
                          at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:174)
                          at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:49)
                          at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
                          at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
                          at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
                          at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
                          at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
                      19:24:31,488 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'
                      19:24:32,490 DEBUG [org.springframework.integration.endpoint.PollingConsumer.doPoll] Received no Message during the poll, returning 'false'

                      Comment


                      • #12
                        I asked about the DEBUG for flow, but you show only the error.
                        And now show, please, and your flow definition - from <gateway> adn to the end of flow, where you build the reply for gateway

                        Comment


                        • #13
                          Artem,
                          I am sorry. I didn't get you. Do you want me to show the code or log after turning on DEBUG.

                          Comment


                          • #14
                            Show, code, please. I mean Integration flow definition

                            Comment


                            • #15

                              The following is the code where the first splitter is used in a chain and then second splitter as separate one. After that a queue and splitter with poller is used.
                              Code:
                              <!-- Get all the issues associated to the cases -->
                                  <int:chain  input-channel="Build-Response-After-PQCLKUP-Response-Aggregation"  output-channel="queueChannel" >
                                     <int:service-activator ref="msgHandler" method="buildMessageFromExtSysResponse" />
                                     
                                     <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Format-response-StageOne}"  />
                                     <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Format-response-StageTwo}"  />
                                     
                                      <int:header-enricher default-overwrite="true"  should-skip-nulls="true"  >
                                          <int:header name="${headerNames.originalPayload}" expression="payload" />
                                      </int:header-enricher>    
                                      
                                      <!-- Split the Folders-->
                                      <int-xml:xpath-splitter >
                                      <int-xml:xpath-expression expression="//folder"/>
                                      </int-xml:xpath-splitter>
                                      
                                       <int:header-enricher default-overwrite="true"  should-skip-nulls="true"  >
                                          <int:header name="folderInfo" expression="payload" />
                                      </int:header-enricher> 
                                      
                                      </int:chain>
                                      
                                      <int:channel id="queueChannel">
                                      <int:queue capacity="25"/>
                                      </int:channel>
                                  
                                      <int-xml:xpath-splitter input-channel="queueChannel"  output-channel="pollerChannel" >
                                      <int:poller  fixed-delay="1" error-channel="nullChannel" />
                                      <int-xml:xpath-expression expression="//case"/>
                                      </int-xml:xpath-splitter>
                                      
                                  <int:chain  input-channel="pollerChannel"  output-channel="Aggregate-Cases-Channel" >
                                      
                                       <int:header-enricher default-overwrite="true"  should-skip-nulls="true"  >
                                          <int:header name="${headerNames.originalPayload}" expression="payload" />
                                      </int:header-enricher> 
                                         
                                      <int-jdbc:stored-proc-outbound-gateway
                                                      auto-startup="true"
                                                      data-source="routingDataSource"
                                                      stored-procedure-name="${PQCaseInquiry.storedProcedureName.pqcallisslookup}"
                                                      skip-undeclared-results="true"
                                                      ignore-column-meta-data="true"  
                                                      use-payload-as-parameter-source = "false"
                                                      expect-single-result="true" >
                                                              
                                                              <int-jdbc:sql-parameter-definition name="P_CDATTIM" direction="IN" type="VARCHAR" />
                                                              <int-jdbc:sql-parameter-definition name="P_CRECORDCD" direction="IN" type="VARCHAR" />
                                                              <int-jdbc:sql-parameter-definition name="P_CCRNODE" direction="IN" type="VARCHAR" />
                                                              
                                                              <int-jdbc:parameter name="P_CDATTIM" expression="#xpath(payload, '//CRDATTIM')" />
                                                              <int-jdbc:parameter name="P_CRECORDCD" expression="#xpath(payload, '//RECORDCD')" />
                                                              <int-jdbc:parameter name="P_CCRNODE" expression="#xpath(payload, '//CRNODE')" />
                                                              
                                              <int-jdbc:returning-resultset name="rowMapper" row-mapper="com.dsths.cs.awd.utils.ResultSetRowMapper"/>
                                      </int-jdbc:stored-proc-outbound-gateway>
                                    
                                    <int:service-activator ref="msgHandler" method="buildMessageFromExtSysResponse" />
                                    <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Merge-All-Issues}"  />
                                  
                                  </int:chain>
                                  
                                    <int:aggregator input-channel="Aggregate-Cases-Channel" output-channel="Aggregate-Folders-Channel"
                                                      ref="xmlAggregator"  method="aggregateCases">         
                                      </int:aggregator>    
                                  
                                      <int:aggregator input-channel="Aggregate-Folders-Channel" output-channel="PQCaseInquiry-XsltTransformOutputChannel-Final-Transformation"
                                                      ref="xmlAggregator"  method="aggregateFolders">         
                                      </int:aggregator>    
                               
                                   <int:chain input-channel="PQCaseInquiry-XsltTransformOutputChannel-Final-Transformation">
                                     
                                      <int:service-activator ref="msgHandler" method="buildMessageFromExtSysResponseTest" />
                                  
                                      <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Format-Response-Stage-One}" />
                                  
                                      <int:service-activator ref="msgHandler"  method="enrichPayloadXml"  />
                                      
                                      <int-xml:xslt-transformer xsl-resource="${stylesheet.PQCaseInquiry-Format-Final-Response}" />
                                  </int:chain>

                              Please let me know if you need more info. Thanks in advance.

                              Comment

                              Working...
                              X