我需要为Calcite添加一个用户定义的函数,它将一个整数作为参数并返回一个整数.
public class SquareFunction {
public int eval(int a) {
return a*a;
}
}
Run Code Online (Sandbox Code Playgroud)
以及创建模式并添加函数的相关代码
SchemaPlus rootSchema = Frameworks.createRootSchema(false);
rootSchema.add("SQUARE_FUNC",
ScalarFunctionImpl.create(SquareFunction.class,"eval");
Run Code Online (Sandbox Code Playgroud)
但是简单的SQL喜欢
select SQUARE_FUNC(1) from test;
Run Code Online (Sandbox Code Playgroud)
验证期间失败,并显示以下消息:
No match found for function signature SQUARE_FUNC(<NUMERIC>)
Run Code Online (Sandbox Code Playgroud)
堆栈跟踪是:
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:422)
at org.apache.calcite.runtime.Resources$ExInstWithCause.ex(Resources.java:463)
at org.apache.calcite.sql.SqlUtil.newContextException(SqlUtil.java:804)
at org.apache.calcite.sql.SqlUtil.newContextException(SqlUtil.java:789)
at org.apache.calcite.sql.validate.SqlValidatorImpl.newValidationError(SqlValidatorImpl.java:4386)
at org.apache.calcite.sql.validate.SqlValidatorImpl.handleUnresolvedFunction(SqlValidatorImpl.java:1670)
at org.apache.calcite.sql.SqlFunction.deriveType(SqlFunction.java:278)
at org.apache.calcite.sql.SqlFunction.deriveType(SqlFunction.java:223)
at org.apache.calcite.sql.validate.SqlValidatorImpl$DeriveTypeVisitor.visit(SqlValidatorImpl.java:4965)
at org.apache.calcite.sql.validate.SqlValidatorImpl$DeriveTypeVisitor.visit(SqlValidatorImpl.java:1)
at org.apache.calcite.sql.SqlCall.accept(SqlCall.java:137)
at org.apache.calcite.sql.validate.SqlValidatorImpl.deriveTypeImpl(SqlValidatorImpl.java:1586)
at org.apache.calcite.sql.validate.SqlValidatorImpl.deriveType(SqlValidatorImpl.java:1571)
at org.apache.calcite.sql.validate.SqlValidatorImpl.expandSelectItem(SqlValidatorImpl.java:453)
at org.apache.calcite.sql.validate.SqlValidatorImpl.validateSelectList(SqlValidatorImpl.java:3668)
at org.apache.calcite.sql.validate.SqlValidatorImpl.validateSelect(SqlValidatorImpl.java:3186)
at org.apache.calcite.sql.validate.SelectNamespace.validateImpl(SelectNamespace.java:60)
at org.apache.calcite.sql.validate.AbstractNamespace.validate(AbstractNamespace.java:84)
at org.apache.calcite.sql.validate.SqlValidatorImpl.validateNamespace(SqlValidatorImpl.java:937) …
Run Code Online (Sandbox Code Playgroud) 我想在不使用 jdbc 连接的情况下使用 apache calcite api raw。我可以很好地使用 jdbc api,但是在尝试使用 api 时出现空 ptr 异常。到目前为止我所做的是:
package calcite.examples
import java.util.Properties
import calcite.demo.DemoSchema
import org.apache.calcite.DataContext
import org.apache.calcite.config.CalciteConnectionConfigImpl
import org.apache.calcite.jdbc.CalcitePrepare.Query
import org.apache.calcite.jdbc.{CalcitePrepare, CalciteSchema, JavaTypeFactoryImpl}
import org.apache.calcite.prepare.CalcitePrepareImpl
import scala.collection.JavaConverters._
object TryIt extends App
{
val ctx = new AdapterContext
val sql = Query.of[Any]("SELECT * FROM dep")
// assert(sql.rel != null)
val elementType = classOf[Array[Object]]
val prepared = new CalcitePrepareImpl().prepareSql(ctx, sql, elementType, -1)
val enumerable = prepared.enumerable(new MyDataContext)
}
class AdapterContext extends CalcitePrepare.Context
{
private val properties …
Run Code Online (Sandbox Code Playgroud) 我试图建立一个Maven项目,它将包含我想在我的Hive查询中使用的用户定义函数(UDF).我开始使用不包含源文件的Maven项目,以及以下POM:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>exp</groupId>
<artifactId>HiveUdfTestProject</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>jar</packaging>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.7</maven.compiler.source>
<maven.compiler.target>1.7</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>org.apache.hive</groupId>
<artifactId>hive-exec</artifactId>
<version>0.14.0</version>
</dependency>
</dependencies>
</project>
Run Code Online (Sandbox Code Playgroud)
当我尝试构建项目时,出现以下错误:
无法在项目HiveUdfTestProject上执行目标:无法解析项目exp的依赖项:HiveUdfTestProject:jar:1.0-SNAPSHOT:无法解析以下工件:org.apache.calcite:calcite-core:jar:0.9.2-incubating- SNAPSHOT,org.apache.calcite:calcite-avatica:jar:0.9.2-incubating-SNAPSHOT:找不到工件org.apache.calcite:calcite-core:jar:0.9.2-incubating-SNAPSHOT - > [帮助1 ]
我正在实现一个简单的应用程序,它可以更改 SQL 语句中的列名称(并保留表名称)。该语句作为 a 传递String
,修改后的语句也作为 a 返回String
,不涉及数据库连接。
为了实现这一点,我使用 Apache Calcite 的 SQL 解析器。我将 SQL 字符串解析为SqlNode
,接受SqlVisitor
创建重命名的SqlNode
,然后将所有内容写回String
(使用SqlNode.toSqlString()
)。
问题是我不知道如何在SqlNode
接受SqlVisitor
. 两者都表示为SqlIdentifier
, 具有相同的SqlKind
。因此,当SqlVisitor
访问 时SqlIdentifier
,它会重命名它,无论它是列还是表。
private String changeNames(String str) throws SqlParseException {
SqlShuttle visitor = new SqlShuttle() {
private String rename(String str) {
return str + "-test";
}
@Override
public SqlNode visit(SqlIdentifier identifier) {
SqlIdentifier output = new SqlIdentifier(rename(identifier.getSimple()), identifier.getCollation(), …
Run Code Online (Sandbox Code Playgroud) 我正在尝试使用Apache Calcite查询Postgres数据库。我可以通过Calcite JDBC驱动程序细读关于数据库的元数据,因此我绝对可以连接到该数据库,但是无论何时查询表,Calcite始终都会以“未找到表x”作为响应。如果我更改代码以改为使用Hsqldb,则一切正常。下面是代码(根据此Calcite测试用例改编而成:https : //github.com/apache/calcite/blob/master/core/src/test/java/org/apache/calcite/test/MultiJdbcSchemaJoinTest.java)
package org.apache.calcite;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import javax.sql.DataSource;
import org.apache.calcite.adapter.jdbc.JdbcSchema;
import org.apache.calcite.jdbc.CalciteConnection;
import org.apache.calcite.schema.SchemaPlus;
/**
* This class demonstrates Calcite unable to recognize tables in Postgres on
* Mac OS X 10.11.5 with Calcite 1.7.0, Postgres 9.5.2.0 and Java 1.8.0_77.
*
* Before you run this class, you must create the user and database in
* Postgres by executing the following SQL:
*
* create user johnsnow …
Run Code Online (Sandbox Code Playgroud) 我正在使用Apache Calcite来实现分布式OLAP系统,该数据源是RDBMS。所以我想将RelNode
树中的项目/过滤器/聚合推到MyTableScan extends TableScan
。在MyTableScan
,RelBuilder
得到推RelNode
。最后,RelBuilder
生成对源数据库的查询。同时,RelNode
应移动或修改原始树中的项目/过滤器/集合。
据我所知,方解石不支持此功能。
当前的局限性:JDBC适配器当前仅下推表扫描操作。所有其他处理(过滤,联接,聚集等)都在方解石内部进行。我们的目标是尽可能减少对源系统的处理,尽可能地翻译语法,数据类型和内置函数。如果Calcite查询基于单个JDBC数据库中的表,则原则上整个查询应转到该数据库。如果表来自多个JDBC来源,或JDBC和非JDBC的混合,则Calcite将使用它可以使用的最高效的分布式查询方法。
我认为,这RelOptRule
可能是一个不错的选择。不幸的是,当我创建new时RelOptRule
,我不容易找到要删除的父节点。
RelOptRule
是个好选择吗?任何人都有实现此功能的好主意吗?
谢谢。
我正在使用 Calcite 的 SqlParser,但我遇到了 Postgres 查询的一些问题,即PRIMARY
、TIME
、 和ZONE
没有被正确解析。以下代码是我正在使用的代码:
import org.apache.calcite.sql.parser.SqlParser;
import org.apache.calcite.sql.ddl.SqlCreateTable;
SqlParser.Config sqlParserConfig = SqlParser
.configBuilder()
.setParserFactory(SqlDdlParserImpl.FACTORY)
.build();
String sql = "CREATE TABLE \"elements_elementcomponent\" (\"id\" bigserial NOT NULL, \"created_at\" timestamp with time zone NOT NULL, \"updated_at\" timestamp with time zone NOT NULL, \"version\" double precision NOT NULL, \"git_sha\" varchar(60) NOT NULL, \"element_id\" bigint NULL, \"element_item_id\" bigint NULL, \"element_basket_id\" bigint NULL);";
SqlParser parser = SqlParser.create(sql, sqlParserConfig);
SqlCreateTable stmt = (SqlCreateTable) parser.parseQuery();
Run Code Online (Sandbox Code Playgroud)
使用上述关键字会出现以下错误:
org.apache.calcite.sql.parser.SqlParseException: Encountered "PRIMARY" …
Run Code Online (Sandbox Code Playgroud) 我已经阅读了文档,对我来说有点难以掌握应该如何为任何事情编写适配器。我希望通过类似 SQL 的界面让业务人员轻松访问 RESTful Web 服务。
粗略的要求看起来像:
我正在尝试用方解石做一些基本的事情来理解框架。我设置了一个简单的示例,应该从 2 个 json 文件中读取。我的模型看起来像
{
version: '1.0',
defaultSchema: 'PEOPLE',
schemas: [
{
name: 'PEOPLE',
type: 'custom',
factory: 'demo.JsonSchemaFactory',
operand: {
directory: '/..../calcite-json/src/test/resources/files'
}
}
]
}
Run Code Online (Sandbox Code Playgroud)
在我的测试中,模型似乎加载得很好,因为当我提取数据库元数据信息时,我可以看到我的文件正在作为 PEOPLE 模式下的表加载。但是在该语句之后,我尝试select *
从该表中执行操作,但收到一条错误,表示未找到表。
Run Code Online (Sandbox Code Playgroud)> -- null PEOPLE a TABLE --> Jun 29, 2015 8:53:30 AM org.apache.calcite.sql.validate.SqlValidatorException <init> SEVERE: org.apache.calcite.sql.validate.SqlValidatorException: Table 'A' not found Jun 29, 2015 8:53:30 AM org.apache.calcite.runtime.CalciteException <init> SEVERE: org.apache.calcite.runtime.CalciteContextException: At line 1, column 26: Table 'A' not found
输出中的第一行显示数据库元数据“-- null PEOPLE a TABLE -->”中的表。这表明表“a”存在于模式“people”下并且类型为“table”。
我的测试代码如下所示
@Test
public …
Run Code Online (Sandbox Code Playgroud) 如何更改Calcite的默认sql语法,支持这样的sql语句"select func(id)as(a,b,c)from xx;"
我有一个用例,我想知道在SQL
SELECT name, age*5 as intelligence FROM bla WHERE bla=bla
字符串中选择的列,例如,如果SQL是这样的:那么在解析上面的String之后,我只希望输出是:name, intelligence
。
首先,是否可以通过方解石?
也欢迎任何其他选择。
PS:在实际在数据库上运行查询之前,我想知道这一点。
apache-calcite ×11
java ×7
postgresql ×2
sql ×2
sql-parser ×2
adapter ×1
database ×1
hive ×1
jdbc ×1
maven ×1
parsing ×1
rest ×1