Merge pull request #12323 from taosdata/feature/3.0_wxy
fix: some problems of parser
This commit is contained in:
commit
b7776f9244
|
@ -328,6 +328,9 @@ typedef struct {
|
||||||
int8_t alterType;
|
int8_t alterType;
|
||||||
int32_t numOfFields;
|
int32_t numOfFields;
|
||||||
SArray* pFields;
|
SArray* pFields;
|
||||||
|
int32_t ttl;
|
||||||
|
int32_t commentLen;
|
||||||
|
char* comment;
|
||||||
} SMAlterStbReq;
|
} SMAlterStbReq;
|
||||||
|
|
||||||
int32_t tSerializeSMAlterStbReq(void* buf, int32_t bufLen, SMAlterStbReq* pReq);
|
int32_t tSerializeSMAlterStbReq(void* buf, int32_t bufLen, SMAlterStbReq* pReq);
|
||||||
|
|
|
@ -179,6 +179,7 @@ typedef enum ENodeType {
|
||||||
QUERY_NODE_KILL_CONNECTION_STMT,
|
QUERY_NODE_KILL_CONNECTION_STMT,
|
||||||
QUERY_NODE_KILL_QUERY_STMT,
|
QUERY_NODE_KILL_QUERY_STMT,
|
||||||
QUERY_NODE_KILL_TRANSACTION_STMT,
|
QUERY_NODE_KILL_TRANSACTION_STMT,
|
||||||
|
QUERY_NODE_QUERY,
|
||||||
|
|
||||||
// logic plan node
|
// logic plan node
|
||||||
QUERY_NODE_LOGIC_PLAN_SCAN,
|
QUERY_NODE_LOGIC_PLAN_SCAN,
|
||||||
|
|
|
@ -295,6 +295,37 @@ typedef struct SExplainStmt {
|
||||||
SNode* pQuery;
|
SNode* pQuery;
|
||||||
} SExplainStmt;
|
} SExplainStmt;
|
||||||
|
|
||||||
|
typedef struct SCmdMsgInfo {
|
||||||
|
int16_t msgType;
|
||||||
|
SEpSet epSet;
|
||||||
|
void* pMsg;
|
||||||
|
int32_t msgLen;
|
||||||
|
void* pExtension; // todo remove it soon
|
||||||
|
} SCmdMsgInfo;
|
||||||
|
|
||||||
|
typedef enum EQueryExecMode {
|
||||||
|
QUERY_EXEC_MODE_LOCAL = 1,
|
||||||
|
QUERY_EXEC_MODE_RPC,
|
||||||
|
QUERY_EXEC_MODE_SCHEDULE,
|
||||||
|
QUERY_EXEC_MODE_EMPTY_RESULT
|
||||||
|
} EQueryExecMode;
|
||||||
|
|
||||||
|
typedef struct SQuery {
|
||||||
|
ENodeType type;
|
||||||
|
EQueryExecMode execMode;
|
||||||
|
bool haveResultSet;
|
||||||
|
SNode* pRoot;
|
||||||
|
int32_t numOfResCols;
|
||||||
|
SSchema* pResSchema;
|
||||||
|
int8_t precision;
|
||||||
|
SCmdMsgInfo* pCmdMsg;
|
||||||
|
int32_t msgType;
|
||||||
|
SArray* pDbList;
|
||||||
|
SArray* pTableList;
|
||||||
|
bool showRewrite;
|
||||||
|
int32_t placeholderNum;
|
||||||
|
} SQuery;
|
||||||
|
|
||||||
void nodesWalkSelectStmt(SSelectStmt* pSelect, ESqlClause clause, FNodeWalker walker, void* pContext);
|
void nodesWalkSelectStmt(SSelectStmt* pSelect, ESqlClause clause, FNodeWalker walker, void* pContext);
|
||||||
void nodesRewriteSelectStmt(SSelectStmt* pSelect, ESqlClause clause, FNodeRewriter rewriter, void* pContext);
|
void nodesRewriteSelectStmt(SSelectStmt* pSelect, ESqlClause clause, FNodeRewriter rewriter, void* pContext);
|
||||||
|
|
||||||
|
|
|
@ -48,36 +48,6 @@ typedef struct SParseContext {
|
||||||
bool isSuperUser;
|
bool isSuperUser;
|
||||||
} SParseContext;
|
} SParseContext;
|
||||||
|
|
||||||
typedef struct SCmdMsgInfo {
|
|
||||||
int16_t msgType;
|
|
||||||
SEpSet epSet;
|
|
||||||
void* pMsg;
|
|
||||||
int32_t msgLen;
|
|
||||||
void* pExtension; // todo remove it soon
|
|
||||||
} SCmdMsgInfo;
|
|
||||||
|
|
||||||
typedef enum EQueryExecMode {
|
|
||||||
QUERY_EXEC_MODE_LOCAL = 1,
|
|
||||||
QUERY_EXEC_MODE_RPC,
|
|
||||||
QUERY_EXEC_MODE_SCHEDULE,
|
|
||||||
QUERY_EXEC_MODE_EMPTY_RESULT
|
|
||||||
} EQueryExecMode;
|
|
||||||
|
|
||||||
typedef struct SQuery {
|
|
||||||
EQueryExecMode execMode;
|
|
||||||
bool haveResultSet;
|
|
||||||
SNode* pRoot;
|
|
||||||
int32_t numOfResCols;
|
|
||||||
SSchema* pResSchema;
|
|
||||||
int8_t precision;
|
|
||||||
SCmdMsgInfo* pCmdMsg;
|
|
||||||
int32_t msgType;
|
|
||||||
SArray* pDbList;
|
|
||||||
SArray* pTableList;
|
|
||||||
bool showRewrite;
|
|
||||||
int32_t placeholderNum;
|
|
||||||
} SQuery;
|
|
||||||
|
|
||||||
int32_t qParseQuerySql(SParseContext* pCxt, SQuery** pQuery);
|
int32_t qParseQuerySql(SParseContext* pCxt, SQuery** pQuery);
|
||||||
bool isInsertSql(const char* pStr, size_t length);
|
bool isInsertSql(const char* pStr, size_t length);
|
||||||
|
|
||||||
|
@ -103,9 +73,10 @@ void destroyBoundColumnInfo(void* pBoundInfo);
|
||||||
int32_t qCreateSName(SName* pName, const char* pTableName, int32_t acctId, char* dbName, char* msgBuf,
|
int32_t qCreateSName(SName* pName, const char* pTableName, int32_t acctId, char* dbName, char* msgBuf,
|
||||||
int32_t msgBufLen);
|
int32_t msgBufLen);
|
||||||
|
|
||||||
void* smlInitHandle(SQuery *pQuery);
|
void* smlInitHandle(SQuery* pQuery);
|
||||||
void smlDestroyHandle(void *pHandle);
|
void smlDestroyHandle(void* pHandle);
|
||||||
int32_t smlBindData(void *handle, SArray *tags, SArray *colsFormat, SArray *colsSchema, SArray *cols, bool format, STableMeta *pTableMeta, char *tableName, char *msgBuf, int16_t msgBufLen);
|
int32_t smlBindData(void* handle, SArray* tags, SArray* colsFormat, SArray* colsSchema, SArray* cols, bool format,
|
||||||
|
STableMeta* pTableMeta, char* tableName, char* msgBuf, int16_t msgBufLen);
|
||||||
int32_t smlBuildOutput(void* handle, SHashObj* pVgHash);
|
int32_t smlBuildOutput(void* handle, SHashObj* pVgHash);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
|
|
|
@ -633,6 +633,7 @@ int32_t* taosGetErrno();
|
||||||
#define TSDB_CODE_PAR_INVALID_VAR_COLUMN_LEN TAOS_DEF_ERROR_CODE(0, 0x2642)
|
#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)
|
#define TSDB_CODE_PAR_INVALID_TAGS_NUM TAOS_DEF_ERROR_CODE(0, 0x2643)
|
||||||
#define TSDB_CODE_PAR_PERMISSION_DENIED TAOS_DEF_ERROR_CODE(0, 0x2644)
|
#define TSDB_CODE_PAR_PERMISSION_DENIED TAOS_DEF_ERROR_CODE(0, 0x2644)
|
||||||
|
#define TSDB_CODE_PAR_INVALID_STREAM_QUERY TAOS_DEF_ERROR_CODE(0, 0x2645)
|
||||||
|
|
||||||
//planner
|
//planner
|
||||||
#define TSDB_CODE_PLAN_INTERNAL_ERROR TAOS_DEF_ERROR_CODE(0, 0x2700)
|
#define TSDB_CODE_PLAN_INTERNAL_ERROR TAOS_DEF_ERROR_CODE(0, 0x2700)
|
||||||
|
|
|
@ -607,6 +607,11 @@ int32_t tSerializeSMAlterStbReq(void *buf, int32_t bufLen, SMAlterStbReq *pReq)
|
||||||
if (tEncodeI32(&encoder, pField->bytes) < 0) return -1;
|
if (tEncodeI32(&encoder, pField->bytes) < 0) return -1;
|
||||||
if (tEncodeCStr(&encoder, pField->name) < 0) return -1;
|
if (tEncodeCStr(&encoder, pField->name) < 0) return -1;
|
||||||
}
|
}
|
||||||
|
if (tEncodeI32(&encoder, pReq->ttl) < 0) return -1;
|
||||||
|
if (tEncodeI32(&encoder, pReq->commentLen) < 0) return -1;
|
||||||
|
if (pReq->commentLen > 0) {
|
||||||
|
if (tEncodeCStr(&encoder, pReq->comment) < 0) return -1;
|
||||||
|
}
|
||||||
tEndEncode(&encoder);
|
tEndEncode(&encoder);
|
||||||
|
|
||||||
int32_t tlen = encoder.pos;
|
int32_t tlen = encoder.pos;
|
||||||
|
@ -639,6 +644,14 @@ int32_t tDeserializeSMAlterStbReq(void *buf, int32_t bufLen, SMAlterStbReq *pReq
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (tDecodeI32(&decoder, &pReq->ttl) < 0) return -1;
|
||||||
|
if (tDecodeI32(&decoder, &pReq->commentLen) < 0) return -1;
|
||||||
|
if (pReq->commentLen > 0) {
|
||||||
|
pReq->comment = taosMemoryMalloc(pReq->commentLen);
|
||||||
|
if (pReq->comment == NULL) return -1;
|
||||||
|
if (tDecodeCStrTo(&decoder, pReq->comment) < 0) return -1;
|
||||||
|
}
|
||||||
|
|
||||||
tEndDecode(&decoder);
|
tEndDecode(&decoder);
|
||||||
tDecoderClear(&decoder);
|
tDecoderClear(&decoder);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -987,6 +987,16 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
|
||||||
.sprocessFunc = NULL,
|
.sprocessFunc = NULL,
|
||||||
.finalizeFunc = NULL
|
.finalizeFunc = NULL
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
.name = "_c0",
|
||||||
|
.type = FUNCTION_TYPE_ROWTS,
|
||||||
|
.classification = FUNC_MGT_PSEUDO_COLUMN_FUNC,
|
||||||
|
.translateFunc = translateTimePseudoColumn,
|
||||||
|
.getEnvFunc = getTimePseudoFuncEnv,
|
||||||
|
.initFunc = NULL,
|
||||||
|
.sprocessFunc = NULL,
|
||||||
|
.finalizeFunc = NULL
|
||||||
|
},
|
||||||
{
|
{
|
||||||
.name = "tbname",
|
.name = "tbname",
|
||||||
.type = FUNCTION_TYPE_TBNAME,
|
.type = FUNCTION_TYPE_TBNAME,
|
||||||
|
|
|
@ -907,6 +907,13 @@ SNode* createDropSuperTableStmt(SAstCreateContext* pCxt, bool ignoreNotExists, S
|
||||||
return (SNode*)pStmt;
|
return (SNode*)pStmt;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static SNode* createAlterTableStmtFinalize(SNode* pRealTable, SAlterTableStmt* pStmt) {
|
||||||
|
strcpy(pStmt->dbName, ((SRealTableNode*)pRealTable)->table.dbName);
|
||||||
|
strcpy(pStmt->tableName, ((SRealTableNode*)pRealTable)->table.tableName);
|
||||||
|
nodesDestroyNode(pRealTable);
|
||||||
|
return (SNode*)pStmt;
|
||||||
|
}
|
||||||
|
|
||||||
SNode* createAlterTableModifyOptions(SAstCreateContext* pCxt, SNode* pRealTable, SNode* pOptions) {
|
SNode* createAlterTableModifyOptions(SAstCreateContext* pCxt, SNode* pRealTable, SNode* pOptions) {
|
||||||
if (NULL == pRealTable) {
|
if (NULL == pRealTable) {
|
||||||
return NULL;
|
return NULL;
|
||||||
|
@ -915,7 +922,7 @@ SNode* createAlterTableModifyOptions(SAstCreateContext* pCxt, SNode* pRealTable,
|
||||||
CHECK_OUT_OF_MEM(pStmt);
|
CHECK_OUT_OF_MEM(pStmt);
|
||||||
pStmt->alterType = TSDB_ALTER_TABLE_UPDATE_OPTIONS;
|
pStmt->alterType = TSDB_ALTER_TABLE_UPDATE_OPTIONS;
|
||||||
pStmt->pOptions = (STableOptions*)pOptions;
|
pStmt->pOptions = (STableOptions*)pOptions;
|
||||||
return (SNode*)pStmt;
|
return createAlterTableStmtFinalize(pRealTable, pStmt);
|
||||||
}
|
}
|
||||||
|
|
||||||
SNode* createAlterTableAddModifyCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_t alterType,
|
SNode* createAlterTableAddModifyCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_t alterType,
|
||||||
|
@ -928,7 +935,7 @@ SNode* createAlterTableAddModifyCol(SAstCreateContext* pCxt, SNode* pRealTable,
|
||||||
pStmt->alterType = alterType;
|
pStmt->alterType = alterType;
|
||||||
strncpy(pStmt->colName, pColName->z, pColName->n);
|
strncpy(pStmt->colName, pColName->z, pColName->n);
|
||||||
pStmt->dataType = dataType;
|
pStmt->dataType = dataType;
|
||||||
return (SNode*)pStmt;
|
return createAlterTableStmtFinalize(pRealTable, pStmt);
|
||||||
}
|
}
|
||||||
|
|
||||||
SNode* createAlterTableDropCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_t alterType, const SToken* pColName) {
|
SNode* createAlterTableDropCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_t alterType, const SToken* pColName) {
|
||||||
|
@ -939,7 +946,7 @@ SNode* createAlterTableDropCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_
|
||||||
CHECK_OUT_OF_MEM(pStmt);
|
CHECK_OUT_OF_MEM(pStmt);
|
||||||
pStmt->alterType = alterType;
|
pStmt->alterType = alterType;
|
||||||
strncpy(pStmt->colName, pColName->z, pColName->n);
|
strncpy(pStmt->colName, pColName->z, pColName->n);
|
||||||
return (SNode*)pStmt;
|
return createAlterTableStmtFinalize(pRealTable, pStmt);
|
||||||
}
|
}
|
||||||
|
|
||||||
SNode* createAlterTableRenameCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_t alterType,
|
SNode* createAlterTableRenameCol(SAstCreateContext* pCxt, SNode* pRealTable, int8_t alterType,
|
||||||
|
@ -952,7 +959,7 @@ SNode* createAlterTableRenameCol(SAstCreateContext* pCxt, SNode* pRealTable, int
|
||||||
pStmt->alterType = alterType;
|
pStmt->alterType = alterType;
|
||||||
strncpy(pStmt->colName, pOldColName->z, pOldColName->n);
|
strncpy(pStmt->colName, pOldColName->z, pOldColName->n);
|
||||||
strncpy(pStmt->newColName, pNewColName->z, pNewColName->n);
|
strncpy(pStmt->newColName, pNewColName->z, pNewColName->n);
|
||||||
return (SNode*)pStmt;
|
return createAlterTableStmtFinalize(pRealTable, pStmt);
|
||||||
}
|
}
|
||||||
|
|
||||||
SNode* createAlterTableSetTag(SAstCreateContext* pCxt, SNode* pRealTable, const SToken* pTagName, SNode* pVal) {
|
SNode* createAlterTableSetTag(SAstCreateContext* pCxt, SNode* pRealTable, const SToken* pTagName, SNode* pVal) {
|
||||||
|
@ -964,7 +971,7 @@ SNode* createAlterTableSetTag(SAstCreateContext* pCxt, SNode* pRealTable, const
|
||||||
pStmt->alterType = TSDB_ALTER_TABLE_UPDATE_TAG_VAL;
|
pStmt->alterType = TSDB_ALTER_TABLE_UPDATE_TAG_VAL;
|
||||||
strncpy(pStmt->colName, pTagName->z, pTagName->n);
|
strncpy(pStmt->colName, pTagName->z, pTagName->n);
|
||||||
pStmt->pVal = (SValueNode*)pVal;
|
pStmt->pVal = (SValueNode*)pVal;
|
||||||
return (SNode*)pStmt;
|
return createAlterTableStmtFinalize(pRealTable, pStmt);
|
||||||
}
|
}
|
||||||
|
|
||||||
SNode* createUseDatabaseStmt(SAstCreateContext* pCxt, SToken* pDbName) {
|
SNode* createUseDatabaseStmt(SAstCreateContext* pCxt, SToken* pDbName) {
|
||||||
|
|
|
@ -214,6 +214,7 @@ static SKeyword keywordTable[] = {
|
||||||
{"WINDOW_CLOSE", TK_WINDOW_CLOSE},
|
{"WINDOW_CLOSE", TK_WINDOW_CLOSE},
|
||||||
{"WITH", TK_WITH},
|
{"WITH", TK_WITH},
|
||||||
{"WRITE", TK_WRITE},
|
{"WRITE", TK_WRITE},
|
||||||
|
{"_C0", TK_ROWTS},
|
||||||
{"_QENDTS", TK_QENDTS},
|
{"_QENDTS", TK_QENDTS},
|
||||||
{"_QSTARTTS", TK_QSTARTTS},
|
{"_QSTARTTS", TK_QSTARTTS},
|
||||||
{"_ROWTS", TK_ROWTS},
|
{"_ROWTS", TK_ROWTS},
|
||||||
|
|
|
@ -782,6 +782,7 @@ static EDealRes rewriteColToSelectValFunc(STranslateContext* pCxt, bool* pHasSel
|
||||||
return DEAL_RES_ERROR;
|
return DEAL_RES_ERROR;
|
||||||
}
|
}
|
||||||
strcpy(pFunc->functionName, "_select_value");
|
strcpy(pFunc->functionName, "_select_value");
|
||||||
|
strcpy(pFunc->node.aliasName, ((SExprNode*)*pNode)->aliasName);
|
||||||
pCxt->errCode = nodesListMakeAppend(&pFunc->pParameterList, *pNode);
|
pCxt->errCode = nodesListMakeAppend(&pFunc->pParameterList, *pNode);
|
||||||
if (TSDB_CODE_SUCCESS == pCxt->errCode) {
|
if (TSDB_CODE_SUCCESS == pCxt->errCode) {
|
||||||
translateFunction(pCxt, pFunc);
|
translateFunction(pCxt, pFunc);
|
||||||
|
@ -2540,10 +2541,18 @@ static int32_t buildCreateStbReq(STranslateContext* pCxt, SCreateTableStmt* pStm
|
||||||
pReq->igExists = pStmt->ignoreExists;
|
pReq->igExists = pStmt->ignoreExists;
|
||||||
pReq->xFilesFactor = pStmt->pOptions->filesFactor;
|
pReq->xFilesFactor = pStmt->pOptions->filesFactor;
|
||||||
pReq->delay = pStmt->pOptions->delay;
|
pReq->delay = pStmt->pOptions->delay;
|
||||||
|
pReq->ttl = pStmt->pOptions->ttl;
|
||||||
columnDefNodeToField(pStmt->pCols, &pReq->pColumns);
|
columnDefNodeToField(pStmt->pCols, &pReq->pColumns);
|
||||||
columnDefNodeToField(pStmt->pTags, &pReq->pTags);
|
columnDefNodeToField(pStmt->pTags, &pReq->pTags);
|
||||||
pReq->numOfColumns = LIST_LENGTH(pStmt->pCols);
|
pReq->numOfColumns = LIST_LENGTH(pStmt->pCols);
|
||||||
pReq->numOfTags = LIST_LENGTH(pStmt->pTags);
|
pReq->numOfTags = LIST_LENGTH(pStmt->pTags);
|
||||||
|
if ('\0' != pStmt->pOptions->comment[0]) {
|
||||||
|
pReq->comment = strdup(pStmt->pOptions->comment);
|
||||||
|
if (NULL == pReq->comment) {
|
||||||
|
return TSDB_CODE_OUT_OF_MEMORY;
|
||||||
|
}
|
||||||
|
pReq->commentLen = strlen(pStmt->pOptions->comment) + 1;
|
||||||
|
}
|
||||||
|
|
||||||
SName tableName;
|
SName tableName;
|
||||||
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pStmt->dbName, pStmt->tableName, &tableName), pReq->name);
|
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pStmt->dbName, pStmt->tableName, &tableName), pReq->name);
|
||||||
|
@ -2602,6 +2611,18 @@ static int32_t translateDropSuperTable(STranslateContext* pCxt, SDropSuperTableS
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t setAlterTableField(SAlterTableStmt* pStmt, SMAlterStbReq* pAlterReq) {
|
static int32_t setAlterTableField(SAlterTableStmt* pStmt, SMAlterStbReq* pAlterReq) {
|
||||||
|
if (TSDB_ALTER_TABLE_UPDATE_OPTIONS == pStmt->alterType) {
|
||||||
|
pAlterReq->ttl = pStmt->pOptions->ttl;
|
||||||
|
if ('\0' != pStmt->pOptions->comment[0]) {
|
||||||
|
pAlterReq->comment = strdup(pStmt->pOptions->comment);
|
||||||
|
if (NULL == pAlterReq->comment) {
|
||||||
|
return TSDB_CODE_OUT_OF_MEMORY;
|
||||||
|
}
|
||||||
|
pAlterReq->commentLen = strlen(pStmt->pOptions->comment) + 1;
|
||||||
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
pAlterReq->pFields = taosArrayInit(2, sizeof(TAOS_FIELD));
|
pAlterReq->pFields = taosArrayInit(2, sizeof(TAOS_FIELD));
|
||||||
if (NULL == pAlterReq->pFields) {
|
if (NULL == pAlterReq->pFields) {
|
||||||
return TSDB_CODE_OUT_OF_MEMORY;
|
return TSDB_CODE_OUT_OF_MEMORY;
|
||||||
|
@ -2614,7 +2635,7 @@ static int32_t setAlterTableField(SAlterTableStmt* pStmt, SMAlterStbReq* pAlterR
|
||||||
case TSDB_ALTER_TABLE_DROP_COLUMN:
|
case TSDB_ALTER_TABLE_DROP_COLUMN:
|
||||||
case TSDB_ALTER_TABLE_UPDATE_COLUMN_BYTES:
|
case TSDB_ALTER_TABLE_UPDATE_COLUMN_BYTES:
|
||||||
case TSDB_ALTER_TABLE_UPDATE_TAG_BYTES: {
|
case TSDB_ALTER_TABLE_UPDATE_TAG_BYTES: {
|
||||||
TAOS_FIELD field = {.type = pStmt->dataType.type, .bytes = pStmt->dataType.bytes};
|
TAOS_FIELD field = {.type = pStmt->dataType.type, .bytes = calcTypeBytes(pStmt->dataType)};
|
||||||
strcpy(field.name, pStmt->colName);
|
strcpy(field.name, pStmt->colName);
|
||||||
taosArrayPush(pAlterReq->pFields, &field);
|
taosArrayPush(pAlterReq->pFields, &field);
|
||||||
break;
|
break;
|
||||||
|
@ -2625,7 +2646,7 @@ static int32_t setAlterTableField(SAlterTableStmt* pStmt, SMAlterStbReq* pAlterR
|
||||||
strcpy(oldField.name, pStmt->colName);
|
strcpy(oldField.name, pStmt->colName);
|
||||||
taosArrayPush(pAlterReq->pFields, &oldField);
|
taosArrayPush(pAlterReq->pFields, &oldField);
|
||||||
TAOS_FIELD newField = {0};
|
TAOS_FIELD newField = {0};
|
||||||
strcpy(oldField.name, pStmt->newColName);
|
strcpy(newField.name, pStmt->newColName);
|
||||||
taosArrayPush(pAlterReq->pFields, &newField);
|
taosArrayPush(pAlterReq->pFields, &newField);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -2642,7 +2663,7 @@ static int32_t translateAlterTable(STranslateContext* pCxt, SAlterTableStmt* pSt
|
||||||
SName tableName;
|
SName tableName;
|
||||||
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pStmt->dbName, pStmt->tableName, &tableName), alterReq.name);
|
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pStmt->dbName, pStmt->tableName, &tableName), alterReq.name);
|
||||||
alterReq.alterType = pStmt->alterType;
|
alterReq.alterType = pStmt->alterType;
|
||||||
if (TSDB_ALTER_TABLE_UPDATE_OPTIONS == pStmt->alterType || TSDB_ALTER_TABLE_UPDATE_TAG_VAL == pStmt->alterType) {
|
if (TSDB_ALTER_TABLE_UPDATE_TAG_VAL == pStmt->alterType) {
|
||||||
return TSDB_CODE_FAILED;
|
return TSDB_CODE_FAILED;
|
||||||
} else {
|
} else {
|
||||||
if (TSDB_CODE_SUCCESS != setAlterTableField(pStmt, &alterReq)) {
|
if (TSDB_CODE_SUCCESS != setAlterTableField(pStmt, &alterReq)) {
|
||||||
|
@ -2929,7 +2950,6 @@ static int32_t buildCreateTopicReq(STranslateContext* pCxt, SCreateTopicStmt* pS
|
||||||
SName name;
|
SName name;
|
||||||
tNameSetDbName(&name, pCxt->pParseCxt->acctId, pStmt->topicName, strlen(pStmt->topicName));
|
tNameSetDbName(&name, pCxt->pParseCxt->acctId, pStmt->topicName, strlen(pStmt->topicName));
|
||||||
tNameGetFullDbName(&name, pReq->name);
|
tNameGetFullDbName(&name, pReq->name);
|
||||||
/*tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pCxt->pParseCxt->db, pStmt->topicName, &name), pReq->name);*/
|
|
||||||
pReq->igExists = pStmt->ignoreExists;
|
pReq->igExists = pStmt->ignoreExists;
|
||||||
pReq->withTbName = pStmt->pOptions->withTable;
|
pReq->withTbName = pStmt->pOptions->withTable;
|
||||||
pReq->withSchema = pStmt->pOptions->withSchema;
|
pReq->withSchema = pStmt->pOptions->withSchema;
|
||||||
|
@ -2993,7 +3013,8 @@ static int32_t translateDropTopic(STranslateContext* pCxt, SDropTopicStmt* pStmt
|
||||||
SMDropTopicReq dropReq = {0};
|
SMDropTopicReq dropReq = {0};
|
||||||
|
|
||||||
SName name;
|
SName name;
|
||||||
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pCxt->pParseCxt->db, pStmt->topicName, &name), dropReq.name);
|
tNameSetDbName(&name, pCxt->pParseCxt->acctId, pStmt->topicName, strlen(pStmt->topicName));
|
||||||
|
tNameGetFullDbName(&name, dropReq.name);
|
||||||
dropReq.igNotExists = pStmt->ignoreNotExists;
|
dropReq.igNotExists = pStmt->ignoreNotExists;
|
||||||
|
|
||||||
return buildCmdMsg(pCxt, TDMT_MND_DROP_TOPIC, (FSerializeFunc)tSerializeSMDropTopicReq, &dropReq);
|
return buildCmdMsg(pCxt, TDMT_MND_DROP_TOPIC, (FSerializeFunc)tSerializeSMDropTopicReq, &dropReq);
|
||||||
|
@ -3033,28 +3054,48 @@ static int32_t translateKillTransaction(STranslateContext* pCxt, SKillStmt* pStm
|
||||||
return buildCmdMsg(pCxt, TDMT_MND_KILL_TRANS, (FSerializeFunc)tSerializeSKillTransReq, &killReq);
|
return buildCmdMsg(pCxt, TDMT_MND_KILL_TRANS, (FSerializeFunc)tSerializeSKillTransReq, &killReq);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t translateCreateStream(STranslateContext* pCxt, SCreateStreamStmt* pStmt) {
|
static int32_t checkCreateStream(STranslateContext* pCxt, SCreateStreamStmt* pStmt) {
|
||||||
SCMCreateStreamReq createReq = {0};
|
if (NULL == pStmt->pQuery) {
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
createReq.igExists = pStmt->ignoreExists;
|
if (QUERY_NODE_SELECT_STMT == nodeType(pStmt->pQuery)) {
|
||||||
|
SSelectStmt* pSelect = (SSelectStmt*)pStmt->pQuery;
|
||||||
|
if (QUERY_NODE_REAL_TABLE == nodeType(pSelect->pFromTable)) {
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_STREAM_QUERY);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void getSourceDatabase(SNode* pStmt, int32_t acctId, char* pDbFName) {
|
||||||
|
SName name = {.type = TSDB_DB_NAME_T, .acctId = acctId};
|
||||||
|
strcpy(name.dbname, ((SRealTableNode*)(((SSelectStmt*)pStmt)->pFromTable))->table.dbName);
|
||||||
|
tNameGetFullDbName(&name, pDbFName);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int32_t buildCreateStreamReq(STranslateContext* pCxt, SCreateStreamStmt* pStmt, SCMCreateStreamReq* pReq) {
|
||||||
|
pReq->igExists = pStmt->ignoreExists;
|
||||||
|
|
||||||
SName name;
|
SName name;
|
||||||
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pCxt->pParseCxt->db, pStmt->streamName, &name), createReq.name);
|
tNameExtractFullName(toName(pCxt->pParseCxt->acctId, pCxt->pParseCxt->db, pStmt->streamName, &name), pReq->name);
|
||||||
|
|
||||||
if ('\0' != pStmt->targetTabName[0]) {
|
if ('\0' != pStmt->targetTabName[0]) {
|
||||||
strcpy(name.dbname, pStmt->targetDbName);
|
strcpy(name.dbname, pStmt->targetDbName);
|
||||||
strcpy(name.tname, pStmt->targetTabName);
|
strcpy(name.tname, pStmt->targetTabName);
|
||||||
tNameExtractFullName(&name, createReq.targetStbFullName);
|
tNameExtractFullName(&name, pReq->targetStbFullName);
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t code = translateQuery(pCxt, pStmt->pQuery);
|
int32_t code = translateQuery(pCxt, pStmt->pQuery);
|
||||||
if (TSDB_CODE_SUCCESS == code) {
|
if (TSDB_CODE_SUCCESS == code) {
|
||||||
code = nodesNodeToString(pStmt->pQuery, false, &createReq.ast, NULL);
|
getSourceDatabase(pStmt->pQuery, pCxt->pParseCxt->acctId, pReq->sourceDB);
|
||||||
|
code = nodesNodeToString(pStmt->pQuery, false, &pReq->ast, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (TSDB_CODE_SUCCESS == code) {
|
if (TSDB_CODE_SUCCESS == code) {
|
||||||
createReq.sql = strdup(pCxt->pParseCxt->pSql);
|
pReq->sql = strdup(pCxt->pParseCxt->pSql);
|
||||||
if (NULL == createReq.sql) {
|
if (NULL == pReq->sql) {
|
||||||
code = TSDB_CODE_OUT_OF_MEMORY;
|
code = TSDB_CODE_OUT_OF_MEMORY;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3064,11 +3105,20 @@ static int32_t translateCreateStream(STranslateContext* pCxt, SCreateStreamStmt*
|
||||||
: TSDB_CODE_SUCCESS;
|
: TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
if (TSDB_CODE_SUCCESS == code) {
|
if (TSDB_CODE_SUCCESS == code) {
|
||||||
createReq.triggerType = pStmt->pOptions->triggerType;
|
pReq->triggerType = pStmt->pOptions->triggerType;
|
||||||
createReq.watermark =
|
pReq->watermark = (NULL != pStmt->pOptions->pWatermark ? ((SValueNode*)pStmt->pOptions->pWatermark)->datum.i : 0);
|
||||||
(NULL != pStmt->pOptions->pWatermark ? ((SValueNode*)pStmt->pOptions->pWatermark)->datum.i : 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int32_t translateCreateStream(STranslateContext* pCxt, SCreateStreamStmt* pStmt) {
|
||||||
|
SCMCreateStreamReq createReq = {0};
|
||||||
|
|
||||||
|
int32_t code = checkCreateStream(pCxt, pStmt);
|
||||||
|
if (TSDB_CODE_SUCCESS == code) {
|
||||||
|
code = buildCreateStreamReq(pCxt, pStmt, &createReq);
|
||||||
|
}
|
||||||
if (TSDB_CODE_SUCCESS == code) {
|
if (TSDB_CODE_SUCCESS == code) {
|
||||||
code = buildCmdMsg(pCxt, TDMT_MND_CREATE_STREAM, (FSerializeFunc)tSerializeSCMCreateStreamReq, &createReq);
|
code = buildCmdMsg(pCxt, TDMT_MND_CREATE_STREAM, (FSerializeFunc)tSerializeSCMCreateStreamReq, &createReq);
|
||||||
}
|
}
|
||||||
|
@ -3166,7 +3216,7 @@ static int32_t translateRevoke(STranslateContext* pCxt, SRevokeStmt* pStmt) {
|
||||||
req.alterType = TSDB_ALTER_USER_REMOVE_WRITE_DB;
|
req.alterType = TSDB_ALTER_USER_REMOVE_WRITE_DB;
|
||||||
}
|
}
|
||||||
strcpy(req.user, pStmt->userName);
|
strcpy(req.user, pStmt->userName);
|
||||||
strcpy(req.dbname, pStmt->dbName);
|
sprintf(req.dbname, "%d.%s", pCxt->pParseCxt->acctId, pStmt->dbName);
|
||||||
return buildCmdMsg(pCxt, TDMT_MND_ALTER_USER, (FSerializeFunc)tSerializeSAlterUserReq, &req);
|
return buildCmdMsg(pCxt, TDMT_MND_ALTER_USER, (FSerializeFunc)tSerializeSAlterUserReq, &req);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -19,7 +19,7 @@ using namespace std;
|
||||||
|
|
||||||
namespace ParserTest {
|
namespace ParserTest {
|
||||||
|
|
||||||
class ParserInitialATest : public ParserTestBase {};
|
class ParserInitialATest : public ParserDdlTest {};
|
||||||
|
|
||||||
TEST_F(ParserInitialATest, alterAccount) {
|
TEST_F(ParserInitialATest, alterAccount) {
|
||||||
useDb("root", "test");
|
useDb("root", "test");
|
||||||
|
@ -72,16 +72,103 @@ TEST_F(ParserInitialATest, alterDatabase) {
|
||||||
TEST_F(ParserInitialATest, alterTable) {
|
TEST_F(ParserInitialATest, alterTable) {
|
||||||
useDb("root", "test");
|
useDb("root", "test");
|
||||||
|
|
||||||
// run("ALTER TABLE t1 TTL 10");
|
SMAlterStbReq expect = {0};
|
||||||
// run("ALTER TABLE t1 COMMENT 'test'");
|
|
||||||
|
auto setAlterStbReqFunc = [&](const char* pTbname, int8_t alterType, int32_t numOfFields = 0,
|
||||||
|
const char* pField1Name = nullptr, int8_t field1Type = 0, int32_t field1Bytes = 0,
|
||||||
|
const char* pField2Name = nullptr, const char* pComment = nullptr,
|
||||||
|
int32_t ttl = TSDB_DEFAULT_TABLE_TTL) {
|
||||||
|
int32_t len = snprintf(expect.name, sizeof(expect.name), "0.test.%s", pTbname);
|
||||||
|
expect.name[len] = '\0';
|
||||||
|
expect.alterType = alterType;
|
||||||
|
expect.ttl = ttl;
|
||||||
|
if (nullptr != pComment) {
|
||||||
|
expect.comment = strdup(pComment);
|
||||||
|
expect.commentLen = strlen(pComment) + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
expect.numOfFields = numOfFields;
|
||||||
|
if (NULL == expect.pFields) {
|
||||||
|
expect.pFields = taosArrayInit(2, sizeof(TAOS_FIELD));
|
||||||
|
TAOS_FIELD field = {0};
|
||||||
|
taosArrayPush(expect.pFields, &field);
|
||||||
|
taosArrayPush(expect.pFields, &field);
|
||||||
|
}
|
||||||
|
|
||||||
|
TAOS_FIELD* pField = (TAOS_FIELD*)taosArrayGet(expect.pFields, 0);
|
||||||
|
if (NULL != pField1Name) {
|
||||||
|
strcpy(pField->name, pField1Name);
|
||||||
|
pField->name[strlen(pField1Name)] = '\0';
|
||||||
|
} else {
|
||||||
|
memset(pField, 0, sizeof(TAOS_FIELD));
|
||||||
|
}
|
||||||
|
pField->type = field1Type;
|
||||||
|
pField->bytes = field1Bytes > 0 ? field1Bytes : (field1Type > 0 ? tDataTypes[field1Type].bytes : 0);
|
||||||
|
|
||||||
|
pField = (TAOS_FIELD*)taosArrayGet(expect.pFields, 1);
|
||||||
|
if (NULL != pField2Name) {
|
||||||
|
strcpy(pField->name, pField2Name);
|
||||||
|
pField->name[strlen(pField2Name)] = '\0';
|
||||||
|
} else {
|
||||||
|
memset(pField, 0, sizeof(TAOS_FIELD));
|
||||||
|
}
|
||||||
|
pField->type = 0;
|
||||||
|
pField->bytes = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
setCheckDdlFunc([&](const SQuery* pQuery, ParserStage stage) {
|
||||||
|
ASSERT_EQ(nodeType(pQuery->pRoot), QUERY_NODE_ALTER_TABLE_STMT);
|
||||||
|
SMAlterStbReq req = {0};
|
||||||
|
ASSERT_TRUE(TSDB_CODE_SUCCESS == tDeserializeSMAlterStbReq(pQuery->pCmdMsg->pMsg, pQuery->pCmdMsg->msgLen, &req));
|
||||||
|
ASSERT_EQ(std::string(req.name), std::string(expect.name));
|
||||||
|
ASSERT_EQ(req.alterType, expect.alterType);
|
||||||
|
ASSERT_EQ(req.numOfFields, expect.numOfFields);
|
||||||
|
if (expect.numOfFields > 0) {
|
||||||
|
TAOS_FIELD* pField = (TAOS_FIELD*)taosArrayGet(req.pFields, 0);
|
||||||
|
TAOS_FIELD* pExpectField = (TAOS_FIELD*)taosArrayGet(expect.pFields, 0);
|
||||||
|
ASSERT_EQ(std::string(pField->name), std::string(pExpectField->name));
|
||||||
|
ASSERT_EQ(pField->type, pExpectField->type);
|
||||||
|
ASSERT_EQ(pField->bytes, pExpectField->bytes);
|
||||||
|
}
|
||||||
|
if (expect.numOfFields > 1) {
|
||||||
|
TAOS_FIELD* pField = (TAOS_FIELD*)taosArrayGet(req.pFields, 1);
|
||||||
|
TAOS_FIELD* pExpectField = (TAOS_FIELD*)taosArrayGet(expect.pFields, 1);
|
||||||
|
ASSERT_EQ(std::string(pField->name), std::string(pExpectField->name));
|
||||||
|
ASSERT_EQ(pField->type, pExpectField->type);
|
||||||
|
ASSERT_EQ(pField->bytes, pExpectField->bytes);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
setAlterStbReqFunc("t1", TSDB_ALTER_TABLE_UPDATE_OPTIONS, 0, nullptr, 0, 0, nullptr, nullptr, 10);
|
||||||
|
run("ALTER TABLE t1 TTL 10");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("t1", TSDB_ALTER_TABLE_UPDATE_OPTIONS, 0, nullptr, 0, 0, nullptr, "test");
|
||||||
|
run("ALTER TABLE t1 COMMENT 'test'");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("t1", TSDB_ALTER_TABLE_ADD_COLUMN, 1, "cc1", TSDB_DATA_TYPE_BIGINT);
|
||||||
run("ALTER TABLE t1 ADD COLUMN cc1 BIGINT");
|
run("ALTER TABLE t1 ADD COLUMN cc1 BIGINT");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("t1", TSDB_ALTER_TABLE_DROP_COLUMN, 1, "c1");
|
||||||
run("ALTER TABLE t1 DROP COLUMN c1");
|
run("ALTER TABLE t1 DROP COLUMN c1");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("t1", TSDB_ALTER_TABLE_UPDATE_COLUMN_BYTES, 1, "c1", TSDB_DATA_TYPE_VARCHAR,
|
||||||
|
20 + VARSTR_HEADER_SIZE);
|
||||||
run("ALTER TABLE t1 MODIFY COLUMN c1 VARCHAR(20)");
|
run("ALTER TABLE t1 MODIFY COLUMN c1 VARCHAR(20)");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("t1", TSDB_ALTER_TABLE_UPDATE_COLUMN_NAME, 2, "c1", 0, 0, "cc1");
|
||||||
run("ALTER TABLE t1 RENAME COLUMN c1 cc1");
|
run("ALTER TABLE t1 RENAME COLUMN c1 cc1");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("st1", TSDB_ALTER_TABLE_ADD_TAG, 1, "tag11", TSDB_DATA_TYPE_BIGINT);
|
||||||
run("ALTER TABLE st1 ADD TAG tag11 BIGINT");
|
run("ALTER TABLE st1 ADD TAG tag11 BIGINT");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("st1", TSDB_ALTER_TABLE_DROP_TAG, 1, "tag1");
|
||||||
run("ALTER TABLE st1 DROP TAG tag1");
|
run("ALTER TABLE st1 DROP TAG tag1");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("st1", TSDB_ALTER_TABLE_UPDATE_TAG_BYTES, 1, "tag1", TSDB_DATA_TYPE_VARCHAR,
|
||||||
|
20 + VARSTR_HEADER_SIZE);
|
||||||
run("ALTER TABLE st1 MODIFY TAG tag1 VARCHAR(20)");
|
run("ALTER TABLE st1 MODIFY TAG tag1 VARCHAR(20)");
|
||||||
|
|
||||||
|
setAlterStbReqFunc("st1", TSDB_ALTER_TABLE_UPDATE_TAG_NAME, 2, "tag1", 0, 0, "tag11");
|
||||||
run("ALTER TABLE st1 RENAME TAG tag1 tag11");
|
run("ALTER TABLE st1 RENAME TAG tag1 tag11");
|
||||||
|
|
||||||
// run("ALTER TABLE st1s1 SET TAG tag1=10");
|
// run("ALTER TABLE st1s1 SET TAG tag1=10");
|
||||||
|
|
|
@ -19,7 +19,7 @@ using namespace std;
|
||||||
|
|
||||||
namespace ParserTest {
|
namespace ParserTest {
|
||||||
|
|
||||||
class ParserInitialCTest : public ParserTestBase {};
|
class ParserInitialCTest : public ParserDdlTest {};
|
||||||
|
|
||||||
// todo compact
|
// todo compact
|
||||||
|
|
||||||
|
@ -97,17 +97,143 @@ TEST_F(ParserInitialCTest, createSnode) {
|
||||||
TEST_F(ParserInitialCTest, createStable) {
|
TEST_F(ParserInitialCTest, createStable) {
|
||||||
useDb("root", "test");
|
useDb("root", "test");
|
||||||
|
|
||||||
|
SMCreateStbReq expect = {0};
|
||||||
|
|
||||||
|
auto setCreateStbReqFunc = [&](const char* pTbname, int8_t igExists = 0,
|
||||||
|
float xFilesFactor = TSDB_DEFAULT_ROLLUP_FILE_FACTOR,
|
||||||
|
int32_t delay = TSDB_DEFAULT_ROLLUP_DELAY, int32_t ttl = TSDB_DEFAULT_TABLE_TTL,
|
||||||
|
const char* pComment = nullptr) {
|
||||||
|
memset(&expect, 0, sizeof(SMCreateStbReq));
|
||||||
|
int32_t len = snprintf(expect.name, sizeof(expect.name), "0.test.%s", pTbname);
|
||||||
|
expect.name[len] = '\0';
|
||||||
|
expect.igExists = igExists;
|
||||||
|
expect.xFilesFactor = xFilesFactor;
|
||||||
|
expect.delay = delay;
|
||||||
|
expect.ttl = ttl;
|
||||||
|
if (nullptr != pComment) {
|
||||||
|
expect.comment = strdup(pComment);
|
||||||
|
expect.commentLen = strlen(pComment) + 1;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
auto addFieldToCreateStbReqFunc = [&](bool col, const char* pFieldName, uint8_t type, int32_t bytes = 0,
|
||||||
|
int8_t flags = SCHEMA_SMA_ON) {
|
||||||
|
SField field = {0};
|
||||||
|
strcpy(field.name, pFieldName);
|
||||||
|
field.type = type;
|
||||||
|
field.bytes = bytes > 0 ? bytes : tDataTypes[type].bytes;
|
||||||
|
field.flags = flags;
|
||||||
|
|
||||||
|
if (col) {
|
||||||
|
if (NULL == expect.pColumns) {
|
||||||
|
expect.pColumns = taosArrayInit(TARRAY_MIN_SIZE, sizeof(SField));
|
||||||
|
}
|
||||||
|
taosArrayPush(expect.pColumns, &field);
|
||||||
|
expect.numOfColumns += 1;
|
||||||
|
} else {
|
||||||
|
if (NULL == expect.pTags) {
|
||||||
|
expect.pTags = taosArrayInit(TARRAY_MIN_SIZE, sizeof(SField));
|
||||||
|
}
|
||||||
|
taosArrayPush(expect.pTags, &field);
|
||||||
|
expect.numOfTags += 1;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
setCheckDdlFunc([&](const SQuery* pQuery, ParserStage stage) {
|
||||||
|
ASSERT_EQ(nodeType(pQuery->pRoot), QUERY_NODE_CREATE_TABLE_STMT);
|
||||||
|
SMCreateStbReq req = {0};
|
||||||
|
ASSERT_TRUE(TSDB_CODE_SUCCESS == tDeserializeSMCreateStbReq(pQuery->pCmdMsg->pMsg, pQuery->pCmdMsg->msgLen, &req));
|
||||||
|
|
||||||
|
ASSERT_EQ(std::string(req.name), std::string(expect.name));
|
||||||
|
ASSERT_EQ(req.igExists, expect.igExists);
|
||||||
|
ASSERT_EQ(req.xFilesFactor, expect.xFilesFactor);
|
||||||
|
ASSERT_EQ(req.delay, expect.delay);
|
||||||
|
ASSERT_EQ(req.ttl, expect.ttl);
|
||||||
|
ASSERT_EQ(req.numOfColumns, expect.numOfColumns);
|
||||||
|
ASSERT_EQ(req.numOfTags, expect.numOfTags);
|
||||||
|
ASSERT_EQ(req.commentLen, expect.commentLen);
|
||||||
|
ASSERT_EQ(req.ast1Len, expect.ast1Len);
|
||||||
|
ASSERT_EQ(req.ast2Len, expect.ast2Len);
|
||||||
|
|
||||||
|
if (expect.numOfColumns > 0) {
|
||||||
|
ASSERT_EQ(taosArrayGetSize(req.pColumns), expect.numOfColumns);
|
||||||
|
ASSERT_EQ(taosArrayGetSize(req.pColumns), taosArrayGetSize(expect.pColumns));
|
||||||
|
for (int32_t i = 0; i < expect.numOfColumns; ++i) {
|
||||||
|
SField* pField = (SField*)taosArrayGet(req.pColumns, i);
|
||||||
|
SField* pExpectField = (SField*)taosArrayGet(expect.pColumns, i);
|
||||||
|
ASSERT_EQ(std::string(pField->name), std::string(pExpectField->name));
|
||||||
|
ASSERT_EQ(pField->type, pExpectField->type);
|
||||||
|
ASSERT_EQ(pField->bytes, pExpectField->bytes);
|
||||||
|
ASSERT_EQ(pField->flags, pExpectField->flags);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (expect.numOfTags > 0) {
|
||||||
|
ASSERT_EQ(taosArrayGetSize(req.pTags), expect.numOfTags);
|
||||||
|
ASSERT_EQ(taosArrayGetSize(req.pTags), taosArrayGetSize(expect.pTags));
|
||||||
|
for (int32_t i = 0; i < expect.numOfTags; ++i) {
|
||||||
|
SField* pField = (SField*)taosArrayGet(req.pTags, i);
|
||||||
|
SField* pExpectField = (SField*)taosArrayGet(expect.pTags, i);
|
||||||
|
ASSERT_EQ(std::string(pField->name), std::string(pExpectField->name));
|
||||||
|
ASSERT_EQ(pField->type, pExpectField->type);
|
||||||
|
ASSERT_EQ(pField->bytes, pExpectField->bytes);
|
||||||
|
ASSERT_EQ(pField->flags, pExpectField->flags);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (expect.commentLen > 0) {
|
||||||
|
ASSERT_EQ(std::string(req.comment), std::string(expect.comment));
|
||||||
|
}
|
||||||
|
if (expect.ast1Len > 0) {
|
||||||
|
ASSERT_EQ(std::string(req.pAst1), std::string(expect.pAst1));
|
||||||
|
}
|
||||||
|
if (expect.ast2Len > 0) {
|
||||||
|
ASSERT_EQ(std::string(req.pAst2), std::string(expect.pAst2));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
setCreateStbReqFunc("t1");
|
||||||
|
addFieldToCreateStbReqFunc(true, "ts", TSDB_DATA_TYPE_TIMESTAMP);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c1", TSDB_DATA_TYPE_INT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "id", TSDB_DATA_TYPE_INT);
|
||||||
run("create stable t1(ts timestamp, c1 int) TAGS(id int)");
|
run("create stable t1(ts timestamp, c1 int) TAGS(id int)");
|
||||||
|
|
||||||
|
setCreateStbReqFunc("t1", 1, 0.1, 2, 100, "test create table");
|
||||||
|
addFieldToCreateStbReqFunc(true, "ts", TSDB_DATA_TYPE_TIMESTAMP, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c1", TSDB_DATA_TYPE_INT);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c2", TSDB_DATA_TYPE_UINT);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c3", TSDB_DATA_TYPE_BIGINT);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c4", TSDB_DATA_TYPE_UBIGINT, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c5", TSDB_DATA_TYPE_FLOAT, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c6", TSDB_DATA_TYPE_DOUBLE, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c7", TSDB_DATA_TYPE_BINARY, 20 + VARSTR_HEADER_SIZE, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c8", TSDB_DATA_TYPE_SMALLINT, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c9", TSDB_DATA_TYPE_USMALLINT, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c10", TSDB_DATA_TYPE_TINYINT, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c11", TSDB_DATA_TYPE_UTINYINT, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c12", TSDB_DATA_TYPE_BOOL, 0, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c13", TSDB_DATA_TYPE_NCHAR, 30 * TSDB_NCHAR_SIZE + VARSTR_HEADER_SIZE, 0);
|
||||||
|
addFieldToCreateStbReqFunc(true, "c14", TSDB_DATA_TYPE_VARCHAR, 50 + VARSTR_HEADER_SIZE, 0);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a1", TSDB_DATA_TYPE_TIMESTAMP);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a2", TSDB_DATA_TYPE_INT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a3", TSDB_DATA_TYPE_UINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a4", TSDB_DATA_TYPE_BIGINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a5", TSDB_DATA_TYPE_UBIGINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a6", TSDB_DATA_TYPE_FLOAT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a7", TSDB_DATA_TYPE_DOUBLE);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a8", TSDB_DATA_TYPE_BINARY, 20 + VARSTR_HEADER_SIZE);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a9", TSDB_DATA_TYPE_SMALLINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a10", TSDB_DATA_TYPE_USMALLINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a11", TSDB_DATA_TYPE_TINYINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a12", TSDB_DATA_TYPE_UTINYINT);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a13", TSDB_DATA_TYPE_BOOL);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a14", TSDB_DATA_TYPE_NCHAR, 30 * TSDB_NCHAR_SIZE + VARSTR_HEADER_SIZE);
|
||||||
|
addFieldToCreateStbReqFunc(false, "a15", TSDB_DATA_TYPE_VARCHAR, 50 + VARSTR_HEADER_SIZE);
|
||||||
run("create stable if not exists test.t1("
|
run("create stable if not exists test.t1("
|
||||||
"ts TIMESTAMP, c1 INT, c2 INT UNSIGNED, c3 BIGINT, c4 BIGINT UNSIGNED, c5 FLOAT, c6 DOUBLE, c7 BINARY(20), c8 "
|
"ts TIMESTAMP, c1 INT, c2 INT UNSIGNED, c3 BIGINT, c4 BIGINT UNSIGNED, c5 FLOAT, c6 DOUBLE, c7 BINARY(20), "
|
||||||
"SMALLINT, "
|
"c8 SMALLINT, c9 SMALLINT UNSIGNED COMMENT 'test column comment', c10 TINYINT, c11 TINYINT UNSIGNED, c12 BOOL, "
|
||||||
"c9 SMALLINT UNSIGNED COMMENT 'test column comment', c10 TINYINT, c11 TINYINT UNSIGNED, c12 BOOL, c13 NCHAR(30), "
|
"c13 NCHAR(30), c14 VARCHAR(50)) "
|
||||||
"c15 VARCHAR(50)) "
|
"TAGS (a1 TIMESTAMP, a2 INT, a3 INT UNSIGNED, a4 BIGINT, a5 BIGINT UNSIGNED, a6 FLOAT, a7 DOUBLE, "
|
||||||
"TAGS (tsa TIMESTAMP, a1 INT, a2 INT UNSIGNED, a3 BIGINT, a4 BIGINT UNSIGNED, a5 FLOAT, a6 DOUBLE, a7 "
|
"a8 BINARY(20), a9 SMALLINT, a10 SMALLINT UNSIGNED COMMENT 'test column comment', a11 TINYINT, "
|
||||||
"BINARY(20), a8 SMALLINT, "
|
"a12 TINYINT UNSIGNED, a13 BOOL, a14 NCHAR(30), a15 VARCHAR(50)) "
|
||||||
"a9 SMALLINT UNSIGNED COMMENT 'test column comment', a10 TINYINT, a11 TINYINT UNSIGNED, a12 BOOL, a13 NCHAR(30), "
|
|
||||||
"a15 VARCHAR(50)) "
|
|
||||||
"TTL 100 COMMENT 'test create table' SMA(c1, c2, c3) ROLLUP (min) FILE_FACTOR 0.1 DELAY 2");
|
"TTL 100 COMMENT 'test create table' SMA(c1, c2, c3) ROLLUP (min) FILE_FACTOR 0.1 DELAY 2");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -49,6 +49,8 @@ struct TerminateFlag : public exception {
|
||||||
|
|
||||||
class ParserTestBaseImpl {
|
class ParserTestBaseImpl {
|
||||||
public:
|
public:
|
||||||
|
ParserTestBaseImpl(ParserTestBase* pBase) : pBase_(pBase) {}
|
||||||
|
|
||||||
void useDb(const string& acctId, const string& db) {
|
void useDb(const string& acctId, const string& db) {
|
||||||
caseEnv_.acctId_ = acctId;
|
caseEnv_.acctId_ = acctId;
|
||||||
caseEnv_.db_ = db;
|
caseEnv_.db_ = db;
|
||||||
|
@ -156,11 +158,13 @@ class ParserTestBaseImpl {
|
||||||
|
|
||||||
void doParse(SParseContext* pCxt, SQuery** pQuery) {
|
void doParse(SParseContext* pCxt, SQuery** pQuery) {
|
||||||
DO_WITH_THROW(parse, pCxt, pQuery);
|
DO_WITH_THROW(parse, pCxt, pQuery);
|
||||||
|
ASSERT_NE(*pQuery, nullptr);
|
||||||
res_.parsedAst_ = toString((*pQuery)->pRoot);
|
res_.parsedAst_ = toString((*pQuery)->pRoot);
|
||||||
}
|
}
|
||||||
|
|
||||||
void doTranslate(SParseContext* pCxt, SQuery* pQuery) {
|
void doTranslate(SParseContext* pCxt, SQuery* pQuery) {
|
||||||
DO_WITH_THROW(translate, pCxt, pQuery);
|
DO_WITH_THROW(translate, pCxt, pQuery);
|
||||||
|
checkQuery(pQuery, PARSER_STAGE_TRANSLATE);
|
||||||
res_.translatedAst_ = toString(pQuery->pRoot);
|
res_.translatedAst_ = toString(pQuery->pRoot);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -178,12 +182,15 @@ class ParserTestBaseImpl {
|
||||||
return str;
|
return str;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void checkQuery(const SQuery* pQuery, ParserStage stage) { pBase_->checkDdl(pQuery, stage); }
|
||||||
|
|
||||||
caseEnv caseEnv_;
|
caseEnv caseEnv_;
|
||||||
stmtEnv stmtEnv_;
|
stmtEnv stmtEnv_;
|
||||||
stmtRes res_;
|
stmtRes res_;
|
||||||
|
ParserTestBase* pBase_;
|
||||||
};
|
};
|
||||||
|
|
||||||
ParserTestBase::ParserTestBase() : impl_(new ParserTestBaseImpl()) {}
|
ParserTestBase::ParserTestBase() : impl_(new ParserTestBaseImpl(this)) {}
|
||||||
|
|
||||||
ParserTestBase::~ParserTestBase() {}
|
ParserTestBase::~ParserTestBase() {}
|
||||||
|
|
||||||
|
@ -193,4 +200,6 @@ void ParserTestBase::run(const std::string& sql, int32_t expect, ParserStage che
|
||||||
return impl_->run(sql, expect, checkStage);
|
return impl_->run(sql, expect, checkStage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ParserTestBase::checkDdl(const SQuery* pQuery, ParserStage stage) { return; }
|
||||||
|
|
||||||
} // namespace ParserTest
|
} // namespace ParserTest
|
||||||
|
|
|
@ -18,6 +18,9 @@
|
||||||
|
|
||||||
#include <gtest/gtest.h>
|
#include <gtest/gtest.h>
|
||||||
|
|
||||||
|
#define ALLOW_FORBID_FUNC
|
||||||
|
|
||||||
|
#include "querynodes.h"
|
||||||
#include "taoserror.h"
|
#include "taoserror.h"
|
||||||
|
|
||||||
namespace ParserTest {
|
namespace ParserTest {
|
||||||
|
@ -34,10 +37,32 @@ class ParserTestBase : public testing::Test {
|
||||||
void useDb(const std::string& acctId, const std::string& db);
|
void useDb(const std::string& acctId, const std::string& db);
|
||||||
void run(const std::string& sql, int32_t expect = TSDB_CODE_SUCCESS, ParserStage checkStage = PARSER_STAGE_ALL);
|
void run(const std::string& sql, int32_t expect = TSDB_CODE_SUCCESS, ParserStage checkStage = PARSER_STAGE_ALL);
|
||||||
|
|
||||||
|
virtual void checkDdl(const SQuery* pQuery, ParserStage stage);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::unique_ptr<ParserTestBaseImpl> impl_;
|
std::unique_ptr<ParserTestBaseImpl> impl_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class ParserDdlTest : public ParserTestBase {
|
||||||
|
public:
|
||||||
|
void setCheckDdlFunc(const std::function<void(const SQuery*, ParserStage)>& func) { checkDdl_ = func; }
|
||||||
|
|
||||||
|
virtual void checkDdl(const SQuery* pQuery, ParserStage stage) {
|
||||||
|
ASSERT_NE(pQuery, nullptr);
|
||||||
|
ASSERT_EQ(pQuery->haveResultSet, false);
|
||||||
|
ASSERT_NE(pQuery->pRoot, nullptr);
|
||||||
|
ASSERT_EQ(pQuery->numOfResCols, 0);
|
||||||
|
ASSERT_EQ(pQuery->pResSchema, nullptr);
|
||||||
|
ASSERT_EQ(pQuery->precision, 0);
|
||||||
|
if (nullptr != checkDdl_) {
|
||||||
|
checkDdl_(pQuery, stage);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::function<void(const SQuery*, ParserStage)> checkDdl_;
|
||||||
|
};
|
||||||
|
|
||||||
extern bool g_isDump;
|
extern bool g_isDump;
|
||||||
|
|
||||||
} // namespace ParserTest
|
} // namespace ParserTest
|
||||||
|
|
Loading…
Reference in New Issue