This is an automated email from the ASF dual-hosted git repository. zhaojinchao pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/shardingsphere.git
The following commit(s) were added to refs/heads/master by this push: new fbbc52c149e Remove FederationSchemaMetaData usage in AdvancedFederationExecutor and OriginalFederationExecutor (#19779) fbbc52c149e is described below commit fbbc52c149e1f146803fb829670188c195cb3b20 Author: Zhengqiang Duan <duanzhengqi...@apache.org> AuthorDate: Tue Aug 2 15:03:56 2022 +0800 Remove FederationSchemaMetaData usage in AdvancedFederationExecutor and OriginalFederationExecutor (#19779) * Remove FederationSchemaMetaData usage in AdvancedFederationExecutor and OriginalFederationExecutor * Remove RelProtoDataType * modify java doc --- .../advanced/AdvancedFederationExecutor.java | 7 ++-- .../original/OriginalFederationExecutor.java | 2 +- .../original/database/FilterableDatabase.java | 19 +++++------ .../executor/original/schema/FilterableSchema.java | 16 +++++----- .../executor/original/table/FilterableTable.java | 25 ++++++++++++--- .../table/FilterableTableScanExecutor.java | 37 ++++++++++++++-------- .../optimizer/ShardingSphereOptimizer.java | 11 +++---- .../optimizer/ShardingSphereOptimizerTest.java | 35 ++++++++++---------- 8 files changed, 90 insertions(+), 62 deletions(-) diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/advanced/AdvancedFederationExecutor.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/advanced/AdvancedFederationExecutor.java index 8512655a30c..d3a0c89e6f7 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/advanced/AdvancedFederationExecutor.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/advanced/AdvancedFederationExecutor.java @@ -49,7 +49,7 @@ import org.apache.shardingsphere.infra.federation.executor.original.table.Filter import org.apache.shardingsphere.infra.federation.optimizer.ShardingSphereOptimizer; import org.apache.shardingsphere.infra.federation.optimizer.context.OptimizerContext; import org.apache.shardingsphere.infra.federation.optimizer.context.planner.OptimizerPlannerContextFactory; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationSchemaMetaData; +import org.apache.shardingsphere.infra.federation.optimizer.planner.QueryOptimizePlannerFactory; import org.apache.shardingsphere.infra.metadata.database.rule.ShardingSphereRuleMetaData; import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereSchema; import org.apache.shardingsphere.sql.parser.sql.common.statement.SQLStatement; @@ -108,8 +108,7 @@ public final class AdvancedFederationExecutor implements FederationExecutor { final JDBCExecutorCallback<? extends ExecuteResult> callback, final FederationContext federationContext) { FilterableTableScanExecutorContext executorContext = new FilterableTableScanExecutorContext(databaseName, schemaName, props, federationContext); FilterableTableScanExecutor executor = new FilterableTableScanExecutor(prepareEngine, jdbcExecutor, callback, optimizerContext, globalRuleMetaData, executorContext, eventBusContext); - FederationSchemaMetaData schemaMetaData = new FederationSchemaMetaData(schemaName, schema.getTables()); - return new FilterableSchema(schemaMetaData, executor); + return new FilterableSchema(schemaName, schema, executor); } @SuppressWarnings("unchecked") @@ -120,7 +119,7 @@ public final class AdvancedFederationExecutor implements FederationExecutor { CalciteCatalogReader catalogReader = OptimizerPlannerContextFactory.createCatalogReader(schemaName, filterableSchema, relDataTypeFactory, connectionConfig); SqlValidator validator = OptimizerPlannerContextFactory.createValidator(catalogReader, relDataTypeFactory, connectionConfig); SqlToRelConverter converter = OptimizerPlannerContextFactory.createConverter(catalogReader, validator, relDataTypeFactory); - RelNode bestPlan = new ShardingSphereOptimizer(optimizerContext, converter).optimize(databaseName, schemaName, sqlStatement); + RelNode bestPlan = new ShardingSphereOptimizer(converter, QueryOptimizePlannerFactory.createHepPlanner()).optimize(sqlStatement); Bindable<Object[]> executablePlan = EnumerableInterpretable.toBindable(Collections.emptyMap(), null, (EnumerableRel) bestPlan, EnumerableRel.Prefer.ARRAY); return executablePlan.bind(new AdvancedExecuteDataContext(validator, converter)); } diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/OriginalFederationExecutor.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/OriginalFederationExecutor.java index cb65c3ef85e..8dc4901bc34 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/OriginalFederationExecutor.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/OriginalFederationExecutor.java @@ -98,7 +98,7 @@ public final class OriginalFederationExecutor implements FederationExecutor { final JDBCExecutorCallback<? extends ExecuteResult> callback, final FederationContext federationContext) throws SQLException { FilterableTableScanExecutorContext executorContext = new FilterableTableScanExecutorContext(databaseName, schemaName, props, federationContext); FilterableTableScanExecutor executor = new FilterableTableScanExecutor(prepareEngine, jdbcExecutor, callback, optimizerContext, globalRuleMetaData, executorContext, eventBusContext); - FilterableDatabase database = new FilterableDatabase(optimizerContext.getFederationMetaData().getDatabase(databaseName), executor); + FilterableDatabase database = new FilterableDatabase(federationContext.getDatabases().get(databaseName.toLowerCase()), executor); // TODO support database.schema.table query when switch to CustomizedFilterableExecutor, calcite jdbc just support schema.table query now connection.getRootSchema().add(schemaName, database.getSubSchema(schemaName)); connection.setSchema(schemaName); diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/database/FilterableDatabase.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/database/FilterableDatabase.java index 5d51705a881..d8101491f26 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/database/FilterableDatabase.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/database/FilterableDatabase.java @@ -22,11 +22,12 @@ import org.apache.calcite.schema.Schema; import org.apache.calcite.schema.impl.AbstractSchema; import org.apache.shardingsphere.infra.federation.executor.original.schema.FilterableSchema; import org.apache.shardingsphere.infra.federation.executor.original.table.FilterableTableScanExecutor; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationDatabaseMetaData; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationSchemaMetaData; +import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereSchema; import java.util.LinkedHashMap; import java.util.Map; +import java.util.Map.Entry; /** * Filterable database. @@ -38,15 +39,15 @@ public final class FilterableDatabase extends AbstractSchema { private final Map<String, Schema> subSchemaMap; - public FilterableDatabase(final FederationDatabaseMetaData databaseMetaData, final FilterableTableScanExecutor executor) { - name = databaseMetaData.getName(); - subSchemaMap = createSubSchemaMap(databaseMetaData, executor); + public FilterableDatabase(final ShardingSphereDatabase database, final FilterableTableScanExecutor executor) { + name = database.getName(); + subSchemaMap = createSubSchemaMap(database, executor); } - private Map<String, Schema> createSubSchemaMap(final FederationDatabaseMetaData databaseMetaData, final FilterableTableScanExecutor executor) { - Map<String, Schema> result = new LinkedHashMap<>(databaseMetaData.getSchemas().size(), 1); - for (FederationSchemaMetaData each : databaseMetaData.getSchemas().values()) { - result.put(each.getName(), new FilterableSchema(each, executor)); + private Map<String, Schema> createSubSchemaMap(final ShardingSphereDatabase database, final FilterableTableScanExecutor executor) { + Map<String, Schema> result = new LinkedHashMap<>(database.getSchemas().size(), 1); + for (Entry<String, ShardingSphereSchema> entry : database.getSchemas().entrySet()) { + result.put(entry.getKey(), new FilterableSchema(entry.getKey(), entry.getValue(), executor)); } return result; } diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/schema/FilterableSchema.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/schema/FilterableSchema.java index ca851972870..c8770be3aac 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/schema/FilterableSchema.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/schema/FilterableSchema.java @@ -23,8 +23,8 @@ import org.apache.calcite.schema.impl.AbstractSchema; import org.apache.shardingsphere.infra.federation.executor.original.table.FederationTableStatistic; import org.apache.shardingsphere.infra.federation.executor.original.table.FilterableTable; import org.apache.shardingsphere.infra.federation.executor.original.table.FilterableTableScanExecutor; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationSchemaMetaData; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationTableMetaData; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereSchema; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereTable; import java.util.LinkedHashMap; import java.util.Map; @@ -39,14 +39,14 @@ public final class FilterableSchema extends AbstractSchema { private final Map<String, Table> tableMap; - public FilterableSchema(final FederationSchemaMetaData schemaMetaData, final FilterableTableScanExecutor executor) { - name = schemaMetaData.getName(); - tableMap = createTableMap(schemaMetaData, executor); + public FilterableSchema(final String schemaName, final ShardingSphereSchema schema, final FilterableTableScanExecutor executor) { + name = schemaName; + tableMap = createTableMap(schema, executor); } - private Map<String, Table> createTableMap(final FederationSchemaMetaData schemaMetaData, final FilterableTableScanExecutor executor) { - Map<String, Table> result = new LinkedHashMap<>(schemaMetaData.getTables().size(), 1); - for (FederationTableMetaData each : schemaMetaData.getTables().values()) { + private Map<String, Table> createTableMap(final ShardingSphereSchema schema, final FilterableTableScanExecutor executor) { + Map<String, Table> result = new LinkedHashMap<>(schema.getTables().size(), 1); + for (ShardingSphereTable each : schema.getTables().values()) { // TODO implement table statistic logic after using custom operators result.put(each.getName(), new FilterableTable(each, executor, new FederationTableStatistic())); } diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTable.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTable.java index aa0fb7b0048..10c7908d812 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTable.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTable.java @@ -19,14 +19,17 @@ package org.apache.shardingsphere.infra.federation.executor.original.table; import lombok.RequiredArgsConstructor; import org.apache.calcite.DataContext; +import org.apache.calcite.avatica.SqlType; import org.apache.calcite.linq4j.Enumerable; import org.apache.calcite.rel.type.RelDataType; import org.apache.calcite.rel.type.RelDataTypeFactory; +import org.apache.calcite.rel.type.RelDataTypeFactory.Builder; import org.apache.calcite.rex.RexNode; import org.apache.calcite.schema.ProjectableFilterableTable; import org.apache.calcite.schema.Statistic; import org.apache.calcite.schema.impl.AbstractTable; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationTableMetaData; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereColumn; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereTable; import java.util.List; @@ -36,7 +39,7 @@ import java.util.List; @RequiredArgsConstructor public final class FilterableTable extends AbstractTable implements ProjectableFilterableTable { - private final FederationTableMetaData metaData; + private final ShardingSphereTable table; private final FilterableTableScanExecutor executor; @@ -44,16 +47,30 @@ public final class FilterableTable extends AbstractTable implements ProjectableF @Override public RelDataType getRowType(final RelDataTypeFactory typeFactory) { - return metaData.getRelProtoDataType().apply(typeFactory); + return createRelDataType(table, typeFactory); } @Override public Enumerable<Object[]> scan(final DataContext root, final List<RexNode> filters, final int[] projects) { - return executor.execute(metaData, new FilterableTableScanContext(root, filters, projects)); + return executor.execute(table, new FilterableTableScanContext(root, filters, projects)); } @Override public Statistic getStatistic() { return statistic; } + + private RelDataType createRelDataType(final ShardingSphereTable table, final RelDataTypeFactory typeFactory) { + Builder fieldInfoBuilder = typeFactory.builder(); + for (ShardingSphereColumn each : table.getColumns().values()) { + fieldInfoBuilder.add(each.getName(), getRelDataType(each, typeFactory)); + } + return fieldInfoBuilder.build(); + } + + private RelDataType getRelDataType(final ShardingSphereColumn column, final RelDataTypeFactory typeFactory) { + Class<?> sqlTypeClass = SqlType.valueOf(column.getDataType()).clazz; + RelDataType javaType = typeFactory.createJavaType(sqlTypeClass); + return typeFactory.createTypeWithNullability(javaType, true); + } } diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTableScanExecutor.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTableScanExecutor.java index dfba55c9652..81a31241847 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTableScanExecutor.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-executor/src/main/java/org/apache/shardingsphere/infra/federation/executor/original/table/FilterableTableScanExecutor.java @@ -19,14 +19,18 @@ package org.apache.shardingsphere.infra.federation.executor.original.table; import lombok.RequiredArgsConstructor; import lombok.SneakyThrows; +import org.apache.calcite.config.CalciteConnectionConfig; +import org.apache.calcite.config.CalciteConnectionConfigImpl; +import org.apache.calcite.jdbc.JavaTypeFactoryImpl; import org.apache.calcite.linq4j.AbstractEnumerable; import org.apache.calcite.linq4j.Enumerable; import org.apache.calcite.linq4j.Enumerator; import org.apache.calcite.plan.RelOptCluster; -import org.apache.calcite.plan.RelOptSchema; +import org.apache.calcite.prepare.CalciteCatalogReader; import org.apache.calcite.rel.RelNode; import org.apache.calcite.rel.core.RelFactories; import org.apache.calcite.rel.rel2sql.RelToSqlConverter; +import org.apache.calcite.rex.RexBuilder; import org.apache.calcite.rex.RexNode; import org.apache.calcite.sql.SqlDialect; import org.apache.calcite.sql.util.SqlString; @@ -37,7 +41,6 @@ import org.apache.shardingsphere.infra.binder.statement.SQLStatementContext; import org.apache.shardingsphere.infra.context.kernel.KernelProcessor; import org.apache.shardingsphere.infra.database.type.DatabaseType; import org.apache.shardingsphere.infra.database.type.DatabaseTypeEngine; -import org.apache.shardingsphere.infra.util.eventbus.EventBusContext; import org.apache.shardingsphere.infra.exception.ShardingSphereException; import org.apache.shardingsphere.infra.executor.kernel.model.ExecutionGroup; import org.apache.shardingsphere.infra.executor.kernel.model.ExecutionGroupContext; @@ -56,13 +59,18 @@ import org.apache.shardingsphere.infra.federation.executor.FederationContext; import org.apache.shardingsphere.infra.federation.executor.original.SQLDialectFactory; import org.apache.shardingsphere.infra.federation.executor.original.row.EmptyRowEnumerator; import org.apache.shardingsphere.infra.federation.executor.original.row.FilterableRowEnumerator; +import org.apache.shardingsphere.infra.federation.executor.original.schema.FilterableSchema; import org.apache.shardingsphere.infra.federation.optimizer.context.OptimizerContext; -import org.apache.shardingsphere.infra.federation.optimizer.metadata.FederationTableMetaData; +import org.apache.shardingsphere.infra.federation.optimizer.context.planner.OptimizerPlannerContextFactory; +import org.apache.shardingsphere.infra.federation.optimizer.planner.QueryOptimizePlannerFactory; import org.apache.shardingsphere.infra.merge.MergeEngine; import org.apache.shardingsphere.infra.merge.result.MergedResult; import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase; import org.apache.shardingsphere.infra.metadata.database.rule.ShardingSphereRuleMetaData; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereSchema; +import org.apache.shardingsphere.infra.metadata.database.schema.decorator.model.ShardingSphereTable; import org.apache.shardingsphere.infra.parser.sql.SQLStatementParserEngine; +import org.apache.shardingsphere.infra.util.eventbus.EventBusContext; import org.apache.shardingsphere.sql.parser.sql.common.statement.SQLStatement; import java.sql.Connection; @@ -100,15 +108,15 @@ public final class FilterableTableScanExecutor { /** * Execute. * - * @param tableMetaData federation table meta data + * @param table table meta data * @param scanContext filterable table scan context * @return query results */ - public Enumerable<Object[]> execute(final FederationTableMetaData tableMetaData, final FilterableTableScanContext scanContext) { + public Enumerable<Object[]> execute(final ShardingSphereTable table, final FilterableTableScanContext scanContext) { String databaseName = executorContext.getDatabaseName(); String schemaName = executorContext.getSchemaName(); DatabaseType databaseType = DatabaseTypeEngine.getTrunkDatabaseType(optimizerContext.getParserContexts().get(databaseName).getDatabaseType().getType()); - SqlString sqlString = createSQLString(tableMetaData, scanContext, SQLDialectFactory.getSQLDialect(databaseType)); + SqlString sqlString = createSQLString(table, scanContext, SQLDialectFactory.getSQLDialect(databaseType)); // TODO replace sql parse with sql convert FederationContext federationContext = executorContext.getFederationContext(); LogicSQL logicSQL = createLogicSQL(federationContext.getDatabases(), sqlString, databaseType); @@ -161,8 +169,8 @@ public final class FilterableTableScanExecutor { return result; } - private SqlString createSQLString(final FederationTableMetaData tableMetaData, final FilterableTableScanContext scanContext, final SqlDialect sqlDialect) { - return new RelToSqlConverter(sqlDialect).visitRoot(createRelNode(tableMetaData, scanContext)).asStatement().toSqlString(sqlDialect); + private SqlString createSQLString(final ShardingSphereTable table, final FilterableTableScanContext scanContext, final SqlDialect sqlDialect) { + return new RelToSqlConverter(sqlDialect).visitRoot(createRelNode(table, scanContext)).asStatement().toSqlString(sqlDialect); } private void setParameters(final Collection<ExecutionGroup<JDBCExecutionUnit>> inputGroups) { @@ -184,14 +192,17 @@ public final class FilterableTableScanExecutor { } } - private RelNode createRelNode(final FederationTableMetaData tableMetaData, final FilterableTableScanContext scanContext) { + private RelNode createRelNode(final ShardingSphereTable table, final FilterableTableScanContext scanContext) { String databaseName = executorContext.getDatabaseName(); String schemaName = executorContext.getSchemaName(); - RelOptCluster relOptCluster = optimizerContext.getPlannerContexts().get(databaseName).getConverters().get(schemaName).getCluster(); - RelOptSchema relOptSchema = (RelOptSchema) optimizerContext.getPlannerContexts().get(databaseName).getValidators().get(schemaName).getCatalogReader(); - RelBuilder builder = RelFactories.LOGICAL_BUILDER.create(relOptCluster, relOptSchema).scan(tableMetaData.getName()).filter(scanContext.getFilters()); + CalciteConnectionConfig connectionConfig = new CalciteConnectionConfigImpl(OptimizerPlannerContextFactory.createConnectionProperties()); + ShardingSphereSchema schema = executorContext.getFederationContext().getDatabases().get(databaseName).getSchema(schemaName); + CalciteCatalogReader catalogReader = OptimizerPlannerContextFactory.createCatalogReader(schemaName, + new FilterableSchema(schemaName, schema, null), new JavaTypeFactoryImpl(), connectionConfig); + RelOptCluster relOptCluster = RelOptCluster.create(QueryOptimizePlannerFactory.createVolcanoPlanner(), new RexBuilder(new JavaTypeFactoryImpl())); + RelBuilder builder = RelFactories.LOGICAL_BUILDER.create(relOptCluster, catalogReader).scan(table.getName()).filter(scanContext.getFilters()); if (null != scanContext.getProjects()) { - builder.project(createProjections(scanContext.getProjects(), builder, tableMetaData.getColumnNames())); + builder.project(createProjections(scanContext.getProjects(), builder, table.getColumnNames())); } return builder.build(); } diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/main/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizer.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/main/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizer.java index 27eac3e72b9..ae1b595981e 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/main/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizer.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/main/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizer.java @@ -24,7 +24,6 @@ import org.apache.calcite.rel.RelNode; import org.apache.calcite.sql.SqlNode; import org.apache.calcite.sql2rel.SqlToRelConverter; import org.apache.shardingsphere.infra.exception.ShardingSphereException; -import org.apache.shardingsphere.infra.federation.optimizer.context.OptimizerContext; import org.apache.shardingsphere.infra.federation.optimizer.converter.SQLNodeConverterEngine; import org.apache.shardingsphere.sql.parser.sql.common.statement.SQLStatement; @@ -34,23 +33,21 @@ import org.apache.shardingsphere.sql.parser.sql.common.statement.SQLStatement; @RequiredArgsConstructor public final class ShardingSphereOptimizer { - private final OptimizerContext context; - private final SqlToRelConverter converter; + private final RelOptPlanner hepPlanner; + /** * Optimize query execution plan. * - * @param databaseName database name - * @param schemaName schema name * @param sqlStatement SQL statement * @return optimized relational node */ - public RelNode optimize(final String databaseName, final String schemaName, final SQLStatement sqlStatement) { + public RelNode optimize(final SQLStatement sqlStatement) { try { SqlNode sqlNode = SQLNodeConverterEngine.convertToSQLNode(sqlStatement); RelNode logicPlan = converter.convertQuery(sqlNode, true, true).rel; - RelNode bestPlan = optimizeWithRBO(logicPlan, context.getPlannerContexts().get(databaseName).getHepPlanners().get(schemaName)); + RelNode bestPlan = optimizeWithRBO(logicPlan, hepPlanner); return optimizeWithCBO(bestPlan, converter); } catch (final UnsupportedOperationException ex) { throw new ShardingSphereException(ex); diff --git a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/test/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizerTest.java b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/test/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizerTest.java index 63f09b94dc9..a36e9667cfe 100644 --- a/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/test/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizerTest.java +++ b/shardingsphere-infra/shardingsphere-infra-federation/shardingsphere-infra-federation-optimizer/src/test/java/org/apache/shardingsphere/infra/federation/optimizer/ShardingSphereOptimizerTest.java @@ -17,10 +17,12 @@ package org.apache.shardingsphere.infra.federation.optimizer; +import org.apache.calcite.sql2rel.SqlToRelConverter; import org.apache.shardingsphere.infra.database.type.DatabaseTypeEngine; import org.apache.shardingsphere.infra.database.type.dialect.H2DatabaseType; import org.apache.shardingsphere.infra.federation.optimizer.context.OptimizerContext; import org.apache.shardingsphere.infra.federation.optimizer.context.OptimizerContextFactory; +import org.apache.shardingsphere.infra.federation.optimizer.planner.QueryOptimizePlannerFactory; import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase; import org.apache.shardingsphere.infra.metadata.database.resource.ShardingSphereResource; import org.apache.shardingsphere.infra.metadata.database.rule.ShardingSphereRuleMetaData; @@ -87,9 +89,9 @@ public final class ShardingSphereOptimizerTest { + "WHERE user_id BETWEEN (SELECT user_id FROM t_user_info WHERE information = 'before') " + "AND (SELECT user_id FROM t_user_info WHERE information = 'after')"; - private final String databaseName = "sharding_db"; + private static final String DATABASE_NAME = "sharding_db"; - private final String schemaName = "federate_jdbc"; + private static final String SCHEMA_NAME = "federate_jdbc"; private final SQLParserRule sqlParserRule = new SQLParserRule(new DefaultSQLParserRuleConfigurationBuilder().build()); @@ -100,10 +102,11 @@ public final class ShardingSphereOptimizerTest { Map<String, ShardingSphereTable> tables = new HashMap<>(2, 1); tables.put("t_order_federate", createOrderTableMetaData()); tables.put("t_user_info", createUserInfoTableMetaData()); - ShardingSphereDatabase database = new ShardingSphereDatabase(databaseName, - new H2DatabaseType(), mockResource(), null, Collections.singletonMap(schemaName, new ShardingSphereSchema(tables))); - OptimizerContext optimizerContext = OptimizerContextFactory.create(Collections.singletonMap(databaseName, database), createGlobalRuleMetaData()); - optimizer = new ShardingSphereOptimizer(optimizerContext, optimizerContext.getPlannerContexts().get(databaseName).getConverters().get(schemaName)); + ShardingSphereDatabase database = new ShardingSphereDatabase(DATABASE_NAME, + new H2DatabaseType(), mockResource(), null, Collections.singletonMap(SCHEMA_NAME, new ShardingSphereSchema(tables))); + OptimizerContext optimizerContext = OptimizerContextFactory.create(Collections.singletonMap(DATABASE_NAME, database), createGlobalRuleMetaData()); + SqlToRelConverter sqlToRelConverter = optimizerContext.getPlannerContexts().get(DATABASE_NAME).getConverters().get(SCHEMA_NAME); + optimizer = new ShardingSphereOptimizer(sqlToRelConverter, QueryOptimizePlannerFactory.createHepPlanner()); } private ShardingSphereRuleMetaData createGlobalRuleMetaData() { @@ -136,7 +139,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectCrossJoinCondition() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_CROSS_JOIN_CONDITION, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..6=[{inputs}], proj#0..1=[{exprs}], user_id0=[$t4])" + LINE_SEPARATOR + " EnumerableHashJoin(condition=[=($3, $6)], joinType=[inner])" + LINE_SEPARATOR + " EnumerableCalc(expr#0..2=[{inputs}], expr#3=[CAST($t1):VARCHAR], proj#0..3=[{exprs}])" + LINE_SEPARATOR @@ -151,7 +154,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectWhereAllFields() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_WHERE_ALL_FIELDS, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..1=[{inputs}], expr#2=[CAST($t0):INTEGER], expr#3=[12], expr#4=[=($t2, $t3)], proj#0..1=[{exprs}], $condition=[$t4])" + LINE_SEPARATOR + " EnumerableTableScan(table=[[federate_jdbc, t_user_info]])" + LINE_SEPARATOR; assertThat(actual, is(expected)); @@ -161,7 +164,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectWhereSingleField() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_WHERE_SINGLE_FIELD, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..1=[{inputs}], expr#2=[CAST($t0):INTEGER], expr#3=[12], expr#4=[=($t2, $t3)], user_id=[$t0], $condition=[$t4])" + LINE_SEPARATOR + " EnumerableTableScan(table=[[federate_jdbc, t_user_info]])" + LINE_SEPARATOR; assertThat(actual, is(expected)); @@ -171,7 +174,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectCrossWhere() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_CROSS_WHERE, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..6=[{inputs}], proj#0..1=[{exprs}], user_id0=[$t4])" + LINE_SEPARATOR + " EnumerableHashJoin(condition=[=($3, $6)], joinType=[inner])" + LINE_SEPARATOR + " EnumerableCalc(expr#0..2=[{inputs}], expr#3=[CAST($t1):VARCHAR], proj#0..3=[{exprs}])" + LINE_SEPARATOR @@ -185,7 +188,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectCrossJoin() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_CROSS_JOIN, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..6=[{inputs}], proj#0..1=[{exprs}], user_id0=[$t4])" + LINE_SEPARATOR + " EnumerableHashJoin(condition=[=($3, $6)], joinType=[inner])" + LINE_SEPARATOR + " EnumerableCalc(expr#0..2=[{inputs}], expr#3=[CAST($t1):VARCHAR], proj#0..3=[{exprs}])" + LINE_SEPARATOR @@ -199,7 +202,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectJoinWhere() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_CROSS_WHERE_CONDITION, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..6=[{inputs}], proj#0..1=[{exprs}], user_id0=[$t4])" + LINE_SEPARATOR + " EnumerableHashJoin(condition=[=($3, $6)], joinType=[inner])" + LINE_SEPARATOR + " EnumerableCalc(expr#0..2=[{inputs}], expr#3=[CAST($t1):VARCHAR], proj#0..3=[{exprs}])" + LINE_SEPARATOR @@ -214,7 +217,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectSubQueryFrom() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_SUBQUERY_FROM, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..1=[{inputs}], expr#2=[CAST($t0):INTEGER], expr#3=[1], expr#4=[>($t2, $t3)], proj#0..1=[{exprs}], $condition=[$t4])" + LINE_SEPARATOR + " EnumerableTableScan(table=[[federate_jdbc, t_user_info]])" + LINE_SEPARATOR; assertThat(actual, is(expected)); @@ -224,7 +227,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectSubQueryWhereExist() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_SUBQUERY_WHERE_EXIST, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..3=[{inputs}], expr#4=[IS NOT NULL($t3)], proj#0..1=[{exprs}], $condition=[$t4])" + LINE_SEPARATOR + " EnumerableCorrelate(correlation=[$cor0], joinType=[left], requiredColumns=[{1}])" + LINE_SEPARATOR + " EnumerableTableScan(table=[[federate_jdbc, t_order_federate]])" + LINE_SEPARATOR @@ -239,7 +242,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectSubQueryWhereIn() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_SUBQUERY_WHERE_IN, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..3=[{inputs}], proj#0..1=[{exprs}])" + LINE_SEPARATOR + " EnumerableHashJoin(condition=[=($1, $3)], joinType=[inner])" + LINE_SEPARATOR + " EnumerableTableScan(table=[[federate_jdbc, t_order_federate]])" + LINE_SEPARATOR @@ -253,7 +256,7 @@ public final class ShardingSphereOptimizerTest { public void assertSelectSubQueryWhereBetween() { ShardingSphereSQLParserEngine sqlParserEngine = sqlParserRule.getSQLParserEngine(DatabaseTypeEngine.getTrunkDatabaseTypeName(new H2DatabaseType())); SQLStatement sqlStatement = sqlParserEngine.parse(SELECT_SUBQUERY_WHERE_BETWEEN, false); - String actual = optimizer.optimize(databaseName, schemaName, sqlStatement).explain(); + String actual = optimizer.optimize(sqlStatement).explain(); String expected = "EnumerableCalc(expr#0..4=[{inputs}], proj#0..1=[{exprs}])" + LINE_SEPARATOR + " EnumerableNestedLoopJoin(condition=[<=($1, $4)], joinType=[inner])" + LINE_SEPARATOR + " EnumerableNestedLoopJoin(condition=[>=($1, $3)], joinType=[inner])" + LINE_SEPARATOR