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/06/05 09:05:55 UTC

[shardingsphere] branch master updated: Fix oracle parse when projection contains parameter (#26055)

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 d647ecc3efe Fix oracle parse when projection contains parameter (#26055)
d647ecc3efe is described below

commit d647ecc3efe2b06253f7e134f91479e37083a6d5
Author: Zhengqiang Duan <du...@apache.org>
AuthorDate: Mon Jun 5 17:05:38 2023 +0800

    Fix oracle parse when projection contains parameter (#26055)
---
 .../statement/type/OracleDMLStatementVisitor.java  | 34 +++++-----------------
 .../simple/ParameterMarkerExpressionSegment.java   |  5 ++++
 .../parser/src/main/resources/case/dml/select.xml  | 28 ++++++++++++++++++
 .../main/resources/sql/supported/dml/select.xml    |  1 +
 4 files changed, 41 insertions(+), 27 deletions(-)

diff --git a/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/type/OracleDMLStatementVisitor.java b/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/type/OracleDMLStatementVisitor.java
index 9f289342724..5eee6f69429 100644
--- a/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/type/OracleDMLStatementVisitor.java
+++ b/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/type/OracleDMLStatementVisitor.java
@@ -124,7 +124,6 @@ import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.complex.
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.expr.simple.LiteralExpressionSegment;
 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.segment.dml.item.AggregationProjectionSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ColumnProjectionSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.DatetimeProjectionSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.item.ExpressionProjectionSegment;
@@ -141,6 +140,7 @@ import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.order.item.Or
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.predicate.HavingSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.predicate.LockSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.dml.predicate.WhereSegment;
+import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.AliasAvailable;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.AliasSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.InsertMultiTableElementSegment;
 import org.apache.shardingsphere.sql.parser.sql.common.segment.generic.ModelSegment;
@@ -686,14 +686,6 @@ public final class OracleDMLStatementVisitor extends OracleStatementVisitor impl
     private ASTNode createProjection(final SelectProjectionExprClauseContext ctx) {
         AliasSegment alias = null == ctx.alias() ? null : (AliasSegment) visit(ctx.alias());
         ASTNode projection = visit(ctx.expr());
-        if (projection instanceof AggregationProjectionSegment) {
-            ((AggregationProjectionSegment) projection).setAlias(alias);
-            return projection;
-        }
-        if (projection instanceof ExpressionProjectionSegment) {
-            ((ExpressionProjectionSegment) projection).setAlias(alias);
-            return projection;
-        }
         if (projection instanceof FunctionSegment) {
             FunctionSegment segment = (FunctionSegment) projection;
             ExpressionProjectionSegment result = new ExpressionProjectionSegment(segment.getStartIndex(), segment.getStopIndex(), segment.getText(), segment);
@@ -734,24 +726,12 @@ public final class OracleDMLStatementVisitor extends OracleStatementVisitor impl
                     : new DatetimeProjectionSegment(datetimeExpression.getStartIndex(), datetimeExpression.getStopIndex(),
                             datetimeExpression.getLeft(), datetimeExpression.getRight(), datetimeExpression.getText());
         }
-        if (projection instanceof XmlQueryAndExistsFunctionSegment) {
-            XmlQueryAndExistsFunctionSegment xmlExistsFunctionSegment = (XmlQueryAndExistsFunctionSegment) projection;
-            return new XmlQueryAndExistsFunctionSegment(xmlExistsFunctionSegment.getStartIndex(),
-                    xmlExistsFunctionSegment.getStopIndex(), xmlExistsFunctionSegment.getFunctionName(), xmlExistsFunctionSegment.getXQueryString(), xmlExistsFunctionSegment.getText());
-        }
-        if (projection instanceof XmlPiFunctionSegment) {
-            XmlPiFunctionSegment xmlPiFunctionSegment = (XmlPiFunctionSegment) projection;
-            return null == xmlPiFunctionSegment.getIdentifier()
-                    ? new XmlPiFunctionSegment(xmlPiFunctionSegment.getStartIndex(), xmlPiFunctionSegment.getStopIndex(),
-                            xmlPiFunctionSegment.getFunctionName(), xmlPiFunctionSegment.getEvalNameValueExpr(), xmlPiFunctionSegment.getValueExpr(), xmlPiFunctionSegment.getText())
-                    : new XmlPiFunctionSegment(xmlPiFunctionSegment.getStartIndex(), xmlPiFunctionSegment.getStopIndex(),
-                            xmlPiFunctionSegment.getFunctionName(), xmlPiFunctionSegment.getIdentifier(), xmlPiFunctionSegment.getValueExpr(), xmlPiFunctionSegment.getText());
-        }
-        if (projection instanceof XmlSerializeFunctionSegment) {
-            XmlSerializeFunctionSegment xmlSerializeFunctionSegment = (XmlSerializeFunctionSegment) projection;
-            return new XmlSerializeFunctionSegment(xmlSerializeFunctionSegment.getStartIndex(), xmlSerializeFunctionSegment.getStopIndex(), xmlSerializeFunctionSegment.getFunctionName(),
-                    xmlSerializeFunctionSegment.getParameter(), xmlSerializeFunctionSegment.getDataType(), xmlSerializeFunctionSegment.getEncoding(), xmlSerializeFunctionSegment.getVersion(),
-                    xmlSerializeFunctionSegment.getIdentSize(), xmlSerializeFunctionSegment.getText());
+        if (projection instanceof XmlQueryAndExistsFunctionSegment || projection instanceof XmlPiFunctionSegment || projection instanceof XmlSerializeFunctionSegment) {
+            return projection;
+        }
+        if (projection instanceof AliasAvailable) {
+            ((AliasAvailable) projection).setAlias(alias);
+            return projection;
         }
         LiteralExpressionSegment column = (LiteralExpressionSegment) projection;
         ExpressionProjectionSegment result = null == alias
diff --git a/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/expr/simple/ParameterMarkerExpressionSegment.java b/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/expr/simple/ParameterMarkerExpressionSegment.java
index 9cd81f1912b..62401242ffb 100644
--- a/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/expr/simple/ParameterMarkerExpressionSegment.java
+++ b/parser/sql/statement/src/main/java/org/apache/shardingsphere/sql/parser/sql/common/segment/dml/expr/simple/ParameterMarkerExpressionSegment.java
@@ -69,4 +69,9 @@ public class ParameterMarkerExpressionSegment implements SimpleExpressionSegment
     public int getParameterIndex() {
         return parameterMarkerIndex;
     }
+    
+    @Override
+    public int getStopIndex() {
+        return null != alias ? alias.getStopIndex() : stopIndex;
+    }
 }
diff --git a/test/it/parser/src/main/resources/case/dml/select.xml b/test/it/parser/src/main/resources/case/dml/select.xml
index c3b9929a0b8..17af6381dc4 100644
--- a/test/it/parser/src/main/resources/case/dml/select.xml
+++ b/test/it/parser/src/main/resources/case/dml/select.xml
@@ -4939,4 +4939,32 @@
             </expression-projection>
         </projections>
     </select>
+
+    <select sql-case-id="select_projection_with_parameter" parameters="'OK'">
+        <projections start-index="7" stop-index="81" literal-stop-index="84">
+            <expression-projection text="1" start-index="7" stop-index="13" alias="id">
+                <expr>
+                    <literal-expression value="1" start-index="7" stop-index="7" />
+                </expr>
+            </expression-projection>
+            <expression-projection text="OK" start-index="16" stop-index="26" literal-stop-index="29" alias="status">
+                <expr>
+                    <literal-expression value="OK" start-index="16" stop-index="19" />
+                </expr>
+            </expression-projection>
+            <column-projection name="SYSDATE" start-index="29" stop-index="50" literal-start-index="32" literal-stop-index="53" alias="create_time" />
+            <expression-projection text="TRUNC(SYSDATE)" start-index="53" stop-index="81" literal-start-index="56" literal-stop-index="84" alias="create_date">
+                <expr>
+                    <function function-name="TRUNC" start-index="53" stop-index="66" literal-start-index="56" literal-stop-index="69" text="TRUNC(SYSDATE)">
+                        <parameter>
+                            <column name="SYSDATE" start-index="59" stop-index="65" literal-start-index="62" literal-stop-index="68" />
+                        </parameter>
+                    </function>
+                </expr>
+            </expression-projection>
+        </projections>
+        <from>
+            <simple-table name="DUAL" start-index="88" stop-index="91" literal-start-index="91" literal-stop-index="94" />
+        </from>
+    </select>
 </sql-parser-test-cases>
diff --git a/test/it/parser/src/main/resources/sql/supported/dml/select.xml b/test/it/parser/src/main/resources/sql/supported/dml/select.xml
index 843d70ca529..3d2035bff7e 100644
--- a/test/it/parser/src/main/resources/sql/supported/dml/select.xml
+++ b/test/it/parser/src/main/resources/sql/supported/dml/select.xml
@@ -161,4 +161,5 @@
     <sql-case id="select_positional_parameter_type_cast_money" value="SELECT $1::money" db-types="PostgreSQL,openGauss" case-types="Placeholder" />
     <sql-case id="select_string_constant_type_cast" value="SELECT int4 '1', money '2'" db-types="PostgreSQL,openGauss" />
     <sql-case id="select_constant_with_nested_type_cast" value="SELECT CAST(MONEY '1' AS VARCHAR)::CHAR(10)::VARCHAR::CHAR(4)" db-types="PostgreSQL,openGauss"  />
+    <sql-case id="select_projection_with_parameter" value="SELECT 1 AS id, ? AS status, SYSDATE AS create_time, TRUNC(SYSDATE) AS create_date FROM DUAL" db-types="Oracle"  />
 </sql-cases>