diff --git a/include/libs/nodes/querynodes.h b/include/libs/nodes/querynodes.h index db87bde5213a2837b67f0e34fdcad4499a70cb28..38c50550591b47ae6e5fc5075340c6c8d5af7c23 100644 --- a/include/libs/nodes/querynodes.h +++ b/include/libs/nodes/querynodes.h @@ -269,6 +269,7 @@ typedef struct SSelectStmt { bool hasInterpFunc; bool hasLastRowFunc; bool hasTimeLineFunc; + bool hasUdaf; bool onlyHasKeepOrderFunc; bool groupSort; } SSelectStmt; diff --git a/source/common/src/systable.c b/source/common/src/systable.c index 16681fb70562a74c569a66cb91886e603eaeddb6..6dddcc2f7422aaa09d4e8b7691cce0c2fc107b6d 100644 --- a/source/common/src/systable.c +++ b/source/common/src/systable.c @@ -346,7 +346,7 @@ static const SSysTableMeta perfsMeta[] = { {TSDB_PERFS_TABLE_TOPICS, topicSchema, tListLen(topicSchema)}, {TSDB_PERFS_TABLE_CONSUMERS, consumerSchema, tListLen(consumerSchema)}, {TSDB_PERFS_TABLE_SUBSCRIPTIONS, subscriptionSchema, tListLen(subscriptionSchema)}, - {TSDB_PERFS_TABLE_OFFSETS, offsetSchema, tListLen(offsetSchema)}, + // {TSDB_PERFS_TABLE_OFFSETS, offsetSchema, tListLen(offsetSchema)}, {TSDB_PERFS_TABLE_TRANS, transSchema, tListLen(transSchema)}, {TSDB_PERFS_TABLE_SMAS, smaSchema, tListLen(smaSchema)}, {TSDB_PERFS_TABLE_STREAMS, streamSchema, tListLen(streamSchema)}, diff --git a/source/libs/parser/src/parTranslater.c b/source/libs/parser/src/parTranslater.c index 4743a9aa9a2f3e3b97cd97d0011aaaa45fbef53d..be4ac404fd866665a3f1a98fd082d72cb038757b 100644 --- a/source/libs/parser/src/parTranslater.c +++ b/source/libs/parser/src/parTranslater.c @@ -1350,6 +1350,7 @@ static void setFuncClassification(SNode* pCurrStmt, SFunctionNode* pFunc) { pSelect->hasInterpFunc = pSelect->hasInterpFunc ? true : (FUNCTION_TYPE_INTERP == pFunc->funcType); pSelect->hasLastRowFunc = pSelect->hasLastRowFunc ? true : (FUNCTION_TYPE_LAST_ROW == pFunc->funcType); pSelect->hasTimeLineFunc = pSelect->hasTimeLineFunc ? true : fmIsTimelineFunc(pFunc->funcId); + pSelect->hasUdaf = pSelect->hasUdaf ? true : fmIsUserDefinedFunc(pFunc->funcId) && fmIsAggFunc(pFunc->funcId); pSelect->onlyHasKeepOrderFunc = pSelect->onlyHasKeepOrderFunc ? fmIsKeepOrderFunc(pFunc->funcId) : false; } } @@ -2644,6 +2645,11 @@ static int32_t translateInterp(STranslateContext* pCxt, SSelectStmt* pSelect) { return TSDB_CODE_SUCCESS; } + if (NULL == pSelect->pRange || NULL == pSelect->pEvery || NULL == pSelect->pFill) { + return generateSyntaxErrMsgExt(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_INTERP_CLAUSE, + "Missing RANGE clause, EVERY clause or FILL clause"); + } + int32_t code = translateExpr(pCxt, &pSelect->pRange); if (TSDB_CODE_SUCCESS == code) { code = translateExpr(pCxt, &pSelect->pEvery); @@ -4734,6 +4740,11 @@ static bool crossTableWithoutAggOper(SSelectStmt* pSelect) { !isPartitionByTbname(pSelect->pPartitionByList); } +static bool crossTableWithUdaf(SSelectStmt* pSelect) { + return pSelect->hasUdaf && TSDB_SUPER_TABLE == ((SRealTableNode*)pSelect->pFromTable)->pMeta->tableType && + !isPartitionByTbname(pSelect->pPartitionByList); +} + static int32_t checkCreateStream(STranslateContext* pCxt, SCreateStreamStmt* pStmt) { if (NULL != pStmt->pOptions->pWatermark && (DEAL_RES_ERROR == translateValue(pCxt, (SValueNode*)pStmt->pOptions->pWatermark))) { @@ -4785,7 +4796,8 @@ static int32_t addWstartTsToCreateStreamQuery(SNode* pStmt) { static int32_t checkStreamQuery(STranslateContext* pCxt, SSelectStmt* pSelect) { if (TSDB_DATA_TYPE_TIMESTAMP != ((SExprNode*)nodesListGetNode(pSelect->pProjectionList, 0))->resType.type || - !pSelect->isTimeLineResult || crossTableWithoutAggOper(pSelect)) { + !pSelect->isTimeLineResult || crossTableWithoutAggOper(pSelect) || NULL != pSelect->pOrderByList || + crossTableWithUdaf(pSelect)) { return generateSyntaxErrMsgExt(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_STREAM_QUERY, "Unsupported stream query"); } return TSDB_CODE_SUCCESS; diff --git a/source/libs/parser/test/parSelectTest.cpp b/source/libs/parser/test/parSelectTest.cpp index 5b222a8deca0d7f22a27286f903810004fda9c37..716dd7ffc000c5995a1121314825c6f1081d7079 100644 --- a/source/libs/parser/test/parSelectTest.cpp +++ b/source/libs/parser/test/parSelectTest.cpp @@ -294,16 +294,6 @@ TEST_F(ParserSelectTest, intervalSemanticCheck) { TEST_F(ParserSelectTest, interp) { useDb("root", "test"); - run("SELECT INTERP(c1) FROM t1"); - - run("SELECT INTERP(c1) FROM t1 RANGE('2017-7-14 18:00:00', '2017-7-14 19:00:00')"); - - run("SELECT INTERP(c1) FROM t1 RANGE('2017-7-14 18:00:00', '2017-7-14 19:00:00') FILL(LINEAR)"); - - run("SELECT INTERP(c1) FROM t1 EVERY(5s)"); - - run("SELECT INTERP(c1) FROM t1 RANGE('2017-7-14 18:00:00', '2017-7-14 19:00:00') EVERY(5s)"); - run("SELECT INTERP(c1) FROM t1 RANGE('2017-7-14 18:00:00', '2017-7-14 19:00:00') EVERY(5s) FILL(LINEAR)"); } diff --git a/source/libs/planner/src/planOptimizer.c b/source/libs/planner/src/planOptimizer.c index f4f7c9aefdfe64f5e14aa02a4adecc1129683080..45ab3903a9e9eb6df844244b6fc7cd8d009ebd47 100644 --- a/source/libs/planner/src/planOptimizer.c +++ b/source/libs/planner/src/planOptimizer.c @@ -1615,6 +1615,9 @@ static int32_t partTagsOptimize(SOptimizeContext* pCxt, SLogicSubplan* pLogicSub if (QUERY_NODE_LOGIC_PLAN_PARTITION == nodeType(pNode)) { TSWAP(((SPartitionLogicNode*)pNode)->pPartitionKeys, pScan->pGroupTags); int32_t code = replaceLogicNode(pLogicSubplan, pNode, (SLogicNode*)pScan); + if (TSDB_CODE_SUCCESS == code) { + code = adjustLogicNodeDataRequirement((SLogicNode*)pScan, pNode->resultDataOrder); + } if (TSDB_CODE_SUCCESS == code) { NODES_CLEAR_LIST(pNode->pChildren); nodesDestroyNode((SNode*)pNode); diff --git a/source/libs/planner/test/planBasicTest.cpp b/source/libs/planner/test/planBasicTest.cpp index d7c947a20dce65be73e8be97172dbcfa5c00a70d..27ec409d52a912834ae6e3ec6e2e6a41f2812fe1 100644 --- a/source/libs/planner/test/planBasicTest.cpp +++ b/source/libs/planner/test/planBasicTest.cpp @@ -93,8 +93,6 @@ TEST_F(PlanBasicTest, tailFunc) { TEST_F(PlanBasicTest, interpFunc) { useDb("root", "test"); - run("SELECT INTERP(c1) FROM t1"); - run("SELECT INTERP(c1) FROM t1 RANGE('2017-7-14 18:00:00', '2017-7-14 19:00:00') EVERY(5s) FILL(LINEAR)"); }