Announcement Announcement Module
Collapse
No announcement yet.
ItemProcessListener Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • ItemProcessListener

    I am using chained item processors (,i.e., CompositeItemProcessor ) and defined itemprocesslistener for each of the item processors but they are not being called.

    When I debug, it is looking for CompositeItemProcessListener. Any suggestions how to get it working ?

  • #2
    Did you register the listeners in your job configuration?

    Comment


    • #3
      I registered StepExecutionListener in the steps and JobExecutionListener in the job.

      For the custom itemreader/writers implemented the ItemReadListener and ItemWriteListener respectively which works absolutely fine.

      Btw I am using 2.0.0.RC1

      Comment


      • #4
        But you said that you are using ItemProcessListeners. Did you register those with the step?

        Comment


        • #5
          Nope. I did not register the ItemProcessListener with the job.

          So does that mean for every processor, if I need to set a listener, it should be registered in the job configuration ? ItemReadLsitener and ItemWriteListener would not be required to be registered ?

          Comment


          • #6
            The job configuration looks like this :
            Code:
            <job id="testJob">
            		<step id="step1" ref="testStep1" >
            			<end on="FAILED" exit-code="FAILED" />
            			<next on="*" to="step2"/>			
            		</step>
            		<step id="step2" ref="testStep2">
            		</step>
            		<listeners>
            			<listener ref="testobExecutionListener" />
            		</listeners>
            	</job>

            And the definition for the compositeItemProcessor is
            Code:
            <beans:bean id="testItemProcessor"
            		class="org.springframework.batch.item.support.CompositeItemProcessor">
            		<beans:property name="itemProcessors">
            			<beans:list>
            				<beans:bean
            					class="com.xxx.xxx.testItemProcessor1"	scope="step">
            					<beans:property name="schemaSourceURI" value="#{jobParameters[xsdFileURI]}" />
            				</beans:bean>
            				<beans:bean
            					class="com.xxx.xxx.testItemProcessor2"
            					scope="step">
            					<beans:property name="xslFileName"
            						value="#{jobParameters[xslfileName]}" />
            				</beans:bean>
            				<beans:bean
            					class="com.xxx.xxx.testItemProcessor3"
            					scope="step">
            					<beans:property name="vocabulary" value="${vocabulary}" />
            				</beans:bean>
            			</beans:list>
            		</beans:property>
            	</beans:bean>

            Comment


            • #7
              The issue is that only the top-level ItemReader/Processor/Writer will be auto-registered if they are listeners. If you use a composite ItemReader/Processor/Writer, and the delegate is the listener, then the step will have no way of knowing that it needs to register that class. Therefore, you must do it manually.

              Comment


              • #8
                I created a compositeItemProcesslistener and registered it with the step. It works. Thank you.

                Comment


                • #9
                  I am having issues with the ItemProcessListener, I have only one processor and want to set-up listener, this is what I did,

                  Code:
                  	<bean id="itemProcessListener"
                  		class="xxx.xxx.xxx.abc.ItemProcessListener" />
                  
                  
                  <batch:job id="sampleJob" job-repository="jobRepository"
                  		incrementer="jobParamIncrementer">
                  		<batch:step id="processingStep">
                  			<batch:tasklet transaction-manager="transactionManager" allow-start-if-complete="true"> 
                  				<batch:chunk reader="sampleReader" 
                  							 processor="samplerocessor"
                  							 writer="sampleWriter" commit-interval="100000">
                  				</batch:chunk>
                  				<batch:listeners>
                  					<batch:listener ref="itemReadListener"/>
                  					<batch:listener ref="itemProcessListener"/>
                  					<batch:listener ref="itemWriteListener"/>
                  			</batch:listeners>				
                  			</batch:tasklet>		
                  		</batch:step>
                  		<batch:listeners>
                  			<batch:listener ref="jobListener" />
                  			<batch:listener ref="itemFailureListener"/>
                  		</batch:listeners>
                  	</batch:job>
                  Code:
                  @Component
                  public class ItemProcessListener {
                      
                  
                      
                      /**
                       * This method confirm the database is available and if not, the job is immediately terminated since running the
                       * job without a database would be pointless.
                       * 
                       * @param item
                       */
                      @BeforeProcess
                      public void checkBeforeProcess(Object item) {
                      	log.report("checkOnProcessError prc obj:"+item.getClass());
                      	
                          log.report("\n@Before Process.... \n");
                      }
                      
                      
                      /**
                       * @param item
                       * @param result
                       */
                      @AfterProcess
                      public void checkAfterProcess(Object item, String result) {
                      	log.report("after prc obj:"+item.getClass());
                          log.report("\n@After Process.... \n"+result);
                      }
                      
                      
                  
                      
                      /**
                       * @param item
                       * @param exception
                       */
                      @OnProcessError
                      public void checkOnProcessError(Object item, Exception exception) {
                      	log.report("checkOnProcessError prc obj:"+item.getClass());
                      	
                          log.report("\n@Error during process.... \n"+exception.getMessage());
                      }    
                  }

                  Not sure why I am getting the following exception

                  Code:
                  Caused by: java.lang.IllegalArgumentException: Unable to invoke method: [public void xxx.xxx.abc.ItemProcessListener.checkAfterProcess(java.lang.Object,java.lang.String)] on object: [xxx.xxx.abc.ItemProcessListener@a3e75d] with arguments: [[xxx.xxx.domain.SampleData@95b3a2, xxx.xxx.domain.SampleData@95b3a2]]
                  	at org.springframework.batch.support.SimpleMethodInvoker.invokeMethod(SimpleMethodInvoker.java:108)
                  	at org.springframework.batch.core.listener.MethodInvokerMethodInterceptor.invoke(MethodInvokerMethodInterceptor.java:68)
                  	at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
                  	at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:202)
                  	at $Proxy30.afterProcess(Unknown Source)
                  	at org.springframework.batch.core.listener.CompositeItemProcessListener.afterProcess(CompositeItemProcessListener.java:59)
                  	at org.springframework.batch.core.listener.MulticasterBatchListener.afterProcess(MulticasterBatchListener.java:111)
                  	... 24 more
                  Caused by: java.lang.IllegalArgumentException: argument type mismatch
                  	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.batch.support.SimpleMethodInvoker.invokeMethod(SimpleMethodInvoker.java:105)
                  	... 30 more

                  And my processor is simple,

                  Code:
                  @Component
                  public class SampleProcessor implements ItemProcessor {
                      
                  
                  	public Object process(Object obj) throws Exception {
                  
                            return new xxx.xxx.domain.SampleData();
                          }
                  }
                  Please let me know how to resolve the above exception issue. Thanks.

                  Comment


                  • #10
                    the error message is pretty clear: type mismatch. The processor sends back a SampleData object, whereas the listener expects a String for the result object (checkOnProcessError method). The processor and the processor listener aren't compatible.

                    Comment

                    Working...
                    X