Skip to content

Commit

Permalink
#10: Code coverage for message related Runnable tasks
Browse files Browse the repository at this point in the history
  • Loading branch information
manusa committed Aug 31, 2019
1 parent d883e86 commit a1804cd
Show file tree
Hide file tree
Showing 5 changed files with 421 additions and 0 deletions.
7 changes: 7 additions & 0 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,9 @@ repositories {

dependencies {
compile('com.sun.mail:javax.mail:1.6.1')
testCompile('org.junit.jupiter:junit-jupiter:5.5.1')
testCompile('org.mockito:mockito-core:3.0.0')
testCompile('org.hamcrest:java-hamcrest:2.0.0.0')
}

group = 'com.marcnuri'
Expand All @@ -27,6 +30,10 @@ sourceCompatibility = 1.8

mainClassName = 'com.marcnuri.mnimapsync.MNIMAPSync'

test {
useJUnitPlatform()
}

task fatJar(type: Jar, group: BasePlugin.BUILD_GROUP) {
manifest {
attributes (
Expand Down
137 changes: 137 additions & 0 deletions src/test/java/com/marcnuri/mnimapsync/store/FolderCrawlerTest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,137 @@
/*
* FolderCrawlerTest.java
*
* Created on 2019-08-16, 7:00
*
* Copyright 2019 Marc Nuri San Felix
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
package com.marcnuri.mnimapsync.store;

import static org.hamcrest.CoreMatchers.equalTo;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.collection.IsCollectionWithSize.hasSize;
import static org.mockito.ArgumentMatchers.anyLong;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.doThrow;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;

import com.sun.mail.imap.IMAPMessage;
import com.sun.mail.imap.IMAPStore;
import javax.mail.Folder;
import javax.mail.Message;
import javax.mail.MessagingException;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.mockito.Mockito;

/**
* Created by Marc Nuri <[email protected]> on 2019-08-16.
*/
class FolderCrawlerTest {

private IMAPStore imapStore;
private Folder folder;
private StoreIndex storeIndex;

@BeforeEach
void setUp() throws Exception {
imapStore = Mockito.mock(IMAPStore.class);
folder = Mockito.mock(Folder.class);
doReturn(folder).when(imapStore).getFolder(anyString());
storeIndex = Mockito.spy(new StoreIndex());
}

@AfterEach
void tearDown() {
storeIndex = null;
folder = null;
imapStore = null;
}

@Test
void run_emptyFolder_shouldOnlyUpdateIndexes() throws Exception {
// Given
final FolderCrawler folderCrawler = new FolderCrawler(
imapStore, "FolderName", 0, 100, storeIndex);
doReturn(new Message[0]).when(folder).getMessages(eq(0), eq(100));
// When
folderCrawler.run();
// Then
verify(imapStore, times(1)).getFolder(eq("FolderName"));
verify(storeIndex, times(1)).updatedIndexedMessageCount(eq(0L));
verify(storeIndex, times(1)).updatedSkippedMessageCount(eq(0L));
}

@Test
void run_notEmptyFolderAndStoreWithExceptions_shouldReturn() throws Exception {
// Given
final FolderCrawler folderCrawler = new FolderCrawler(
imapStore, "FolderName", 0, 100, storeIndex);
final Message message = Mockito.mock(Message.class);
doReturn(new Message[]{message}).when(folder).getMessages(eq(0), eq(100));
doReturn(true).when(storeIndex).hasCrawlException();
// When
folderCrawler.run();
// Then
verify(imapStore, times(1)).getFolder(eq("FolderName"));
verify(storeIndex, times(0)).updatedIndexedMessageCount(anyLong());
verify(storeIndex, times(0)).updatedSkippedMessageCount(anyLong());
}

@Test
void run_notEmptyFolderAndRepeatedMessages_shouldUpdateIndexes() throws Exception {
// Given
final FolderCrawler folderCrawler = new FolderCrawler(
imapStore, "FolderName", 0, 100, storeIndex);
final IMAPMessage message = Mockito.mock(IMAPMessage.class);
doReturn(new String[]{"1337"}).when(message).getHeader("Message-Id");
final IMAPMessage repeatedMessage = Mockito.mock(IMAPMessage.class);
doReturn(new String[]{"313373"}).when(repeatedMessage).getHeader("Message-Id");
storeIndex.getFolderMessages("FolderName").add(new MessageId(repeatedMessage));
doReturn(new Message[]{message, repeatedMessage}).when(folder).getMessages(eq(0), eq(100));
// When
folderCrawler.run();
// Then
verify(imapStore, times(1)).getFolder(eq("FolderName"));
assertThat(storeIndex.getIndexedMessageCount(), equalTo(1L));
assertThat(storeIndex.getSkippedMessageCount(), equalTo(1L));
}

@Test
void run_notEmptyFolderAndThrowsMessageIdExceptionWithCause_shouldUpdateIndexesAndAddCrawlException() throws Exception {
// Given
final FolderCrawler folderCrawler = new FolderCrawler(
imapStore, "FolderName", 0, 100, storeIndex);
final IMAPMessage message = Mockito.mock(IMAPMessage.class);
doThrow(new MessagingException()).when(message).getHeader("Message-Id");
doReturn(new Message[]{message}).when(folder).getMessages(eq(0), eq(100));
// When
folderCrawler.run();
// Then
verify(imapStore, times(1)).getFolder(eq("FolderName"));
verify(storeIndex, times(1)).updatedIndexedMessageCount(eq(0L));
verify(storeIndex, times(1)).updatedSkippedMessageCount(eq(0L));
assertThat(storeIndex.getIndexedMessageCount(), equalTo(0L));
assertThat(storeIndex.getSkippedMessageCount(), equalTo(0L));
assertThat(storeIndex.hasCrawlException(), equalTo(true));
assertThat(storeIndex.getCrawlExceptions(), hasSize(1));
}

}
149 changes: 149 additions & 0 deletions src/test/java/com/marcnuri/mnimapsync/store/MessageCopierTest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,149 @@
/*
* MessageCopierTest.java
*
* Created on 2019-08-17, 8:24
*
* Copyright 2019 Marc Nuri San Felix
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
package com.marcnuri.mnimapsync.store;

import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.hasSize;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.doThrow;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;

import com.sun.mail.imap.IMAPFolder;
import com.sun.mail.imap.IMAPMessage;
import com.sun.mail.imap.IMAPStore;
import java.util.HashSet;
import java.util.Set;
import javax.mail.Message;
import javax.mail.MessagingException;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.mockito.ArgumentMatchers;
import org.mockito.Mockito;

/**
* Created by Marc Nuri <[email protected]> on 2019-08-17.
*/
public class MessageCopierTest {

private IMAPFolder imapFolder;
private IMAPStore imapStore;
private StoreIndex sourceIndex;
private StoreIndex targetIndex;
private StoreCopier storeCopier;

@BeforeEach
void setUp() throws Exception {
imapFolder = Mockito.mock(IMAPFolder.class);
doReturn('.').when(imapFolder).getSeparator();
imapStore = Mockito.mock(IMAPStore.class);
doReturn(imapFolder).when(imapStore).getFolder(anyString());
doReturn(imapFolder).when(imapStore).getDefaultFolder();
sourceIndex = Mockito.spy(new StoreIndex());
targetIndex = Mockito.spy(new StoreIndex());
storeCopier = Mockito.spy(new StoreCopier(imapStore, sourceIndex, imapStore, targetIndex, 1));
}

@AfterEach
void tearDown() {
storeCopier = null;
targetIndex = null;
sourceIndex = null;
imapStore = null;
imapFolder = null;
}

@Test
void run_emptyFolder_shouldOnlyUpdateIndexes() throws Exception {
// Given
final MessageCopier messageCopier = new MessageCopier(
storeCopier, "Source Folder", "Target Folder", 0, 100, new HashSet<>());
doReturn(new Message[0]).when(imapFolder).getMessages(eq(0), eq(100));
// When
messageCopier.run();
// Then
verify(storeCopier, times(1)).updatedMessagesCopiedCount(eq(0L));
verify(storeCopier, times(1)).updateMessagesSkippedCount(eq(0L));
verify(sourceIndex, times(1)).updatedIndexedMessageCount(eq(0L));
}

@Test
void run_folderWithAlreadyCopiedMessages_shouldOnlyUpdateIndexes() throws Exception {
// Given
final Set<MessageId> copiedMessages = new HashSet<>();
final MessageCopier messageCopier = new MessageCopier(
storeCopier, "Source Folder", "Target Folder", 0, 100, copiedMessages);
final IMAPMessage message = Mockito.mock(IMAPMessage.class);
doReturn(new String[]{"1337"}).when(message).getHeader("Message-Id");
copiedMessages.add(new MessageId(message));
doReturn(new Message[]{message}).when(imapFolder).getMessages(eq(0), eq(100));
// When
messageCopier.run();
// Then
verify(storeCopier, times(1)).updatedMessagesCopiedCount(eq(0L));
verify(storeCopier, times(1)).updateMessagesSkippedCount(eq(1L));
verify(sourceIndex, times(1)).updatedIndexedMessageCount(eq(1L));
assertThat(storeCopier.getMessagesSkippedCount(), equalTo(1L));
}

@Test
void run_folderWithCopiedAndNonCopiedMessages_shouldUpdateIndexesAndCopy() throws Exception {
// Given
final Set<MessageId> copiedMessages = new HashSet<>();
final MessageCopier messageCopier = new MessageCopier(
storeCopier, "Source Folder", "Target Folder", 0, 100, copiedMessages);
final IMAPMessage copiedMessage = Mockito.mock(IMAPMessage.class);
doReturn(new String[]{"1337"}).when(copiedMessage).getHeader("Message-Id");
copiedMessages.add(new MessageId(copiedMessage));
final IMAPMessage newMessage = Mockito.mock(IMAPMessage.class);
doReturn(new String[]{"313373"}).when(newMessage).getHeader("Message-Id");
doReturn(new Message[]{copiedMessage, newMessage}).when(imapFolder).getMessages(eq(0), eq(100));
// When
messageCopier.run();
// Then
verify(imapFolder, times(1)).appendMessages(ArgumentMatchers.any());
verify(storeCopier, times(1)).updatedMessagesCopiedCount(eq(1L));
verify(storeCopier, times(1)).updateMessagesSkippedCount(eq(1L));
verify(sourceIndex, times(1)).updatedIndexedMessageCount(eq(2L));
assertThat(storeCopier.getMessagesSkippedCount(), equalTo(1L));
assertThat(storeCopier.getMessagesCopiedCount(), equalTo(1L));
}

@Test
void run_folderThrowsException_shouldOnlyUpdateIndexes() throws Exception {
// Given
final MessageCopier messageCopier = new MessageCopier(
storeCopier, "Source Folder", "Target Folder", 0, 100, new HashSet<>());
doThrow(new MessagingException()).when(imapFolder).open(anyInt());
// When
messageCopier.run();
// Then
assertThat(storeCopier.getCopyExceptions(), hasSize(1));
verify(storeCopier, times(1)).updatedMessagesCopiedCount(eq(0L));
verify(storeCopier, times(1)).updateMessagesSkippedCount(eq(0L));
verify(sourceIndex, times(1)).updatedIndexedMessageCount(eq(0L));
}
}
Loading

0 comments on commit a1804cd

Please sign in to comment.