You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cxf.apache.org by re...@apache.org on 2014/02/16 17:50:11 UTC

svn commit: r1568790 - in /cxf/trunk/rt/rs/extensions/search/src: main/java/org/apache/cxf/jaxrs/ext/search/ main/java/org/apache/cxf/jaxrs/ext/search/odata/ test/java/org/apache/cxf/jaxrs/ext/search/lucene/

Author: reta
Date: Sun Feb 16 16:50:11 2014
New Revision: 1568790

URL: http://svn.apache.org/r1568790
Log:
[CXF-5430]: Added initial support for OData 2.0 query language. Covered Lucene SearchBean test cases

Added:
    cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/AbstractLuceneQueryVisitorTest.java
    cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorFiqlTest.java
      - copied, changed from r1568765, cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorTest.java
    cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorODataTest.java
Removed:
    cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorTest.java
Modified:
    cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/Beanspector.java
    cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/odata/ODataParser.java

Modified: cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/Beanspector.java
URL: http://svn.apache.org/viewvc/cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/Beanspector.java?rev=1568790&r1=1568789&r2=1568790&view=diff
==============================================================================
--- cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/Beanspector.java (original)
+++ cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/Beanspector.java Sun Feb 16 16:50:11 2014
@@ -23,6 +23,7 @@ import java.lang.reflect.InvocationTarge
 import java.lang.reflect.Method;
 import java.lang.reflect.Type;
 import java.util.Collections;
+import java.util.HashMap;
 import java.util.HashSet;
 import java.util.LinkedHashMap;
 import java.util.Map;
@@ -34,6 +35,7 @@ import org.apache.cxf.jaxrs.ext.search.c
  * Bean introspection utility.
  */
 public class Beanspector<T> {
+    private final Map< Class< ? >, Class< ? > > primitiveWrappers = getPrimitiveWrappers();        
 
     private Class<T> tclass;
     private T tobj;
@@ -105,7 +107,8 @@ public class Beanspector<T> {
                                        setters.keySet(), getters.keySet());
             throw new IntrospectionException(msg);
         }
-        return new TypeInfo(m.getReturnType(), m.getGenericReturnType());
+        return new TypeInfo(m.getReturnType(), m.getGenericReturnType(), 
+            primitiveToWrapper(m.getReturnType()));
     }
 
     public Beanspector<T> swap(T newobject) throws Exception {
@@ -169,6 +172,25 @@ public class Beanspector<T> {
         }
     }
 
+    private Map< Class< ? >, Class< ? > > getPrimitiveWrappers() {
+        final Map< Class< ? >, Class< ? > > wrappers = new HashMap< Class< ? >, Class< ? > >();
+        
+        wrappers.put(boolean.class, Boolean.class);
+        wrappers.put(byte.class, Byte.class);
+        wrappers.put(char.class, Character.class);
+        wrappers.put(short.class, Short.class);
+        wrappers.put(int.class, Integer.class);
+        wrappers.put(long.class, Long.class);
+        wrappers.put(double.class, Double.class);
+        wrappers.put(float.class, Float.class);
+        
+        return wrappers;
+    }
+    
+    private Class< ? > primitiveToWrapper(final Class< ? > cls) {
+        return cls.isPrimitive() ?  primitiveWrappers.get(cls) : cls;
+    }
+    
     private boolean isGetter(Method m) {
         return m.getParameterTypes().length == 0
                && (m.getName().startsWith("get") || m.getName().startsWith("is"));
@@ -195,18 +217,29 @@ public class Beanspector<T> {
     
     public static class TypeInfo {
         private Class<?> cls;
+        // The wrapper class in case cls is a primitive class (byte, long, ...)
+        private Class<?> wrapper; 
         private Type genericType;
         private CollectionCheckInfo checkInfo;
         
         public TypeInfo(Class<?> cls, Type genericType) {
+            this(cls, genericType, cls);
+        }
+        
+        public TypeInfo(Class<?> cls, Type genericType, Class<?> wrapper) {
             this.cls = cls;
             this.genericType = genericType;
+            this.wrapper = wrapper;
         }
         
         public Class<?> getTypeClass() {
             return cls;
         }
         
+        public Class<?> getWrappedTypeClass() {
+            return wrapper;
+        }
+        
         public Type getGenericType() {
             return genericType;
         }

Modified: cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/odata/ODataParser.java
URL: http://svn.apache.org/viewvc/cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/odata/ODataParser.java?rev=1568790&r1=1568789&r2=1568790&view=diff
==============================================================================
--- cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/odata/ODataParser.java (original)
+++ cxf/trunk/rt/rs/extensions/search/src/main/java/org/apache/cxf/jaxrs/ext/search/odata/ODataParser.java Sun Feb 16 16:50:11 2014
@@ -162,7 +162,7 @@ public class ODataParser<T> extends Abst
             
             Object typedValue = null;
             // If property type and value type are compatible, just use them
-            if (property.typeInfo.getTypeClass().isAssignableFrom(value.typeClass)) {
+            if (property.typeInfo.getWrappedTypeClass().isAssignableFrom(value.typeClass)) {
                 typedValue = value.value;
             } else { // Property type and value type are not compatible and convert / cast are required
                 typedValue = parseType(property.propertyName, null, null, property.propertyName, 

Added: cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/AbstractLuceneQueryVisitorTest.java
URL: http://svn.apache.org/viewvc/cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/AbstractLuceneQueryVisitorTest.java?rev=1568790&view=auto
==============================================================================
--- cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/AbstractLuceneQueryVisitorTest.java (added)
+++ cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/AbstractLuceneQueryVisitorTest.java Sun Feb 16 16:50:11 2014
@@ -0,0 +1,165 @@
+/**
+ * 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.cxf.jaxrs.ext.search.lucene;
+
+import java.util.Collections;
+
+import org.apache.cxf.jaxrs.ext.search.SearchBean;
+import org.apache.cxf.jaxrs.ext.search.SearchCondition;
+import org.apache.cxf.jaxrs.ext.search.SearchConditionParser;
+import org.apache.cxf.jaxrs.ext.search.SearchConditionVisitor;
+import org.apache.lucene.analysis.Analyzer;
+import org.apache.lucene.analysis.standard.StandardAnalyzer;
+import org.apache.lucene.document.Document;
+import org.apache.lucene.document.Field;
+import org.apache.lucene.document.IntField;
+import org.apache.lucene.document.TextField;
+import org.apache.lucene.index.DirectoryReader;
+import org.apache.lucene.index.IndexWriter;
+import org.apache.lucene.index.IndexWriterConfig;
+import org.apache.lucene.index.IndexableField;
+import org.apache.lucene.search.IndexSearcher;
+import org.apache.lucene.search.Query;
+import org.apache.lucene.search.ScoreDoc;
+import org.apache.lucene.store.Directory;
+import org.apache.lucene.store.RAMDirectory;
+import org.apache.lucene.util.Version;
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+
+public abstract class AbstractLuceneQueryVisitorTest extends Assert {
+
+    private DirectoryReader ireader;
+    private IndexSearcher isearcher;
+    private Directory directory;
+    private Analyzer analyzer;
+    
+    @Before
+    public void setUp() throws Exception {
+        analyzer = new StandardAnalyzer(Version.LUCENE_40);
+        directory = new RAMDirectory();
+        IndexWriterConfig config = new IndexWriterConfig(Version.LUCENE_40, analyzer);
+        IndexWriter iwriter = new IndexWriter(directory, config);
+        
+        Document doc = new Document();
+        doc.add(new Field("contents", "name=text", TextField.TYPE_STORED));
+        
+        IntField intField = new IntField("intfield", 4, Field.Store.YES);
+        doc.add(intField);
+        iwriter.addDocument(doc);
+        
+        iwriter.close();
+        ireader = DirectoryReader.open(directory);
+        isearcher = new IndexSearcher(ireader);
+    }
+    
+    @After
+    public void tearDown() throws Exception {
+        ireader.close();
+        directory.close();
+    }
+    
+
+    protected abstract SearchConditionParser<SearchBean> getParser();
+ 
+    protected void doTestTextContentMatch(String expression) throws Exception {
+        
+        Query query = createTermQuery("contents", expression);
+        doTestTextContentMatchWithQuery(query);
+            
+    }
+    
+    protected void doTestNoMatch(Query query) throws Exception {
+        ScoreDoc[] hits = isearcher.search(query, null, 1000).scoreDocs;
+        assertEquals(0, hits.length);
+    }
+    
+    protected void doTestTextContentMatchWithQuery(Query query) throws Exception {
+        ScoreDoc[] hits = isearcher.search(query, null, 1000).scoreDocs;
+        assertEquals(1, hits.length);
+        // Iterate through the results:
+        for (int i = 0; i < hits.length; i++) {
+            Document hitDoc = isearcher.doc(hits[i].doc);
+            assertEquals("name=text", hitDoc.get("contents"));
+        }
+            
+    }
+    
+    protected void doTestIntContentMatch(String expression) throws Exception {
+        
+        Query query = createTermQuery("intfield", expression);
+        doTestIntContentMatchWithQuery(query);
+            
+    }
+    
+    protected void doTestIntContentMatchWithQuery(Query query) throws Exception {
+        
+        ScoreDoc[] hits = isearcher.search(query, null, 1000).scoreDocs;
+        assertEquals(1, hits.length);
+        // Iterate through the results:
+        for (int i = 0; i < hits.length; i++) {
+            Document hitDoc = isearcher.doc(hits[i].doc);
+            IndexableField field = hitDoc.getField("intfield");
+            assertEquals(4, field.numericValue().intValue());
+        }
+            
+    }
+    
+    protected Query createTermQuery(String expression) throws Exception {
+        SearchCondition<SearchBean> filter = getParser().parse(expression);
+        SearchConditionVisitor<SearchBean, Query> lucene = new LuceneQueryVisitor<SearchBean>();
+        lucene.visit(filter);
+        return lucene.getQuery();
+    }
+    
+    protected Query createTermQueryWithFieldClass(String expression, Class<?> cls) throws Exception {
+        SearchCondition<SearchBean> filter = getParser().parse(expression);
+        LuceneQueryVisitor<SearchBean> lucene = new LuceneQueryVisitor<SearchBean>();
+        lucene.setPrimitiveFieldTypeMap(Collections.<String, Class<?>>singletonMap("intfield", cls));
+        lucene.visit(filter);
+        return lucene.getQuery();
+    }
+    
+    protected Query createTermQuery(String fieldName, String expression) throws Exception {
+        SearchCondition<SearchBean> filter = getParser().parse(expression);
+        LuceneQueryVisitor<SearchBean> lucene = 
+            new LuceneQueryVisitor<SearchBean>("ct", fieldName);
+        lucene.visit(filter);
+        return lucene.getQuery();
+    }
+    
+    protected Query createTermQueryWithFieldClass(String fieldName, String expression, Class<?> cls) 
+        throws Exception {
+        SearchCondition<SearchBean> filter = getParser().parse(expression);
+        LuceneQueryVisitor<SearchBean> lucene = 
+            new LuceneQueryVisitor<SearchBean>("ct", fieldName);
+        lucene.setPrimitiveFieldTypeMap(Collections.<String, Class<?>>singletonMap(fieldName, cls));
+        lucene.visit(filter);
+        return lucene.getQuery();
+    }
+    
+    protected Query createPhraseQuery(String fieldName, String expression) throws Exception {
+        SearchCondition<SearchBean> filter = getParser().parse(expression);
+        LuceneQueryVisitor<SearchBean> lucene = 
+            new LuceneQueryVisitor<SearchBean>(fieldName);
+        lucene.visit(filter);
+        return lucene.getQuery();
+    }
+}

Copied: cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorFiqlTest.java (from r1568765, cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorTest.java)
URL: http://svn.apache.org/viewvc/cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorFiqlTest.java?p2=cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorFiqlTest.java&p1=cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorTest.java&r1=1568765&r2=1568790&rev=1568790&view=diff
==============================================================================
--- cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorTest.java (original)
+++ cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorFiqlTest.java Sun Feb 16 16:50:11 2014
@@ -18,66 +18,13 @@
  */
 package org.apache.cxf.jaxrs.ext.search.lucene;
 
-import java.util.Collections;
-
 import org.apache.cxf.jaxrs.ext.search.SearchBean;
-import org.apache.cxf.jaxrs.ext.search.SearchCondition;
-import org.apache.cxf.jaxrs.ext.search.SearchConditionVisitor;
+import org.apache.cxf.jaxrs.ext.search.SearchConditionParser;
 import org.apache.cxf.jaxrs.ext.search.fiql.FiqlParser;
-import org.apache.lucene.analysis.Analyzer;
-import org.apache.lucene.analysis.standard.StandardAnalyzer;
-import org.apache.lucene.document.Document;
-import org.apache.lucene.document.Field;
-import org.apache.lucene.document.IntField;
-import org.apache.lucene.document.TextField;
-import org.apache.lucene.index.DirectoryReader;
-import org.apache.lucene.index.IndexWriter;
-import org.apache.lucene.index.IndexWriterConfig;
-import org.apache.lucene.index.IndexableField;
-import org.apache.lucene.search.IndexSearcher;
 import org.apache.lucene.search.Query;
-import org.apache.lucene.search.ScoreDoc;
-import org.apache.lucene.store.Directory;
-import org.apache.lucene.store.RAMDirectory;
-import org.apache.lucene.util.Version;
-
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
 import org.junit.Test;
 
-public class LuceneQueryVisitorTest extends Assert {
-
-    private DirectoryReader ireader;
-    private IndexSearcher isearcher;
-    private Directory directory;
-    private Analyzer analyzer;
-    
-    @Before
-    public void setUp() throws Exception {
-        analyzer = new StandardAnalyzer(Version.LUCENE_40);
-        directory = new RAMDirectory();
-        IndexWriterConfig config = new IndexWriterConfig(Version.LUCENE_40, analyzer);
-        IndexWriter iwriter = new IndexWriter(directory, config);
-        
-        Document doc = new Document();
-        doc.add(new Field("contents", "name=text", TextField.TYPE_STORED));
-        
-        IntField intField = new IntField("intfield", 4, Field.Store.YES);
-        doc.add(intField);
-        iwriter.addDocument(doc);
-        
-        iwriter.close();
-        ireader = DirectoryReader.open(directory);
-        isearcher = new IndexSearcher(ireader);
-    }
-    
-    @After
-    public void tearDown() throws Exception {
-        ireader.close();
-        directory.close();
-    }
-    
+public class LuceneQueryVisitorFiqlTest extends AbstractLuceneQueryVisitorTest {
     @Test
     public void testTextContentMatchEqual() throws Exception {
         
@@ -242,92 +189,8 @@ public class LuceneQueryVisitorTest exte
         doTestTextContentMatchWithQuery(query);
     }
     
-    private void doTestTextContentMatch(String expression) throws Exception {
-        
-        Query query = createTermQuery("contents", expression);
-        doTestTextContentMatchWithQuery(query);
-            
-    }
-    
-    private void doTestNoMatch(Query query) throws Exception {
-        ScoreDoc[] hits = isearcher.search(query, null, 1000).scoreDocs;
-        assertEquals(0, hits.length);
-    }
-    
-    private void doTestTextContentMatchWithQuery(Query query) throws Exception {
-        ScoreDoc[] hits = isearcher.search(query, null, 1000).scoreDocs;
-        assertEquals(1, hits.length);
-        // Iterate through the results:
-        for (int i = 0; i < hits.length; i++) {
-            Document hitDoc = isearcher.doc(hits[i].doc);
-            assertEquals("name=text", hitDoc.get("contents"));
-        }
-            
-    }
-    
-    private void doTestIntContentMatch(String expression) throws Exception {
-        
-        Query query = createTermQuery("intfield", expression);
-        doTestIntContentMatchWithQuery(query);
-            
-    }
-    
-    private void doTestIntContentMatchWithQuery(Query query) throws Exception {
-        
-        ScoreDoc[] hits = isearcher.search(query, null, 1000).scoreDocs;
-        assertEquals(1, hits.length);
-        // Iterate through the results:
-        for (int i = 0; i < hits.length; i++) {
-            Document hitDoc = isearcher.doc(hits[i].doc);
-            IndexableField field = hitDoc.getField("intfield");
-            assertEquals(4, field.numericValue().intValue());
-        }
-            
-    }
-    
-    private Query createTermQuery(String expression) throws Exception {
-        SearchCondition<SearchBean> filter = 
-            new FiqlParser<SearchBean>(SearchBean.class).parse(expression);
-        SearchConditionVisitor<SearchBean, Query> lucene = new LuceneQueryVisitor<SearchBean>();
-        lucene.visit(filter);
-        return lucene.getQuery();
-    }
-    
-    private Query createTermQueryWithFieldClass(String expression, Class<?> cls) throws Exception {
-        SearchCondition<SearchBean> filter = 
-            new FiqlParser<SearchBean>(SearchBean.class).parse(expression);
-        LuceneQueryVisitor<SearchBean> lucene = new LuceneQueryVisitor<SearchBean>();
-        lucene.setPrimitiveFieldTypeMap(Collections.<String, Class<?>>singletonMap("intfield", cls));
-        lucene.visit(filter);
-        return lucene.getQuery();
-    }
-    
-    private Query createTermQuery(String fieldName, String expression) throws Exception {
-        SearchCondition<SearchBean> filter = 
-            new FiqlParser<SearchBean>(SearchBean.class).parse(expression);
-        LuceneQueryVisitor<SearchBean> lucene = 
-            new LuceneQueryVisitor<SearchBean>("ct", fieldName);
-        lucene.visit(filter);
-        return lucene.getQuery();
-    }
-    
-    private Query createTermQueryWithFieldClass(String fieldName, String expression, Class<?> cls) 
-        throws Exception {
-        SearchCondition<SearchBean> filter = 
-            new FiqlParser<SearchBean>(SearchBean.class).parse(expression);
-        LuceneQueryVisitor<SearchBean> lucene = 
-            new LuceneQueryVisitor<SearchBean>("ct", fieldName);
-        lucene.setPrimitiveFieldTypeMap(Collections.<String, Class<?>>singletonMap(fieldName, cls));
-        lucene.visit(filter);
-        return lucene.getQuery();
-    }
-    
-    private Query createPhraseQuery(String fieldName, String expression) throws Exception {
-        SearchCondition<SearchBean> filter = 
-            new FiqlParser<SearchBean>(SearchBean.class).parse(expression);
-        LuceneQueryVisitor<SearchBean> lucene = 
-            new LuceneQueryVisitor<SearchBean>(fieldName);
-        lucene.visit(filter);
-        return lucene.getQuery();
+    @Override
+    protected SearchConditionParser<SearchBean> getParser() {
+        return new FiqlParser<SearchBean>(SearchBean.class);
     }
 }

Added: cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorODataTest.java
URL: http://svn.apache.org/viewvc/cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorODataTest.java?rev=1568790&view=auto
==============================================================================
--- cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorODataTest.java (added)
+++ cxf/trunk/rt/rs/extensions/search/src/test/java/org/apache/cxf/jaxrs/ext/search/lucene/LuceneQueryVisitorODataTest.java Sun Feb 16 16:50:11 2014
@@ -0,0 +1,196 @@
+/**
+ * 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.cxf.jaxrs.ext.search.lucene;
+
+import org.apache.cxf.jaxrs.ext.search.SearchBean;
+import org.apache.cxf.jaxrs.ext.search.SearchConditionParser;
+import org.apache.cxf.jaxrs.ext.search.odata.ODataParser;
+import org.apache.lucene.search.Query;
+import org.junit.Test;
+
+public class LuceneQueryVisitorODataTest extends AbstractLuceneQueryVisitorTest {
+    @Test
+    public void testTextContentMatchEqual() throws Exception {
+        
+        doTestTextContentMatch("ct eq 'text'");
+    }
+    
+    @Test
+    public void testTextContentMatchNotEqual() throws Exception {
+        
+        Query query = createTermQuery("contents", "ct ne 'text'");
+        doTestNoMatch(query);
+            
+    }
+    
+    @Test
+    public void testTextContentMatchNotEqualPositive() throws Exception {
+        
+        Query query = createTermQuery("contents", "ct ne 'bar'");
+        doTestNoMatch(query);
+            
+    }
+    
+    @Test
+    public void testTextContentMatchWildcardEnd() throws Exception {
+        doTestTextContentMatch("ct eq 'tex*'");
+    }
+    
+    @Test
+    public void testTextContentMatchWildcardStart() throws Exception {
+        doTestTextContentMatch("ct eq '*ext'");
+    }
+    
+    @Test
+    public void testIntContentMatchGreater() throws Exception {
+        doTestIntContentMatch("ct gt 3");
+    }
+    
+    @Test
+    public void testIntContentMatchGreaterWithClassFiled() throws Exception {
+        Query query = createTermQueryWithFieldClass("intfield", "ct gt 3", Integer.class);
+        doTestIntContentMatchWithQuery(query);
+    }
+    
+    @Test
+    public void testIntContentMatchGreaterNoMatch() throws Exception {
+        Query query = createTermQuery("intfield", "ct gt 5");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testIntContentMatchGreaterOrEqual() throws Exception {
+        doTestIntContentMatch("ct ge 4");
+        doTestIntContentMatch("ct ge 3");
+    }
+    
+    @Test
+    public void testIntContentMatchGreaterOrEqualNoMatch() throws Exception {
+        Query query = createTermQuery("intfield", "ct ge 5");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testIntContentMatchLess() throws Exception {
+        doTestIntContentMatch("ct lt 5");
+    }
+    
+    @Test
+    public void testIntContentMatchLessNoMatch() throws Exception {
+        Query query = createTermQuery("intfield", "ct lt 3");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testIntContentMatchLessOrEqual() throws Exception {
+        doTestIntContentMatch("ct le 4");
+        doTestIntContentMatch("ct le 5");
+    }
+    
+    @Test
+    public void testIntContentMatchLessOrEqualNoMatch() throws Exception {
+        Query query = createTermQuery("intfield", "ct le 3");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testIntContentMatchEquals() throws Exception {
+        Query query = createTermQueryWithFieldClass("intfield", "ct eq 4", Integer.class);
+        doTestIntContentMatchWithQuery(query);
+    }
+    
+    @Test
+    public void testTextAndContentMatch() throws Exception {
+        Query query = createTermQuery("contents eq 'name' and contents eq 'text'");
+        doTestTextContentMatchWithQuery(query);
+        
+    }
+    
+    @Test
+    public void testTextAndContentNoMatch() throws Exception {
+        Query query = createTermQuery("contents eq 'bar' and contents eq 'text'");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testTextOrContentMatch() throws Exception {
+        Query query = createTermQuery("contents eq 'bar' or contents eq 'text'");
+        doTestTextContentMatchWithQuery(query);
+        
+    }
+    
+    @Test
+    public void testTextOrContentNoMatch() throws Exception {
+        Query query = createTermQuery("contents eq 'bar' or contents eq 'foo'");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testIntAndTextContentMatch() throws Exception {
+        
+        Query query = createTermQueryWithFieldClass("intfield eq 4 and contents eq 'text'", Integer.class);
+        doTestIntContentMatchWithQuery(query);
+        doTestTextContentMatchWithQuery(query);
+        
+    }
+    
+    @Test
+    public void testIntAndTextContentNoMatch() throws Exception {
+        Query query = createTermQuery("intfield eq 3 and contents eq 'text'");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testIntOrTextContentMatch() throws Exception {
+        Query query = createTermQuery("intfield eq 3 or contents eq 'text'");
+        doTestTextContentMatchWithQuery(query);
+        doTestIntContentMatchWithQuery(query);
+        
+    }
+    
+    @Test
+    public void testIntOrTextContentNoMatch() throws Exception {
+        Query query = createTermQuery("intfield eq 3 or contents eq 'bar'");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testTextContentMatchEqualPhrase() throws Exception {
+        Query query = createPhraseQuery("contents", "name eq 'text'");
+        doTestTextContentMatchWithQuery(query);
+    }
+    
+    @Test
+    public void testTextContentMatchNotEqualPhrase() throws Exception {
+        
+        Query query = createPhraseQuery("contents", "name ne 'text'");
+        doTestNoMatch(query);
+    }
+    
+    @Test
+    public void testTextContentMatchEqualPhraseWildcard() throws Exception {
+        Query query = createPhraseQuery("contents", "name eq 'tex*'");
+        doTestTextContentMatchWithQuery(query);
+    }
+    
+    @Override
+    protected SearchConditionParser<SearchBean> getParser() {
+        return new ODataParser<SearchBean>(SearchBean.class);
+    }
+}