Chaps
Chaps

Reputation: 131

How to retrieve a whole mailbox with Spring Integration Mail

I'm trying to create a piece of code that would retrieve the whole content of an INBOX, using Spring Integration Mail. By default, an ImapIdleChannelAdapter will only fetch recent, unseen, unanswered etc... emails. So when I created my adapter, I tried to use a special strategy that would retrieve all emails without a given unique user flag (so basically, all the mails I haven't retrieve yet).

Here is my adapter:

Mail.imapIdleAdapter(imapUrl(user, pw, provider))
            .javaMailProperties { p: PropertiesBuilder -> p.put("mail.debug", "false") }
            .userFlag(uniqueFlag)
            .shouldMarkMessagesAsRead(false)
            .searchTermStrategy(GetAllMailsStrategy(uniqueFlag))
            .shouldReconnectAutomatically(true)
            .autoCloseFolder(false)

val integrationFlowBuilder = IntegrationFlows.from(imapIdleAdapter)
            .handle { message -> onNewEmail(user, uniqueFlag, message as org.springframework.messaging.Message<Message>) }

        val flow: IntegrationFlow = integrationFlowBuilder.get()

        flowContext.registration(flow).register()

And here is my strategy:

inner class GetAllMailsStrategy(private val uniqueFlag: String) : SearchTermStrategy {
        override fun generateSearchTerm(supportedFlags: Flags?, folder: Folder?): SearchTerm {
            val userFlag = Flags()
            userFlag.add(uniqueFlag)
            return NotTerm(FlagTerm(userFlag, true))
        }
    }

This piece of code does work, on small inboxes. As soon as I try to retrieve mails from an inbox with thousands of mails, at some point it just stops (sometime with FolderClosedException, even though I set autoCloseFolder to false, and sometime without any exception or log...), and then won't retrieve missing emails even if I start it all over with the same unique user flag. As if all the mails where flagged even though I never retrieved them. It does work on all new incoming emails though...

Any idea on what strategy I should use? Is there a way to get all the mails once, without flagging them? Should I use Spring mail only to get incoming new mail but something else for the task of retrieving all the mails once?

Thanks

Upvotes: 1

Views: 448

Answers (1)

Artem Bilan
Artem Bilan

Reputation: 121282

I never did it, but I think you are right: you should use an ImapIdleChannelAdapter for new (in IMAP terms RECENT) message, and some other ImapMailReceiver instance for initial call with your custom SearchTermStrategy.

The folder might be closed for some other reason, e.g. too many messages too long processed.

Upvotes: 0

Related Questions