INT-3859: Fix NPE in the ImapMailReceiver

JIRA: https://jira.spring.io/browse/INT-3859

The Java Mail `MessageCache.getMessageBySeqnum()` has the code:
````java
if (msgnum < 0) {		// XXX - < 1 ?
    if (logger.isLoggable(Level.FINE))
	logger.fine("no message seqnum " + seqnum);
        return null;
}
````
about which the `IMAPFolder.search` doesn't care:
````java
matchMsgs[i] = getMessageBySeqNumber(matches[i]);
````
therefore pops `null`s to the top for the `ImapMailReceiver`

* Fix `NPE` filtering the `Message[]` from `null` items

Note: its enough difficult to reproduce it because it isn't clear how we can end up with:
````java
if (seqnums[msgnum-1] > seqnum)
		break;		// message doesn't exist
````

in the `MessageCache`.
That's why there is no test-cases on the matter.

**Cherry-pick to 4.1.x**

Polishing

- Only create a new array if needed.
- Add a test case
This commit is contained in:
Artem Bilan
2015-10-21 21:47:06 -04:00
committed by Gary Russell
parent df85b87d5b
commit 9039a1b4c5
2 changed files with 74 additions and 2 deletions

View File

@@ -870,6 +870,53 @@ public class ImapMailReceiverTests {
assertTrue(exec.isShutdown());
}
@Test
public void testNullMessages() throws Exception {
Message message1 = mock(Message.class);
Message message2 = mock(Message.class);
final Message[] messages1 = new Message[] { null, null, message1 };
final Message[] messages2 = new Message[] { message2 };
final SearchTermStrategy searchTermStrategy = mock(SearchTermStrategy.class);
class TestReceiver extends ImapMailReceiver {
private boolean firstDone;
public TestReceiver() {
setSearchTermStrategy(searchTermStrategy);
}
@Override
protected Folder getFolder() {
Folder folder = mock(Folder.class);
when(folder.isOpen()).thenReturn(true);
try {
when(folder.getMessages())
.thenReturn(!this.firstDone ? messages1 : messages2);
}
catch (MessagingException e) {
}
return folder;
}
@Override
public Message[] receive() throws MessagingException {
Message[] messages = searchForNewMessages();
this.firstDone = true;
return messages;
}
};
ImapMailReceiver receiver = new TestReceiver();
Message[] received = receiver.receive();
assertEquals(1, received.length);
assertSame(message1, received[0]);
received = receiver.receive();
assertEquals(1, received.length);
assertSame(messages2, received);
assertSame(message2, received[0]);
}
private void setUpScheduler(ImapMailReceiver mailReceiver, ThreadPoolTaskScheduler taskScheduler) {
taskScheduler.setPoolSize(5);
taskScheduler.initialize();