Skip to content

Commit 5518a87

Browse files
committed
Merge pull request #256 from davelindquist-egistix/merge-into-adjustments
Corrected "MERGE INTO" parsing for more complicated statements.
2 parents d54b82b + 7efd58f commit 5518a87

File tree

3 files changed

+93
-3
lines changed

3 files changed

+93
-3
lines changed

src/main/java/net/sf/jsqlparser/statement/merge/MergeUpdate.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,9 @@ public String toString() {
7373
StringBuilder b = new StringBuilder();
7474
b.append(" WHEN MATCHED THEN UPDATE SET ");
7575
for (int i = 0; i < columns.size(); i++) {
76+
if (i != 0) {
77+
b.append(", ");
78+
}
7679
b.append(columns.get(i).toString()).append(" = ").append(values.get(i).toString());
7780
}
7881
if (whereCondition != null) {

src/main/jjtree/net/sf/jsqlparser/parser/JSqlParserCC.jjt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -590,7 +590,7 @@ Statement Merge() : {
590590
( table=Table() { merge.setUsingTable(table); }
591591
| "(" select=SubSelect() { merge.setUsingSelect(select); } ")" )
592592
[ alias = Alias() { merge.setUsingAlias(alias); } ] <K_ON>
593-
"(" condition = Condition() { merge.setOnCondition(condition); } ")"
593+
"(" condition = Expression() { merge.setOnCondition(condition); } ")"
594594

595595
[ LOOKAHEAD(2) update = MergeUpdateClause() { merge.setMergeUpdate(update); } ]
596596

@@ -616,8 +616,8 @@ MergeUpdate MergeUpdateClause() : {
616616

617617
{ mu.setColumns(columns); mu.setValues(expList); }
618618

619-
[ <K_WHERE> condition = Condition() { mu.setWhereCondition(condition); }]
620-
[ <K_DELETE> <K_WHERE> condition = Condition() { mu.setDeleteWhereCondition(condition); } ]
619+
[ <K_WHERE> condition = Expression() { mu.setWhereCondition(condition); }]
620+
[ <K_DELETE> <K_WHERE> condition = Expression() { mu.setDeleteWhereCondition(condition); } ]
621621

622622
{ return mu; }
623623
}

src/test/java/net/sf/jsqlparser/test/merge/MergeTest.java

Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,4 +62,91 @@ public void testMergeIssue232() throws JSQLParserException {
6262

6363
assertSqlCanBeParsedAndDeparsed(sql, true);
6464
}
65+
66+
@Test
67+
public void testComplexOracleMergeIntoStatement() throws JSQLParserException {
68+
String sql = "MERGE INTO DestinationValue Dest USING\n"
69+
+ "(SELECT TheMonth ,\n"
70+
+ " IdentifyingKey ,\n"
71+
+ " SUM(NetPrice) NetPrice ,\n"
72+
+ " SUM(NetDeductionPrice) NetDeductionPrice ,\n"
73+
+ " MAX(CASE RowNumberMain WHEN 1 THEN QualityIndicator ELSE NULL END) QualityIndicatorMain ,\n"
74+
+ " MAX(CASE RowNumberDeduction WHEN 1 THEN QualityIndicator ELSE NULL END) QualityIndicatorDeduction \n"
75+
+ "FROM\n"
76+
+ " (SELECT pd.TheMonth ,\n"
77+
+ " COALESCE(pd.IdentifyingKey, 0) IdentifyingKey ,\n"
78+
+ " COALESCE(CASE pd.IsDeduction WHEN 1 THEN NULL ELSE ConvertedCalculatedValue END, 0) NetPrice ,\n"
79+
+ " COALESCE(CASE pd.IsDeduction WHEN 1 THEN ConvertedCalculatedValue ELSE NULL END, 0) NetDeductionPrice ,\n"
80+
+ " pd.QualityIndicator ,\n"
81+
+ " row_number() OVER (PARTITION BY pd.TheMonth , pd.IdentifyingKey ORDER BY COALESCE(pd.QualityMonth, to_date('18991230', 'yyyymmdd')) DESC ) RowNumberMain ,\n"
82+
+ " NULL RowNumberDeduction\n"
83+
+ " FROM PricingData pd\n"
84+
+ " WHERE pd.ThingsKey IN (:ThingsKeys)\n"
85+
+ " AND pd.TheMonth >= :startdate\n"
86+
+ " AND pd.TheMonth <= :enddate\n"
87+
+ " AND pd.IsDeduction = 0\n"
88+
+ " UNION ALL\n"
89+
+ " SELECT pd.TheMonth ,\n"
90+
+ " COALESCE(pd.IdentifyingKey, 0) IdentifyingKey ,\n"
91+
+ " COALESCE(CASE pd.IsDeduction WHEN 1 THEN NULL ELSE ConvertedCalculatedValue END, 0) NetPrice ,\n"
92+
+ " COALESCE(CASE pd.IsDeduction WHEN 1 THEN ConvertedCalculatedValue ELSE NULL END, 0) NetDeductionPrice ,\n"
93+
+ " pd.QualityIndicator ,\n"
94+
+ " NULL RowNumberMain ,\n"
95+
+ " row_number() OVER (PARTITION BY pd.TheMonth , pd.IdentifyingKey ORDER BY COALESCE(pd.QualityMonth, to_date('18991230', 'yyyymmdd')) DESC ) RowNumberDeduction \n"
96+
+ " FROM PricingData pd\n"
97+
+ " WHERE pd.ThingsKey IN (:ThingsKeys)\n"
98+
+ " AND pd.TheMonth >= :startdate\n"
99+
+ " AND pd.TheMonth <= :enddate\n"
100+
+ " AND pd.IsDeduction <> 0\n"
101+
+ " )\n"
102+
+ "GROUP BY TheMonth ,\n"
103+
+ " IdentifyingKey\n"
104+
+ ") Data ON ( Dest.TheMonth = Data.TheMonth \n"
105+
+ " AND COALESCE(Dest.IdentifyingKey,0) = Data.IdentifyingKey )\n"
106+
+ "WHEN MATCHED THEN\n"
107+
+ " UPDATE\n"
108+
+ " SET NetPrice = ROUND(Data.NetPrice, PriceDecimalScale) ,\n"
109+
+ " DeductionPrice = ROUND(Data.NetDeductionPrice, PriceDecimalScale) ,\n"
110+
+ " SubTotalPrice = ROUND(Data.NetPrice + (Data.NetDeductionPrice * Dest.HasDeductions), PriceDecimalScale) ,\n"
111+
+ " QualityIndicator =\n"
112+
+ " CASE Dest.HasDeductions\n"
113+
+ " WHEN 0\n"
114+
+ " THEN Data.QualityIndicatorMain\n"
115+
+ " ELSE\n"
116+
+ " CASE\n"
117+
+ " WHEN COALESCE(Data.CheckMonth1, to_date('18991230', 'yyyymmdd'))> COALESCE(Data.CheckMonth2,to_date('18991230', 'yyyymmdd'))\n"
118+
+ " THEN Data.QualityIndicatorMain\n"
119+
+ " ELSE Data.QualityIndicatorDeduction\n"
120+
+ " END\n"
121+
+ " END ,\n"
122+
+ " RecUser = :recuser ,\n"
123+
+ " RecDate = :recdate\n"
124+
+ " WHERE 1 =1\n"
125+
+ " AND IsImportant = 1\n"
126+
+ " AND COALESCE(Data.SomeFlag,-1) <> COALESCE(ROUND(Something, 1),-1)\n"
127+
+ " DELETE WHERE\n"
128+
+ " IsImportant = 0\n"
129+
+ " OR COALESCE(Data.SomeFlag,-1) = COALESCE(ROUND(Something, 1),-1)\n"
130+
+ " WHEN NOT MATCHED THEN \n"
131+
+ " INSERT\n"
132+
+ " (\n"
133+
+ " TheMonth ,\n"
134+
+ " ThingsKey ,\n"
135+
+ " IsDeduction ,\n"
136+
+ " CreatedAt \n"
137+
+ " )\n"
138+
+ " VALUES\n"
139+
+ " (\n"
140+
+ " Data.TheMonth ,\n"
141+
+ " Data.ThingsKey ,\n"
142+
+ " Data.IsDeduction ,\n"
143+
+ " SYSDATE\n"
144+
+ " )\n";
145+
146+
Statement statement = CCJSqlParserUtil.parse(sql);
147+
148+
System.out.println(statement.toString());
149+
150+
assertSqlCanBeParsedAndDeparsed(sql, true);
151+
}
65152
}

0 commit comments

Comments
 (0)