package adql.parser;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import java.util.Arrays;
import java.util.Collection;
import org.junit.After;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import adql.db.DBChecker;
import adql.db.DBColumn;
import adql.db.DBTable;
import adql.db.DBType;
import adql.db.DBType.DBDatatype;
import adql.db.DefaultDBColumn;
import adql.db.DefaultDBTable;
import adql.db.FunctionDef;
import adql.query.ADQLQuery;
public class TestUnknownTypes {
@BeforeClass
public static void setUpBeforeClass() throws Exception{}
@AfterClass
public static void tearDownAfterClass() throws Exception{
DBType.DBDatatype.UNKNOWN.setCustomType(null);
}
@Before
public void setUp() throws Exception{}
@After
public void tearDown() throws Exception{}
public void testForFctDef(){
// Test with the return type:
try{
FunctionDef fct = FunctionDef.parse("foo()->aType");
assertTrue(fct.isUnknown());
assertFalse(fct.isString());
assertFalse(fct.isNumeric());
assertFalse(fct.isGeometry());
assertEquals("?aType?", fct.returnType.type.toString());
}catch(Exception ex){
ex.printStackTrace(System.err);
fail("Unknown types MUST be allowed!");
}
// Test with a parameter type:
try{
FunctionDef fct = FunctionDef.parse("foo(param1 aType)");
assertTrue(fct.getParam(0).type.isUnknown());
assertFalse(fct.getParam(0).type.isString());
assertFalse(fct.getParam(0).type.isNumeric());
assertFalse(fct.getParam(0).type.isGeometry());
assertEquals("?aType?", fct.getParam(0).type.toString());
}catch(Exception ex){
ex.printStackTrace(System.err);
fail("Unknown types MUST be allowed!");
}
}
@Test
public void testForColumns(){
final String QUERY_TXT = "SELECT FOO(C1), FOO(C2), FOO(C4), C1, C2, C3, C4 FROM T1";
try{
// Create the parser:
ADQLParser parser = new ADQLParser();
// Create table/column metadata:
DefaultDBTable table1 = new DefaultDBTable("T1");
table1.addColumn(new DefaultDBColumn("C1", table1));
table1.addColumn(new DefaultDBColumn("C2", new DBType(DBDatatype.UNKNOWN), table1));
table1.addColumn(new DefaultDBColumn("C3", new DBType(DBDatatype.VARCHAR), table1));
table1.addColumn(new DefaultDBColumn("C4", new DBType(DBDatatype.UNKNOWN_NUMERIC), table1));
Collection<DBTable> tList = Arrays.asList(new DBTable[]{table1});
// Check the type of the column T1.C1:
DBColumn col = table1.getColumn("C1", true);
assertNotNull(col);
assertNull(col.getDatatype());
// Check the type of the column T1.C2:
col = table1.getColumn("C2", true);
assertNotNull(col);
assertNotNull(col.getDatatype());
assertTrue(col.getDatatype().isUnknown());
assertFalse(col.getDatatype().isNumeric());
assertFalse(col.getDatatype().isString());
assertFalse(col.getDatatype().isGeometry());
assertEquals("UNKNOWN", col.getDatatype().toString());
// Check the type of the column T1.C4:
col = table1.getColumn("C4", true);
assertNotNull(col);
assertNotNull(col.getDatatype());
assertTrue(col.getDatatype().isUnknown());
assertTrue(col.getDatatype().isNumeric());
assertFalse(col.getDatatype().isString());
assertFalse(col.getDatatype().isGeometry());
assertEquals("UNKNOWN_NUMERIC", col.getDatatype().toString());
// Define a UDF, and allow all geometrical functions and coordinate systems:
FunctionDef udf1 = FunctionDef.parse("FOO(x INTEGER) -> INTEGER");
Collection<FunctionDef> udfList = Arrays.asList(new FunctionDef[]{udf1});
Collection<String> geoList = null;
Collection<String> csList = null;
// Create the Query checker:
QueryChecker checker = new DBChecker(tList, udfList, geoList, csList);
// Parse the query:
ADQLQuery pq = parser.parseQuery(QUERY_TXT);
// Check the parsed query:
checker.check(pq);
/* Ensure the type of every ADQLColumn is as expected: */
// isNumeric() = true for FOO(C1), but false for the others
assertTrue(pq.getSelect().get(0).getOperand().isNumeric());
assertFalse(pq.getSelect().get(0).getOperand().isString());
assertFalse(pq.getSelect().get(0).getOperand().isGeometry());
// isNumeric() = true for FOO(C2), but false for the others
assertTrue(pq.getSelect().get(1).getOperand().isNumeric());
assertFalse(pq.getSelect().get(1).getOperand().isString());
assertFalse(pq.getSelect().get(1).getOperand().isGeometry());
// isNumeric() = true for FOO(C4), but false for the others
assertTrue(pq.getSelect().get(2).getOperand().isNumeric());
assertFalse(pq.getSelect().get(2).getOperand().isString());
assertFalse(pq.getSelect().get(2).getOperand().isGeometry());
// isNumeric() = isString() = isGeometry() for C1
assertTrue(pq.getSelect().get(3).getOperand().isNumeric());
assertTrue(pq.getSelect().get(3).getOperand().isString());
assertTrue(pq.getSelect().get(3).getOperand().isGeometry());
// isNumeric() = isString() = isGeometry() for C2
assertTrue(pq.getSelect().get(4).getOperand().isNumeric());
assertTrue(pq.getSelect().get(4).getOperand().isString());
assertTrue(pq.getSelect().get(4).getOperand().isGeometry());
// isString() = true for C3, but false for the others
assertFalse(pq.getSelect().get(5).getOperand().isNumeric());
assertTrue(pq.getSelect().get(5).getOperand().isString());
assertFalse(pq.getSelect().get(5).getOperand().isGeometry());
// isString() = true for C4, but false for the others
assertTrue(pq.getSelect().get(6).getOperand().isNumeric());
assertFalse(pq.getSelect().get(6).getOperand().isString());
assertFalse(pq.getSelect().get(6).getOperand().isGeometry());
}catch(Exception ex){
ex.printStackTrace(System.err);
fail("The construction, configuration and usage of the parser are correct. Nothing should have failed here. (see console for more details)");
}
}
}