This is an automated email from the ASF dual-hosted git repository.

rouazana pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/james-project.git

commit c357bafff687374c8809e28ae5d1354aa3717711
Author: RĂ©mi Kowalski <[email protected]>
AuthorDate: Thu Jul 18 17:23:07 2019 +0200

    JAMES-2813 convert Query to QueryDTO
---
 .../james/vault/dto/query/QueryTranslator.java     |  60 +++++++-
 .../org/apache/james/vault/search/Criterion.java   |   8 ++
 .../java/org/apache/james/vault/search/Query.java  |   4 +
 .../james/vault/dto/query/QueryTranslatorTest.java | 156 ++++++++++++++++++++-
 4 files changed, 217 insertions(+), 11 deletions(-)

diff --git 
a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/dto/query/QueryTranslator.java
 
b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/dto/query/QueryTranslator.java
index 2bd22fc..d76f884 100644
--- 
a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/dto/query/QueryTranslator.java
+++ 
b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/dto/query/QueryTranslator.java
@@ -19,7 +19,6 @@
 
 package org.apache.james.vault.dto.query;
 
-
 import static 
org.apache.james.vault.dto.query.QueryTranslator.FieldValueParser.BOOLEAN_PARSER;
 import static 
org.apache.james.vault.dto.query.QueryTranslator.FieldValueParser.MAIL_ADDRESS_PARSER;
 import static 
org.apache.james.vault.dto.query.QueryTranslator.FieldValueParser.STRING_PARSER;
@@ -32,6 +31,7 @@ import static org.apache.james.vault.search.Operator.EQUALS;
 import static org.apache.james.vault.search.Operator.EQUALS_IGNORE_CASE;
 
 import java.time.ZonedDateTime;
+import java.util.List;
 import java.util.Objects;
 import java.util.Optional;
 import java.util.function.Function;
@@ -123,6 +123,36 @@ public class QueryTranslator {
         T parse(String input);
     }
 
+    interface FieldValueSerializer<T> {
+
+        FieldValueSerializer<MailboxId> MAILBOX_ID_SERIALIZER = 
MailboxId::serialize;
+        FieldValueSerializer<ZonedDateTime> ZONED_DATE_TIME_SERIALIZER = 
ZonedDateTime::toString;
+        FieldValueSerializer<String> STRING_SERIALIZER = input -> input;
+        FieldValueSerializer<Boolean> BOOLEAN_SERIALIZER = input -> 
input.toString();
+        FieldValueSerializer<MailAddress> MAIL_ADDRESS_SERIALIZER = 
MailAddress::asString;
+
+        static Optional<FieldValueSerializer> getSerializerForValue(Object 
value) {
+            if (value instanceof MailboxId) {
+                return Optional.of(MAILBOX_ID_SERIALIZER);
+            }
+            if (value instanceof ZonedDateTime) {
+                return Optional.of(ZONED_DATE_TIME_SERIALIZER);
+            }
+            if (value instanceof String) {
+                return Optional.of(STRING_SERIALIZER);
+            }
+            if (value instanceof Boolean) {
+                return Optional.of(BOOLEAN_SERIALIZER);
+            }
+            if (value instanceof MailAddress) {
+                return Optional.of(MAIL_ADDRESS_SERIALIZER);
+            }
+            return Optional.empty();
+        }
+
+       String serialize(T input);
+    }
+
     private final ImmutableTable<FieldName, Operator, Function<String, 
Criterion<?>>> criterionRegistry;
 
     @Inject
@@ -139,7 +169,7 @@ public class QueryTranslator {
             .build();
     }
 
-    private ImmutableTable.Builder<FieldName, Operator, Function<String, 
Criterion<?>>> defaultRegistryBuilder() {
+     private ImmutableTable.Builder<FieldName, Operator, Function<String, 
Criterion<?>>> defaultRegistryBuilder() {
         return ImmutableTable.<FieldName, Operator, Function<String, 
Criterion<?>>>builder()
             .put(FieldName.DELETION_DATE, BEFORE_OR_EQUALS, testedValue -> 
CriterionFactory.deletionDate().beforeOrEquals(ZONED_DATE_TIME_PARSER.parse(testedValue)))
             .put(FieldName.DELETION_DATE, AFTER_OR_EQUALS, testedValue -> 
CriterionFactory.deletionDate().afterOrEquals(ZONED_DATE_TIME_PARSER.parse(testedValue)))
@@ -161,9 +191,11 @@ public class QueryTranslator {
     }
 
     private Function<String, Criterion<?>> getCriterionParser(CriterionDTO 
dto) {
-        return criterionRegistry.get(
-            getField(dto.getFieldName()),
-            getOperator(dto.getOperator()));
+        return getCriterionParser(getField(dto.getFieldName()), 
getOperator(dto.getOperator()));
+    }
+
+    private Function<String, Criterion<?>> getCriterionParser(FieldName 
fieldName, Operator operator) {
+        return criterionRegistry.get(fieldName, operator);
     }
 
     public Query translate(QueryElement queryElement) throws 
QueryTranslatorException {
@@ -175,6 +207,24 @@ public class QueryTranslator {
         throw new IllegalArgumentException("cannot resolve query type: " + 
queryElement.getClass().getName());
     }
 
+    public QueryDTO toDTO(Query query) throws QueryTranslatorException {
+        List<QueryElement> queryElements = 
query.getCriteria().stream().map(criterion -> {
+            FieldName fieldName = criterion.getField().fieldName();
+            Operator operator = criterion.getValueMatcher().operator();
+            Object value = criterion.getValueMatcher().expectedValue();
+
+            FieldValueSerializer fieldValueSerializer = 
FieldValueSerializer.getSerializerForValue(value).orElseThrow(
+                () -> new IllegalArgumentException("Value of type " + 
value.getClass().getSimpleName()
+                    + "' is not handled by the combinaison of operator : " + 
operator.name()
+                    + " and field :" + fieldName.name())
+            );
+
+            return new CriterionDTO(fieldName.getValue(), operator.getValue(), 
fieldValueSerializer.serialize(value));
+        }).collect(Guavate.toImmutableList());
+
+        return new QueryDTO(Combinator.AND.value, queryElements);
+    }
+
     Query translate(QueryDTO queryDTO) throws QueryTranslatorException {
         
Preconditions.checkArgument(combinatorIsValid(queryDTO.getCombinator()), 
"combinator '" + queryDTO.getCombinator() + "' is not yet handled");
         
Preconditions.checkArgument(queryDTO.getCriteria().stream().allMatch(this::isCriterion),
 "nested query structure is not yet handled");
diff --git 
a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Criterion.java
 
b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Criterion.java
index 770c596..734e407 100644
--- 
a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Criterion.java
+++ 
b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Criterion.java
@@ -75,4 +75,12 @@ public class Criterion<T> {
             .map(valueMatcher::matches)
             .orElse(DEFAULT_TO_NON_MATCHED_IF_NON_EXIST);
     }
+
+    public DeletedMessageField<T> getField() {
+        return field;
+    }
+
+    public ValueMatcher<?, T> getValueMatcher() {
+        return valueMatcher;
+    }
 }
diff --git 
a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Query.java
 
b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Query.java
index ecc9b6c..f73e067 100644
--- 
a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Query.java
+++ 
b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/search/Query.java
@@ -50,4 +50,8 @@ public class Query {
             .reduce(Predicate::and)
             .orElse(MATCH_ALL);
     }
+
+    public List<Criterion<?>> getCriteria() {
+        return criteria;
+    }
 }
diff --git 
a/mailbox/plugin/deleted-messages-vault/src/test/java/org/apache/james/vault/dto/query/QueryTranslatorTest.java
 
b/mailbox/plugin/deleted-messages-vault/src/test/java/org/apache/james/vault/dto/query/QueryTranslatorTest.java
index 37986f7..7360bd8 100644
--- 
a/mailbox/plugin/deleted-messages-vault/src/test/java/org/apache/james/vault/dto/query/QueryTranslatorTest.java
+++ 
b/mailbox/plugin/deleted-messages-vault/src/test/java/org/apache/james/vault/dto/query/QueryTranslatorTest.java
@@ -19,12 +19,19 @@
 
 package org.apache.james.vault.dto.query;
 
+import static org.assertj.core.api.Assertions.assertThat;
 import static org.assertj.core.api.Assertions.assertThatCode;
 import static org.assertj.core.api.Assertions.assertThatThrownBy;
 
+import java.time.ZonedDateTime;
+
+import org.apache.james.core.MailAddress;
 import org.apache.james.mailbox.inmemory.InMemoryId;
+import org.apache.james.mailbox.model.TestId;
+import org.apache.james.vault.search.CriterionFactory;
 import org.apache.james.vault.search.FieldName;
 import org.apache.james.vault.search.Operator;
+import org.apache.james.vault.search.Query;
 import org.junit.jupiter.api.BeforeEach;
 import org.junit.jupiter.api.Test;
 
@@ -56,8 +63,8 @@ class QueryTranslatorTest {
     @Test
     void translateShouldThrowWhenPassingNestedQuery() {
         assertThatThrownBy(() -> queryTranslator.translate(QueryDTO.and(
-                QueryDTO.and(new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS.getValue(), "james"))
-            )))
+            QueryDTO.and(new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS.getValue(), "james"))
+        )))
             .isInstanceOf(IllegalArgumentException.class)
             .hasMessage("nested query structure is not yet handled");
     }
@@ -65,10 +72,147 @@ class QueryTranslatorTest {
     @Test
     void translateShouldNotThrowWhenPassingFlattenQuery() {
         assertThatCode(() -> queryTranslator.translate(QueryDTO.and(
-                new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS.getValue(), "james"),
-                new CriterionDTO(FieldName.SENDER.getValue(), 
Operator.EQUALS.getValue(), "[email protected]"),
-                new CriterionDTO(FieldName.HAS_ATTACHMENT.getValue(), 
Operator.EQUALS.getValue(), "true")
-            )))
+            new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS.getValue(), "james"),
+            new CriterionDTO(FieldName.SENDER.getValue(), 
Operator.EQUALS.getValue(), "[email protected]"),
+            new CriterionDTO(FieldName.HAS_ATTACHMENT.getValue(), 
Operator.EQUALS.getValue(), "true")
+        )))
             .doesNotThrowAnyException();
     }
+
+    @Test
+    void toDTOShouldConvertQueryWithDeletionDateBeforeOrEquals() throws 
Exception{
+        String serializedDate = "2007-12-03T10:15:30+01:00[Europe/Paris]";
+        Query query = Query.of(
+            
CriterionFactory.deletionDate().beforeOrEquals(ZonedDateTime.parse(serializedDate))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.DELETION_DATE.getValue(), 
Operator.BEFORE_OR_EQUALS.getValue(), serializedDate)
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithDeletionDateAfterOrEquals() throws 
Exception{
+        String serializedDate = "2007-12-03T10:15:30+01:00[Europe/Paris]";
+        Query query = Query.of(
+            
CriterionFactory.deletionDate().afterOrEquals(ZonedDateTime.parse(serializedDate))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.DELETION_DATE.getValue(), 
Operator.AFTER_OR_EQUALS.getValue(), serializedDate)
+        ));
+    }
+    @Test
+    void toDTOShouldConvertQueryWithDeliveryDateBeforeOrEquals() throws 
Exception{
+        String serializedDate = "2007-12-03T10:15:30+01:00[Europe/Paris]";
+        Query query = Query.of(
+            
CriterionFactory.deliveryDate().beforeOrEquals(ZonedDateTime.parse(serializedDate))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.DELIVERY_DATE.getValue(), 
Operator.BEFORE_OR_EQUALS.getValue(), serializedDate)
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithDeliveryDateAfterOrEquals() throws 
Exception{
+        String serializedDate = "2007-12-03T10:15:30+01:00[Europe/Paris]";
+        Query query = Query.of(
+            
CriterionFactory.deliveryDate().afterOrEquals(ZonedDateTime.parse(serializedDate))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.DELIVERY_DATE.getValue(), 
Operator.AFTER_OR_EQUALS.getValue(), serializedDate)
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithRecipientsContains() throws Exception{
+        Query query = Query.of(
+            CriterionFactory.containsRecipient(new 
MailAddress("[email protected]"))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.RECIPIENTS.getValue(), 
Operator.CONTAINS.getValue(), "[email protected]")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithSenderEquals() throws Exception{
+        Query query = Query.of(
+            CriterionFactory.hasSender(new MailAddress("[email protected]"))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.SENDER.getValue(), 
Operator.EQUALS.getValue(), "[email protected]")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithHasAttachement() {
+        Query query = Query.of(
+            CriterionFactory.hasAttachment(true)
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.HAS_ATTACHMENT.getValue(), 
Operator.EQUALS.getValue(), "true")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithSubjectEquals() {
+        Query query = Query.of(
+            CriterionFactory.subject().equals("james")
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.EQUALS.getValue(), "james")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithSubjectEqualsIgnoreCase() {
+        Query query = Query.of(
+            CriterionFactory.subject().equalsIgnoreCase("james")
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.EQUALS_IGNORE_CASE.getValue(), "james")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithSubjectContains() {
+        Query query = Query.of(
+            CriterionFactory.subject().contains("james")
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS.getValue(), "james")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithSubjectContainsIgnoreCase() {
+        Query query = Query.of(
+            CriterionFactory.subject().containsIgnoreCase("james")
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS_IGNORE_CASE.getValue(), "james")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertQueryWithContainsOriginMailbox() {
+        Query query = Query.of(
+            CriterionFactory.containsOriginMailbox(TestId.of(1L))
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.ORIGIN_MAILBOXES.getValue(), 
Operator.CONTAINS.getValue(), "1")
+        ));
+    }
+
+    @Test
+    void toDTOShouldConvertFlattenQuery() throws Exception {
+        Query query = Query.of(
+            CriterionFactory.subject().contains("james"),
+            CriterionFactory.hasSender(new MailAddress("[email protected]")),
+            CriterionFactory.hasAttachment(true)
+        );
+        assertThat(queryTranslator.toDTO(query)).isEqualTo(QueryDTO.and(
+            new CriterionDTO(FieldName.SUBJECT.getValue(), 
Operator.CONTAINS.getValue(), "james"),
+            new CriterionDTO(FieldName.SENDER.getValue(), 
Operator.EQUALS.getValue(), "[email protected]"),
+            new CriterionDTO(FieldName.HAS_ATTACHMENT.getValue(), 
Operator.EQUALS.getValue(), "true")
+        ));
+    }
 }
\ No newline at end of file


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to