diff --git a/include/util/taoserror.h b/include/util/taoserror.h index abc752955d..441e87eff7 100644 --- a/include/util/taoserror.h +++ b/include/util/taoserror.h @@ -621,6 +621,14 @@ int32_t* taosGetErrno(); #define TSDB_CODE_PAR_INVALID_TOPIC_QUERY TAOS_DEF_ERROR_CODE(0, 0x2639) #define TSDB_CODE_PAR_INVALID_DROP_STABLE TAOS_DEF_ERROR_CODE(0, 0x263A) #define TSDB_CODE_PAR_INVALID_FILL_TIME_RANGE TAOS_DEF_ERROR_CODE(0, 0x263B) +#define TSDB_CODE_PAR_DUPLICATED_COLUMN TAOS_DEF_ERROR_CODE(0, 0x263C) +#define TSDB_CODE_PAR_INVALID_TAGS_LENGTH TAOS_DEF_ERROR_CODE(0, 0x263D) +#define TSDB_CODE_PAR_INVALID_ROW_LENGTH TAOS_DEF_ERROR_CODE(0, 0x263E) +#define TSDB_CODE_PAR_INVALID_COLUMNS_NUM TAOS_DEF_ERROR_CODE(0, 0x263F) +#define TSDB_CODE_PAR_TOO_MANY_COLUMNS TAOS_DEF_ERROR_CODE(0, 0x2640) +#define TSDB_CODE_PAR_INVALID_FIRST_COLUMN TAOS_DEF_ERROR_CODE(0, 0x2641) +#define TSDB_CODE_PAR_INVALID_VAR_COLUMN_LEN TAOS_DEF_ERROR_CODE(0, 0x2642) +#define TSDB_CODE_PAR_INVALID_TAGS_NUM TAOS_DEF_ERROR_CODE(0, 0x2643) //planner #define TSDB_CODE_PLAN_INTERNAL_ERROR TAOS_DEF_ERROR_CODE(0, 0x2700) diff --git a/source/libs/function/inc/builtinsimpl.h b/source/libs/function/inc/builtinsimpl.h index 87cd3e24a8..abb9525cc5 100644 --- a/source/libs/function/inc/builtinsimpl.h +++ b/source/libs/function/inc/builtinsimpl.h @@ -73,6 +73,11 @@ bool spreadFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo) int32_t spreadFunction(SqlFunctionCtx* pCtx); int32_t spreadFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock); +bool getHistogramFuncEnv(struct SFunctionNode* pFunc, SFuncExecEnv* pEnv); +bool histogramFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo); +int32_t histogramFunction(SqlFunctionCtx* pCtx); +int32_t histogramFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock); + #ifdef __cplusplus } #endif diff --git a/source/libs/function/src/builtins.c b/source/libs/function/src/builtins.c index eac11558cb..8fa4bd0c4d 100644 --- a/source/libs/function/src/builtins.c +++ b/source/libs/function/src/builtins.c @@ -225,6 +225,26 @@ static int32_t translateSpread(SFunctionNode* pFunc, char* pErrBuf, int32_t len) return TSDB_CODE_SUCCESS; } +static int32_t translateHistogram(SFunctionNode* pFunc, char* pErrBuf, int32_t len) { + if (4 != LIST_LENGTH(pFunc->pParameterList)) { + return invaildFuncParaNumErrMsg(pErrBuf, len, pFunc->functionName); + } + + uint8_t colType = ((SExprNode*)nodesListGetNode(pFunc->pParameterList, 0))->resType.type; + if (!IS_NUMERIC_TYPE(colType)) { + return invaildFuncParaTypeErrMsg(pErrBuf, len, pFunc->functionName); + } + + if (((SExprNode*)nodesListGetNode(pFunc->pParameterList, 1))->resType.type != TSDB_DATA_TYPE_BINARY || + ((SExprNode*)nodesListGetNode(pFunc->pParameterList, 2))->resType.type != TSDB_DATA_TYPE_BINARY || + ((SExprNode*)nodesListGetNode(pFunc->pParameterList, 3))->resType.type != TSDB_DATA_TYPE_BIGINT) { + return invaildFuncParaTypeErrMsg(pErrBuf, len, pFunc->functionName); + } + + pFunc->node.resType = (SDataType) { .bytes = tDataTypes[TSDB_DATA_TYPE_DOUBLE].bytes, .type = TSDB_DATA_TYPE_DOUBLE }; + return TSDB_CODE_SUCCESS; +} + static int32_t translateLastRow(SFunctionNode* pFunc, char* pErrBuf, int32_t len) { // todo return TSDB_CODE_SUCCESS; @@ -242,8 +262,7 @@ static int32_t translateFirstLast(SFunctionNode* pFunc, char* pErrBuf, int32_t l "The parameters of first/last can only be columns"); } - uint8_t paraType = ((SExprNode*)pPara)->resType.type; - pFunc->node.resType = (SDataType){.bytes = tDataTypes[paraType].bytes, .type = paraType}; + pFunc->node.resType = ((SExprNode*)pPara)->resType; return TSDB_CODE_SUCCESS; } @@ -600,6 +619,16 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = { .processFunc = diffFunction, .finalizeFunc = functionFinalize }, + { + .name = "histogram", + .type = FUNCTION_TYPE_HISTOGRAM, + .classification = FUNC_MGT_AGG_FUNC, + .translateFunc = translateHistogram, + .getEnvFunc = getHistogramFuncEnv, + .initFunc = histogramFunctionSetup, + .processFunc = histogramFunction, + .finalizeFunc = histogramFinalize + }, { .name = "abs", .type = FUNCTION_TYPE_ABS, diff --git a/source/libs/function/src/builtinsimpl.c b/source/libs/function/src/builtinsimpl.c index 0eba442e66..3c9eca85dd 100644 --- a/source/libs/function/src/builtinsimpl.c +++ b/source/libs/function/src/builtinsimpl.c @@ -20,6 +20,8 @@ #include "tdatablock.h" #include "tpercentile.h" +#define HISTOGRAM_MAX_BINS_NUM 100 + typedef struct SSumRes { union { int64_t isum; @@ -89,6 +91,22 @@ typedef struct SSpreadInfo { double max; } SSpreadInfo; +typedef struct SHistoFuncBin { + double lower; + double upper; + union { + int64_t count; + double percentage; + }; +} SHistoFuncBin; + +typedef struct SHistoFuncInfo { + int32_t numOfBins; + bool normalized; + SHistoFuncBin bins[]; +} SHistoFuncInfo; + + #define SET_VAL(_info, numOfElem, res) \ do { \ if ((numOfElem) <= 0) { \ @@ -1777,3 +1795,34 @@ int32_t spreadFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock) { } return functionFinalize(pCtx, pBlock); } + +bool getHistogramFuncEnv(SFunctionNode* UNUSED_PARAM(pFunc), SFuncExecEnv* pEnv) { + pEnv->calcMemSize = sizeof(SHistoFuncInfo) + HISTOGRAM_MAX_BINS_NUM * sizeof(SHistoFuncBin); + return true; +} + +bool histogramFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo) { + if (!functionSetup(pCtx, pResultInfo)) { + return false; + } + + SHistoFuncInfo* pInfo = GET_ROWCELL_INTERBUF(pResultInfo); + char* binType = pCtx->param[1].param.pz; + char* binDesc = pCtx->param[2].param.pz; + int64_t nornalized = pCtx->param[3].param.i; + + + return true; +} + +int32_t histogramFunction(SqlFunctionCtx *pCtx) { + return TSDB_CODE_SUCCESS; +} + +int32_t histogramFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock) { + SHistoFuncInfo* pInfo = GET_ROWCELL_INTERBUF(GET_RES_INFO(pCtx)); + //if (pInfo->hasResult == true) { + // SET_DOUBLE_VAL(&pInfo->result, pInfo->max - pInfo->min); + //} + return functionFinalize(pCtx, pBlock); +} diff --git a/source/libs/parser/src/parTranslater.c b/source/libs/parser/src/parTranslater.c index fbb1f34217..6874b5b7d4 100644 --- a/source/libs/parser/src/parTranslater.c +++ b/source/libs/parser/src/parTranslater.c @@ -2174,17 +2174,6 @@ static int32_t checkTableSmaOption(STranslateContext* pCxt, SCreateTableStmt* pS return TSDB_CODE_SUCCESS; } -static int32_t checkTableTags(STranslateContext* pCxt, SCreateTableStmt* pStmt) { - SNode* pNode; - FOREACH(pNode, pStmt->pTags) { - SColumnDefNode* pCol = (SColumnDefNode*)pNode; - if (pCol->dataType.type == TSDB_DATA_TYPE_JSON && LIST_LENGTH(pStmt->pTags) > 1) { - return generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_ONLY_ONE_JSON_TAG); - } - } - return TSDB_CODE_SUCCESS; -} - static int32_t checkTableRollupOption(STranslateContext* pCxt, SNodeList* pFuncs) { if (NULL == pFuncs) { return TSDB_CODE_SUCCESS; @@ -2196,6 +2185,113 @@ static int32_t checkTableRollupOption(STranslateContext* pCxt, SNodeList* pFuncs return TSDB_CODE_SUCCESS; } +static int32_t checkTableTagsSchema(STranslateContext* pCxt, SHashObj* pHash, SNodeList* pTags) { + int32_t ntags = LIST_LENGTH(pTags); + if (0 == ntags) { + return TSDB_CODE_SUCCESS; + } else if (ntags > TSDB_MAX_TAGS) { + return generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_TAGS_NUM); + } + + int32_t code = TSDB_CODE_SUCCESS; + int32_t tagsSize = 0; + SNode* pNode = NULL; + FOREACH(pNode, pTags) { + SColumnDefNode* pTag = (SColumnDefNode*)pNode; + int32_t len = strlen(pTag->colName); + if (NULL != taosHashGet(pHash, pTag->colName, len)) { + code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_DUPLICATED_COLUMN); + } + if (TSDB_CODE_SUCCESS == code && pTag->dataType.type == TSDB_DATA_TYPE_JSON && ntags > 1) { + code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_ONLY_ONE_JSON_TAG); + } + if (TSDB_CODE_SUCCESS == code) { + if ((TSDB_DATA_TYPE_VARCHAR == pTag->dataType.type && pTag->dataType.bytes > TSDB_MAX_BINARY_LEN) || + (TSDB_DATA_TYPE_NCHAR == pTag->dataType.type && pTag->dataType.bytes > TSDB_MAX_NCHAR_LEN)) { + code = code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_VAR_COLUMN_LEN); + } + } + if (TSDB_CODE_SUCCESS == code) { + code = taosHashPut(pHash, pTag->colName, len, &pTag, POINTER_BYTES); + } + if (TSDB_CODE_SUCCESS == code) { + tagsSize += pTag->dataType.bytes; + } else { + break; + } + } + + if (TSDB_CODE_SUCCESS == code && tagsSize > TSDB_MAX_TAGS_LEN) { + code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_TAGS_LENGTH, TSDB_MAX_TAGS_LEN); + } + + return code; +} + +static int32_t checkTableColsSchema(STranslateContext* pCxt, SHashObj* pHash, SNodeList* pCols) { + int32_t ncols = LIST_LENGTH(pCols); + if (ncols < TSDB_MIN_COLUMNS) { + return generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_COLUMNS_NUM); + } else if (ncols > TSDB_MAX_COLUMNS) { + return generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_TOO_MANY_COLUMNS); + } + + int32_t code = TSDB_CODE_SUCCESS; + + bool first = true; + int32_t rowSize = 0; + SNode* pNode = NULL; + FOREACH(pNode, pCols) { + SColumnDefNode* pCol = (SColumnDefNode*)pNode; + if (first) { + first = false; + if (TSDB_DATA_TYPE_TIMESTAMP != pCol->dataType.type) { + code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_FIRST_COLUMN); + } + } + int32_t len = strlen(pCol->colName); + if (TSDB_CODE_SUCCESS == code && NULL != taosHashGet(pHash, pCol->colName, len)) { + code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_DUPLICATED_COLUMN); + } + if (TSDB_CODE_SUCCESS == code) { + if ((TSDB_DATA_TYPE_VARCHAR == pCol->dataType.type && pCol->dataType.bytes > TSDB_MAX_BINARY_LEN) || + (TSDB_DATA_TYPE_NCHAR == pCol->dataType.type && pCol->dataType.bytes > TSDB_MAX_NCHAR_LEN)) { + code = code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_VAR_COLUMN_LEN); + } + } + if (TSDB_CODE_SUCCESS == code) { + code = taosHashPut(pHash, pCol->colName, len, &pCol, POINTER_BYTES); + } + if (TSDB_CODE_SUCCESS == code) { + rowSize += pCol->dataType.bytes; + } else { + break; + } + } + + if (TSDB_CODE_SUCCESS == code && rowSize > TSDB_MAX_BYTES_PER_ROW) { + code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_ROW_LENGTH, TSDB_MAX_BYTES_PER_ROW); + } + + return code; +} + +static int32_t checkTableSchema(STranslateContext* pCxt, SCreateTableStmt* pStmt) { + SHashObj* pHash = taosHashInit(LIST_LENGTH(pStmt->pTags) + LIST_LENGTH(pStmt->pCols), + taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), false, HASH_NO_LOCK); + if (NULL == pHash) { + return TSDB_CODE_OUT_OF_MEMORY; + } + + int32_t code = checkTableTagsSchema(pCxt, pHash, pStmt->pTags); + if (TSDB_CODE_SUCCESS == code) { + code = checkTableColsSchema(pCxt, pHash, pStmt->pCols); + } + + taosHashCleanup(pHash); + return code; +} + static int32_t checkCreateTable(STranslateContext* pCxt, SCreateTableStmt* pStmt) { int32_t code = checkRangeOption(pCxt, "delay", pStmt->pOptions->delay, TSDB_MIN_ROLLUP_DELAY, TSDB_MAX_ROLLUP_DELAY); if (TSDB_CODE_SUCCESS == code) { @@ -2211,7 +2307,7 @@ static int32_t checkCreateTable(STranslateContext* pCxt, SCreateTableStmt* pStmt code = checkTableSmaOption(pCxt, pStmt); } if (TSDB_CODE_SUCCESS == code) { - code = checkTableTags(pCxt, pStmt); + code = checkTableSchema(pCxt, pStmt); } return code; } @@ -3838,6 +3934,10 @@ static int32_t buildDropTableVgroupHashmap(STranslateContext* pCxt, SDropTableCl goto over; } + if (TSDB_CODE_PAR_TABLE_NOT_EXIST == code && pClause->ignoreNotExists) { + code = TSDB_CODE_SUCCESS; + } + *pIsSuperTable = false; SVgroupInfo info = {0}; diff --git a/source/libs/parser/src/parUtil.c b/source/libs/parser/src/parUtil.c index e839536218..e37dbd1edd 100644 --- a/source/libs/parser/src/parUtil.c +++ b/source/libs/parser/src/parUtil.c @@ -129,7 +129,23 @@ static char* getSyntaxErrFormat(int32_t errCode) { case TSDB_CODE_PAR_INVALID_DROP_STABLE: return "Cannot drop super table in batch"; case TSDB_CODE_PAR_INVALID_FILL_TIME_RANGE: - return "start(end) time of query range required or time range too large"; + return "Start(end) time of query range required or time range too large"; + case TSDB_CODE_PAR_DUPLICATED_COLUMN: + return "Duplicated column names"; + case TSDB_CODE_PAR_INVALID_TAGS_LENGTH: + return "Tags length exceeds max length %d"; + case TSDB_CODE_PAR_INVALID_ROW_LENGTH: + return "Row length exceeds max length %d"; + case TSDB_CODE_PAR_INVALID_COLUMNS_NUM: + return "Illegal number of columns"; + case TSDB_CODE_PAR_TOO_MANY_COLUMNS: + return "Too many columns"; + case TSDB_CODE_PAR_INVALID_FIRST_COLUMN: + return "First column must be timestamp"; + case TSDB_CODE_PAR_INVALID_VAR_COLUMN_LEN: + return "Invalid binary/nchar column length"; + case TSDB_CODE_PAR_INVALID_TAGS_NUM: + return "Invalid number of tag columns"; case TSDB_CODE_OUT_OF_MEMORY: return "Out of memory"; default: diff --git a/source/libs/planner/src/planLogicCreater.c b/source/libs/planner/src/planLogicCreater.c index 0bc700696b..3e19ccbd82 100644 --- a/source/libs/planner/src/planLogicCreater.c +++ b/source/libs/planner/src/planLogicCreater.c @@ -277,6 +277,11 @@ static int32_t createScanLogicNode(SLogicPlanContext* pCxt, SSelectStmt* pSelect code = nodesCollectFuncs(pSelect, SQL_CLAUSE_FROM, fmIsScanPseudoColumnFunc, &pScan->pScanPseudoCols); } + // rewrite the expression in subsequent clauses + if (TSDB_CODE_SUCCESS == code) { + code = rewriteExprForSelect(pScan->pScanPseudoCols, pSelect, SQL_CLAUSE_FROM); + } + pScan->scanType = getScanType(pCxt, pScan->pScanPseudoCols, pScan->pScanCols, pScan->pMeta); if (TSDB_CODE_SUCCESS == code) { diff --git a/source/libs/planner/src/planOptimizer.c b/source/libs/planner/src/planOptimizer.c index 67609355d7..dbce9abf36 100644 --- a/source/libs/planner/src/planOptimizer.c +++ b/source/libs/planner/src/planOptimizer.c @@ -123,14 +123,40 @@ static SNodeList* osdGetAllFuncs(SLogicNode* pNode) { return NULL; } +static bool needOptimizeDataRequire(const SFunctionNode* pFunc) { + if (!fmIsSpecialDataRequiredFunc(pFunc->funcId)) { + return false; + } + SNode* pPara = NULL; + FOREACH(pPara, pFunc->pParameterList) { + if (QUERY_NODE_COLUMN != nodeType(pPara) && QUERY_NODE_VALUE != nodeType(pPara)) { + return false; + } + } + return true; +} + +static bool needOptimizeDynamicScan(const SFunctionNode* pFunc) { + if (!fmIsDynamicScanOptimizedFunc(pFunc->funcId)) { + return false; + } + SNode* pPara = NULL; + FOREACH(pPara, pFunc->pParameterList) { + if (QUERY_NODE_COLUMN != nodeType(pPara) && QUERY_NODE_VALUE != nodeType(pPara)) { + return false; + } + } + return true; +} + static int32_t osdGetRelatedFuncs(SScanLogicNode* pScan, SNodeList** pSdrFuncs, SNodeList** pDsoFuncs) { SNodeList* pAllFuncs = osdGetAllFuncs(pScan->node.pParent); SNode* pFunc = NULL; FOREACH(pFunc, pAllFuncs) { int32_t code = TSDB_CODE_SUCCESS; - if (fmIsSpecialDataRequiredFunc(((SFunctionNode*)pFunc)->funcId)) { + if (needOptimizeDataRequire((SFunctionNode*)pFunc)) { code = nodesListMakeStrictAppend(pSdrFuncs, nodesCloneNode(pFunc)); - } else if (fmIsDynamicScanOptimizedFunc(((SFunctionNode*)pFunc)->funcId)) { + } else if (needOptimizeDynamicScan((SFunctionNode*)pFunc)) { code = nodesListMakeStrictAppend(pDsoFuncs, nodesCloneNode(pFunc)); } if (TSDB_CODE_SUCCESS != code) { @@ -541,9 +567,14 @@ static bool cpdIsPrimaryKeyEqualCond(SJoinLogicNode* pJoin, SNode* pCond) { if (QUERY_NODE_OPERATOR != nodeType(pCond)) { return false; } - SNodeList* pLeftCols = ((SLogicNode*)nodesListGetNode(pJoin->node.pChildren, 0))->pTargets; - SNodeList* pRightCols = ((SLogicNode*)nodesListGetNode(pJoin->node.pChildren, 1))->pTargets; + SOperatorNode* pOper = (SOperatorNode*)pJoin->pOnConditions; + if (OP_TYPE_EQUAL != pOper->opType) { + return false; + } + + SNodeList* pLeftCols = ((SLogicNode*)nodesListGetNode(pJoin->node.pChildren, 0))->pTargets; + SNodeList* pRightCols = ((SLogicNode*)nodesListGetNode(pJoin->node.pChildren, 1))->pTargets; if (cpdIsPrimaryKey(pOper->pLeft, pLeftCols)) { return cpdIsPrimaryKey(pOper->pRight, pRightCols); } else if (cpdIsPrimaryKey(pOper->pLeft, pRightCols)) { diff --git a/source/libs/planner/test/planOptimizeTest.cpp b/source/libs/planner/test/planOptimizeTest.cpp index deb20c65a4..4938618db6 100644 --- a/source/libs/planner/test/planOptimizeTest.cpp +++ b/source/libs/planner/test/planOptimizeTest.cpp @@ -20,11 +20,21 @@ using namespace std; class PlanOptimizeTest : public PlannerTestBase {}; +TEST_F(PlanOptimizeTest, optimizeScanData) { + useDb("root", "test"); + + run("SELECT COUNT(*) FROM t1"); + + run("SELECT COUNT(c1) FROM t1"); + + run("SELECT COUNT(CAST(c1 AS BIGINT)) FROM t1"); +} + TEST_F(PlanOptimizeTest, orderByPrimaryKey) { useDb("root", "test"); - run("select * from t1 order by ts"); - run("select * from t1 order by ts desc"); - run("select c1 from t1 order by ts"); - run("select c1 from t1 order by ts desc"); + run("SELECT * FROM t1 ORDER BY ts"); + run("SELECT * FROM t1 ORDER BY ts DESC"); + run("SELECT c1 FROM t1 ORDER BY ts"); + run("SELECT c1 FROM t1 ORDER BY ts DESC"); } diff --git a/source/libs/scheduler/src/scheduler.c b/source/libs/scheduler/src/scheduler.c index a70d366e9b..53772601ca 100644 --- a/source/libs/scheduler/src/scheduler.c +++ b/source/libs/scheduler/src/scheduler.c @@ -22,7 +22,7 @@ #include "trpc.h" SSchedulerMgmt schMgmt = { - .jobRef = -1, + .jobRef = -1, }; FORCE_INLINE SSchJob *schAcquireJob(int64_t refId) { return (SSchJob *)taosAcquireRef(schMgmt.jobRef, refId); } @@ -72,7 +72,7 @@ int32_t schInitTask(SSchJob *pJob, SSchTask *pTask, SSubplan *pPlan, SSchLevel * int32_t schInitJob(SSchJob **pSchJob, SQueryPlan *pDag, void *transport, SArray *pNodeList, const char *sql, int64_t startTs, bool syncSchedule) { int32_t code = 0; - int64_t refId = -1; + int64_t refId = -1; SSchJob *pJob = taosMemoryCalloc(1, sizeof(SSchJob)); if (NULL == pJob) { qError("QID:%" PRIx64 " calloc %d failed", pDag->queryId, (int32_t)sizeof(SSchJob)); @@ -124,7 +124,7 @@ int32_t schInitJob(SSchJob **pSchJob, SQueryPlan *pDag, void *transport, SArray } atomic_add_fetch_32(&schMgmt.jobNum, 1); - + if (NULL == schAcquireJob(refId)) { SCH_JOB_ELOG("schAcquireJob job failed, refId:%" PRIx64, refId); SCH_ERR_JRET(TSDB_CODE_SCH_STATUS_ERROR); @@ -1085,19 +1085,22 @@ int32_t schHandleResponseMsg(SSchJob *pJob, SSchTask *pTask, int32_t msgType, ch case TDMT_VND_CREATE_TABLE_RSP: { SVCreateTbBatchRsp batchRsp = {0}; if (msg) { - SCH_ERR_JRET(tDeserializeSVCreateTbBatchRsp(msg, msgSize, &batchRsp)); - if (batchRsp.pArray) { - int32_t num = taosArrayGetSize(batchRsp.pArray); - for (int32_t i = 0; i < num; ++i) { - SVCreateTbRsp *rsp = taosArrayGet(batchRsp.pArray, i); + SCoder coder = {0}; + tCoderInit(&coder, TD_LITTLE_ENDIAN, msg, msgSize, TD_DECODER); + code = tDecodeSVCreateTbBatchRsp(&coder, &batchRsp); + if (TSDB_CODE_SUCCESS == code && batchRsp.nRsps > 0) { + for (int32_t i = 0; i < batchRsp.nRsps; ++i) { + SVCreateTbRsp *rsp = batchRsp.pRsps + i; if (NEED_CLIENT_HANDLE_ERROR(rsp->code)) { - taosArrayDestroy(batchRsp.pArray); + tCoderClear(&coder); SCH_ERR_JRET(rsp->code); + } else if (TSDB_CODE_SUCCESS != rsp->code) { + code = rsp->code; } } - - taosArrayDestroy(batchRsp.pArray); } + tCoderClear(&coder); + SCH_ERR_JRET(code); } SCH_ERR_JRET(rspCode); @@ -1110,13 +1113,14 @@ int32_t schHandleResponseMsg(SSchJob *pJob, SSchTask *pTask, int32_t msgType, ch SCoder coder = {0}; tCoderInit(&coder, TD_LITTLE_ENDIAN, msg, msgSize, TD_DECODER); code = tDecodeSVDropTbBatchRsp(&coder, &batchRsp); - if (TSDB_CODE_SUCCESS == code && batchRsp.pArray) { - int32_t num = taosArrayGetSize(batchRsp.pArray); - for (int32_t i = 0; i < num; ++i) { - SVDropTbRsp *rsp = taosArrayGet(batchRsp.pArray, i); + if (TSDB_CODE_SUCCESS == code && batchRsp.nRsps > 0) { + for (int32_t i = 0; i < batchRsp.nRsps; ++i) { + SVDropTbRsp *rsp = batchRsp.pRsps + i; if (NEED_CLIENT_HANDLE_ERROR(rsp->code)) { tCoderClear(&coder); SCH_ERR_JRET(rsp->code); + } else if (TSDB_CODE_SUCCESS != rsp->code) { + code = rsp->code; } } } @@ -2282,10 +2286,10 @@ int32_t schCancelJob(SSchJob *pJob) { } void schCloseJobRef(void) { - if (!atomic_load_8((int8_t*)&schMgmt.exit)) { + if (!atomic_load_8((int8_t *)&schMgmt.exit)) { return; } - + SCH_LOCK(SCH_WRITE, &schMgmt.lock); if (atomic_load_32(&schMgmt.jobNum) <= 0 && schMgmt.jobRef >= 0) { taosCloseRef(schMgmt.jobRef); @@ -2791,8 +2795,8 @@ void schedulerFreeTaskList(SArray *taskList) { } void schedulerDestroy(void) { - atomic_store_8((int8_t*)&schMgmt.exit, 1); - + atomic_store_8((int8_t *)&schMgmt.exit, 1); + if (schMgmt.jobRef >= 0) { SSchJob *pJob = taosIterateRef(schMgmt.jobRef, 0); int64_t refId = 0; diff --git a/source/util/src/terror.c b/source/util/src/terror.c index 00fe8bd0e9..1470496c68 100644 --- a/source/util/src/terror.c +++ b/source/util/src/terror.c @@ -443,6 +443,9 @@ TAOS_DEFINE_ERROR(TSDB_CODE_SCH_STATUS_ERROR, "scheduler status erro TAOS_DEFINE_ERROR(TSDB_CODE_SCH_INTERNAL_ERROR, "scheduler internal error") TAOS_DEFINE_ERROR(TSDB_CODE_QW_MSG_ERROR, "Invalid msg order") +// parser +TAOS_DEFINE_ERROR(TSDB_CODE_PAR_TABLE_NOT_EXIST, "Table does not exist") + //planner TAOS_DEFINE_ERROR(TSDB_CODE_PLAN_INTERNAL_ERROR, "planner internal error") diff --git a/tests/script/tsim/query/explain.sim b/tests/script/tsim/query/explain.sim index 66d3c48f5d..71f7969c83 100644 --- a/tests/script/tsim/query/explain.sim +++ b/tests/script/tsim/query/explain.sim @@ -25,15 +25,15 @@ sql insert into tb3 values (now, 3, "Hash (cost=229.20..229.20 rows=101 width=2 sql create table tb4 using st1 tags(4); sql insert into tb4 values (now, 4, "Bitmap Heap Scan on tenk1 t1 (cost=5.07..229.20 rows=101 width=244) (actual time=0.080..0.526 rows=100 loops=1)"); -sql create table tb1 using st2 tags(1); -sql insert into tb1 values (now, 1, "Hash Join (cost=230.47..713.98 rows=101 width=488) (actual time=0.711..7.427 rows=100 loops=1)"); +#sql create table tb1 using st2 tags(1); +#sql insert into tb1 values (now, 1, "Hash Join (cost=230.47..713.98 rows=101 width=488) (actual time=0.711..7.427 rows=100 loops=1)"); -sql create table tb2 using st2 tags(2); -sql insert into tb2 values (now, 2, "Seq Scan on tenk2 t2 (cost=0.00..445.00 rows=10000 width=244) (actual time=0.007..2.583 rows=10000 loops=1)"); -sql create table tb3 using st2 tags(3); -sql insert into tb3 values (now, 3, "Hash (cost=229.20..229.20 rows=101 width=244) (actual time=0.659..0.659 rows=100 loops=1)"); -sql create table tb4 using st2 tags(4); -sql insert into tb4 values (now, 4, "Bitmap Heap Scan on tenk1 t1 (cost=5.07..229.20 rows=101 width=244) (actual time=0.080..0.526 rows=100 loops=1)"); +#sql create table tb2 using st2 tags(2); +#sql insert into tb2 values (now, 2, "Seq Scan on tenk2 t2 (cost=0.00..445.00 rows=10000 width=244) (actual time=0.007..2.583 rows=10000 loops=1)"); +#sql create table tb3 using st2 tags(3); +#sql insert into tb3 values (now, 3, "Hash (cost=229.20..229.20 rows=101 width=244) (actual time=0.659..0.659 rows=100 loops=1)"); +#sql create table tb4 using st2 tags(4); +#sql insert into tb4 values (now, 4, "Bitmap Heap Scan on tenk1 t1 (cost=5.07..229.20 rows=101 width=244) (actual time=0.080..0.526 rows=100 loops=1)"); print ======== step2 diff --git a/tests/script/tsim/query/session.sim b/tests/script/tsim/query/session.sim index a69b6249fc..c39956c0df 100644 --- a/tests/script/tsim/query/session.sim +++ b/tests/script/tsim/query/session.sim @@ -65,6 +65,15 @@ sql INSERT INTO dev_002 VALUES('2020-05-13 10:00:00.031', 5) sql INSERT INTO dev_002 VALUES('2020-05-13 10:00:00.036', 6) sql INSERT INTO dev_002 VALUES('2020-05-13 10:00:00.51', 7) +# vnode does not return the precision of the table +print ====> create database d1 precision 'us' +sql create database d1 precision 'us' +sql use d1 +sql create table dev_001 (ts timestamp ,i timestamp ,j int) +sql insert into dev_001 values(1623046993681000,now,1)(1623046993681001,now+1s,2)(1623046993681002,now+2s,3)(1623046993681004,now+5s,4) +sql create table secondts(ts timestamp,t2 timestamp,i int) +sql insert into secondts values(1623046993681000,now,1)(1623046993681001,now+1s,2)(1623046993681002,now+2s,3)(1623046993681004,now+5s,4) + $loop_test = 0 loop_test_pos: @@ -288,15 +297,6 @@ sql_error sql select count(*) from dev_001 session(ts,0s) sql_error select count(*) from dev_001 session(i,1y) sql_error select count(*) from dev_001 session(ts,1d) where ts <'2020-05-20 0:0:0' -# vnode does not return the precision of the table -print ====> create database d1 precision 'us' -sql create database d1 precision 'us' -sql use d1 -sql create table dev_001 (ts timestamp ,i timestamp ,j int) -sql insert into dev_001 values(1623046993681000,now,1)(1623046993681001,now+1s,2)(1623046993681002,now+2s,3)(1623046993681004,now+5s,4) -sql create table secondts(ts timestamp,t2 timestamp,i int) -sql insert into secondts values(1623046993681000,now,1)(1623046993681001,now+1s,2)(1623046993681002,now+2s,3)(1623046993681004,now+5s,4) - #print ====> select count(*) from dev_001 session(ts,1u) #sql select _wstartts, count(*) from dev_001 session(ts,1u) #print rows: $rows diff --git a/tests/script/tsim/table/basic1.sim b/tests/script/tsim/table/basic1.sim index be3b718fae..913ced74aa 100644 --- a/tests/script/tsim/table/basic1.sim +++ b/tests/script/tsim/table/basic1.sim @@ -91,9 +91,9 @@ print =============== create normal table sql create database ndb sql use ndb sql create table nt0 (ts timestamp, i int) -sql create table if not exists nt0 (ts timestamp, i int) +# sql create table if not exists nt0 (ts timestamp, i int) sql create table nt1 (ts timestamp, i int) -sql create table if not exists nt1 (ts timestamp, i int) +# sql create table if not exists nt1 (ts timestamp, i int) sql create table if not exists nt3 (ts timestamp, i int) sql show tables