You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@shardingsphere.apache.org by pa...@apache.org on 2023/08/08 00:26:24 UTC
[shardingsphere] branch master updated: Remove useless findTableNamesByColumnProjection and simplify code (#27963)
This is an automated email from the ASF dual-hosted git repository.
panjuan 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 17dbb3fe233 Remove useless findTableNamesByColumnProjection and simplify code (#27963)
17dbb3fe233 is described below
commit 17dbb3fe2332c74ab9d937e2daf9d7896bfd0d96
Author: Zhengqiang Duan <du...@apache.org>
AuthorDate: Tue Aug 8 08:26:18 2023 +0800
Remove useless findTableNamesByColumnProjection and simplify code (#27963)
---
.../encrypt/merge/dql/EncryptMergedResult.java | 34 ++--------
.../generator/EncryptProjectionTokenGenerator.java | 79 ++++++++--------------
.../EncryptProjectionTokenGeneratorTest.java | 7 +-
.../mask/merge/dql/MaskAlgorithmMetaData.java | 23 +------
.../mask/merge/dql/MaskAlgorithmMetaDataTest.java | 6 +-
.../engine/type/standard/SubqueryRouteTest.java | 2 +-
.../standard/assertion/ShardingRouteAssert.java | 3 +-
.../context/segment/table/TablesContext.java | 69 -------------------
.../expression/ExpressionSegmentBinder.java | 63 +++++++++++++++++
.../BinaryOperationExpressionBinder.java} | 27 ++++----
.../expression/{ => impl}/ColumnSegmentBinder.java | 2 +-
.../ExistsSubqueryExpressionBinder.java} | 23 +++----
.../InExpressionBinder.java} | 27 ++++----
.../SubqueryExpressionSegmentBinder.java} | 23 +++----
.../{ => impl}/SubquerySegmentBinder.java | 2 +-
.../projection/ProjectionsSegmentBinder.java | 19 ++++--
.../impl/ColumnProjectionSegmentBinder.java | 2 +-
...r.java => SubqueryProjectionSegmentBinder.java} | 30 ++++----
.../WhereSegmentBinder.java} | 26 +++----
.../statement/dml/InsertStatementBinder.java | 2 +-
.../statement/dml/SelectStatementBinder.java | 5 +-
.../context/segment/table/TablesContextTest.java | 59 ----------------
.../resultset/SQLFederationResultSetMetaData.java | 5 +-
.../dml/item/SubqueryProjectionSegment.java | 9 +++
.../prepare/MySQLComStmtPrepareExecutor.java | 9 +--
25 files changed, 220 insertions(+), 336 deletions(-)
diff --git a/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/merge/dql/EncryptMergedResult.java b/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/merge/dql/EncryptMergedResult.java
index 6432674c11a..32724b912c6 100644
--- a/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/merge/dql/EncryptMergedResult.java
+++ b/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/merge/dql/EncryptMergedResult.java
@@ -21,7 +21,6 @@ import lombok.RequiredArgsConstructor;
import org.apache.shardingsphere.encrypt.rule.EncryptRule;
import org.apache.shardingsphere.encrypt.rule.column.EncryptColumn;
import org.apache.shardingsphere.infra.binder.context.segment.select.projection.impl.ColumnProjection;
-import org.apache.shardingsphere.infra.binder.context.segment.table.TablesContext;
import org.apache.shardingsphere.infra.binder.context.statement.dml.SelectStatementContext;
import org.apache.shardingsphere.infra.database.core.type.DatabaseTypeRegistry;
import org.apache.shardingsphere.infra.merge.result.MergedResult;
@@ -31,8 +30,6 @@ import java.io.InputStream;
import java.io.Reader;
import java.sql.SQLException;
import java.util.Calendar;
-import java.util.Collections;
-import java.util.Map;
import java.util.Optional;
/**
@@ -60,33 +57,16 @@ public final class EncryptMergedResult implements MergedResult {
if (!columnProjection.isPresent()) {
return mergedResult.getValue(columnIndex, type);
}
- TablesContext tablesContext = selectStatementContext.getTablesContext();
- String schemaName = tablesContext.getSchemaName().orElseGet(() -> new DatabaseTypeRegistry(selectStatementContext.getDatabaseType()).getDefaultSchemaName(database.getName()));
- ColumnProjection originalColumn = new ColumnProjection(columnProjection.get().getOriginalTable(), columnProjection.get().getOriginalColumn(), null, selectStatementContext.getDatabaseType());
- Map<String, String> expressionTableNames = tablesContext.findTableNamesByColumnProjection(Collections.singletonList(originalColumn), database.getSchema(schemaName));
- Optional<String> tableName = findTableName(originalColumn, expressionTableNames);
- if (!tableName.isPresent()) {
- return mergedResult.getValue(columnIndex, type);
- }
- if (!encryptRule.findEncryptTable(tableName.get()).map(optional -> optional.isEncryptColumn(originalColumn.getName().getValue())).orElse(false)) {
+ String originalTableName = columnProjection.get().getOriginalTable().getValue();
+ String originalColumnName = columnProjection.get().getOriginalColumn().getValue();
+ if (!encryptRule.findEncryptTable(originalTableName).map(optional -> optional.isEncryptColumn(originalColumnName)).orElse(false)) {
return mergedResult.getValue(columnIndex, type);
}
Object cipherValue = mergedResult.getValue(columnIndex, Object.class);
- EncryptColumn encryptColumn = encryptRule.getEncryptTable(tableName.get()).getEncryptColumn(originalColumn.getName().getValue());
- return encryptColumn.getCipher().decrypt(database.getName(), schemaName, tableName.get(), originalColumn.getName().getValue(), cipherValue);
- }
-
- private Optional<String> findTableName(final ColumnProjection columnProjection, final Map<String, String> columnTableNames) {
- String tableName = columnTableNames.get(columnProjection.getExpression());
- if (null != tableName) {
- return Optional.of(tableName);
- }
- for (String each : selectStatementContext.getTablesContext().getTableNames()) {
- if (encryptRule.findEncryptTable(each).map(optional -> optional.isEncryptColumn(columnProjection.getName().getValue())).orElse(false)) {
- return Optional.of(each);
- }
- }
- return Optional.empty();
+ EncryptColumn encryptColumn = encryptRule.getEncryptTable(originalTableName).getEncryptColumn(originalColumnName);
+ String schemaName =
+ selectStatementContext.getTablesContext().getSchemaName().orElseGet(() -> new DatabaseTypeRegistry(selectStatementContext.getDatabaseType()).getDefaultSchemaName(database.getName()));
+ return encryptColumn.getCipher().decrypt(database.getName(), schemaName, originalTableName, originalColumnName, cipherValue);
}
@Override
diff --git a/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGenerator.java b/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGenerator.java
index 9bfdd0879b5..99bfe795eb5 100644
--- a/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGenerator.java
+++ b/features/encrypt/core/src/main/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGenerator.java
@@ -35,10 +35,8 @@ import org.apache.shardingsphere.infra.binder.context.statement.dml.SelectStatem
import org.apache.shardingsphere.infra.database.core.metadata.database.DialectDatabaseMetaData;
import org.apache.shardingsphere.infra.database.core.type.DatabaseType;
import org.apache.shardingsphere.infra.database.core.type.DatabaseTypeRegistry;
-import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereSchema;
import org.apache.shardingsphere.infra.rewrite.sql.token.generator.CollectionSQLTokenGenerator;
import org.apache.shardingsphere.infra.rewrite.sql.token.generator.aware.PreviousSQLTokensAware;
-import org.apache.shardingsphere.infra.rewrite.sql.token.generator.aware.SchemaMetaDataAware;
import org.apache.shardingsphere.infra.rewrite.sql.token.pojo.SQLToken;
import org.apache.shardingsphere.infra.rewrite.sql.token.pojo.generic.SubstitutableColumnNameToken;
import org.apache.shardingsphere.sql.parser.sql.common.enums.SubqueryType;
@@ -48,29 +46,25 @@ import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.Shorthan
import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.OwnerSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.table.JoinTableSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.table.SubqueryTableSegment;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.table.TableSegment;
import org.apache.shardingsphere.sql.parser.sql.common.value.identifier.IdentifierValue;
import java.util.Collection;
import java.util.LinkedHashSet;
import java.util.LinkedList;
import java.util.List;
-import java.util.Map;
import java.util.Optional;
/**
* Projection token generator for encrypt.
*/
@Setter
-public final class EncryptProjectionTokenGenerator implements CollectionSQLTokenGenerator<SQLStatementContext>, PreviousSQLTokensAware, SchemaMetaDataAware, EncryptRuleAware, DatabaseTypeAware {
+public final class EncryptProjectionTokenGenerator implements CollectionSQLTokenGenerator<SQLStatementContext>, PreviousSQLTokensAware, EncryptRuleAware, DatabaseTypeAware {
private List<SQLToken> previousSQLTokens;
private EncryptRule encryptRule;
- private String databaseName;
-
- private Map<String, ShardingSphereSchema> schemas;
-
private DatabaseType databaseType;
@Override
@@ -91,31 +85,37 @@ public final class EncryptProjectionTokenGenerator implements CollectionSQLToken
}
private void addGenerateSQLTokens(final Collection<SQLToken> sqlTokens, final SelectStatementContext selectStatementContext) {
- Map<String, String> columnTableNames = getColumnTableNames(selectStatementContext);
for (ProjectionSegment each : selectStatementContext.getSqlStatement().getProjections().getProjections()) {
SubqueryType subqueryType = selectStatementContext.getSubqueryType();
if (each instanceof ColumnProjectionSegment) {
ColumnProjectionSegment columnSegment = (ColumnProjectionSegment) each;
ColumnProjection columnProjection = buildColumnProjection(columnSegment);
- String tableName = columnTableNames.get(columnProjection.getExpression());
- if (null == tableName) {
- continue;
- }
- Optional<EncryptTable> encryptTable = encryptRule.findEncryptTable(tableName);
- if (encryptTable.isPresent() && encryptTable.get().isEncryptColumn(columnProjection.getName().getValue()) && !containsTableSubquery(selectStatementContext)) {
- sqlTokens.add(generateSQLToken(encryptTable.get().getEncryptColumn(columnProjection.getName().getValue()), columnSegment, columnProjection, subqueryType));
+ String originalColumnName = columnProjection.getOriginalColumn().getValue();
+ Optional<EncryptTable> encryptTable = encryptRule.findEncryptTable(columnProjection.getOriginalTable().getValue());
+ if (encryptTable.isPresent() && encryptTable.get().isEncryptColumn(originalColumnName) && !containsTableSubquery(selectStatementContext.getSqlStatement().getFrom())) {
+ sqlTokens.add(generateSQLToken(encryptTable.get().getEncryptColumn(originalColumnName), columnSegment, columnProjection, subqueryType));
}
}
if (each instanceof ShorthandProjectionSegment) {
ShorthandProjectionSegment shorthandSegment = (ShorthandProjectionSegment) each;
Collection<Projection> actualColumns = getShorthandProjection(shorthandSegment, selectStatementContext.getProjectionsContext()).getActualColumns();
if (!actualColumns.isEmpty()) {
- sqlTokens.add(generateSQLToken(shorthandSegment, actualColumns, selectStatementContext, subqueryType, columnTableNames));
+ sqlTokens.add(generateSQLToken(shorthandSegment, actualColumns, selectStatementContext, subqueryType));
}
}
}
}
+ private boolean containsTableSubquery(final TableSegment tableSegment) {
+ if (tableSegment instanceof SubqueryTableSegment) {
+ return true;
+ } else if (tableSegment instanceof JoinTableSegment) {
+ JoinTableSegment joinTableSegment = (JoinTableSegment) tableSegment;
+ return containsTableSubquery(joinTableSegment.getLeft()) || containsTableSubquery(joinTableSegment.getRight());
+ }
+ return false;
+ }
+
private SubstitutableColumnNameToken generateSQLToken(final EncryptColumn encryptColumn, final ColumnProjectionSegment columnSegment,
final ColumnProjection columnProjection, final SubqueryType subqueryType) {
Collection<Projection> projections = generateProjections(encryptColumn, columnProjection, subqueryType, false, null);
@@ -125,16 +125,19 @@ public final class EncryptProjectionTokenGenerator implements CollectionSQLToken
}
private SubstitutableColumnNameToken generateSQLToken(final ShorthandProjectionSegment segment, final Collection<Projection> actualColumns,
- final SelectStatementContext selectStatementContext, final SubqueryType subqueryType, final Map<String, String> columnTableNames) {
+ final SelectStatementContext selectStatementContext, final SubqueryType subqueryType) {
List<Projection> projections = new LinkedList<>();
for (Projection each : actualColumns) {
- String tableName = columnTableNames.get(each.getExpression());
- Optional<EncryptTable> encryptTable = null == tableName ? Optional.empty() : encryptRule.findEncryptTable(tableName);
- if (!encryptTable.isPresent() || !encryptTable.get().isEncryptColumn(each.getColumnLabel()) || containsTableSubquery(selectStatementContext)) {
+ if (each instanceof ColumnProjection) {
+ Optional<EncryptTable> encryptTable = encryptRule.findEncryptTable(((ColumnProjection) each).getOriginalTable().getValue());
+ if (encryptTable.isPresent() && encryptTable.get().isEncryptColumn(((ColumnProjection) each).getOriginalColumn().getValue())
+ && !containsTableSubquery(selectStatementContext.getSqlStatement().getFrom())) {
+ EncryptColumn encryptColumn = encryptTable.get().getEncryptColumn(((ColumnProjection) each).getName().getValue());
+ projections.addAll(generateProjections(encryptColumn, (ColumnProjection) each, subqueryType, true, segment));
+ continue;
+ }
projections.add(each.getAlias().filter(alias -> !DerivedColumn.isDerivedColumnName(alias.getValue()))
.map(optional -> (Projection) new ColumnProjection(null, optional, null, databaseType)).orElse(each));
- } else if (each instanceof ColumnProjection) {
- projections.addAll(generateProjections(encryptTable.get().getEncryptColumn(((ColumnProjection) each).getName().getValue()), (ColumnProjection) each, subqueryType, true, segment));
}
}
int startIndex = segment.getOwner().isPresent() ? segment.getOwner().get().getStartIndex() : segment.getStartIndex();
@@ -143,34 +146,12 @@ public final class EncryptProjectionTokenGenerator implements CollectionSQLToken
return new SubstitutableColumnNameToken(startIndex, segment.getStopIndex(), projections, dialectDatabaseMetaData.getQuoteCharacter());
}
- private boolean containsTableSubquery(final SelectStatementContext selectStatementContext) {
- if (selectStatementContext.getSqlStatement().getFrom() instanceof SubqueryTableSegment) {
- return true;
- } else if (selectStatementContext.getSqlStatement().getFrom() instanceof JoinTableSegment) {
- JoinTableSegment joinTableSegment = (JoinTableSegment) selectStatementContext.getSqlStatement().getFrom();
- return joinTableSegment.getLeft() instanceof SubqueryTableSegment || joinTableSegment.getRight() instanceof SubqueryTableSegment;
- }
- return false;
- }
-
private ColumnProjection buildColumnProjection(final ColumnProjectionSegment segment) {
IdentifierValue owner = segment.getColumn().getOwner().map(OwnerSegment::getIdentifier).orElse(null);
- return new ColumnProjection(owner, segment.getColumn().getIdentifier(), segment.getAliasName().isPresent() ? segment.getAlias().orElse(null) : null, databaseType);
- }
-
- private Map<String, String> getColumnTableNames(final SelectStatementContext selectStatementContext) {
- Collection<ColumnProjection> columns = new LinkedList<>();
- for (Projection projection : selectStatementContext.getProjectionsContext().getProjections()) {
- if (projection instanceof ColumnProjection) {
- columns.add((ColumnProjection) projection);
- }
- if (projection instanceof ShorthandProjection) {
- columns.addAll(((ShorthandProjection) projection).getColumnProjections());
- }
- }
- String defaultSchema = new DatabaseTypeRegistry(selectStatementContext.getDatabaseType()).getDefaultSchemaName(databaseName);
- ShardingSphereSchema schema = selectStatementContext.getTablesContext().getSchemaName().map(schemas::get).orElseGet(() -> schemas.get(defaultSchema));
- return selectStatementContext.getTablesContext().findTableNamesByColumnProjection(columns, schema);
+ ColumnProjection result = new ColumnProjection(owner, segment.getColumn().getIdentifier(), segment.getAliasName().isPresent() ? segment.getAlias().orElse(null) : null, databaseType);
+ result.setOriginalColumn(segment.getColumn().getOriginalColumn());
+ result.setOriginalTable(segment.getColumn().getOriginalTable());
+ return result;
}
private Collection<Projection> generateProjections(final EncryptColumn encryptColumn, final ColumnProjection column,
diff --git a/features/encrypt/core/src/test/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGeneratorTest.java b/features/encrypt/core/src/test/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGeneratorTest.java
index 1180ccb294f..fe4e21962d3 100644
--- a/features/encrypt/core/src/test/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGeneratorTest.java
+++ b/features/encrypt/core/src/test/java/org/apache/shardingsphere/encrypt/rewrite/token/generator/EncryptProjectionTokenGeneratorTest.java
@@ -24,7 +24,6 @@ import org.apache.shardingsphere.infra.binder.context.segment.select.projection.
import org.apache.shardingsphere.infra.binder.context.segment.table.TablesContext;
import org.apache.shardingsphere.infra.binder.context.statement.dml.SelectStatementContext;
import org.apache.shardingsphere.infra.database.core.type.DatabaseType;
-import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereSchema;
import org.apache.shardingsphere.infra.rewrite.sql.token.pojo.SQLToken;
import org.apache.shardingsphere.infra.spi.type.typed.TypedSPILoader;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.column.ColumnSegment;
@@ -58,8 +57,6 @@ class EncryptProjectionTokenGeneratorTest {
@BeforeEach
void setup() {
generator.setEncryptRule(mockEncryptRule());
- generator.setDatabaseName("db_schema");
- generator.setSchemas(Collections.singletonMap("test", mock(ShardingSphereSchema.class)));
}
private EncryptRule mockEncryptRule() {
@@ -82,6 +79,8 @@ class EncryptProjectionTokenGeneratorTest {
SimpleTableSegment doctorTable = new SimpleTableSegment(new TableNameSegment(0, 0, new IdentifierValue("doctor")));
doctorTable.setAlias(new AliasSegment(0, 0, new IdentifierValue("a")));
ColumnSegment column = new ColumnSegment(0, 0, new IdentifierValue("mobile"));
+ column.setOriginalColumn(new IdentifierValue("mobile"));
+ column.setOriginalTable(new IdentifierValue("doctor"));
column.setOwner(new OwnerSegment(0, 0, new IdentifierValue("a")));
ProjectionsSegment projections = mock(ProjectionsSegment.class);
when(projections.getProjections()).thenReturn(Collections.singletonList(new ColumnProjectionSegment(column)));
@@ -101,6 +100,8 @@ class EncryptProjectionTokenGeneratorTest {
SimpleTableSegment doctorTable = new SimpleTableSegment(new TableNameSegment(0, 0, new IdentifierValue("doctor")));
doctorTable.setAlias(new AliasSegment(0, 0, new IdentifierValue("a")));
ColumnSegment column = new ColumnSegment(0, 0, new IdentifierValue("mobile"));
+ column.setOriginalColumn(new IdentifierValue("mobile"));
+ column.setOriginalTable(new IdentifierValue("doctor"));
column.setOwner(new OwnerSegment(0, 0, new IdentifierValue("a")));
ProjectionsSegment projections = mock(ProjectionsSegment.class);
when(projections.getProjections()).thenReturn(Collections.singletonList(new ColumnProjectionSegment(column)));
diff --git a/features/mask/core/src/main/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaData.java b/features/mask/core/src/main/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaData.java
index 0a4da833854..70b85687899 100644
--- a/features/mask/core/src/main/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaData.java
+++ b/features/mask/core/src/main/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaData.java
@@ -20,16 +20,12 @@ package org.apache.shardingsphere.mask.merge.dql;
import lombok.RequiredArgsConstructor;
import org.apache.shardingsphere.infra.binder.context.segment.select.projection.Projection;
import org.apache.shardingsphere.infra.binder.context.segment.select.projection.impl.ColumnProjection;
-import org.apache.shardingsphere.infra.binder.context.segment.table.TablesContext;
import org.apache.shardingsphere.infra.binder.context.statement.dml.SelectStatementContext;
-import org.apache.shardingsphere.infra.database.core.type.DatabaseTypeRegistry;
import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase;
import org.apache.shardingsphere.mask.rule.MaskRule;
import org.apache.shardingsphere.mask.spi.MaskAlgorithm;
-import java.util.Collections;
import java.util.List;
-import java.util.Map;
import java.util.Optional;
/**
@@ -56,11 +52,7 @@ public final class MaskAlgorithmMetaData {
if (!columnProjection.isPresent()) {
return Optional.empty();
}
- TablesContext tablesContext = selectStatementContext.getTablesContext();
- String schemaName = tablesContext.getSchemaName().orElseGet(() -> new DatabaseTypeRegistry(selectStatementContext.getDatabaseType()).getDefaultSchemaName(database.getName()));
- Map<String, String> expressionTableNames = tablesContext.findTableNamesByColumnProjection(
- Collections.singletonList(columnProjection.get()), database.getSchema(schemaName));
- return findTableName(columnProjection.get(), expressionTableNames).flatMap(optional -> maskRule.findMaskAlgorithm(optional, columnProjection.get().getName().getValue()));
+ return maskRule.findMaskAlgorithm(columnProjection.get().getOriginalTable().getValue(), columnProjection.get().getName().getValue());
}
private Optional<ColumnProjection> findColumnProjection(final int columnIndex) {
@@ -71,17 +63,4 @@ public final class MaskAlgorithmMetaData {
Projection projection = expandProjections.get(columnIndex - 1);
return projection instanceof ColumnProjection ? Optional.of((ColumnProjection) projection) : Optional.empty();
}
-
- private Optional<String> findTableName(final ColumnProjection columnProjection, final Map<String, String> columnTableNames) {
- String tableName = columnTableNames.get(columnProjection.getExpression());
- if (null != tableName) {
- return Optional.of(tableName);
- }
- for (String each : selectStatementContext.getTablesContext().getTableNames()) {
- if (maskRule.findMaskAlgorithm(each, columnProjection.getName().getValue()).isPresent()) {
- return Optional.of(each);
- }
- }
- return Optional.empty();
- }
}
diff --git a/features/mask/core/src/test/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaDataTest.java b/features/mask/core/src/test/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaDataTest.java
index 9de8619e000..eae75d2a29c 100644
--- a/features/mask/core/src/test/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaDataTest.java
+++ b/features/mask/core/src/test/java/org/apache/shardingsphere/mask/merge/dql/MaskAlgorithmMetaDataTest.java
@@ -24,6 +24,7 @@ import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase;
import org.apache.shardingsphere.infra.spi.type.typed.TypedSPILoader;
import org.apache.shardingsphere.mask.rule.MaskRule;
import org.apache.shardingsphere.mask.spi.MaskAlgorithm;
+import org.apache.shardingsphere.sql.parser.sql.common.value.identifier.IdentifierValue;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.Answers;
@@ -55,7 +56,10 @@ class MaskAlgorithmMetaDataTest {
@Test
void assertFindMaskAlgorithmByColumnIndex() {
when(maskRule.findMaskAlgorithm("t_order", "order_id")).thenReturn(Optional.of(TypedSPILoader.getService(MaskAlgorithm.class, "MD5")));
- when(selectStatementContext.getProjectionsContext().getExpandProjections()).thenReturn(Collections.singletonList(new ColumnProjection(null, "order_id", null, mock(DatabaseType.class))));
+ ColumnProjection columnProjection = new ColumnProjection(null, "order_id", null, mock(DatabaseType.class));
+ columnProjection.setOriginalColumn(new IdentifierValue("order_id"));
+ columnProjection.setOriginalTable(new IdentifierValue("t_order"));
+ when(selectStatementContext.getProjectionsContext().getExpandProjections()).thenReturn(Collections.singletonList(columnProjection));
when(selectStatementContext.getTablesContext().getTableNames()).thenReturn(Collections.singletonList("t_order"));
Optional<MaskAlgorithm> actual = new MaskAlgorithmMetaData(database, maskRule, selectStatementContext).findMaskAlgorithmByColumnIndex(1);
assertTrue(actual.isPresent());
diff --git a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/SubqueryRouteTest.java b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/SubqueryRouteTest.java
index 95d9e28a684..2622fe3b6d5 100644
--- a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/SubqueryRouteTest.java
+++ b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/SubqueryRouteTest.java
@@ -45,7 +45,7 @@ class SubqueryRouteTest {
HintManager hintManager = HintManager.getInstance();
hintManager.addDatabaseShardingValue("t_hint_test", 1);
hintManager.addTableShardingValue("t_hint_test", 1);
- String sql = "select count(*) from t_hint_test where user_id = (select t_hint_test from t_hint_test where user_id in (?,?,?)) ";
+ String sql = "select count(*) from t_hint_test where user_id = (select user_id from t_hint_test where user_id in (?,?,?)) ";
ShardingRouteAssert.assertRoute(sql, Arrays.asList(1, 3, 5));
hintManager.close();
}
diff --git a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/assertion/ShardingRouteAssert.java b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/assertion/ShardingRouteAssert.java
index a8caa0b5cde..06b396c70d3 100644
--- a/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/assertion/ShardingRouteAssert.java
+++ b/features/sharding/core/src/test/java/org/apache/shardingsphere/sharding/route/engine/type/standard/assertion/ShardingRouteAssert.java
@@ -108,7 +108,8 @@ public final class ShardingRouteAssert {
tables.put("t_category", new ShardingSphereTable("t_category", Collections.emptyList(), Collections.emptyList(), Collections.emptyList()));
tables.put("t_product", new ShardingSphereTable("t_product", Collections.emptyList(), Collections.emptyList(), Collections.emptyList()));
tables.put("t_user", new ShardingSphereTable("t_user", Collections.emptyList(), Collections.emptyList(), Collections.emptyList()));
- tables.put("t_hint_test", new ShardingSphereTable("t_hint_test", Collections.emptyList(), Collections.emptyList(), Collections.emptyList()));
+ tables.put("t_hint_test", new ShardingSphereTable("t_hint_test", Collections.singleton(new ShardingSphereColumn("user_id", Types.INTEGER, true, false, false, true, false, false)),
+ Collections.emptyList(), Collections.emptyList()));
return Collections.singletonMap(DefaultDatabase.LOGIC_NAME, new ShardingSphereSchema(tables, Collections.emptyMap()));
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContext.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContext.java
index c899a39a9f2..d47750d7fdb 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContext.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContext.java
@@ -20,7 +20,6 @@ package org.apache.shardingsphere.infra.binder.context.segment.table;
import com.google.common.base.Preconditions;
import lombok.Getter;
import lombok.ToString;
-import org.apache.shardingsphere.infra.binder.context.segment.select.projection.impl.ColumnProjection;
import org.apache.shardingsphere.infra.binder.context.segment.select.subquery.SubqueryTableContext;
import org.apache.shardingsphere.infra.binder.context.segment.select.subquery.engine.SubqueryTableContextEngine;
import org.apache.shardingsphere.infra.binder.context.statement.dml.SelectStatementContext;
@@ -138,26 +137,6 @@ public final class TablesContext {
return result;
}
- /**
- * Find expression table name map by column projection.
- *
- * @param columns column segment collection
- * @param schema schema meta data
- * @return expression table name map
- */
- public Map<String, String> findTableNamesByColumnProjection(final Collection<ColumnProjection> columns, final ShardingSphereSchema schema) {
- if (1 == simpleTableSegments.size()) {
- return findTableNameFromSingleTableByColumnProjection(columns);
- }
- Map<String, String> result = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
- Map<String, Collection<String>> ownerColumnNames = getOwnerColumnNamesByColumnProjection(columns);
- result.putAll(findTableNameFromSQL(ownerColumnNames));
- Collection<String> noOwnerColumnNames = getNoOwnerColumnNamesByColumnProjection(columns);
- result.putAll(findTableNameFromMetaData(noOwnerColumnNames, schema));
- result.putAll(findTableNameFromSubqueryByColumnProjection(columns, result));
- return result;
- }
-
private Map<String, String> findTableNameFromSubqueryByColumnSegment(final Collection<ColumnSegment> columns, final Map<String, String> ownerTableNames) {
if (ownerTableNames.size() == columns.size() || subqueryTables.isEmpty()) {
return Collections.emptyMap();
@@ -178,25 +157,6 @@ public final class TablesContext {
return result;
}
- private Map<String, String> findTableNameFromSubqueryByColumnProjection(final Collection<ColumnProjection> columns, final Map<String, String> ownerTableNames) {
- if (ownerTableNames.size() == columns.size() || subqueryTables.isEmpty()) {
- return Collections.emptyMap();
- }
- Map<String, String> result = new LinkedHashMap<>(columns.size(), 1F);
- for (ColumnProjection each : columns) {
- if (ownerTableNames.containsKey(each.getExpression())) {
- continue;
- }
- Collection<SubqueryTableContext> subqueryTableContexts = each.getOwner().map(optional -> subqueryTables.get(each.getOwner().get().getValue())).orElseGet(Collections::emptyList);
- for (SubqueryTableContext subqueryTableContext : subqueryTableContexts) {
- if (subqueryTableContext.getColumnNames().contains(each.getName().getValue())) {
- result.put(each.getExpression(), subqueryTableContext.getTableName());
- }
- }
- }
- return result;
- }
-
private Map<String, String> findTableNameFromSingleTableByColumnSegment(final Collection<ColumnSegment> columns) {
String tableName = simpleTableSegments.iterator().next().getTableName().getIdentifier().getValue();
Map<String, String> result = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
@@ -206,15 +166,6 @@ public final class TablesContext {
return result;
}
- private Map<String, String> findTableNameFromSingleTableByColumnProjection(final Collection<ColumnProjection> columns) {
- String tableName = simpleTableSegments.iterator().next().getTableName().getIdentifier().getValue();
- Map<String, String> result = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
- for (ColumnProjection each : columns) {
- result.putIfAbsent(each.getExpression(), tableName);
- }
- return result;
- }
-
private Map<String, Collection<String>> getOwnerColumnNamesByColumnSegment(final Collection<ColumnSegment> columns) {
Map<String, Collection<String>> result = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
for (ColumnSegment each : columns) {
@@ -226,16 +177,6 @@ public final class TablesContext {
return result;
}
- private Map<String, Collection<String>> getOwnerColumnNamesByColumnProjection(final Collection<ColumnProjection> columns) {
- Map<String, Collection<String>> result = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
- for (ColumnProjection each : columns) {
- if (each.getOwner().isPresent()) {
- result.computeIfAbsent(each.getOwner().get().getValue(), unused -> new LinkedList<>()).add(each.getExpression());
- }
- }
- return result;
- }
-
private Map<String, String> findTableNameFromSQL(final Map<String, Collection<String>> ownerColumnNames) {
if (ownerColumnNames.isEmpty()) {
return Collections.emptyMap();
@@ -280,16 +221,6 @@ public final class TablesContext {
return result;
}
- private Collection<String> getNoOwnerColumnNamesByColumnProjection(final Collection<ColumnProjection> columns) {
- Collection<String> result = new TreeSet<>(String.CASE_INSENSITIVE_ORDER);
- for (ColumnProjection each : columns) {
- if (!each.getOwner().isPresent()) {
- result.add(each.getName().getValue());
- }
- }
- return result;
- }
-
/**
* Get database name.
*
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/ExpressionSegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/ExpressionSegmentBinder.java
new file mode 100644
index 00000000000..b342ac81d2e
--- /dev/null
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/ExpressionSegmentBinder.java
@@ -0,0 +1,63 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.shardingsphere.infra.binder.segment.expression;
+
+import lombok.AccessLevel;
+import lombok.NoArgsConstructor;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.BinaryOperationExpressionBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.ExistsSubqueryExpressionBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.InExpressionBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.SubqueryExpressionSegmentBinder;
+import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.BinaryOperationExpression;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.ExistsSubqueryExpression;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.ExpressionSegment;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.InExpression;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubqueryExpressionSegment;
+
+/**
+ * Expression segment binder.
+ */
+@NoArgsConstructor(access = AccessLevel.PRIVATE)
+public final class ExpressionSegmentBinder {
+
+ /**
+ * Bind expression segment with metadata.
+ *
+ * @param segment expression segment
+ * @param metaData metaData
+ * @param defaultDatabaseName default database name
+ * @return bounded expression segment
+ */
+ public static ExpressionSegment bind(final ExpressionSegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ if (segment instanceof BinaryOperationExpression) {
+ return BinaryOperationExpressionBinder.bind((BinaryOperationExpression) segment, metaData, defaultDatabaseName);
+ }
+ if (segment instanceof ExistsSubqueryExpression) {
+ return ExistsSubqueryExpressionBinder.bind((ExistsSubqueryExpression) segment, metaData, defaultDatabaseName);
+ }
+ if (segment instanceof SubqueryExpressionSegment) {
+ return SubqueryExpressionSegmentBinder.bind((SubqueryExpressionSegment) segment, metaData, defaultDatabaseName);
+ }
+ if (segment instanceof InExpression) {
+ return InExpressionBinder.bind((InExpression) segment, metaData, defaultDatabaseName);
+ }
+ // TODO support more ExpressionSegment bind
+ return segment;
+ }
+}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/BinaryOperationExpressionBinder.java
similarity index 54%
copy from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
copy to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/BinaryOperationExpressionBinder.java
index 7fde0c58618..913aabbcafc 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/BinaryOperationExpressionBinder.java
@@ -15,33 +15,32 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.expression.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.statement.dml.SelectStatementBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.ExpressionSegmentBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
-import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubquerySegment;
-import org.apache.shardingsphere.sql.parser.sql.common.statement.dml.SelectStatement;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.BinaryOperationExpression;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.ExpressionSegment;
/**
- * Subquery segment binder.
+ * Binary operation expression binder.
*/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
-public final class SubquerySegmentBinder {
+public final class BinaryOperationExpressionBinder {
/**
- * Bind subquery segment with metadata.
+ * Bind binary operation expression with metadata.
*
- * @param segment subquery segment
+ * @param segment binary operation expression segment
* @param metaData metaData
* @param defaultDatabaseName default database name
- * @return bounded subquery segment
+ * @return bounded binary operation expression segment
*/
- public static SubquerySegment bind(final SubquerySegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
- SelectStatement boundedSelectStatement = new SelectStatementBinder().bind(segment.getSelect(), metaData, defaultDatabaseName);
- SubquerySegment result = new SubquerySegment(segment.getStartIndex(), segment.getStopIndex(), boundedSelectStatement);
- result.setSubqueryType(segment.getSubqueryType());
- return result;
+ public static BinaryOperationExpression bind(final BinaryOperationExpression segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ ExpressionSegment boundedLeft = ExpressionSegmentBinder.bind(segment.getLeft(), metaData, defaultDatabaseName);
+ ExpressionSegment boundedRight = ExpressionSegmentBinder.bind(segment.getRight(), metaData, defaultDatabaseName);
+ return new BinaryOperationExpression(segment.getStartIndex(), segment.getStopIndex(), boundedLeft, boundedRight, segment.getOperator(), segment.getText());
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/ColumnSegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/ColumnSegmentBinder.java
similarity index 99%
rename from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/ColumnSegmentBinder.java
rename to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/ColumnSegmentBinder.java
index cc8a09ac2bd..bead7512381 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/ColumnSegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/ColumnSegmentBinder.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.expression.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/ExistsSubqueryExpressionBinder.java
similarity index 61%
copy from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
copy to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/ExistsSubqueryExpressionBinder.java
index 7fde0c58618..dac518c89dd 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/ExistsSubqueryExpressionBinder.java
@@ -15,33 +15,32 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.expression.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.statement.dml.SelectStatementBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.ExistsSubqueryExpression;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubquerySegment;
-import org.apache.shardingsphere.sql.parser.sql.common.statement.dml.SelectStatement;
/**
- * Subquery segment binder.
+ * Exists subquery expression binder.
*/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
-public final class SubquerySegmentBinder {
+public final class ExistsSubqueryExpressionBinder {
/**
- * Bind subquery segment with metadata.
+ * Bind exists subquery expression with metadata.
*
- * @param segment subquery segment
+ * @param segment exists subquery expression segment
* @param metaData metaData
* @param defaultDatabaseName default database name
- * @return bounded subquery segment
+ * @return bounded exists subquery expression segment
*/
- public static SubquerySegment bind(final SubquerySegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
- SelectStatement boundedSelectStatement = new SelectStatementBinder().bind(segment.getSelect(), metaData, defaultDatabaseName);
- SubquerySegment result = new SubquerySegment(segment.getStartIndex(), segment.getStopIndex(), boundedSelectStatement);
- result.setSubqueryType(segment.getSubqueryType());
+ public static ExistsSubqueryExpression bind(final ExistsSubqueryExpression segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ SubquerySegment boundedSubquery = SubquerySegmentBinder.bind(segment.getSubquery(), metaData, defaultDatabaseName);
+ ExistsSubqueryExpression result = new ExistsSubqueryExpression(segment.getStartIndex(), segment.getStopIndex(), boundedSubquery);
+ result.setNot(segment.isNot());
return result;
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/InExpressionBinder.java
similarity index 57%
copy from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
copy to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/InExpressionBinder.java
index 7fde0c58618..3f3f1ba13fe 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/InExpressionBinder.java
@@ -15,33 +15,32 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.expression.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.statement.dml.SelectStatementBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.ExpressionSegmentBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
-import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubquerySegment;
-import org.apache.shardingsphere.sql.parser.sql.common.statement.dml.SelectStatement;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.ExpressionSegment;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.InExpression;
/**
- * Subquery segment binder.
+ * In expression binder.
*/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
-public final class SubquerySegmentBinder {
+public final class InExpressionBinder {
/**
- * Bind subquery segment with metadata.
+ * Bind in expression segment with metadata.
*
- * @param segment subquery segment
+ * @param segment in expression
* @param metaData metaData
* @param defaultDatabaseName default database name
- * @return bounded subquery segment
+ * @return bounded in expression
*/
- public static SubquerySegment bind(final SubquerySegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
- SelectStatement boundedSelectStatement = new SelectStatementBinder().bind(segment.getSelect(), metaData, defaultDatabaseName);
- SubquerySegment result = new SubquerySegment(segment.getStartIndex(), segment.getStopIndex(), boundedSelectStatement);
- result.setSubqueryType(segment.getSubqueryType());
- return result;
+ public static InExpression bind(final InExpression segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ ExpressionSegment boundedLeft = ExpressionSegmentBinder.bind(segment.getLeft(), metaData, defaultDatabaseName);
+ ExpressionSegment boundedRight = ExpressionSegmentBinder.bind(segment.getRight(), metaData, defaultDatabaseName);
+ return new InExpression(segment.getStartIndex(), segment.getStopIndex(), boundedLeft, boundedRight, segment.isNot());
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/SubqueryExpressionSegmentBinder.java
similarity index 59%
copy from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
copy to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/SubqueryExpressionSegmentBinder.java
index 7fde0c58618..ac16a62dbaa 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/SubqueryExpressionSegmentBinder.java
@@ -15,33 +15,30 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.expression.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.statement.dml.SelectStatementBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubqueryExpressionSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubquerySegment;
-import org.apache.shardingsphere.sql.parser.sql.common.statement.dml.SelectStatement;
/**
- * Subquery segment binder.
+ * Subquery expression segment binder.
*/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
-public final class SubquerySegmentBinder {
+public final class SubqueryExpressionSegmentBinder {
/**
- * Bind subquery segment with metadata.
+ * Bind subquery expression segment with metadata.
*
- * @param segment subquery segment
+ * @param segment subquery expression segment
* @param metaData metaData
* @param defaultDatabaseName default database name
- * @return bounded subquery segment
+ * @return bounded subquery expression segment
*/
- public static SubquerySegment bind(final SubquerySegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
- SelectStatement boundedSelectStatement = new SelectStatementBinder().bind(segment.getSelect(), metaData, defaultDatabaseName);
- SubquerySegment result = new SubquerySegment(segment.getStartIndex(), segment.getStopIndex(), boundedSelectStatement);
- result.setSubqueryType(segment.getSubqueryType());
- return result;
+ public static SubqueryExpressionSegment bind(final SubqueryExpressionSegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ SubquerySegment boundedSubquery = SubquerySegmentBinder.bind(segment.getSubquery(), metaData, defaultDatabaseName);
+ return new SubqueryExpressionSegment(boundedSubquery);
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/SubquerySegmentBinder.java
similarity index 99%
copy from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
copy to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/SubquerySegmentBinder.java
index 7fde0c58618..e3b8b42a7f4 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/impl/SubquerySegmentBinder.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.expression.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/ProjectionsSegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/ProjectionsSegmentBinder.java
index 2efa2510ff8..1db1dcf1155 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/ProjectionsSegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/ProjectionsSegmentBinder.java
@@ -17,18 +17,22 @@
package org.apache.shardingsphere.infra.binder.segment.projection;
-import java.util.Map;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
import org.apache.shardingsphere.infra.binder.segment.from.TableSegmentBinderContext;
import org.apache.shardingsphere.infra.binder.segment.projection.impl.ColumnProjectionSegmentBinder;
import org.apache.shardingsphere.infra.binder.segment.projection.impl.ShorthandProjectionSegmentBinder;
+import org.apache.shardingsphere.infra.binder.segment.projection.impl.SubqueryProjectionSegmentBinder;
+import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ColumnProjectionSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ProjectionSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ProjectionsSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ShorthandProjectionSegment;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.SubqueryProjectionSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.table.TableSegment;
+import java.util.Map;
+
/**
* Projections segment binder.
*/
@@ -39,24 +43,31 @@ public final class ProjectionsSegmentBinder {
* Bind projections segment with metadata.
*
* @param segment table segment
+ * @param metaData meta data
+ * @param defaultDatabaseName default database name
* @param boundedTableSegment bounded table segment
* @param tableBinderContexts table binder contexts
* @return bounded projections segment
*/
- public static ProjectionsSegment bind(final ProjectionsSegment segment, final TableSegment boundedTableSegment, final Map<String, TableSegmentBinderContext> tableBinderContexts) {
+ public static ProjectionsSegment bind(final ProjectionsSegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName, final TableSegment boundedTableSegment,
+ final Map<String, TableSegmentBinderContext> tableBinderContexts) {
ProjectionsSegment result = new ProjectionsSegment(segment.getStartIndex(), segment.getStopIndex());
result.setDistinctRow(segment.isDistinctRow());
- segment.getProjections().forEach(each -> result.getProjections().add(bind(each, boundedTableSegment, tableBinderContexts)));
+ segment.getProjections().forEach(each -> result.getProjections().add(bind(each, metaData, defaultDatabaseName, boundedTableSegment, tableBinderContexts)));
return result;
}
- private static ProjectionSegment bind(final ProjectionSegment projectionSegment, final TableSegment boundedTableSegment, final Map<String, TableSegmentBinderContext> tableBinderContexts) {
+ private static ProjectionSegment bind(final ProjectionSegment projectionSegment, final ShardingSphereMetaData metaData, final String defaultDatabaseName, final TableSegment boundedTableSegment,
+ final Map<String, TableSegmentBinderContext> tableBinderContexts) {
if (projectionSegment instanceof ColumnProjectionSegment) {
return ColumnProjectionSegmentBinder.bind((ColumnProjectionSegment) projectionSegment, tableBinderContexts);
}
if (projectionSegment instanceof ShorthandProjectionSegment) {
return ShorthandProjectionSegmentBinder.bind((ShorthandProjectionSegment) projectionSegment, boundedTableSegment, tableBinderContexts);
}
+ if (projectionSegment instanceof SubqueryProjectionSegment) {
+ return SubqueryProjectionSegmentBinder.bind((SubqueryProjectionSegment) projectionSegment, metaData, defaultDatabaseName);
+ }
// TODO support more ProjectionSegment bind
return projectionSegment;
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java
index 60b2796b98c..d131993c87b 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java
@@ -19,7 +19,7 @@ package org.apache.shardingsphere.infra.binder.segment.projection.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.segment.expression.ColumnSegmentBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.ColumnSegmentBinder;
import org.apache.shardingsphere.infra.binder.segment.from.TableSegmentBinderContext;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.column.ColumnSegment;
import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ColumnProjectionSegment;
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/SubqueryProjectionSegmentBinder.java
similarity index 58%
copy from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java
copy to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/SubqueryProjectionSegmentBinder.java
index 60b2796b98c..47a9431a574 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/ColumnProjectionSegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/projection/impl/SubqueryProjectionSegmentBinder.java
@@ -19,31 +19,29 @@ package org.apache.shardingsphere.infra.binder.segment.projection.impl;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.segment.expression.ColumnSegmentBinder;
-import org.apache.shardingsphere.infra.binder.segment.from.TableSegmentBinderContext;
-import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.column.ColumnSegment;
-import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ColumnProjectionSegment;
-
-import java.util.Map;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.SubquerySegmentBinder;
+import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubquerySegment;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.SubqueryProjectionSegment;
/**
- * Column projection segment binder.
+ * Subquery projection segment binder.
*/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
-public final class ColumnProjectionSegmentBinder {
+public final class SubqueryProjectionSegmentBinder {
/**
- * Bind column projection segment with metadata.
+ * Bind subquery projection segment with metadata.
*
- * @param segment table segment
- * @param tableBinderContexts table binder contexts
- * @return bounded column projection segment
+ * @param segment subquery projection segment
+ * @param metaData meta data
+ * @param defaultDatabaseName default database name
+ * @return bounded subquery projection segment
*/
- public static ColumnProjectionSegment bind(final ColumnProjectionSegment segment, final Map<String, TableSegmentBinderContext> tableBinderContexts) {
- ColumnSegment boundedColumn = ColumnSegmentBinder.bind(segment.getColumn(), tableBinderContexts);
- ColumnProjectionSegment result = new ColumnProjectionSegment(boundedColumn);
+ public static SubqueryProjectionSegment bind(final SubqueryProjectionSegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ SubquerySegment boundedSubquerySegment = SubquerySegmentBinder.bind(segment.getSubquery(), metaData, defaultDatabaseName);
+ SubqueryProjectionSegment result = new SubqueryProjectionSegment(boundedSubquerySegment, segment.getText());
segment.getAliasSegment().ifPresent(result::setAlias);
- result.setVisible(segment.isVisible());
return result;
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/where/WhereSegmentBinder.java
similarity index 53%
rename from infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
rename to infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/where/WhereSegmentBinder.java
index 7fde0c58618..1fd7f2fdb48 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/expression/SubquerySegmentBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/segment/where/WhereSegmentBinder.java
@@ -15,33 +15,29 @@
* limitations under the License.
*/
-package org.apache.shardingsphere.infra.binder.segment.expression;
+package org.apache.shardingsphere.infra.binder.segment.where;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
-import org.apache.shardingsphere.infra.binder.statement.dml.SelectStatementBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.ExpressionSegmentBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
-import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.subquery.SubquerySegment;
-import org.apache.shardingsphere.sql.parser.sql.common.statement.dml.SelectStatement;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.predicate.WhereSegment;
/**
- * Subquery segment binder.
+ * Where segment binder.
*/
@NoArgsConstructor(access = AccessLevel.PRIVATE)
-public final class SubquerySegmentBinder {
+public final class WhereSegmentBinder {
/**
- * Bind subquery segment with metadata.
+ * Bind where segment with metadata.
*
- * @param segment subquery segment
- * @param metaData metaData
+ * @param segment where segment
+ * @param metaData meta data
* @param defaultDatabaseName default database name
- * @return bounded subquery segment
+ * @return bounded where segment
*/
- public static SubquerySegment bind(final SubquerySegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
- SelectStatement boundedSelectStatement = new SelectStatementBinder().bind(segment.getSelect(), metaData, defaultDatabaseName);
- SubquerySegment result = new SubquerySegment(segment.getStartIndex(), segment.getStopIndex(), boundedSelectStatement);
- result.setSubqueryType(segment.getSubqueryType());
- return result;
+ public static WhereSegment bind(final WhereSegment segment, final ShardingSphereMetaData metaData, final String defaultDatabaseName) {
+ return new WhereSegment(segment.getStartIndex(), segment.getStopIndex(), ExpressionSegmentBinder.bind(segment.getExpr(), metaData, defaultDatabaseName));
}
}
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/InsertStatementBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/InsertStatementBinder.java
index 4e40205ac23..754ad565052 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/InsertStatementBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/InsertStatementBinder.java
@@ -18,7 +18,7 @@
package org.apache.shardingsphere.infra.binder.statement.dml;
import lombok.SneakyThrows;
-import org.apache.shardingsphere.infra.binder.segment.expression.SubquerySegmentBinder;
+import org.apache.shardingsphere.infra.binder.segment.expression.impl.SubquerySegmentBinder;
import org.apache.shardingsphere.infra.binder.statement.SQLStatementBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
import org.apache.shardingsphere.sql.parser.sql.common.statement.dml.InsertStatement;
diff --git a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/SelectStatementBinder.java b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/SelectStatementBinder.java
index 7380470fb55..1b506c11948 100644
--- a/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/SelectStatementBinder.java
+++ b/infra/binder/src/main/java/org/apache/shardingsphere/infra/binder/statement/dml/SelectStatementBinder.java
@@ -23,6 +23,7 @@ import org.apache.shardingsphere.infra.binder.segment.combine.CombineSegmentBind
import org.apache.shardingsphere.infra.binder.segment.from.TableSegmentBinder;
import org.apache.shardingsphere.infra.binder.segment.from.TableSegmentBinderContext;
import org.apache.shardingsphere.infra.binder.segment.projection.ProjectionsSegmentBinder;
+import org.apache.shardingsphere.infra.binder.segment.where.WhereSegmentBinder;
import org.apache.shardingsphere.infra.binder.statement.SQLStatementBinder;
import org.apache.shardingsphere.infra.metadata.ShardingSphereMetaData;
import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.table.TableSegment;
@@ -43,9 +44,9 @@ public final class SelectStatementBinder implements SQLStatementBinder<SelectSta
Map<String, TableSegmentBinderContext> tableBinderContexts = new CaseInsensitiveMap<>();
TableSegment boundedTableSegment = TableSegmentBinder.bind(sqlStatement.getFrom(), metaData, defaultDatabaseName, sqlStatement.getDatabaseType(), tableBinderContexts);
result.setFrom(boundedTableSegment);
- result.setProjections(ProjectionsSegmentBinder.bind(sqlStatement.getProjections(), boundedTableSegment, tableBinderContexts));
+ result.setProjections(ProjectionsSegmentBinder.bind(sqlStatement.getProjections(), metaData, defaultDatabaseName, boundedTableSegment, tableBinderContexts));
// TODO support other segment bind in select statement
- sqlStatement.getWhere().ifPresent(result::setWhere);
+ sqlStatement.getWhere().ifPresent(optional -> result.setWhere(WhereSegmentBinder.bind(optional, metaData, defaultDatabaseName)));
sqlStatement.getGroupBy().ifPresent(result::setGroupBy);
sqlStatement.getHaving().ifPresent(result::setHaving);
sqlStatement.getOrderBy().ifPresent(result::setOrderBy);
diff --git a/infra/binder/src/test/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContextTest.java b/infra/binder/src/test/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContextTest.java
index 0057549a06c..7669110ca53 100644
--- a/infra/binder/src/test/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContextTest.java
+++ b/infra/binder/src/test/java/org/apache/shardingsphere/infra/binder/context/segment/table/TablesContextTest.java
@@ -17,7 +17,6 @@
package org.apache.shardingsphere.infra.binder.context.segment.table;
-import org.apache.shardingsphere.infra.binder.context.segment.select.projection.impl.ColumnProjection;
import org.apache.shardingsphere.infra.database.core.type.DatabaseType;
import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereColumn;
import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereSchema;
@@ -125,64 +124,6 @@ class TablesContextTest {
assertThat(actual.get("col"), is("TABLE_1"));
}
- @Test
- void assertFindTableNameWhenColumnProjectionWhenSingleTable() {
- SimpleTableSegment tableSegment = createTableSegment("table_1", "tbl_1");
- ColumnProjection columnProjection = new ColumnProjection(null, "col", "cl", mock(DatabaseType.class));
- Map<String, String> actual = new TablesContext(Collections.singletonList(tableSegment), TypedSPILoader.getService(DatabaseType.class, "FIXTURE"))
- .findTableNamesByColumnProjection(Collections.singletonList(columnProjection), mock(ShardingSphereSchema.class));
- assertFalse(actual.isEmpty());
- assertThat(actual.get("col"), is("table_1"));
- }
-
- @Test
- void assertFindTableNameWhenColumnProjectionOwnerPresent() {
- SimpleTableSegment tableSegment1 = createTableSegment("table_1", "tbl_1");
- SimpleTableSegment tableSegment2 = createTableSegment("table_2", "tbl_2");
- ColumnProjection columnProjection = new ColumnProjection("table_1", "col", "cl", mock(DatabaseType.class));
- Map<String, String> actual = new TablesContext(Arrays.asList(tableSegment1, tableSegment2), TypedSPILoader.getService(DatabaseType.class, "FIXTURE"))
- .findTableNamesByColumnProjection(Collections.singletonList(columnProjection), mock(ShardingSphereSchema.class));
- assertFalse(actual.isEmpty());
- assertThat(actual.get("table_1.col"), is("table_1"));
- }
-
- @Test
- void assertFindTableNameWhenColumnProjectionOwnerAbsent() {
- SimpleTableSegment tableSegment1 = createTableSegment("table_1", "tbl_1");
- SimpleTableSegment tableSegment2 = createTableSegment("table_2", "tbl_2");
- ColumnProjection columnProjection = new ColumnProjection(null, "col", "cl", mock(DatabaseType.class));
- Map<String, String> actual = new TablesContext(Arrays.asList(tableSegment1, tableSegment2), TypedSPILoader.getService(DatabaseType.class, "FIXTURE"))
- .findTableNamesByColumnProjection(Collections.singletonList(columnProjection), mock(ShardingSphereSchema.class));
- assertTrue(actual.isEmpty());
- }
-
- @Test
- void assertFindTableNameWhenColumnProjectionOwnerAbsentAndSchemaMetaDataContainsColumn() {
- SimpleTableSegment tableSegment1 = createTableSegment("table_1", "tbl_1");
- SimpleTableSegment tableSegment2 = createTableSegment("table_2", "tbl_2");
- ShardingSphereSchema schema = mock(ShardingSphereSchema.class);
- when(schema.getAllColumnNames("table_1")).thenReturn(Collections.singletonList("col"));
- ColumnProjection columnProjection = new ColumnProjection(null, "col", "cl", mock(DatabaseType.class));
- Map<String, String> actual = new TablesContext(Arrays.asList(tableSegment1, tableSegment2), TypedSPILoader.getService(DatabaseType.class, "FIXTURE"))
- .findTableNamesByColumnProjection(Collections.singletonList(columnProjection), schema);
- assertFalse(actual.isEmpty());
- assertThat(actual.get("col"), is("table_1"));
- }
-
- @Test
- void assertFindTableNameWhenColumnProjectionOwnerAbsentAndSchemaMetaDataContainsColumnInUpperCase() {
- SimpleTableSegment tableSegment1 = createTableSegment("TABLE_1", "TBL_1");
- SimpleTableSegment tableSegment2 = createTableSegment("TABLE_2", "TBL_2");
- ShardingSphereTable table = new ShardingSphereTable("TABLE_1", Collections.singletonList(
- new ShardingSphereColumn("COL", 0, false, false, true, true, false, false)), Collections.emptyList(), Collections.emptyList());
- ShardingSphereSchema schema = new ShardingSphereSchema(Stream.of(table).collect(Collectors.toMap(ShardingSphereTable::getName, value -> value)), Collections.emptyMap());
- ColumnProjection columnProjection = new ColumnProjection(null, "COL", "CL", mock(DatabaseType.class));
- Map<String, String> actual = new TablesContext(Arrays.asList(tableSegment1, tableSegment2), TypedSPILoader.getService(DatabaseType.class, "FIXTURE"))
- .findTableNamesByColumnProjection(Collections.singletonList(columnProjection), schema);
- assertFalse(actual.isEmpty());
- assertThat(actual.get("col"), is("TABLE_1"));
- }
-
private SimpleTableSegment createTableSegment(final String tableName, final String alias) {
SimpleTableSegment result = new SimpleTableSegment(new TableNameSegment(0, 0, new IdentifierValue(tableName)));
AliasSegment aliasSegment = new AliasSegment(0, 0, new IdentifierValue(alias));
diff --git a/kernel/sql-federation/core/src/main/java/org/apache/shardingsphere/sqlfederation/resultset/SQLFederationResultSetMetaData.java b/kernel/sql-federation/core/src/main/java/org/apache/shardingsphere/sqlfederation/resultset/SQLFederationResultSetMetaData.java
index cdee84ceffa..9e122e7236f 100644
--- a/kernel/sql-federation/core/src/main/java/org/apache/shardingsphere/sqlfederation/resultset/SQLFederationResultSetMetaData.java
+++ b/kernel/sql-federation/core/src/main/java/org/apache/shardingsphere/sqlfederation/resultset/SQLFederationResultSetMetaData.java
@@ -29,7 +29,6 @@ import org.apache.shardingsphere.infra.database.core.DefaultDatabase;
import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereSchema;
import java.sql.ResultSetMetaData;
-import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Optional;
@@ -182,9 +181,7 @@ public final class SQLFederationResultSetMetaData extends WrapperAdapter impleme
expandProjections.size() < column ? new ColumnProjection(null, resultColumnType.getFieldList().get(column - 1).getName(), null, selectStatementContext.getDatabaseType())
: expandProjections.get(column - 1);
if (projection instanceof ColumnProjection) {
- Map<String, String> tableNamesByColumnProjection =
- selectStatementContext.getTablesContext().findTableNamesByColumnProjection(Collections.singletonList((ColumnProjection) projection), schema);
- return Optional.of(tableNamesByColumnProjection.get(projection.getExpression()));
+ return Optional.of(((ColumnProjection) projection).getOriginalTable().getValue());
}
return Optional.empty();
}
diff --git a/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/item/SubqueryProjectionSegment.java b/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/item/SubqueryProjectionSegment.java
index e180b0c6eed..10d23113f02 100644
--- a/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/item/SubqueryProjectionSegment.java
+++ b/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/item/SubqueryProjectionSegment.java
@@ -56,6 +56,15 @@ public final class SubqueryProjectionSegment implements ProjectionSegment, Alias
return Optional.ofNullable(alias).map(AliasSegment::getIdentifier);
}
+ /**
+ * Get alias segment.
+ *
+ * @return alias segment
+ */
+ public Optional<AliasSegment> getAliasSegment() {
+ return Optional.ofNullable(alias);
+ }
+
@Override
public int getStartIndex() {
return subquery.getStartIndex();
diff --git a/proxy/frontend/type/mysql/src/main/java/org/apache/shardingsphere/proxy/frontend/mysql/command/query/binary/prepare/MySQLComStmtPrepareExecutor.java b/proxy/frontend/type/mysql/src/main/java/org/apache/shardingsphere/proxy/frontend/mysql/command/query/binary/prepare/MySQLComStmtPrepareExecutor.java
index 23e9a91eaf4..4184e3ad204 100644
--- a/proxy/frontend/type/mysql/src/main/java/org/apache/shardingsphere/proxy/frontend/mysql/command/query/binary/prepare/MySQLComStmtPrepareExecutor.java
+++ b/proxy/frontend/type/mysql/src/main/java/org/apache/shardingsphere/proxy/frontend/mysql/command/query/binary/prepare/MySQLComStmtPrepareExecutor.java
@@ -28,7 +28,6 @@ import org.apache.shardingsphere.db.protocol.mysql.packet.command.query.binary.p
import org.apache.shardingsphere.db.protocol.mysql.packet.command.query.binary.prepare.MySQLComStmtPreparePacket;
import org.apache.shardingsphere.db.protocol.mysql.packet.generic.MySQLEofPacket;
import org.apache.shardingsphere.db.protocol.packet.DatabasePacket;
-import org.apache.shardingsphere.infra.exception.mysql.exception.UnsupportedPreparedStatementException;
import org.apache.shardingsphere.infra.binder.context.segment.select.projection.Projection;
import org.apache.shardingsphere.infra.binder.context.segment.select.projection.impl.ColumnProjection;
import org.apache.shardingsphere.infra.binder.context.statement.SQLStatementContext;
@@ -36,6 +35,7 @@ import org.apache.shardingsphere.infra.binder.context.statement.dml.SelectStatem
import org.apache.shardingsphere.infra.binder.engine.SQLBindEngine;
import org.apache.shardingsphere.infra.database.core.type.DatabaseType;
import org.apache.shardingsphere.infra.database.core.type.DatabaseTypeRegistry;
+import org.apache.shardingsphere.infra.exception.mysql.exception.UnsupportedPreparedStatementException;
import org.apache.shardingsphere.infra.metadata.database.ShardingSphereDatabase;
import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereColumn;
import org.apache.shardingsphere.infra.metadata.database.schema.model.ShardingSphereSchema;
@@ -60,7 +60,6 @@ import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.concurrent.CopyOnWriteArrayList;
-import java.util.stream.Collectors;
/**
* COM_STMT_PREPARE command executor for MySQL.
@@ -143,13 +142,11 @@ public final class MySQLComStmtPrepareExecutor implements CommandExecutor {
private Collection<MySQLPacket> createProjectionColumnDefinition41Packets(final SelectStatementContext selectStatementContext, final int characterSet) {
Collection<Projection> projections = selectStatementContext.getProjectionsContext().getExpandProjections();
ShardingSphereSchema schema = getSchema(selectStatementContext);
- Map<String, String> columnToTableMap = selectStatementContext.getTablesContext()
- .findTableNamesByColumnProjection(projections.stream().filter(ColumnProjection.class::isInstance).map(ColumnProjection.class::cast).collect(Collectors.toList()), schema);
Collection<MySQLPacket> result = new ArrayList<>(projections.size());
for (Projection each : projections) {
// TODO Calculate column definition flag for other projection types
- if (each instanceof ColumnProjection && null != ((ColumnProjection) each).getOriginalColumn()) {
- result.add(Optional.ofNullable(columnToTableMap.get(each.getExpression())).map(schema::getTable)
+ if (each instanceof ColumnProjection) {
+ result.add(Optional.ofNullable(schema.getTable(((ColumnProjection) each).getOriginalTable().getValue()))
.map(table -> table.getColumns().get(((ColumnProjection) each).getOriginalColumn().getValue()))
.map(column -> createMySQLColumnDefinition41Packet(characterSet, calculateColumnDefinitionFlag(column), MySQLBinaryColumnType.valueOfJDBCType(column.getDataType())))
.orElseGet(() -> createMySQLColumnDefinition41Packet(characterSet, 0, MySQLBinaryColumnType.VAR_STRING)));