From d7f4ec73c50af82dd34e2ec7533fe3ee6af4bc1d Mon Sep 17 00:00:00 2001 From: mariadb-AndreyPiskunov Date: Mon, 31 Oct 2022 14:55:12 +0200 Subject: [PATCH] Small fixes + test sorting --- dbcon/mysql/ha_mcs_execplan.cpp | 93 ++++++++++++++++--- .../basic/r/func_jsonarrayagg.result | 8 +- .../basic/t/func_jsonarrayagg.test | 4 + 3 files changed, 87 insertions(+), 18 deletions(-) diff --git a/dbcon/mysql/ha_mcs_execplan.cpp b/dbcon/mysql/ha_mcs_execplan.cpp index 83fc958ef..3a0061444 100644 --- a/dbcon/mysql/ha_mcs_execplan.cpp +++ b/dbcon/mysql/ha_mcs_execplan.cpp @@ -2907,7 +2907,7 @@ uint32_t setAggOp(AggregateColumn* ac, Item_sum* isp) case Item_sum::JSON_ARRAYAGG_FUNC: { - Item_func_group_concat* gc = (Item_func_group_concat*)isp; + Item_func_json_arrayagg* gc = (Item_func_json_arrayagg*)isp; ac->aggOp(AggregateColumn::JSON_ARRAYAGG); ac->distinct(gc->get_distinct()); return rc; @@ -4916,7 +4916,7 @@ ReturnedColumn* buildAggregateColumn(Item* item, gp_walk_info& gwi) gwi.aggOnSelect = true; // Argument_count() is the # of formal parms to the agg fcn. Columnstore - // only supports 1 argument except UDAnF, COUNT(DISTINC) and GROUP_CONCAT + // only supports 1 argument except UDAnF, COUNT(DISTINC), GROUP_CONCAT and JSON_ARRAYAGG if (isp->argument_count() != 1 && isp->sum_func() != Item_sum::COUNT_DISTINCT_FUNC && isp->sum_func() != Item_sum::GROUP_CONCAT_FUNC && isp->sum_func() != Item_sum::UDF_SUM_FUNC && isp->sum_func() != Item_sum::JSON_ARRAYAGG_FUNC) @@ -4964,7 +4964,7 @@ ReturnedColumn* buildAggregateColumn(Item* item, gp_walk_info& gwi) try { // special parsing for group_concat - if (isp->sum_func() == Item_sum::GROUP_CONCAT_FUNC || isp->sum_func() == Item_sum::JSON_ARRAYAGG_FUNC) + if (isp->sum_func() == Item_sum::GROUP_CONCAT_FUNC) { Item_func_group_concat* gc = (Item_func_group_concat*)isp; vector orderCols; @@ -5032,14 +5032,7 @@ ReturnedColumn* buildAggregateColumn(Item* item, gp_walk_info& gwi) } rowCol->columnVec(selCols); - if (isp->sum_func() == Item_sum::GROUP_CONCAT_FUNC) - { - (dynamic_cast(ac))->orderCols(orderCols); - } - else - { - (dynamic_cast(ac))->orderCols(orderCols); - } + (dynamic_cast(ac))->orderCols(orderCols); parm.reset(rowCol); ac->aggParms().push_back(parm); @@ -5047,14 +5040,86 @@ ReturnedColumn* buildAggregateColumn(Item* item, gp_walk_info& gwi) { string separator; separator.assign(gc->get_separator()->ptr(), gc->get_separator()->length()); - if (isp->sum_func() == Item_sum::GROUP_CONCAT_FUNC) + (dynamic_cast(ac))->separator(separator); + } + } + else if (isp->sum_func() == Item_sum::JSON_ARRAYAGG_FUNC) + { + Item_func_json_arrayagg* gc = (Item_func_json_arrayagg*)isp; + vector orderCols; + RowColumn* rowCol = new RowColumn(); + vector selCols; + + uint32_t select_ctn = gc->get_count_field(); + ReturnedColumn* rc = NULL; + + for (uint32_t i = 0; i < select_ctn; i++) + { + rc = buildReturnedColumn(sfitempp[i], gwi, gwi.fatalParseError); + + if (!rc || gwi.fatalParseError) { - (dynamic_cast(ac))->separator(separator); + if (ac) + delete ac; + + return NULL; + } + + selCols.push_back(SRCP(rc)); + } + + ORDER **order_item, **end; + + for (order_item = gc->get_order(), end = order_item + gc->get_order_field(); order_item < end; + order_item++) + { + Item* ord_col = *(*order_item)->item; + + if (ord_col->type() == Item::CONST_ITEM && ord_col->cmp_type() == INT_RESULT) + { + Item_int* id = (Item_int*)ord_col; + + if (id->val_int() > (int)selCols.size()) + { + gwi.fatalParseError = true; + + if (ac) + delete ac; + + return NULL; + } + + rc = selCols[id->val_int() - 1]->clone(); + rc->orderPos(id->val_int() - 1); } else { - (dynamic_cast(ac))->separator(separator); + rc = buildReturnedColumn(ord_col, gwi, gwi.fatalParseError); + + if (!rc || gwi.fatalParseError) + { + if (ac) + delete ac; + + return NULL; + } } + + // 10.2 TODO: direction is now a tri-state flag + rc->asc((*order_item)->direction == ORDER::ORDER_ASC ? true : false); + orderCols.push_back(SRCP(rc)); + } + + rowCol->columnVec(selCols); + (dynamic_cast(ac))->orderCols(orderCols); + parm.reset(rowCol); + ac->aggParms().push_back(parm); + + if (gc->get_separator()) + { + string separator; + separator.assign(gc->get_separator()->ptr(), gc->get_separator()->length()); + (dynamic_cast(ac))->separator(separator); } } else if (isSupportedAggregateWithOneConstArg(isp, sfitempp)) diff --git a/mysql-test/columnstore/basic/r/func_jsonarrayagg.result b/mysql-test/columnstore/basic/r/func_jsonarrayagg.result index 8e8214ba6..310c6d40a 100644 --- a/mysql-test/columnstore/basic/r/func_jsonarrayagg.result +++ b/mysql-test/columnstore/basic/r/func_jsonarrayagg.result @@ -90,13 +90,13 @@ JSON_ARRAYAGG(b LIMIT 2) ["Hello","World","This","Will","Work","!","Hello","World","This","Will","Work","!"] SELECT JSON_ARRAYAGG(b LIMIT 1) FROM t1 GROUP BY b; JSON_ARRAYAGG(b LIMIT 1) -["Hello","Hello"] NULL -["Work","Work"] -["This","This"] -["World","World"] ["!","!"] +["Hello","Hello"] +["This","This"] ["Will","Will"] +["Work","Work"] +["World","World"] SELECT JSON_ARRAYAGG(b LIMIT 2) FROM t1 GROUP BY a; JSON_ARRAYAGG(b LIMIT 2) NULL diff --git a/mysql-test/columnstore/basic/t/func_jsonarrayagg.test b/mysql-test/columnstore/basic/t/func_jsonarrayagg.test index 98bf93e36..7ef892d8d 100644 --- a/mysql-test/columnstore/basic/t/func_jsonarrayagg.test +++ b/mysql-test/columnstore/basic/t/func_jsonarrayagg.test @@ -27,7 +27,9 @@ DROP TABLE t1; CREATE TABLE t1 (a BOOLEAN, b BOOLEAN)ENGINE=COLUMNSTORE; INSERT INTO t1 VALUES (TRUE, TRUE), (TRUE, FALSE), (FALSE, TRUE), (FALSE, FALSE); SELECT JSON_VALID(JSON_ARRAYAGG(a)) FROM t1; +sorted_result; SELECT JSON_ARRAYAGG(a), JSON_ARRAYAGG(b) FROM t1; +sorted_result; SELECT JSON_ARRAYAGG(a), JSON_ARRAYAGG(b) FROM t1 GROUP BY b; SELECT JSON_ARRAYAGG(TRUE), JSON_ARRAYAGG(FALSE) FROM t1; DROP TABLE t1; @@ -59,7 +61,9 @@ SELECT JSON_ARRAYAGG(a), JSON_ARRAYAGG(b) FROM t1 GROUP BY a; -- echo # SELECT JSON_ARRAYAGG(b LIMIT 1) FROM t1; SELECT JSON_ARRAYAGG(b LIMIT 2) FROM t1; +sorted_result; SELECT JSON_ARRAYAGG(b LIMIT 1) FROM t1 GROUP BY b; +sorted_result; SELECT JSON_ARRAYAGG(b LIMIT 2) FROM t1 GROUP BY a; SELECT JSON_ARRAYAGG(DISTINCT a) FROM t1; SELECT JSON_ARRAYAGG(DISTINCT b) FROM t1;