Repository: james-project
Updated Branches:
  refs/heads/master 8e9c667e7 -> 38acce230


JAMES-2244 Allow message creation in several mailboxes

Message creation assertions concerning mailboxIds should be done explicitly on 
mailboxIds

Tests are then easier. The checked properties of creation entries are then 
easier.

Note: As drafts are still overrides to be in draft mailbox, we can not write 
integration test for this yet.


Project: http://git-wip-us.apache.org/repos/asf/james-project/repo
Commit: http://git-wip-us.apache.org/repos/asf/james-project/commit/66f19b2b
Tree: http://git-wip-us.apache.org/repos/asf/james-project/tree/66f19b2b
Diff: http://git-wip-us.apache.org/repos/asf/james-project/diff/66f19b2b

Branch: refs/heads/master
Commit: 66f19b2b9103c2b64f1627019f6e8e5a51d98293
Parents: b812aaa
Author: benwa <btell...@linagora.com>
Authored: Tue Dec 12 16:02:04 2017 +0700
Committer: benwa <btell...@linagora.com>
Committed: Thu Dec 14 16:03:11 2017 +0700

----------------------------------------------------------------------
 .../james/jmap/methods/MessageAppender.java     | 21 ++++++-------
 .../methods/SetMessagesCreationProcessor.java   | 33 +++++++++++++-------
 .../SetMessagesCreationProcessorTest.java       | 26 +++++----------
 3 files changed, 38 insertions(+), 42 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/james-project/blob/66f19b2b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/MessageAppender.java
----------------------------------------------------------------------
diff --git 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/MessageAppender.java
 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/MessageAppender.java
index 763ba27..5ca9ab3 100644
--- 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/MessageAppender.java
+++ 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/MessageAppender.java
@@ -20,6 +20,7 @@
 package org.apache.james.jmap.methods;
 
 import java.util.Date;
+import java.util.List;
 import java.util.Optional;
 
 import javax.inject.Inject;
@@ -35,6 +36,7 @@ import org.apache.james.jmap.model.OldKeyword;
 import org.apache.james.mailbox.AttachmentManager;
 import org.apache.james.mailbox.MailboxManager;
 import org.apache.james.mailbox.MailboxSession;
+import org.apache.james.mailbox.MessageIdManager;
 import org.apache.james.mailbox.MessageManager;
 import org.apache.james.mailbox.exception.AttachmentNotFoundException;
 import org.apache.james.mailbox.exception.MailboxException;
@@ -56,18 +58,20 @@ public class MessageAppender {
     private static final Logger LOGGER = 
LoggerFactory.getLogger(MessageAppender.class);
 
     private final MailboxManager mailboxManager;
+    private final MessageIdManager messageIdManager;
     private final AttachmentManager attachmentManager;
     private final MIMEMessageConverter mimeMessageConverter;
 
     @Inject
-    public MessageAppender(MailboxManager mailboxManager, AttachmentManager 
attachmentManager, MIMEMessageConverter mimeMessageConverter) {
+    public MessageAppender(MailboxManager mailboxManager, MessageIdManager 
messageIdManager, AttachmentManager attachmentManager, MIMEMessageConverter 
mimeMessageConverter) {
         this.mailboxManager = mailboxManager;
+        this.messageIdManager = messageIdManager;
         this.attachmentManager = attachmentManager;
         this.mimeMessageConverter = mimeMessageConverter;
     }
 
     public MessageFactory.MetaDataWithContent 
appendMessageInMailbox(CreationMessageEntry createdEntry,
-                                                                     
MessageManager mailbox,
+                                                                     
List<MailboxId> targetMailboxes,
                                                                      
MailboxSession session) throws MailboxException {
         ImmutableList<MessageAttachment> messageAttachments = 
getMessageAttachments(session, createdEntry.getValue().getAttachments());
         byte[] messageContent = mimeMessageConverter.convert(createdEntry, 
messageAttachments);
@@ -75,8 +79,11 @@ public class MessageAppender {
         Date internalDate = 
Date.from(createdEntry.getValue().getDate().toInstant());
 
         boolean notRecent = false;
-
+        MessageManager mailbox = 
mailboxManager.getMailbox(targetMailboxes.get(0), session);
         ComposedMessageId message = mailbox.appendMessage(content, 
internalDate, session, notRecent, getFlags(createdEntry.getValue()));
+        if (targetMailboxes.size() > 0) {
+            messageIdManager.setInMailboxes(message.getMessageId(), 
targetMailboxes, session);
+        }
 
         return MessageFactory.MetaDataWithContent.builder()
             .uid(message.getUid())
@@ -102,14 +109,6 @@ public class MessageAppender {
                 .orElse(Keywords.DEFAULT_VALUE);
     }
 
-    public MessageFactory.MetaDataWithContent 
appendMessageInMailbox(CreationMessageEntry createdEntry,
-                                                                     MailboxId 
mailboxId,
-                                                                     
MailboxSession session) throws MailboxException {
-        return appendMessageInMailbox(createdEntry,
-            mailboxManager.getMailbox(mailboxId, session),
-            session);
-    }
-
     private ImmutableList<MessageAttachment> 
getMessageAttachments(MailboxSession session, ImmutableList<Attachment> 
attachments) throws MailboxException {
         ThrowingFunction<Attachment, Optional<MessageAttachment>> 
toMessageAttachment = att -> messageAttachment(session, att);
         return attachments.stream()

http://git-wip-us.apache.org/repos/asf/james-project/blob/66f19b2b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMessagesCreationProcessor.java
----------------------------------------------------------------------
diff --git 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMessagesCreationProcessor.java
 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMessagesCreationProcessor.java
index 07c087c..b8f820b 100644
--- 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMessagesCreationProcessor.java
+++ 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMessagesCreationProcessor.java
@@ -65,8 +65,10 @@ import org.slf4j.LoggerFactory;
 
 import com.github.fge.lambdas.Throwing;
 import com.github.fge.lambdas.functions.FunctionChainer;
+import com.github.steveash.guavate.Guavate;
 import com.google.common.annotations.VisibleForTesting;
 import com.google.common.base.Splitter;
+import com.google.common.collect.ImmutableList;
 
 
 public class SetMessagesCreationProcessor implements SetMessagesProcessor {
@@ -112,8 +114,9 @@ public class SetMessagesCreationProcessor implements 
SetMessagesProcessor {
 
     private void handleCreate(CreationMessageEntry create, Builder 
responseBuilder, MailboxSession mailboxSession) {
         try {
-            assertAtLeastOneMailbox(create);
-            assertIsUserOwnerOfMailboxes(create, mailboxSession);
+            List<MailboxId> mailboxIds = toMailboxIds(create);
+            assertAtLeastOneMailbox(mailboxIds);
+            assertIsUserOwnerOfMailboxes(mailboxIds, mailboxSession);
             performCreate(create, responseBuilder, mailboxSession);
         } catch (MailboxSendingNotAllowedException e) {
             responseBuilder.notCreated(create.getCreationId(), 
@@ -186,7 +189,15 @@ public class SetMessagesCreationProcessor implements 
SetMessagesProcessor {
                         .build());
         }
     }
-    
+
+    private ImmutableList<MailboxId> toMailboxIds(CreationMessageEntry create) 
{
+        return create.getValue().getMailboxIds()
+            .stream()
+            .distinct()
+            .map(mailboxIdFactory::fromString)
+            .collect(Guavate.toImmutableList());
+    }
+
     private void performCreate(CreationMessageEntry entry, Builder 
responseBuilder, MailboxSession session) throws MailboxException, 
InvalidMailboxForCreationException, MessagingException, 
AttachmentsNotFoundException {
         if (isAppendToMailboxWithRole(Role.OUTBOX, entry.getValue(), session)) 
{
             sendMailViaOutbox(entry, responseBuilder, session);
@@ -207,8 +218,8 @@ public class SetMessagesCreationProcessor implements 
SetMessagesProcessor {
         }
     }
 
-    private void assertAtLeastOneMailbox(CreationMessageEntry entry) throws 
MailboxException {
-        if (entry.getValue().getMailboxIds().isEmpty()) {
+    private void assertAtLeastOneMailbox(List<MailboxId> mailboxIds) throws 
MailboxException {
+        if (mailboxIds.isEmpty()) {
             throw new MessageHasNoMailboxException();
         }
     }
@@ -246,16 +257,15 @@ public class SetMessagesCreationProcessor implements 
SetMessagesProcessor {
         attachmentChecker.assertAttachmentsExist(entry, session);
     }
 
-    @VisibleForTesting void assertIsUserOwnerOfMailboxes(CreationMessageEntry 
entry, MailboxSession session) throws MailboxNotOwnedException {
-        if (containsMailboxNotOwn(entry.getValue().getMailboxIds(), session)) {
+    @VisibleForTesting void assertIsUserOwnerOfMailboxes(List<MailboxId> 
mailboxIds, MailboxSession session) throws MailboxNotOwnedException {
+        if (containsMailboxNotOwn(mailboxIds, session)) {
             throw new MailboxNotOwnedException();
         }
     }
 
-    private boolean containsMailboxNotOwn(List<String> mailboxIds, 
MailboxSession session) {
+    private boolean containsMailboxNotOwn(List<MailboxId> mailboxIds, 
MailboxSession session) {
         FunctionChainer<MailboxId, MessageManager> findMailbox = 
Throwing.function(mailboxId -> mailboxManager.getMailbox(mailboxId, session));
         return mailboxIds.stream()
-            .map(mailboxIdFactory::fromString)
             .map(findMailbox.sneakyThrow())
             .map(Throwing.function(MessageManager::getMailboxPath))
             .anyMatch(path -> !path.belongsTo(session));
@@ -263,8 +273,7 @@ public class SetMessagesCreationProcessor implements 
SetMessagesProcessor {
 
     private MessageWithId handleOutboxMessages(CreationMessageEntry entry, 
MailboxSession session) throws MailboxException, MessagingException {
         assertUserIsSender(session, entry.getValue().getFrom());
-        MessageManager outbox = getMailboxWithRole(session, 
Role.OUTBOX).orElseThrow(() -> new 
MailboxNotFoundException(Role.OUTBOX.serialize()));
-        MetaDataWithContent newMessage = 
messageAppender.appendMessageInMailbox(entry, outbox, session);
+        MetaDataWithContent newMessage = 
messageAppender.appendMessageInMailbox(entry, toMailboxIds(entry), session);
         Message jmapMessage = 
messageFactory.fromMetaDataWithContent(newMessage);
         Envelope envelope = Envelope.fromMessage(jmapMessage);
         messageSender.sendMessage(newMessage, envelope, session);
@@ -282,7 +291,7 @@ public class SetMessagesCreationProcessor implements 
SetMessagesProcessor {
 
     private MessageWithId handleDraftMessages(CreationMessageEntry entry, 
MailboxSession session) throws MailboxException, MessagingException {
         MessageManager draftMailbox = getMailboxWithRole(session, 
Role.DRAFTS).orElseThrow(() -> new 
MailboxNotFoundException(Role.DRAFTS.serialize()));
-        MetaDataWithContent newMessage = 
messageAppender.appendMessageInMailbox(entry, draftMailbox, session);
+        MetaDataWithContent newMessage = 
messageAppender.appendMessageInMailbox(entry, 
ImmutableList.of(draftMailbox.getId()), session);
         Message jmapMessage = 
messageFactory.fromMetaDataWithContent(newMessage);
         return new ValueWithId.MessageWithId(entry.getCreationId(), 
jmapMessage);
     }

http://git-wip-us.apache.org/repos/asf/james-project/blob/66f19b2b/server/protocols/jmap/src/test/java/org/apache/james/jmap/methods/SetMessagesCreationProcessorTest.java
----------------------------------------------------------------------
diff --git 
a/server/protocols/jmap/src/test/java/org/apache/james/jmap/methods/SetMessagesCreationProcessorTest.java
 
b/server/protocols/jmap/src/test/java/org/apache/james/jmap/methods/SetMessagesCreationProcessorTest.java
index 0d8a9cb..ebdcc83 100644
--- 
a/server/protocols/jmap/src/test/java/org/apache/james/jmap/methods/SetMessagesCreationProcessorTest.java
+++ 
b/server/protocols/jmap/src/test/java/org/apache/james/jmap/methods/SetMessagesCreationProcessorTest.java
@@ -36,7 +36,6 @@ import java.util.stream.Stream;
 import javax.mail.Flags;
 
 import org.apache.james.jmap.exceptions.MailboxNotOwnedException;
-import org.apache.james.jmap.methods.ValueWithId.CreationMessageEntry;
 import org.apache.james.jmap.model.CreationMessage;
 import org.apache.james.jmap.model.CreationMessage.DraftEmailer;
 import org.apache.james.jmap.model.CreationMessageId;
@@ -54,6 +53,7 @@ import org.apache.james.mailbox.AttachmentManager;
 import org.apache.james.mailbox.BlobManager;
 import org.apache.james.mailbox.MailboxManager;
 import org.apache.james.mailbox.MailboxSession;
+import org.apache.james.mailbox.MessageIdManager;
 import org.apache.james.mailbox.MessageManager;
 import org.apache.james.mailbox.MessageUid;
 import org.apache.james.mailbox.exception.MailboxException;
@@ -135,11 +135,12 @@ public class SetMessagesCreationProcessorTest {
         mockedAttachmentManager = mock(AttachmentManager.class);
         mockedMailboxManager = mock(MailboxManager.class);
         mockedMailboxIdFactory = mock(Factory.class);
+        MessageIdManager mockMessageIdManager = mock(MessageIdManager.class);
         
         fakeSystemMailboxesProvider = new TestSystemMailboxesProvider(() -> 
optionalOutbox, () -> optionalDrafts);
         session = new MockMailboxSession(USER);
         MIMEMessageConverter mimeMessageConverter = new MIMEMessageConverter();
-        messageAppender = new MessageAppender(mockedMailboxManager, 
mockedAttachmentManager, mimeMessageConverter);
+        messageAppender = new MessageAppender(mockedMailboxManager, 
mockMessageIdManager, mockedAttachmentManager, mimeMessageConverter);
         messageSender = new MessageSender(mockedMailSpool, mockedMailFactory);
         sut = new SetMessagesCreationProcessor(messageFactory,
             fakeSystemMailboxesProvider,
@@ -319,15 +320,12 @@ public class SetMessagesCreationProcessorTest {
             .thenThrow(new MailboxNotFoundException(mailboxId));
         when(mockedMailboxIdFactory.fromString(mailboxId.serialize()))
             .thenReturn(mailboxId);
-        CreationMessageId creationMessageId = 
CreationMessageId.of("anything-really");
-        CreationMessageEntry entry = new 
CreationMessageEntry(creationMessageId, 
creationMessageBuilder.mailboxId(mailboxId.serialize()).build());
 
-        assertThatThrownBy(() -> sut.assertIsUserOwnerOfMailboxes(entry, 
session));
+        assertThatThrownBy(() -> 
sut.assertIsUserOwnerOfMailboxes(ImmutableList.of(mailboxId), session));
     }
 
     @Test
     public void 
assertIsUserOwnerOfMailboxesShouldThrowWhenRetrievingMailboxPathFails() throws 
Exception {
-        CreationMessageId creationMessageId = 
CreationMessageId.of("anything-really");
         InMemoryId mailboxId = InMemoryId.of(6789);
         MessageManager mailbox = mock(MessageManager.class);
         when(mockedMailboxManager.getMailbox(mailboxId, session))
@@ -337,14 +335,11 @@ public class SetMessagesCreationProcessorTest {
         when(mailbox.getMailboxPath())
             .thenThrow(new MailboxException());
 
-        CreationMessageEntry entry = new 
CreationMessageEntry(creationMessageId, 
creationMessageBuilder.mailboxId(mailboxId.serialize()).build());
-
-        assertThatThrownBy(() -> sut.assertIsUserOwnerOfMailboxes(entry, 
session));
+        assertThatThrownBy(() -> 
sut.assertIsUserOwnerOfMailboxes(ImmutableList.of(mailboxId), session));
     }
 
     @Test
     public void 
assertIsUserOwnerOfMailboxesShouldThrowWhenUserIsNotTheOwnerOfTheMailbox() 
throws Exception {
-        CreationMessageId creationMessageId = 
CreationMessageId.of("anything-really");
         InMemoryId mailboxId = InMemoryId.of(6789);
         MessageManager mailbox = mock(MessageManager.class);
         when(mockedMailboxManager.getMailbox(mailboxId, session))
@@ -354,16 +349,12 @@ public class SetMessagesCreationProcessorTest {
         when(mailbox.getMailboxPath())
             .thenReturn(MailboxPath.forUser("otheru...@example.com", 
mailboxId.serialize()));
 
-
-        CreationMessageEntry entry = new 
CreationMessageEntry(creationMessageId, 
creationMessageBuilder.mailboxId(mailboxId.serialize()).build());
-
-        assertThatThrownBy(() -> sut.assertIsUserOwnerOfMailboxes(entry, 
session))
+        assertThatThrownBy(() -> 
sut.assertIsUserOwnerOfMailboxes(ImmutableList.of(mailboxId), session))
             .isInstanceOf(MailboxNotOwnedException.class);
     }
 
     @Test
     public void 
assertIsUserOwnerOfMailboxesShouldNotThrowWhenUserIsTheOwnerOfTheMailbox() 
throws Exception {
-        CreationMessageId creationMessageId = 
CreationMessageId.of("anything-really");
         InMemoryId mailboxId = InMemoryId.of(6789);
         MessageManager mailbox = mock(MessageManager.class);
         when(mockedMailboxManager.getMailbox(mailboxId, session))
@@ -373,10 +364,7 @@ public class SetMessagesCreationProcessorTest {
         when(mailbox.getMailboxPath())
             .thenReturn(MailboxPath.forUser(USER, mailboxId.serialize()));
 
-
-        CreationMessageEntry entry = new 
CreationMessageEntry(creationMessageId, 
creationMessageBuilder.mailboxId(mailboxId.serialize()).build());
-
-        sut.assertIsUserOwnerOfMailboxes(entry, session);
+        sut.assertIsUserOwnerOfMailboxes(ImmutableList.of(mailboxId), session);
     }
     
     public static class TestSystemMailboxesProvider implements 
SystemMailboxesProvider {


---------------------------------------------------------------------
To unsubscribe, e-mail: server-dev-unsubscr...@james.apache.org
For additional commands, e-mail: server-dev-h...@james.apache.org

Reply via email to