flink calcite 解析sql中的表 java语言实现

从网上看的的一个scala版本的实现,使用java翻译过来的


import org.apache.calcite.config.Lex;
import org.apache.calcite.sql.SqlCall;
import org.apache.calcite.sql.SqlIdentifier;
import org.apache.calcite.sql.SqlInsert;
import org.apache.calcite.sql.SqlJoin;
import org.apache.calcite.sql.SqlNode;
import org.apache.calcite.sql.SqlSelect;
import org.apache.calcite.sql.parser.SqlParser;
import org.apache.calcite.sql.validate.SqlConformance;
import org.apache.flink.configuration.DelegatingConfiguration;
import org.apache.flink.sql.parser.dml.RichSqlInsert;
import org.apache.flink.sql.parser.validate.FlinkSqlConformance;
import org.apache.flink.streaming.api.environment.LocalStreamEnvironment;
import org.apache.flink.streaming.api.environment.StreamExecutionEnvironment;
import org.apache.flink.table.api.*;
import org.apache.flink.table.api.bridge.java.StreamTableEnvironment;
import org.apache.flink.table.api.internal.CatalogTableSchemaResolver;
import org.apache.flink.table.catalog.Catalog;
import org.apache.flink.table.catalog.CatalogManager;
import org.apache.flink.table.catalog.FunctionCatalog;
import org.apache.flink.table.catalog.hive.HiveCatalog;
import org.apache.flink.table.delegation.*;
import org.apache.flink.table.factories.ComponentFactoryService;
import org.apache.flink.table.module.ModuleManager;
import org.apache.flink.table.operations.Operation;
import org.apache.flink.table.operations.ddl.CreateTableOperation;
import org.apache.flink.table.planner.calcite.CalciteConfig;
import org.apache.flink.table.planner.calcite.CalciteConfig$;
import org.apache.flink.table.planner.calcite.CalciteParser;
import org.apache.flink.table.planner.delegation.FlinkSqlParserFactories;
import org.apache.flink.table.planner.utils.JavaScalaConversionUtil;
import org.apache.flink.types.Row;
import org.apache.flink.util.CloseableIterator;
import org.apache.hadoop.hive.ql.parse.ParseException;
import org.apache.hadoop.hive.ql.parse.SemanticException;

import java.lang.reflect.Method;
import java.util.*;
import java.util.stream.Collectors;

public class SQLUtils {

   

    private static void extractTablesInSql(SqlNode sqlNode, Set<String> tables) {
        switch (sqlNode.getKind()) {
            case SELECT:
                extractTablesInSqlSelect((SqlSelect) sqlNode, tables);
                break;
            case INSERT:
                extractTablesInSqlInsert((SqlInsert) sqlNode, tables);
                break;
            default:
                throw new RuntimeException("unknown sql types...");
        }
    }

    private static void extractTablesInSqlInsert(SqlInsert sqlInsert, Set<String> tables) {
        extractSourceTableInSql(sqlInsert, false, tables);
        if (sqlInsert.getTargetTable() instanceof SqlIdentifier) {
            tables.add(((SqlIdentifier) sqlInsert.getTargetTable()).toString().toUpperCase());
        }
    }


    private static void extractTablesInSqlSelect(SqlSelect sqlSelect, Set<String> tables) {
        extractSourceTableInSql(sqlSelect, false, tables);
    }

    private static void extractSourceTableInSql(SqlNode sqlNode, Boolean fromOrJoin, Set<String> tables) {
        if (sqlNode == null) {
            return;
        } else {
            switch (sqlNode.getKind()) {
                case SELECT:
                    SqlSelect selectNode = (SqlSelect) sqlNode;
                    extractSourceTableInSql(selectNode.getFrom(), true, tables);
                    List<SqlNode> selectList = selectNode.getSelectList().getList().stream().
                            filter(t -> t instanceof SqlCall).collect(Collectors.toList());
                    for (SqlNode select : selectList) {
                        extractSourceTableInSql(select, false, tables);
                    }
                    extractSourceTableInSql(selectNode.getWhere(), false, tables);
                    extractSourceTableInSql(selectNode.getHaving(), false, tables);
                    break;
                case JOIN:
                    extractSourceTableInSql(((SqlJoin) sqlNode).getLeft(), true, tables);
                    extractSourceTableInSql(((SqlJoin) sqlNode).getRight(), true, tables);
                    break;
                case AS:
                    if (((SqlCall) sqlNode).operandCount() >= 2) {
                        extractSourceTableInSql(((SqlCall) sqlNode).operand(0), fromOrJoin, tables);
                    }
                    break;
                case IDENTIFIER:
                    //
                    if (fromOrJoin) {
                        tables.add(((SqlIdentifier) sqlNode).toString().toUpperCase());
                    }
                    break;
                default:
                    if (sqlNode instanceof SqlCall) {
                        for (SqlNode node : ((SqlCall) sqlNode).getOperandList()) {
                            extractSourceTableInSql(node, false, tables);
                        }
                    }
            }
        }

    }

    public static CalciteConfig getCalciteConfig(TableConfig tableConfig) {
        return tableConfig.getPlannerConfig().unwrap(CalciteConfig.class).orElse(
                CalciteConfig$.MODULE$.DEFAULT());
    }

    public static CalciteParser getParser() {
        return new CalciteParser(getSqlParserConfig());
    }

    private static SqlParser.Config getSqlParserConfig() {
        return JavaScalaConversionUtil.<SqlParser.Config>toJava(getCalciteConfig(new TableConfig()).getSqlParserConfig()).orElseGet(
                // we use Java lex because back ticks are easier than double quotes in programming
                // and cases are preserved
                () -> {
                    SqlConformance conformance = FlinkSqlConformance.DEFAULT;
                    return SqlParser
                            .configBuilder()
                            .setParserFactory(FlinkSqlParserFactories.create(conformance))
                            .setConformance(conformance)
                            .setLex(Lex.JAVA)
                            .setIdentifierMaxLength(256)
                            .build();
                }
        );
    }

  


    
    private static HiveCatalog getHiveCatalog() {
        String name = "myhive";
        String defaultDatabase = "flink";
        String hiveConfDir = "/etc/hive/conf/"; // a local path
        String version = "1.2.1";
        HiveCatalog hive = new HiveCatalog(name, defaultDatabase, hiveConfDir, version);
        return hive;
    }

  

    private static Planner getPlanner() {
        StreamExecutionEnvironment environment = LocalStreamEnvironment.getExecutionEnvironment();
        Catalog catalog = getHiveCatalog();
        CatalogManager catalogManager = CatalogManager.newBuilder().defaultCatalog("myhive", catalog).
                classLoader(Thread.currentThread().getContextClassLoader()).config(new DelegatingConfiguration()).build();
        catalog.open();
        FunctionCatalog functionCatalog = new FunctionCatalog(new TableConfig(), catalogManager, new ModuleManager());
        //        Parser parser=new ParserImpl(catalogManager,)
        EnvironmentSettings settings = EnvironmentSettings.newInstance()
                .useBlinkPlanner()
                .inStreamingMode()
                .build();
        PlannerFactory plannerFactory = ComponentFactoryService.find(PlannerFactory.class, settings.toPlannerProperties());
        Planner planner = plannerFactory.create(settings.toPlannerProperties(), lookupExecutor(settings.toExecutorProperties(), environment), new TableConfig(),
                functionCatalog, catalogManager);
        catalogManager.setCatalogTableSchemaResolver(new CatalogTableSchemaResolver(planner.getParser(), true));
        return planner;
    }

    private static Executor lookupExecutor(
            Map<String, String> executorProperties,
            StreamExecutionEnvironment executionEnvironment) {
        try {
            ExecutorFactory executorFactory = ComponentFactoryService.find(ExecutorFactory.class, executorProperties);
            Method createMethod = executorFactory.getClass()
                    .getMethod("create", Map.class, StreamExecutionEnvironment.class);

            return (Executor) createMethod.invoke(
                    executorFactory,
                    executorProperties,
                    executionEnvironment);
        } catch (Exception e) {
            throw new TableException(
                    "Could not instantiate the executor. Make sure a planner module is on the classpath",
                    e);
        } 
    }

}

 

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值