You are viewing a plain text version of this content. The canonical link for it is here.
Posted to server-dev@james.apache.org by ad...@apache.org on 2017/11/08 07:29:50 UTC

[3/9] james-project git commit: MAILBOX-318 Refuse to share mailbox with other domains

MAILBOX-318 Refuse to share mailbox with other domains


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

Branch: refs/heads/master
Commit: d0d9b2f9ea106691b2b3627ad4fe28aaa2fb7e7b
Parents: 562eeaa
Author: Antoine Duprat <ad...@linagora.com>
Authored: Fri Nov 3 14:30:54 2017 +0100
Committer: Antoine Duprat <ad...@linagora.com>
Committed: Tue Nov 7 15:33:53 2017 +0100

----------------------------------------------------------------------
 .../exception/DifferentDomainException.java     | 27 +++++++++
 mailbox/store/pom.xml                           |  4 ++
 .../james/mailbox/store/StoreRightManager.java  | 27 +++++++++
 .../mailbox/store/StoreRightManagerTest.java    | 59 ++++++++++++++++++++
 ...CassandraSetMailboxesMethodCucumberTest.java |  4 +-
 .../integration/GetMailboxesMethodTest.java     | 11 ++--
 .../integration/SetMailboxesMethodTest.java     | 10 ++--
 .../cucumber/SetMailboxesMethodStepdefs.java    | 15 +++++
 .../resources/cucumber/SetMailboxes.feature     | 30 ++++++++++
 .../MemorySetMailboxesMethodCucumberTest.java   |  4 +-
 .../methods/SetMailboxesUpdateProcessor.java    |  6 ++
 11 files changed, 183 insertions(+), 14 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/mailbox/api/src/main/java/org/apache/james/mailbox/exception/DifferentDomainException.java
----------------------------------------------------------------------
diff --git a/mailbox/api/src/main/java/org/apache/james/mailbox/exception/DifferentDomainException.java b/mailbox/api/src/main/java/org/apache/james/mailbox/exception/DifferentDomainException.java
new file mode 100644
index 0000000..20e7aa8
--- /dev/null
+++ b/mailbox/api/src/main/java/org/apache/james/mailbox/exception/DifferentDomainException.java
@@ -0,0 +1,27 @@
+/****************************************************************
+ * Licensed to the Apache Software Foundation (ASF) under one   *
+ * or more contributor license agreements.  See the NOTICE file *
+ * distributed with this work for additional information        *
+ * regarding copyright ownership.  The ASF licenses this file   *
+ * to you 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 org.apache.james.mailbox.exception;
+
+public class DifferentDomainException extends MailboxException {
+
+    public DifferentDomainException() {
+        super();
+    }
+}

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/mailbox/store/pom.xml
----------------------------------------------------------------------
diff --git a/mailbox/store/pom.xml b/mailbox/store/pom.xml
index 3049c2e..9befb3a 100644
--- a/mailbox/store/pom.xml
+++ b/mailbox/store/pom.xml
@@ -56,6 +56,10 @@
         </dependency>
         <dependency>
             <groupId>${project.groupId}</groupId>
+            <artifactId>james-core</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>${project.groupId}</groupId>
             <artifactId>james-server-util</artifactId>
         </dependency>
         <dependency>

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
----------------------------------------------------------------------
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
index 1ddfd6c..e1796fb 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
@@ -19,20 +19,24 @@
 
 package org.apache.james.mailbox.store;
 
+import java.util.Map;
 import java.util.Optional;
 
 import javax.inject.Inject;
 import javax.mail.Flags;
 
+import org.apache.james.core.User;
 import org.apache.james.mailbox.MailboxSession;
 import org.apache.james.mailbox.RightManager;
 import org.apache.james.mailbox.acl.GroupMembershipResolver;
 import org.apache.james.mailbox.acl.MailboxACLResolver;
+import org.apache.james.mailbox.exception.DifferentDomainException;
 import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.exception.UnsupportedRightException;
 import org.apache.james.mailbox.model.MailboxACL;
 import org.apache.james.mailbox.model.MailboxACL.ACLCommand;
 import org.apache.james.mailbox.model.MailboxACL.EntryKey;
+import org.apache.james.mailbox.model.MailboxACL.NameType;
 import org.apache.james.mailbox.model.MailboxACL.Rfc4314Rights;
 import org.apache.james.mailbox.model.MailboxACL.Right;
 import org.apache.james.mailbox.model.MailboxId;
@@ -112,11 +116,16 @@ public class StoreRightManager implements RightManager {
 
     @Override
     public void applyRightsCommand(MailboxPath mailboxPath, ACLCommand mailboxACLCommand, MailboxSession session) throws MailboxException {
+        assertSharesBelongsToUserDomain(mailboxPath.getUser(), mailboxACLCommand);
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
         Mailbox mailbox = mapper.findMailboxByPath(mailboxPath);
         mapper.execute(Mapper.toTransaction(() -> mapper.updateACL(mailbox, mailboxACLCommand)));
     }
 
+    private void assertSharesBelongsToUserDomain(String user, ACLCommand mailboxACLCommand) throws DifferentDomainException {
+        assertSharesBelongsToUserDomain(user, ImmutableMap.of(mailboxACLCommand.getEntryKey(), mailboxACLCommand.getRights()));
+    }
+
     public boolean isReadWrite(MailboxSession session, Mailbox mailbox, Flags sharedPermanentFlags) throws UnsupportedRightException {
         Rfc4314Rights rights = myRights(mailbox, session);
 
@@ -161,12 +170,30 @@ public class StoreRightManager implements RightManager {
 
     @Override
     public void setRights(MailboxPath mailboxPath, MailboxACL mailboxACL, MailboxSession session) throws MailboxException {
+        assertSharesBelongsToUserDomain(mailboxPath.getUser(), mailboxACL.getEntries());
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
         Mailbox mailbox = mapper.findMailboxByPath(mailboxPath);
 
         setRights(mailboxACL, mapper, mailbox);
     }
 
+    @VisibleForTesting
+    void assertSharesBelongsToUserDomain(String user, Map<EntryKey, Rfc4314Rights> entries) throws DifferentDomainException {
+        if (entries.keySet().stream()
+            .filter(entry -> !entry.getNameType().equals(NameType.special))
+            .map(EntryKey::getName)
+            .anyMatch(name -> areDomainsDifferent(name, user))) {
+            throw new DifferentDomainException();
+        }
+    }
+
+    @VisibleForTesting
+    boolean areDomainsDifferent(String user, String otherUser) {
+        Optional<String> domain = User.fromUsername(user).getDomainPart();
+        Optional<String> otherDomain = User.fromUsername(otherUser).getDomainPart();
+        return !domain.equals(otherDomain);
+    }
+
     private void setRights(MailboxACL mailboxACL, MailboxMapper mapper, Mailbox mailbox) throws MailboxException {
         mapper.execute(Mapper.toTransaction(() -> mapper.setACL(mailbox, mailboxACL)));
     }

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
----------------------------------------------------------------------
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
index 2b9a81b..265bfe8 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
@@ -24,6 +24,7 @@ import static org.apache.james.mailbox.fixture.MailboxFixture.BOB;
 import static org.apache.james.mailbox.fixture.MailboxFixture.CEDRIC;
 import static org.apache.james.mailbox.fixture.MailboxFixture.INBOX_ALICE;
 import static org.assertj.core.api.Assertions.assertThat;
+import static org.assertj.core.api.Assertions.assertThatThrownBy;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
 
@@ -33,12 +34,14 @@ import org.apache.james.mailbox.acl.GroupMembershipResolver;
 import org.apache.james.mailbox.acl.MailboxACLResolver;
 import org.apache.james.mailbox.acl.SimpleGroupMembershipResolver;
 import org.apache.james.mailbox.acl.UnionMailboxACLResolver;
+import org.apache.james.mailbox.exception.DifferentDomainException;
 import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.exception.UnsupportedRightException;
 import org.apache.james.mailbox.fixture.MailboxFixture;
 import org.apache.james.mailbox.mock.MockMailboxSession;
 import org.apache.james.mailbox.model.MailboxACL;
+import org.apache.james.mailbox.model.MailboxACL.ACLCommand;
 import org.apache.james.mailbox.model.MailboxACL.Right;
 import org.apache.james.mailbox.model.MailboxPath;
 import org.apache.james.mailbox.store.mail.MailboxMapper;
@@ -223,4 +226,60 @@ public class StoreRightManagerTest {
             new SimpleMailbox(INBOX_ALICE, UID_VALIDITY), acl, new MockMailboxSession(BOB));
         assertThat(actual.getEntries()).containsKey(MailboxACL.EntryKey.createUserEntryKey(BOB));
     }
+
+    @Test
+    public void areDomainsDifferentShouldReturnTrueWhenOneHasDomainNotTheOther() {
+        assertThat(storeRightManager.areDomainsDifferent("user@domain.org", "otherUser")).isTrue();
+    }
+
+    @Test
+    public void areDomainsDifferentShouldReturnTrueWhenOtherHasDomainNotTheOne() {
+        assertThat(storeRightManager.areDomainsDifferent("user", "otherUser@domain.org")).isTrue();
+    }
+
+    @Test
+    public void areDomainsDifferentShouldReturnFalseWhenNoDomain() {
+        assertThat(storeRightManager.areDomainsDifferent("user", "otherUser")).isFalse();
+    }
+
+    @Test
+    public void areDomainsDifferentShouldReturnTrueWhenDomainsAreDifferent() {
+        assertThat(storeRightManager.areDomainsDifferent("user@domain.org", "otherUser@otherdomain.org")).isTrue();
+    }
+
+    @Test
+    public void areDomainsDifferentShouldReturnFalseWhenDomainsAreIdentical() {
+        assertThat(storeRightManager.areDomainsDifferent("user@domain.org", "otherUser@domain.org")).isFalse();
+    }
+
+    @Test
+    public void assertSharesBelongsToUserDomainShouldThrowWhenOneDomainIsDifferent() throws Exception  {
+        MailboxACL mailboxACL = new MailboxACL(new MailboxACL.Entry("a@domain.org", Right.Write), 
+                new MailboxACL.Entry("b@otherdomain.org", Right.Write), 
+                new MailboxACL.Entry("c@domain.org", Right.Write));
+        
+        assertThatThrownBy(() -> storeRightManager.assertSharesBelongsToUserDomain("user@domain.org", mailboxACL.getEntries()))
+            .isInstanceOf(DifferentDomainException.class);
+    }
+
+    @Test
+    public void assertSharesBelongsToUserDomainShouldNotThrowWhenDomainsAreIdentical() throws Exception  {
+        MailboxACL mailboxACL = new MailboxACL(new MailboxACL.Entry("a@domain.org", Right.Write), 
+                new MailboxACL.Entry("b@domain.org", Right.Write), 
+                new MailboxACL.Entry("c@domain.org", Right.Write));
+        
+        storeRightManager.assertSharesBelongsToUserDomain("user@domain.org", mailboxACL.getEntries());
+    }
+
+    @Test
+    public void applyRightsCommandShouldThrowWhenDomainsAreDifferent() {
+        MailboxPath mailboxPath = MailboxPath.forUser("user@domain.org", "mailbox");
+        ACLCommand aclCommand = MailboxACL.command()
+            .forUser("otherUser@otherdomain.org")
+            .rights(MailboxACL.FULL_RIGHTS)
+            .asAddition();
+       
+        assertThatThrownBy(() -> storeRightManager.applyRightsCommand(mailboxPath, aclCommand, aliceSession))
+            .isInstanceOf(DifferentDomainException.class);
+    }
 }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap-integration-testing/cassandra-jmap-integration-testing/src/test/java/org/apache/james/jmap/cassandra/cucumber/CassandraSetMailboxesMethodCucumberTest.java
----------------------------------------------------------------------
diff --git a/server/protocols/jmap-integration-testing/cassandra-jmap-integration-testing/src/test/java/org/apache/james/jmap/cassandra/cucumber/CassandraSetMailboxesMethodCucumberTest.java b/server/protocols/jmap-integration-testing/cassandra-jmap-integration-testing/src/test/java/org/apache/james/jmap/cassandra/cucumber/CassandraSetMailboxesMethodCucumberTest.java
index c7ed001..1751d4b 100644
--- a/server/protocols/jmap-integration-testing/cassandra-jmap-integration-testing/src/test/java/org/apache/james/jmap/cassandra/cucumber/CassandraSetMailboxesMethodCucumberTest.java
+++ b/server/protocols/jmap-integration-testing/cassandra-jmap-integration-testing/src/test/java/org/apache/james/jmap/cassandra/cucumber/CassandraSetMailboxesMethodCucumberTest.java
@@ -27,8 +27,8 @@ import cucumber.api.CucumberOptions;
 import cucumber.api.junit.Cucumber;
 
 @RunWith(Cucumber.class)
-@CucumberOptions(features="classpath:cucumber/MailboxModification.feature",
-                glue={"org.apache.james.jmap.methods.integration", "org.apache.james.jmap.cassandra.cucumber"},
+@CucumberOptions(features= { "classpath:cucumber/MailboxModification.feature", "classpath:cucumber/SetMailboxes.feature" },
+                glue= { "org.apache.james.jmap.methods.integration", "org.apache.james.jmap.cassandra.cucumber" },
                 strict = true)
 public class CassandraSetMailboxesMethodCucumberTest {
 

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/GetMailboxesMethodTest.java
----------------------------------------------------------------------
diff --git a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/GetMailboxesMethodTest.java b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/GetMailboxesMethodTest.java
index 48c7a39..ffc7e89 100644
--- a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/GetMailboxesMethodTest.java
+++ b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/GetMailboxesMethodTest.java
@@ -84,6 +84,7 @@ public abstract class GetMailboxesMethodTest {
     protected abstract GuiceJamesServer createJmapServer();
 
     private AccessToken accessToken;
+    private String domain;
     private String alice;
     private String bob;
     private String cedric;
@@ -106,7 +107,7 @@ public abstract class GetMailboxesMethodTest {
                 .build();
         RestAssured.enableLoggingOfRequestAndResponseIfValidationFails();
 
-        String domain = "domain.tld";
+        domain = "domain.tld";
         alice = "alice@" + domain;
         String alicePassword = "aliceSecret";
         bob = "bob@" + domain;
@@ -252,8 +253,8 @@ public abstract class GetMailboxesMethodTest {
     public void getMailboxesShouldReturnSharedWithProperty() throws Exception {
         String mailboxName = "myMailbox";
         String myMailboxId = mailboxProbe.createMailbox(MailboxConstants.USER_NAMESPACE, alice, mailboxName).serialize();
-        String targetUser1 = "toUser1@domain.com";
-        String targetUser2 = "toUser2@domain.com";
+        String targetUser1 = "toUser1@" + domain;
+        String targetUser2 = "toUser2@" + domain;
         Mailbox myMailbox = mailboxProbe.getMailbox(MailboxConstants.USER_NAMESPACE, alice, mailboxName);
         aclProbe.replaceRights(myMailbox.generateAssociatedPath(), targetUser1, new Rfc4314Rights(Right.Lookup, Right.Administer));
         aclProbe.replaceRights(myMailbox.generateAssociatedPath(), targetUser2, new Rfc4314Rights(Right.Read, Right.Lookup));
@@ -275,7 +276,7 @@ public abstract class GetMailboxesMethodTest {
     public void getMailboxesShouldRemoveOwnerRight() throws Exception {
         String mailboxName = "myMailbox";
         String myMailboxId = mailboxProbe.createMailbox(MailboxConstants.USER_NAMESPACE, alice, mailboxName).serialize();
-        String targetUser1 = "toUser1@domain.com";
+        String targetUser1 = "toUser1@" + domain;
         Mailbox myMailbox = mailboxProbe.getMailbox(MailboxConstants.USER_NAMESPACE, alice, mailboxName);
         aclProbe.replaceRights(myMailbox.generateAssociatedPath(), alice, new Rfc4314Rights(Right.Read, Right.Administer));
         aclProbe.replaceRights(myMailbox.generateAssociatedPath(), targetUser1, new Rfc4314Rights(Right.Read, Right.Lookup));
@@ -313,7 +314,7 @@ public abstract class GetMailboxesMethodTest {
     public void nonHandledRightsShouldBeFilteredOut() throws Exception {
         String mailboxName = "myMailbox";
         String myMailboxId = mailboxProbe.createMailbox(MailboxConstants.USER_NAMESPACE, alice, mailboxName).serialize();
-        String targetUser1 = "toUser1@domain.com";
+        String targetUser1 = "toUser1@" + domain;
         Mailbox myMailbox = mailboxProbe.getMailbox(MailboxConstants.USER_NAMESPACE, alice, mailboxName);
         aclProbe.replaceRights(myMailbox.generateAssociatedPath(), targetUser1, new Rfc4314Rights(Right.Lookup, Right.Post));
 

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/SetMailboxesMethodTest.java
----------------------------------------------------------------------
diff --git a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/SetMailboxesMethodTest.java b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/SetMailboxesMethodTest.java
index baeac41..690de87 100644
--- a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/SetMailboxesMethodTest.java
+++ b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/SetMailboxesMethodTest.java
@@ -1176,7 +1176,7 @@ public abstract class SetMailboxesMethodTest {
                 "    {" +
                 "      \"update\": {" +
                 "        \"" + mailboxId.serialize() + "\" : {" +
-                "          \"sharedWith\" : {\"user\": [\"a\", \"w\"]}" +
+                "          \"sharedWith\" : {\"user@" + USERS_DOMAIN + "\": [\"a\", \"w\"]}" +
                 "        }" +
                 "      }" +
                 "    }," +
@@ -1285,7 +1285,7 @@ public abstract class SetMailboxesMethodTest {
     @Test
     public void updateShouldApplyWhenSettingNewACL() {
         String myBox = "myBox";
-        String user = "user";
+        String user = "user@" + USERS_DOMAIN;
         MailboxId mailboxId = mailboxProbe.createMailbox(MailboxConstants.USER_NAMESPACE, username, myBox);
         String requestBody =
             "[" +
@@ -1321,7 +1321,7 @@ public abstract class SetMailboxesMethodTest {
     @Test
     public void updateShouldModifyStoredDataWhenUpdatingACL() {
         String myBox = "myBox";
-        String user = "user";
+        String user = "user@" + USERS_DOMAIN;
         MailboxId mailboxId = mailboxProbe.createMailbox(MailboxConstants.USER_NAMESPACE, username, myBox);
 
         with()
@@ -1421,8 +1421,8 @@ public abstract class SetMailboxesMethodTest {
     @Test
     public void updateShouldModifyStoredDataWhenSwitchingACLUser() {
         String myBox = "myBox";
-        String user1 = "user1";
-        String user2 = "user2";
+        String user1 = "user1@" + USERS_DOMAIN;
+        String user2 = "user2@" + USERS_DOMAIN;
         MailboxId mailboxId = mailboxProbe.createMailbox(MailboxConstants.USER_NAMESPACE, username, myBox);
 
         with()

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/cucumber/SetMailboxesMethodStepdefs.java
----------------------------------------------------------------------
diff --git a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/cucumber/SetMailboxesMethodStepdefs.java b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/cucumber/SetMailboxesMethodStepdefs.java
index d26df19..3705db7 100644
--- a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/cucumber/SetMailboxesMethodStepdefs.java
+++ b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/java/org/apache/james/jmap/methods/integration/cucumber/SetMailboxesMethodStepdefs.java
@@ -24,6 +24,7 @@ import static org.assertj.core.api.Assertions.assertThat;
 import java.io.ByteArrayInputStream;
 import java.util.Date;
 import java.util.List;
+import java.util.Map;
 import java.util.stream.Collectors;
 import java.util.stream.IntStream;
 
@@ -38,6 +39,7 @@ import org.apache.james.mailbox.model.MailboxPath;
 import org.apache.james.mailbox.store.mail.model.Mailbox;
 
 import com.github.fge.lambdas.Throwing;
+import com.google.common.collect.Maps;
 import com.jayway.awaitility.Awaitility;
 import com.jayway.awaitility.Duration;
 import com.jayway.jsonpath.DocumentContext;
@@ -191,4 +193,17 @@ public class SetMailboxesMethodStepdefs {
             return jsonPath.<List<String>>read(ARGUMENTS + ".messageIds").size() == messageCount;
         });
     }
+
+    @Then("^\"([^\"]*)\" receives not updated on mailbox \"([^\"]*)\" with kind \"([^\"]*)\" and message \"([^\"]*)\"$")
+    public void assertNotUpdatedWithGivenProperties(String userName, String mailboxName, String type, String message) throws Exception {
+        Mailbox mailbox = mainStepdefs.mailboxProbe.getMailbox("#private", userName, mailboxName);
+        assertThat(httpClient.response.getStatusLine().getStatusCode()).isEqualTo(200);
+        assertThat(httpClient.jsonPath.<String>read(NAME)).isEqualTo("mailboxesSet");
+        
+        Map<String, Map<String, String>> notUpdated = httpClient.jsonPath.<Map<String, Map<String, String>>>read(ARGUMENTS + ".notUpdated");
+        assertThat(notUpdated).hasSize(1);
+        Map<String, String> parameters = notUpdated.get(mailbox.getMailboxId().serialize());
+        assertThat(parameters).contains(Maps.immutableEntry("type", type),
+                Maps.immutableEntry("description", message));
+    }
 }

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/resources/cucumber/SetMailboxes.feature
----------------------------------------------------------------------
diff --git a/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/resources/cucumber/SetMailboxes.feature b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/resources/cucumber/SetMailboxes.feature
new file mode 100644
index 0000000..57a7512
--- /dev/null
+++ b/server/protocols/jmap-integration-testing/jmap-integration-testing-common/src/test/resources/cucumber/SetMailboxes.feature
@@ -0,0 +1,30 @@
+#***************************************************************
+# Licensed to the Apache Software Foundation (ASF) under one   *
+# or more contributor license agreements.  See the NOTICE file *
+# distributed with this work for additional information        *
+# regarding copyright ownership.  The ASF licenses this file   *
+# to you 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.                                           *
+# **************************************************************/
+Feature: SetMailboxes method
+
+  Background:
+    Given a domain named "domain.tld"
+    And a user "alice@domain.tld"
+    And "alice@domain.tld" has a mailbox "shared"
+
+  Scenario: setMailboxes should reject sharing a mailbox to another domain
+    Given a domain named "otherdomain.tld"
+    And a user "bob@otherdomain.tld"
+    When "alice@domain.tld" shares its mailbox "shared" with rights "lrw" with "bob@otherdomain.tld"
+    Then "alice@domain.tld" receives not updated on mailbox "shared" with kind "invalidArguments" and message "Cannot share a mailbox to another domain"

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap-integration-testing/memory-jmap-integration-testing/src/test/java/org/apache/james/jmap/memory/cucumber/MemorySetMailboxesMethodCucumberTest.java
----------------------------------------------------------------------
diff --git a/server/protocols/jmap-integration-testing/memory-jmap-integration-testing/src/test/java/org/apache/james/jmap/memory/cucumber/MemorySetMailboxesMethodCucumberTest.java b/server/protocols/jmap-integration-testing/memory-jmap-integration-testing/src/test/java/org/apache/james/jmap/memory/cucumber/MemorySetMailboxesMethodCucumberTest.java
index c61cfb5..e0cbec0 100644
--- a/server/protocols/jmap-integration-testing/memory-jmap-integration-testing/src/test/java/org/apache/james/jmap/memory/cucumber/MemorySetMailboxesMethodCucumberTest.java
+++ b/server/protocols/jmap-integration-testing/memory-jmap-integration-testing/src/test/java/org/apache/james/jmap/memory/cucumber/MemorySetMailboxesMethodCucumberTest.java
@@ -25,8 +25,8 @@ import cucumber.api.CucumberOptions;
 import cucumber.api.junit.Cucumber;
 
 @RunWith(Cucumber.class)
-@CucumberOptions(features="classpath:cucumber/MailboxModification.feature",
-                glue={"org.apache.james.jmap.methods.integration", "org.apache.james.jmap.memory.cucumber"},
+@CucumberOptions(features= { "classpath:cucumber/MailboxModification.feature", "classpath:cucumber/SetMailboxes.feature" },
+                glue= { "org.apache.james.jmap.methods.integration", "org.apache.james.jmap.memory.cucumber" },
                 strict = true)
 public class MemorySetMailboxesMethodCucumberTest {
 }

http://git-wip-us.apache.org/repos/asf/james-project/blob/d0d9b2f9/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMailboxesUpdateProcessor.java
----------------------------------------------------------------------
diff --git a/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMailboxesUpdateProcessor.java b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMailboxesUpdateProcessor.java
index 634c73a..4d7a8fd 100644
--- a/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMailboxesUpdateProcessor.java
+++ b/server/protocols/jmap/src/main/java/org/apache/james/jmap/methods/SetMailboxesUpdateProcessor.java
@@ -41,6 +41,7 @@ import org.apache.james.jmap.utils.MailboxUtils;
 import org.apache.james.mailbox.MailboxManager;
 import org.apache.james.mailbox.MailboxSession;
 import org.apache.james.mailbox.SubscriptionManager;
+import org.apache.james.mailbox.exception.DifferentDomainException;
 import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.exception.MailboxExistsException;
 import org.apache.james.mailbox.exception.MailboxNameException;
@@ -134,6 +135,11 @@ public class SetMailboxesUpdateProcessor implements SetMailboxesProcessor {
                     .type("invalidArguments")
                     .description("Cannot rename a mailbox to an already existing mailbox.")
                     .build());
+        } catch (DifferentDomainException e) {
+            responseBuilder.notUpdated(mailboxId, SetError.builder()
+                .type("invalidArguments")
+                .description("Cannot share a mailbox to another domain")
+                .build());
         } catch (MailboxException e) {
             LOGGER.error("Error while updating mailbox", e);
             responseBuilder.notUpdated(mailboxId, SetError.builder()


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