提交 23964bec 编写于 作者: T tristaZero

Merge branch 'dev' of ssh://github.com/shardingjdbc/sharding-jdbc into dev

# Conflicts:
#	sharding-core/sharding-core-rewrite/src/main/java/org/apache/shardingsphere/core/rewrite/SQLRewriteEngine.java
#	sharding-core/sharding-core-rewrite/src/main/java/org/apache/shardingsphere/core/rewrite/rewriter/sql/BaseSQLRewriter.java
#	sharding-core/sharding-core-rewrite/src/main/java/org/apache/shardingsphere/core/rewrite/rewriter/sql/EncryptSQLRewriter.java
#	sharding-core/sharding-core-rewrite/src/main/java/org/apache/shardingsphere/core/rewrite/rewriter/sql/ShardingSQLRewriter.java
#	sharding-core/sharding-core-rewrite/src/test/java/org/apache/shardingsphere/core/rewrite/rewriter/ShardingSQLRewriterTest.java
......@@ -24,8 +24,10 @@ import org.apache.shardingsphere.core.constant.properties.ShardingProperties;
import org.apache.shardingsphere.core.constant.properties.ShardingPropertiesConstant;
import org.apache.shardingsphere.core.metadata.ShardingMetaData;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.rewriter.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.ShardingSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ShardingParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.ShardingSQLRewriter;
import org.apache.shardingsphere.core.route.RouteUnit;
import org.apache.shardingsphere.core.route.SQLLogger;
import org.apache.shardingsphere.core.route.SQLRouteResult;
......@@ -34,7 +36,9 @@ import org.apache.shardingsphere.core.route.hook.SPIRoutingHook;
import org.apache.shardingsphere.core.route.type.RoutingUnit;
import org.apache.shardingsphere.core.rule.ShardingRule;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.LinkedHashSet;
import java.util.List;
......@@ -102,10 +106,11 @@ public abstract class BaseShardingEngine {
}
private Collection<RouteUnit> rewriteAndConvert(final List<Object> parameters, final SQLRouteResult sqlRouteResult) {
SQLRewriteEngine rewriteEngine = new SQLRewriteEngine(shardingRule, sqlRouteResult.getSqlStatement(), parameters);
SQLRewriteEngine rewriteEngine = new SQLRewriteEngine(shardingRule, sqlRouteResult.getSqlStatement(), parameters, sqlRouteResult.getRoutingResult().isSingleRouting());
ShardingParameterRewriter shardingParameterRewriter = new ShardingParameterRewriter(databaseType, sqlRouteResult);
ShardingSQLRewriter shardingSQLRewriter = new ShardingSQLRewriter(shardingRule, databaseType, sqlRouteResult, sqlRouteResult.getOptimizeResult());
EncryptSQLRewriter encryptSQLRewriter = new EncryptSQLRewriter(shardingRule.getEncryptRule().getEncryptorEngine(), sqlRouteResult.getSqlStatement(), sqlRouteResult.getOptimizeResult());
rewriteEngine.init(shardingSQLRewriter, encryptSQLRewriter);
rewriteEngine.init(Collections.<ParameterRewriter>singletonList(shardingParameterRewriter), Arrays.asList(shardingSQLRewriter, encryptSQLRewriter));
Collection<RouteUnit> result = new LinkedHashSet<>();
for (RoutingUnit each : sqlRouteResult.getRoutingResult().getRoutingUnits()) {
result.add(new RouteUnit(each.getDataSourceName(), rewriteEngine.generateSQL(each)));
......
......@@ -19,11 +19,12 @@ package org.apache.shardingsphere.core.rewrite;
import com.google.common.base.Optional;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.token.pojo.SQLToken;
import org.apache.shardingsphere.core.parse.sql.token.SQLToken;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
import org.apache.shardingsphere.core.rewrite.builder.SQLBuilder;
import org.apache.shardingsphere.core.rewrite.rewriter.BaseSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.SQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.BaseSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.SQLRewriter;
import org.apache.shardingsphere.core.rewrite.token.BaseTokenGenerateEngine;
import org.apache.shardingsphere.core.rewrite.token.EncryptTokenGenerateEngine;
import org.apache.shardingsphere.core.rewrite.token.MasterSlaveTokenGenerateEngine;
......@@ -36,6 +37,7 @@ import org.apache.shardingsphere.core.rule.BindingTableRule;
import org.apache.shardingsphere.core.rule.EncryptRule;
import org.apache.shardingsphere.core.rule.ShardingRule;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.LinkedList;
......@@ -62,10 +64,10 @@ public final class SQLRewriteEngine {
private final BaseSQLRewriter baseSQLRewriter;
public SQLRewriteEngine(final ShardingRule shardingRule, final SQLStatement sqlStatement, final List<Object> parameters) {
public SQLRewriteEngine(final ShardingRule shardingRule, final SQLStatement sqlStatement, final List<Object> parameters, final boolean isSingleRoute) {
baseRule = shardingRule;
this.sqlStatement = sqlStatement;
sqlTokens = createSQLTokens(shardingRule, sqlStatement);
sqlTokens = createSQLTokens(shardingRule, sqlStatement, isSingleRoute);
sqlBuilder = new SQLBuilder();
parameterBuilder = new ParameterBuilder(parameters);
baseSQLRewriter = new BaseSQLRewriter(sqlStatement, sqlTokens);
......@@ -74,7 +76,7 @@ public final class SQLRewriteEngine {
public SQLRewriteEngine(final EncryptRule encryptRule, final SQLStatement sqlStatement, final List<Object> parameters) {
baseRule = encryptRule;
this.sqlStatement = sqlStatement;
sqlTokens = createSQLTokens(encryptRule, sqlStatement);
sqlTokens = createSQLTokens(encryptRule, sqlStatement, true);
sqlBuilder = new SQLBuilder();
parameterBuilder = new ParameterBuilder(parameters);
baseSQLRewriter = new BaseSQLRewriter(sqlStatement, sqlTokens);
......@@ -83,23 +85,23 @@ public final class SQLRewriteEngine {
public SQLRewriteEngine(final SQLStatement sqlStatement) {
baseRule = null;
this.sqlStatement = sqlStatement;
sqlTokens = createSQLTokens(null, sqlStatement);
sqlTokens = createSQLTokens(null, sqlStatement, true);
sqlBuilder = new SQLBuilder();
parameterBuilder = new ParameterBuilder(Collections.emptyList());
baseSQLRewriter = new BaseSQLRewriter(sqlStatement, sqlTokens);
}
private List<SQLToken> createSQLTokens(final BaseRule baseRule, final SQLStatement sqlStatement) {
List<SQLToken> result = new LinkedList<>();
result.addAll(new BaseTokenGenerateEngine().generateSQLTokens(sqlStatement, baseRule));
private List<SQLToken> createSQLTokens(final BaseRule baseRule, final SQLStatement sqlStatement, final boolean isSingleRoute) {
List<SQLToken> result = new LinkedList<>(sqlStatement.getSQLTokens());
result.addAll(new BaseTokenGenerateEngine().generateSQLTokens(sqlStatement, baseRule, isSingleRoute));
if (baseRule instanceof ShardingRule) {
ShardingRule shardingRule = (ShardingRule) baseRule;
result.addAll(new ShardingTokenGenerateEngine().generateSQLTokens(sqlStatement, shardingRule));
result.addAll(new EncryptTokenGenerateEngine().generateSQLTokens(sqlStatement, shardingRule.getEncryptRule()));
result.addAll(new ShardingTokenGenerateEngine().generateSQLTokens(sqlStatement, shardingRule, isSingleRoute));
result.addAll(new EncryptTokenGenerateEngine().generateSQLTokens(sqlStatement, shardingRule.getEncryptRule(), isSingleRoute));
} else if (baseRule instanceof EncryptRule) {
result.addAll(new EncryptTokenGenerateEngine().generateSQLTokens(sqlStatement, (EncryptRule) baseRule));
result.addAll(new EncryptTokenGenerateEngine().generateSQLTokens(sqlStatement, (EncryptRule) baseRule, isSingleRoute));
} else {
result.addAll(new MasterSlaveTokenGenerateEngine().generateSQLTokens(sqlStatement, null));
result.addAll(new MasterSlaveTokenGenerateEngine().generateSQLTokens(sqlStatement, null, isSingleRoute));
}
Collections.sort(result);
return result;
......@@ -108,9 +110,13 @@ public final class SQLRewriteEngine {
/**
* Initialize SQL rewrite engine.
*
* @param parameterRewriters parameter rewriters
* @param sqlRewriters SQL rewriters
*/
public void init(final SQLRewriter... sqlRewriters) {
public void init(final Collection<ParameterRewriter> parameterRewriters, final Collection<SQLRewriter> sqlRewriters) {
for (ParameterRewriter each : parameterRewriters) {
each.rewrite(parameterBuilder);
}
if (sqlTokens.isEmpty()) {
baseSQLRewriter.appendWholeSQL(sqlBuilder);
return;
......
......@@ -40,13 +40,16 @@ public final class ParameterBuilder {
private final List<Object> originalParameters;
private final Map<Integer, Object> assistedIndexAndParametersForUpdate;
private final Map<Integer, Object> addedIndexAndParameters;
private final Map<Integer, Object> replacedIndexAndParameters;
private final List<InsertParameterUnit> insertParameterUnits;
public ParameterBuilder(final List<Object> parameters) {
originalParameters = new LinkedList<>(parameters);
assistedIndexAndParametersForUpdate = new HashMap<>();
addedIndexAndParameters = new HashMap<>();
replacedIndexAndParameters = new HashMap<>();
insertParameterUnits = new LinkedList<>();
}
......@@ -122,9 +125,12 @@ public final class ParameterBuilder {
private List<Object> getRevisedParameters() {
List<Object> result = new LinkedList<>(originalParameters);
for (Entry<Integer, Object> entry : assistedIndexAndParametersForUpdate.entrySet()) {
for (Entry<Integer, Object> entry : addedIndexAndParameters.entrySet()) {
result.add(entry.getKey(), entry.getValue());
}
for (Entry<Integer, Object> entry : replacedIndexAndParameters.entrySet()) {
result.set(entry.getKey(), entry.getValue());
}
return result;
}
}
/*
* 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.core.rewrite.rewriter.parameter;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
/**
* Parameter rewriter.
*
* @author zhangliang
*/
public interface ParameterRewriter {
/**
* Rewrite.
*
* @param parameterBuilder parameter builder
*/
void rewrite(ParameterBuilder parameterBuilder);
}
/*
* 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.core.rewrite.rewriter.parameter;
import lombok.RequiredArgsConstructor;
import org.apache.shardingsphere.core.constant.DatabaseType;
import org.apache.shardingsphere.core.parse.sql.statement.dml.SelectStatement;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
import org.apache.shardingsphere.core.route.SQLRouteResult;
/**
* Parameter rewriter for sharding.
*
* @author zhangliang
*/
@RequiredArgsConstructor
public final class ShardingParameterRewriter implements ParameterRewriter {
private final DatabaseType databaseType;
private final SQLRouteResult sqlRouteResult;
@Override
public void rewrite(final ParameterBuilder parameterBuilder) {
if (sqlRouteResult.getSqlStatement() instanceof SelectStatement && null != sqlRouteResult.getLimit()) {
rewriteLimit((SelectStatement) sqlRouteResult.getSqlStatement(), parameterBuilder);
}
}
private void rewriteLimit(final SelectStatement selectStatement, final ParameterBuilder parameterBuilder) {
boolean isNeedFetchAll = (!selectStatement.getGroupByItems().isEmpty() || !selectStatement.getAggregationSelectItems().isEmpty()) && !selectStatement.isSameGroupByAndOrderByItems();
parameterBuilder.getReplacedIndexAndParameters().putAll(sqlRouteResult.getLimit().getRevisedIndexAndParameters(isNeedFetchAll, databaseType.name()));
}
}
......@@ -15,16 +15,16 @@
* limitations under the License.
*/
package org.apache.shardingsphere.core.rewrite.rewriter;
package org.apache.shardingsphere.core.rewrite.rewriter.sql;
import lombok.RequiredArgsConstructor;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.token.pojo.SQLToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.Substitutable;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertColumnsToken;
import org.apache.shardingsphere.core.parse.sql.token.SQLToken;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
import org.apache.shardingsphere.core.rewrite.builder.SQLBuilder;
import org.apache.shardingsphere.core.rewrite.placeholder.InsertColumnsPlaceholder;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertColumnsToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.Substitutable;
import java.util.List;
......
......@@ -15,7 +15,7 @@
* limitations under the License.
*/
package org.apache.shardingsphere.core.rewrite.rewriter;
package org.apache.shardingsphere.core.rewrite.rewriter.sql;
import com.google.common.base.Optional;
import com.google.common.base.Preconditions;
......@@ -29,11 +29,7 @@ import org.apache.shardingsphere.core.parse.sql.segment.dml.expr.simple.Paramete
import org.apache.shardingsphere.core.parse.sql.segment.dml.predicate.PredicateSegment;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.parse.sql.statement.dml.UpdateStatement;
import org.apache.shardingsphere.core.rewrite.token.pojo.SQLToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertAssistedColumnsToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertSetAddAssistedColumnsToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertSetEncryptValueToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertValuesToken;
import org.apache.shardingsphere.core.parse.sql.token.SQLToken;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
import org.apache.shardingsphere.core.rewrite.builder.SQLBuilder;
import org.apache.shardingsphere.core.rewrite.placeholder.InsertAssistedColumnsPlaceholder;
......@@ -46,6 +42,10 @@ import org.apache.shardingsphere.core.rewrite.placeholder.UpdateEncryptAssistedI
import org.apache.shardingsphere.core.rewrite.placeholder.UpdateEncryptItemPlaceholder;
import org.apache.shardingsphere.core.rewrite.placeholder.WhereEncryptColumnPlaceholder;
import org.apache.shardingsphere.core.rewrite.token.pojo.EncryptColumnToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertAssistedColumnsToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertSetAddAssistedColumnsToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertSetEncryptValueToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertValuesToken;
import org.apache.shardingsphere.core.rule.ColumnNode;
import org.apache.shardingsphere.core.strategy.encrypt.ShardingEncryptorEngine;
import org.apache.shardingsphere.spi.encrypt.ShardingEncryptor;
......@@ -140,8 +140,8 @@ public final class EncryptSQLRewriter implements SQLRewriter {
sqlBuilder.appendPlaceholder(new InsertSetEncryptValuePlaceholder(insertOptimizeResult.getUnits().get(0).getColumnSQLExpression(insertSetEncryptValueToken.getColumnName())));
}
private void appendInsertSetAddItemsPlaceholder(final SQLBuilder sqlBuilder,
final InsertSetAddAssistedColumnsToken insertSetAddAssistedColumnsToken, final InsertOptimizeResult insertOptimizeResult) {
private void appendInsertSetAddItemsPlaceholder(
final SQLBuilder sqlBuilder, final InsertSetAddAssistedColumnsToken insertSetAddAssistedColumnsToken, final InsertOptimizeResult insertOptimizeResult) {
List<ExpressionSegment> columnValues = new LinkedList<>();
for (String each : insertSetAddAssistedColumnsToken.getColumnNames()) {
columnValues.add(insertOptimizeResult.getUnits().get(0).getColumnSQLExpression(each));
......@@ -215,7 +215,7 @@ public final class EncryptSQLRewriter implements SQLRewriter {
return getUpdateEncryptItemPlaceholder(encryptColumnToken, encryptColumnValues);
}
List<Comparable<?>> encryptAssistedColumnValues = encryptorEngine.getEncryptAssistedColumnValues(columnNode, Collections.<Comparable<?>>singletonList(originalColumnValue));
parameterBuilder.getAssistedIndexAndParametersForUpdate().putAll(getIndexAndParameters(encryptColumnToken, encryptAssistedColumnValues));
parameterBuilder.getAddedIndexAndParameters().putAll(getIndexAndParameters(encryptColumnToken, encryptAssistedColumnValues));
return getUpdateEncryptAssistedItemPlaceholder(encryptColumnToken, encryptColumnValues, encryptAssistedColumnValues);
}
......
......@@ -15,7 +15,7 @@
* limitations under the License.
*/
package org.apache.shardingsphere.core.rewrite.rewriter;
package org.apache.shardingsphere.core.rewrite.rewriter.sql;
import org.apache.shardingsphere.core.rewrite.token.pojo.SQLToken;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
......
......@@ -15,7 +15,7 @@
* limitations under the License.
*/
package org.apache.shardingsphere.core.rewrite.rewriter;
package org.apache.shardingsphere.core.rewrite.rewriter.sql;
import com.google.common.base.Optional;
import com.google.common.base.Strings;
......@@ -25,8 +25,7 @@ import org.apache.shardingsphere.core.optimize.result.insert.InsertOptimizeResul
import org.apache.shardingsphere.core.parse.sql.segment.dml.order.item.OrderByItemSegment;
import org.apache.shardingsphere.core.parse.sql.segment.dml.order.item.TextOrderByItemSegment;
import org.apache.shardingsphere.core.parse.sql.statement.dml.SelectStatement;
import org.apache.shardingsphere.core.rewrite.token.pojo.SQLToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertSetAddGeneratedKeyToken;
import org.apache.shardingsphere.core.parse.sql.token.SQLToken;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
import org.apache.shardingsphere.core.rewrite.builder.SQLBuilder;
import org.apache.shardingsphere.core.rewrite.placeholder.AggregationDistinctPlaceholder;
......@@ -42,6 +41,7 @@ import org.apache.shardingsphere.core.rewrite.placeholder.TablePlaceholder;
import org.apache.shardingsphere.core.rewrite.token.pojo.AggregationDistinctToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.IndexToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertGeneratedKeyToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.InsertSetAddGeneratedKeyToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.OffsetToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.OrderByToken;
import org.apache.shardingsphere.core.rewrite.token.pojo.RowCountToken;
......@@ -186,7 +186,8 @@ public final class ShardingSQLRewriter implements SQLRewriter {
sqlBuilder.appendPlaceholder(new InsertGeneratedKeyPlaceholder(insertGeneratedKeyToken.getColumn(), insertGeneratedKeyToken.isToAddCloseParenthesis()));
}
private void appendInsertSetAddGeneratedKeyPlaceholder(final SQLBuilder sqlBuilder, final InsertSetAddGeneratedKeyToken insertSetAddGeneratedKeyToken, final InsertOptimizeResult insertOptimizeResult) {
private void appendInsertSetAddGeneratedKeyPlaceholder(
final SQLBuilder sqlBuilder, final InsertSetAddGeneratedKeyToken insertSetAddGeneratedKeyToken, final InsertOptimizeResult insertOptimizeResult) {
String columnName = insertSetAddGeneratedKeyToken.getColumnName();
sqlBuilder.appendPlaceholder(new InsertSetAddGeneratedKeyPlaceholder(columnName, insertOptimizeResult.getUnits().get(0).getColumnSQLExpression(columnName)));
}
......
......@@ -21,6 +21,7 @@ import com.google.common.base.Optional;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.token.pojo.SQLToken;
import org.apache.shardingsphere.core.rewrite.token.generator.CollectionSQLTokenGenerator;
import org.apache.shardingsphere.core.rewrite.token.generator.IgnoreForSingleRoute;
import org.apache.shardingsphere.core.rewrite.token.generator.OptionalSQLTokenGenerator;
import org.apache.shardingsphere.core.rewrite.token.generator.SQLTokenGenerator;
import org.apache.shardingsphere.core.rule.BaseRule;
......@@ -43,12 +44,16 @@ public abstract class SQLTokenGenerateEngine<T extends BaseRule> {
*
* @param sqlStatement SQL statement
* @param rule rule
* @param isSingleRoute is single route
* @return SQL tokens
*/
@SuppressWarnings("unchecked")
public final List<SQLToken> generateSQLTokens(final SQLStatement sqlStatement, final T rule) {
public final List<SQLToken> generateSQLTokens(final SQLStatement sqlStatement, final T rule, final boolean isSingleRoute) {
List<SQLToken> result = new LinkedList<>();
for (SQLTokenGenerator each : getSQLTokenGenerators()) {
if (isSingleRoute && each instanceof IgnoreForSingleRoute) {
continue;
}
if (each instanceof OptionalSQLTokenGenerator) {
Optional<? extends SQLToken> sqlToken = ((OptionalSQLTokenGenerator) each).generateSQLToken(sqlStatement, rule);
if (sqlToken.isPresent()) {
......
/*
* 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.core.rewrite.token.generator;
/**
* Ignore for single route.
*
* @author zhangliang
*/
public interface IgnoreForSingleRoute {
}
......@@ -30,7 +30,7 @@ import org.apache.shardingsphere.core.rule.ShardingRule;
*
* @author panjuan
*/
public final class OffsetTokenGenerator implements OptionalSQLTokenGenerator<ShardingRule> {
public final class OffsetTokenGenerator implements OptionalSQLTokenGenerator<ShardingRule>, IgnoreForSingleRoute {
@Override
public Optional<OffsetToken> generateSQLToken(final SQLStatement sqlStatement, final ShardingRule shardingRule) {
......
......@@ -30,7 +30,7 @@ import org.apache.shardingsphere.core.rule.ShardingRule;
*
* @author panjuan
*/
public final class RowCountTokenGenerator implements OptionalSQLTokenGenerator<ShardingRule> {
public final class RowCountTokenGenerator implements OptionalSQLTokenGenerator<ShardingRule>, IgnoreForSingleRoute {
@Override
public Optional<RowCountToken> generateSQLToken(final SQLStatement sqlStatement, final ShardingRule shardingRule) {
......
......@@ -28,6 +28,9 @@ import org.apache.shardingsphere.core.optimize.result.OptimizeResult;
import org.apache.shardingsphere.core.parse.entry.EncryptSQLParseEntry;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.SQLRewriter;
import org.apache.shardingsphere.core.route.SQLUnit;
import org.apache.shardingsphere.core.rule.EncryptRule;
import org.junit.Before;
......@@ -185,7 +188,8 @@ public final class EncryptSQLRewriterTest {
SQLStatement sqlStatement = encryptSQLParseEngine.parse(sql, false);
SQLRewriteEngine sqlRewriteEngine = new SQLRewriteEngine(encryptRule, sqlStatement, parameters);
OptimizeResult optimizeResult = OptimizeEngineFactory.newInstance(encryptRule, sqlStatement, parameters).optimize();
sqlRewriteEngine.init(new EncryptSQLRewriter(encryptRule.getEncryptorEngine(), sqlStatement, optimizeResult));
sqlRewriteEngine.init(
Collections.<ParameterRewriter>emptyList(), Collections.<SQLRewriter>singletonList(new EncryptSQLRewriter(encryptRule.getEncryptorEngine(), sqlStatement, optimizeResult)));
return sqlRewriteEngine.generateSQL();
}
}
......@@ -59,6 +59,10 @@ import org.apache.shardingsphere.core.parse.sql.statement.dml.UpdateStatement;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.builder.ParameterBuilder;
import org.apache.shardingsphere.core.rewrite.builder.SQLBuilder;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ShardingParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.ShardingSQLRewriter;
import org.apache.shardingsphere.core.route.SQLRouteResult;
import org.apache.shardingsphere.core.route.limit.Limit;
import org.apache.shardingsphere.core.route.limit.LimitValue;
......@@ -549,10 +553,10 @@ public final class ShardingSQLRewriterTest {
routeResult = new SQLRouteResult(selectStatement);
routeResult.setRoutingResult(new RoutingResult());
selectStatement.setLogicSQL("SELECT table_x.id, x.name FROM table_x x, table_y y WHERE table_x.id=? AND x.name=?");
SQLRewriteEngine rewriteEngine = new SQLRewriteEngine(shardingRule, routeResult.getSqlStatement(), parameters);
rewriteEngine.init(
new ShardingSQLRewriter(shardingRule, DatabaseType.MySQL, routeResult, null),
new EncryptSQLRewriter(shardingRule.getEncryptRule().getEncryptorEngine(), routeResult.getSqlStatement(), routeResult.getOptimizeResult()));
SQLRewriteEngine rewriteEngine = new SQLRewriteEngine(shardingRule, routeResult.getSqlStatement(), parameters, routeResult.getRoutingResult().isSingleRouting());
rewriteEngine.init(Collections.<ParameterRewriter>singletonList(new ShardingParameterRewriter(DatabaseType.MySQL, routeResult)),
Arrays.asList(new ShardingSQLRewriter(shardingRule, DatabaseType.MySQL, routeResult, null),
new EncryptSQLRewriter(shardingRule.getEncryptRule().getEncryptorEngine(), routeResult.getSqlStatement(), routeResult.getOptimizeResult())));
RoutingUnit routingUnit = new RoutingUnit("db0");
routingUnit.getTableUnits().add(new TableUnit("table_x", "table_x"));
assertThat(rewriteEngine.generateSQL(routingUnit).getSql(), is("SELECT table_x.id, x.name FROM table_x x, table_y y WHERE table_x.id=? AND x.name=?"));
......@@ -917,10 +921,10 @@ public final class ShardingSQLRewriterTest {
}
private SQLRewriteEngine createSQLRewriteEngine(final DatabaseType databaseType, final List<Object> parameters) {
SQLRewriteEngine result = new SQLRewriteEngine(shardingRule, routeResult.getSqlStatement(), parameters);
result.init(
new ShardingSQLRewriter(shardingRule, databaseType, routeResult, routeResult.getOptimizeResult()),
new EncryptSQLRewriter(shardingRule.getEncryptRule().getEncryptorEngine(), routeResult.getSqlStatement(), routeResult.getOptimizeResult()));
SQLRewriteEngine result = new SQLRewriteEngine(shardingRule, routeResult.getSqlStatement(), parameters, routeResult.getRoutingResult().isSingleRouting());
result.init(Collections.<ParameterRewriter>singletonList(new ShardingParameterRewriter(DatabaseType.MySQL, routeResult)),
Arrays.asList(new ShardingSQLRewriter(shardingRule, databaseType, routeResult, routeResult.getOptimizeResult()),
new EncryptSQLRewriter(shardingRule.getEncryptRule().getEncryptorEngine(), routeResult.getSqlStatement(), routeResult.getOptimizeResult())));
return result;
}
}
......@@ -63,6 +63,6 @@ public final class PreparedStatementRoutingEngine {
if (null == sqlStatement) {
sqlStatement = shardingRouter.parse(logicSQL, true);
}
return masterSlaveRouter.route(shardingRouter.route(logicSQL, parameters, sqlStatement));
return masterSlaveRouter.route(shardingRouter.route(sqlStatement, parameters));
}
}
......@@ -54,6 +54,6 @@ public final class StatementRoutingEngine {
*/
public SQLRouteResult route(final String logicSQL) {
SQLStatement sqlStatement = shardingRouter.parse(logicSQL, false);
return masterSlaveRouter.route(shardingRouter.route(logicSQL, Collections.emptyList(), sqlStatement));
return masterSlaveRouter.route(shardingRouter.route(sqlStatement, Collections.emptyList()));
}
}
......@@ -23,7 +23,9 @@ import lombok.ToString;
import org.apache.shardingsphere.core.parse.exception.SQLParsingException;
import org.apache.shardingsphere.core.util.NumberUtil;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* Limit object.
......@@ -60,18 +62,11 @@ public final class Limit {
}
/**
* Fill parameters for rewrite limit.
* Fill parameters.
*
* @param parameters parameters
* @param isFetchAll is fetch all data or not
* @param databaseType database type
* @param parameters SQL parameters
*/
public void processParameters(final List<Object> parameters, final boolean isFetchAll, final String databaseType) {
fill(parameters);
rewrite(parameters, isFetchAll, databaseType);
}
private void fill(final List<Object> parameters) {
public void fillParameters(final List<Object> parameters) {
int offset = 0;
if (null != this.offset) {
offset = -1 == this.offset.getIndex() ? getOffsetValue() : NumberUtil.roundHalfUp(parameters.get(this.offset.getIndex()));
......@@ -87,7 +82,15 @@ public final class Limit {
}
}
private void rewrite(final List<Object> parameters, final boolean isFetchAll, final String databaseType) {
/**
* Revise parameters.
*
* @param isFetchAll is fetch all data or not
* @param databaseType database type
* @return revised indexes and parameters
*/
public Map<Integer, Object> getRevisedIndexAndParameters(final boolean isFetchAll, final String databaseType) {
Map<Integer, Object> result = new HashMap<>(2, 1);
int rewriteOffset = 0;
int rewriteRowCount;
if (isFetchAll) {
......@@ -98,11 +101,12 @@ public final class Limit {
rewriteRowCount = rowCount.getValue();
}
if (null != offset && offset.getIndex() > -1) {
parameters.set(offset.getIndex(), rewriteOffset);
result.put(offset.getIndex(), rewriteOffset);
}
if (null != rowCount && rowCount.getIndex() > -1) {
parameters.set(rowCount.getIndex(), rewriteRowCount);
result.put(rowCount.getIndex(), rewriteRowCount);
}
return result;
}
/**
......
......@@ -51,7 +51,7 @@ public final class DatabaseHintSQLRouter implements ShardingRouter {
@Override
// TODO insert SQL need parse gen key
public SQLRouteResult route(final String logicSQL, final List<Object> parameters, final SQLStatement sqlStatement) {
public SQLRouteResult route(final SQLStatement sqlStatement, final List<Object> parameters) {
SQLRouteResult result = new SQLRouteResult(sqlStatement);
RoutingResult routingResult = new DatabaseHintRoutingEngine(
shardingRule.getShardingDataSourceNames().getDataSourceNames(), (HintShardingStrategy) shardingRule.getDefaultDatabaseShardingStrategy()).route();
......
......@@ -91,7 +91,7 @@ public final class ParsingSQLRouter implements ShardingRouter {
}
@Override
public SQLRouteResult route(final String logicSQL, final List<Object> parameters, final SQLStatement sqlStatement) {
public SQLRouteResult route(final SQLStatement sqlStatement, final List<Object> parameters) {
Optional<GeneratedKey> generatedKey = sqlStatement instanceof InsertStatement
? GeneratedKey.getGenerateKey(shardingRule, parameters, (InsertStatement) sqlStatement) : Optional.<GeneratedKey>absent();
SQLRouteResult result = new SQLRouteResult(sqlStatement, generatedKey.orNull());
......@@ -109,7 +109,7 @@ public final class ParsingSQLRouter implements ShardingRouter {
}
RoutingResult routingResult = RoutingEngineFactory.newInstance(shardingRule, shardingMetaData.getDataSource(), sqlStatement, optimizeResult).route();
if (sqlStatement instanceof SelectStatement && null != ((SelectStatement) sqlStatement).getLimit() && !routingResult.isSingleRouting()) {
result.setLimit(getProcessedLimit(parameters, (SelectStatement) sqlStatement));
result.setLimit(createLimit((SelectStatement) sqlStatement, parameters));
}
if (needMerge) {
Preconditions.checkState(1 == routingResult.getRoutingUnits().size(), "Must have one sharding with subquery.");
......@@ -189,10 +189,9 @@ public final class ParsingSQLRouter implements ShardingRouter {
}
}
private Limit getProcessedLimit(final List<Object> parameters, final SelectStatement selectStatement) {
boolean isNeedFetchAll = (!selectStatement.getGroupByItems().isEmpty() || !selectStatement.getAggregationSelectItems().isEmpty()) && !selectStatement.isSameGroupByAndOrderByItems();
private Limit createLimit(final SelectStatement selectStatement, final List<Object> parameters) {
Limit result = createLimit(selectStatement.getLimit());
result.processParameters(parameters, isNeedFetchAll, databaseType.name());
result.fillParameters(parameters);
return result;
}
......
......@@ -41,10 +41,9 @@ public interface ShardingRouter {
/**
* Route SQL.
*
* @param logicSQL logic SQL
* @param sqlStatement SQL statement
* @param parameters parameters
* @return parse result
*/
SQLRouteResult route(String logicSQL, List<Object> parameters, SQLStatement sqlStatement);
SQLRouteResult route(SQLStatement sqlStatement, List<Object> parameters);
}
......@@ -66,6 +66,8 @@ public final class DatabaseHintSQLRouterTest {
@Test
public void assertRoute() {
hintManager.addDatabaseShardingValue("", 1);
assertNotNull(databaseHintSQLRouter.route("select t from tbl t", Collections.emptyList(), new DQLStatement()));
DQLStatement dqlStatement = new DQLStatement();
dqlStatement.setLogicSQL("select t from tbl t");
assertNotNull(databaseHintSQLRouter.route(dqlStatement, Collections.emptyList()));
}
}
......@@ -23,7 +23,9 @@ import org.apache.shardingsphere.core.optimize.OptimizeEngineFactory;
import org.apache.shardingsphere.core.optimize.result.OptimizeResult;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.rewriter.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.SQLRewriter;
import org.apache.shardingsphere.core.route.SQLUnit;
import org.apache.shardingsphere.shardingjdbc.jdbc.adapter.AbstractShardingPreparedStatementAdapter;
import org.apache.shardingsphere.shardingjdbc.jdbc.core.connection.EncryptConnection;
......@@ -35,6 +37,7 @@ import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Collection;
import java.util.Collections;
import java.util.LinkedList;
/**
......@@ -149,7 +152,8 @@ public final class EncryptPreparedStatement extends AbstractShardingPreparedStat
SQLStatement sqlStatement = connection.getParseEngine().parse(sql, true);
SQLRewriteEngine encryptSQLRewriteEngine = new SQLRewriteEngine(connection.getEncryptRule(), sqlStatement, getParameters());
OptimizeResult optimizeResult = OptimizeEngineFactory.newInstance(connection.getEncryptRule(), sqlStatement, getParameters()).optimize();
encryptSQLRewriteEngine.init(new EncryptSQLRewriter(connection.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult));
encryptSQLRewriteEngine.init(Collections.<ParameterRewriter>emptyList(),
Collections.<SQLRewriter>singletonList(new EncryptSQLRewriter(connection.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult)));
return encryptSQLRewriteEngine.generateSQL();
}
......
......@@ -22,7 +22,9 @@ import org.apache.shardingsphere.core.optimize.OptimizeEngineFactory;
import org.apache.shardingsphere.core.optimize.result.OptimizeResult;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.rewriter.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.SQLRewriter;
import org.apache.shardingsphere.shardingjdbc.jdbc.core.connection.EncryptConnection;
import org.apache.shardingsphere.shardingjdbc.jdbc.core.resultset.EncryptResultSet;
import org.apache.shardingsphere.shardingjdbc.jdbc.unsupported.AbstractUnsupportedOperationStatement;
......@@ -81,7 +83,8 @@ public final class EncryptStatement extends AbstractUnsupportedOperationStatemen
SQLStatement sqlStatement = connection.getParseEngine().parse(sql, false);
SQLRewriteEngine encryptSQLRewriteEngine = new SQLRewriteEngine(connection.getEncryptRule(), sqlStatement, Collections.emptyList());
OptimizeResult optimizeResult = OptimizeEngineFactory.newInstance(connection.getEncryptRule(), sqlStatement, Collections.emptyList()).optimize();
encryptSQLRewriteEngine.init(new EncryptSQLRewriter(connection.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult));
encryptSQLRewriteEngine.init(Collections.<ParameterRewriter>emptyList(),
Collections.<SQLRewriter>singletonList(new EncryptSQLRewriter(connection.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult)));
return encryptSQLRewriteEngine.generateSQL().getSql();
}
......
......@@ -25,7 +25,9 @@ import org.apache.shardingsphere.core.optimize.OptimizeEngineFactory;
import org.apache.shardingsphere.core.optimize.result.OptimizeResult;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.rewriter.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.SQLRewriter;
import org.apache.shardingsphere.core.route.RouteUnit;
import org.apache.shardingsphere.core.route.SQLRouteResult;
import org.apache.shardingsphere.core.route.SQLUnit;
......@@ -40,6 +42,7 @@ import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Collections;
import java.util.List;
/**
......@@ -77,7 +80,7 @@ public final class PreparedStatementExecutorWrapper implements JDBCExecutorWrapp
private SQLRouteResult doMasterSlaveRoute(final String sql) {
SQLStatement sqlStatement = ((MasterSlaveSchema) logicSchema).getParseEngine().parse(sql, true);
SQLRewriteEngine sqlRewriteEngine = new SQLRewriteEngine(sqlStatement);
sqlRewriteEngine.init();
sqlRewriteEngine.init(Collections.<ParameterRewriter>emptyList(), Collections.<SQLRewriter>emptyList());
String rewriteSQL = sqlRewriteEngine.generateSQL().getSql();
SQLRouteResult result = new SQLRouteResult(sqlStatement);
for (String each : new MasterSlaveRouter(((MasterSlaveSchema) logicSchema).getMasterSlaveRule(), ((MasterSlaveSchema) logicSchema).getParseEngine(),
......@@ -92,7 +95,8 @@ public final class PreparedStatementExecutorWrapper implements JDBCExecutorWrapp
SQLStatement sqlStatement = encryptSchema.getEncryptSQLParseEntry().parse(sql, true);
SQLRewriteEngine sqlRewriteEngine = new SQLRewriteEngine(encryptSchema.getEncryptRule(), sqlStatement, parameters);
OptimizeResult optimizeResult = OptimizeEngineFactory.newInstance(encryptSchema.getEncryptRule(), sqlStatement, parameters).optimize();
sqlRewriteEngine.init(new EncryptSQLRewriter(encryptSchema.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult));
sqlRewriteEngine.init(Collections.<ParameterRewriter>emptyList(),
Collections.<SQLRewriter>singletonList(new EncryptSQLRewriter(encryptSchema.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult)));
SQLRouteResult result = new SQLRouteResult(sqlStatement);
result.getRouteUnits().add(new RouteUnit(logicSchema.getDataSources().keySet().iterator().next(), new SQLUnit(sqlRewriteEngine.generateSQL().getSql(), parameters)));
return result;
......
......@@ -25,7 +25,9 @@ import org.apache.shardingsphere.core.optimize.OptimizeEngineFactory;
import org.apache.shardingsphere.core.optimize.result.OptimizeResult;
import org.apache.shardingsphere.core.parse.sql.statement.SQLStatement;
import org.apache.shardingsphere.core.rewrite.SQLRewriteEngine;
import org.apache.shardingsphere.core.rewrite.rewriter.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.parameter.ParameterRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.EncryptSQLRewriter;
import org.apache.shardingsphere.core.rewrite.rewriter.sql.SQLRewriter;
import org.apache.shardingsphere.core.route.RouteUnit;
import org.apache.shardingsphere.core.route.SQLRouteResult;
import org.apache.shardingsphere.core.route.SQLUnit;
......@@ -78,7 +80,7 @@ public final class StatementExecutorWrapper implements JDBCExecutorWrapper {
private SQLRouteResult doMasterSlaveRoute(final String sql) {
SQLStatement sqlStatement = ((MasterSlaveSchema) logicSchema).getParseEngine().parse(sql, false);
SQLRewriteEngine sqlRewriteEngine = new SQLRewriteEngine(sqlStatement);
sqlRewriteEngine.init();
sqlRewriteEngine.init(Collections.<ParameterRewriter>emptyList(), Collections.<SQLRewriter>emptyList());
String rewriteSQL = sqlRewriteEngine.generateSQL().getSql();
SQLRouteResult result = new SQLRouteResult(sqlStatement);
for (String each : new MasterSlaveRouter(((MasterSlaveSchema) logicSchema).getMasterSlaveRule(), ((MasterSlaveSchema) logicSchema).getParseEngine(),
......@@ -93,7 +95,8 @@ public final class StatementExecutorWrapper implements JDBCExecutorWrapper {
SQLStatement sqlStatement = encryptSchema.getEncryptSQLParseEntry().parse(sql, false);
SQLRewriteEngine sqlRewriteEngine = new SQLRewriteEngine(encryptSchema.getEncryptRule(), sqlStatement, Collections.emptyList());
OptimizeResult optimizeResult = OptimizeEngineFactory.newInstance(encryptSchema.getEncryptRule(), sqlStatement, new LinkedList<>()).optimize();
sqlRewriteEngine.init(new EncryptSQLRewriter(encryptSchema.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult));
sqlRewriteEngine.init(Collections.<ParameterRewriter>emptyList(),
Collections.<SQLRewriter>singletonList(new EncryptSQLRewriter(encryptSchema.getEncryptRule().getEncryptorEngine(), sqlStatement, optimizeResult)));
SQLRouteResult result = new SQLRouteResult(sqlStatement);
result.getRouteUnits().add(new RouteUnit(logicSchema.getDataSources().keySet().iterator().next(), new SQLUnit(sqlRewriteEngine.generateSQL().getSql(), Collections.emptyList())));
return result;
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册