Announcement Announcement Module
Collapse
No announcement yet.
Splitter Question: what is happening to the header values I have modified? Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Splitter Question: what is happening to the header values I have modified?

    I have a spring integration splitter with the following method signature:

    Code:
    @Splitter
    public List<Message<String[]>> splitCsvIntoSeperateMessages(Message<List<String[]>> message)
    The message payload is an ArrayList of String[]. The splitter reads each row in the List, Creates a new Message setting the payload to the data item in the List, adds a CorrelationId, SequenceNumber and SequenceSize to the header and finally returns an ArrayList of Messages.

    The problem is that when each individual message is sent to the next channel, the CorrelationId, SequenceNumber and SequenceSize are all overwritten with new values. Is that expected behavior or am I missing something?

    Code:
    @Splitter
    public List<Message<String[]>> splitCsvIntoSeperateMessages(Message<List<String[]>> message) {
    
     List<Message<String[]>> returnVal = new ArrayList<Message<String[]>>();
     String headerId = null;
     int sequenceSize = 0;
     int sequenceNumber = 0;
     for(String[] payload : message.getPayload()){
    
      if(payload[0].equals("HEAD")){
       headerId = UUID.randomUUID().toString();
       sequenceSize = Integer.parseInt(payload[payload.length-1]);
       sequenceNumber=0;
      }
      sequenceNumber++;
      Message<String[]> msg = 
       MessageBuilder
            .withPayload(payload)
         .setCorrelationId(headerId)
         .setSequenceSize(sequenceSize)
         .setSequenceNumber(sequenceNumber)
         .build();
    
      returnVal.add(msg);
     }
     return returnVal;
    }

  • norge
    replied
    Actually, I am using the service activator to split and send back the individual messages with the headers I want.

    Let me show you the modified splitCsvIntoSeperateMessages method:


    Code:
    	@ServiceActivator
    	public void splitCsvIntoSeperateMessages(Message<List<String[]>> message) throws IOException {
    
        	MessageChannel replyChannel =(MessageChannel)message.getHeaders().getReplyChannel();
        	String headerId = null;
        	int sequenceSize = 0;
        	int sequenceNumber = 0;
        	for(String[] payload : message.getPayload()){
    
        		if(payload[0].equals("HEAD")){
        			headerId = UUID.randomUUID().toString();
        			sequenceSize = Integer.parseInt(payload[payload.length-1])+1;
        			sequenceNumber=0;
        		}
        		sequenceNumber++;
        		Message<String[]> msg =
        			MessageBuilder
    		    		.withPayload(payload)
    		    		.copyHeaders(message.getHeaders())
    		    		.setSequenceNumber(sequenceNumber)
    					.setSequenceSize(sequenceSize)
    					.setCorrelationId(headerId)
    		    		.build();
        		replyChannel.send(msg);
        	}
    	}

    Leave a comment:


  • Mark Fisher
    replied
    Well, the Service Activator's replies are not going to be individual messages right?... would be the full list as a single payload.

    Leave a comment:


  • norge
    replied
    so can you take a look at my configuration file and tell me if I am "over using" service-activator? (this may not be a fair question without explaining my use case)



    Code:
    	<file:inbound-channel-adapter
    		auto-startup="true" auto-create-directory="true" directory="file:c:/temp/vaonce/load/" filename-pattern=".*\.txt"
    		channel="fileInputChannel">
    		<poller default="true">
    			<interval-trigger interval="10000" time-unit="MILLISECONDS" />
    		</poller>
    	</file:inbound-channel-adapter>
    
    	<chain input-channel="fileInputChannel">
    		<transformer ref="transformer" method="enrichHeaderWithFileInfo" />
    		<header-enricher>
    			<error-channel ref="errorChannel"/>
    			<header name="$discardChannel" ref="discardChannel"/>
    		</header-enricher>
    		<router channel-resolver="fileNameResolver">
    			<beans:bean class="org.springframework.integration.router.HeaderValueRouter">
    				<beans:constructor-arg value="$file_name" />
    			</beans:bean>
    		</router>
    	</chain>
    
    	<chain input-channel="enrollmentFile">
    		<service-activator ref="handler" method="loadVaOnceFile"/>
    		<service-activator ref="handler" method="verifyDetailRecordCounts"/>
    		<header-enricher>
    			<reply-channel ref="enrollmentFileSplit"/>
    		</header-enricher>
    		<service-activator ref="splitter" method="splitCsvIntoSeperateMessages"/>
    	</chain>
    
    	<chain input-channel="enrollmentFileSplit">
    		<aggregator/>
    		<transformer ref="transformer" method="transformEnrollmentToJpa" />
    		<splitter ref="splitter" method="splitEnrollmentJpaRecords"  />
    		<service-activator ref="handler" method="saveEnrollment" />
    	</chain>
    
    	<chain input-channel="amendmentFile">
    		<service-activator ref="handler" method="loadVaOnceFile"/>
    		<service-activator ref="handler" method="verifyDetailRecordCounts"/>
    		<header-enricher>
    			<reply-channel ref="enrollmentFileSplit"/>
    		</header-enricher>
    		<service-activator ref="splitter" method="splitCsvIntoSeperateMessages"/>
    	</chain>
    
    	<chain input-channel="amendmentFileSplit">
    		<aggregator/>
    		<transformer ref="transformer" method="transformEnrollmentToJpa" />
    		<splitter ref="splitter" method="splitEnrollmentJpaRecords"  />
    		<service-activator ref="handler" method="saveAmendment" />
    	</chain>

    Leave a comment:


  • Mark Fisher
    replied
    The main difference between Splitter and Service-Activator is that the Splitter will send multiple Messages (one for each "payload" in the list) while a Service-Activator would send the whole list as a single payload.

    Leave a comment:


  • norge
    replied
    That makes sense....the default implementation of a splitter...

    Can you tell me what happens if I use <serivce-activator> vs <spitter>.

    Is it important to annotate the methods with @Splitter or @ServiceActivation?

    John

    Leave a comment:


  • Mark Fisher
    replied
    Actually, the internal Splitter implementation does write those headers itself before sending the reply (and since List is an ordered collection, it can determine sequenceNumber/sequenceSize from that).

    Are you using values that would be different from those defaults? If so, can you explain the use-case?

    Thanks,
    Mark

    Leave a comment:

Working...
X