You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@chemistry.apache.org by je...@apache.org on 2010/06/14 20:51:25 UTC
svn commit: r954587 [4/4] - in /incubator/chemistry/opencmis/trunk:
chemistry-opencmis-commons/chemistry-opencmis-commons-impl/src/main/java/org/apache/chemistry/opencmis/commons/impl/dataobjects/
chemistry-opencmis-server/chemistry-opencmis-server-inm...
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTestDataCreator.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTestDataCreator.java?rev=954587&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTestDataCreator.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTestDataCreator.java Mon Jun 14 18:51:24 2010
@@ -0,0 +1,279 @@
+/*
+ * 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.chemistry.opencmis.inmemory.query;
+
+import static org.junit.Assert.fail;
+
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.util.ArrayList;
+import java.util.GregorianCalendar;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.TimeZone;
+
+import org.apache.chemistry.opencmis.commons.PropertyIds;
+import org.apache.chemistry.opencmis.commons.data.Acl;
+import org.apache.chemistry.opencmis.commons.data.ContentStream;
+import org.apache.chemistry.opencmis.commons.data.ExtensionsData;
+import org.apache.chemistry.opencmis.commons.data.Properties;
+import org.apache.chemistry.opencmis.commons.data.PropertyData;
+import org.apache.chemistry.opencmis.commons.enums.VersioningState;
+import org.apache.chemistry.opencmis.commons.impl.dataobjects.BindingsObjectFactoryImpl;
+import org.apache.chemistry.opencmis.commons.spi.BindingsObjectFactory;
+import org.apache.chemistry.opencmis.commons.spi.ObjectService;
+import static org.apache.chemistry.opencmis.inmemory.UnitTestTypeSystemCreator.*;
+
+/**
+ * Utility class that fills the in-memory repository with some test objects that
+ * can be used for query
+ *
+ * @author Jens
+ *
+ * This class uses the following data for query testing. We have one document type
+ * "ComplexType" and one folder type "FolderType" The document type has one property of
+ * each of the types boolean, integer, decimal, string and datetime. id, uri and html are
+ * treated like a string and do not make a difference.
+ *
+ * String Int Double DateTime Boolean
+ * ------------------------------------------------
+ * Alpha -100 -1.6E-5 23.05.1618 true
+ * Beta -50 -4.0E24 08.05.1945 false
+ * Gamma 0 3.141592 (now) true
+ * Delta 50 1.23456E-6 20.01.2038 true
+ * Epsilon 100 1.2345E12 14.07.2345 false
+ *
+ * For folder and tree tests this series is put in each of the three test folders
+ */
+public class QueryTestDataCreator {
+
+ private BindingsObjectFactory fFactory = new BindingsObjectFactoryImpl();
+ private String rootFolderId;
+ private String repositoryId;
+ private ObjectService fObjSvc;
+ private String doc1, doc2, doc3, doc4, doc5;
+ private String folder1;
+ private String folder2;
+ private String folder11;
+ private static final TimeZone TZ = TimeZone.getTimeZone("Zulu");
+
+ public QueryTestDataCreator(String repositoryId, String rootFolderId, ObjectService objSvc) {
+ this.rootFolderId = rootFolderId;
+ this.repositoryId = repositoryId;
+ fObjSvc = objSvc;
+ }
+
+ public void createTestData() {
+ createTestFolders();
+ createTestDocuments();
+ }
+
+ @SuppressWarnings("serial")
+ public void createTestDocuments() {
+
+ final GregorianCalendar gc1 = new GregorianCalendar(TZ);
+ gc1.clear();
+ gc1.set(1945, 4, 8);
+
+ final Map<String, Object> propertyMap1 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_STRING, "Alpha");
+ put(PROP_ID_INT, new Integer(-100));
+ put(PROP_ID_DECIMAL, new Double(-4.0E24d));
+ put(PROP_ID_DATETIME, gc1);
+ put(PROP_ID_BOOLEAN, true);
+ }};
+ doc1 = createDocument("alpha", rootFolderId, COMPLEX_TYPE, propertyMap1);
+
+ final GregorianCalendar gc2 = new GregorianCalendar(TZ);
+ gc2.clear();
+ gc2.set(1618, 4, 23);
+
+ final Map<String, Object> propertyMap2 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_STRING, "Beta");
+ put(PROP_ID_INT, new Integer(-50));
+ put(PROP_ID_DECIMAL, new Double(-1.6E-5d));
+ put(PROP_ID_DATETIME, gc2);
+ put(PROP_ID_BOOLEAN, false);
+ }};
+ doc2 = createDocument("beta", rootFolderId, COMPLEX_TYPE, propertyMap2);
+
+ final Map<String, Object> propertyMap3 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_STRING, "Gamma");
+ put(PROP_ID_INT, new Integer(0));
+ put(PROP_ID_DECIMAL, new Double(Math.PI));
+ put(PROP_ID_DATETIME, new GregorianCalendar(TZ));
+ put(PROP_ID_BOOLEAN, true);
+ }};
+ doc3 = createDocument("gamma", rootFolderId, COMPLEX_TYPE, propertyMap3);
+
+ final GregorianCalendar gc4 = new GregorianCalendar(TZ);
+ gc4.clear();
+ gc4.set(2038, 0, 20);
+
+ final Map<String, Object> propertyMap4 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_STRING, "Delta");
+ put(PROP_ID_INT, new Integer(50));
+ put(PROP_ID_DECIMAL, new Double(1.23456E-6));
+ put(PROP_ID_DATETIME, gc4);
+ put(PROP_ID_BOOLEAN, true);
+ }};
+ doc4 = createDocument("delta", rootFolderId, COMPLEX_TYPE, propertyMap4);
+
+ final GregorianCalendar gc5 = new GregorianCalendar(TZ);
+ gc5.clear();
+ gc5.set(2345, 6, 14);
+
+ final Map<String, Object> propertyMap5 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_STRING, "Epsilon");
+ put(PROP_ID_INT, new Integer(100));
+ put(PROP_ID_DECIMAL, new Double(1.2345E12));
+ put(PROP_ID_DATETIME, gc5);
+ put(PROP_ID_BOOLEAN, false);
+ }};
+ doc5 = createDocument("epsilon", rootFolderId, COMPLEX_TYPE, propertyMap5);
+
+}
+
+ @SuppressWarnings("serial")
+ public void createTestFolders() {
+ final Map<String, Object> propertyMap1 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_INT, new Integer(1234));
+ put(PROP_ID_STRING, "ABCD");
+ }};
+ folder1 = createFolder("Folder 1", rootFolderId, FOLDER_TYPE, propertyMap1);
+
+ final Map<String, Object> propertyMap2 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_INT, new Integer(-2345));
+ put(PROP_ID_STRING, "defg");
+ }};
+ folder2 = createFolder("Folder 2", rootFolderId, FOLDER_TYPE, propertyMap2);
+
+ final Map<String, Object> propertyMap3 =
+ new HashMap<String, Object>() {
+ {
+ put(PROP_ID_INT, new Integer(123));
+ put(PROP_ID_STRING, "ZZZZ");
+ }};
+ folder11 = createFolder("Folder 11", folder1, FOLDER_TYPE, propertyMap3);
+ }
+
+
+ private String createFolder(String folderName, String parentFolderId, String typeId, Map<String, Object> properties) {
+ Properties props = createFolderProperties(folderName, typeId, properties);
+ String id = null;
+ try {
+ id = fObjSvc.createFolder(repositoryId, props, parentFolderId, null, null, null, null);
+ if (null == id)
+ fail("createFolder failed.");
+ } catch (Exception e) {
+ fail("createFolder() failed with exception: " + e);
+ }
+ return id;
+ }
+
+ private String createDocument(String name, String folderId, String typeId, Map<String, Object> properties) {
+ ContentStream contentStream = null;
+ List<String> policies = null;
+ Acl addACEs = null;
+ Acl removeACEs = null;
+ ExtensionsData extension = null;
+
+ Properties props = createDocumentProperties(name, typeId, properties);
+
+ String id = null;
+ try {
+ id = fObjSvc.createDocument(repositoryId, props, folderId, contentStream, VersioningState.NONE, policies,
+ addACEs, removeACEs, extension);
+ if (null == id)
+ fail("createDocument failed.");
+ } catch (Exception e) {
+ fail("createDocument() failed with exception: " + e);
+ }
+ return id;
+
+ }
+
+ private Properties createDocumentProperties(String name, String typeId, Map<String, Object> propertyMap) {
+ List<PropertyData<?>> properties = new ArrayList<PropertyData<?>>();
+ properties.add(fFactory.createPropertyIdData(PropertyIds.NAME, name));
+ properties.add(fFactory.createPropertyIdData(PropertyIds.OBJECT_TYPE_ID, typeId));
+ for (Map.Entry<String,Object> propEntry :propertyMap.entrySet()) {
+ PropertyData<?> pd =
+ createPropertyData(propEntry.getKey(), propEntry.getValue());
+ properties.add(pd);
+ }
+ Properties props = fFactory.createPropertiesData(properties);
+ return props;
+ }
+
+ private Properties createFolderProperties(String folderName, String typeId, Map<String, Object> propertyMap) {
+ List<PropertyData<?>> properties = new ArrayList<PropertyData<?>>();
+ properties.add(fFactory.createPropertyIdData(PropertyIds.NAME, folderName));
+ properties.add(fFactory.createPropertyIdData(PropertyIds.OBJECT_TYPE_ID, typeId));
+ for (Map.Entry<String,Object> propEntry :propertyMap.entrySet()) {
+ PropertyData<?> pd =
+ createPropertyData(propEntry.getKey(), propEntry.getValue());
+ properties.add(pd);
+ }
+ Properties props = fFactory.createPropertiesData(properties);
+ return props;
+ }
+
+
+ /**
+ * Simplified property creation method, create Property of Boolean, String, Integer,
+ * Decimal, or DataTime depending on class of value (Boolean, String, Integer, Double,
+ * or GregorianCalendar. Id, Html and URI are not supported
+ *
+ * @param propId
+ * @param value
+ * @return
+ */
+ private PropertyData<?> createPropertyData (String propId, Object value) {
+ Class<?> clazz = value.getClass();
+ if (clazz.equals(Boolean.class)) {
+ return fFactory.createPropertyBooleanData(propId, (Boolean)value);
+ } else if (clazz.equals(Double.class)) {
+ return fFactory.createPropertyDecimalData(propId, BigDecimal.valueOf((Double)value));
+ } else if (clazz.equals(Integer.class)) {
+ return fFactory.createPropertyIntegerData(propId, BigInteger.valueOf((Integer)value));
+ } else if (clazz.equals(String.class)) {
+ return fFactory.createPropertyStringData(propId, (String)value);
+ } else if (clazz.equals(GregorianCalendar.class)) {
+ return fFactory.createPropertyDateTimeData(propId, (GregorianCalendar)value);
+ } else
+ fail("unsupported type in propery value: " + clazz);
+ return null;
+ }
+}
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTypesTest.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTypesTest.java?rev=954587&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTypesTest.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/query/QueryTypesTest.java Mon Jun 14 18:51:24 2010
@@ -0,0 +1,422 @@
+/*
+ * 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.chemistry.opencmis.inmemory.query;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+
+import java.util.List;
+import java.util.Map;
+
+import org.apache.chemistry.opencmis.commons.definitions.TypeDefinition;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisInvalidArgumentException;
+import org.apache.chemistry.opencmis.inmemory.TypeManagerImpl;
+import org.apache.chemistry.opencmis.inmemory.query.CmisQueryWalker;
+import org.apache.chemistry.opencmis.inmemory.query.CmisSelector;
+import org.apache.chemistry.opencmis.inmemory.query.ColumnReference;
+import org.apache.chemistry.opencmis.inmemory.query.QueryObject;
+import org.apache.chemistry.opencmis.inmemory.query.QueryObject.SortSpec;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+public class QueryTypesTest extends AbstractQueryTest {
+
+ private TypeManagerImpl tm;
+
+ @Before
+ public void setUp() throws Exception {
+ tm = new TypeManagerImpl();
+ tm.initTypeSystem(null); // create CMIS default types
+
+ // create some types for testing
+ List<TypeDefinition> typeDefs = super.createTypes();
+ for (TypeDefinition typeDef : typeDefs)
+ tm.addTypeDefinition(typeDef);
+
+ // initialize query object with type manager
+ super.setUp(new QueryObject(tm, null));
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ }
+
+ @Test
+ public void resolveTypesTest1() throws Exception {
+ String statement = "SELECT " + TITLE_PROP + ", " + AUTHOR_PROP + " FROM " + BOOK_TYPE + " AS BooksAlias WHERE " + ISBN_PROP + " = '100'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest2() throws Exception {
+ String statement = "SELECT BookType.Title, BookType.Author FROM BookType WHERE ISBN = '100'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest3() throws Exception {
+ String statement = "SELECT BookType.Title, BookType.Author FROM BookType AS BooksAlias WHERE ISBN = '100'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest4() throws Exception {
+ String statement = "SELECT BooksAlias.Title, BooksAlias.Author FROM BookType AS BooksAlias WHERE ISBN = '100'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest5() throws Exception {
+ String statement = "SELECT BooksAlias.Title AS abc, BooksAlias.Author def FROM BookType AS BooksAlias WHERE ISBN = '100'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest6() throws Exception {
+ String statement = "SELECT BookType.UnknownProperty FROM BookType WHERE ISBN = '100'";
+ try {
+ verifyResolveSelect(statement);
+ fail("Select of unknown property in type should fail.");
+ } catch (Exception e) {
+ assertTrue(e instanceof CmisInvalidArgumentException);
+ assertTrue(e.getMessage().contains("is not a valid property query name in"));
+ }
+ }
+
+ @Test
+ public void resolveTypesTest7() throws Exception {
+ String statement = "SELECT UnknownProperty FROM BookType WHERE ISBN = '100'";
+ try {
+ verifyResolveSelect(statement);
+ fail("Select of unknown property in type should fail.");
+ } catch (Exception e) {
+ assertTrue(e instanceof CmisInvalidArgumentException);
+ assertTrue(e.getMessage().contains("is not a property query name in any"));
+ }
+ }
+
+ @Test
+ public void resolveTypesTest8() throws Exception {
+ String statement = "SELECT BookType.Title, BookType.Author FROM BookType WHERE ISBN = '100'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest9() throws Exception {
+ String statement = "SELECT BookType.Author, Title TitleAlias FROM BookType WHERE TitleAlias <> 'Harry Potter'";
+ verifyResolveSelect(statement);
+ }
+
+ @Test
+ public void resolveTypesTest10() throws Exception {
+ String statement = "SELECT BookType.Author, BookType.Title TitleAlias FROM BookType WHERE TitleAlias <> 'Harry Potter'";
+ verifyResolveSelect(statement);
+ }
+
+ private void verifyResolveSelect(String statement) throws Exception {
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(1 == types.size());
+ List<CmisSelector> selects = qo.getSelectReferences();
+ assertTrue(2 == selects.size());
+ for (CmisSelector select : selects) {
+ assertTrue(select instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) select);
+ assertEquals(bookType, colRef.getTypeDefinition());
+ assertTrue(colRef.getPropertyQueryName().equals(TITLE_PROP) || colRef.getPropertyQueryName().equals(AUTHOR_PROP));
+ }
+ }
+
+ @Test
+ public void resolveTypesWithTwoFromsQualified() throws Exception {
+ String statement = "SELECT BookType.Title, MyDocType.MyStringProp FROM BookType JOIN MyDocType WHERE BookType.ISBN = '100'";
+
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(2 == types.size());
+ List<CmisSelector> selects = qo.getSelectReferences();
+ assertTrue(2 == selects.size());
+
+ ColumnReference colRef = ((ColumnReference) selects.get(0));
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(TITLE_PROP));
+
+ colRef = ((ColumnReference) selects.get(1));
+ assertEquals(colRef.getTypeDefinition(), myType);
+ assertTrue(colRef.getPropertyQueryName().equals(STRING_PROP));
+ }
+
+ @Test
+ public void resolveTypesWithTwoFromsUnqualified() throws Exception {
+ String statement = "SELECT Title, MyStringProp FROM BookType JOIN MyDocType AS MyDocAlias WHERE BookType.ISBN = '100'";
+
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(2 == types.size());
+ List<CmisSelector> selects = qo.getSelectReferences();
+ assertTrue(2 == selects.size());
+
+ ColumnReference colRef = ((ColumnReference) selects.get(0));
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(TITLE_PROP));
+
+ colRef = ((ColumnReference) selects.get(1));
+ assertEquals(colRef.getTypeDefinition(), myType);
+ assertTrue(colRef.getPropertyQueryName().equals(STRING_PROP));
+ }
+
+ @Test
+ public void resolveTypesWithTwoFromsNotUnique() throws Exception {
+ String statement = "SELECT MyStringProp FROM MyDocTypeCopy JOIN MyDocType";
+
+ try {
+ traverseStatement(statement);
+ fail("Select with an unqualified property that is not unique should fail.");
+ } catch (Exception e) {
+ assertTrue(e instanceof CmisInvalidArgumentException);
+ assertTrue(e.getMessage().contains("is not a unique property query name within the types in from"));
+ }
+ }
+
+ @Test
+ public void resolveTypesWithTwoFromsUniqueByQualifying() throws Exception {
+ String statement = "SELECT MyDocType.MyStringProp FROM MyDocTypeCopy JOIN MyDocType";
+
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(2 == types.size());
+ List<CmisSelector> selects = qo.getSelectReferences();
+ assertTrue(1 == selects.size());
+ ColumnReference colRef = ((ColumnReference) selects.get(0));
+ assertEquals(myType, colRef.getTypeDefinition());
+ assertTrue(colRef.getPropertyQueryName().equals(STRING_PROP));
+ }
+
+ @Test
+ public void resolveTypesTest11() throws Exception {
+ String statement = "SELECT BookType.* FROM BookType WHERE ISBN = '100'";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(1 == types.size());
+ List<CmisSelector> selects = qo.getSelectReferences();
+ assertTrue(1 == selects.size());
+ ColumnReference colRef = ((ColumnReference) selects.get(0));
+ assertTrue(colRef.getPropertyQueryName().equals("*"));
+ assertEquals(bookType, colRef.getTypeDefinition());
+ }
+
+ @Test
+ public void resolveTypesTest12() throws Exception {
+ String statement = "SELECT * FROM MyDocTypeCopy JOIN MyDocType";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(2 == types.size());
+ List<CmisSelector> selects = qo.getSelectReferences();
+ assertTrue(1 == selects.size());
+ ColumnReference colRef = ((ColumnReference) selects.get(0));
+ assertTrue(colRef.getPropertyQueryName().equals("*"));
+ assertEquals(null, colRef.getTypeDefinition());
+ }
+
+ @Test
+ public void resolveTypesWhere1() throws Exception {
+ String statement = "SELECT * FROM BookType WHERE ISBN = '100'";
+ verifyResolveWhere(statement);
+ }
+
+ @Test
+ public void resolveTypesWhere2() throws Exception {
+ String statement = "SELECT * FROM BookType WHERE BookType.ISBN = '100'";
+ verifyResolveWhere(statement);
+ }
+
+ @Test
+ public void resolveTypesWhere3() throws Exception {
+ String statement = "SELECT * FROM BookType As BookAlias WHERE BookAlias.ISBN = '100'";
+ verifyResolveWhere(statement);
+ }
+
+ @Test
+ public void resolveTypesWhere4() throws Exception {
+ String statement = "SELECT BookType.ISBN IsbnAlias FROM BookType WHERE IsbnAlias < '100'";
+ verifyResolveWhere(statement);
+ }
+
+ @Test
+ public void resolveTypesWhereWithTwoFromsUnqualified() throws Exception {
+ String statement = "SELECT * FROM BookType JOIN MyDocType WHERE ISBN = '100'";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<CmisSelector> wheres = qo.getWhereReferences();
+ assertTrue(1 == wheres.size());
+ for (CmisSelector where : wheres) {
+ assertTrue(where instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) where);
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(ISBN_PROP));
+ }
+ }
+
+ @Test
+ public void resolveTypesWhereWithTwoFromsQualified() throws Exception {
+ String statement = "SELECT * FROM BookType JOIN MyDocType AS MyDocAlias WHERE BookType.ISBN = '100'";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<CmisSelector> wheres = qo.getWhereReferences();
+ assertTrue(1 == wheres.size());
+ for (CmisSelector where : wheres) {
+ assertTrue(where instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) where);
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(ISBN_PROP));
+ }
+ }
+
+
+ @Test
+ public void resolveTypesWhereWithTwoFromsQualifiedWithAlias() throws Exception {
+ String statement = "SELECT * FROM BookType AS MyBookAlias JOIN MyDocType WHERE MyBookAlias.ISBN = '100'";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<CmisSelector> wheres = qo.getWhereReferences();
+ assertTrue(1 == wheres.size());
+ for (CmisSelector where : wheres) {
+ assertTrue(where instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) where);
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(ISBN_PROP));
+ }
+ }
+
+ private void verifyResolveWhere(String statement) throws Exception {
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ Map<String,String> types = qo.getTypes();
+ assertTrue(1 == types.size());
+ List<CmisSelector> wheres = qo.getWhereReferences();
+ assertTrue(1 == wheres.size());
+ for (CmisSelector where : wheres) {
+ assertTrue(where instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) where);
+ assertEquals(bookType, colRef.getTypeDefinition());
+ assertTrue(colRef.getPropertyQueryName().equals(ISBN_PROP));
+ }
+ }
+
+ @Test
+ public void resolveTypesWhereWithTwoFromsNotUnique() throws Exception {
+ String statement = "SELECT * FROM MyDocTypeCopy JOIN MyDocType WHERE MyStringProp = '100'";
+
+ try {
+ CmisQueryWalker walker = traverseStatement(statement);
+ fail("Select with an unqualified property that is not unique should fail.");
+ } catch (Exception e) {
+ assertTrue(e instanceof CmisInvalidArgumentException);
+ assertTrue(e.getMessage().contains("is not a unique property query name within the types in from"));
+ }
+ }
+
+ @Test
+ public void resolveTypesWhereWithTwoFromsUniqueByQualifying() throws Exception {
+ String statement = "SELECT * FROM MyDocTypeCopy JOIN MyDocType WHERE MyDocType.MyStringProp = '100'";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<CmisSelector> wheres = qo.getWhereReferences();
+ assertTrue(1 == wheres.size());
+ for (CmisSelector where : wheres) {
+ assertTrue(where instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) where);
+ assertEquals(colRef.getTypeDefinition(), myType);
+ assertTrue(colRef.getPropertyQueryName().equals(STRING_PROP));
+ }
+ }
+
+ @Test
+ public void resolveTypesOrderBy() throws Exception {
+ String statement = "SELECT Title AS TitleAlias FROM BookType WHERE Author = 'Jim' ORDER BY TitleAlias";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<SortSpec> sorts = qo.getOrderBys();
+ assertTrue(1 == sorts.size());
+ for (SortSpec sort : sorts) {
+ assertTrue(sort.getSelector() instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) sort.getSelector());
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(TITLE_PROP));
+ }
+ }
+
+ @Test
+ public void resolveTypesOrderBy2() throws Exception {
+ String statement = "SELECT Title AS TitleAlias FROM BookType WHERE Author = 'Jim' ORDER BY BookType.Author";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<SortSpec> sorts = qo.getOrderBys();
+ assertTrue(1 == sorts.size());
+ for (SortSpec sort : sorts) {
+ assertTrue(sort.getSelector() instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) sort.getSelector());
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(AUTHOR_PROP));
+ }
+ }
+
+ @Test
+ public void resolveTypesOrderBy3() throws Exception {
+ String statement = "SELECT Title FROM BookType WHERE ISBN < '100' ORDER BY Author";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<SortSpec> sorts = qo.getOrderBys();
+ assertTrue(1 == sorts.size());
+ for (SortSpec sort : sorts) {
+ assertTrue(sort.getSelector() instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) sort.getSelector());
+ assertEquals(colRef.getTypeDefinition(), bookType);
+ assertTrue(colRef.getPropertyQueryName().equals(AUTHOR_PROP));
+ }
+ }
+
+ @Test
+ public void resolveJoinTypesSimple() throws Exception {
+ String statement = "SELECT * FROM MyDocType JOIN BookType ON MyDocType.MyStringProp = BookType.Title";
+ CmisQueryWalker walker = traverseStatement(statement);
+ QueryObject qo = walker.queryObj;
+ List<CmisSelector> joins = qo.getJoinReferences();
+ assertTrue(2 == joins.size());
+ for (CmisSelector join : joins) {
+ assertTrue(join instanceof ColumnReference);
+ ColumnReference colRef = ((ColumnReference) join);
+ if (myType.equals(colRef.getTypeDefinition())) {
+ assertTrue(colRef.getPropertyQueryName().equals(STRING_PROP));
+ } else if (bookType.equals(colRef.getTypeDefinition())) {
+ assertTrue(colRef.getPropertyQueryName().equals(TITLE_PROP));
+ } else
+ fail("Unexpected type in JOIN reference");
+ }
+ }
+
+}