Announcement Announcement Module
Collapse
No announcement yet.
Transactional POP3 Mailbox access with Spring Integration Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • #16
    Thanks for the quick response!

    Hopefully this is the key part of the configuration you are after from integration.xml. I added the trans sync parts based on the recent reply to using RC2 instead of M4 but with or without the sync I get the same issue. Let me know if you need any more info.

    Code:
    <util:properties id="javaMailProperties">
        <prop key="mail.pop3.socketFactory.fallback">false</prop>
        <prop key="mail.debug">true</prop>
        <prop key="mail.pop3.rsetbeforequit">false</prop>
    </util:properties>
    
    <mail:inbound-channel-adapter id="mailAdapter"
    	store-uri="pop3://xxxxxx:[email protected]/inbox"
    	channel="receiveEmailChannel"
    	should-delete-messages="false"
    	auto-startup="true"
    	java-mail-properties="javaMailProperties">
    	<int:poller fixed-delay="20" max-messages-per-poll="20"
    		time-unit="SECONDS">
    		<int:transactional
    			synchronization-factory="syncFactory"
    			isolation="DEFAULT"
    			propagation="REQUIRED"
    			read-only="false"
    			timeout="10000"/>
    	</int:poller>
    </mail:inbound-channel-adapter>
    
    <int:channel id="receiveEmailChannel">
    	<int:interceptors>
    		<int:wire-tap channel="logger" />
    	</int:interceptors>
    </int:channel>
    
    <int:logging-channel-adapter id="logger"
    	level="DEBUG" />
    
    <int:service-activator input-channel="receiveEmailChannel"
    	ref="emailAdapterService" method="processEmail" />
    	
    <int:transaction-synchronization-factory id="syncFactory">
    	<int:after-commit expression="@syncProcessor.markMimeMessageAsDeleted(payload)"/>
    </int:transaction-synchronization-factory>
    
    <bean id="syncProcessor"
    	class="xx.xxx.xxxxxxxxxxx.xxxx.MailTransactionSynchronizationProcessor" />
    Last edited by MachineCode; Oct 24th, 2012, 10:21 AM. Reason: got rid of top-level indentation in code section

    Comment


    • #17
      Yeah, this is enough, give me few hours

      Comment


      • #18
        OK, thanks for looking at it. I finish work in 30 mins, at 4pm here in the UK so no rush to reply. Thanks again for responding quickly.

        Comment


        • #19
          I just remembered; The javax.mail.Message arrives with a handle to its Folder which is indeed closed which means you have to open it (if you need and in your case you do), do whatever you need and close it again.
          Here is my example:
          Code:
          public void postProcess(Message mailMessage) throws Exception{
          		mailMessage.getFolder().open(Folder.READ_WRITE);
          		mailMessage.setFlag(Flags.Flag.DELETED, true);
          		mailMessage.getFolder().close(true);
          		System.out.println("Deleted");
          }

          Comment


          • #20
            Also, look at the underlying JIRA for this one https://jira.springsource.org/browse/INT-1819 you can see a sample code there as well.
            Let us know how it goes

            Comment


            • #21
              I'm struggling to get this to work. Basically, the plan was to for the poller to get each POP3 email message, write its attachment to the database as a BLOB, send a JMS message and delete the email if all goes well - so all in a transaction like the M4 version did (with should-delete-messages set to true however). This code is done within the service-activator method called by the poller - but leaving the email deletion to the transaction (in the M4 version).

              Now with the RC2 version, I can get all but the deletion working as should-delete-messages was advised to be set to false, which I understand the reasons for. In the trans-sync method, I have copied the examples mentioned by setting the message's flag to DELETED but it has no effect. It still does not work if I move the deletion code to the end of the service-activator method and remove the trans-sync stuff.

              Here is what I had in the trans-sync method:
              Code:
              Folder folder = message.getFolder();
              if (!folder.isOpen()) {
              	folder.open(Folder.READ_WRITE);
              }
              
              message.setFlag(Flags.Flag.DELETED, true);
              folder.close(true);  // True means do expunge.
              This method is being called as I can see my println output appearing in the console. Crucially though, there is no "C: DELE 1" being output by the mail debugger anywhere.

              I'm still investigating but your input would be appreciated.

              Comment


              • #22
                Ok, let me look at this again, i'll let you know

                Comment


                • #23
                  Hi Oleg.

                  Have you been able to find out anything on this recently? I'll come back to the problem and look at it further but I'd run out of ideas before. If I do find anything, or indeed the reason for the problem then I'll let you know.

                  Comment


                  • #24
                    Hi, the JavaDocs for the Folder indicate once the folder is closed you can't use it again with the same message.

                    Message objects from a Folder are only valid while a Folder is open and should not be accessed after the Folder is closed, even if the Folder is subsequently reopened. Instead, new Message objects must be fetched from the Folder after the Folder is reopened.
                    I just got this to work (with IMAP) ...

                    Code:
                    		Folder folder = message.getFolder();
                    		folder.open(Folder.READ_WRITE);
                    		String messageId = message.getMessageID();
                    		Message[] messages = folder.getMessages();
                    		FetchProfile contentsProfile = new FetchProfile();
                    		contentsProfile.add(FetchProfile.Item.ENVELOPE);
                    		contentsProfile.add(FetchProfile.Item.CONTENT_INFO);
                    		contentsProfile.add(FetchProfile.Item.FLAGS);
                    		folder.fetch(messages, contentsProfile);
                    
                    		for (int i = 0; i < messages.length; i++) {
                    			if (((MimeMessage) messages[i]).getMessageID().equals(messageId)) {
                    				messages[i].setFlag(Flags.Flag.DELETED, true);
                    				break;
                    			}
                    		}
                    		folder.expunge();
                    		folder.close(true);
                    That said, I am working on a fix (INT-2803) because, right now, the folder in the message is the same instance as that in the MailReceiver so you could get collisions. So, until RC3 comes out, it would be safer to use

                    Code:
                    ...
                    
                    		URLName url = new URLName("INBOX");
                    		Folder folder = message.getFolder().getStore().getFolder(url);
                    ...
                    instead of message.getFolder();

                    Comment


                    • #25
                      FYI, I just tested with POP3 (Apache James) and it worked fine (had to remove the call to folder.expunge() because it's not supported by POP3)...

                      Code:
                      Subject: Test SI Delete
                      Content-Type: text/plain; charset=ISO-8859-1; format=flowed
                      Content-Transfer-Encoding: 7bit
                      
                      Test SI Delete
                      .
                      DEBUG POP3: got message size 662
                      C: DELE 1
                      S: +OK Message deleted
                      C: QUIT
                      S: +OK Apache James POP3 Server signing off.

                      Comment


                      • #26
                        OK, thanks for that. I'll look into it again in more detail to see what I might be doing wrong.

                        Comment


                        • #27
                          Thanks Gary,

                          Your code example has worked. I have put it in the syncProcessor before-commit (for now) and it does delete the message.

                          Thank you both very much for your help Gary and Oleg.

                          Comment

                          Working...
                          X