Search in sources :

Example 1 with TableFunction

use of org.apache.calcite.schema.TableFunction in project calcite by apache.

the class ModelHandler method addFunctions.

/**
 * Creates and validates a {@link ScalarFunctionImpl}, and adds it to a
 * schema. If {@code methodName} is "*", may add more than one function.
 *
 * @param schema Schema to add to
 * @param functionName Name of function; null to derived from method name
 * @param path Path to look for functions
 * @param className Class to inspect for methods that may be user-defined
 *                  functions
 * @param methodName Method name;
 *                  null means use the class as a UDF;
 *                  "*" means add all methods
 * @param upCase Whether to convert method names to upper case, so that they
 *               can be called without using quotes
 */
public static void addFunctions(SchemaPlus schema, String functionName, List<String> path, String className, String methodName, boolean upCase) {
    final Class<?> clazz;
    try {
        clazz = Class.forName(className);
    } catch (ClassNotFoundException e) {
        throw new RuntimeException("UDF class '" + className + "' not found");
    }
    final TableFunction tableFunction = TableFunctionImpl.create(clazz, Util.first(methodName, "eval"));
    if (tableFunction != null) {
        schema.add(functionName, tableFunction);
        return;
    }
    // Must look for TableMacro before ScalarFunction. Both have an "eval"
    // method.
    final TableMacro macro = TableMacroImpl.create(clazz);
    if (macro != null) {
        schema.add(functionName, macro);
        return;
    }
    if (methodName != null && methodName.equals("*")) {
        for (Map.Entry<String, ScalarFunction> entry : ScalarFunctionImpl.createAll(clazz).entries()) {
            String name = entry.getKey();
            if (upCase) {
                name = name.toUpperCase(Locale.ROOT);
            }
            schema.add(name, entry.getValue());
        }
        return;
    } else {
        final ScalarFunction function = ScalarFunctionImpl.create(clazz, Util.first(methodName, "eval"));
        if (function != null) {
            final String name;
            if (functionName != null) {
                name = functionName;
            } else if (upCase) {
                name = methodName.toUpperCase(Locale.ROOT);
            } else {
                name = methodName;
            }
            schema.add(name, function);
            return;
        }
    }
    if (methodName == null) {
        final AggregateFunction aggFunction = AggregateFunctionImpl.create(clazz);
        if (aggFunction != null) {
            schema.add(functionName, aggFunction);
            return;
        }
    }
    throw new RuntimeException("Not a valid function class: " + clazz + ". Scalar functions and table macros have an 'eval' method; " + "aggregate functions have 'init' and 'add' methods, and optionally " + "'initAdd', 'merge' and 'result' methods.");
}
Also used : TableMacro(org.apache.calcite.schema.TableMacro) ScalarFunction(org.apache.calcite.schema.ScalarFunction) AggregateFunction(org.apache.calcite.schema.AggregateFunction) TableFunction(org.apache.calcite.schema.TableFunction) Map(java.util.Map) ImmutableMap(com.google.common.collect.ImmutableMap)

Example 2 with TableFunction

use of org.apache.calcite.schema.TableFunction in project calcite by apache.

the class JdbcTest method adviseSql.

private void adviseSql(String sql, Function<ResultSet, Void> checker) throws ClassNotFoundException, SQLException {
    Properties info = new Properties();
    info.put("lex", "JAVA");
    info.put("quoting", "DOUBLE_QUOTE");
    Connection connection = DriverManager.getConnection("jdbc:calcite:", info);
    CalciteConnection calciteConnection = connection.unwrap(CalciteConnection.class);
    SchemaPlus rootSchema = calciteConnection.getRootSchema();
    rootSchema.add("hr", new ReflectiveSchema(new HrSchema()));
    SchemaPlus schema = rootSchema.add("s", new AbstractSchema());
    calciteConnection.setSchema("hr");
    final TableFunction table = new SqlAdvisorGetHintsFunction();
    schema.add("get_hints", table);
    PreparedStatement ps = connection.prepareStatement("select *\n" + "from table(\"s\".\"get_hints\"(?, ?)) as t(id, names, type)");
    SqlParserUtil.StringAndPos sap = SqlParserUtil.findPos(sql);
    ps.setString(1, sap.sql);
    ps.setInt(2, sap.cursor);
    final ResultSet resultSet = ps.executeQuery();
    checker.apply(resultSet);
    resultSet.close();
    connection.close();
}
Also used : SqlAdvisorGetHintsFunction(org.apache.calcite.sql.advise.SqlAdvisorGetHintsFunction) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection) AvaticaConnection(org.apache.calcite.avatica.AvaticaConnection) Connection(java.sql.Connection) SchemaPlus(org.apache.calcite.schema.SchemaPlus) ReflectiveSchema(org.apache.calcite.adapter.java.ReflectiveSchema) PreparedStatement(java.sql.PreparedStatement) Properties(java.util.Properties) SqlParserUtil(org.apache.calcite.sql.parser.SqlParserUtil) AbstractSchema(org.apache.calcite.schema.impl.AbstractSchema) ResultSet(java.sql.ResultSet) TableFunction(org.apache.calcite.schema.TableFunction) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection)

Example 3 with TableFunction

use of org.apache.calcite.schema.TableFunction in project calcite by apache.

the class TableFunctionTest method testTableFunction.

/**
 * Tests a table function with literal arguments.
 */
@Test
public void testTableFunction() throws SQLException, ClassNotFoundException {
    Connection connection = DriverManager.getConnection("jdbc:calcite:");
    CalciteConnection calciteConnection = connection.unwrap(CalciteConnection.class);
    SchemaPlus rootSchema = calciteConnection.getRootSchema();
    SchemaPlus schema = rootSchema.add("s", new AbstractSchema());
    final TableFunction table = TableFunctionImpl.create(Smalls.GENERATE_STRINGS_METHOD);
    schema.add("GenerateStrings", table);
    ResultSet resultSet = connection.createStatement().executeQuery("select *\n" + "from table(\"s\".\"GenerateStrings\"(5)) as t(n, c)\n" + "where char_length(c) > 3");
    assertThat(CalciteAssert.toString(resultSet), equalTo("N=4; C=abcd\n"));
}
Also used : AbstractSchema(org.apache.calcite.schema.impl.AbstractSchema) Connection(java.sql.Connection) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection) SchemaPlus(org.apache.calcite.schema.SchemaPlus) ResultSet(java.sql.ResultSet) TableFunction(org.apache.calcite.schema.TableFunction) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection) Test(org.junit.Test)

Example 4 with TableFunction

use of org.apache.calcite.schema.TableFunction in project calcite by apache.

the class TableFunctionTest method getConnectionWithMultiplyFunction.

private Connection getConnectionWithMultiplyFunction() throws ClassNotFoundException, SQLException {
    Connection connection = DriverManager.getConnection("jdbc:calcite:");
    CalciteConnection calciteConnection = connection.unwrap(CalciteConnection.class);
    SchemaPlus rootSchema = calciteConnection.getRootSchema();
    SchemaPlus schema = rootSchema.add("s", new AbstractSchema());
    final TableFunction table = TableFunctionImpl.create(Smalls.MULTIPLICATION_TABLE_METHOD);
    schema.add("multiplication", table);
    return connection;
}
Also used : AbstractSchema(org.apache.calcite.schema.impl.AbstractSchema) Connection(java.sql.Connection) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection) SchemaPlus(org.apache.calcite.schema.SchemaPlus) TableFunction(org.apache.calcite.schema.TableFunction) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection)

Example 5 with TableFunction

use of org.apache.calcite.schema.TableFunction in project calcite by apache.

the class TableFunctionTest method testScannableTableFunction.

/**
 * Tests a table function that implements {@link ScannableTable} and returns
 * a single column.
 */
@Test
public void testScannableTableFunction() throws SQLException, ClassNotFoundException {
    Connection connection = DriverManager.getConnection("jdbc:calcite:");
    CalciteConnection calciteConnection = connection.unwrap(CalciteConnection.class);
    SchemaPlus rootSchema = calciteConnection.getRootSchema();
    SchemaPlus schema = rootSchema.add("s", new AbstractSchema());
    final TableFunction table = TableFunctionImpl.create(Smalls.MAZE_METHOD);
    schema.add("Maze", table);
    final String sql = "select *\n" + "from table(\"s\".\"Maze\"(5, 3, 1))";
    ResultSet resultSet = connection.createStatement().executeQuery(sql);
    final String result = "S=abcde\n" + "S=xyz\n" + "S=generate(w=5, h=3, s=1)\n";
    assertThat(CalciteAssert.toString(resultSet), is(result));
}
Also used : AbstractSchema(org.apache.calcite.schema.impl.AbstractSchema) Connection(java.sql.Connection) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection) SchemaPlus(org.apache.calcite.schema.SchemaPlus) ResultSet(java.sql.ResultSet) TableFunction(org.apache.calcite.schema.TableFunction) CoreMatchers.containsString(org.hamcrest.CoreMatchers.containsString) CalciteConnection(org.apache.calcite.jdbc.CalciteConnection) Test(org.junit.Test)

Aggregations

TableFunction (org.apache.calcite.schema.TableFunction)12 Connection (java.sql.Connection)10 CalciteConnection (org.apache.calcite.jdbc.CalciteConnection)10 SchemaPlus (org.apache.calcite.schema.SchemaPlus)10 AbstractSchema (org.apache.calcite.schema.impl.AbstractSchema)9 ResultSet (java.sql.ResultSet)8 Test (org.junit.Test)7 PreparedStatement (java.sql.PreparedStatement)5 CoreMatchers.containsString (org.hamcrest.CoreMatchers.containsString)3 Statement (java.sql.Statement)2 ArrayList (java.util.ArrayList)2 AggregateFunction (org.apache.calcite.schema.AggregateFunction)2 ScalarFunction (org.apache.calcite.schema.ScalarFunction)2 TableMacro (org.apache.calcite.schema.TableMacro)2 SqlUserDefinedTableFunction (org.apache.calcite.sql.validate.SqlUserDefinedTableFunction)2 Ignore (org.junit.Ignore)2 ImmutableMap (com.google.common.collect.ImmutableMap)1 Map (java.util.Map)1 Properties (java.util.Properties)1 JavaTypeFactory (org.apache.calcite.adapter.java.JavaTypeFactory)1