This is an automated email from the ASF dual-hosted git repository.
duanzhengqiang 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 8ed52536168 Support oracle wm_concat function parse (#28945)
8ed52536168 is described below
commit 8ed525361686d0febb63d3adba3b25fde6b8ceba
Author: niu niu <[email protected]>
AuthorDate: Mon Nov 6 08:00:43 2023 +0800
Support oracle wm_concat function parse (#28945)
---
.../src/main/antlr4/imports/oracle/BaseRule.g4 | 6 +-
.../src/main/antlr4/imports/oracle/Keyword.g4 | 4 +
.../visitor/statement/OracleStatementVisitor.java | 11 ++
.../parser/src/main/resources/case/dml/select.xml | 142 +++++++++++++++++++++
.../main/resources/sql/supported/dml/select.xml | 4 +
5 files changed, 166 insertions(+), 1 deletion(-)
diff --git
a/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/BaseRule.g4
b/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/BaseRule.g4
index de4c4074888..d18cb9e3b86 100644
--- a/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/BaseRule.g4
+++ b/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/BaseRule.g4
@@ -783,7 +783,11 @@ leadLagInfo
specialFunction
: castFunction | charFunction | extractFunction | formatFunction |
firstOrLastValueFunction | trimFunction | featureFunction
- | setFunction | translateFunction | cursorFunction | toDateFunction |
approxRank
+ | setFunction | translateFunction | cursorFunction | toDateFunction |
approxRank | wmConcatFunction
+ ;
+
+wmConcatFunction
+ : WM_CONCAT LP_ expr RP_ overClause?
;
approxRank
diff --git
a/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/Keyword.g4
b/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/Keyword.g4
index 37d228e1e22..0580c89348a 100644
--- a/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/Keyword.g4
+++ b/parser/sql/dialect/oracle/src/main/antlr4/imports/oracle/Keyword.g4
@@ -835,3 +835,7 @@ ANYDATASET
AUTONOMOUS_TRANSACTION
: A U T O N O M O U S UL_ T R A N S A C T I O N
;
+
+WM_CONCAT
+ : W M UL_ C O N C A T
+ ;
diff --git
a/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/OracleStatementVisitor.java
b/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/OracleStatementVisitor.java
index 915d2a392c1..7b375b5e28a 100644
---
a/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/OracleStatementVisitor.java
+++
b/parser/sql/dialect/oracle/src/main/java/org/apache/shardingsphere/sql/parser/oracle/visitor/statement/OracleStatementVisitor.java
@@ -85,6 +85,7 @@ import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.TrimFu
import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.TypeNameContext;
import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.UnreservedWordContext;
import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.ViewNameContext;
+import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.WmConcatFunctionContext;
import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.XmlAggFunctionContext;
import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.XmlCdataFunctionContext;
import
org.apache.shardingsphere.sql.parser.autogen.OracleStatementParser.XmlColattvalFunctionContext;
@@ -710,6 +711,13 @@ public abstract class OracleStatementVisitor extends
OracleStatementBaseVisitor<
: createAggregationFunctionSegment(ctx, aggregationType);
}
+ @Override
+ public ASTNode visitWmConcatFunction(final WmConcatFunctionContext ctx) {
+ FunctionSegment result = new
FunctionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(),
ctx.WM_CONCAT().getText(), getOriginalText(ctx));
+ result.getParameters().add((ExpressionSegment) visit(ctx.expr()));
+ return result;
+ }
+
private FunctionSegment createAggregationFunctionSegment(final
AggregationFunctionContext ctx, final String aggregationType) {
FunctionSegment result = new
FunctionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(),
aggregationType, getOriginalText(ctx));
result.getParameters().addAll(getExpressions(ctx.expr()));
@@ -982,6 +990,9 @@ public abstract class OracleStatementVisitor extends
OracleStatementBaseVisitor<
if (null != ctx.approxRank()) {
return visit(ctx.approxRank());
}
+ if (null != ctx.wmConcatFunction()) {
+ return visit(ctx.wmConcatFunction());
+ }
throw new IllegalStateException(
"SpecialFunctionContext must have castFunction, charFunction,
extractFunction, formatFunction, firstOrLastValueFunction, trimFunction,
toDateFunction, approxCount"
+ " or featureFunction.");
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 9dd07a52faf..8a497f44e3c 100644
--- a/test/it/parser/src/main/resources/case/dml/select.xml
+++ b/test/it/parser/src/main/resources/case/dml/select.xml
@@ -7032,4 +7032,146 @@
literal-stop-index="32"/>
</from>
</select>
+
+ <select sql-case-id="select_wm_concat_function1">
+ <projections start-index="7" stop-index="72">
+ <expression-projection alias="ID" text="TO_CHAR(WM_CONCAT(DISTINCT
TEST_ID) OVER(PARTITION BY TEST_ID))" start-index="7" stop-index="72">
+ <expr>
+ <function alias="ID" function-name="TO_CHAR"
text="TO_CHAR(WM_CONCAT(DISTINCT TEST_ID) OVER(PARTITION BY TEST_ID))"
start-index="7" stop-index="69">
+ <parameter>
+ <function alias="ID" function-name="WM_CONCAT"
text="WM_CONCAT(DISTINCT TEST_ID) OVER(PARTITION BY TEST_ID)" start-index="15"
stop-index="68">
+ <parameter>
+ <column name="TEST_ID" start-index="34"
stop-index="40" />
+ </parameter>
+ </function>
+ </parameter>
+ </function>
+ </expr>
+ </expression-projection>
+ </projections>
+ <from>
+ <simple-table name="TEST_TABLE" start-index="79" stop-index="88" />
+ </from>
+ </select>
+
+ <select sql-case-id="select_wm_concat_function2">
+ <projections start-index="7" stop-index="26">
+ <expression-projection alias="NAME" text="WM_CONCAT(NAME)"
start-index="7" stop-index="26">
+ <expr>
+ <function alias="ID" function-name="WM_CONCAT"
text="WM_CONCAT(NAME)" start-index="7" stop-index="21">
+ <parameter>
+ <column name="NAME" start-index="17"
stop-index="20" />
+ </parameter>
+ </function>
+ </expr>
+ </expression-projection>
+ </projections>
+ <from>
+ <simple-table name="TEST_TABLE" start-index="33" stop-index="42" />
+ </from>
+ </select>
+
+ <select sql-case-id="select_wm_concat_function3">
+ <projections start-index="7" stop-index="38">
+ <expression-projection text="REPLACE(WM_CONCAT(NAME),',','|')"
start-index="7" stop-index="38">
+ <expr>
+ <function function-name="REPLACE"
text="REPLACE(WM_CONCAT(NAME),',','|')" start-index="7" stop-index="38">
+ <parameter>
+ <function alias="ID" function-name="WM_CONCAT"
text="WM_CONCAT(NAME)" start-index="15" stop-index="29">
+ <parameter>
+ <column name="NAME" start-index="25"
stop-index="28" />
+ </parameter>
+ </function>
+ </parameter>
+ <parameter>
+ <literal-expression start-index="31"
stop-index="33" value="," />
+ </parameter>
+ <parameter>
+ <literal-expression start-index="35"
stop-index="37" value="|" />
+ </parameter>
+ </function>
+ </expr>
+ </expression-projection>
+ </projections>
+ <from>
+ <simple-table name="TEST_TABLE" start-index="45" stop-index="54" />
+ </from>
+ </select>
+
+ <select sql-case-id="select_wm_concat_function4">
+ <projections start-index="7" stop-index="102">
+ <column-projection name="NAME" start-index="7" stop-index="10" />
+ <expression-projection alias="WM_NAME"
text="WM_CONCAT(DECODE(SUBSTR((TO_CHAR(NAME)),0,1),'.','0'||TO_CHAR(NAME),TO_CHAR(NAME)))"
start-index="12" stop-index="102">
+ <expr>
+ <function function-name="WM_CONCAT"
text="WM_CONCAT(DECODE(SUBSTR((TO_CHAR(NAME)),0,1),'.','0'||TO_CHAR(NAME),TO_CHAR(NAME)))"
start-index="12" stop-index="94">
+ <parameter>
+ <function function-name="DECODE"
text="DECODE(SUBSTR((TO_CHAR(NAME)),0,1),'.','0'||TO_CHAR(NAME),TO_CHAR(NAME))"
start-index="22" stop-index="93">
+ <parameter>
+ <function function-name="SUBSTR"
text="SUBSTR((TO_CHAR(NAME)),0,1)" start-index="29" stop-index="55">
+ <parameter>
+ <function function-name="TO_CHAR"
text="TO_CHAR(NAME)" start-index="37" stop-index="49">
+ <parameter>
+ <column name="NAME"
start-index="45" stop-index="48" />
+ </parameter>
+ </function>
+ </parameter>
+ <parameter>
+ <literal-expression
start-index="52" stop-index="52" value="0" />
+ </parameter>
+ <parameter>
+ <literal-expression
start-index="54" stop-index="54" value="1" />
+ </parameter>
+ </function>
+ </parameter>
+ <parameter>
+ <literal-expression start-index="57"
stop-index="59" value="." />
+ </parameter>
+ <parameter>
+ <binary-operation-expression
text="'0'||TO_CHAR(NAME)" start-index="61" stop-index="78">
+ <left>
+ <literal-expression
start-index="61" stop-index="63" value="0" />
+ </left>
+ <right>
+ <function start-index="66"
stop-index="78" text="TO_CHAR(NAME)" function-name="TO_CHAR">
+ <parameter>
+ <column name="NAME"
start-index="74" stop-index="77" />
+ </parameter>
+ </function>
+ </right>
+ <operator>||</operator>
+ </binary-operation-expression>
+ </parameter>
+ <parameter>
+ <function function-name="TO_CHAR"
text="TO_CHAR(NAME)" start-index="80" stop-index="92">
+ <parameter>
+ <column name="NAME"
start-index="88" stop-index="91" />
+ </parameter>
+ </function>
+ </parameter>
+ </function>
+ </parameter>
+ </function>
+ </expr>
+ </expression-projection>
+ </projections>
+ <from>
+ <simple-table name="TEST_TABLE" start-index="109" stop-index="118"
/>
+ </from>
+ <where start-index="120" stop-index="137">
+ <expr>
+ <binary-operation-expression text="NAME ='TEST'"
start-index="126" stop-index="137">
+ <left>
+ <column name="NAME" start-index="126" stop-index="129"
/>
+ </left>
+ <right>
+ <literal-expression start-index="132" stop-index="137"
value="TEST" />
+ </right>
+ <operator>=</operator>
+ </binary-operation-expression>
+ </expr>
+ </where>
+ <group-by>
+ <column-item name="NAME" order-direction="ASC" start-index="148"
stop-index="151" />
+ </group-by>
+ </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 47d15ee9abf..00db43c5587 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
@@ -213,4 +213,8 @@
<sql-case id="select_numeric_operator" value="SELECT 5! AS RESULT;"
db-types="openGauss" />
<sql-case id="select_with_custom_distinct_function" value="select
custom_concat(distinct a.P1) From TEST a;" db-types="Oracle" />
<sql-case id="select_with_unicode_string" value="SELECT u'test', U'test'
from DUAL" db-types="Oracle" />
+ <sql-case id="select_wm_concat_function1" value="SELECT
TO_CHAR(WM_CONCAT(DISTINCT TEST_ID) OVER(PARTITION BY TEST_ID)) ID FROM
TEST_TABLE" db-types="Oracle" />
+ <sql-case id="select_wm_concat_function2" value="SELECT WM_CONCAT(NAME)
NAME FROM TEST_TABLE" db-types="Oracle" />
+ <sql-case id="select_wm_concat_function3" value="SELECT
REPLACE(WM_CONCAT(NAME),',','|') FROM TEST_TABLE" db-types="Oracle" />
+ <sql-case id="select_wm_concat_function4" value="SELECT
NAME,WM_CONCAT(DECODE(SUBSTR((TO_CHAR(NAME)),0,1),'.','0'||TO_CHAR(NAME),TO_CHAR(NAME)))
WM_NAME FROM TEST_TABLE WHERE NAME ='TEST' GROUP BY NAME" db-types="Oracle" />
</sql-cases>