JAMES-2183 Adding KeywordsCombiner

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

Branch: refs/heads/master
Commit: f0b277144369e938fdd11eebc705e7f02c96ed9c
Parents: d1238fc
Author: benwa <btell...@linagora.com>
Authored: Thu Oct 12 10:04:33 2017 +0700
Committer: benwa <btell...@linagora.com>
Committed: Wed Oct 18 09:00:56 2017 +0700

----------------------------------------------------------------------
 .../org/apache/james/jmap/model/Keywords.java   |   6 +
 .../james/jmap/utils/KeywordsCombiner.java      |  65 +++++++++
 .../james/jmap/utils/KeywordsCombinerTest.java  | 132 +++++++++++++++++++
 3 files changed, 203 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/james-project/blob/f0b27714/server/protocols/jmap/src/main/java/org/apache/james/jmap/model/Keywords.java
----------------------------------------------------------------------
diff --git 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/model/Keywords.java 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/model/Keywords.java
index ed07982..c410cf9 100644
--- 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/model/Keywords.java
+++ 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/model/Keywords.java
@@ -19,6 +19,7 @@
 
 package org.apache.james.jmap.model;
 
+import java.util.Arrays;
 import java.util.List;
 import java.util.Map;
 import java.util.Optional;
@@ -86,6 +87,11 @@ public class Keywords {
                 .collect(Guavate.toImmutableSet()));
         }
 
+        public Keywords from(Keyword... keywords) {
+            return fromSet(Arrays.stream(keywords)
+                .collect(Guavate.toImmutableSet()));
+        }
+
         public Keywords fromList(List<String> keywords) {
             return fromSet(keywords.stream()
                 .map(Keyword::new)

http://git-wip-us.apache.org/repos/asf/james-project/blob/f0b27714/server/protocols/jmap/src/main/java/org/apache/james/jmap/utils/KeywordsCombiner.java
----------------------------------------------------------------------
diff --git 
a/server/protocols/jmap/src/main/java/org/apache/james/jmap/utils/KeywordsCombiner.java
 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/utils/KeywordsCombiner.java
new file mode 100644
index 0000000..258f5df
--- /dev/null
+++ 
b/server/protocols/jmap/src/main/java/org/apache/james/jmap/utils/KeywordsCombiner.java
@@ -0,0 +1,65 @@
+/****************************************************************
+ * 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.jmap.utils;
+
+import java.util.List;
+import java.util.Set;
+import java.util.function.BinaryOperator;
+
+import org.apache.james.jmap.model.Keyword;
+import org.apache.james.jmap.model.Keywords;
+
+import com.github.steveash.guavate.Guavate;
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.Sets;
+
+public class KeywordsCombiner implements BinaryOperator<Keywords> {
+    private static final ImmutableList<Keyword> KEYWORD_TO_INTERSECT = 
ImmutableList.of(Keyword.DRAFT);
+    private static final ImmutableList<Keyword> KEYWORD_NOT_TO_UNION = 
KEYWORD_TO_INTERSECT;
+
+    private Keywords.KeywordsFactory keywordsFactory;
+
+    public KeywordsCombiner() {
+        this.keywordsFactory = Keywords.factory()
+            .filterImapNonExposedKeywords();
+    }
+
+    @Override
+    public Keywords apply(Keywords keywords, Keywords keywords2) {
+        return keywordsFactory
+            .fromSet(Sets.union(
+                union(keywords.getKeywords(), keywords2.getKeywords(), 
KEYWORD_NOT_TO_UNION),
+                intersect(keywords.getKeywords(), keywords2.getKeywords(), 
KEYWORD_TO_INTERSECT)));
+    }
+
+    public Set<Keyword> union(Set<Keyword> set1, Set<Keyword> set2, 
List<Keyword> exceptKeywords) {
+        return Sets.union(set1, set2)
+            .stream()
+            .filter(keyword -> !exceptKeywords.contains(keyword))
+            .collect(Guavate.toImmutableSet());
+    }
+
+    public Set<Keyword> intersect(Set<Keyword> set1, Set<Keyword> set2, 
List<Keyword> forKeywords) {
+        return Sets.intersection(set1, set2)
+            .stream()
+            .filter(forKeywords::contains)
+            .collect(Guavate.toImmutableSet());
+    }
+}

http://git-wip-us.apache.org/repos/asf/james-project/blob/f0b27714/server/protocols/jmap/src/test/java/org/apache/james/jmap/utils/KeywordsCombinerTest.java
----------------------------------------------------------------------
diff --git 
a/server/protocols/jmap/src/test/java/org/apache/james/jmap/utils/KeywordsCombinerTest.java
 
b/server/protocols/jmap/src/test/java/org/apache/james/jmap/utils/KeywordsCombinerTest.java
new file mode 100644
index 0000000..df36ab4
--- /dev/null
+++ 
b/server/protocols/jmap/src/test/java/org/apache/james/jmap/utils/KeywordsCombinerTest.java
@@ -0,0 +1,132 @@
+/****************************************************************
+ * 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.jmap.utils;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+import org.apache.james.jmap.model.Keyword;
+import org.apache.james.jmap.model.Keywords;
+import org.apache.james.util.CommutativityChecker;
+import org.junit.Test;
+
+import com.google.common.collect.ImmutableSet;
+
+public class KeywordsCombinerTest {
+
+    public static final Keywords.KeywordsFactory FACTORY = Keywords.factory();
+
+    @Test
+    public void applyShouldUnionSeenKeyword() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        assertThat(keywordsCombiner.apply(
+            Keywords.DEFAULT_VALUE,
+            Keywords.factory().from(Keyword.SEEN)))
+            .isEqualTo(Keywords.factory().from(Keyword.SEEN));
+    }
+
+    @Test
+    public void applyShouldUnionAnsweredKeyword() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        assertThat(keywordsCombiner.apply(
+            Keywords.DEFAULT_VALUE,
+            Keywords.factory().from(Keyword.ANSWERED)))
+            .isEqualTo(Keywords.factory().from(Keyword.ANSWERED));
+    }
+
+    @Test
+    public void applyShouldUnionFlaggedKeyword() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        assertThat(keywordsCombiner.apply(
+            Keywords.DEFAULT_VALUE,
+            Keywords.factory().from(Keyword.FLAGGED)))
+            .isEqualTo(Keywords.factory().from(Keyword.FLAGGED));
+    }
+
+    @Test
+    public void applyShouldIntersectDraftKeyword() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        assertThat(keywordsCombiner.apply(
+            Keywords.DEFAULT_VALUE,
+            Keywords.factory().from(Keyword.DRAFT)))
+            .isEqualTo(Keywords.DEFAULT_VALUE);
+    }
+
+    @Test
+    public void applyShouldUnionCustomKeyword() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        Keyword customKeyword = new Keyword("$Any");
+        assertThat(keywordsCombiner.apply(
+            Keywords.DEFAULT_VALUE,
+            Keywords.factory().from(customKeyword)))
+            .isEqualTo(Keywords.factory().from(customKeyword));
+    }
+
+    @Test
+    public void applyShouldAcceptEmptyAsAZeroValue() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        assertThat(keywordsCombiner.apply(
+            Keywords.DEFAULT_VALUE,
+            Keywords.DEFAULT_VALUE))
+            .isEqualTo(Keywords.DEFAULT_VALUE);
+    }
+
+    @Test
+    public void applyShouldUnionDifferentFlags() {
+        KeywordsCombiner keywordsCombiner = new KeywordsCombiner();
+
+        assertThat(keywordsCombiner.apply(
+            Keywords.factory().from(Keyword.FLAGGED),
+            Keywords.factory().from(Keyword.ANSWERED)))
+            .isEqualTo(Keywords.factory().from(Keyword.FLAGGED, 
Keyword.ANSWERED));
+    }
+
+    @Test
+    public void keywordsCombinerShouldBeCommutative() {
+        Keywords allKeyword = FACTORY.from(Keyword.ANSWERED,
+            Keyword.DELETED,
+            Keyword.DRAFT,
+            Keyword.FLAGGED,
+            Keyword.SEEN,
+            new Keyword("$Forwarded"),
+            new Keyword("$Any"));
+
+        ImmutableSet<Keywords> values = ImmutableSet.of(
+            FACTORY.from(Keyword.ANSWERED),
+            FACTORY.from(Keyword.DELETED),
+            FACTORY.from(Keyword.DRAFT),
+            FACTORY.from(Keyword.FLAGGED),
+            FACTORY.from(Keyword.SEEN),
+            FACTORY.from(),
+            FACTORY.from(new Keyword("$Forwarded")),
+            FACTORY.from(new Keyword("$Any")),
+            allKeyword);
+
+        assertThat(
+            new CommutativityChecker<>(values, new KeywordsCombiner())
+                .findNonCommutativeInput())
+            .isEmpty();
+    }
+}
\ No newline at end of file


---------------------------------------------------------------------
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