Merge pull request #25935 from taosdata/fix/3.0/TD-30188
fix select from union all caused crash
This commit is contained in:
commit
4f67ccc5d5
|
@ -183,6 +183,7 @@ typedef struct SProjectLogicNode {
|
||||||
char stmtName[TSDB_TABLE_NAME_LEN];
|
char stmtName[TSDB_TABLE_NAME_LEN];
|
||||||
bool ignoreGroupId;
|
bool ignoreGroupId;
|
||||||
bool inputIgnoreGroup;
|
bool inputIgnoreGroup;
|
||||||
|
bool isSetOpProj;
|
||||||
} SProjectLogicNode;
|
} SProjectLogicNode;
|
||||||
|
|
||||||
typedef struct SIndefRowsFuncLogicNode {
|
typedef struct SIndefRowsFuncLogicNode {
|
||||||
|
|
|
@ -1587,6 +1587,7 @@ static int32_t createSetOpProjectLogicNode(SLogicPlanContext* pCxt, SSetOperator
|
||||||
TSWAP(pProject->node.pLimit, pSetOperator->pLimit);
|
TSWAP(pProject->node.pLimit, pSetOperator->pLimit);
|
||||||
}
|
}
|
||||||
pProject->ignoreGroupId = true;
|
pProject->ignoreGroupId = true;
|
||||||
|
pProject->isSetOpProj = true;
|
||||||
|
|
||||||
int32_t code = TSDB_CODE_SUCCESS;
|
int32_t code = TSDB_CODE_SUCCESS;
|
||||||
|
|
||||||
|
|
|
@ -3284,9 +3284,23 @@ static int32_t eliminateProjOptimizeImpl(SOptimizeContext* pCxt, SLogicSubplan*
|
||||||
SNodeList* pNewChildTargets = nodesMakeList();
|
SNodeList* pNewChildTargets = nodesMakeList();
|
||||||
|
|
||||||
if (NULL == pProjectNode->node.pParent) {
|
if (NULL == pProjectNode->node.pParent) {
|
||||||
SNode* pProjection = NULL;
|
SNode *pProjection = NULL, *pChildTarget = NULL;
|
||||||
|
bool needOrderMatch = QUERY_NODE_LOGIC_PLAN_PROJECT == nodeType(pChild) && ((SProjectLogicNode*)pChild)->isSetOpProj;
|
||||||
|
bool orderMatch = true;
|
||||||
|
if (needOrderMatch) {
|
||||||
|
// For sql: select ... from (select ... union all select ...);
|
||||||
|
// When eliminating the outer proj (the outer select), we have to make sure that the outer proj projections and
|
||||||
|
// union all project targets have same columns in the same order. See detail in TD-30188
|
||||||
|
FORBOTH(pProjection, pProjectNode->pProjections, pChildTarget, pChild->pTargets) {
|
||||||
|
if (!pProjection) break;
|
||||||
|
if (0 != strcmp(((SColumnNode*)pProjection)->colName, ((SColumnNode*)pChildTarget)->colName)) {
|
||||||
|
orderMatch = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
nodesListAppend(pNewChildTargets, nodesCloneNode(pChildTarget));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
FOREACH(pProjection, pProjectNode->pProjections) {
|
FOREACH(pProjection, pProjectNode->pProjections) {
|
||||||
SNode* pChildTarget = NULL;
|
|
||||||
FOREACH(pChildTarget, pChild->pTargets) {
|
FOREACH(pChildTarget, pChild->pTargets) {
|
||||||
if (0 == strcmp(((SColumnNode*)pProjection)->colName, ((SColumnNode*)pChildTarget)->colName)) {
|
if (0 == strcmp(((SColumnNode*)pProjection)->colName, ((SColumnNode*)pChildTarget)->colName)) {
|
||||||
nodesListAppend(pNewChildTargets, nodesCloneNode(pChildTarget));
|
nodesListAppend(pNewChildTargets, nodesCloneNode(pChildTarget));
|
||||||
|
@ -3294,8 +3308,10 @@ static int32_t eliminateProjOptimizeImpl(SOptimizeContext* pCxt, SLogicSubplan*
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (eliminateProjOptCanChildConditionUseChildTargets(pChild, pNewChildTargets)) {
|
if (eliminateProjOptCanChildConditionUseChildTargets(pChild, pNewChildTargets) &&
|
||||||
|
(!needOrderMatch || (needOrderMatch && orderMatch))) {
|
||||||
nodesDestroyList(pChild->pTargets);
|
nodesDestroyList(pChild->pTargets);
|
||||||
pChild->pTargets = pNewChildTargets;
|
pChild->pTargets = pNewChildTargets;
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -240,9 +240,22 @@ class TDTestCase:
|
||||||
tdSql.error( " '' union all select c1 from ct1 " )
|
tdSql.error( " '' union all select c1 from ct1 " )
|
||||||
# tdSql.error( "select c1 from ct1 union select c1 from ct2 union select c1 from ct4 ")
|
# tdSql.error( "select c1 from ct1 union select c1 from ct2 union select c1 from ct4 ")
|
||||||
|
|
||||||
|
def test_select_from_union_all(self):
|
||||||
|
tdSql.query('select c8, ts from ((select ts, c8,c1 from stb1 order by c1) union all select ts, c8, c1 from stb1 limit 15)')
|
||||||
|
tdSql.checkRows(15)
|
||||||
|
tdSql.query('select c8, ts from ((select ts, c8,c1 from stb1 order by c1) union all (select ts, c8, c1 from stb1 order by c8 limit 10) limit 15)')
|
||||||
|
tdSql.checkRows(15)
|
||||||
|
tdSql.query('select ts, c1 from ((select ts, c8,c1 from stb1 order by c1) union all (select ts, c8, c1 from stb1 order by c8 limit 10) limit 15)')
|
||||||
|
tdSql.checkRows(15)
|
||||||
|
tdSql.query('select ts, c1, c8 from ((select ts, c8,c1 from stb1 order by c1) union all (select ts, c8, c1 from stb1 order by c8 limit 10) limit 15)')
|
||||||
|
tdSql.checkRows(15)
|
||||||
|
tdSql.query('select ts, c8, c1, 123 from ((select ts, c8,c1 from stb1 order by c1) union all (select ts, c8, c1 from stb1 order by c8 limit 10) limit 15)')
|
||||||
|
tdSql.checkRows(15)
|
||||||
|
|
||||||
def all_test(self):
|
def all_test(self):
|
||||||
self.__test_error()
|
self.__test_error()
|
||||||
self.union_check()
|
self.union_check()
|
||||||
|
self.test_select_from_union_all()
|
||||||
|
|
||||||
|
|
||||||
def __create_tb(self):
|
def __create_tb(self):
|
||||||
|
|
Loading…
Reference in New Issue