diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/AssignmentExtractor.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/AssignmentExtractor.java index 46c9e3dd42098..6d48b1439ca17 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/AssignmentExtractor.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/AssignmentExtractor.java @@ -27,7 +27,8 @@ import org.apache.shardingsphere.core.parse.antlr.extractor.util.RuleName; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.assignment.AssignmentSegment; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.column.ColumnSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ParameterMarkerExpressionSegment; import java.util.Map; @@ -51,7 +52,10 @@ public Optional extract(final ParserRuleContext ancestorNode, } Optional columnSegment = columnExtractor.extract((ParserRuleContext) assignmentNode.get().getChild(0), parameterMarkerIndexes); Preconditions.checkState(columnSegment.isPresent()); - LiteralExpressionSegment expressionSegment = expressionExtractor.extractLiteralExpressionSegment((ParserRuleContext) assignmentNode.get().getChild(2), parameterMarkerIndexes); + Optional parameterMarkerExpressionSegment = expressionExtractor.extractParameterMarkerExpressionSegment( + (ParserRuleContext) assignmentNode.get().getChild(2), parameterMarkerIndexes); + ExpressionSegment expressionSegment = parameterMarkerExpressionSegment.isPresent() + ? parameterMarkerExpressionSegment.get() : expressionExtractor.extractLiteralExpressionSegment((ParserRuleContext) assignmentNode.get().getChild(2)); return Optional.of(new AssignmentSegment(columnSegment.get(), expressionSegment)); } } diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/ExpressionExtractor.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/ExpressionExtractor.java index 69285b432e14c..31125d84aca5f 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/ExpressionExtractor.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/ExpressionExtractor.java @@ -18,6 +18,7 @@ package org.apache.shardingsphere.core.parse.antlr.extractor.impl.dml; import com.google.common.base.Optional; +import com.google.common.base.Preconditions; import org.antlr.v4.runtime.ParserRuleContext; import org.apache.shardingsphere.core.parse.antlr.extractor.api.OptionalSQLSegmentExtractor; import org.apache.shardingsphere.core.parse.antlr.extractor.impl.dml.select.SubqueryExtractor; @@ -26,6 +27,7 @@ import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.CommonExpressionSegment; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ParameterMarkerExpressionSegment; import org.apache.shardingsphere.core.util.NumberUtil; import java.util.Map; @@ -46,26 +48,36 @@ public Optional extract(final ParserRuleContext exp private ExpressionSegment extractExpression(final ParserRuleContext expressionNode, final Map parameterMarkerIndexes) { Optional parameterMarkerNode = ExtractorUtils.findSingleNodeFromFirstDescendant(expressionNode, RuleName.PARAMETER_MARKER); if (parameterMarkerNode.isPresent()) { - return extractLiteralExpressionSegment(parameterMarkerNode.get(), parameterMarkerIndexes); + Optional result = extractParameterMarkerExpressionSegment(parameterMarkerNode.get(), parameterMarkerIndexes); + Preconditions.checkState(result.isPresent()); + return result.get(); } Optional literalsNode = ExtractorUtils.findSingleNodeFromFirstDescendant(expressionNode, RuleName.LITERALS); - return literalsNode.isPresent() ? extractLiteralExpressionSegment(literalsNode.get(), parameterMarkerIndexes) : extractCommonExpressionSegment(expressionNode); + return literalsNode.isPresent() ? extractLiteralExpressionSegment(literalsNode.get()) : extractCommonExpressionSegment(expressionNode); } /** - * Extract literal expression segment. + * Extract parameter marker expression segment. * * @param parameterMarkerIndexes parameter marker indexes * @param expressionNode expression node - * @return common expression segment + * @return parameter marker expression segment */ - public LiteralExpressionSegment extractLiteralExpressionSegment(final ParserRuleContext expressionNode, final Map parameterMarkerIndexes) { - LiteralExpressionSegment result = new LiteralExpressionSegment(expressionNode.getStart().getStartIndex(), expressionNode.getStop().getStopIndex()); + public Optional extractParameterMarkerExpressionSegment(final ParserRuleContext expressionNode, final Map parameterMarkerIndexes) { Optional parameterMarkerNode = ExtractorUtils.findFirstChildNode(expressionNode, RuleName.PARAMETER_MARKER); - if (parameterMarkerNode.isPresent()) { - result.setParameterMarkerIndex(parameterMarkerIndexes.get(parameterMarkerNode.get())); - return result; - } + return parameterMarkerNode.isPresent() + ? Optional.of(new ParameterMarkerExpressionSegment(expressionNode.getStart().getStartIndex(), expressionNode.getStop().getStopIndex(), + parameterMarkerIndexes.get(parameterMarkerNode.get()))) : Optional.absent(); + } + + /** + * Extract literal expression segment. + * + * @param expressionNode expression node + * @return literal expression segment + */ + public LiteralExpressionSegment extractLiteralExpressionSegment(final ParserRuleContext expressionNode) { + LiteralExpressionSegment result = new LiteralExpressionSegment(expressionNode.getStart().getStartIndex(), expressionNode.getStop().getStopIndex()); Optional numberLiteralsNode = ExtractorUtils.findFirstChildNode(expressionNode, RuleName.NUMBER_LITERALS); if (numberLiteralsNode.isPresent()) { result.setLiterals(NumberUtil.getExactlyNumber(numberLiteralsNode.get().getText(), 10)); diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/insert/InsertValuesExtractor.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/insert/InsertValuesExtractor.java index fa179c7c77fcb..5205f249e3587 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/insert/InsertValuesExtractor.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/extractor/impl/dml/insert/InsertValuesExtractor.java @@ -24,7 +24,8 @@ import org.apache.shardingsphere.core.parse.antlr.extractor.util.ExtractorUtils; import org.apache.shardingsphere.core.parse.antlr.extractor.util.RuleName; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.InsertValuesSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ParameterMarkerExpressionSegment; import java.util.Collection; import java.util.Collections; @@ -48,15 +49,20 @@ public Collection extract(final ParserRuleContext ancestorN } Collection result = new LinkedList<>(); for (ParserRuleContext each : ExtractorUtils.getAllDescendantNodes(insertValuesClauseNode.get(), RuleName.ASSIGNMENT_VALUES)) { - result.add(new InsertValuesSegment(extractCommonExpressionSegments(each, parameterMarkerIndexes))); + result.add(new InsertValuesSegment(extractExpressionSegments(each, parameterMarkerIndexes))); } return result; } - private Collection extractCommonExpressionSegments(final ParserRuleContext assignmentValuesNode, final Map parameterMarkerIndexes) { - Collection result = new LinkedList<>(); + private Collection extractExpressionSegments(final ParserRuleContext assignmentValuesNode, final Map parameterMarkerIndexes) { + Collection result = new LinkedList<>(); for (ParserRuleContext each : ExtractorUtils.getAllDescendantNodes(assignmentValuesNode, RuleName.ASSIGNMENT_VALUE)) { - result.add(expressionExtractor.extractLiteralExpressionSegment(each, parameterMarkerIndexes)); + Optional parameterMarkerExpressionSegment = expressionExtractor.extractParameterMarkerExpressionSegment(each, parameterMarkerIndexes); + if (parameterMarkerExpressionSegment.isPresent()) { + result.add(parameterMarkerExpressionSegment.get()); + } else { + result.add(expressionExtractor.extractLiteralExpressionSegment(each)); + } } return result; } diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/encrypt/dml/insert/EncryptInsertValuesFiller.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/encrypt/dml/insert/EncryptInsertValuesFiller.java index 568d150ef44ce..b2934afff83a1 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/encrypt/dml/insert/EncryptInsertValuesFiller.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/encrypt/dml/insert/EncryptInsertValuesFiller.java @@ -19,7 +19,7 @@ import org.apache.shardingsphere.core.parse.antlr.filler.api.SQLSegmentFiller; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.InsertValuesSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; import org.apache.shardingsphere.core.parse.antlr.sql.statement.SQLStatement; import org.apache.shardingsphere.core.parse.antlr.sql.statement.dml.InsertStatement; import org.apache.shardingsphere.core.parse.old.parser.context.insertvalue.InsertValue; @@ -45,7 +45,7 @@ public void fill(final InsertValuesSegment sqlSegment, final SQLStatement sqlSta private InsertValue getInsertValue(final InsertValuesSegment sqlSegment, final String sql) { List columnValues = new LinkedList<>(); - for (LiteralExpressionSegment each : sqlSegment.getValues()) { + for (ExpressionSegment each : sqlSegment.getValues()) { SQLExpression sqlExpression = each.getSQLExpression(sql); columnValues.add(sqlExpression); } diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/ShardingSetAssignmentsFiller.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/ShardingSetAssignmentsFiller.java index af3c244573856..89ae0e3ed743a 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/ShardingSetAssignmentsFiller.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/ShardingSetAssignmentsFiller.java @@ -25,7 +25,7 @@ import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.assignment.AssignmentSegment; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.assignment.SetAssignmentsSegment; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.column.ColumnSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; import org.apache.shardingsphere.core.parse.antlr.sql.statement.SQLStatement; import org.apache.shardingsphere.core.parse.antlr.sql.statement.dml.InsertStatement; import org.apache.shardingsphere.core.parse.antlr.sql.statement.dml.UpdateStatement; @@ -107,7 +107,7 @@ private int getColumnCountExcludeAssistedQueryColumns(final InsertStatement inse return insertStatement.getColumnNames().size() - assistedQueryColumnCount; } - private SQLExpression getColumnValue(final InsertStatement insertStatement, final AndCondition andCondition, final String columnName, final LiteralExpressionSegment expressionSegment) { + private SQLExpression getColumnValue(final InsertStatement insertStatement, final AndCondition andCondition, final String columnName, final ExpressionSegment expressionSegment) { SQLExpression result = expressionSegment.getSQLExpression(insertStatement.getLogicSQL()); String tableName = insertStatement.getTables().getSingleTableName(); fillShardingCondition(andCondition, columnName, tableName, result); diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/insert/InsertValuesFiller.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/insert/InsertValuesFiller.java index f0fa9cef0f75b..92db4fa7bf483 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/insert/InsertValuesFiller.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/filler/sharding/dml/insert/InsertValuesFiller.java @@ -22,7 +22,7 @@ import org.apache.shardingsphere.core.parse.antlr.filler.api.SQLSegmentFiller; import org.apache.shardingsphere.core.parse.antlr.filler.api.ShardingRuleAwareFiller; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.InsertValuesSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; import org.apache.shardingsphere.core.parse.antlr.sql.statement.SQLStatement; import org.apache.shardingsphere.core.parse.antlr.sql.statement.dml.InsertStatement; import org.apache.shardingsphere.core.parse.old.parser.context.condition.AndCondition; @@ -58,7 +58,7 @@ public void fill(final InsertValuesSegment sqlSegment, final SQLStatement sqlSta AndCondition andCondition = new AndCondition(); Iterator columnNames = getColumnNames(sqlSegment, insertStatement); List columnValues = new LinkedList<>(); - for (LiteralExpressionSegment each : sqlSegment.getValues()) { + for (ExpressionSegment each : sqlSegment.getValues()) { String columnName = columnNames.next(); SQLExpression columnValue = getColumnValue(insertStatement, andCondition, columnName, each); columnValues.add(columnValue); @@ -78,7 +78,7 @@ private Iterator getColumnNames(final InsertValuesSegment sqlSegment, fi return result.iterator(); } - private SQLExpression getColumnValue(final InsertStatement insertStatement, final AndCondition andCondition, final String columnName, final LiteralExpressionSegment expressionSegment) { + private SQLExpression getColumnValue(final InsertStatement insertStatement, final AndCondition andCondition, final String columnName, final ExpressionSegment expressionSegment) { SQLExpression result = expressionSegment.getSQLExpression(insertStatement.getLogicSQL()); String tableName = insertStatement.getTables().getSingleTableName(); fillShardingCondition(andCondition, tableName, columnName, result); diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/InsertValuesSegment.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/InsertValuesSegment.java index 727a551ac99f2..672858de6567b 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/InsertValuesSegment.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/InsertValuesSegment.java @@ -20,7 +20,7 @@ import lombok.Getter; import lombok.RequiredArgsConstructor; import org.apache.shardingsphere.core.parse.antlr.sql.segment.SQLSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; import java.util.Collection; @@ -34,5 +34,5 @@ @Getter public final class InsertValuesSegment implements SQLSegment { - private final Collection values; + private final Collection values; } diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/assignment/AssignmentSegment.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/assignment/AssignmentSegment.java index b455ed63d7fdc..914566a8510a4 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/assignment/AssignmentSegment.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/assignment/AssignmentSegment.java @@ -21,7 +21,7 @@ import lombok.RequiredArgsConstructor; import org.apache.shardingsphere.core.parse.antlr.sql.segment.SQLSegment; import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.column.ColumnSegment; -import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.LiteralExpressionSegment; +import org.apache.shardingsphere.core.parse.antlr.sql.segment.dml.expr.ExpressionSegment; /** * Assignment segment. @@ -34,5 +34,5 @@ public final class AssignmentSegment implements SQLSegment { private final ColumnSegment column; - private final LiteralExpressionSegment value; + private final ExpressionSegment value; } diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/LiteralExpressionSegment.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/LiteralExpressionSegment.java index e61e56b6fd183..b2317bce3f19c 100644 --- a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/LiteralExpressionSegment.java +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/LiteralExpressionSegment.java @@ -23,7 +23,6 @@ import org.apache.shardingsphere.core.parse.old.lexer.token.DefaultKeyword; import org.apache.shardingsphere.core.parse.old.parser.expression.SQLExpression; import org.apache.shardingsphere.core.parse.old.parser.expression.SQLNumberExpression; -import org.apache.shardingsphere.core.parse.old.parser.expression.SQLPlaceholderExpression; import org.apache.shardingsphere.core.parse.old.parser.expression.SQLTextExpression; /** @@ -42,15 +41,10 @@ public final class LiteralExpressionSegment implements ExpressionSegment { private final int stopIndex; - private int parameterMarkerIndex = -1; - private Object literals; @Override public SQLExpression getSQLExpression(final String sql) { - if (-1 != parameterMarkerIndex) { - return new SQLPlaceholderExpression(parameterMarkerIndex); - } if (literals instanceof Number) { return new SQLNumberExpression((Number) literals); } diff --git a/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/ParameterMarkerExpressionSegment.java b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/ParameterMarkerExpressionSegment.java new file mode 100644 index 0000000000000..42f88ad5ef9b0 --- /dev/null +++ b/sharding-core/sharding-core-parse/sharding-core-parse-common/src/main/java/org/apache/shardingsphere/core/parse/antlr/sql/segment/dml/expr/ParameterMarkerExpressionSegment.java @@ -0,0 +1,44 @@ +/* + * 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.parse.antlr.sql.segment.dml.expr; + +import lombok.Getter; +import lombok.RequiredArgsConstructor; +import org.apache.shardingsphere.core.parse.old.parser.expression.SQLExpression; +import org.apache.shardingsphere.core.parse.old.parser.expression.SQLPlaceholderExpression; + +/** + * Parameter marker expression segment. + * + * @author zhangliang + */ +@RequiredArgsConstructor +@Getter +public final class ParameterMarkerExpressionSegment implements ExpressionSegment { + + private final int startIndex; + + private final int stopIndex; + + private final int parameterMarkerIndex; + + @Override + public SQLExpression getSQLExpression(final String sql) { + return new SQLPlaceholderExpression(parameterMarkerIndex); + } +}