Merge branch '3.0' of github.com:taosdata/TDengine into szhou/tms-wide-column
This commit is contained in:
commit
81b95f2135
|
@ -1,6 +1,7 @@
|
||||||
# curl
|
# curl
|
||||||
ExternalProject_Add(curl2
|
ExternalProject_Add(curl2
|
||||||
URL https://curl.se/download/curl-8.2.1.tar.gz
|
URL https://github.com/curl/curl/releases/download/curl-8_2_1/curl-8.2.1.tar.gz
|
||||||
|
#URL https://curl.se/download/curl-8.2.1.tar.gz
|
||||||
URL_HASH MD5=b25588a43556068be05e1624e0e74d41
|
URL_HASH MD5=b25588a43556068be05e1624e0e74d41
|
||||||
DOWNLOAD_NO_PROGRESS 1
|
DOWNLOAD_NO_PROGRESS 1
|
||||||
DOWNLOAD_DIR "${TD_CONTRIB_DIR}/deps-download"
|
DOWNLOAD_DIR "${TD_CONTRIB_DIR}/deps-download"
|
||||||
|
|
|
@ -105,7 +105,7 @@ int32_t taosTm2Ts(struct STm* tm, int64_t* ts, int32_t precision);
|
||||||
/// formats array; If not NULL, [formats] will be used instead of [format] to skip parse formats again.
|
/// formats array; If not NULL, [formats] will be used instead of [format] to skip parse formats again.
|
||||||
/// @param out output buffer, should be initialized by memset
|
/// @param out output buffer, should be initialized by memset
|
||||||
/// @notes remember to free the generated formats
|
/// @notes remember to free the generated formats
|
||||||
void taosTs2Char(const char* format, SArray** formats, int64_t ts, int32_t precision, char* out, int32_t outLen);
|
int32_t taosTs2Char(const char* format, SArray** formats, int64_t ts, int32_t precision, char* out, int32_t outLen);
|
||||||
/// @brief convert a formatted timestamp string to a timestamp
|
/// @brief convert a formatted timestamp string to a timestamp
|
||||||
/// @param format must null terminated
|
/// @param format must null terminated
|
||||||
/// @param [in, out] formats, see taosTs2Char
|
/// @param [in, out] formats, see taosTs2Char
|
||||||
|
|
|
@ -30,7 +30,8 @@ int32_t tqStreamTaskProcessCheckpointReadyMsg(SStreamMeta* pMeta, SRpcMsg* pMsg)
|
||||||
int32_t tqStreamTaskProcessDeployReq(SStreamMeta* pMeta, int64_t sversion, char* msg, int32_t msgLen, bool isLeader, bool restored);
|
int32_t tqStreamTaskProcessDeployReq(SStreamMeta* pMeta, int64_t sversion, char* msg, int32_t msgLen, bool isLeader, bool restored);
|
||||||
int32_t tqStreamTaskProcessDropReq(SStreamMeta* pMeta, char* msg, int32_t msgLen);
|
int32_t tqStreamTaskProcessDropReq(SStreamMeta* pMeta, char* msg, int32_t msgLen);
|
||||||
int32_t tqStreamTaskProcessRunReq(SStreamMeta* pMeta, SRpcMsg* pMsg, bool isLeader);
|
int32_t tqStreamTaskProcessRunReq(SStreamMeta* pMeta, SRpcMsg* pMsg, bool isLeader);
|
||||||
int32_t startStreamTasks(SStreamMeta* pMeta);
|
int32_t tqStreamTaskResetStatus(SStreamMeta* pMeta);
|
||||||
int32_t resetStreamTaskStatus(SStreamMeta* pMeta);
|
int32_t tqStartTaskCompleteCallback(SStreamMeta* pMeta);
|
||||||
|
int32_t tqStreamTaskProcessTaskResetReq(SStreamMeta* pMeta, SRpcMsg* pMsg);
|
||||||
|
|
||||||
#endif // TDENGINE_TQ_COMMON_H
|
#endif // TDENGINE_TQ_COMMON_H
|
||||||
|
|
|
@ -237,9 +237,9 @@ struct SScalarParam {
|
||||||
int32_t numOfQualified; // number of qualified elements in the final results
|
int32_t numOfQualified; // number of qualified elements in the final results
|
||||||
};
|
};
|
||||||
|
|
||||||
void cleanupResultRowEntry(struct SResultRowEntryInfo *pCell);
|
#define cleanupResultRowEntry(p) p->initialized = false
|
||||||
bool isRowEntryCompleted(struct SResultRowEntryInfo *pEntry);
|
#define isRowEntryCompleted(p) (p->complete)
|
||||||
bool isRowEntryInitialized(struct SResultRowEntryInfo *pEntry);
|
#define isRowEntryInitialized(p) (p->initialized)
|
||||||
|
|
||||||
typedef struct SPoint {
|
typedef struct SPoint {
|
||||||
int64_t key;
|
int64_t key;
|
||||||
|
|
|
@ -53,6 +53,7 @@ extern "C" {
|
||||||
#define STREAM_EXEC_EXTRACT_DATA_IN_WAL_ID (-1)
|
#define STREAM_EXEC_EXTRACT_DATA_IN_WAL_ID (-1)
|
||||||
#define STREAM_EXEC_START_ALL_TASKS_ID (-2)
|
#define STREAM_EXEC_START_ALL_TASKS_ID (-2)
|
||||||
#define STREAM_EXEC_RESTART_ALL_TASKS_ID (-3)
|
#define STREAM_EXEC_RESTART_ALL_TASKS_ID (-3)
|
||||||
|
#define STREAM_EXEC_STOP_ALL_TASKS_ID (-4)
|
||||||
|
|
||||||
typedef struct SStreamTask SStreamTask;
|
typedef struct SStreamTask SStreamTask;
|
||||||
typedef struct SStreamQueue SStreamQueue;
|
typedef struct SStreamQueue SStreamQueue;
|
||||||
|
@ -314,6 +315,7 @@ typedef struct SCheckpointInfo {
|
||||||
int32_t checkpointNotReadyTasks;
|
int32_t checkpointNotReadyTasks;
|
||||||
bool dispatchCheckpointTrigger;
|
bool dispatchCheckpointTrigger;
|
||||||
int64_t msgVer;
|
int64_t msgVer;
|
||||||
|
int32_t transId;
|
||||||
} SCheckpointInfo;
|
} SCheckpointInfo;
|
||||||
|
|
||||||
typedef struct SStreamStatus {
|
typedef struct SStreamStatus {
|
||||||
|
@ -324,6 +326,7 @@ typedef struct SStreamStatus {
|
||||||
int8_t keepTaskStatus;
|
int8_t keepTaskStatus;
|
||||||
bool appendTranstateBlock; // has append the transfer state data block already, todo: remove it
|
bool appendTranstateBlock; // has append the transfer state data block already, todo: remove it
|
||||||
int32_t timerActive; // timer is active
|
int32_t timerActive; // timer is active
|
||||||
|
int8_t allowedAddInTimer; // allowed to add into timer
|
||||||
int32_t inScanHistorySentinel;
|
int32_t inScanHistorySentinel;
|
||||||
} SStreamStatus;
|
} SStreamStatus;
|
||||||
|
|
||||||
|
@ -460,14 +463,18 @@ struct SStreamTask {
|
||||||
char reserve[256];
|
char reserve[256];
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef int32_t (*startComplete_fn_t)(struct SStreamMeta*);
|
||||||
|
|
||||||
typedef struct STaskStartInfo {
|
typedef struct STaskStartInfo {
|
||||||
int64_t startTs;
|
int64_t startTs;
|
||||||
int64_t readyTs;
|
int64_t readyTs;
|
||||||
int32_t tasksWillRestart;
|
int32_t tasksWillRestart;
|
||||||
int32_t taskStarting; // restart flag, sentinel to guard the restart procedure.
|
int32_t taskStarting; // restart flag, sentinel to guard the restart procedure.
|
||||||
SHashObj* pReadyTaskSet; // tasks that are all ready for running stream processing
|
SHashObj* pReadyTaskSet; // tasks that are all ready for running stream processing
|
||||||
SHashObj* pFailedTaskSet; // tasks that are done the check downstream process, may be successful or failed
|
SHashObj* pFailedTaskSet; // tasks that are done the check downstream process, may be successful or failed
|
||||||
int64_t elapsedTime;
|
int64_t elapsedTime;
|
||||||
|
int32_t restartCount; // restart task counter
|
||||||
|
startComplete_fn_t completeFn; // complete callback function
|
||||||
} STaskStartInfo;
|
} STaskStartInfo;
|
||||||
|
|
||||||
typedef struct STaskUpdateInfo {
|
typedef struct STaskUpdateInfo {
|
||||||
|
@ -489,8 +496,9 @@ typedef struct SStreamMeta {
|
||||||
int32_t vgId;
|
int32_t vgId;
|
||||||
int64_t stage;
|
int64_t stage;
|
||||||
int32_t role;
|
int32_t role;
|
||||||
|
bool sendMsgBeforeClosing; // send hb to mnode before close all tasks when switch to follower.
|
||||||
STaskStartInfo startInfo;
|
STaskStartInfo startInfo;
|
||||||
SRWLatch lock;
|
TdThreadRwlock lock;
|
||||||
int32_t walScanCounter;
|
int32_t walScanCounter;
|
||||||
void* streamBackend;
|
void* streamBackend;
|
||||||
int64_t streamBackendRid;
|
int64_t streamBackendRid;
|
||||||
|
@ -629,6 +637,7 @@ typedef struct {
|
||||||
int32_t nodeId;
|
int32_t nodeId;
|
||||||
SEpSet mgmtEps;
|
SEpSet mgmtEps;
|
||||||
int32_t mnodeId;
|
int32_t mnodeId;
|
||||||
|
int32_t transId;
|
||||||
int64_t expireTime;
|
int64_t expireTime;
|
||||||
} SStreamCheckpointSourceReq;
|
} SStreamCheckpointSourceReq;
|
||||||
|
|
||||||
|
@ -671,8 +680,8 @@ typedef struct STaskStatusEntry {
|
||||||
int64_t verStart; // start version in WAL, only valid for source task
|
int64_t verStart; // start version in WAL, only valid for source task
|
||||||
int64_t verEnd; // end version in WAL, only valid for source task
|
int64_t verEnd; // end version in WAL, only valid for source task
|
||||||
int64_t processedVer; // only valid for source task
|
int64_t processedVer; // only valid for source task
|
||||||
int32_t relatedHTask; // has related fill-history task
|
|
||||||
int64_t activeCheckpointId; // current active checkpoint id
|
int64_t activeCheckpointId; // current active checkpoint id
|
||||||
|
int32_t chkpointTransId; // checkpoint trans id
|
||||||
bool checkpointFailed; // denote if the checkpoint is failed or not
|
bool checkpointFailed; // denote if the checkpoint is failed or not
|
||||||
bool inputQChanging; // inputQ is changing or not
|
bool inputQChanging; // inputQ is changing or not
|
||||||
int64_t inputQUnchangeCounter;
|
int64_t inputQUnchangeCounter;
|
||||||
|
@ -811,6 +820,7 @@ int32_t streamTaskReleaseState(SStreamTask* pTask);
|
||||||
int32_t streamTaskReloadState(SStreamTask* pTask);
|
int32_t streamTaskReloadState(SStreamTask* pTask);
|
||||||
void streamTaskCloseUpstreamInput(SStreamTask* pTask, int32_t taskId);
|
void streamTaskCloseUpstreamInput(SStreamTask* pTask, int32_t taskId);
|
||||||
void streamTaskOpenAllUpstreamInput(SStreamTask* pTask);
|
void streamTaskOpenAllUpstreamInput(SStreamTask* pTask);
|
||||||
|
int32_t streamTaskSetDb(SStreamMeta* pMeta, void* pTask, char* key);
|
||||||
|
|
||||||
void streamTaskStatusInit(STaskStatusEntry* pEntry, const SStreamTask* pTask);
|
void streamTaskStatusInit(STaskStatusEntry* pEntry, const SStreamTask* pTask);
|
||||||
void streamTaskStatusCopy(STaskStatusEntry* pDst, const STaskStatusEntry* pSrc);
|
void streamTaskStatusCopy(STaskStatusEntry* pDst, const STaskStatusEntry* pSrc);
|
||||||
|
@ -828,22 +838,21 @@ int32_t streamProcessScanHistoryFinishRsp(SStreamTask* pTask);
|
||||||
// stream task meta
|
// stream task meta
|
||||||
void streamMetaInit();
|
void streamMetaInit();
|
||||||
void streamMetaCleanup();
|
void streamMetaCleanup();
|
||||||
SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandFunc, int32_t vgId, int64_t stage);
|
SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandFunc, int32_t vgId, int64_t stage, startComplete_fn_t fn);
|
||||||
void streamMetaClose(SStreamMeta* streamMeta);
|
void streamMetaClose(SStreamMeta* streamMeta);
|
||||||
int32_t streamMetaSaveTask(SStreamMeta* pMeta, SStreamTask* pTask); // save to stream meta store
|
int32_t streamMetaSaveTask(SStreamMeta* pMeta, SStreamTask* pTask); // save to stream meta store
|
||||||
int32_t streamMetaRemoveTask(SStreamMeta* pMeta, STaskId* pKey);
|
int32_t streamMetaRemoveTask(SStreamMeta* pMeta, STaskId* pKey);
|
||||||
int32_t streamMetaRegisterTask(SStreamMeta* pMeta, int64_t ver, SStreamTask* pTask, bool* pAdded);
|
int32_t streamMetaRegisterTask(SStreamMeta* pMeta, int64_t ver, SStreamTask* pTask, bool* pAdded);
|
||||||
int32_t streamMetaUnregisterTask(SStreamMeta* pMeta, int64_t streamId, int32_t taskId);
|
int32_t streamMetaUnregisterTask(SStreamMeta* pMeta, int64_t streamId, int32_t taskId);
|
||||||
int32_t streamMetaGetNumOfTasks(SStreamMeta* pMeta);
|
int32_t streamMetaGetNumOfTasks(SStreamMeta* pMeta);
|
||||||
|
SStreamTask* streamMetaAcquireTaskNoLock(SStreamMeta* pMeta, int64_t streamId, int32_t taskId);
|
||||||
SStreamTask* streamMetaAcquireTask(SStreamMeta* pMeta, int64_t streamId, int32_t taskId);
|
SStreamTask* streamMetaAcquireTask(SStreamMeta* pMeta, int64_t streamId, int32_t taskId);
|
||||||
void streamMetaReleaseTask(SStreamMeta* pMeta, SStreamTask* pTask);
|
void streamMetaReleaseTask(SStreamMeta* pMeta, SStreamTask* pTask);
|
||||||
void streamMetaClear(SStreamMeta* pMeta);
|
void streamMetaClear(SStreamMeta* pMeta);
|
||||||
void streamMetaInitBackend(SStreamMeta* pMeta);
|
void streamMetaInitBackend(SStreamMeta* pMeta);
|
||||||
int32_t streamMetaCommit(SStreamMeta* pMeta);
|
int32_t streamMetaCommit(SStreamMeta* pMeta);
|
||||||
int32_t streamMetaLoadAllTasks(SStreamMeta* pMeta);
|
|
||||||
int64_t streamMetaGetLatestCheckpointId(SStreamMeta* pMeta);
|
int64_t streamMetaGetLatestCheckpointId(SStreamMeta* pMeta);
|
||||||
void streamMetaNotifyClose(SStreamMeta* pMeta);
|
void streamMetaNotifyClose(SStreamMeta* pMeta);
|
||||||
int32_t streamTaskSetDb(SStreamMeta* pMeta, void* pTask, char* key);
|
|
||||||
void streamMetaStartHb(SStreamMeta* pMeta);
|
void streamMetaStartHb(SStreamMeta* pMeta);
|
||||||
bool streamMetaTaskInTimer(SStreamMeta* pMeta);
|
bool streamMetaTaskInTimer(SStreamMeta* pMeta);
|
||||||
int32_t streamMetaUpdateTaskDownstreamStatus(SStreamMeta* pMeta, int64_t streamId, int32_t taskId, int64_t startTs,
|
int32_t streamMetaUpdateTaskDownstreamStatus(SStreamMeta* pMeta, int64_t streamId, int32_t taskId, int64_t startTs,
|
||||||
|
@ -853,6 +862,11 @@ void streamMetaRUnLock(SStreamMeta* pMeta);
|
||||||
void streamMetaWLock(SStreamMeta* pMeta);
|
void streamMetaWLock(SStreamMeta* pMeta);
|
||||||
void streamMetaWUnLock(SStreamMeta* pMeta);
|
void streamMetaWUnLock(SStreamMeta* pMeta);
|
||||||
void streamMetaResetStartInfo(STaskStartInfo* pMeta);
|
void streamMetaResetStartInfo(STaskStartInfo* pMeta);
|
||||||
|
SArray* streamMetaSendMsgBeforeCloseTasks(SStreamMeta* pMeta);
|
||||||
|
void streamMetaUpdateStageRole(SStreamMeta* pMeta, int64_t stage, bool isLeader);
|
||||||
|
int32_t streamMetaLoadAllTasks(SStreamMeta* pMeta);
|
||||||
|
int32_t streamMetaStartAllTasks(SStreamMeta* pMeta);
|
||||||
|
int32_t streamMetaStopAllTasks(SStreamMeta* pMeta);
|
||||||
|
|
||||||
// checkpoint
|
// checkpoint
|
||||||
int32_t streamProcessCheckpointSourceReq(SStreamTask* pTask, SStreamCheckpointSourceReq* pReq);
|
int32_t streamProcessCheckpointSourceReq(SStreamTask* pTask, SStreamCheckpointSourceReq* pReq);
|
||||||
|
|
|
@ -355,6 +355,7 @@ int32_t* taosGetErrno();
|
||||||
#define TSDB_CODE_MND_TRANS_NETWORK_UNAVAILL TAOS_DEF_ERROR_CODE(0, 0x03D5)
|
#define TSDB_CODE_MND_TRANS_NETWORK_UNAVAILL TAOS_DEF_ERROR_CODE(0, 0x03D5)
|
||||||
#define TSDB_CODE_MND_LAST_TRANS_NOT_FINISHED TAOS_DEF_ERROR_CODE(0, 0x03D6) //internal
|
#define TSDB_CODE_MND_LAST_TRANS_NOT_FINISHED TAOS_DEF_ERROR_CODE(0, 0x03D6) //internal
|
||||||
#define TSDB_CODE_MND_TRANS_SYNC_TIMEOUT TAOS_DEF_ERROR_CODE(0, 0x03D7)
|
#define TSDB_CODE_MND_TRANS_SYNC_TIMEOUT TAOS_DEF_ERROR_CODE(0, 0x03D7)
|
||||||
|
#define TSDB_CODE_MND_TRANS_CTX_SWITCH TAOS_DEF_ERROR_CODE(0, 0x03D8)
|
||||||
#define TSDB_CODE_MND_TRANS_UNKNOW_ERROR TAOS_DEF_ERROR_CODE(0, 0x03DF)
|
#define TSDB_CODE_MND_TRANS_UNKNOW_ERROR TAOS_DEF_ERROR_CODE(0, 0x03DF)
|
||||||
|
|
||||||
// mnode-mq
|
// mnode-mq
|
||||||
|
@ -760,6 +761,7 @@ int32_t* taosGetErrno();
|
||||||
#define TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_FORMAT_ERR TAOS_DEF_ERROR_CODE(0, 0x2806)
|
#define TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_FORMAT_ERR TAOS_DEF_ERROR_CODE(0, 0x2806)
|
||||||
#define TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_TS_ERR TAOS_DEF_ERROR_CODE(0, 0x2807)
|
#define TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_TS_ERR TAOS_DEF_ERROR_CODE(0, 0x2807)
|
||||||
#define TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_NOT_SUPPORTED TAOS_DEF_ERROR_CODE(0, 0x2808)
|
#define TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_NOT_SUPPORTED TAOS_DEF_ERROR_CODE(0, 0x2808)
|
||||||
|
#define TSDB_CODE_FUNC_TO_CHAR_NOT_SUPPORTED TAOS_DEF_ERROR_CODE(0, 0x2809)
|
||||||
|
|
||||||
//udf
|
//udf
|
||||||
#define TSDB_CODE_UDF_STOPPING TAOS_DEF_ERROR_CODE(0, 0x2901)
|
#define TSDB_CODE_UDF_STOPPING TAOS_DEF_ERROR_CODE(0, 0x2901)
|
||||||
|
|
|
@ -1432,6 +1432,13 @@ static int32_t taosCfgSetOption(OptionNameAndVar *pOptions, int32_t optionSize,
|
||||||
static int32_t taosCfgDynamicOptionsForServer(SConfig *pCfg, char *name) {
|
static int32_t taosCfgDynamicOptionsForServer(SConfig *pCfg, char *name) {
|
||||||
terrno = TSDB_CODE_SUCCESS;
|
terrno = TSDB_CODE_SUCCESS;
|
||||||
|
|
||||||
|
if (strcasecmp(name, "resetlog") == 0) {
|
||||||
|
// trigger, no item in cfg
|
||||||
|
taosResetLog();
|
||||||
|
cfgDumpCfg(tsCfg, 0, false);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
SConfigItem *pItem = cfgGetItem(pCfg, name);
|
SConfigItem *pItem = cfgGetItem(pCfg, name);
|
||||||
if (!pItem || (pItem->dynScope & CFG_DYN_SERVER) == 0) {
|
if (!pItem || (pItem->dynScope & CFG_DYN_SERVER) == 0) {
|
||||||
uError("failed to config:%s, not support", name);
|
uError("failed to config:%s, not support", name);
|
||||||
|
@ -1445,12 +1452,6 @@ static int32_t taosCfgDynamicOptionsForServer(SConfig *pCfg, char *name) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (strcasecmp(name, "resetlog") == 0) {
|
|
||||||
taosResetLog();
|
|
||||||
cfgDumpCfg(tsCfg, 0, false);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
{ // 'bool/int32_t/int64_t/float/double' variables with general modification function
|
{ // 'bool/int32_t/int64_t/float/double' variables with general modification function
|
||||||
static OptionNameAndVar debugOptions[] = {
|
static OptionNameAndVar debugOptions[] = {
|
||||||
{"dDebugFlag", &dDebugFlag}, {"vDebugFlag", &vDebugFlag}, {"mDebugFlag", &mDebugFlag},
|
{"dDebugFlag", &dDebugFlag}, {"vDebugFlag", &vDebugFlag}, {"mDebugFlag", &mDebugFlag},
|
||||||
|
|
|
@ -143,6 +143,7 @@ STSRow *tGetSubmitBlkNext(SSubmitBlkIter *pIter) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef BUILD_NO_CALL
|
||||||
int32_t tPrintFixedSchemaSubmitReq(SSubmitReq *pReq, STSchema *pTschema) {
|
int32_t tPrintFixedSchemaSubmitReq(SSubmitReq *pReq, STSchema *pTschema) {
|
||||||
SSubmitMsgIter msgIter = {0};
|
SSubmitMsgIter msgIter = {0};
|
||||||
if (tInitSubmitMsgIter(pReq, &msgIter) < 0) return -1;
|
if (tInitSubmitMsgIter(pReq, &msgIter) < 0) return -1;
|
||||||
|
@ -161,6 +162,7 @@ int32_t tPrintFixedSchemaSubmitReq(SSubmitReq *pReq, STSchema *pTschema) {
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
int32_t tEncodeSEpSet(SEncoder *pEncoder, const SEpSet *pEp) {
|
int32_t tEncodeSEpSet(SEncoder *pEncoder, const SEpSet *pEp) {
|
||||||
if (tEncodeI8(pEncoder, pEp->inUse) < 0) return -1;
|
if (tEncodeI8(pEncoder, pEp->inUse) < 0) return -1;
|
||||||
|
|
|
@ -17,6 +17,221 @@
|
||||||
#include "trow.h"
|
#include "trow.h"
|
||||||
#include "tlog.h"
|
#include "tlog.h"
|
||||||
|
|
||||||
|
static bool tdSTSRowIterGetTpVal(STSRowIter *pIter, col_type_t colType, int32_t offset, SCellVal *pVal);
|
||||||
|
static bool tdSTSRowIterGetKvVal(STSRowIter *pIter, col_id_t colId, col_id_t *nIdx, SCellVal *pVal);
|
||||||
|
|
||||||
|
void tdSTSRowIterInit(STSRowIter *pIter, STSchema *pSchema) {
|
||||||
|
pIter->pSchema = pSchema;
|
||||||
|
pIter->maxColId = pSchema->columns[pSchema->numOfCols - 1].colId;
|
||||||
|
}
|
||||||
|
|
||||||
|
void *tdGetBitmapAddr(STSRow *pRow, uint8_t rowType, uint32_t flen, col_id_t nKvCols) {
|
||||||
|
#ifdef TD_SUPPORT_BITMAP
|
||||||
|
switch (rowType) {
|
||||||
|
case TD_ROW_TP:
|
||||||
|
return tdGetBitmapAddrTp(pRow, flen);
|
||||||
|
case TD_ROW_KV:
|
||||||
|
return tdGetBitmapAddrKv(pRow, nKvCols);
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void tdSTSRowIterReset(STSRowIter *pIter, STSRow *pRow) {
|
||||||
|
pIter->pRow = pRow;
|
||||||
|
pIter->pBitmap = tdGetBitmapAddr(pRow, pRow->type, pIter->pSchema->flen, tdRowGetNCols(pRow));
|
||||||
|
pIter->offset = 0;
|
||||||
|
pIter->colIdx = 0; // PRIMARYKEY_TIMESTAMP_COL_ID;
|
||||||
|
pIter->kvIdx = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool tdSTSRowIterFetch(STSRowIter *pIter, col_id_t colId, col_type_t colType, SCellVal *pVal) {
|
||||||
|
if (colId == PRIMARYKEY_TIMESTAMP_COL_ID) {
|
||||||
|
pVal->val = &pIter->pRow->ts;
|
||||||
|
pVal->valType = TD_VTYPE_NORM;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (TD_IS_TP_ROW(pIter->pRow)) {
|
||||||
|
STColumn *pCol = NULL;
|
||||||
|
STSchema *pSchema = pIter->pSchema;
|
||||||
|
while (pIter->colIdx < pSchema->numOfCols) {
|
||||||
|
pCol = &pSchema->columns[pIter->colIdx]; // 1st column of schema is primary TS key
|
||||||
|
if (colId == pCol->colId) {
|
||||||
|
break;
|
||||||
|
} else if (pCol->colId < colId) {
|
||||||
|
++pIter->colIdx;
|
||||||
|
continue;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tdSTSRowIterGetTpVal(pIter, pCol->type, pCol->offset, pVal);
|
||||||
|
++pIter->colIdx;
|
||||||
|
} else if (TD_IS_KV_ROW(pIter->pRow)) {
|
||||||
|
return tdSTSRowIterGetKvVal(pIter, colId, &pIter->kvIdx, pVal);
|
||||||
|
} else {
|
||||||
|
pVal->valType = TD_VTYPE_NONE;
|
||||||
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
if (COL_REACH_END(colId, pIter->maxColId)) return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool tdSTSRowIterGetTpVal(STSRowIter *pIter, col_type_t colType, int32_t offset, SCellVal *pVal) {
|
||||||
|
STSRow *pRow = pIter->pRow;
|
||||||
|
if (pRow->statis == 0) {
|
||||||
|
pVal->valType = TD_VTYPE_NORM;
|
||||||
|
if (IS_VAR_DATA_TYPE(colType)) {
|
||||||
|
pVal->val = POINTER_SHIFT(pRow, *(VarDataOffsetT *)POINTER_SHIFT(TD_ROW_DATA(pRow), offset));
|
||||||
|
} else {
|
||||||
|
pVal->val = POINTER_SHIFT(TD_ROW_DATA(pRow), offset);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tdGetBitmapValType(pIter->pBitmap, pIter->colIdx - 1, &pVal->valType, 0) != TSDB_CODE_SUCCESS) {
|
||||||
|
pVal->valType = TD_VTYPE_NONE;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (pVal->valType == TD_VTYPE_NORM) {
|
||||||
|
if (IS_VAR_DATA_TYPE(colType)) {
|
||||||
|
pVal->val = POINTER_SHIFT(pRow, *(VarDataOffsetT *)POINTER_SHIFT(TD_ROW_DATA(pRow), offset));
|
||||||
|
} else {
|
||||||
|
pVal->val = POINTER_SHIFT(TD_ROW_DATA(pRow), offset);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t tdGetBitmapValTypeII(const void *pBitmap, int16_t colIdx, TDRowValT *pValType) {
|
||||||
|
if (!pBitmap || colIdx < 0) {
|
||||||
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
return terrno;
|
||||||
|
}
|
||||||
|
int16_t nBytes = colIdx / TD_VTYPE_PARTS;
|
||||||
|
int16_t nOffset = colIdx & TD_VTYPE_OPTR;
|
||||||
|
char *pDestByte = (char *)POINTER_SHIFT(pBitmap, nBytes);
|
||||||
|
// use literal value directly and not use formula to simplify the codes
|
||||||
|
switch (nOffset) {
|
||||||
|
case 0:
|
||||||
|
*pValType = (((*pDestByte) & 0xC0) >> 6);
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
*pValType = (((*pDestByte) & 0x30) >> 4);
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
*pValType = (((*pDestByte) & 0x0C) >> 2);
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
*pValType = ((*pDestByte) & 0x03);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
return terrno;
|
||||||
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t tdGetBitmapValTypeI(const void *pBitmap, int16_t colIdx, TDRowValT *pValType) {
|
||||||
|
if (!pBitmap || colIdx < 0) {
|
||||||
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
return terrno;
|
||||||
|
}
|
||||||
|
int16_t nBytes = colIdx / TD_VTYPE_PARTS_I;
|
||||||
|
int16_t nOffset = colIdx & TD_VTYPE_OPTR_I;
|
||||||
|
char *pDestByte = (char *)POINTER_SHIFT(pBitmap, nBytes);
|
||||||
|
// use literal value directly and not use formula to simplify the codes
|
||||||
|
switch (nOffset) {
|
||||||
|
case 0:
|
||||||
|
*pValType = (((*pDestByte) & 0x80) >> 7);
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
*pValType = (((*pDestByte) & 0x40) >> 6);
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
*pValType = (((*pDestByte) & 0x20) >> 5);
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
*pValType = (((*pDestByte) & 0x10) >> 4);
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
*pValType = (((*pDestByte) & 0x08) >> 3);
|
||||||
|
break;
|
||||||
|
case 5:
|
||||||
|
*pValType = (((*pDestByte) & 0x04) >> 2);
|
||||||
|
break;
|
||||||
|
case 6:
|
||||||
|
*pValType = (((*pDestByte) & 0x02) >> 1);
|
||||||
|
break;
|
||||||
|
case 7:
|
||||||
|
*pValType = ((*pDestByte) & 0x01);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
return terrno;
|
||||||
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t tdGetBitmapValType(const void *pBitmap, int16_t colIdx, TDRowValT *pValType, int8_t bitmapMode) {
|
||||||
|
switch (bitmapMode) {
|
||||||
|
case 0:
|
||||||
|
tdGetBitmapValTypeII(pBitmap, colIdx, pValType);
|
||||||
|
break;
|
||||||
|
case -1:
|
||||||
|
case 1:
|
||||||
|
tdGetBitmapValTypeI(pBitmap, colIdx, pValType);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
return TSDB_CODE_FAILED;
|
||||||
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool tdSTSRowIterGetKvVal(STSRowIter *pIter, col_id_t colId, col_id_t *nIdx, SCellVal *pVal) {
|
||||||
|
STSRow *pRow = pIter->pRow;
|
||||||
|
SKvRowIdx *pKvIdx = NULL;
|
||||||
|
bool colFound = false;
|
||||||
|
col_id_t kvNCols = tdRowGetNCols(pRow) - 1;
|
||||||
|
void *pColIdx = TD_ROW_COL_IDX(pRow);
|
||||||
|
while (*nIdx < kvNCols) {
|
||||||
|
pKvIdx = (SKvRowIdx *)POINTER_SHIFT(pColIdx, *nIdx * sizeof(SKvRowIdx));
|
||||||
|
if (pKvIdx->colId == colId) {
|
||||||
|
++(*nIdx);
|
||||||
|
pVal->val = POINTER_SHIFT(pRow, pKvIdx->offset);
|
||||||
|
colFound = true;
|
||||||
|
break;
|
||||||
|
} else if (pKvIdx->colId > colId) {
|
||||||
|
pVal->valType = TD_VTYPE_NONE;
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
++(*nIdx);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!colFound) {
|
||||||
|
if (colId <= pIter->maxColId) {
|
||||||
|
pVal->valType = TD_VTYPE_NONE;
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tdGetBitmapValType(pIter->pBitmap, pIter->kvIdx - 1, &pVal->valType, 0) != TSDB_CODE_SUCCESS) {
|
||||||
|
pVal->valType = TD_VTYPE_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef BUILD_NO_CALL
|
||||||
const uint8_t tdVTypeByte[2][3] = {{
|
const uint8_t tdVTypeByte[2][3] = {{
|
||||||
// 2 bits
|
// 2 bits
|
||||||
TD_VTYPE_NORM_BYTE_II,
|
TD_VTYPE_NORM_BYTE_II,
|
||||||
|
@ -34,8 +249,6 @@ const uint8_t tdVTypeByte[2][3] = {{
|
||||||
|
|
||||||
// declaration
|
// declaration
|
||||||
static uint8_t tdGetBitmapByte(uint8_t byte);
|
static uint8_t tdGetBitmapByte(uint8_t byte);
|
||||||
static bool tdSTSRowIterGetTpVal(STSRowIter *pIter, col_type_t colType, int32_t offset, SCellVal *pVal);
|
|
||||||
static bool tdSTSRowIterGetKvVal(STSRowIter *pIter, col_id_t colId, col_id_t *nIdx, SCellVal *pVal);
|
|
||||||
static bool tdSTpRowGetVal(STSRow *pRow, col_id_t colId, col_type_t colType, int32_t flen, uint32_t offset,
|
static bool tdSTpRowGetVal(STSRow *pRow, col_id_t colId, col_type_t colType, int32_t flen, uint32_t offset,
|
||||||
col_id_t colIdx, SCellVal *pVal);
|
col_id_t colIdx, SCellVal *pVal);
|
||||||
static bool tdSKvRowGetVal(STSRow *pRow, col_id_t colId, col_id_t colIdx, SCellVal *pVal);
|
static bool tdSKvRowGetVal(STSRow *pRow, col_id_t colId, col_id_t colIdx, SCellVal *pVal);
|
||||||
|
@ -199,38 +412,6 @@ bool tdSTpRowGetVal(STSRow *pRow, col_id_t colId, col_type_t colType, int32_t fl
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tdSTSRowIterFetch(STSRowIter *pIter, col_id_t colId, col_type_t colType, SCellVal *pVal) {
|
|
||||||
if (colId == PRIMARYKEY_TIMESTAMP_COL_ID) {
|
|
||||||
pVal->val = &pIter->pRow->ts;
|
|
||||||
pVal->valType = TD_VTYPE_NORM;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (TD_IS_TP_ROW(pIter->pRow)) {
|
|
||||||
STColumn *pCol = NULL;
|
|
||||||
STSchema *pSchema = pIter->pSchema;
|
|
||||||
while (pIter->colIdx < pSchema->numOfCols) {
|
|
||||||
pCol = &pSchema->columns[pIter->colIdx]; // 1st column of schema is primary TS key
|
|
||||||
if (colId == pCol->colId) {
|
|
||||||
break;
|
|
||||||
} else if (pCol->colId < colId) {
|
|
||||||
++pIter->colIdx;
|
|
||||||
continue;
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
tdSTSRowIterGetTpVal(pIter, pCol->type, pCol->offset, pVal);
|
|
||||||
++pIter->colIdx;
|
|
||||||
} else if (TD_IS_KV_ROW(pIter->pRow)) {
|
|
||||||
return tdSTSRowIterGetKvVal(pIter, colId, &pIter->kvIdx, pVal);
|
|
||||||
} else {
|
|
||||||
pVal->valType = TD_VTYPE_NONE;
|
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
|
||||||
if (COL_REACH_END(colId, pIter->maxColId)) return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool tdSTSRowIterNext(STSRowIter *pIter, SCellVal *pVal) {
|
bool tdSTSRowIterNext(STSRowIter *pIter, SCellVal *pVal) {
|
||||||
if (pIter->colIdx >= pIter->pSchema->numOfCols) {
|
if (pIter->colIdx >= pIter->pSchema->numOfCols) {
|
||||||
|
@ -258,71 +439,6 @@ bool tdSTSRowIterNext(STSRowIter *pIter, SCellVal *pVal) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tdSTSRowIterGetTpVal(STSRowIter *pIter, col_type_t colType, int32_t offset, SCellVal *pVal) {
|
|
||||||
STSRow *pRow = pIter->pRow;
|
|
||||||
if (pRow->statis == 0) {
|
|
||||||
pVal->valType = TD_VTYPE_NORM;
|
|
||||||
if (IS_VAR_DATA_TYPE(colType)) {
|
|
||||||
pVal->val = POINTER_SHIFT(pRow, *(VarDataOffsetT *)POINTER_SHIFT(TD_ROW_DATA(pRow), offset));
|
|
||||||
} else {
|
|
||||||
pVal->val = POINTER_SHIFT(TD_ROW_DATA(pRow), offset);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (tdGetBitmapValType(pIter->pBitmap, pIter->colIdx - 1, &pVal->valType, 0) != TSDB_CODE_SUCCESS) {
|
|
||||||
pVal->valType = TD_VTYPE_NONE;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (pVal->valType == TD_VTYPE_NORM) {
|
|
||||||
if (IS_VAR_DATA_TYPE(colType)) {
|
|
||||||
pVal->val = POINTER_SHIFT(pRow, *(VarDataOffsetT *)POINTER_SHIFT(TD_ROW_DATA(pRow), offset));
|
|
||||||
} else {
|
|
||||||
pVal->val = POINTER_SHIFT(TD_ROW_DATA(pRow), offset);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool tdSTSRowIterGetKvVal(STSRowIter *pIter, col_id_t colId, col_id_t *nIdx, SCellVal *pVal) {
|
|
||||||
STSRow *pRow = pIter->pRow;
|
|
||||||
SKvRowIdx *pKvIdx = NULL;
|
|
||||||
bool colFound = false;
|
|
||||||
col_id_t kvNCols = tdRowGetNCols(pRow) - 1;
|
|
||||||
void *pColIdx = TD_ROW_COL_IDX(pRow);
|
|
||||||
while (*nIdx < kvNCols) {
|
|
||||||
pKvIdx = (SKvRowIdx *)POINTER_SHIFT(pColIdx, *nIdx * sizeof(SKvRowIdx));
|
|
||||||
if (pKvIdx->colId == colId) {
|
|
||||||
++(*nIdx);
|
|
||||||
pVal->val = POINTER_SHIFT(pRow, pKvIdx->offset);
|
|
||||||
colFound = true;
|
|
||||||
break;
|
|
||||||
} else if (pKvIdx->colId > colId) {
|
|
||||||
pVal->valType = TD_VTYPE_NONE;
|
|
||||||
return true;
|
|
||||||
} else {
|
|
||||||
++(*nIdx);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!colFound) {
|
|
||||||
if (colId <= pIter->maxColId) {
|
|
||||||
pVal->valType = TD_VTYPE_NONE;
|
|
||||||
return true;
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (tdGetBitmapValType(pIter->pBitmap, pIter->kvIdx - 1, &pVal->valType, 0) != TSDB_CODE_SUCCESS) {
|
|
||||||
pVal->valType = TD_VTYPE_NONE;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
int32_t tdSTSRowNew(SArray *pArray, STSchema *pTSchema, STSRow **ppRow) {
|
int32_t tdSTSRowNew(SArray *pArray, STSchema *pTSchema, STSRow **ppRow) {
|
||||||
STColumn *pTColumn;
|
STColumn *pTColumn;
|
||||||
SColVal *pColVal;
|
SColVal *pColVal;
|
||||||
|
@ -490,76 +606,6 @@ bool tdSTSRowGetVal(STSRowIter *pIter, col_id_t colId, col_type_t colType, SCell
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t tdGetBitmapValTypeII(const void *pBitmap, int16_t colIdx, TDRowValT *pValType) {
|
|
||||||
if (!pBitmap || colIdx < 0) {
|
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
|
||||||
return terrno;
|
|
||||||
}
|
|
||||||
int16_t nBytes = colIdx / TD_VTYPE_PARTS;
|
|
||||||
int16_t nOffset = colIdx & TD_VTYPE_OPTR;
|
|
||||||
char *pDestByte = (char *)POINTER_SHIFT(pBitmap, nBytes);
|
|
||||||
// use literal value directly and not use formula to simplify the codes
|
|
||||||
switch (nOffset) {
|
|
||||||
case 0:
|
|
||||||
*pValType = (((*pDestByte) & 0xC0) >> 6);
|
|
||||||
break;
|
|
||||||
case 1:
|
|
||||||
*pValType = (((*pDestByte) & 0x30) >> 4);
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
*pValType = (((*pDestByte) & 0x0C) >> 2);
|
|
||||||
break;
|
|
||||||
case 3:
|
|
||||||
*pValType = ((*pDestByte) & 0x03);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
|
||||||
return terrno;
|
|
||||||
}
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
int32_t tdGetBitmapValTypeI(const void *pBitmap, int16_t colIdx, TDRowValT *pValType) {
|
|
||||||
if (!pBitmap || colIdx < 0) {
|
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
|
||||||
return terrno;
|
|
||||||
}
|
|
||||||
int16_t nBytes = colIdx / TD_VTYPE_PARTS_I;
|
|
||||||
int16_t nOffset = colIdx & TD_VTYPE_OPTR_I;
|
|
||||||
char *pDestByte = (char *)POINTER_SHIFT(pBitmap, nBytes);
|
|
||||||
// use literal value directly and not use formula to simplify the codes
|
|
||||||
switch (nOffset) {
|
|
||||||
case 0:
|
|
||||||
*pValType = (((*pDestByte) & 0x80) >> 7);
|
|
||||||
break;
|
|
||||||
case 1:
|
|
||||||
*pValType = (((*pDestByte) & 0x40) >> 6);
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
*pValType = (((*pDestByte) & 0x20) >> 5);
|
|
||||||
break;
|
|
||||||
case 3:
|
|
||||||
*pValType = (((*pDestByte) & 0x10) >> 4);
|
|
||||||
break;
|
|
||||||
case 4:
|
|
||||||
*pValType = (((*pDestByte) & 0x08) >> 3);
|
|
||||||
break;
|
|
||||||
case 5:
|
|
||||||
*pValType = (((*pDestByte) & 0x04) >> 2);
|
|
||||||
break;
|
|
||||||
case 6:
|
|
||||||
*pValType = (((*pDestByte) & 0x02) >> 1);
|
|
||||||
break;
|
|
||||||
case 7:
|
|
||||||
*pValType = ((*pDestByte) & 0x01);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
|
||||||
return terrno;
|
|
||||||
}
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
int32_t tdSetBitmapValTypeI(void *pBitmap, int16_t colIdx, TDRowValT valType) {
|
int32_t tdSetBitmapValTypeI(void *pBitmap, int16_t colIdx, TDRowValT valType) {
|
||||||
if (!pBitmap || colIdx < 0) {
|
if (!pBitmap || colIdx < 0) {
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
terrno = TSDB_CODE_INVALID_PARA;
|
||||||
|
@ -944,21 +990,6 @@ int32_t tdSRowSetInfo(SRowBuilder *pBuilder, int32_t nCols, int32_t nBoundCols,
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t tdGetBitmapValType(const void *pBitmap, int16_t colIdx, TDRowValT *pValType, int8_t bitmapMode) {
|
|
||||||
switch (bitmapMode) {
|
|
||||||
case 0:
|
|
||||||
tdGetBitmapValTypeII(pBitmap, colIdx, pValType);
|
|
||||||
break;
|
|
||||||
case -1:
|
|
||||||
case 1:
|
|
||||||
tdGetBitmapValTypeI(pBitmap, colIdx, pValType);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
terrno = TSDB_CODE_INVALID_PARA;
|
|
||||||
return TSDB_CODE_FAILED;
|
|
||||||
}
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
|
||||||
#if 0
|
#if 0
|
||||||
bool tdIsBitmapValTypeNorm(const void *pBitmap, int16_t idx, int8_t bitmapMode) {
|
bool tdIsBitmapValTypeNorm(const void *pBitmap, int16_t idx, int8_t bitmapMode) {
|
||||||
TDRowValT valType = 0;
|
TDRowValT valType = 0;
|
||||||
|
@ -1020,32 +1051,7 @@ int32_t tdSetBitmapValType(void *pBitmap, int16_t colIdx, TDRowValT valType, int
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
void *tdGetBitmapAddr(STSRow *pRow, uint8_t rowType, uint32_t flen, col_id_t nKvCols) {
|
|
||||||
#ifdef TD_SUPPORT_BITMAP
|
|
||||||
switch (rowType) {
|
|
||||||
case TD_ROW_TP:
|
|
||||||
return tdGetBitmapAddrTp(pRow, flen);
|
|
||||||
case TD_ROW_KV:
|
|
||||||
return tdGetBitmapAddrKv(pRow, nKvCols);
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
void tdSTSRowIterReset(STSRowIter *pIter, STSRow *pRow) {
|
|
||||||
pIter->pRow = pRow;
|
|
||||||
pIter->pBitmap = tdGetBitmapAddr(pRow, pRow->type, pIter->pSchema->flen, tdRowGetNCols(pRow));
|
|
||||||
pIter->offset = 0;
|
|
||||||
pIter->colIdx = 0; // PRIMARYKEY_TIMESTAMP_COL_ID;
|
|
||||||
pIter->kvIdx = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void tdSTSRowIterInit(STSRowIter *pIter, STSchema *pSchema) {
|
|
||||||
pIter->pSchema = pSchema;
|
|
||||||
pIter->maxColId = pSchema->columns[pSchema->numOfCols - 1].colId;
|
|
||||||
}
|
|
||||||
|
|
||||||
void tTSRowGetVal(STSRow *pRow, STSchema *pTSchema, int16_t iCol, SColVal *pColVal) {
|
void tTSRowGetVal(STSRow *pRow, STSchema *pTSchema, int16_t iCol, SColVal *pColVal) {
|
||||||
STColumn *pTColumn = &pTSchema->columns[iCol];
|
STColumn *pTColumn = &pTSchema->columns[iCol];
|
||||||
|
@ -1079,3 +1085,4 @@ void tTSRowGetVal(STSRow *pRow, STSchema *pTSchema, int16_t iCol, SColVal *pColV
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#endif
|
|
@ -1297,7 +1297,7 @@ static void parseTsFormat(const char* formatStr, SArray* formats) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void tm2char(const SArray* formats, const struct STm* tm, char* s, int32_t outLen) {
|
static int32_t tm2char(const SArray* formats, const struct STm* tm, char* s, int32_t outLen) {
|
||||||
int32_t size = taosArrayGetSize(formats);
|
int32_t size = taosArrayGetSize(formats);
|
||||||
const char* start = s;
|
const char* start = s;
|
||||||
for (int32_t i = 0; i < size; ++i) {
|
for (int32_t i = 0; i < size; ++i) {
|
||||||
|
@ -1332,6 +1332,9 @@ static void tm2char(const SArray* formats, const struct STm* tm, char* s, int32_
|
||||||
s += 4;
|
s += 4;
|
||||||
break;
|
break;
|
||||||
case TSFKW_DDD:
|
case TSFKW_DDD:
|
||||||
|
#ifdef WINDOWS
|
||||||
|
return TSDB_CODE_FUNC_TO_CHAR_NOT_SUPPORTED;
|
||||||
|
#endif
|
||||||
sprintf(s, "%03d", tm->tm.tm_yday + 1);
|
sprintf(s, "%03d", tm->tm.tm_yday + 1);
|
||||||
s += strlen(s);
|
s += strlen(s);
|
||||||
break;
|
break;
|
||||||
|
@ -1486,6 +1489,7 @@ static void tm2char(const SArray* formats, const struct STm* tm, char* s, int32_
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @brief find s in arr case insensitively
|
/// @brief find s in arr case insensitively
|
||||||
|
@ -1889,14 +1893,14 @@ static int32_t char2ts(const char* s, SArray* formats, int64_t* ts, int32_t prec
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void taosTs2Char(const char* format, SArray** formats, int64_t ts, int32_t precision, char* out, int32_t outLen) {
|
int32_t taosTs2Char(const char* format, SArray** formats, int64_t ts, int32_t precision, char* out, int32_t outLen) {
|
||||||
if (!*formats) {
|
if (!*formats) {
|
||||||
*formats = taosArrayInit(8, sizeof(TSFormatNode));
|
*formats = taosArrayInit(8, sizeof(TSFormatNode));
|
||||||
parseTsFormat(format, *formats);
|
parseTsFormat(format, *formats);
|
||||||
}
|
}
|
||||||
struct STm tm;
|
struct STm tm;
|
||||||
taosTs2Tm(ts, precision, &tm);
|
taosTs2Tm(ts, precision, &tm);
|
||||||
tm2char(*formats, &tm, out, outLen);
|
return tm2char(*formats, &tm, out, outLen);
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t taosChar2Ts(const char* format, SArray** formats, const char* tsStr, int64_t* ts, int32_t precision, char* errMsg,
|
int32_t taosChar2Ts(const char* format, SArray** formats, const char* tsStr, int64_t* ts, int32_t precision, char* errMsg,
|
||||||
|
|
|
@ -108,11 +108,11 @@ SArray *mmGetMsgHandles() {
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_DROP_SNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_DROP_SNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_CREATE_VNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_CREATE_VNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_DROP_VNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_DROP_VNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_CONFIG_DNODE_RSP, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_CONFIG_DNODE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_ALTER_MNODE_TYPE_RSP, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_ALTER_MNODE_TYPE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_ALTER_VNODE_TYPE_RSP, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_ALTER_VNODE_TYPE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_DND_CHECK_VNODE_LEARNER_CATCHUP_RSP, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_DND_CHECK_VNODE_LEARNER_CATCHUP_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_SYNC_CONFIG_CHANGE_RSP, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_SYNC_CONFIG_CHANGE_RSP, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
|
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_MND_CONNECT, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_MND_CONNECT, mmPutMsgToReadQueue, 0) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_MND_CREATE_ACCT, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_MND_CREATE_ACCT, mmPutMsgToWriteQueue, 0) == NULL) goto _OVER;
|
||||||
|
|
|
@ -90,7 +90,7 @@ SArray *smGetMsgHandles() {
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_VND_STREAM_SCAN_HISTORY_FINISH, smPutNodeMsgToStreamQueue, 1) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_VND_STREAM_SCAN_HISTORY_FINISH, smPutNodeMsgToStreamQueue, 1) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_VND_STREAM_SCAN_HISTORY_FINISH_RSP, smPutNodeMsgToStreamQueue, 1) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_VND_STREAM_SCAN_HISTORY_FINISH_RSP, smPutNodeMsgToStreamQueue, 1) == NULL) goto _OVER;
|
||||||
if (dmSetMgmtHandle(pArray, TDMT_STREAM_TASK_CHECKPOINT_READY, smPutNodeMsgToStreamQueue, 1) == NULL) goto _OVER;
|
if (dmSetMgmtHandle(pArray, TDMT_STREAM_TASK_CHECKPOINT_READY, smPutNodeMsgToStreamQueue, 1) == NULL) goto _OVER;
|
||||||
|
if (dmSetMgmtHandle(pArray, TDMT_VND_STREAM_TASK_RESET, smPutNodeMsgToMgmtQueue, 1) == NULL) goto _OVER;
|
||||||
|
|
||||||
code = 0;
|
code = 0;
|
||||||
_OVER:
|
_OVER:
|
||||||
|
|
|
@ -44,12 +44,11 @@ typedef struct SStreamTransMgmt {
|
||||||
} SStreamTransMgmt;
|
} SStreamTransMgmt;
|
||||||
|
|
||||||
typedef struct SStreamExecInfo {
|
typedef struct SStreamExecInfo {
|
||||||
SArray * pNodeList;
|
SArray *pNodeList;
|
||||||
int64_t ts; // snapshot ts
|
int64_t ts; // snapshot ts
|
||||||
SStreamTransMgmt transMgmt;
|
SStreamTransMgmt transMgmt;
|
||||||
int64_t activeCheckpoint; // active check point id
|
SHashObj *pTaskMap;
|
||||||
SHashObj * pTaskMap;
|
SArray *pTaskList;
|
||||||
SArray * pTaskList;
|
|
||||||
TdThreadMutex lock;
|
TdThreadMutex lock;
|
||||||
} SStreamExecInfo;
|
} SStreamExecInfo;
|
||||||
|
|
||||||
|
|
|
@ -97,7 +97,7 @@ SSdbRaw *mndTransEncode(STrans *pTrans);
|
||||||
SSdbRow *mndTransDecode(SSdbRaw *pRaw);
|
SSdbRow *mndTransDecode(SSdbRaw *pRaw);
|
||||||
void mndTransDropData(STrans *pTrans);
|
void mndTransDropData(STrans *pTrans);
|
||||||
|
|
||||||
bool mndTransPerformPrepareStage(SMnode *pMnode, STrans *pTrans);
|
bool mndTransPerformPrepareStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -290,7 +290,7 @@ int32_t mndAddCompactDetailToTran(SMnode *pMnode, STrans *pTrans, SCompactObj* p
|
||||||
|
|
||||||
SSdbRaw *pVgRaw = mndCompactDetailActionEncode(&compactDetail);
|
SSdbRaw *pVgRaw = mndCompactDetailActionEncode(&compactDetail);
|
||||||
if (pVgRaw == NULL) return -1;
|
if (pVgRaw == NULL) return -1;
|
||||||
if (mndTransAppendRedolog(pTrans, pVgRaw) != 0) {
|
if (mndTransAppendCommitlog(pTrans, pVgRaw) != 0) {
|
||||||
sdbFreeRaw(pVgRaw);
|
sdbFreeRaw(pVgRaw);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
|
@ -62,7 +62,7 @@ static void mndCancelGetNextStreamTask(SMnode *pMnode, void *pIter);
|
||||||
static int32_t mndProcessPauseStreamReq(SRpcMsg *pReq);
|
static int32_t mndProcessPauseStreamReq(SRpcMsg *pReq);
|
||||||
static int32_t mndProcessResumeStreamReq(SRpcMsg *pReq);
|
static int32_t mndProcessResumeStreamReq(SRpcMsg *pReq);
|
||||||
static int32_t mndBuildStreamCheckpointSourceReq2(void **pBuf, int32_t *pLen, int32_t nodeId, int64_t checkpointId,
|
static int32_t mndBuildStreamCheckpointSourceReq2(void **pBuf, int32_t *pLen, int32_t nodeId, int64_t checkpointId,
|
||||||
int64_t streamId, int32_t taskId);
|
int64_t streamId, int32_t taskId, int32_t transId);
|
||||||
static int32_t mndProcessNodeCheck(SRpcMsg *pReq);
|
static int32_t mndProcessNodeCheck(SRpcMsg *pReq);
|
||||||
static int32_t mndProcessNodeCheckReq(SRpcMsg *pMsg);
|
static int32_t mndProcessNodeCheckReq(SRpcMsg *pMsg);
|
||||||
static SArray *extractNodeListFromStream(SMnode *pMnode);
|
static SArray *extractNodeListFromStream(SMnode *pMnode);
|
||||||
|
@ -685,6 +685,40 @@ _OVER:
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int32_t extractNodeEpset(SMnode *pMnode, SEpSet *pEpSet, bool* hasEpset, int32_t taskId, int32_t nodeId) {
|
||||||
|
*hasEpset = false;
|
||||||
|
|
||||||
|
if (nodeId == SNODE_HANDLE) {
|
||||||
|
SSnodeObj *pObj = NULL;
|
||||||
|
void *pIter = NULL;
|
||||||
|
|
||||||
|
pIter = sdbFetch(pMnode->pSdb, SDB_SNODE, pIter, (void **)&pObj);
|
||||||
|
if (pIter != NULL) {
|
||||||
|
addEpIntoEpSet(pEpSet, pObj->pDnode->fqdn, pObj->pDnode->port);
|
||||||
|
sdbRelease(pMnode->pSdb, pObj);
|
||||||
|
sdbCancelFetch(pMnode->pSdb, pIter);
|
||||||
|
*hasEpset = true;
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
} else {
|
||||||
|
mError("failed to acquire snode epset");
|
||||||
|
return TSDB_CODE_INVALID_PARA;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
SVgObj *pVgObj = mndAcquireVgroup(pMnode, nodeId);
|
||||||
|
if (pVgObj != NULL) {
|
||||||
|
SEpSet epset = mndGetVgroupEpset(pMnode, pVgObj);
|
||||||
|
mndReleaseVgroup(pMnode, pVgObj);
|
||||||
|
|
||||||
|
epsetAssign(pEpSet, &epset);
|
||||||
|
*hasEpset = true;
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
} else {
|
||||||
|
mDebug("orphaned task:0x%x need to be dropped, nodeId:%d, no redo action", taskId, nodeId);
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static int32_t mndPersistTaskDropReq(SMnode *pMnode, STrans *pTrans, SStreamTask *pTask) {
|
static int32_t mndPersistTaskDropReq(SMnode *pMnode, STrans *pTrans, SStreamTask *pTask) {
|
||||||
SVDropStreamTaskReq *pReq = taosMemoryCalloc(1, sizeof(SVDropStreamTaskReq));
|
SVDropStreamTaskReq *pReq = taosMemoryCalloc(1, sizeof(SVDropStreamTaskReq));
|
||||||
if (pReq == NULL) {
|
if (pReq == NULL) {
|
||||||
|
@ -698,28 +732,17 @@ static int32_t mndPersistTaskDropReq(SMnode *pMnode, STrans *pTrans, SStreamTask
|
||||||
|
|
||||||
STransAction action = {0};
|
STransAction action = {0};
|
||||||
SEpSet epset = {0};
|
SEpSet epset = {0};
|
||||||
if (pTask->info.nodeId == SNODE_HANDLE) {
|
bool hasEpset = false;
|
||||||
SSnodeObj *pObj = NULL;
|
|
||||||
void *pIter = NULL;
|
|
||||||
while (1) {
|
|
||||||
pIter = sdbFetch(pMnode->pSdb, SDB_SNODE, pIter, (void **)&pObj);
|
|
||||||
if (pIter == NULL) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
addEpIntoEpSet(&epset, pObj->pDnode->fqdn, pObj->pDnode->port);
|
int32_t code = extractNodeEpset(pMnode, &epset, &hasEpset, pTask->id.taskId, pTask->info.nodeId);
|
||||||
sdbRelease(pMnode->pSdb, pObj);
|
if (code != TSDB_CODE_SUCCESS) {
|
||||||
}
|
terrno = code;
|
||||||
} else {
|
return -1;
|
||||||
SVgObj *pVgObj = mndAcquireVgroup(pMnode, pTask->info.nodeId);
|
}
|
||||||
if (pVgObj != NULL) {
|
|
||||||
epset = mndGetVgroupEpset(pMnode, pVgObj);
|
// no valid epset, return directly without redoAction
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
if (!hasEpset) {
|
||||||
} else {
|
return TSDB_CODE_SUCCESS;
|
||||||
mDebug("orphaned task:0x%x need to be dropped, nodeId:%d, no redo action", pTask->id.taskId, pTask->info.nodeId);
|
|
||||||
taosMemoryFree(pReq);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// The epset of nodeId of this task may have been expired now, let's use the newest epset from mnode.
|
// The epset of nodeId of this task may have been expired now, let's use the newest epset from mnode.
|
||||||
|
@ -974,13 +997,14 @@ static int32_t mndProcessStreamRemainChkptTmr(SRpcMsg *pReq) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndBuildStreamCheckpointSourceReq2(void **pBuf, int32_t *pLen, int32_t nodeId, int64_t checkpointId,
|
static int32_t mndBuildStreamCheckpointSourceReq2(void **pBuf, int32_t *pLen, int32_t nodeId, int64_t checkpointId,
|
||||||
int64_t streamId, int32_t taskId) {
|
int64_t streamId, int32_t taskId, int32_t transId) {
|
||||||
SStreamCheckpointSourceReq req = {0};
|
SStreamCheckpointSourceReq req = {0};
|
||||||
req.checkpointId = checkpointId;
|
req.checkpointId = checkpointId;
|
||||||
req.nodeId = nodeId;
|
req.nodeId = nodeId;
|
||||||
req.expireTime = -1;
|
req.expireTime = -1;
|
||||||
req.streamId = streamId; // pTask->id.streamId;
|
req.streamId = streamId; // pTask->id.streamId;
|
||||||
req.taskId = taskId; // pTask->id.taskId;
|
req.taskId = taskId; // pTask->id.taskId;
|
||||||
|
req.transId = transId;
|
||||||
|
|
||||||
int32_t code;
|
int32_t code;
|
||||||
int32_t blen;
|
int32_t blen;
|
||||||
|
@ -1070,7 +1094,7 @@ static int32_t mndProcessStreamCheckpointTrans(SMnode *pMnode, SStreamObj *pStre
|
||||||
void * buf;
|
void * buf;
|
||||||
int32_t tlen;
|
int32_t tlen;
|
||||||
if (mndBuildStreamCheckpointSourceReq2(&buf, &tlen, pTask->info.nodeId, checkpointId, pTask->id.streamId,
|
if (mndBuildStreamCheckpointSourceReq2(&buf, &tlen, pTask->info.nodeId, checkpointId, pTask->id.streamId,
|
||||||
pTask->id.taskId) < 0) {
|
pTask->id.taskId, pTrans->id) < 0) {
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
mndReleaseVgroup(pMnode, pVgObj);
|
||||||
taosWUnLockLatch(&pStream->lock);
|
taosWUnLockLatch(&pStream->lock);
|
||||||
goto _ERR;
|
goto _ERR;
|
||||||
|
@ -1139,7 +1163,7 @@ static int32_t mndAddStreamCheckpointToTrans(STrans *pTrans, SStreamObj *pStream
|
||||||
void * buf;
|
void * buf;
|
||||||
int32_t tlen;
|
int32_t tlen;
|
||||||
if (mndBuildStreamCheckpointSourceReq2(&buf, &tlen, pTask->info.nodeId, chkptId, pTask->id.streamId,
|
if (mndBuildStreamCheckpointSourceReq2(&buf, &tlen, pTask->info.nodeId, chkptId, pTask->id.streamId,
|
||||||
pTask->id.taskId) < 0) {
|
pTask->id.taskId, pTrans->id) < 0) {
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
mndReleaseVgroup(pMnode, pVgObj);
|
||||||
taosWUnLockLatch(&pStream->lock);
|
taosWUnLockLatch(&pStream->lock);
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -1776,9 +1800,20 @@ static int32_t mndPauseStreamTask(SMnode *pMnode, STrans *pTrans, SStreamTask *p
|
||||||
pReq->taskId = pTask->id.taskId;
|
pReq->taskId = pTask->id.taskId;
|
||||||
pReq->streamId = pTask->id.streamId;
|
pReq->streamId = pTask->id.streamId;
|
||||||
|
|
||||||
SVgObj *pVgObj = mndAcquireVgroup(pMnode, pTask->info.nodeId);
|
SEpSet epset;
|
||||||
SEpSet epset = mndGetVgroupEpset(pMnode, pVgObj);
|
bool hasEpset = false;
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
int32_t code = extractNodeEpset(pMnode, &epset, &hasEpset, pTask->id.taskId, pTask->info.nodeId);
|
||||||
|
if (code != TSDB_CODE_SUCCESS) {
|
||||||
|
terrno = code;
|
||||||
|
taosMemoryFree(pReq);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// no valid epset, return directly without redoAction
|
||||||
|
if (!hasEpset) {
|
||||||
|
taosMemoryFree(pReq);
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
STransAction action = {0};
|
STransAction action = {0};
|
||||||
initTransAction(&action, pReq, sizeof(SVPauseStreamTaskReq), TDMT_STREAM_TASK_PAUSE, &epset, 0);
|
initTransAction(&action, pReq, sizeof(SVPauseStreamTaskReq), TDMT_STREAM_TASK_PAUSE, &epset, 0);
|
||||||
|
@ -1920,17 +1955,25 @@ static int32_t mndProcessPauseStreamReq(SRpcMsg *pReq) {
|
||||||
static int32_t mndResumeStreamTask(STrans *pTrans, SMnode *pMnode, SStreamTask *pTask, int8_t igUntreated) {
|
static int32_t mndResumeStreamTask(STrans *pTrans, SMnode *pMnode, SStreamTask *pTask, int8_t igUntreated) {
|
||||||
SVResumeStreamTaskReq *pReq = taosMemoryCalloc(1, sizeof(SVResumeStreamTaskReq));
|
SVResumeStreamTaskReq *pReq = taosMemoryCalloc(1, sizeof(SVResumeStreamTaskReq));
|
||||||
if (pReq == NULL) {
|
if (pReq == NULL) {
|
||||||
|
mError("failed to malloc in resume stream, size:%" PRIzu ", code:%s", sizeof(SVResumeStreamTaskReq),
|
||||||
|
tstrerror(TSDB_CODE_OUT_OF_MEMORY));
|
||||||
terrno = TSDB_CODE_OUT_OF_MEMORY;
|
terrno = TSDB_CODE_OUT_OF_MEMORY;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
pReq->head.vgId = htonl(pTask->info.nodeId);
|
pReq->head.vgId = htonl(pTask->info.nodeId);
|
||||||
pReq->taskId = pTask->id.taskId;
|
pReq->taskId = pTask->id.taskId;
|
||||||
pReq->streamId = pTask->id.streamId;
|
pReq->streamId = pTask->id.streamId;
|
||||||
pReq->igUntreated = igUntreated;
|
pReq->igUntreated = igUntreated;
|
||||||
|
|
||||||
SVgObj *pVgObj = mndAcquireVgroup(pMnode, pTask->info.nodeId);
|
SEpSet epset;
|
||||||
SEpSet epset = mndGetVgroupEpset(pMnode, pVgObj);
|
bool hasEpset = false;
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
int32_t code = extractNodeEpset(pMnode, &epset, &hasEpset, pTask->id.taskId, pTask->info.nodeId);
|
||||||
|
if (code != TSDB_CODE_SUCCESS) {
|
||||||
|
terrno = code;
|
||||||
|
taosMemoryFree(pReq);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
STransAction action = {0};
|
STransAction action = {0};
|
||||||
initTransAction(&action, pReq, sizeof(SVResumeStreamTaskReq), TDMT_STREAM_TASK_RESUME, &epset, 0);
|
initTransAction(&action, pReq, sizeof(SVResumeStreamTaskReq), TDMT_STREAM_TASK_RESUME, &epset, 0);
|
||||||
|
@ -2208,6 +2251,8 @@ static SVgroupChangeInfo mndFindChangedNodeInfo(SMnode *pMnode, const SArray *pP
|
||||||
epsetAssign(&updateInfo.newEp, &pCurrent->epset);
|
epsetAssign(&updateInfo.newEp, &pCurrent->epset);
|
||||||
taosArrayPush(info.pUpdateNodeList, &updateInfo);
|
taosArrayPush(info.pUpdateNodeList, &updateInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// todo handle the snode info
|
||||||
if (pCurrent->nodeId != SNODE_HANDLE) {
|
if (pCurrent->nodeId != SNODE_HANDLE) {
|
||||||
SVgObj *pVgroup = mndAcquireVgroup(pMnode, pCurrent->nodeId);
|
SVgObj *pVgroup = mndAcquireVgroup(pMnode, pCurrent->nodeId);
|
||||||
taosHashPut(info.pDBMap, pVgroup->dbName, strlen(pVgroup->dbName), NULL, 0);
|
taosHashPut(info.pDBMap, pVgroup->dbName, strlen(pVgroup->dbName), NULL, 0);
|
||||||
|
@ -2286,12 +2331,28 @@ static SArray *mndTakeVgroupSnapshot(SMnode *pMnode, bool *allReady) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndProcessVgroupChange(SMnode *pMnode, SVgroupChangeInfo *pChangeInfo) {
|
static int32_t mndProcessVgroupChange(SMnode *pMnode, SVgroupChangeInfo *pChangeInfo) {
|
||||||
SSdb *pSdb = pMnode->pSdb;
|
SSdb *pSdb = pMnode->pSdb;
|
||||||
|
|
||||||
// check all streams that involved this vnode should update the epset info
|
|
||||||
SStreamObj *pStream = NULL;
|
SStreamObj *pStream = NULL;
|
||||||
void * pIter = NULL;
|
void *pIter = NULL;
|
||||||
STrans * pTrans = NULL;
|
STrans *pTrans = NULL;
|
||||||
|
|
||||||
|
// conflict check for nodeUpdate trans, here we randomly chose one stream to add into the trans pool
|
||||||
|
while(1) {
|
||||||
|
pIter = sdbFetch(pSdb, SDB_STREAM, pIter, (void **)&pStream);
|
||||||
|
if (pIter == NULL) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool conflict = streamTransConflictOtherTrans(pMnode, pStream->uid, MND_STREAM_TASK_UPDATE_NAME, false);
|
||||||
|
sdbRelease(pSdb, pStream);
|
||||||
|
|
||||||
|
if (conflict) {
|
||||||
|
mWarn("nodeUpdate trans in progress, current nodeUpdate ignored");
|
||||||
|
sdbCancelFetch(pSdb, pIter);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
pIter = sdbFetch(pSdb, SDB_STREAM, pIter, (void **)&pStream);
|
pIter = sdbFetch(pSdb, SDB_STREAM, pIter, (void **)&pStream);
|
||||||
|
@ -2307,6 +2368,8 @@ static int32_t mndProcessVgroupChange(SMnode *pMnode, SVgroupChangeInfo *pChange
|
||||||
sdbCancelFetch(pSdb, pIter);
|
sdbCancelFetch(pSdb, pIter);
|
||||||
return terrno;
|
return terrno;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mndStreamRegisterTrans(pTrans, MND_STREAM_TASK_RESET_NAME, pStream->uid);
|
||||||
}
|
}
|
||||||
|
|
||||||
void *p = taosHashGet(pChangeInfo->pDBMap, pStream->targetDb, strlen(pStream->targetDb));
|
void *p = taosHashGet(pChangeInfo->pDBMap, pStream->targetDb, strlen(pStream->targetDb));
|
||||||
|
@ -2553,7 +2616,7 @@ static int32_t mndProcessNodeCheckReq(SRpcMsg *pMsg) {
|
||||||
|
|
||||||
code = mndProcessVgroupChange(pMnode, &changeInfo);
|
code = mndProcessVgroupChange(pMnode, &changeInfo);
|
||||||
|
|
||||||
// keep the new vnode snapshot
|
// keep the new vnode snapshot if success
|
||||||
if (code == TSDB_CODE_SUCCESS || code == TSDB_CODE_ACTION_IN_PROGRESS) {
|
if (code == TSDB_CODE_SUCCESS || code == TSDB_CODE_ACTION_IN_PROGRESS) {
|
||||||
mDebug("create trans successfully, update cached node list");
|
mDebug("create trans successfully, update cached node list");
|
||||||
taosArrayDestroy(execInfo.pNodeList);
|
taosArrayDestroy(execInfo.pNodeList);
|
||||||
|
@ -2704,9 +2767,18 @@ int32_t createStreamResetStatusTrans(SMnode *pMnode, SStreamObj *pStream) {
|
||||||
pReq->taskId = pTask->id.taskId;
|
pReq->taskId = pTask->id.taskId;
|
||||||
pReq->streamId = pTask->id.streamId;
|
pReq->streamId = pTask->id.streamId;
|
||||||
|
|
||||||
SVgObj *pVgObj = mndAcquireVgroup(pMnode, pTask->info.nodeId);
|
SEpSet epset;
|
||||||
SEpSet epset = mndGetVgroupEpset(pMnode, pVgObj);
|
bool hasEpset = false;
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
int32_t code = extractNodeEpset(pMnode, &epset, &hasEpset, pTask->id.taskId, pTask->info.nodeId);
|
||||||
|
if (code != TSDB_CODE_SUCCESS) {
|
||||||
|
taosMemoryFree(pReq);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!hasEpset) {
|
||||||
|
taosMemoryFree(pReq);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
STransAction action = {0};
|
STransAction action = {0};
|
||||||
initTransAction(&action, pReq, sizeof(SVResetStreamTaskReq), TDMT_VND_STREAM_TASK_RESET, &epset, 0);
|
initTransAction(&action, pReq, sizeof(SVResetStreamTaskReq), TDMT_VND_STREAM_TASK_RESET, &epset, 0);
|
||||||
|
@ -2766,39 +2838,36 @@ int32_t killActiveCheckpointTrans(SMnode *pMnode, const char *pDBName, size_t le
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndResetStatusFromCheckpoint(SMnode *pMnode, int32_t transId) {
|
static int32_t mndResetStatusFromCheckpoint(SMnode *pMnode, int64_t streamId, int32_t transId) {
|
||||||
|
int32_t code = TSDB_CODE_SUCCESS;
|
||||||
|
|
||||||
STrans *pTrans = mndAcquireTrans(pMnode, transId);
|
STrans *pTrans = mndAcquireTrans(pMnode, transId);
|
||||||
if (pTrans != NULL) {
|
if (pTrans != NULL) {
|
||||||
mInfo("kill checkpoint transId:%d to reset task status", transId);
|
mInfo("kill checkpoint transId:%d to reset task status", transId);
|
||||||
mndKillTrans(pMnode, pTrans);
|
mndKillTrans(pMnode, pTrans);
|
||||||
mndReleaseTrans(pMnode, pTrans);
|
mndReleaseTrans(pMnode, pTrans);
|
||||||
|
} else {
|
||||||
|
mError("failed to acquire checkpoint trans:%d", transId);
|
||||||
}
|
}
|
||||||
|
|
||||||
// set all tasks status to be normal, refactor later to be stream level, instead of vnode level.
|
SStreamObj *pStream = mndGetStreamObj(pMnode, streamId);
|
||||||
SSdb * pSdb = pMnode->pSdb;
|
if (pStream == NULL) {
|
||||||
SStreamObj *pStream = NULL;
|
code = TSDB_CODE_STREAM_TASK_NOT_EXIST;
|
||||||
void * pIter = NULL;
|
mError("failed to acquire the streamObj:0x%" PRIx64 " to reset checkpoint, may have been dropped", pStream->uid);
|
||||||
while (1) {
|
} else {
|
||||||
pIter = sdbFetch(pSdb, SDB_STREAM, pIter, (void **)&pStream);
|
|
||||||
if (pIter == NULL) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool conflict = streamTransConflictOtherTrans(pMnode, pStream->uid, MND_STREAM_TASK_RESET_NAME, false);
|
bool conflict = streamTransConflictOtherTrans(pMnode, pStream->uid, MND_STREAM_TASK_RESET_NAME, false);
|
||||||
if (conflict) {
|
if (conflict) {
|
||||||
mError("stream:%s other trans exists in DB:%s & %s failed to start reset-status trans", pStream->name,
|
mError("stream:%s other trans exists in DB:%s, dstTable:%s failed to start reset-status trans", pStream->name,
|
||||||
pStream->sourceDb, pStream->targetDb);
|
pStream->sourceDb, pStream->targetSTbName);
|
||||||
continue;
|
} else {
|
||||||
}
|
mDebug("stream:%s (0x%" PRIx64 ") reset checkpoint procedure, transId:%d, create reset trans", pStream->name,
|
||||||
|
pStream->uid, transId);
|
||||||
mDebug("stream:%s (0x%" PRIx64 ") reset checkpoint procedure, create reset trans", pStream->name, pStream->uid);
|
code = createStreamResetStatusTrans(pMnode, pStream);
|
||||||
int32_t code = createStreamResetStatusTrans(pMnode, pStream);
|
mndReleaseStream(pMnode, pStream);
|
||||||
if (code != TSDB_CODE_SUCCESS) {
|
|
||||||
sdbCancelFetch(pSdb, pIter);
|
|
||||||
return code;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
|
||||||
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static SStreamTask *mndGetStreamTask(STaskId *pId, SStreamObj *pStream) {
|
static SStreamTask *mndGetStreamTask(STaskId *pId, SStreamObj *pStream) {
|
||||||
|
@ -2878,11 +2947,17 @@ static int32_t mndDropRelatedFillhistoryTask(SMnode *pMnode, STaskStatusEntry *p
|
||||||
|
|
||||||
mDebug("build and send drop related fill-history task for task:0x%x", pTask->id.taskId);
|
mDebug("build and send drop related fill-history task for task:0x%x", pTask->id.taskId);
|
||||||
|
|
||||||
SVgObj *pVgObj = mndAcquireVgroup(pMnode, pTask->info.nodeId);
|
SEpSet epset;
|
||||||
SEpSet epset = mndGetVgroupEpset(pMnode, pVgObj);
|
bool hasEpset = false;
|
||||||
mndReleaseVgroup(pMnode, pVgObj);
|
int32_t code = extractNodeEpset(pMnode, &epset, &hasEpset, pTask->id.taskId, pTask->info.nodeId);
|
||||||
|
if (code != TSDB_CODE_SUCCESS) {
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (hasEpset) {
|
||||||
|
tmsgSendReq(&epset, &msg);
|
||||||
|
}
|
||||||
|
|
||||||
tmsgSendReq(&epset, &msg);
|
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2930,6 +3005,8 @@ int32_t mndProcessStreamHb(SRpcMsg *pReq) {
|
||||||
|
|
||||||
bool checkpointFailed = false;
|
bool checkpointFailed = false;
|
||||||
int64_t activeCheckpointId = 0;
|
int64_t activeCheckpointId = 0;
|
||||||
|
int64_t streamId = 0;
|
||||||
|
int32_t transId = 0;
|
||||||
|
|
||||||
SDecoder decoder = {0};
|
SDecoder decoder = {0};
|
||||||
tDecoderInit(&decoder, pReq->pCont, pReq->contLen);
|
tDecoderInit(&decoder, pReq->pCont, pReq->contLen);
|
||||||
|
@ -2972,7 +3049,9 @@ int32_t mndProcessStreamHb(SRpcMsg *pReq) {
|
||||||
|
|
||||||
if (pTaskEntry->stage != p->stage && pTaskEntry->stage != -1) {
|
if (pTaskEntry->stage != p->stage && pTaskEntry->stage != -1) {
|
||||||
updateStageInfo(pTaskEntry, p->stage);
|
updateStageInfo(pTaskEntry, p->stage);
|
||||||
if (pTaskEntry->nodeId == SNODE_HANDLE) snodeChanged = true;
|
if (pTaskEntry->nodeId == SNODE_HANDLE) {
|
||||||
|
snodeChanged = true;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// task is idle for more than 50 sec.
|
// task is idle for more than 50 sec.
|
||||||
if (fabs(pTaskEntry->inputQUsed - p->inputQUsed) <= DBL_EPSILON) {
|
if (fabs(pTaskEntry->inputQUsed - p->inputQUsed) <= DBL_EPSILON) {
|
||||||
|
@ -2996,6 +3075,8 @@ int32_t mndProcessStreamHb(SRpcMsg *pReq) {
|
||||||
|
|
||||||
if (p->checkpointFailed) {
|
if (p->checkpointFailed) {
|
||||||
checkpointFailed = p->checkpointFailed;
|
checkpointFailed = p->checkpointFailed;
|
||||||
|
streamId = p->id.streamId;
|
||||||
|
transId = p->chkpointTransId;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3034,9 +3115,8 @@ int32_t mndProcessStreamHb(SRpcMsg *pReq) {
|
||||||
|
|
||||||
if (allReady || snodeChanged) {
|
if (allReady || snodeChanged) {
|
||||||
// if the execInfo.activeCheckpoint == 0, the checkpoint is restoring from wal
|
// if the execInfo.activeCheckpoint == 0, the checkpoint is restoring from wal
|
||||||
mInfo("checkpointId:%" PRId64 " failed, issue task-reset trans to reset all tasks status",
|
mInfo("checkpointId:%" PRId64 " failed, issue task-reset trans to reset all tasks status", activeCheckpointId);
|
||||||
execInfo.activeCheckpoint);
|
mndResetStatusFromCheckpoint(pMnode, streamId, transId);
|
||||||
mndResetStatusFromCheckpoint(pMnode, activeCheckpointId);
|
|
||||||
} else {
|
} else {
|
||||||
mInfo("not all vgroups are ready, wait for next HB from stream tasks");
|
mInfo("not all vgroups are ready, wait for next HB from stream tasks");
|
||||||
}
|
}
|
||||||
|
|
|
@ -90,16 +90,20 @@ bool streamTransConflictOtherTrans(SMnode* pMnode, int64_t streamUid, const char
|
||||||
|
|
||||||
if (strcmp(tInfo.name, MND_STREAM_CHECKPOINT_NAME) == 0) {
|
if (strcmp(tInfo.name, MND_STREAM_CHECKPOINT_NAME) == 0) {
|
||||||
if (strcmp(pTransName, MND_STREAM_DROP_NAME) != 0) {
|
if (strcmp(pTransName, MND_STREAM_DROP_NAME) != 0) {
|
||||||
mWarn("conflict with other transId:%d streamUid:%" PRIx64 ", trans:%s", tInfo.transId, tInfo.streamUid,
|
mWarn("conflict with other transId:%d streamUid:0x%" PRIx64 ", trans:%s", tInfo.transId, tInfo.streamUid,
|
||||||
tInfo.name);
|
tInfo.name);
|
||||||
return true;
|
return true;
|
||||||
|
} else {
|
||||||
|
mDebug("not conflict with checkpoint trans, name:%s, continue create trans", pTransName);
|
||||||
}
|
}
|
||||||
} else if ((strcmp(tInfo.name, MND_STREAM_CREATE_NAME) == 0) ||
|
} else if ((strcmp(tInfo.name, MND_STREAM_CREATE_NAME) == 0) || (strcmp(tInfo.name, MND_STREAM_DROP_NAME) == 0) ||
|
||||||
(strcmp(tInfo.name, MND_STREAM_DROP_NAME) == 0)) {
|
(strcmp(tInfo.name, MND_STREAM_TASK_RESET_NAME) == 0)) {
|
||||||
mWarn("conflict with other transId:%d streamUid:%" PRIx64 ", trans:%s", tInfo.transId, tInfo.streamUid,
|
mWarn("conflict with other transId:%d streamUid:0x%" PRIx64 ", trans:%s", tInfo.transId, tInfo.streamUid,
|
||||||
tInfo.name);
|
tInfo.name);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
mDebug("stream:0x%"PRIx64" no conflict trans existed, continue create trans", streamUid);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (lock) {
|
if (lock) {
|
||||||
|
|
|
@ -1215,7 +1215,7 @@ int32_t mndDropSubByTopic(SMnode *pMnode, STrans *pTrans, const char *topicName)
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mndSetDropSubRedoLogs(pMnode, pTrans, pSub) < 0) {
|
if (mndSetDropSubCommitLogs(pMnode, pTrans, pSub) < 0) {
|
||||||
sdbRelease(pSdb, pSub);
|
sdbRelease(pSdb, pSub);
|
||||||
sdbCancelFetch(pSdb, pIter);
|
sdbCancelFetch(pSdb, pIter);
|
||||||
return -1;
|
return -1;
|
||||||
|
|
|
@ -180,7 +180,7 @@ int32_t mndProcessWriteMsg(SMnode *pMnode, SRpcMsg *pMsg, SFsmCbMeta *pMeta) {
|
||||||
goto _OUT;
|
goto _OUT;
|
||||||
}
|
}
|
||||||
|
|
||||||
mInfo("trans:%d, is proposed, saved:%d code:0x%x, apply index:%" PRId64 " term:%" PRIu64 " config:%" PRId64
|
mInfo("trans:%d, process sync proposal, saved:%d code:0x%x, apply index:%" PRId64 " term:%" PRIu64 " config:%" PRId64
|
||||||
" role:%s raw:%p sec:%d seq:%" PRId64,
|
" role:%s raw:%p sec:%d seq:%" PRId64,
|
||||||
transId, pMgmt->transId, pMeta->code, pMeta->index, pMeta->term, pMeta->lastConfigIndex, syncStr(pMeta->state),
|
transId, pMgmt->transId, pMeta->code, pMeta->index, pMeta->term, pMeta->lastConfigIndex, syncStr(pMeta->state),
|
||||||
pRaw, pMgmt->transSec, pMgmt->transSeq);
|
pRaw, pMgmt->transSec, pMgmt->transSeq);
|
||||||
|
@ -208,15 +208,11 @@ int32_t mndProcessWriteMsg(SMnode *pMnode, SRpcMsg *pMsg, SFsmCbMeta *pMeta) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pTrans->stage == TRN_STAGE_PREPARE) {
|
if (pTrans->stage == TRN_STAGE_PREPARE) {
|
||||||
bool continueExec = mndTransPerformPrepareStage(pMnode, pTrans);
|
bool continueExec = mndTransPerformPrepareStage(pMnode, pTrans, false);
|
||||||
if (!continueExec) goto _OUT;
|
if (!continueExec) goto _OUT;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pTrans->id != pMgmt->transId) {
|
mndTransRefresh(pMnode, pTrans);
|
||||||
mInfo("trans:%d, execute in mnode which not leader or sync timeout, createTime:%" PRId64 " saved trans:%d",
|
|
||||||
pTrans->id, pTrans->createdTime, pMgmt->transId);
|
|
||||||
mndTransRefresh(pMnode, pTrans);
|
|
||||||
}
|
|
||||||
|
|
||||||
sdbSetApplyInfo(pMnode->pSdb, pMeta->index, pMeta->term, pMeta->lastConfigIndex);
|
sdbSetApplyInfo(pMnode->pSdb, pMeta->index, pMeta->term, pMeta->lastConfigIndex);
|
||||||
sdbWriteFile(pMnode->pSdb, tsMndSdbWriteDelta);
|
sdbWriteFile(pMnode->pSdb, tsMndSdbWriteDelta);
|
||||||
|
@ -234,6 +230,7 @@ static int32_t mndPostMgmtCode(SMnode *pMnode, int32_t code) {
|
||||||
goto _OUT;
|
goto _OUT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int32_t transId = pMgmt->transId;
|
||||||
pMgmt->transId = 0;
|
pMgmt->transId = 0;
|
||||||
pMgmt->transSec = 0;
|
pMgmt->transSec = 0;
|
||||||
pMgmt->transSeq = 0;
|
pMgmt->transSeq = 0;
|
||||||
|
@ -241,9 +238,9 @@ static int32_t mndPostMgmtCode(SMnode *pMnode, int32_t code) {
|
||||||
tsem_post(&pMgmt->syncSem);
|
tsem_post(&pMgmt->syncSem);
|
||||||
|
|
||||||
if (pMgmt->errCode != 0) {
|
if (pMgmt->errCode != 0) {
|
||||||
mError("trans:%d, failed to propose since %s, post sem", pMgmt->transId, tstrerror(pMgmt->errCode));
|
mError("trans:%d, failed to propose since %s, post sem", transId, tstrerror(pMgmt->errCode));
|
||||||
} else {
|
} else {
|
||||||
mInfo("trans:%d, is proposed and post sem, seq:%" PRId64, pMgmt->transId, pMgmt->transSeq);
|
mInfo("trans:%d, is proposed and post sem, seq:%" PRId64, transId, pMgmt->transSeq);
|
||||||
}
|
}
|
||||||
|
|
||||||
_OUT:
|
_OUT:
|
||||||
|
@ -542,7 +539,7 @@ int32_t mndSyncPropose(SMnode *pMnode, SSdbRaw *pRaw, int32_t transId) {
|
||||||
taosThreadMutexLock(&pMgmt->lock);
|
taosThreadMutexLock(&pMgmt->lock);
|
||||||
pMgmt->errCode = 0;
|
pMgmt->errCode = 0;
|
||||||
|
|
||||||
if (pMgmt->transId != 0 /* && pMgmt->transId != transId*/) {
|
if (pMgmt->transId != 0) {
|
||||||
mError("trans:%d, can't be proposed since trans:%d already waiting for confirm", transId, pMgmt->transId);
|
mError("trans:%d, can't be proposed since trans:%d already waiting for confirm", transId, pMgmt->transId);
|
||||||
taosThreadMutexUnlock(&pMgmt->lock);
|
taosThreadMutexUnlock(&pMgmt->lock);
|
||||||
rpcFreeCont(req.pCont);
|
rpcFreeCont(req.pCont);
|
||||||
|
|
|
@ -36,21 +36,25 @@ static int32_t mndTransAppendLog(SArray *pArray, SSdbRaw *pRaw);
|
||||||
static int32_t mndTransAppendAction(SArray *pArray, STransAction *pAction);
|
static int32_t mndTransAppendAction(SArray *pArray, STransAction *pAction);
|
||||||
static void mndTransDropLogs(SArray *pArray);
|
static void mndTransDropLogs(SArray *pArray);
|
||||||
static void mndTransDropActions(SArray *pArray);
|
static void mndTransDropActions(SArray *pArray);
|
||||||
static int32_t mndTransExecuteActions(SMnode *pMnode, STrans *pTrans, SArray *pArray);
|
|
||||||
static int32_t mndTransExecuteRedoLogs(SMnode *pMnode, STrans *pTrans);
|
static int32_t mndTransExecuteActions(SMnode *pMnode, STrans *pTrans, SArray *pArray, bool topHalf);
|
||||||
static int32_t mndTransExecuteUndoLogs(SMnode *pMnode, STrans *pTrans);
|
static int32_t mndTransExecuteRedoLogs(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static int32_t mndTransExecuteRedoActions(SMnode *pMnode, STrans *pTrans);
|
static int32_t mndTransExecuteUndoLogs(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static int32_t mndTransExecuteUndoActions(SMnode *pMnode, STrans *pTrans);
|
static int32_t mndTransExecuteRedoActions(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static int32_t mndTransExecuteCommitActions(SMnode *pMnode, STrans *pTrans);
|
static int32_t mndTransExecuteUndoActions(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformRedoLogStage(SMnode *pMnode, STrans *pTrans);
|
static int32_t mndTransExecuteCommitActions(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformRedoActionStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformRedoLogStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformUndoLogStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformRedoActionStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformUndoActionStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformUndoLogStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformCommitActionStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformUndoActionStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformCommitStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformCommitActionStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformRollbackStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformCommitStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndTransPerformFinishStage(SMnode *pMnode, STrans *pTrans);
|
static bool mndTransPerformRollbackStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
static bool mndCannotExecuteTransAction(SMnode *pMnode) { return !pMnode->deploy && !mndIsLeader(pMnode); }
|
static bool mndTransPerformFinishStage(SMnode *pMnode, STrans *pTrans, bool topHalf);
|
||||||
|
|
||||||
|
static bool mndCannotExecuteTransAction(SMnode *pMnode, bool topHalf) {
|
||||||
|
return (!pMnode->deploy && !mndIsLeader(pMnode)) || !topHalf;
|
||||||
|
}
|
||||||
|
|
||||||
static void mndTransSendRpcRsp(SMnode *pMnode, STrans *pTrans);
|
static void mndTransSendRpcRsp(SMnode *pMnode, STrans *pTrans);
|
||||||
static int32_t mndProcessTransTimer(SRpcMsg *pReq);
|
static int32_t mndProcessTransTimer(SRpcMsg *pReq);
|
||||||
|
@ -1090,8 +1094,9 @@ static void mndTransResetActions(SMnode *pMnode, STrans *pTrans, SArray *pArray)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransWriteSingleLog(SMnode *pMnode, STrans *pTrans, STransAction *pAction) {
|
static int32_t mndTransWriteSingleLog(SMnode *pMnode, STrans *pTrans, STransAction *pAction, bool topHalf) {
|
||||||
if (pAction->rawWritten) return 0;
|
if (pAction->rawWritten) return 0;
|
||||||
|
if (topHalf) return TSDB_CODE_MND_TRANS_CTX_SWITCH;
|
||||||
|
|
||||||
int32_t code = sdbWriteWithoutFree(pMnode->pSdb, pAction->pRaw);
|
int32_t code = sdbWriteWithoutFree(pMnode->pSdb, pAction->pRaw);
|
||||||
if (code == 0 || terrno == TSDB_CODE_SDB_OBJ_NOT_THERE) {
|
if (code == 0 || terrno == TSDB_CODE_SDB_OBJ_NOT_THERE) {
|
||||||
|
@ -1112,9 +1117,9 @@ static int32_t mndTransWriteSingleLog(SMnode *pMnode, STrans *pTrans, STransActi
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransSendSingleMsg(SMnode *pMnode, STrans *pTrans, STransAction *pAction) {
|
static int32_t mndTransSendSingleMsg(SMnode *pMnode, STrans *pTrans, STransAction *pAction, bool topHalf) {
|
||||||
if (pAction->msgSent) return 0;
|
if (pAction->msgSent) return 0;
|
||||||
if (mndCannotExecuteTransAction(pMnode)) return -1;
|
if (mndCannotExecuteTransAction(pMnode, topHalf)) return TSDB_CODE_MND_TRANS_CTX_SWITCH;
|
||||||
|
|
||||||
int64_t signature = pTrans->id;
|
int64_t signature = pTrans->id;
|
||||||
signature = (signature << 32);
|
signature = (signature << 32);
|
||||||
|
@ -1159,7 +1164,8 @@ static int32_t mndTransSendSingleMsg(SMnode *pMnode, STrans *pTrans, STransActio
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecNullMsg(SMnode *pMnode, STrans *pTrans, STransAction *pAction) {
|
static int32_t mndTransExecNullMsg(SMnode *pMnode, STrans *pTrans, STransAction *pAction, bool topHalf) {
|
||||||
|
if (!topHalf) return TSDB_CODE_MND_TRANS_CTX_SWITCH;
|
||||||
pAction->rawWritten = 0;
|
pAction->rawWritten = 0;
|
||||||
pAction->errCode = 0;
|
pAction->errCode = 0;
|
||||||
mInfo("trans:%d, %s:%d confirm action executed", pTrans->id, mndTransStr(pAction->stage), pAction->id);
|
mInfo("trans:%d, %s:%d confirm action executed", pTrans->id, mndTransStr(pAction->stage), pAction->id);
|
||||||
|
@ -1168,34 +1174,39 @@ static int32_t mndTransExecNullMsg(SMnode *pMnode, STrans *pTrans, STransAction
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecSingleAction(SMnode *pMnode, STrans *pTrans, STransAction *pAction) {
|
static int32_t mndTransExecSingleAction(SMnode *pMnode, STrans *pTrans, STransAction *pAction, bool topHalf) {
|
||||||
if (pAction->actionType == TRANS_ACTION_RAW) {
|
if (pAction->actionType == TRANS_ACTION_RAW) {
|
||||||
return mndTransWriteSingleLog(pMnode, pTrans, pAction);
|
return mndTransWriteSingleLog(pMnode, pTrans, pAction, topHalf);
|
||||||
} else if (pAction->actionType == TRANS_ACTION_MSG) {
|
} else if (pAction->actionType == TRANS_ACTION_MSG) {
|
||||||
return mndTransSendSingleMsg(pMnode, pTrans, pAction);
|
return mndTransSendSingleMsg(pMnode, pTrans, pAction, topHalf);
|
||||||
} else {
|
} else {
|
||||||
return mndTransExecNullMsg(pMnode, pTrans, pAction);
|
return mndTransExecNullMsg(pMnode, pTrans, pAction, topHalf);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecSingleActions(SMnode *pMnode, STrans *pTrans, SArray *pArray) {
|
static int32_t mndTransExecSingleActions(SMnode *pMnode, STrans *pTrans, SArray *pArray, bool topHalf) {
|
||||||
int32_t numOfActions = taosArrayGetSize(pArray);
|
int32_t numOfActions = taosArrayGetSize(pArray);
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
|
|
||||||
for (int32_t action = 0; action < numOfActions; ++action) {
|
for (int32_t action = 0; action < numOfActions; ++action) {
|
||||||
STransAction *pAction = taosArrayGet(pArray, action);
|
STransAction *pAction = taosArrayGet(pArray, action);
|
||||||
code = mndTransExecSingleAction(pMnode, pTrans, pAction);
|
code = mndTransExecSingleAction(pMnode, pTrans, pAction, topHalf);
|
||||||
if (code != 0) break;
|
if (code != 0) {
|
||||||
|
mInfo("trans:%d, action:%d not executed since %s. numOfActions:%d", pTrans->id, action, tstrerror(code),
|
||||||
|
numOfActions);
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecuteActions(SMnode *pMnode, STrans *pTrans, SArray *pArray) {
|
static int32_t mndTransExecuteActions(SMnode *pMnode, STrans *pTrans, SArray *pArray, bool topHalf) {
|
||||||
int32_t numOfActions = taosArrayGetSize(pArray);
|
int32_t numOfActions = taosArrayGetSize(pArray);
|
||||||
|
int32_t code = 0;
|
||||||
if (numOfActions == 0) return 0;
|
if (numOfActions == 0) return 0;
|
||||||
|
|
||||||
if (mndTransExecSingleActions(pMnode, pTrans, pArray) != 0) {
|
if ((code = mndTransExecSingleActions(pMnode, pTrans, pArray, topHalf)) != 0) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1248,31 +1259,31 @@ static int32_t mndTransExecuteActions(SMnode *pMnode, STrans *pTrans, SArray *pA
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecuteRedoActions(SMnode *pMnode, STrans *pTrans) {
|
static int32_t mndTransExecuteRedoActions(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
int32_t code = mndTransExecuteActions(pMnode, pTrans, pTrans->redoActions);
|
int32_t code = mndTransExecuteActions(pMnode, pTrans, pTrans->redoActions, topHalf);
|
||||||
if (code != 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
|
if (code != 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
|
||||||
mError("failed to execute redoActions since:%s, code:0x%x", terrstr(), terrno);
|
mError("failed to execute redoActions since:%s, code:0x%x", terrstr(), terrno);
|
||||||
}
|
}
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecuteUndoActions(SMnode *pMnode, STrans *pTrans) {
|
static int32_t mndTransExecuteUndoActions(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
int32_t code = mndTransExecuteActions(pMnode, pTrans, pTrans->undoActions);
|
int32_t code = mndTransExecuteActions(pMnode, pTrans, pTrans->undoActions, topHalf);
|
||||||
if (code != 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
|
if (code != 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
|
||||||
mError("failed to execute undoActions since %s", terrstr());
|
mError("failed to execute undoActions since %s", terrstr());
|
||||||
}
|
}
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecuteCommitActions(SMnode *pMnode, STrans *pTrans) {
|
static int32_t mndTransExecuteCommitActions(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
int32_t code = mndTransExecuteActions(pMnode, pTrans, pTrans->commitActions);
|
int32_t code = mndTransExecuteActions(pMnode, pTrans, pTrans->commitActions, topHalf);
|
||||||
if (code != 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
|
if (code != 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
|
||||||
mError("failed to execute commitActions since %s", terrstr());
|
mError("failed to execute commitActions since %s", terrstr());
|
||||||
}
|
}
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t mndTransExecuteRedoActionsSerial(SMnode *pMnode, STrans *pTrans) {
|
static int32_t mndTransExecuteRedoActionsSerial(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
int32_t numOfActions = taosArrayGetSize(pTrans->redoActions);
|
int32_t numOfActions = taosArrayGetSize(pTrans->redoActions);
|
||||||
if (numOfActions == 0) return code;
|
if (numOfActions == 0) return code;
|
||||||
|
@ -1289,7 +1300,7 @@ static int32_t mndTransExecuteRedoActionsSerial(SMnode *pMnode, STrans *pTrans)
|
||||||
for (int32_t action = pTrans->redoActionPos; action < numOfActions; ++action) {
|
for (int32_t action = pTrans->redoActionPos; action < numOfActions; ++action) {
|
||||||
STransAction *pAction = taosArrayGet(pTrans->redoActions, pTrans->redoActionPos);
|
STransAction *pAction = taosArrayGet(pTrans->redoActions, pTrans->redoActionPos);
|
||||||
|
|
||||||
code = mndTransExecSingleAction(pMnode, pTrans, pAction);
|
code = mndTransExecSingleAction(pMnode, pTrans, pAction, topHalf);
|
||||||
if (code == 0) {
|
if (code == 0) {
|
||||||
if (pAction->msgSent) {
|
if (pAction->msgSent) {
|
||||||
if (pAction->msgReceived) {
|
if (pAction->msgReceived) {
|
||||||
|
@ -1317,14 +1328,16 @@ static int32_t mndTransExecuteRedoActionsSerial(SMnode *pMnode, STrans *pTrans)
|
||||||
}
|
}
|
||||||
mndSetTransLastAction(pTrans, pAction);
|
mndSetTransLastAction(pTrans, pAction);
|
||||||
|
|
||||||
if (mndCannotExecuteTransAction(pMnode)) break;
|
if (mndCannotExecuteTransAction(pMnode, topHalf)) break;
|
||||||
|
|
||||||
if (code == 0) {
|
if (code == 0) {
|
||||||
pTrans->code = 0;
|
pTrans->code = 0;
|
||||||
pTrans->redoActionPos++;
|
pTrans->redoActionPos++;
|
||||||
mInfo("trans:%d, %s:%d is executed and need sync to other mnodes", pTrans->id, mndTransStr(pAction->stage),
|
mInfo("trans:%d, %s:%d is executed and need sync to other mnodes", pTrans->id, mndTransStr(pAction->stage),
|
||||||
pAction->id);
|
pAction->id);
|
||||||
|
taosThreadMutexUnlock(&pTrans->mutex);
|
||||||
code = mndTransSync(pMnode, pTrans);
|
code = mndTransSync(pMnode, pTrans);
|
||||||
|
taosThreadMutexLock(&pTrans->mutex);
|
||||||
if (code != 0) {
|
if (code != 0) {
|
||||||
pTrans->redoActionPos--;
|
pTrans->redoActionPos--;
|
||||||
pTrans->code = terrno;
|
pTrans->code = terrno;
|
||||||
|
@ -1357,7 +1370,7 @@ static int32_t mndTransExecuteRedoActionsSerial(SMnode *pMnode, STrans *pTrans)
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool mndTransPerformPrepareStage(SMnode *pMnode, STrans *pTrans) {
|
bool mndTransPerformPrepareStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
|
|
||||||
|
@ -1368,7 +1381,7 @@ bool mndTransPerformPrepareStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
|
|
||||||
for (int32_t action = 0; action < numOfActions; ++action) {
|
for (int32_t action = 0; action < numOfActions; ++action) {
|
||||||
STransAction *pAction = taosArrayGet(pTrans->prepareActions, action);
|
STransAction *pAction = taosArrayGet(pTrans->prepareActions, action);
|
||||||
code = mndTransExecSingleAction(pMnode, pTrans, pAction);
|
code = mndTransExecSingleAction(pMnode, pTrans, pAction, topHalf);
|
||||||
if (code != 0) {
|
if (code != 0) {
|
||||||
mError("trans:%d, failed to execute prepare action:%d, numOfActions:%d", pTrans->id, action, numOfActions);
|
mError("trans:%d, failed to execute prepare action:%d, numOfActions:%d", pTrans->id, action, numOfActions);
|
||||||
return false;
|
return false;
|
||||||
|
@ -1381,17 +1394,17 @@ _OVER:
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformRedoActionStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformRedoActionStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
|
|
||||||
if (pTrans->exec == TRN_EXEC_SERIAL) {
|
if (pTrans->exec == TRN_EXEC_SERIAL) {
|
||||||
code = mndTransExecuteRedoActionsSerial(pMnode, pTrans);
|
code = mndTransExecuteRedoActionsSerial(pMnode, pTrans, topHalf);
|
||||||
} else {
|
} else {
|
||||||
code = mndTransExecuteRedoActions(pMnode, pTrans);
|
code = mndTransExecuteRedoActions(pMnode, pTrans, topHalf);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mndCannotExecuteTransAction(pMnode)) return false;
|
if (mndCannotExecuteTransAction(pMnode, topHalf)) return false;
|
||||||
terrno = code;
|
terrno = code;
|
||||||
|
|
||||||
if (code == 0) {
|
if (code == 0) {
|
||||||
|
@ -1431,8 +1444,8 @@ static bool mndTransPerformRedoActionStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformCommitStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformCommitStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
if (mndCannotExecuteTransAction(pMnode)) return false;
|
if (mndCannotExecuteTransAction(pMnode, topHalf)) return false;
|
||||||
|
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = mndTransCommit(pMnode, pTrans);
|
int32_t code = mndTransCommit(pMnode, pTrans);
|
||||||
|
@ -1452,9 +1465,9 @@ static bool mndTransPerformCommitStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformCommitActionStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformCommitActionStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = mndTransExecuteCommitActions(pMnode, pTrans);
|
int32_t code = mndTransExecuteCommitActions(pMnode, pTrans, topHalf);
|
||||||
|
|
||||||
if (code == 0) {
|
if (code == 0) {
|
||||||
pTrans->code = 0;
|
pTrans->code = 0;
|
||||||
|
@ -1471,9 +1484,9 @@ static bool mndTransPerformCommitActionStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformUndoActionStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformUndoActionStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = mndTransExecuteUndoActions(pMnode, pTrans);
|
int32_t code = mndTransExecuteUndoActions(pMnode, pTrans, topHalf);
|
||||||
|
|
||||||
if (code == 0) {
|
if (code == 0) {
|
||||||
pTrans->stage = TRN_STAGE_PRE_FINISH;
|
pTrans->stage = TRN_STAGE_PRE_FINISH;
|
||||||
|
@ -1491,8 +1504,8 @@ static bool mndTransPerformUndoActionStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformRollbackStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformRollbackStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
if (mndCannotExecuteTransAction(pMnode)) return false;
|
if (mndCannotExecuteTransAction(pMnode, topHalf)) return false;
|
||||||
|
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = mndTransRollback(pMnode, pTrans);
|
int32_t code = mndTransRollback(pMnode, pTrans);
|
||||||
|
@ -1510,8 +1523,8 @@ static bool mndTransPerformRollbackStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformPreFinishStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformPreFinishStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
if (mndCannotExecuteTransAction(pMnode)) return false;
|
if (mndCannotExecuteTransAction(pMnode, topHalf)) return false;
|
||||||
|
|
||||||
bool continueExec = true;
|
bool continueExec = true;
|
||||||
int32_t code = mndTransPreFinish(pMnode, pTrans);
|
int32_t code = mndTransPreFinish(pMnode, pTrans);
|
||||||
|
@ -1529,8 +1542,9 @@ static bool mndTransPerformPreFinishStage(SMnode *pMnode, STrans *pTrans) {
|
||||||
return continueExec;
|
return continueExec;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool mndTransPerformFinishStage(SMnode *pMnode, STrans *pTrans) {
|
static bool mndTransPerformFinishStage(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
bool continueExec = false;
|
bool continueExec = false;
|
||||||
|
if (topHalf) return continueExec;
|
||||||
|
|
||||||
SSdbRaw *pRaw = mndTransEncode(pTrans);
|
SSdbRaw *pRaw = mndTransEncode(pTrans);
|
||||||
if (pRaw == NULL) {
|
if (pRaw == NULL) {
|
||||||
|
@ -1558,43 +1572,28 @@ void mndTransExecuteImp(SMnode *pMnode, STrans *pTrans, bool topHalf) {
|
||||||
pTrans->lastExecTime = taosGetTimestampMs();
|
pTrans->lastExecTime = taosGetTimestampMs();
|
||||||
switch (pTrans->stage) {
|
switch (pTrans->stage) {
|
||||||
case TRN_STAGE_PREPARE:
|
case TRN_STAGE_PREPARE:
|
||||||
continueExec = mndTransPerformPrepareStage(pMnode, pTrans);
|
continueExec = mndTransPerformPrepareStage(pMnode, pTrans, topHalf);
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_REDO_ACTION:
|
case TRN_STAGE_REDO_ACTION:
|
||||||
continueExec = mndTransPerformRedoActionStage(pMnode, pTrans);
|
continueExec = mndTransPerformRedoActionStage(pMnode, pTrans, topHalf);
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_COMMIT:
|
case TRN_STAGE_COMMIT:
|
||||||
if (topHalf) {
|
continueExec = mndTransPerformCommitStage(pMnode, pTrans, topHalf);
|
||||||
continueExec = mndTransPerformCommitStage(pMnode, pTrans);
|
|
||||||
} else {
|
|
||||||
mInfo("trans:%d, can not commit since not leader", pTrans->id);
|
|
||||||
continueExec = false;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_COMMIT_ACTION:
|
case TRN_STAGE_COMMIT_ACTION:
|
||||||
continueExec = mndTransPerformCommitActionStage(pMnode, pTrans);
|
continueExec = mndTransPerformCommitActionStage(pMnode, pTrans, topHalf);
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_ROLLBACK:
|
case TRN_STAGE_ROLLBACK:
|
||||||
if (topHalf) {
|
continueExec = mndTransPerformRollbackStage(pMnode, pTrans, topHalf);
|
||||||
continueExec = mndTransPerformRollbackStage(pMnode, pTrans);
|
|
||||||
} else {
|
|
||||||
mInfo("trans:%d, can not rollback since not leader", pTrans->id);
|
|
||||||
continueExec = false;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_UNDO_ACTION:
|
case TRN_STAGE_UNDO_ACTION:
|
||||||
continueExec = mndTransPerformUndoActionStage(pMnode, pTrans);
|
continueExec = mndTransPerformUndoActionStage(pMnode, pTrans, topHalf);
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_PRE_FINISH:
|
case TRN_STAGE_PRE_FINISH:
|
||||||
if (topHalf) {
|
continueExec = mndTransPerformPreFinishStage(pMnode, pTrans, topHalf);
|
||||||
continueExec = mndTransPerformPreFinishStage(pMnode, pTrans);
|
|
||||||
} else {
|
|
||||||
mInfo("trans:%d, can not pre-finish since not leader", pTrans->id);
|
|
||||||
continueExec = false;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case TRN_STAGE_FINISH:
|
case TRN_STAGE_FINISH:
|
||||||
continueExec = mndTransPerformFinishStage(pMnode, pTrans);
|
continueExec = mndTransPerformFinishStage(pMnode, pTrans, topHalf);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
continueExec = false;
|
continueExec = false;
|
||||||
|
|
|
@ -19,26 +19,24 @@
|
||||||
#include "tqCommon.h"
|
#include "tqCommon.h"
|
||||||
#include "tuuid.h"
|
#include "tuuid.h"
|
||||||
|
|
||||||
#define sndError(...) \
|
// clang-format off
|
||||||
do { \
|
#define sndError(...) do { if (sndDebugFlag & DEBUG_ERROR) {taosPrintLog("SND ERROR ", DEBUG_ERROR, sndDebugFlag, __VA_ARGS__);}} while (0)
|
||||||
if (sndDebugFlag & DEBUG_ERROR) { \
|
#define sndInfo(...) do { if (sndDebugFlag & DEBUG_INFO) { taosPrintLog("SND INFO ", DEBUG_INFO, sndDebugFlag, __VA_ARGS__);}} while (0)
|
||||||
taosPrintLog("SND ERROR ", DEBUG_ERROR, sndDebugFlag, __VA_ARGS__); \
|
#define sndDebug(...) do { if (sndDebugFlag & DEBUG_DEBUG) { taosPrintLog("SND ", DEBUG_DEBUG, sndDebugFlag, __VA_ARGS__);}} while (0)
|
||||||
} \
|
// clang-format on
|
||||||
} while (0)
|
|
||||||
|
|
||||||
#define sndInfo(...) \
|
static STaskId replaceStreamTaskId(SStreamTask *pTask) {
|
||||||
do { \
|
ASSERT(pTask->info.fillHistory);
|
||||||
if (sndDebugFlag & DEBUG_INFO) { \
|
STaskId id = {.streamId = pTask->id.streamId, .taskId = pTask->id.taskId};
|
||||||
taosPrintLog("SND INFO ", DEBUG_INFO, sndDebugFlag, __VA_ARGS__); \
|
pTask->id.streamId = pTask->streamTaskId.streamId;
|
||||||
} \
|
pTask->id.taskId = pTask->streamTaskId.taskId;
|
||||||
} while (0)
|
return id;
|
||||||
|
}
|
||||||
#define sndDebug(...) \
|
static void restoreStreamTaskId(SStreamTask *pTask, STaskId *pId) {
|
||||||
do { \
|
ASSERT(pTask->info.fillHistory);
|
||||||
if (sndDebugFlag & DEBUG_DEBUG) { \
|
pTask->id.taskId = pId->taskId;
|
||||||
taosPrintLog("SND ", DEBUG_DEBUG, sndDebugFlag, __VA_ARGS__); \
|
pTask->id.streamId = pId->streamId;
|
||||||
} \
|
}
|
||||||
} while (0)
|
|
||||||
|
|
||||||
int32_t sndExpandTask(SSnode *pSnode, SStreamTask *pTask, int64_t nextProcessVer) {
|
int32_t sndExpandTask(SSnode *pSnode, SStreamTask *pTask, int64_t nextProcessVer) {
|
||||||
ASSERT(pTask->info.taskLevel == TASK_LEVEL__AGG && taosArrayGetSize(pTask->upstreamInfo.pList) != 0);
|
ASSERT(pTask->info.taskLevel == TASK_LEVEL__AGG && taosArrayGetSize(pTask->upstreamInfo.pList) != 0);
|
||||||
|
@ -50,16 +48,12 @@ int32_t sndExpandTask(SSnode *pSnode, SStreamTask *pTask, int64_t nextProcessVer
|
||||||
|
|
||||||
streamTaskOpenAllUpstreamInput(pTask);
|
streamTaskOpenAllUpstreamInput(pTask);
|
||||||
|
|
||||||
SStreamTask *pSateTask = pTask;
|
STaskId taskId = {0};
|
||||||
SStreamTask task = {0};
|
|
||||||
if (pTask->info.fillHistory) {
|
if (pTask->info.fillHistory) {
|
||||||
task.id.streamId = pTask->streamTaskId.streamId;
|
taskId = replaceStreamTaskId(pTask);
|
||||||
task.id.taskId = pTask->streamTaskId.taskId;
|
|
||||||
task.pMeta = pTask->pMeta;
|
|
||||||
pSateTask = &task;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pTask->pState = streamStateOpen(pSnode->path, pSateTask, false, -1, -1);
|
pTask->pState = streamStateOpen(pSnode->path, pTask, false, -1, -1);
|
||||||
if (pTask->pState == NULL) {
|
if (pTask->pState == NULL) {
|
||||||
sndError("s-task:%s failed to open state for task", pTask->id.idStr);
|
sndError("s-task:%s failed to open state for task", pTask->id.idStr);
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -67,6 +61,9 @@ int32_t sndExpandTask(SSnode *pSnode, SStreamTask *pTask, int64_t nextProcessVer
|
||||||
sndDebug("s-task:%s state:%p", pTask->id.idStr, pTask->pState);
|
sndDebug("s-task:%s state:%p", pTask->id.idStr, pTask->pState);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (pTask->info.fillHistory) {
|
||||||
|
restoreStreamTaskId(pTask, &taskId);
|
||||||
|
}
|
||||||
|
|
||||||
int32_t numOfVgroups = (int32_t)taosArrayGetSize(pTask->upstreamInfo.pList);
|
int32_t numOfVgroups = (int32_t)taosArrayGetSize(pTask->upstreamInfo.pList);
|
||||||
SReadHandle handle = {
|
SReadHandle handle = {
|
||||||
|
@ -90,8 +87,8 @@ int32_t sndExpandTask(SSnode *pSnode, SStreamTask *pTask, int64_t nextProcessVer
|
||||||
// checkpoint ver is the kept version, handled data should be the next version.
|
// checkpoint ver is the kept version, handled data should be the next version.
|
||||||
if (pTask->chkInfo.checkpointId != 0) {
|
if (pTask->chkInfo.checkpointId != 0) {
|
||||||
pTask->chkInfo.nextProcessVer = pTask->chkInfo.checkpointVer + 1;
|
pTask->chkInfo.nextProcessVer = pTask->chkInfo.checkpointVer + 1;
|
||||||
sndInfo("s-task:%s restore from the checkpointId:%" PRId64 " ver:%" PRId64 " nextProcessVer:%" PRId64, pTask->id.idStr,
|
sndInfo("s-task:%s restore from the checkpointId:%" PRId64 " ver:%" PRId64 " nextProcessVer:%" PRId64,
|
||||||
pChkInfo->checkpointId, pChkInfo->checkpointVer, pChkInfo->nextProcessVer);
|
pTask->id.idStr, pChkInfo->checkpointId, pChkInfo->checkpointVer, pChkInfo->nextProcessVer);
|
||||||
}
|
}
|
||||||
|
|
||||||
char *p = NULL;
|
char *p = NULL;
|
||||||
|
@ -99,18 +96,18 @@ int32_t sndExpandTask(SSnode *pSnode, SStreamTask *pTask, int64_t nextProcessVer
|
||||||
|
|
||||||
if (pTask->info.fillHistory) {
|
if (pTask->info.fillHistory) {
|
||||||
sndInfo("vgId:%d expand stream task, s-task:%s, checkpointId:%" PRId64 " checkpointVer:%" PRId64
|
sndInfo("vgId:%d expand stream task, s-task:%s, checkpointId:%" PRId64 " checkpointVer:%" PRId64
|
||||||
" nextProcessVer:%" PRId64
|
" nextProcessVer:%" PRId64
|
||||||
" child id:%d, level:%d, status:%s fill-history:%d, related stream task:0x%x trigger:%" PRId64 " ms",
|
" child id:%d, level:%d, status:%s fill-history:%d, related stream task:0x%x trigger:%" PRId64 " ms",
|
||||||
SNODE_HANDLE, pTask->id.idStr, pChkInfo->checkpointId, pChkInfo->checkpointVer, pChkInfo->nextProcessVer,
|
SNODE_HANDLE, pTask->id.idStr, pChkInfo->checkpointId, pChkInfo->checkpointVer, pChkInfo->nextProcessVer,
|
||||||
pTask->info.selfChildId, pTask->info.taskLevel, p, pTask->info.fillHistory,
|
pTask->info.selfChildId, pTask->info.taskLevel, p, pTask->info.fillHistory,
|
||||||
(int32_t)pTask->streamTaskId.taskId, pTask->info.triggerParam);
|
(int32_t)pTask->streamTaskId.taskId, pTask->info.triggerParam);
|
||||||
} else {
|
} else {
|
||||||
sndInfo("vgId:%d expand stream task, s-task:%s, checkpointId:%" PRId64 " checkpointVer:%" PRId64
|
sndInfo("vgId:%d expand stream task, s-task:%s, checkpointId:%" PRId64 " checkpointVer:%" PRId64
|
||||||
" nextProcessVer:%" PRId64
|
" nextProcessVer:%" PRId64
|
||||||
" child id:%d, level:%d, status:%s fill-history:%d, related fill-task:0x%x trigger:%" PRId64 " ms",
|
" child id:%d, level:%d, status:%s fill-history:%d, related fill-task:0x%x trigger:%" PRId64 " ms",
|
||||||
SNODE_HANDLE, pTask->id.idStr, pChkInfo->checkpointId, pChkInfo->checkpointVer, pChkInfo->nextProcessVer,
|
SNODE_HANDLE, pTask->id.idStr, pChkInfo->checkpointId, pChkInfo->checkpointVer, pChkInfo->nextProcessVer,
|
||||||
pTask->info.selfChildId, pTask->info.taskLevel, p, pTask->info.fillHistory,
|
pTask->info.selfChildId, pTask->info.taskLevel, p, pTask->info.fillHistory,
|
||||||
(int32_t)pTask->hTaskInfo.id.taskId, pTask->info.triggerParam);
|
(int32_t)pTask->hTaskInfo.id.taskId, pTask->info.triggerParam);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -128,7 +125,7 @@ SSnode *sndOpen(const char *path, const SSnodeOpt *pOption) {
|
||||||
}
|
}
|
||||||
|
|
||||||
pSnode->msgCb = pOption->msgCb;
|
pSnode->msgCb = pOption->msgCb;
|
||||||
pSnode->pMeta = streamMetaOpen(path, pSnode, (FTaskExpand *)sndExpandTask, SNODE_HANDLE, taosGetTimestampMs());
|
pSnode->pMeta = streamMetaOpen(path, pSnode, (FTaskExpand *)sndExpandTask, SNODE_HANDLE, taosGetTimestampMs(), tqStartTaskCompleteCallback);
|
||||||
if (pSnode->pMeta == NULL) {
|
if (pSnode->pMeta == NULL) {
|
||||||
terrno = TSDB_CODE_OUT_OF_MEMORY;
|
terrno = TSDB_CODE_OUT_OF_MEMORY;
|
||||||
goto FAIL;
|
goto FAIL;
|
||||||
|
@ -149,9 +146,9 @@ FAIL:
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t sndInit(SSnode * pSnode) {
|
int32_t sndInit(SSnode *pSnode) {
|
||||||
resetStreamTaskStatus(pSnode->pMeta);
|
tqStreamTaskResetStatus(pSnode->pMeta);
|
||||||
startStreamTasks(pSnode->pMeta);
|
streamMetaStartAllTasks(pSnode->pMeta);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -205,6 +202,8 @@ int32_t sndProcessWriteMsg(SSnode *pSnode, SRpcMsg *pMsg, SRpcMsg *pRsp) {
|
||||||
return tqStreamTaskProcessDropReq(pSnode->pMeta, pMsg->pCont, pMsg->contLen);
|
return tqStreamTaskProcessDropReq(pSnode->pMeta, pMsg->pCont, pMsg->contLen);
|
||||||
case TDMT_VND_STREAM_TASK_UPDATE:
|
case TDMT_VND_STREAM_TASK_UPDATE:
|
||||||
return tqStreamTaskProcessUpdateReq(pSnode->pMeta, &pSnode->msgCb, pMsg, true);
|
return tqStreamTaskProcessUpdateReq(pSnode->pMeta, &pSnode->msgCb, pMsg, true);
|
||||||
|
case TDMT_VND_STREAM_TASK_RESET:
|
||||||
|
return tqStreamTaskProcessTaskResetReq(pSnode->pMeta, pMsg);
|
||||||
default:
|
default:
|
||||||
ASSERT(0);
|
ASSERT(0);
|
||||||
}
|
}
|
||||||
|
|
|
@ -152,9 +152,6 @@ void tqSinkDataIntoDstTable(SStreamTask* pTask, void* vnode, void* data);
|
||||||
char* tqOffsetBuildFName(const char* path, int32_t fVer);
|
char* tqOffsetBuildFName(const char* path, int32_t fVer);
|
||||||
int32_t tqOffsetRestoreFromFile(STqOffsetStore* pStore, const char* fname);
|
int32_t tqOffsetRestoreFromFile(STqOffsetStore* pStore, const char* fname);
|
||||||
|
|
||||||
// tqStream
|
|
||||||
int32_t tqStopStreamTasks(STQ* pTq);
|
|
||||||
|
|
||||||
// tq util
|
// tq util
|
||||||
int32_t extractDelDataBlock(const void* pData, int32_t len, int64_t ver, void** pRefBlock, int32_t type);
|
int32_t extractDelDataBlock(const void* pData, int32_t len, int64_t ver, void** pRefBlock, int32_t type);
|
||||||
int32_t tqExtractDataForMq(STQ* pTq, STqHandle* pHandle, const SMqPollReq* pRequest, SRpcMsg* pMsg);
|
int32_t tqExtractDataForMq(STQ* pTq, STqHandle* pHandle, const SMqPollReq* pRequest, SRpcMsg* pMsg);
|
||||||
|
|
|
@ -232,6 +232,7 @@ int tqPushMsg(STQ*, tmsg_t msgType);
|
||||||
int tqRegisterPushHandle(STQ* pTq, void* handle, SRpcMsg* pMsg);
|
int tqRegisterPushHandle(STQ* pTq, void* handle, SRpcMsg* pMsg);
|
||||||
int tqUnregisterPushHandle(STQ* pTq, void* pHandle);
|
int tqUnregisterPushHandle(STQ* pTq, void* pHandle);
|
||||||
int tqScanWalAsync(STQ* pTq, bool ckPause);
|
int tqScanWalAsync(STQ* pTq, bool ckPause);
|
||||||
|
int32_t tqStopStreamTasksAsync(STQ* pTq);
|
||||||
int32_t tqProcessTaskCheckPointSourceReq(STQ* pTq, SRpcMsg* pMsg, SRpcMsg* pRsp);
|
int32_t tqProcessTaskCheckPointSourceReq(STQ* pTq, SRpcMsg* pMsg, SRpcMsg* pRsp);
|
||||||
int32_t tqProcessTaskCheckpointReadyMsg(STQ* pTq, SRpcMsg* pMsg);
|
int32_t tqProcessTaskCheckpointReadyMsg(STQ* pTq, SRpcMsg* pMsg);
|
||||||
int32_t tqProcessTaskUpdateReq(STQ* pTq, SRpcMsg* pMsg);
|
int32_t tqProcessTaskUpdateReq(STQ* pTq, SRpcMsg* pMsg);
|
||||||
|
|
|
@ -36,7 +36,6 @@ static int metaDeleteBtimeIdx(SMeta *pMeta, const SMetaEntry *pME);
|
||||||
static int metaUpdateNcolIdx(SMeta *pMeta, const SMetaEntry *pME);
|
static int metaUpdateNcolIdx(SMeta *pMeta, const SMetaEntry *pME);
|
||||||
static int metaDeleteNcolIdx(SMeta *pMeta, const SMetaEntry *pME);
|
static int metaDeleteNcolIdx(SMeta *pMeta, const SMetaEntry *pME);
|
||||||
|
|
||||||
|
|
||||||
static void metaGetEntryInfo(const SMetaEntry *pEntry, SMetaInfo *pInfo) {
|
static void metaGetEntryInfo(const SMetaEntry *pEntry, SMetaInfo *pInfo) {
|
||||||
pInfo->uid = pEntry->uid;
|
pInfo->uid = pEntry->uid;
|
||||||
pInfo->version = pEntry->version;
|
pInfo->version = pEntry->version;
|
||||||
|
@ -562,6 +561,7 @@ int metaAddIndexToSTable(SMeta *pMeta, int64_t version, SVCreateStbReq *pReq) {
|
||||||
tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
|
tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
|
||||||
metaULock(pMeta);
|
metaULock(pMeta);
|
||||||
metaDestroyTagIdxKey(pTagIdxKey);
|
metaDestroyTagIdxKey(pTagIdxKey);
|
||||||
|
pTagIdxKey = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
nStbEntry.version = version;
|
nStbEntry.version = version;
|
||||||
|
@ -692,6 +692,7 @@ int metaDropIndexFromSTable(SMeta *pMeta, int64_t version, SDropIndexReq *pReq)
|
||||||
tdbTbDelete(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, pMeta->txn);
|
tdbTbDelete(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, pMeta->txn);
|
||||||
metaULock(pMeta);
|
metaULock(pMeta);
|
||||||
metaDestroyTagIdxKey(pTagIdxKey);
|
metaDestroyTagIdxKey(pTagIdxKey);
|
||||||
|
pTagIdxKey = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// clear idx flag
|
// clear idx flag
|
||||||
|
@ -1076,7 +1077,7 @@ static int metaDeleteTtl(SMeta *pMeta, const SMetaEntry *pME) {
|
||||||
return ttlMgrDeleteTtl(pMeta->pTtlMgr, &ctx);
|
return ttlMgrDeleteTtl(pMeta->pTtlMgr, &ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int metaDropTableByUid(SMeta *pMeta, tb_uid_t uid, int *type, tb_uid_t *pSuid, int8_t* pSysTbl) {
|
static int metaDropTableByUid(SMeta *pMeta, tb_uid_t uid, int *type, tb_uid_t *pSuid, int8_t *pSysTbl) {
|
||||||
void *pData = NULL;
|
void *pData = NULL;
|
||||||
int nData = 0;
|
int nData = 0;
|
||||||
int rc = 0;
|
int rc = 0;
|
||||||
|
@ -1146,6 +1147,7 @@ static int metaDropTableByUid(SMeta *pMeta, tb_uid_t uid, int *type, tb_uid_t *p
|
||||||
tdbTbDelete(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, pMeta->txn);
|
tdbTbDelete(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, pMeta->txn);
|
||||||
}
|
}
|
||||||
metaDestroyTagIdxKey(pTagIdxKey);
|
metaDestroyTagIdxKey(pTagIdxKey);
|
||||||
|
pTagIdxKey = NULL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
tDecoderClear(&tdc);
|
tDecoderClear(&tdc);
|
||||||
|
@ -1865,6 +1867,7 @@ static int metaAddTagIndex(SMeta *pMeta, int64_t version, SVAlterTbReq *pAlterTb
|
||||||
}
|
}
|
||||||
tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
|
tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
|
||||||
metaDestroyTagIdxKey(pTagIdxKey);
|
metaDestroyTagIdxKey(pTagIdxKey);
|
||||||
|
pTagIdxKey = NULL;
|
||||||
}
|
}
|
||||||
tdbTbcClose(pCtbIdxc);
|
tdbTbcClose(pCtbIdxc);
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -2122,7 +2125,7 @@ int metaUpdateChangeTimeWithLock(SMeta *pMeta, tb_uid_t uid, int64_t changeTimeM
|
||||||
if (!tsTtlChangeOnWrite) return 0;
|
if (!tsTtlChangeOnWrite) return 0;
|
||||||
|
|
||||||
metaWLock(pMeta);
|
metaWLock(pMeta);
|
||||||
int ret = metaUpdateChangeTime(pMeta, uid, changeTimeMs);
|
int ret = metaUpdateChangeTime(pMeta, uid, changeTimeMs);
|
||||||
metaULock(pMeta);
|
metaULock(pMeta);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
@ -2228,15 +2231,14 @@ static int metaUpdateTagIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry) {
|
||||||
nTagData = tDataTypes[pTagColumn->type].bytes;
|
nTagData = tDataTypes[pTagColumn->type].bytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pTagData != NULL) {
|
if (metaCreateTagIdxKey(pCtbEntry->ctbEntry.suid, pTagColumn->colId, pTagData, nTagData, pTagColumn->type,
|
||||||
if (metaCreateTagIdxKey(pCtbEntry->ctbEntry.suid, pTagColumn->colId, pTagData, nTagData, pTagColumn->type,
|
pCtbEntry->uid, &pTagIdxKey, &nTagIdxKey) < 0) {
|
||||||
pCtbEntry->uid, &pTagIdxKey, &nTagIdxKey) < 0) {
|
ret = -1;
|
||||||
ret = -1;
|
goto end;
|
||||||
goto end;
|
|
||||||
}
|
|
||||||
tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
|
|
||||||
}
|
}
|
||||||
|
tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
|
||||||
metaDestroyTagIdxKey(pTagIdxKey);
|
metaDestroyTagIdxKey(pTagIdxKey);
|
||||||
|
pTagIdxKey = NULL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
end:
|
end:
|
||||||
|
|
|
@ -240,23 +240,23 @@ int32_t tdFetchTbUidList(SSma *pSma, STbUidStore **ppStore, tb_uid_t suid, tb_ui
|
||||||
|
|
||||||
static void tdRSmaTaskInit(SStreamMeta *pMeta, SRSmaInfoItem *pItem, SStreamTaskId *pId) {
|
static void tdRSmaTaskInit(SStreamMeta *pMeta, SRSmaInfoItem *pItem, SStreamTaskId *pId) {
|
||||||
STaskId id = {.streamId = pId->streamId, .taskId = pId->taskId};
|
STaskId id = {.streamId = pId->streamId, .taskId = pId->taskId};
|
||||||
taosRLockLatch(&pMeta->lock);
|
streamMetaRLock(pMeta);
|
||||||
SStreamTask **ppTask = (SStreamTask **)taosHashGet(pMeta->pTasksMap, &id, sizeof(id));
|
SStreamTask **ppTask = (SStreamTask **)taosHashGet(pMeta->pTasksMap, &id, sizeof(id));
|
||||||
if (ppTask && *ppTask) {
|
if (ppTask && *ppTask) {
|
||||||
pItem->submitReqVer = (*ppTask)->chkInfo.checkpointVer;
|
pItem->submitReqVer = (*ppTask)->chkInfo.checkpointVer;
|
||||||
pItem->fetchResultVer = (*ppTask)->info.triggerParam;
|
pItem->fetchResultVer = (*ppTask)->info.triggerParam;
|
||||||
}
|
}
|
||||||
taosRUnLockLatch(&pMeta->lock);
|
streamMetaRUnLock(pMeta);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void tdRSmaTaskRemove(SStreamMeta *pMeta, int64_t streamId, int32_t taskId) {
|
static void tdRSmaTaskRemove(SStreamMeta *pMeta, int64_t streamId, int32_t taskId) {
|
||||||
streamMetaUnregisterTask(pMeta, streamId, taskId);
|
streamMetaUnregisterTask(pMeta, streamId, taskId);
|
||||||
taosWLockLatch(&pMeta->lock);
|
streamMetaWLock(pMeta);
|
||||||
int32_t numOfTasks = streamMetaGetNumOfTasks(pMeta);
|
int32_t numOfTasks = streamMetaGetNumOfTasks(pMeta);
|
||||||
if (streamMetaCommit(pMeta) < 0) {
|
if (streamMetaCommit(pMeta) < 0) {
|
||||||
// persist to disk
|
// persist to disk
|
||||||
}
|
}
|
||||||
taosWUnLockLatch(&pMeta->lock);
|
streamMetaWUnLock(pMeta);
|
||||||
smaDebug("vgId:%d, rsma task:%" PRIi64 ",%d dropped, remain tasks:%d", pMeta->vgId, streamId, taskId, numOfTasks);
|
smaDebug("vgId:%d, rsma task:%" PRIi64 ",%d dropped, remain tasks:%d", pMeta->vgId, streamId, taskId, numOfTasks);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1301,14 +1301,14 @@ _checkpoint:
|
||||||
checkpointBuilt = true;
|
checkpointBuilt = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
taosWLockLatch(&pMeta->lock);
|
streamMetaWLock(pMeta);
|
||||||
if (streamMetaSaveTask(pMeta, pTask)) {
|
if (streamMetaSaveTask(pMeta, pTask)) {
|
||||||
taosWUnLockLatch(&pMeta->lock);
|
streamMetaWUnLock(pMeta);
|
||||||
code = terrno ? terrno : TSDB_CODE_OUT_OF_MEMORY;
|
code = terrno ? terrno : TSDB_CODE_OUT_OF_MEMORY;
|
||||||
taosHashCancelIterate(pInfoHash, infoHash);
|
taosHashCancelIterate(pInfoHash, infoHash);
|
||||||
TSDB_CHECK_CODE(code, lino, _exit);
|
TSDB_CHECK_CODE(code, lino, _exit);
|
||||||
}
|
}
|
||||||
taosWUnLockLatch(&pMeta->lock);
|
streamMetaWUnLock(pMeta);
|
||||||
smaDebug("vgId:%d, rsma commit, succeed to commit task:%p, submitReqVer:%" PRIi64 ", fetchResultVer:%" PRIi64
|
smaDebug("vgId:%d, rsma commit, succeed to commit task:%p, submitReqVer:%" PRIi64 ", fetchResultVer:%" PRIi64
|
||||||
", table:%" PRIi64 ", level:%d",
|
", table:%" PRIi64 ", level:%d",
|
||||||
TD_VID(pVnode), pTask, pItem->submitReqVer, pItem->fetchResultVer, pRSmaInfo->suid, i + 1);
|
TD_VID(pVnode), pTask, pItem->submitReqVer, pItem->fetchResultVer, pRSmaInfo->suid, i + 1);
|
||||||
|
@ -1316,13 +1316,13 @@ _checkpoint:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (pMeta) {
|
if (pMeta) {
|
||||||
taosWLockLatch(&pMeta->lock);
|
streamMetaWLock(pMeta);
|
||||||
if (streamMetaCommit(pMeta)) {
|
if (streamMetaCommit(pMeta)) {
|
||||||
taosWUnLockLatch(&pMeta->lock);
|
streamMetaWUnLock(pMeta);
|
||||||
code = terrno ? terrno : TSDB_CODE_OUT_OF_MEMORY;
|
code = terrno ? terrno : TSDB_CODE_OUT_OF_MEMORY;
|
||||||
TSDB_CHECK_CODE(code, lino, _exit);
|
TSDB_CHECK_CODE(code, lino, _exit);
|
||||||
}
|
}
|
||||||
taosWUnLockLatch(&pMeta->lock);
|
streamMetaWUnLock(pMeta);
|
||||||
}
|
}
|
||||||
if (checkpointBuilt) {
|
if (checkpointBuilt) {
|
||||||
smaInfo("vgId:%d, rsma commit, succeed to commit checkpoint:%" PRIi64, TD_VID(pVnode), checkpointId);
|
smaInfo("vgId:%d, rsma commit, succeed to commit checkpoint:%" PRIi64, TD_VID(pVnode), checkpointId);
|
||||||
|
|
|
@ -96,7 +96,8 @@ int32_t tqInitialize(STQ* pTq) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
pTq->pStreamMeta = streamMetaOpen(pTq->path, pTq, (FTaskExpand*)tqExpandTask, pTq->pVnode->config.vgId, -1);
|
int32_t vgId = TD_VID(pTq->pVnode);
|
||||||
|
pTq->pStreamMeta = streamMetaOpen(pTq->path, pTq, (FTaskExpand*)tqExpandTask, vgId, -1, tqStartTaskCompleteCallback);
|
||||||
if (pTq->pStreamMeta == NULL) {
|
if (pTq->pStreamMeta == NULL) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
@ -1070,10 +1071,12 @@ int32_t tqProcessTaskRunReq(STQ* pTq, SRpcMsg* pMsg) {
|
||||||
tqScanWal(pTq);
|
tqScanWal(pTq);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t code = tqStreamTaskProcessRunReq(pTq->pStreamMeta, pMsg, vnodeIsRoleLeader(pTq->pVnode));
|
int32_t code = tqStreamTaskProcessRunReq(pTq->pStreamMeta, pMsg, vnodeIsRoleLeader(pTq->pVnode));
|
||||||
if(code == 0 && taskId > 0){
|
if(code == 0 && taskId > 0){
|
||||||
tqScanWalAsync(pTq, false);
|
tqScanWalAsync(pTq, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1256,10 +1259,11 @@ int32_t tqProcessTaskCheckPointSourceReq(STQ* pTq, SRpcMsg* pMsg, SRpcMsg* pRsp)
|
||||||
if (pTask->status.downstreamReady != 1) {
|
if (pTask->status.downstreamReady != 1) {
|
||||||
pTask->chkInfo.failedId = req.checkpointId; // record the latest failed checkpoint id
|
pTask->chkInfo.failedId = req.checkpointId; // record the latest failed checkpoint id
|
||||||
pTask->chkInfo.checkpointingId = req.checkpointId;
|
pTask->chkInfo.checkpointingId = req.checkpointId;
|
||||||
|
pTask->chkInfo.transId = req.transId;
|
||||||
|
|
||||||
tqError("s-task:%s not ready for checkpoint, since downstream not ready, ignore this checkpoint:%" PRId64
|
tqError("s-task:%s not ready for checkpoint, since downstream not ready, ignore this checkpoint:%" PRId64
|
||||||
", set it failure",
|
", transId:%d set it failed",
|
||||||
pTask->id.idStr, req.checkpointId);
|
pTask->id.idStr, req.checkpointId, req.transId);
|
||||||
streamMetaReleaseTask(pMeta, pTask);
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
|
||||||
SRpcMsg rsp = {0};
|
SRpcMsg rsp = {0};
|
||||||
|
@ -1335,28 +1339,10 @@ int32_t tqProcessTaskUpdateReq(STQ* pTq, SRpcMsg* pMsg) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t tqProcessTaskResetReq(STQ* pTq, SRpcMsg* pMsg) {
|
int32_t tqProcessTaskResetReq(STQ* pTq, SRpcMsg* pMsg) {
|
||||||
SVPauseStreamTaskReq* pReq = (SVPauseStreamTaskReq*)pMsg->pCont;
|
return tqStreamTaskProcessTaskResetReq(pTq->pStreamMeta, pMsg);
|
||||||
|
|
||||||
SStreamMeta* pMeta = pTq->pStreamMeta;
|
|
||||||
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pReq->streamId, pReq->taskId);
|
|
||||||
if (pTask == NULL) {
|
|
||||||
tqError("vgId:%d process task-reset req, failed to acquire task:0x%x, it may have been dropped already",
|
|
||||||
pMeta->vgId, pReq->taskId);
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
tqDebug("s-task:%s receive task-reset msg from mnode, reset status and ready for data processing", pTask->id.idStr);
|
|
||||||
|
|
||||||
// clear flag set during do checkpoint, and open inputQ for all upstream tasks
|
|
||||||
if (streamTaskGetStatus(pTask, NULL) == TASK_STATUS__CK) {
|
|
||||||
streamTaskClearCheckInfo(pTask, true);
|
|
||||||
streamTaskSetStatusReady(pTask);
|
|
||||||
}
|
|
||||||
|
|
||||||
streamMetaReleaseTask(pMeta, pTask);
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// NOTE: here we may receive this message more than once, so need to handle this case
|
||||||
int32_t tqProcessTaskDropHTask(STQ* pTq, SRpcMsg* pMsg) {
|
int32_t tqProcessTaskDropHTask(STQ* pTq, SRpcMsg* pMsg) {
|
||||||
SVDropHTaskReq* pReq = (SVDropHTaskReq*)pMsg->pCont;
|
SVDropHTaskReq* pReq = (SVDropHTaskReq*)pMsg->pCont;
|
||||||
|
|
||||||
|
@ -1375,14 +1361,17 @@ int32_t tqProcessTaskDropHTask(STQ* pTq, SRpcMsg* pMsg) {
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
taosThreadMutexLock(&pTask->lock);
|
||||||
ETaskStatus status = streamTaskGetStatus(pTask, NULL);
|
ETaskStatus status = streamTaskGetStatus(pTask, NULL);
|
||||||
ASSERT(status == TASK_STATUS__STREAM_SCAN_HISTORY);
|
if (status == TASK_STATUS__STREAM_SCAN_HISTORY) {
|
||||||
|
streamTaskHandleEvent(pTask->status.pSM, TASK_EVENT_SCANHIST_DONE);
|
||||||
streamTaskHandleEvent(pTask->status.pSM, TASK_EVENT_SCANHIST_DONE);
|
}
|
||||||
|
|
||||||
SStreamTaskId id = {.streamId = pTask->hTaskInfo.id.streamId, .taskId = pTask->hTaskInfo.id.taskId};
|
SStreamTaskId id = {.streamId = pTask->hTaskInfo.id.streamId, .taskId = pTask->hTaskInfo.id.taskId};
|
||||||
streamBuildAndSendDropTaskMsg(pTask->pMsgCb, pMeta->vgId, &id);
|
streamBuildAndSendDropTaskMsg(pTask->pMsgCb, pMeta->vgId, &id);
|
||||||
|
|
||||||
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
|
||||||
// clear the scheduler status
|
// clear the scheduler status
|
||||||
streamTaskSetSchedStatusInactive(pTask);
|
streamTaskSetSchedStatusInactive(pTask);
|
||||||
tqDebug("s-task:%s set scheduler status:%d after drop fill-history task", pTask->id.idStr, pTask->status.schedStatus);
|
tqDebug("s-task:%s set scheduler status:%d after drop fill-history task", pTask->id.idStr, pTask->status.schedStatus);
|
||||||
|
|
|
@ -109,8 +109,8 @@ int32_t tqScanWalAsync(STQ* pTq, bool ckPause) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
tqDebug("vgId:%d create msg to start wal scan to launch stream tasks, numOfTasks:%d, restored:%d", vgId, numOfTasks,
|
tqDebug("vgId:%d create msg to start wal scan to launch stream tasks, numOfTasks:%d, vnd restored:%d", vgId,
|
||||||
alreadyRestored);
|
numOfTasks, alreadyRestored);
|
||||||
|
|
||||||
pRunReq->head.vgId = vgId;
|
pRunReq->head.vgId = vgId;
|
||||||
pRunReq->streamId = 0;
|
pRunReq->streamId = 0;
|
||||||
|
@ -123,33 +123,25 @@ int32_t tqScanWalAsync(STQ* pTq, bool ckPause) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t tqStopStreamTasks(STQ* pTq) {
|
int32_t tqStopStreamTasksAsync(STQ* pTq) {
|
||||||
SStreamMeta* pMeta = pTq->pStreamMeta;
|
SStreamMeta* pMeta = pTq->pStreamMeta;
|
||||||
int32_t vgId = TD_VID(pTq->pVnode);
|
int32_t vgId = pMeta->vgId;
|
||||||
int32_t numOfTasks = taosArrayGetSize(pMeta->pTaskList);
|
|
||||||
|
|
||||||
tqDebug("vgId:%d stop all %d stream task(s)", vgId, numOfTasks);
|
SStreamTaskRunReq* pRunReq = rpcMallocCont(sizeof(SStreamTaskRunReq));
|
||||||
if (numOfTasks == 0) {
|
if (pRunReq == NULL) {
|
||||||
return TSDB_CODE_SUCCESS;
|
terrno = TSDB_CODE_OUT_OF_MEMORY;
|
||||||
|
tqError("vgId:%d failed to create msg to stop tasks, code:%s", vgId, terrstr());
|
||||||
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
SArray* pTaskList = NULL;
|
tqDebug("vgId:%d create msg to stop tasks", vgId);
|
||||||
streamMetaWLock(pMeta);
|
|
||||||
pTaskList = taosArrayDup(pMeta->pTaskList, NULL);
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
|
|
||||||
for (int32_t i = 0; i < numOfTasks; ++i) {
|
pRunReq->head.vgId = vgId;
|
||||||
SStreamTaskId* pTaskId = taosArrayGet(pTaskList, i);
|
pRunReq->streamId = 0;
|
||||||
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pTaskId->streamId, pTaskId->taskId);
|
pRunReq->taskId = STREAM_EXEC_STOP_ALL_TASKS_ID;
|
||||||
if (pTask == NULL) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
streamTaskStop(pTask);
|
SRpcMsg msg = {.msgType = TDMT_STREAM_TASK_RUN, .pCont = pRunReq, .contLen = sizeof(SStreamTaskRunReq)};
|
||||||
streamMetaReleaseTask(pMeta, pTask);
|
tmsgPutToQueue(&pTq->pVnode->msgCb, STREAM_QUEUE, &msg);
|
||||||
}
|
|
||||||
|
|
||||||
taosArrayDestroy(pTaskList);
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -196,7 +196,7 @@ int32_t streamTaskSnapWriterClose(SStreamTaskWriter* pWriter, int8_t rollback) {
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
STQ* pTq = pWriter->pTq;
|
STQ* pTq = pWriter->pTq;
|
||||||
|
|
||||||
taosWLockLatch(&pTq->pStreamMeta->lock);
|
streamMetaWLock(pTq->pStreamMeta);
|
||||||
tqDebug("vgId:%d, vnode stream-task snapshot writer closed", TD_VID(pTq->pVnode));
|
tqDebug("vgId:%d, vnode stream-task snapshot writer closed", TD_VID(pTq->pVnode));
|
||||||
if (rollback) {
|
if (rollback) {
|
||||||
tdbAbort(pTq->pStreamMeta->db, pTq->pStreamMeta->txn);
|
tdbAbort(pTq->pStreamMeta->db, pTq->pStreamMeta->txn);
|
||||||
|
@ -212,14 +212,14 @@ int32_t streamTaskSnapWriterClose(SStreamTaskWriter* pWriter, int8_t rollback) {
|
||||||
taosMemoryFree(pWriter);
|
taosMemoryFree(pWriter);
|
||||||
goto _err;
|
goto _err;
|
||||||
}
|
}
|
||||||
taosWUnLockLatch(&pTq->pStreamMeta->lock);
|
streamMetaWUnLock(pTq->pStreamMeta);
|
||||||
taosMemoryFree(pWriter);
|
taosMemoryFree(pWriter);
|
||||||
return code;
|
return code;
|
||||||
|
|
||||||
_err:
|
_err:
|
||||||
tqError("vgId:%d, vnode stream-task snapshot writer failed to close since %s", TD_VID(pWriter->pTq->pVnode),
|
tqError("vgId:%d, vnode stream-task snapshot writer failed to close since %s", TD_VID(pWriter->pTq->pVnode),
|
||||||
tstrerror(code));
|
tstrerror(code));
|
||||||
taosWUnLockLatch(&pTq->pStreamMeta->lock);
|
streamMetaWUnLock(pTq->pStreamMeta);
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -240,13 +240,13 @@ int32_t streamTaskSnapWrite(SStreamTaskWriter* pWriter, uint8_t* pData, uint32_t
|
||||||
tDecoderClear(&decoder);
|
tDecoderClear(&decoder);
|
||||||
|
|
||||||
int64_t key[2] = {taskId.streamId, taskId.taskId};
|
int64_t key[2] = {taskId.streamId, taskId.taskId};
|
||||||
taosWLockLatch(&pTq->pStreamMeta->lock);
|
streamMetaWLock(pTq->pStreamMeta);
|
||||||
if (tdbTbUpsert(pTq->pStreamMeta->pTaskDb, key, sizeof(int64_t) << 1, (uint8_t*)pData + sizeof(SSnapDataHdr),
|
if (tdbTbUpsert(pTq->pStreamMeta->pTaskDb, key, sizeof(int64_t) << 1, (uint8_t*)pData + sizeof(SSnapDataHdr),
|
||||||
nData - sizeof(SSnapDataHdr), pTq->pStreamMeta->txn) < 0) {
|
nData - sizeof(SSnapDataHdr), pTq->pStreamMeta->txn) < 0) {
|
||||||
taosWUnLockLatch(&pTq->pStreamMeta->lock);
|
streamMetaWUnLock(pTq->pStreamMeta);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
taosWUnLockLatch(&pTq->pStreamMeta->lock);
|
streamMetaWUnLock(pTq->pStreamMeta);
|
||||||
} else if (pHdr->type == SNAP_DATA_STREAM_TASK_CHECKPOINT) {
|
} else if (pHdr->type == SNAP_DATA_STREAM_TASK_CHECKPOINT) {
|
||||||
// do nothing
|
// do nothing
|
||||||
}
|
}
|
||||||
|
|
|
@ -35,20 +35,8 @@ int32_t tqInitDataRsp(SMqDataRsp* pRsp, STqOffsetVal pOffset) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void tqUpdateNodeStage(STQ* pTq, bool isLeader) {
|
void tqUpdateNodeStage(STQ* pTq, bool isLeader) {
|
||||||
SSyncState state = syncGetState(pTq->pVnode->sync);
|
SSyncState state = syncGetState(pTq->pVnode->sync);
|
||||||
SStreamMeta* pMeta = pTq->pStreamMeta;
|
streamMetaUpdateStageRole(pTq->pStreamMeta, state.term, isLeader);
|
||||||
int64_t stage = pMeta->stage;
|
|
||||||
|
|
||||||
pMeta->stage = state.term;
|
|
||||||
pMeta->role = (isLeader)? NODE_ROLE_LEADER:NODE_ROLE_FOLLOWER;
|
|
||||||
if (isLeader) {
|
|
||||||
tqInfo("vgId:%d update meta stage:%" PRId64 ", prev:%" PRId64 " leader:%d, start to send Hb", pMeta->vgId,
|
|
||||||
state.term, stage, isLeader);
|
|
||||||
streamMetaStartHb(pMeta);
|
|
||||||
} else {
|
|
||||||
tqInfo("vgId:%d update meta stage:%" PRId64 " prev:%" PRId64 " leader:%d", pMeta->vgId, state.term, stage,
|
|
||||||
isLeader);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t tqInitTaosxRsp(STaosxRsp* pRsp, STqOffsetVal pOffset) {
|
static int32_t tqInitTaosxRsp(STaosxRsp* pRsp, STqOffsetVal pOffset) {
|
||||||
|
|
|
@ -106,14 +106,15 @@ int32_t tqStreamTaskProcessUpdateReq(SStreamMeta* pMeta, SMsgCb* cb, SRpcMsg* pM
|
||||||
return rsp.code;
|
return rsp.code;
|
||||||
}
|
}
|
||||||
|
|
||||||
streamMetaWUnLock(pMeta);
|
// streamMetaWUnLock(pMeta);
|
||||||
|
|
||||||
|
// todo for test purpose
|
||||||
// the following two functions should not be executed within the scope of meta lock to avoid deadlock
|
// the following two functions should not be executed within the scope of meta lock to avoid deadlock
|
||||||
streamTaskUpdateEpsetInfo(pTask, req.pNodeList);
|
streamTaskUpdateEpsetInfo(pTask, req.pNodeList);
|
||||||
streamTaskResetStatus(pTask);
|
streamTaskResetStatus(pTask);
|
||||||
|
|
||||||
// continue after lock the meta again
|
// continue after lock the meta again
|
||||||
streamMetaWLock(pMeta);
|
// streamMetaWLock(pMeta);
|
||||||
|
|
||||||
SStreamTask** ppHTask = NULL;
|
SStreamTask** ppHTask = NULL;
|
||||||
if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
||||||
|
@ -166,65 +167,17 @@ int32_t tqStreamTaskProcessUpdateReq(SStreamMeta* pMeta, SMsgCb* cb, SRpcMsg* pM
|
||||||
streamMetaWUnLock(pMeta);
|
streamMetaWUnLock(pMeta);
|
||||||
} else {
|
} else {
|
||||||
if (!restored) {
|
if (!restored) {
|
||||||
tqDebug("vgId:%d vnode restore not completed, not restart the tasks, clear the start after nodeUpdate flag",
|
tqDebug("vgId:%d vnode restore not completed, not start the tasks, clear the start after nodeUpdate flag", vgId);
|
||||||
vgId);
|
|
||||||
pMeta->startInfo.tasksWillRestart = 0;
|
pMeta->startInfo.tasksWillRestart = 0;
|
||||||
streamMetaWUnLock(pMeta);
|
streamMetaWUnLock(pMeta);
|
||||||
} else {
|
} else {
|
||||||
tqDebug("vgId:%d all %d task(s) nodeEp updated and closed", vgId, numOfTasks);
|
tqDebug("vgId:%d all %d task(s) nodeEp updated and closed", vgId, numOfTasks);
|
||||||
#if 1
|
#if 0
|
||||||
|
// for test purpose, to trigger the leader election
|
||||||
|
taosMSleep(5000);
|
||||||
|
#endif
|
||||||
tqStreamTaskStartAsync(pMeta, cb, true);
|
tqStreamTaskStartAsync(pMeta, cb, true);
|
||||||
streamMetaWUnLock(pMeta);
|
streamMetaWUnLock(pMeta);
|
||||||
#else
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
|
|
||||||
// For debug purpose.
|
|
||||||
// the following procedure consume many CPU resource, result in the re-election of leader
|
|
||||||
// with high probability. So we employ it as a test case for the stream processing framework, with
|
|
||||||
// checkpoint/restart/nodeUpdate etc.
|
|
||||||
while (1) {
|
|
||||||
int32_t startVal = atomic_val_compare_exchange_32(&pMeta->startInfo.taskStarting, 0, 1);
|
|
||||||
if (startVal == 0) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
tqDebug("vgId:%d in start stream tasks procedure, wait for 500ms and recheck", vgId);
|
|
||||||
taosMsleep(500);
|
|
||||||
}
|
|
||||||
|
|
||||||
while (streamMetaTaskInTimer(pMeta)) {
|
|
||||||
tqDebug("vgId:%d some tasks in timer, wait for 100ms and recheck", pMeta->vgId);
|
|
||||||
taosMsleep(100);
|
|
||||||
}
|
|
||||||
|
|
||||||
streamMetaWLock(pMeta);
|
|
||||||
|
|
||||||
int32_t code = streamMetaReopen(pMeta);
|
|
||||||
if (code != 0) {
|
|
||||||
tqError("vgId:%d failed to reopen stream meta", vgId);
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
taosArrayDestroy(req.pNodeList);
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
streamMetaInitBackend(pMeta);
|
|
||||||
|
|
||||||
if (streamMetaLoadAllTasks(pTq->pStreamMeta) < 0) {
|
|
||||||
tqError("vgId:%d failed to load stream tasks", vgId);
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
taosArrayDestroy(req.pNodeList);
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (vnodeIsRoleLeader(pTq->pVnode) && !tsDisableStream) {
|
|
||||||
tqInfo("vgId:%d start all stream tasks after all being updated", vgId);
|
|
||||||
resetStreamTaskStatus(pTq->pStreamMeta);
|
|
||||||
tqStartStreamTaskAsync(pTq, false);
|
|
||||||
} else {
|
|
||||||
tqInfo("vgId:%d, follower node not start stream tasks", vgId);
|
|
||||||
}
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -645,65 +598,7 @@ int32_t tqStreamTaskProcessDropReq(SStreamMeta* pMeta, char* msg, int32_t msgLen
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t startStreamTasks(SStreamMeta* pMeta) {
|
int32_t tqStreamTaskResetStatus(SStreamMeta* pMeta) {
|
||||||
int32_t code = TSDB_CODE_SUCCESS;
|
|
||||||
int32_t vgId = pMeta->vgId;
|
|
||||||
|
|
||||||
int32_t numOfTasks = taosArrayGetSize(pMeta->pTaskList);
|
|
||||||
tqDebug("vgId:%d start to check all %d stream task(s) downstream status", vgId, numOfTasks);
|
|
||||||
if (numOfTasks == 0) {
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
SArray* pTaskList = NULL;
|
|
||||||
streamMetaWLock(pMeta);
|
|
||||||
pTaskList = taosArrayDup(pMeta->pTaskList, NULL);
|
|
||||||
taosHashClear(pMeta->startInfo.pReadyTaskSet);
|
|
||||||
taosHashClear(pMeta->startInfo.pFailedTaskSet);
|
|
||||||
pMeta->startInfo.startTs = taosGetTimestampMs();
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
|
|
||||||
// broadcast the check downstream tasks msg
|
|
||||||
for (int32_t i = 0; i < numOfTasks; ++i) {
|
|
||||||
SStreamTaskId* pTaskId = taosArrayGet(pTaskList, i);
|
|
||||||
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pTaskId->streamId, pTaskId->taskId);
|
|
||||||
if (pTask == NULL) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
// fill-history task can only be launched by related stream tasks.
|
|
||||||
if (pTask->info.fillHistory == 1) {
|
|
||||||
streamMetaReleaseTask(pMeta, pTask);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (pTask->status.downstreamReady == 1) {
|
|
||||||
if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
|
||||||
tqDebug("s-task:%s downstream ready, no need to check downstream, check only related fill-history task",
|
|
||||||
pTask->id.idStr);
|
|
||||||
streamLaunchFillHistoryTask(pTask);
|
|
||||||
}
|
|
||||||
|
|
||||||
streamMetaUpdateTaskDownstreamStatus(pTask->pMeta, pTask->id.streamId, pTask->id.taskId, pTask->execInfo.init,
|
|
||||||
pTask->execInfo.start, true);
|
|
||||||
streamMetaReleaseTask(pMeta, pTask);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
EStreamTaskEvent event = (HAS_RELATED_FILLHISTORY_TASK(pTask)) ? TASK_EVENT_INIT_STREAM_SCANHIST : TASK_EVENT_INIT;
|
|
||||||
int32_t ret = streamTaskHandleEvent(pTask->status.pSM, event);
|
|
||||||
if (ret != TSDB_CODE_SUCCESS) {
|
|
||||||
code = ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
streamMetaReleaseTask(pMeta, pTask);
|
|
||||||
}
|
|
||||||
|
|
||||||
taosArrayDestroy(pTaskList);
|
|
||||||
return code;
|
|
||||||
}
|
|
||||||
|
|
||||||
int32_t resetStreamTaskStatus(SStreamMeta* pMeta) {
|
|
||||||
int32_t vgId = pMeta->vgId;
|
int32_t vgId = pMeta->vgId;
|
||||||
int32_t numOfTasks = taosArrayGetSize(pMeta->pTaskList);
|
int32_t numOfTasks = taosArrayGetSize(pMeta->pTaskList);
|
||||||
|
|
||||||
|
@ -728,16 +623,18 @@ static int32_t restartStreamTasks(SStreamMeta* pMeta, bool isLeader) {
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
int64_t st = taosGetTimestampMs();
|
int64_t st = taosGetTimestampMs();
|
||||||
|
|
||||||
while (1) {
|
streamMetaWLock(pMeta);
|
||||||
int32_t startVal = atomic_val_compare_exchange_32(&pMeta->startInfo.taskStarting, 0, 1);
|
if (pMeta->startInfo.taskStarting == 1) {
|
||||||
if (startVal == 0) {
|
pMeta->startInfo.restartCount += 1;
|
||||||
break;
|
tqDebug("vgId:%d in start tasks procedure, inc restartCounter by 1, remaining restart:%d", vgId,
|
||||||
}
|
pMeta->startInfo.restartCount);
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
tqDebug("vgId:%d in start stream tasks procedure, wait for 500ms and recheck", vgId);
|
return TSDB_CODE_SUCCESS;
|
||||||
taosMsleep(500);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pMeta->startInfo.taskStarting = 1;
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
|
|
||||||
terrno = 0;
|
terrno = 0;
|
||||||
tqInfo("vgId:%d tasks are all updated and stopped, restart all tasks, triggered by transId:%d", vgId,
|
tqInfo("vgId:%d tasks are all updated and stopped, restart all tasks, triggered by transId:%d", vgId,
|
||||||
pMeta->updateInfo.transId);
|
pMeta->updateInfo.transId);
|
||||||
|
@ -762,11 +659,9 @@ static int32_t restartStreamTasks(SStreamMeta* pMeta, bool isLeader) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isLeader && !tsDisableStream) {
|
if (isLeader && !tsDisableStream) {
|
||||||
resetStreamTaskStatus(pMeta);
|
tqStreamTaskResetStatus(pMeta);
|
||||||
streamMetaWUnLock(pMeta);
|
streamMetaWUnLock(pMeta);
|
||||||
tqInfo("vgId:%d restart all stream tasks after all tasks being updated", vgId);
|
streamMetaStartAllTasks(pMeta);
|
||||||
|
|
||||||
startStreamTasks(pMeta);
|
|
||||||
} else {
|
} else {
|
||||||
streamMetaResetStartInfo(&pMeta->startInfo);
|
streamMetaResetStartInfo(&pMeta->startInfo);
|
||||||
streamMetaWUnLock(pMeta);
|
streamMetaWUnLock(pMeta);
|
||||||
|
@ -784,11 +679,14 @@ int32_t tqStreamTaskProcessRunReq(SStreamMeta* pMeta, SRpcMsg* pMsg, bool isLead
|
||||||
int32_t vgId = pMeta->vgId;
|
int32_t vgId = pMeta->vgId;
|
||||||
|
|
||||||
if (taskId == STREAM_EXEC_START_ALL_TASKS_ID) {
|
if (taskId == STREAM_EXEC_START_ALL_TASKS_ID) {
|
||||||
startStreamTasks(pMeta);
|
streamMetaStartAllTasks(pMeta);
|
||||||
return 0;
|
return 0;
|
||||||
} else if (taskId == STREAM_EXEC_RESTART_ALL_TASKS_ID) {
|
} else if (taskId == STREAM_EXEC_RESTART_ALL_TASKS_ID) {
|
||||||
restartStreamTasks(pMeta, isLeader);
|
restartStreamTasks(pMeta, isLeader);
|
||||||
return 0;
|
return 0;
|
||||||
|
} else if (taskId == STREAM_EXEC_STOP_ALL_TASKS_ID) {
|
||||||
|
streamMetaStopAllTasks(pMeta);
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pReq->streamId, taskId);
|
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pReq->streamId, taskId);
|
||||||
|
@ -812,3 +710,46 @@ int32_t tqStreamTaskProcessRunReq(SStreamMeta* pMeta, SRpcMsg* pMsg, bool isLead
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int32_t tqStartTaskCompleteCallback(SStreamMeta* pMeta) {
|
||||||
|
STaskStartInfo* pStartInfo = &pMeta->startInfo;
|
||||||
|
streamMetaWLock(pMeta);
|
||||||
|
|
||||||
|
if (pStartInfo->restartCount > 0) {
|
||||||
|
pStartInfo->restartCount -= 1;
|
||||||
|
|
||||||
|
ASSERT(pStartInfo->taskStarting == 0);
|
||||||
|
tqDebug("vgId:%d role:%d need to restart all tasks again, restartCounter:%d", pMeta->vgId, pMeta->role,
|
||||||
|
pStartInfo->restartCount);
|
||||||
|
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
|
restartStreamTasks(pMeta, (pMeta->role == NODE_ROLE_LEADER));
|
||||||
|
} else {
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
|
tqDebug("vgId:%d start all tasks completed", pMeta->vgId);
|
||||||
|
}
|
||||||
|
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t tqStreamTaskProcessTaskResetReq(SStreamMeta* pMeta, SRpcMsg* pMsg) {
|
||||||
|
SVPauseStreamTaskReq* pReq = (SVPauseStreamTaskReq*)pMsg->pCont;
|
||||||
|
|
||||||
|
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pReq->streamId, pReq->taskId);
|
||||||
|
if (pTask == NULL) {
|
||||||
|
tqError("vgId:%d process task-reset req, failed to acquire task:0x%x, it may have been dropped already",
|
||||||
|
pMeta->vgId, pReq->taskId);
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
tqDebug("s-task:%s receive task-reset msg from mnode, reset status and ready for data processing", pTask->id.idStr);
|
||||||
|
|
||||||
|
// clear flag set during do checkpoint, and open inputQ for all upstream tasks
|
||||||
|
if (streamTaskGetStatus(pTask, NULL) == TASK_STATUS__CK) {
|
||||||
|
streamTaskClearCheckInfo(pTask, true);
|
||||||
|
streamTaskSetStatusReady(pTask);
|
||||||
|
}
|
||||||
|
|
||||||
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
|
@ -885,9 +885,17 @@ static int32_t tsdbCacheLoadFromRaw(STsdb *pTsdb, tb_uid_t uid, SArray *pLastArr
|
||||||
int32_t code = 0;
|
int32_t code = 0;
|
||||||
rocksdb_writebatch_t *wb = NULL;
|
rocksdb_writebatch_t *wb = NULL;
|
||||||
SArray *pTmpColArray = NULL;
|
SArray *pTmpColArray = NULL;
|
||||||
int num_keys = TARRAY_SIZE(remainCols);
|
|
||||||
int16_t *aCols = taosMemoryMalloc(num_keys * sizeof(int16_t));
|
SIdxKey *idxKey = taosArrayGet(remainCols, 0);
|
||||||
int16_t *slotIds = taosMemoryMalloc(num_keys * sizeof(int16_t));
|
if (idxKey->key.cid != PRIMARYKEY_TIMESTAMP_COL_ID) {
|
||||||
|
SLastKey *key = &(SLastKey){.ltype = ltype, .uid = uid, .cid = PRIMARYKEY_TIMESTAMP_COL_ID};
|
||||||
|
|
||||||
|
taosArrayInsert(remainCols, 0, &(SIdxKey){0, *key});
|
||||||
|
}
|
||||||
|
|
||||||
|
int num_keys = TARRAY_SIZE(remainCols);
|
||||||
|
int16_t *aCols = taosMemoryMalloc(num_keys * sizeof(int16_t));
|
||||||
|
int16_t *slotIds = taosMemoryMalloc(num_keys * sizeof(int16_t));
|
||||||
|
|
||||||
for (int i = 0; i < num_keys; ++i) {
|
for (int i = 0; i < num_keys; ++i) {
|
||||||
SIdxKey *idxKey = taosArrayGet(remainCols, i);
|
SIdxKey *idxKey = taosArrayGet(remainCols, i);
|
||||||
|
|
|
@ -1360,7 +1360,8 @@ static bool tryCopyDistinctRowFromFileBlock(STsdbReader* pReader, SBlockData* pB
|
||||||
|
|
||||||
static bool nextRowFromSttBlocks(SSttBlockReader* pSttBlockReader, STableBlockScanInfo* pScanInfo,
|
static bool nextRowFromSttBlocks(SSttBlockReader* pSttBlockReader, STableBlockScanInfo* pScanInfo,
|
||||||
SVersionRange* pVerRange) {
|
SVersionRange* pVerRange) {
|
||||||
int32_t step = ASCENDING_TRAVERSE(pSttBlockReader->order) ? 1 : -1;
|
int32_t order = pSttBlockReader->order;
|
||||||
|
int32_t step = ASCENDING_TRAVERSE(order) ? 1 : -1;
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
bool hasVal = tMergeTreeNext(&pSttBlockReader->mergeTree);
|
bool hasVal = tMergeTreeNext(&pSttBlockReader->mergeTree);
|
||||||
|
@ -1377,8 +1378,12 @@ static bool nextRowFromSttBlocks(SSttBlockReader* pSttBlockReader, STableBlockSc
|
||||||
pSttBlockReader->currentKey = key;
|
pSttBlockReader->currentKey = key;
|
||||||
pScanInfo->sttKeyInfo.nextProcKey = key;
|
pScanInfo->sttKeyInfo.nextProcKey = key;
|
||||||
|
|
||||||
if (!hasBeenDropped(pScanInfo->delSkyline, &pScanInfo->sttBlockDelIndex, key, ver, pSttBlockReader->order,
|
if (pScanInfo->delSkyline != NULL && TARRAY_SIZE(pScanInfo->delSkyline) > 0) {
|
||||||
pVerRange)) {
|
if (!hasBeenDropped(pScanInfo->delSkyline, &pScanInfo->sttBlockDelIndex, key, ver, order, pVerRange)) {
|
||||||
|
pScanInfo->sttKeyInfo.status = STT_FILE_HAS_DATA;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
pScanInfo->sttKeyInfo.status = STT_FILE_HAS_DATA;
|
pScanInfo->sttKeyInfo.status = STT_FILE_HAS_DATA;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -2054,9 +2059,12 @@ static bool isValidFileBlockRow(SBlockData* pBlockData, SFileBlockDumpInfo* pDum
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hasBeenDropped(pBlockScanInfo->delSkyline, &pBlockScanInfo->fileDelIndex, ts, ver, pReader->info.order,
|
if (pBlockScanInfo->delSkyline != NULL && TARRAY_SIZE(pBlockScanInfo->delSkyline) > 0) {
|
||||||
&pReader->info.verRange)) {
|
bool dropped = hasBeenDropped(pBlockScanInfo->delSkyline, &pBlockScanInfo->fileDelIndex, ts, ver,
|
||||||
return false;
|
pReader->info.order, &pReader->info.verRange);
|
||||||
|
if (dropped) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
@ -3219,7 +3227,7 @@ SVersionRange getQueryVerRange(SVnode* pVnode, SQueryTableDataCond* pCond, int8_
|
||||||
|
|
||||||
bool hasBeenDropped(const SArray* pDelList, int32_t* index, int64_t key, int64_t ver, int32_t order,
|
bool hasBeenDropped(const SArray* pDelList, int32_t* index, int64_t key, int64_t ver, int32_t order,
|
||||||
SVersionRange* pVerRange) {
|
SVersionRange* pVerRange) {
|
||||||
if (pDelList == NULL || (taosArrayGetSize(pDelList) == 0)) {
|
if (pDelList == NULL || (TARRAY_SIZE(pDelList) == 0)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3327,16 +3335,22 @@ TSDBROW* getValidMemRow(SIterInfo* pIter, const SArray* pDelList, STsdbReader* p
|
||||||
|
|
||||||
TSDBROW* pRow = tsdbTbDataIterGet(pIter->iter);
|
TSDBROW* pRow = tsdbTbDataIterGet(pIter->iter);
|
||||||
TSDBKEY key = TSDBROW_KEY(pRow);
|
TSDBKEY key = TSDBROW_KEY(pRow);
|
||||||
|
int32_t order = pReader->info.order;
|
||||||
if (outOfTimeWindow(key.ts, &pReader->info.window)) {
|
if (outOfTimeWindow(key.ts, &pReader->info.window)) {
|
||||||
pIter->hasVal = false;
|
pIter->hasVal = false;
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// it is a valid data version
|
// it is a valid data version
|
||||||
if ((key.version <= pReader->info.verRange.maxVer && key.version >= pReader->info.verRange.minVer) &&
|
if (key.version <= pReader->info.verRange.maxVer && key.version >= pReader->info.verRange.minVer) {
|
||||||
(!hasBeenDropped(pDelList, &pIter->index, key.ts, key.version, pReader->info.order, &pReader->info.verRange))) {
|
if (pDelList == NULL || TARRAY_SIZE(pDelList) == 0) {
|
||||||
return pRow;
|
return pRow;
|
||||||
|
} else {
|
||||||
|
bool dropped = hasBeenDropped(pDelList, &pIter->index, key.ts, key.version, order, &pReader->info.verRange);
|
||||||
|
if (!dropped) {
|
||||||
|
return pRow;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
|
@ -3353,9 +3367,15 @@ TSDBROW* getValidMemRow(SIterInfo* pIter, const SArray* pDelList, STsdbReader* p
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (key.version <= pReader->info.verRange.maxVer && key.version >= pReader->info.verRange.minVer &&
|
if (key.version <= pReader->info.verRange.maxVer && key.version >= pReader->info.verRange.minVer) {
|
||||||
(!hasBeenDropped(pDelList, &pIter->index, key.ts, key.version, pReader->info.order, &pReader->info.verRange))) {
|
if (pDelList == NULL || TARRAY_SIZE(pDelList) == 0) {
|
||||||
return pRow;
|
return pRow;
|
||||||
|
} else {
|
||||||
|
bool dropped = hasBeenDropped(pDelList, &pIter->index, key.ts, key.version, order, &pReader->info.verRange);
|
||||||
|
if (!dropped) {
|
||||||
|
return pRow;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1266,6 +1266,7 @@ _exit:
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef BUILD_NO_CALL
|
||||||
static int32_t vnodeDebugPrintSingleSubmitMsg(SMeta *pMeta, SSubmitBlk *pBlock, SSubmitMsgIter *msgIter,
|
static int32_t vnodeDebugPrintSingleSubmitMsg(SMeta *pMeta, SSubmitBlk *pBlock, SSubmitMsgIter *msgIter,
|
||||||
const char *tags) {
|
const char *tags) {
|
||||||
SSubmitBlkIter blkIter = {0};
|
SSubmitBlkIter blkIter = {0};
|
||||||
|
@ -1296,7 +1297,7 @@ static int32_t vnodeDebugPrintSingleSubmitMsg(SMeta *pMeta, SSubmitBlk *pBlock,
|
||||||
|
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
typedef struct SSubmitReqConvertCxt {
|
typedef struct SSubmitReqConvertCxt {
|
||||||
SSubmitMsgIter msgIter;
|
SSubmitMsgIter msgIter;
|
||||||
SSubmitBlk *pBlock;
|
SSubmitBlk *pBlock;
|
||||||
|
|
|
@ -570,7 +570,7 @@ static void vnodeRestoreFinish(const SSyncFSM *pFsm, const SyncIndex commitIdx)
|
||||||
vInfo("vgId:%d, sync restore finished, not launch stream tasks, since stream tasks are disabled", vgId);
|
vInfo("vgId:%d, sync restore finished, not launch stream tasks, since stream tasks are disabled", vgId);
|
||||||
} else {
|
} else {
|
||||||
vInfo("vgId:%d sync restore finished, start to launch stream tasks", pVnode->config.vgId);
|
vInfo("vgId:%d sync restore finished, start to launch stream tasks", pVnode->config.vgId);
|
||||||
resetStreamTaskStatus(pVnode->pTq->pStreamMeta);
|
tqStreamTaskResetStatus(pVnode->pTq->pStreamMeta);
|
||||||
tqStreamTaskStartAsync(pMeta, &pVnode->msgCb, false);
|
tqStreamTaskStartAsync(pMeta, &pVnode->msgCb, false);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -594,7 +594,7 @@ static void vnodeBecomeFollower(const SSyncFSM *pFsm) {
|
||||||
|
|
||||||
if (pVnode->pTq) {
|
if (pVnode->pTq) {
|
||||||
tqUpdateNodeStage(pVnode->pTq, false);
|
tqUpdateNodeStage(pVnode->pTq, false);
|
||||||
tqStopStreamTasks(pVnode->pTq);
|
tqStopStreamTasksAsync(pVnode->pTq);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -54,10 +54,10 @@ static int32_t removeRedundantTsCol(SLastRowScanPhysiNode* pScanNode, SColM
|
||||||
|
|
||||||
#define SCAN_ROW_TYPE(_t) ((_t) ? CACHESCAN_RETRIEVE_LAST : CACHESCAN_RETRIEVE_LAST_ROW)
|
#define SCAN_ROW_TYPE(_t) ((_t) ? CACHESCAN_RETRIEVE_LAST : CACHESCAN_RETRIEVE_LAST_ROW)
|
||||||
|
|
||||||
static void setColIdForCacheReadBlock(SSDataBlock* pBlock, SNodeList* pTargets) {
|
static void setColIdForCacheReadBlock(SSDataBlock* pBlock, SLastRowScanPhysiNode* pScan) {
|
||||||
SNode* pNode;
|
SNode* pNode;
|
||||||
int32_t idx = 0;
|
int32_t idx = 0;
|
||||||
FOREACH(pNode, pTargets) {
|
FOREACH(pNode, pScan->pTargets) {
|
||||||
if (nodeType(pNode) == QUERY_NODE_COLUMN) {
|
if (nodeType(pNode) == QUERY_NODE_COLUMN) {
|
||||||
SColumnNode* pCol = (SColumnNode*)pNode;
|
SColumnNode* pCol = (SColumnNode*)pNode;
|
||||||
SColumnInfoData* pColInfo = taosArrayGet(pBlock->pDataBlock, idx);
|
SColumnInfoData* pColInfo = taosArrayGet(pBlock->pDataBlock, idx);
|
||||||
|
@ -65,6 +65,19 @@ static void setColIdForCacheReadBlock(SSDataBlock* pBlock, SNodeList* pTargets)
|
||||||
}
|
}
|
||||||
idx++;
|
idx++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (; idx < pBlock->pDataBlock->size; ++idx) {
|
||||||
|
SColumnInfoData* pColInfo = taosArrayGet(pBlock->pDataBlock, idx);
|
||||||
|
if (pScan->scan.pScanPseudoCols) {
|
||||||
|
FOREACH(pNode, pScan->scan.pScanPseudoCols) {
|
||||||
|
STargetNode* pTarget = (STargetNode*)pNode;
|
||||||
|
if (pColInfo->info.slotId == pTarget->slotId) {
|
||||||
|
pColInfo->info.colId = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SOperatorInfo* createCacherowsScanOperator(SLastRowScanPhysiNode* pScanNode, SReadHandle* readHandle,
|
SOperatorInfo* createCacherowsScanOperator(SLastRowScanPhysiNode* pScanNode, SReadHandle* readHandle,
|
||||||
|
@ -127,12 +140,12 @@ SOperatorInfo* createCacherowsScanOperator(SLastRowScanPhysiNode* pScanNode, SRe
|
||||||
capacity = TMIN(totalTables, 4096);
|
capacity = TMIN(totalTables, 4096);
|
||||||
|
|
||||||
pInfo->pBufferredRes = createOneDataBlock(pInfo->pRes, false);
|
pInfo->pBufferredRes = createOneDataBlock(pInfo->pRes, false);
|
||||||
setColIdForCacheReadBlock(pInfo->pBufferredRes, pScanNode->pTargets);
|
setColIdForCacheReadBlock(pInfo->pBufferredRes, pScanNode);
|
||||||
blockDataEnsureCapacity(pInfo->pBufferredRes, capacity);
|
blockDataEnsureCapacity(pInfo->pBufferredRes, capacity);
|
||||||
} else { // by tags
|
} else { // by tags
|
||||||
pInfo->retrieveType = CACHESCAN_RETRIEVE_TYPE_SINGLE | SCAN_ROW_TYPE(pScanNode->ignoreNull);
|
pInfo->retrieveType = CACHESCAN_RETRIEVE_TYPE_SINGLE | SCAN_ROW_TYPE(pScanNode->ignoreNull);
|
||||||
capacity = 1; // only one row output
|
capacity = 1; // only one row output
|
||||||
setColIdForCacheReadBlock(pInfo->pRes, pScanNode->pTargets);
|
setColIdForCacheReadBlock(pInfo->pRes, pScanNode);
|
||||||
}
|
}
|
||||||
|
|
||||||
initResultSizeInfo(&pOperator->resultInfo, capacity);
|
initResultSizeInfo(&pOperator->resultInfo, capacity);
|
||||||
|
|
|
@ -1623,6 +1623,7 @@ void initDummyFunction(SqlFunctionCtx* pDummy, SqlFunctionCtx* pCtx, int32_t num
|
||||||
pDummy[i].functionId = pCtx[i].functionId;
|
pDummy[i].functionId = pCtx[i].functionId;
|
||||||
pDummy[i].isNotNullFunc = pCtx[i].isNotNullFunc;
|
pDummy[i].isNotNullFunc = pCtx[i].isNotNullFunc;
|
||||||
pDummy[i].isPseudoFunc = pCtx[i].isPseudoFunc;
|
pDummy[i].isPseudoFunc = pCtx[i].isPseudoFunc;
|
||||||
|
pDummy[i].fpSet.init = pCtx[i].fpSet.init;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2774,6 +2775,9 @@ void streamSessionSemiReloadState(SOperatorInfo* pOperator) {
|
||||||
for (int32_t i = 0; i < num; i++) {
|
for (int32_t i = 0; i < num; i++) {
|
||||||
SResultWindowInfo winInfo = {0};
|
SResultWindowInfo winInfo = {0};
|
||||||
getSessionWindowInfoByKey(pAggSup, pSeKeyBuf + i, &winInfo);
|
getSessionWindowInfoByKey(pAggSup, pSeKeyBuf + i, &winInfo);
|
||||||
|
if (!IS_VALID_SESSION_WIN(winInfo)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
compactSessionSemiWindow(pOperator, &winInfo);
|
compactSessionSemiWindow(pOperator, &winInfo);
|
||||||
saveSessionOutputBuf(pAggSup, &winInfo);
|
saveSessionOutputBuf(pAggSup, &winInfo);
|
||||||
}
|
}
|
||||||
|
|
|
@ -475,6 +475,7 @@ static void appendOneRowToDataBlock(SSDataBlock* pBlock, const SSDataBlock* pSou
|
||||||
if (isNull) {
|
if (isNull) {
|
||||||
colDataSetVal(pColInfo, pBlock->info.rows, NULL, true);
|
colDataSetVal(pColInfo, pBlock->info.rows, NULL, true);
|
||||||
} else {
|
} else {
|
||||||
|
if (!pSrcColInfo->pData) continue;
|
||||||
char* pData = colDataGetData(pSrcColInfo, *rowIndex);
|
char* pData = colDataGetData(pSrcColInfo, *rowIndex);
|
||||||
colDataSetVal(pColInfo, pBlock->info.rows, pData, false);
|
colDataSetVal(pColInfo, pBlock->info.rows, pData, false);
|
||||||
}
|
}
|
||||||
|
@ -900,7 +901,7 @@ static int32_t getPageBufIncForRow(SSDataBlock* blk, int32_t row, int32_t rowIdx
|
||||||
for (int32_t i = 0; i < numCols; ++i) {
|
for (int32_t i = 0; i < numCols; ++i) {
|
||||||
SColumnInfoData* pColInfoData = TARRAY_GET_ELEM(blk->pDataBlock, i);
|
SColumnInfoData* pColInfoData = TARRAY_GET_ELEM(blk->pDataBlock, i);
|
||||||
if (IS_VAR_DATA_TYPE(pColInfoData->info.type)) {
|
if (IS_VAR_DATA_TYPE(pColInfoData->info.type)) {
|
||||||
if (pColInfoData->varmeta.offset[row] != -1) {
|
if ((pColInfoData->varmeta.offset[row] != -1) && (pColInfoData->pData)) {
|
||||||
char* p = colDataGetData(pColInfoData, row);
|
char* p = colDataGetData(pColInfoData, row);
|
||||||
sz += varDataTLen(p);
|
sz += varDataTLen(p);
|
||||||
}
|
}
|
||||||
|
@ -970,7 +971,6 @@ static int32_t sortBlocksToExtSource(SSortHandle* pHandle, SArray* aBlk, SBlockO
|
||||||
lastPageBufTs = ((int64_t*)tsCol->pData)[pHandle->pDataBlock->info.rows - 1];
|
lastPageBufTs = ((int64_t*)tsCol->pData)[pHandle->pDataBlock->info.rows - 1];
|
||||||
appendDataBlockToPageBuf(pHandle, pHandle->pDataBlock, aPgId);
|
appendDataBlockToPageBuf(pHandle, pHandle->pDataBlock, aPgId);
|
||||||
nMergedRows += pHandle->pDataBlock->info.rows;
|
nMergedRows += pHandle->pDataBlock->info.rows;
|
||||||
|
|
||||||
blockDataCleanup(pHandle->pDataBlock);
|
blockDataCleanup(pHandle->pDataBlock);
|
||||||
blkPgSz = pgHeaderSz;
|
blkPgSz = pgHeaderSz;
|
||||||
bufInc = getPageBufIncForRow(minBlk, minRow, 0);
|
bufInc = getPageBufIncForRow(minBlk, minRow, 0);
|
||||||
|
|
|
@ -28,8 +28,6 @@ extern "C" {
|
||||||
#include "tudf.h"
|
#include "tudf.h"
|
||||||
#include "tvariant.h"
|
#include "tvariant.h"
|
||||||
|
|
||||||
bool topbot_datablock_filter(SqlFunctionCtx *pCtx, const char *minval, const char *maxval);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* the numOfRes should be kept, since it may be used later
|
* the numOfRes should be kept, since it may be used later
|
||||||
* and allow the ResultInfo to be re initialized
|
* and allow the ResultInfo to be re initialized
|
||||||
|
|
|
@ -27,41 +27,3 @@
|
||||||
#include "tpercentile.h"
|
#include "tpercentile.h"
|
||||||
#include "ttszip.h"
|
#include "ttszip.h"
|
||||||
#include "tudf.h"
|
#include "tudf.h"
|
||||||
|
|
||||||
void cleanupResultRowEntry(struct SResultRowEntryInfo* pCell) { pCell->initialized = false; }
|
|
||||||
|
|
||||||
int32_t getNumOfResult(SqlFunctionCtx* pCtx, int32_t num, SSDataBlock* pResBlock) {
|
|
||||||
int32_t maxRows = 0;
|
|
||||||
|
|
||||||
for (int32_t j = 0; j < num; ++j) {
|
|
||||||
SResultRowEntryInfo* pResInfo = GET_RES_INFO(&pCtx[j]);
|
|
||||||
if (pResInfo != NULL && maxRows < pResInfo->numOfRes) {
|
|
||||||
maxRows = pResInfo->numOfRes;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
blockDataEnsureCapacity(pResBlock, maxRows);
|
|
||||||
for (int32_t i = 0; i < num; ++i) {
|
|
||||||
SColumnInfoData* pCol = taosArrayGet(pResBlock->pDataBlock, i);
|
|
||||||
|
|
||||||
SResultRowEntryInfo* pResInfo = GET_RES_INFO(&pCtx[i]);
|
|
||||||
if (pResInfo->numOfRes == 0) {
|
|
||||||
for (int32_t j = 0; j < pResInfo->numOfRes; ++j) {
|
|
||||||
colDataSetVal(pCol, j, NULL, true); // TODO add set null data api
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
for (int32_t j = 0; j < pResInfo->numOfRes; ++j) {
|
|
||||||
colDataSetVal(pCol, j, GET_ROWCELL_INTERBUF(pResInfo), false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pResBlock->info.rows = maxRows;
|
|
||||||
return maxRows;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool isRowEntryCompleted(struct SResultRowEntryInfo* pEntry) {
|
|
||||||
return pEntry->complete;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool isRowEntryInitialized(struct SResultRowEntryInfo* pEntry) { return pEntry->initialized; }
|
|
||||||
|
|
|
@ -142,13 +142,13 @@ int32_t tBucketIntHash(tMemBucket *pBucket, const void *value) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// divide the value range into 1024 buckets
|
// divide the value range into 1024 buckets
|
||||||
uint64_t span = pBucket->range.i64MaxVal - pBucket->range.i64MinVal;
|
uint64_t span = (uint64_t)(pBucket->range.i64MaxVal - pBucket->range.i64MinVal);
|
||||||
if (span < pBucket->numOfSlots) {
|
if (span < pBucket->numOfSlots) {
|
||||||
int64_t delta = v - pBucket->range.i64MinVal;
|
int64_t delta = v - pBucket->range.i64MinVal;
|
||||||
index = (delta % pBucket->numOfSlots);
|
index = (delta % pBucket->numOfSlots);
|
||||||
} else {
|
} else {
|
||||||
double slotSpan = ((double)span) / pBucket->numOfSlots;
|
double slotSpan = ((double)span) / pBucket->numOfSlots;
|
||||||
uint64_t delta = v - pBucket->range.i64MinVal;
|
uint64_t delta = (uint64_t)(v - pBucket->range.i64MinVal);
|
||||||
|
|
||||||
index = (int32_t)(delta / slotSpan);
|
index = (int32_t)(delta / slotSpan);
|
||||||
if (v == pBucket->range.i64MaxVal || index == pBucket->numOfSlots) {
|
if (v == pBucket->range.i64MaxVal || index == pBucket->numOfSlots) {
|
||||||
|
|
|
@ -4,9 +4,6 @@ IF (TD_ENTERPRISE)
|
||||||
LIST(APPEND PARSER_SRC ${TD_ENTERPRISE_DIR}/src/plugins/view/src/parserView.c)
|
LIST(APPEND PARSER_SRC ${TD_ENTERPRISE_DIR}/src/plugins/view/src/parserView.c)
|
||||||
ENDIF ()
|
ENDIF ()
|
||||||
|
|
||||||
IF (TD_BI_SUPPORT)
|
|
||||||
LIST(APPEND PARSER_SRC ${TD_ENTERPRISE_DIR}/src/plugins/bi/src/biRewriteQuery.c)
|
|
||||||
ENDIF ()
|
|
||||||
add_library(parser STATIC ${PARSER_SRC})
|
add_library(parser STATIC ${PARSER_SRC})
|
||||||
target_include_directories(
|
target_include_directories(
|
||||||
parser
|
parser
|
||||||
|
|
|
@ -1104,11 +1104,192 @@ static EDealRes translateColumnUseAlias(STranslateContext* pCxt, SColumnNode** p
|
||||||
return DEAL_RES_CONTINUE;
|
return DEAL_RES_CONTINUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef TD_ENTERPRISE
|
static void biMakeAliasNameInMD5(char* pExprStr, int32_t len, char* pAlias) {
|
||||||
|
T_MD5_CTX ctx;
|
||||||
|
tMD5Init(&ctx);
|
||||||
|
tMD5Update(&ctx, pExprStr, len);
|
||||||
|
tMD5Final(&ctx);
|
||||||
|
char* p = pAlias;
|
||||||
|
for (uint8_t i = 0; i < tListLen(ctx.digest); ++i) {
|
||||||
|
sprintf(p, "%02x", ctx.digest[i]);
|
||||||
|
p += 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static SNode* biMakeTbnameProjectAstNode(char* funcName, char* tableAlias) {
|
||||||
|
SValueNode* valNode = NULL;
|
||||||
|
if (tableAlias != NULL) {
|
||||||
|
SValueNode* n = (SValueNode*)nodesMakeNode(QUERY_NODE_VALUE);
|
||||||
|
n->literal = tstrdup(tableAlias);
|
||||||
|
n->node.resType.type = TSDB_DATA_TYPE_BINARY;
|
||||||
|
n->node.resType.bytes = strlen(n->literal);
|
||||||
|
n->isDuration = false;
|
||||||
|
n->translate = false;
|
||||||
|
valNode = n;
|
||||||
|
}
|
||||||
|
|
||||||
|
SFunctionNode* tbNameFunc = (SFunctionNode*)nodesMakeNode(QUERY_NODE_FUNCTION);
|
||||||
|
tstrncpy(tbNameFunc->functionName, "tbname", TSDB_FUNC_NAME_LEN);
|
||||||
|
if (valNode != NULL) {
|
||||||
|
nodesListMakeAppend(&tbNameFunc->pParameterList, (SNode*)valNode);
|
||||||
|
}
|
||||||
|
snprintf(tbNameFunc->node.userAlias, sizeof(tbNameFunc->node.userAlias),
|
||||||
|
(tableAlias)? "%s.tbname" : "%stbname",
|
||||||
|
(tableAlias)? tableAlias : "");
|
||||||
|
strncpy(tbNameFunc->node.aliasName, tbNameFunc->functionName, TSDB_COL_NAME_LEN);
|
||||||
|
|
||||||
|
if (funcName == NULL) {
|
||||||
|
return (SNode*)tbNameFunc;
|
||||||
|
} else {
|
||||||
|
SFunctionNode* multiResFunc = (SFunctionNode*)nodesMakeNode(QUERY_NODE_FUNCTION);
|
||||||
|
tstrncpy(multiResFunc->functionName, funcName, TSDB_FUNC_NAME_LEN);
|
||||||
|
nodesListMakeAppend(&multiResFunc->pParameterList, (SNode*)tbNameFunc);
|
||||||
|
|
||||||
|
if (tsKeepColumnName) {
|
||||||
|
snprintf(multiResFunc->node.userAlias, sizeof(tbNameFunc->node.userAlias),
|
||||||
|
(tableAlias)? "%s.tbname" : "%stbname",
|
||||||
|
(tableAlias)? tableAlias : "");
|
||||||
|
strcpy(multiResFunc->node.aliasName, tbNameFunc->functionName);
|
||||||
|
} else {
|
||||||
|
snprintf(multiResFunc->node.userAlias, sizeof(multiResFunc->node.userAlias),
|
||||||
|
tableAlias? "%s(%s.tbname)" : "%s(%stbname)", funcName,
|
||||||
|
tableAlias? tableAlias: "");
|
||||||
|
biMakeAliasNameInMD5(multiResFunc->node.userAlias, strlen(multiResFunc->node.userAlias), multiResFunc->node.aliasName);
|
||||||
|
}
|
||||||
|
|
||||||
|
return (SNode*)multiResFunc;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static int32_t biRewriteSelectFuncParamStar(STranslateContext* pCxt, SSelectStmt* pSelect, SNode* pNode, SListCell* pSelectListCell) {
|
||||||
|
SNodeList* pTbnameNodeList = nodesMakeList();
|
||||||
|
|
||||||
|
SFunctionNode* pFunc = (SFunctionNode*)pNode;
|
||||||
|
if (strcasecmp(pFunc->functionName, "last") == 0 ||
|
||||||
|
strcasecmp(pFunc->functionName, "last_row") == 0 ||
|
||||||
|
strcasecmp(pFunc->functionName, "first") == 0) {
|
||||||
|
SNodeList* pParams = pFunc->pParameterList;
|
||||||
|
SNode* pPara = NULL;
|
||||||
|
FOREACH(pPara, pParams) {
|
||||||
|
if (nodesIsStar(pPara)) {
|
||||||
|
SArray* pTables = taosArrayGetP(pCxt->pNsLevel, pCxt->currLevel);
|
||||||
|
size_t n = taosArrayGetSize(pTables);
|
||||||
|
for (int32_t i = 0; i < n; ++i) {
|
||||||
|
STableNode* pTable = taosArrayGetP(pTables, i);
|
||||||
|
if (nodeType(pTable) == QUERY_NODE_REAL_TABLE && ((SRealTableNode*)pTable)->pMeta != NULL &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta->tableType == TSDB_SUPER_TABLE) {
|
||||||
|
SNode* pTbnameNode = biMakeTbnameProjectAstNode(pFunc->functionName, NULL);
|
||||||
|
nodesListAppend(pTbnameNodeList, pTbnameNode);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (LIST_LENGTH(pTbnameNodeList) > 0) {
|
||||||
|
nodesListInsertListAfterPos(pSelect->pProjectionList, pSelectListCell, pTbnameNodeList);
|
||||||
|
}
|
||||||
|
} else if (nodesIsTableStar(pPara)) {
|
||||||
|
char* pTableAlias = ((SColumnNode*)pPara)->tableAlias;
|
||||||
|
STableNode* pTable = NULL;
|
||||||
|
int32_t code = findTable(pCxt, pTableAlias, &pTable);
|
||||||
|
if (TSDB_CODE_SUCCESS == code && nodeType(pTable) == QUERY_NODE_REAL_TABLE &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta != NULL &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta->tableType == TSDB_SUPER_TABLE) {
|
||||||
|
SNode* pTbnameNode = biMakeTbnameProjectAstNode(pFunc->functionName, pTableAlias);
|
||||||
|
nodesListAppend(pTbnameNodeList, pTbnameNode);
|
||||||
|
}
|
||||||
|
if (LIST_LENGTH(pTbnameNodeList) > 0) {
|
||||||
|
nodesListInsertListAfterPos(pSelect->pProjectionList, pSelectListCell, pTbnameNodeList);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
// after translate from
|
||||||
|
// before translate select list
|
||||||
|
int32_t biRewriteSelectStar(STranslateContext* pCxt, SSelectStmt* pSelect) {
|
||||||
|
SNode* pNode = NULL;
|
||||||
|
SNodeList* pTbnameNodeList = nodesMakeList();
|
||||||
|
WHERE_EACH(pNode, pSelect->pProjectionList) {
|
||||||
|
if (nodesIsStar(pNode)) {
|
||||||
|
SArray* pTables = taosArrayGetP(pCxt->pNsLevel, pCxt->currLevel);
|
||||||
|
size_t n = taosArrayGetSize(pTables);
|
||||||
|
for (int32_t i = 0; i < n; ++i) {
|
||||||
|
STableNode* pTable = taosArrayGetP(pTables, i);
|
||||||
|
if (nodeType(pTable) == QUERY_NODE_REAL_TABLE &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta != NULL &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta->tableType == TSDB_SUPER_TABLE) {
|
||||||
|
SNode* pTbnameNode = biMakeTbnameProjectAstNode(NULL, NULL);
|
||||||
|
nodesListAppend(pTbnameNodeList, pTbnameNode);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (LIST_LENGTH(pTbnameNodeList) > 0) {
|
||||||
|
nodesListInsertListAfterPos(pSelect->pProjectionList, cell, pTbnameNodeList);
|
||||||
|
}
|
||||||
|
} else if (nodesIsTableStar(pNode)) {
|
||||||
|
char* pTableAlias = ((SColumnNode*)pNode)->tableAlias;
|
||||||
|
STableNode* pTable = NULL;
|
||||||
|
int32_t code = findTable(pCxt, pTableAlias, &pTable);
|
||||||
|
if (TSDB_CODE_SUCCESS == code &&
|
||||||
|
nodeType(pTable) == QUERY_NODE_REAL_TABLE &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta != NULL &&
|
||||||
|
((SRealTableNode*)pTable)->pMeta->tableType == TSDB_SUPER_TABLE) {
|
||||||
|
SNode* pTbnameNode = biMakeTbnameProjectAstNode(NULL, pTableAlias);
|
||||||
|
nodesListAppend(pTbnameNodeList, pTbnameNode);
|
||||||
|
}
|
||||||
|
if (LIST_LENGTH(pTbnameNodeList) > 0) {
|
||||||
|
nodesListInsertListAfterPos(pSelect->pProjectionList, cell, pTbnameNodeList);
|
||||||
|
}
|
||||||
|
} else if (nodeType(pNode) == QUERY_NODE_FUNCTION) {
|
||||||
|
biRewriteSelectFuncParamStar(pCxt, pSelect, pNode, cell);
|
||||||
|
}
|
||||||
|
WHERE_NEXT;
|
||||||
|
}
|
||||||
|
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
bool biRewriteToTbnameFunc(STranslateContext* pCxt, SNode** ppNode) {
|
bool biRewriteToTbnameFunc(STranslateContext* pCxt, SNode** ppNode) {
|
||||||
|
SColumnNode* pCol = (SColumnNode*)(*ppNode);
|
||||||
|
if ((strcasecmp(pCol->colName, "tbname") == 0) &&
|
||||||
|
((SSelectStmt*)pCxt->pCurrStmt)->pFromTable &&
|
||||||
|
QUERY_NODE_REAL_TABLE == nodeType(((SSelectStmt*)pCxt->pCurrStmt)->pFromTable)) {
|
||||||
|
SFunctionNode* tbnameFuncNode = NULL;
|
||||||
|
tbnameFuncNode = (SFunctionNode*)biMakeTbnameProjectAstNode(NULL, (pCol->tableAlias[0]!='\0') ? pCol->tableAlias : NULL);
|
||||||
|
tbnameFuncNode->node.resType = pCol->node.resType;
|
||||||
|
strcpy(tbnameFuncNode->node.aliasName, pCol->node.aliasName);
|
||||||
|
strcpy(tbnameFuncNode->node.userAlias, pCol->node.userAlias);
|
||||||
|
|
||||||
|
nodesDestroyNode(*ppNode);
|
||||||
|
*ppNode = (SNode*)tbnameFuncNode;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
int32_t biCheckCreateTableTbnameCol(STranslateContext* pCxt, SCreateTableStmt* pStmt) {
|
||||||
|
if (pStmt->pTags) {
|
||||||
|
SNode* pNode = NULL;
|
||||||
|
FOREACH(pNode, pStmt->pTags) {
|
||||||
|
SColumnDefNode* pTag = (SColumnDefNode*)pNode;
|
||||||
|
if (strcasecmp(pTag->colName, "tbname") == 0) {
|
||||||
|
int32_t code = generateSyntaxErrMsgExt(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_TAG_NAME, "tbname can not used for tags in BI mode");
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (pStmt->pCols) {
|
||||||
|
SNode* pNode = NULL;
|
||||||
|
FOREACH(pNode, pStmt->pCols) {
|
||||||
|
SColumnDefNode* pCol = (SColumnDefNode*)pNode;
|
||||||
|
if (strcasecmp(pCol->colName, "tbname") == 0) {
|
||||||
|
int32_t code = generateSyntaxErrMsgExt(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_COLUMN, "tbname can not used for columns in BI mode");
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
static EDealRes translateColumn(STranslateContext* pCxt, SColumnNode** pCol) {
|
static EDealRes translateColumn(STranslateContext* pCxt, SColumnNode** pCol) {
|
||||||
if (NULL == pCxt->pCurrStmt ||
|
if (NULL == pCxt->pCurrStmt ||
|
||||||
|
@ -3178,10 +3359,6 @@ static int32_t createTags(STranslateContext* pCxt, SNodeList** pOutput) {
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef TD_ENTERPRISE
|
|
||||||
int32_t biRewriteSelectStar(STranslateContext* pCxt, SSelectStmt* pSelect) { return TSDB_CODE_SUCCESS; }
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static int32_t translateStar(STranslateContext* pCxt, SSelectStmt* pSelect) {
|
static int32_t translateStar(STranslateContext* pCxt, SSelectStmt* pSelect) {
|
||||||
SNode* pNode = NULL;
|
SNode* pNode = NULL;
|
||||||
WHERE_EACH(pNode, pSelect->pProjectionList) {
|
WHERE_EACH(pNode, pSelect->pProjectionList) {
|
||||||
|
@ -5743,11 +5920,6 @@ static int32_t checkTableDeleteMarkOption(STranslateContext* pCxt, STableOptions
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifndef TD_ENTERPRISE
|
|
||||||
int32_t biCheckCreateTableTbnameCol(STranslateContext* pCxt, SCreateTableStmt* pStmt) {
|
|
||||||
return TSDB_CODE_SUCCESS;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static int32_t checkCreateTable(STranslateContext* pCxt, SCreateTableStmt* pStmt, bool createStable) {
|
static int32_t checkCreateTable(STranslateContext* pCxt, SCreateTableStmt* pStmt, bool createStable) {
|
||||||
if (NULL != strchr(pStmt->tableName, '.')) {
|
if (NULL != strchr(pStmt->tableName, '.')) {
|
||||||
|
@ -8769,7 +8941,7 @@ static int32_t extractShowVariablesResultSchema(int32_t* numOfCols, SSchema** pS
|
||||||
|
|
||||||
(*pSchema)[0].type = TSDB_DATA_TYPE_BINARY;
|
(*pSchema)[0].type = TSDB_DATA_TYPE_BINARY;
|
||||||
(*pSchema)[0].bytes = TSDB_CONFIG_OPTION_LEN;
|
(*pSchema)[0].bytes = TSDB_CONFIG_OPTION_LEN;
|
||||||
strcpy((*pSchema)[0].name, "name");
|
strcpy((*pSchema)[0].name, "result");
|
||||||
|
|
||||||
(*pSchema)[1].type = TSDB_DATA_TYPE_BINARY;
|
(*pSchema)[1].type = TSDB_DATA_TYPE_BINARY;
|
||||||
(*pSchema)[1].bytes = TSDB_CONFIG_VALUE_LEN;
|
(*pSchema)[1].bytes = TSDB_CONFIG_VALUE_LEN;
|
||||||
|
|
|
@ -1254,6 +1254,7 @@ int32_t toCharFunction(SScalarParam* pInput, int32_t inputNum, SScalarParam* pOu
|
||||||
char * out = taosMemoryCalloc(1, TS_FORMAT_MAX_LEN + VARSTR_HEADER_SIZE);
|
char * out = taosMemoryCalloc(1, TS_FORMAT_MAX_LEN + VARSTR_HEADER_SIZE);
|
||||||
int32_t len;
|
int32_t len;
|
||||||
SArray *formats = NULL;
|
SArray *formats = NULL;
|
||||||
|
int32_t code = 0;
|
||||||
for (int32_t i = 0; i < pInput[0].numOfRows; ++i) {
|
for (int32_t i = 0; i < pInput[0].numOfRows; ++i) {
|
||||||
if (colDataIsNull_s(pInput[1].columnData, i) || colDataIsNull_s(pInput[0].columnData, i)) {
|
if (colDataIsNull_s(pInput[1].columnData, i) || colDataIsNull_s(pInput[0].columnData, i)) {
|
||||||
colDataSetNULL(pOutput->columnData, i);
|
colDataSetNULL(pOutput->columnData, i);
|
||||||
|
@ -1272,14 +1273,15 @@ int32_t toCharFunction(SScalarParam* pInput, int32_t inputNum, SScalarParam* pOu
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
int32_t precision = pInput[0].columnData->info.precision;
|
int32_t precision = pInput[0].columnData->info.precision;
|
||||||
taosTs2Char(format, &formats, *(int64_t *)ts, precision, varDataVal(out), TS_FORMAT_MAX_LEN);
|
code = taosTs2Char(format, &formats, *(int64_t *)ts, precision, varDataVal(out), TS_FORMAT_MAX_LEN);
|
||||||
|
if (code) break;
|
||||||
varDataSetLen(out, strlen(varDataVal(out)));
|
varDataSetLen(out, strlen(varDataVal(out)));
|
||||||
colDataSetVal(pOutput->columnData, i, out, false);
|
colDataSetVal(pOutput->columnData, i, out, false);
|
||||||
}
|
}
|
||||||
if (formats) taosArrayDestroy(formats);
|
if (formats) taosArrayDestroy(formats);
|
||||||
taosMemoryFree(format);
|
taosMemoryFree(format);
|
||||||
taosMemoryFree(out);
|
taosMemoryFree(out);
|
||||||
return TSDB_CODE_SUCCESS;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Time functions **/
|
/** Time functions **/
|
||||||
|
|
|
@ -109,13 +109,12 @@ int32_t streamBroadcastToChildren(SStreamTask* pTask, const SSDataBlock* pBlock)
|
||||||
int32_t tEncodeStreamRetrieveReq(SEncoder* pEncoder, const SStreamRetrieveReq* pReq);
|
int32_t tEncodeStreamRetrieveReq(SEncoder* pEncoder, const SStreamRetrieveReq* pReq);
|
||||||
|
|
||||||
int32_t streamSaveTaskCheckpointInfo(SStreamTask* p, int64_t checkpointId);
|
int32_t streamSaveTaskCheckpointInfo(SStreamTask* p, int64_t checkpointId);
|
||||||
int32_t streamTaskBuildCheckpoint(SStreamTask* pTask);
|
|
||||||
int32_t streamSaveAllTaskStatus(SStreamMeta* pMeta, int64_t checkpointId);
|
|
||||||
int32_t streamSendCheckMsg(SStreamTask* pTask, const SStreamTaskCheckReq* pReq, int32_t nodeId, SEpSet* pEpSet);
|
int32_t streamSendCheckMsg(SStreamTask* pTask, const SStreamTaskCheckReq* pReq, int32_t nodeId, SEpSet* pEpSet);
|
||||||
|
|
||||||
int32_t streamAddCheckpointReadyMsg(SStreamTask* pTask, int32_t srcTaskId, int32_t index, int64_t checkpointId);
|
int32_t streamAddCheckpointReadyMsg(SStreamTask* pTask, int32_t srcTaskId, int32_t index, int64_t checkpointId);
|
||||||
int32_t streamTaskSendCheckpointReadyMsg(SStreamTask* pTask);
|
int32_t streamTaskSendCheckpointReadyMsg(SStreamTask* pTask);
|
||||||
int32_t streamTaskSendCheckpointSourceRsp(SStreamTask* pTask);
|
int32_t streamTaskSendCheckpointSourceRsp(SStreamTask* pTask);
|
||||||
|
void streamTaskSetCheckpointFailedId(SStreamTask* pTask);
|
||||||
int32_t streamTaskGetNumOfDownstream(const SStreamTask* pTask);
|
int32_t streamTaskGetNumOfDownstream(const SStreamTask* pTask);
|
||||||
int32_t streamTaskInitTokenBucket(STokenBucket* pBucket, int32_t numCap, int32_t numRate, float quotaRate, const char*);
|
int32_t streamTaskInitTokenBucket(STokenBucket* pBucket, int32_t numCap, int32_t numRate, float quotaRate, const char*);
|
||||||
STaskId streamTaskExtractKey(const SStreamTask* pTask);
|
STaskId streamTaskExtractKey(const SStreamTask* pTask);
|
||||||
|
@ -137,17 +136,6 @@ int32_t streamAddEndScanHistoryMsg(SStreamTask* pTask, SRpcHandleInfo* pRpcInfo,
|
||||||
int32_t streamNotifyUpstreamContinue(SStreamTask* pTask);
|
int32_t streamNotifyUpstreamContinue(SStreamTask* pTask);
|
||||||
int32_t streamTransferStateToStreamTask(SStreamTask* pTask);
|
int32_t streamTransferStateToStreamTask(SStreamTask* pTask);
|
||||||
|
|
||||||
// <<<<<<< HEAD
|
|
||||||
// void streamClearChkptReadyMsg(SStreamTask* pTask);
|
|
||||||
|
|
||||||
// int32_t streamTaskInitTokenBucket(STokenBucket* pBucket, int32_t numCap, int32_t numRate, float quotaRate, const
|
|
||||||
// char*); STaskId streamTaskExtractKey(const SStreamTask* pTask); void streamTaskInitForLaunchHTask(SHistoryTaskInfo*
|
|
||||||
// pInfo); void streamTaskSetRetryInfoForLaunch(SHistoryTaskInfo* pInfo);
|
|
||||||
|
|
||||||
// void streamMetaResetStartInfo(STaskStartInfo* pMeta);
|
|
||||||
|
|
||||||
// =======
|
|
||||||
// >>>>>>> 3.0
|
|
||||||
SStreamQueue* streamQueueOpen(int64_t cap);
|
SStreamQueue* streamQueueOpen(int64_t cap);
|
||||||
void streamQueueClose(SStreamQueue* pQueue, int32_t taskId);
|
void streamQueueClose(SStreamQueue* pQueue, int32_t taskId);
|
||||||
void streamQueueProcessSuccess(SStreamQueue* queue);
|
void streamQueueProcessSuccess(SStreamQueue* queue);
|
||||||
|
|
|
@ -25,6 +25,7 @@ typedef struct {
|
||||||
|
|
||||||
SStreamTask* pTask;
|
SStreamTask* pTask;
|
||||||
} SAsyncUploadArg;
|
} SAsyncUploadArg;
|
||||||
|
|
||||||
int32_t tEncodeStreamCheckpointSourceReq(SEncoder* pEncoder, const SStreamCheckpointSourceReq* pReq) {
|
int32_t tEncodeStreamCheckpointSourceReq(SEncoder* pEncoder, const SStreamCheckpointSourceReq* pReq) {
|
||||||
if (tStartEncode(pEncoder) < 0) return -1;
|
if (tStartEncode(pEncoder) < 0) return -1;
|
||||||
if (tEncodeI64(pEncoder, pReq->streamId) < 0) return -1;
|
if (tEncodeI64(pEncoder, pReq->streamId) < 0) return -1;
|
||||||
|
@ -34,6 +35,7 @@ int32_t tEncodeStreamCheckpointSourceReq(SEncoder* pEncoder, const SStreamCheckp
|
||||||
if (tEncodeSEpSet(pEncoder, &pReq->mgmtEps) < 0) return -1;
|
if (tEncodeSEpSet(pEncoder, &pReq->mgmtEps) < 0) return -1;
|
||||||
if (tEncodeI32(pEncoder, pReq->mnodeId) < 0) return -1;
|
if (tEncodeI32(pEncoder, pReq->mnodeId) < 0) return -1;
|
||||||
if (tEncodeI64(pEncoder, pReq->expireTime) < 0) return -1;
|
if (tEncodeI64(pEncoder, pReq->expireTime) < 0) return -1;
|
||||||
|
if (tEncodeI32(pEncoder, pReq->transId) < 0) return -1;
|
||||||
tEndEncode(pEncoder);
|
tEndEncode(pEncoder);
|
||||||
return pEncoder->pos;
|
return pEncoder->pos;
|
||||||
}
|
}
|
||||||
|
@ -47,6 +49,7 @@ int32_t tDecodeStreamCheckpointSourceReq(SDecoder* pDecoder, SStreamCheckpointSo
|
||||||
if (tDecodeSEpSet(pDecoder, &pReq->mgmtEps) < 0) return -1;
|
if (tDecodeSEpSet(pDecoder, &pReq->mgmtEps) < 0) return -1;
|
||||||
if (tDecodeI32(pDecoder, &pReq->mnodeId) < 0) return -1;
|
if (tDecodeI32(pDecoder, &pReq->mnodeId) < 0) return -1;
|
||||||
if (tDecodeI64(pDecoder, &pReq->expireTime) < 0) return -1;
|
if (tDecodeI64(pDecoder, &pReq->expireTime) < 0) return -1;
|
||||||
|
if (tDecodeI32(pDecoder, &pReq->transId) < 0) return -1;
|
||||||
tEndDecode(pDecoder);
|
tEndDecode(pDecoder);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -111,6 +114,7 @@ static int32_t streamAlignCheckpoint(SStreamTask* pTask) {
|
||||||
return atomic_sub_fetch_32(&pTask->chkInfo.downstreamAlignNum, 1);
|
return atomic_sub_fetch_32(&pTask->chkInfo.downstreamAlignNum, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// todo handle down the transId of checkpoint to sink/agg tasks.
|
||||||
static int32_t appendCheckpointIntoInputQ(SStreamTask* pTask, int32_t checkpointType) {
|
static int32_t appendCheckpointIntoInputQ(SStreamTask* pTask, int32_t checkpointType) {
|
||||||
SStreamDataBlock* pChkpoint = taosAllocateQitem(sizeof(SStreamDataBlock), DEF_QITEM, sizeof(SSDataBlock));
|
SStreamDataBlock* pChkpoint = taosAllocateQitem(sizeof(SStreamDataBlock), DEF_QITEM, sizeof(SSDataBlock));
|
||||||
if (pChkpoint == NULL) {
|
if (pChkpoint == NULL) {
|
||||||
|
@ -149,6 +153,7 @@ int32_t streamProcessCheckpointSourceReq(SStreamTask* pTask, SStreamCheckpointSo
|
||||||
// 1. set task status to be prepared for check point, no data are allowed to put into inputQ.
|
// 1. set task status to be prepared for check point, no data are allowed to put into inputQ.
|
||||||
streamTaskHandleEvent(pTask->status.pSM, TASK_EVENT_GEN_CHECKPOINT);
|
streamTaskHandleEvent(pTask->status.pSM, TASK_EVENT_GEN_CHECKPOINT);
|
||||||
|
|
||||||
|
pTask->chkInfo.transId = pReq->transId;
|
||||||
pTask->chkInfo.checkpointingId = pReq->checkpointId;
|
pTask->chkInfo.checkpointingId = pReq->checkpointId;
|
||||||
pTask->chkInfo.checkpointNotReadyTasks = streamTaskGetNumOfDownstream(pTask);
|
pTask->chkInfo.checkpointNotReadyTasks = streamTaskGetNumOfDownstream(pTask);
|
||||||
pTask->chkInfo.startTs = taosGetTimestampMs();
|
pTask->chkInfo.startTs = taosGetTimestampMs();
|
||||||
|
@ -273,8 +278,9 @@ void streamTaskClearCheckInfo(SStreamTask* pTask, bool clearChkpReadyMsg) {
|
||||||
pTask->chkInfo.failedId = 0;
|
pTask->chkInfo.failedId = 0;
|
||||||
pTask->chkInfo.startTs = 0; // clear the recorded start time
|
pTask->chkInfo.startTs = 0; // clear the recorded start time
|
||||||
pTask->chkInfo.checkpointNotReadyTasks = 0;
|
pTask->chkInfo.checkpointNotReadyTasks = 0;
|
||||||
// pTask->chkInfo.checkpointAlignCnt = 0;
|
pTask->chkInfo.transId = 0;
|
||||||
pTask->chkInfo.dispatchCheckpointTrigger = false;
|
pTask->chkInfo.dispatchCheckpointTrigger = false;
|
||||||
|
|
||||||
streamTaskOpenAllUpstreamInput(pTask); // open inputQ for all upstream tasks
|
streamTaskOpenAllUpstreamInput(pTask); // open inputQ for all upstream tasks
|
||||||
if (clearChkpReadyMsg) {
|
if (clearChkpReadyMsg) {
|
||||||
streamClearChkptReadyMsg(pTask);
|
streamClearChkptReadyMsg(pTask);
|
||||||
|
@ -341,9 +347,8 @@ int32_t streamSaveTaskCheckpointInfo(SStreamTask* p, int64_t checkpointId) {
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
void streamTaskSetFailedId(SStreamTask* pTask) {
|
void streamTaskSetCheckpointFailedId(SStreamTask* pTask) {
|
||||||
pTask->chkInfo.failedId = pTask->chkInfo.checkpointingId;
|
pTask->chkInfo.failedId = pTask->chkInfo.checkpointingId;
|
||||||
pTask->chkInfo.checkpointId = pTask->chkInfo.checkpointingId;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t getChkpMeta(char* id, char* path, SArray* list) {
|
int32_t getChkpMeta(char* id, char* path, SArray* list) {
|
||||||
|
@ -485,7 +490,7 @@ int32_t streamTaskBuildCheckpoint(SStreamTask* pTask) {
|
||||||
code = streamTaskHandleEvent(pTask->status.pSM, TASK_EVENT_CHECKPOINT_DONE);
|
code = streamTaskHandleEvent(pTask->status.pSM, TASK_EVENT_CHECKPOINT_DONE);
|
||||||
taosThreadMutexUnlock(&pTask->lock);
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
|
||||||
streamTaskSetFailedId(pTask);
|
streamTaskSetCheckpointFailedId(pTask);
|
||||||
stDebug("s-task:%s clear checkpoint flag since gen checkpoint failed, checkpointId:%" PRId64, pTask->id.idStr,
|
stDebug("s-task:%s clear checkpoint flag since gen checkpoint failed, checkpointId:%" PRId64, pTask->id.idStr,
|
||||||
ckId);
|
ckId);
|
||||||
}
|
}
|
||||||
|
|
|
@ -352,6 +352,7 @@ static int32_t doBuildDispatchMsg(SStreamTask* pTask, const SStreamDataBlock* pD
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// it's a new vnode to receive dispatch msg, so add one
|
||||||
if (pReqs[j].blockNum == 0) {
|
if (pReqs[j].blockNum == 0) {
|
||||||
atomic_add_fetch_32(&pTask->outputInfo.shuffleDispatcher.waitingRspCnt, 1);
|
atomic_add_fetch_32(&pTask->outputInfo.shuffleDispatcher.waitingRspCnt, 1);
|
||||||
}
|
}
|
||||||
|
@ -372,8 +373,15 @@ static int32_t doBuildDispatchMsg(SStreamTask* pTask, const SStreamDataBlock* pD
|
||||||
pTask->msgInfo.pData = pReqs;
|
pTask->msgInfo.pData = pReqs;
|
||||||
}
|
}
|
||||||
|
|
||||||
stDebug("s-task:%s build dispatch msg success, msgId:%d, stage:%" PRId64, pTask->id.idStr, pTask->execInfo.dispatch,
|
if (pTask->outputInfo.type == TASK_OUTPUT__FIXED_DISPATCH) {
|
||||||
pTask->pMeta->stage);
|
stDebug("s-task:%s build dispatch msg success, msgId:%d, stage:%" PRId64 " %p", pTask->id.idStr,
|
||||||
|
pTask->execInfo.dispatch, pTask->pMeta->stage, pTask->msgInfo.pData);
|
||||||
|
} else {
|
||||||
|
stDebug("s-task:%s build dispatch msg success, msgId:%d, stage:%" PRId64 " dstVgNum:%d %p", pTask->id.idStr,
|
||||||
|
pTask->execInfo.dispatch, pTask->pMeta->stage, pTask->outputInfo.shuffleDispatcher.waitingRspCnt,
|
||||||
|
pTask->msgInfo.pData);
|
||||||
|
}
|
||||||
|
|
||||||
return code;
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -395,9 +403,11 @@ static int32_t sendDispatchMsg(SStreamTask* pTask, SStreamDispatchReq* pDispatch
|
||||||
SArray* vgInfo = pTask->outputInfo.shuffleDispatcher.dbInfo.pVgroupInfos;
|
SArray* vgInfo = pTask->outputInfo.shuffleDispatcher.dbInfo.pVgroupInfos;
|
||||||
int32_t numOfVgroups = taosArrayGetSize(vgInfo);
|
int32_t numOfVgroups = taosArrayGetSize(vgInfo);
|
||||||
|
|
||||||
stDebug("s-task:%s (child taskId:%d) start to shuffle-dispatch blocks to %d vgroup(s), msgId:%d", id,
|
int32_t actualVgroups = pTask->outputInfo.shuffleDispatcher.waitingRspCnt;
|
||||||
pTask->info.selfChildId, numOfVgroups, msgId);
|
stDebug("s-task:%s (child taskId:%d) start to shuffle-dispatch blocks to %d/%d vgroup(s), msgId:%d", id,
|
||||||
|
pTask->info.selfChildId, actualVgroups, numOfVgroups, msgId);
|
||||||
|
|
||||||
|
int32_t numOfSend = 0;
|
||||||
for (int32_t i = 0; i < numOfVgroups; i++) {
|
for (int32_t i = 0; i < numOfVgroups; i++) {
|
||||||
if (pDispatchMsg[i].blockNum > 0) {
|
if (pDispatchMsg[i].blockNum > 0) {
|
||||||
SVgroupInfo* pVgInfo = taosArrayGet(vgInfo, i);
|
SVgroupInfo* pVgInfo = taosArrayGet(vgInfo, i);
|
||||||
|
@ -408,6 +418,11 @@ static int32_t sendDispatchMsg(SStreamTask* pTask, SStreamDispatchReq* pDispatch
|
||||||
if (code < 0) {
|
if (code < 0) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// no need to try remain, all already send.
|
||||||
|
if (++numOfSend == actualVgroups) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1081,6 +1096,7 @@ int32_t streamNotifyUpstreamContinue(SStreamTask* pTask) {
|
||||||
|
|
||||||
// this message has been sent successfully, let's try next one.
|
// this message has been sent successfully, let's try next one.
|
||||||
static int32_t handleDispatchSuccessRsp(SStreamTask* pTask, int32_t downstreamId) {
|
static int32_t handleDispatchSuccessRsp(SStreamTask* pTask, int32_t downstreamId) {
|
||||||
|
stDebug("s-task:%s destroy dispatch msg:%p", pTask->id.idStr, pTask->msgInfo.pData);
|
||||||
destroyDispatchMsg(pTask->msgInfo.pData, getNumOfDispatchBranch(pTask));
|
destroyDispatchMsg(pTask->msgInfo.pData, getNumOfDispatchBranch(pTask));
|
||||||
|
|
||||||
bool delayDispatch = (pTask->msgInfo.dispatchMsgType == STREAM_INPUT__CHECKPOINT_TRIGGER);
|
bool delayDispatch = (pTask->msgInfo.dispatchMsgType == STREAM_INPUT__CHECKPOINT_TRIGGER);
|
||||||
|
|
|
@ -266,11 +266,12 @@ int32_t streamTaskSetDb(SStreamMeta* pMeta, void* arg, char* key) {
|
||||||
if (pBackend == NULL) {
|
if (pBackend == NULL) {
|
||||||
taosThreadMutexUnlock(&pMeta->backendMutex);
|
taosThreadMutexUnlock(&pMeta->backendMutex);
|
||||||
taosMsleep(1000);
|
taosMsleep(1000);
|
||||||
stDebug("backed holded by other task, restart later, path: %s, key: %s", pMeta->path, key);
|
stDebug("backend held by other task, restart later, path:%s, key:%s", pMeta->path, key);
|
||||||
} else {
|
} else {
|
||||||
taosThreadMutexUnlock(&pMeta->backendMutex);
|
taosThreadMutexUnlock(&pMeta->backendMutex);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
taosThreadMutexLock(&pMeta->backendMutex);
|
taosThreadMutexLock(&pMeta->backendMutex);
|
||||||
pBackend = taskDbOpen(pMeta->path, key, chkpId);
|
pBackend = taskDbOpen(pMeta->path, key, chkpId);
|
||||||
}
|
}
|
||||||
|
@ -297,7 +298,9 @@ void streamMetaRemoveDB(void* arg, char* key) {
|
||||||
|
|
||||||
taosThreadMutexUnlock(&pMeta->backendMutex);
|
taosThreadMutexUnlock(&pMeta->backendMutex);
|
||||||
}
|
}
|
||||||
SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandFunc, int32_t vgId, int64_t stage) {
|
|
||||||
|
SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandFunc, int32_t vgId, int64_t stage,
|
||||||
|
startComplete_fn_t fn) {
|
||||||
int32_t code = -1;
|
int32_t code = -1;
|
||||||
SStreamMeta* pMeta = taosMemoryCalloc(1, sizeof(SStreamMeta));
|
SStreamMeta* pMeta = taosMemoryCalloc(1, sizeof(SStreamMeta));
|
||||||
if (pMeta == NULL) {
|
if (pMeta == NULL) {
|
||||||
|
@ -363,20 +366,9 @@ SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandF
|
||||||
pMeta->stage = stage;
|
pMeta->stage = stage;
|
||||||
pMeta->role = (vgId == SNODE_HANDLE) ? NODE_ROLE_LEADER : NODE_ROLE_UNINIT;
|
pMeta->role = (vgId == SNODE_HANDLE) ? NODE_ROLE_LEADER : NODE_ROLE_UNINIT;
|
||||||
|
|
||||||
|
pMeta->startInfo.completeFn = fn;
|
||||||
pMeta->pTaskDbUnique = taosHashInit(64, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), false, HASH_ENTRY_LOCK);
|
pMeta->pTaskDbUnique = taosHashInit(64, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), false, HASH_ENTRY_LOCK);
|
||||||
|
|
||||||
// pMeta->chkpId = streamGetLatestCheckpointId(pMeta);
|
|
||||||
// pMeta->streamBackend = streamBackendInit(pMeta->path, pMeta->chkpId);
|
|
||||||
// while (pMeta->streamBackend == NULL) {
|
|
||||||
// qError("vgId:%d failed to init stream backend", pMeta->vgId);
|
|
||||||
// taosMsleep(2 * 1000);
|
|
||||||
// qInfo("vgId:%d retry to init stream backend", pMeta->vgId);
|
|
||||||
// pMeta->streamBackend = streamBackendInit(pMeta->path, pMeta->chkpId);
|
|
||||||
// if (pMeta->streamBackend == NULL) {
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// pMeta->streamBackendRid = taosAddRef(streamBackendId, pMeta->streamBackend);
|
|
||||||
|
|
||||||
pMeta->numOfPausedTasks = 0;
|
pMeta->numOfPausedTasks = 0;
|
||||||
pMeta->numOfStreamTasks = 0;
|
pMeta->numOfStreamTasks = 0;
|
||||||
stInfo("vgId:%d open stream meta successfully, latest checkpoint:%" PRId64 ", stage:%" PRId64, vgId, pMeta->chkpId,
|
stInfo("vgId:%d open stream meta successfully, latest checkpoint:%" PRId64 ", stage:%" PRId64, vgId, pMeta->chkpId,
|
||||||
|
@ -384,6 +376,17 @@ SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandF
|
||||||
|
|
||||||
pMeta->rid = taosAddRef(streamMetaId, pMeta);
|
pMeta->rid = taosAddRef(streamMetaId, pMeta);
|
||||||
|
|
||||||
|
// set the attribute when running on Linux OS
|
||||||
|
#if defined LINUX
|
||||||
|
TdThreadRwlockAttr attr;
|
||||||
|
taosThreadRwlockAttrInit(&attr);
|
||||||
|
|
||||||
|
pthread_rwlockattr_setkind_np(&attr, PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP);
|
||||||
|
taosThreadRwlockInit(&pMeta->lock, &attr);
|
||||||
|
|
||||||
|
taosThreadRwlockAttrDestroy(&attr);
|
||||||
|
#endif
|
||||||
|
|
||||||
int64_t* pRid = taosMemoryMalloc(sizeof(int64_t));
|
int64_t* pRid = taosMemoryMalloc(sizeof(int64_t));
|
||||||
memcpy(pRid, &pMeta->rid, sizeof(pMeta->rid));
|
memcpy(pRid, &pMeta->rid, sizeof(pMeta->rid));
|
||||||
metaRefMgtAdd(pMeta->vgId, pRid);
|
metaRefMgtAdd(pMeta->vgId, pRid);
|
||||||
|
@ -394,6 +397,7 @@ SStreamMeta* streamMetaOpen(const char* path, void* ahandle, FTaskExpand expandF
|
||||||
pMeta->qHandle = taosInitScheduler(32, 1, "stream-chkp", NULL);
|
pMeta->qHandle = taosInitScheduler(32, 1, "stream-chkp", NULL);
|
||||||
|
|
||||||
pMeta->bkdChkptMgt = bkdMgtCreate(tpath);
|
pMeta->bkdChkptMgt = bkdMgtCreate(tpath);
|
||||||
|
taosThreadMutexInit(&pMeta->backendMutex, NULL);
|
||||||
|
|
||||||
return pMeta;
|
return pMeta;
|
||||||
|
|
||||||
|
@ -457,7 +461,6 @@ void streamMetaClear(SStreamMeta* pMeta) {
|
||||||
taosRemoveRef(streamBackendId, pMeta->streamBackendRid);
|
taosRemoveRef(streamBackendId, pMeta->streamBackendRid);
|
||||||
|
|
||||||
taosHashClear(pMeta->pTasksMap);
|
taosHashClear(pMeta->pTasksMap);
|
||||||
taosHashClear(pMeta->pTaskDbUnique);
|
|
||||||
|
|
||||||
taosArrayClear(pMeta->pTaskList);
|
taosArrayClear(pMeta->pTaskList);
|
||||||
taosArrayClear(pMeta->chkpSaved);
|
taosArrayClear(pMeta->chkpSaved);
|
||||||
|
@ -616,22 +619,23 @@ int32_t streamMetaGetNumOfTasks(SStreamMeta* pMeta) {
|
||||||
return (int32_t)size;
|
return (int32_t)size;
|
||||||
}
|
}
|
||||||
|
|
||||||
SStreamTask* streamMetaAcquireTask(SStreamMeta* pMeta, int64_t streamId, int32_t taskId) {
|
SStreamTask* streamMetaAcquireTaskNoLock(SStreamMeta* pMeta, int64_t streamId, int32_t taskId) {
|
||||||
streamMetaRLock(pMeta);
|
|
||||||
|
|
||||||
STaskId id = {.streamId = streamId, .taskId = taskId};
|
STaskId id = {.streamId = streamId, .taskId = taskId};
|
||||||
SStreamTask** ppTask = (SStreamTask**)taosHashGet(pMeta->pTasksMap, &id, sizeof(id));
|
SStreamTask** ppTask = (SStreamTask**)taosHashGet(pMeta->pTasksMap, &id, sizeof(id));
|
||||||
if (ppTask != NULL) {
|
if (ppTask == NULL || streamTaskShouldStop(*ppTask)) {
|
||||||
if (!streamTaskShouldStop(*ppTask)) {
|
return NULL;
|
||||||
int32_t ref = atomic_add_fetch_32(&(*ppTask)->refCnt, 1);
|
|
||||||
streamMetaRUnLock(pMeta);
|
|
||||||
stTrace("s-task:%s acquire task, ref:%d", (*ppTask)->id.idStr, ref);
|
|
||||||
return *ppTask;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int32_t ref = atomic_add_fetch_32(&(*ppTask)->refCnt, 1);
|
||||||
|
stTrace("s-task:%s acquire task, ref:%d", (*ppTask)->id.idStr, ref);
|
||||||
|
return *ppTask;
|
||||||
|
}
|
||||||
|
|
||||||
|
SStreamTask* streamMetaAcquireTask(SStreamMeta* pMeta, int64_t streamId, int32_t taskId) {
|
||||||
|
streamMetaRLock(pMeta);
|
||||||
|
SStreamTask* p = streamMetaAcquireTaskNoLock(pMeta, streamId, taskId);
|
||||||
streamMetaRUnLock(pMeta);
|
streamMetaRUnLock(pMeta);
|
||||||
return NULL;
|
return p;
|
||||||
}
|
}
|
||||||
|
|
||||||
void streamMetaReleaseTask(SStreamMeta* UNUSED_PARAM(pMeta), SStreamTask* pTask) {
|
void streamMetaReleaseTask(SStreamMeta* UNUSED_PARAM(pMeta), SStreamTask* pTask) {
|
||||||
|
@ -949,6 +953,7 @@ int32_t tEncodeStreamHbMsg(SEncoder* pEncoder, const SStreamHbMsg* pReq) {
|
||||||
if (tEncodeI64(pEncoder, ps->verEnd) < 0) return -1;
|
if (tEncodeI64(pEncoder, ps->verEnd) < 0) return -1;
|
||||||
if (tEncodeI64(pEncoder, ps->activeCheckpointId) < 0) return -1;
|
if (tEncodeI64(pEncoder, ps->activeCheckpointId) < 0) return -1;
|
||||||
if (tEncodeI8(pEncoder, ps->checkpointFailed) < 0) return -1;
|
if (tEncodeI8(pEncoder, ps->checkpointFailed) < 0) return -1;
|
||||||
|
if (tEncodeI32(pEncoder, ps->chkpointTransId) < 0) return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t numOfVgs = taosArrayGetSize(pReq->pUpdateNodes);
|
int32_t numOfVgs = taosArrayGetSize(pReq->pUpdateNodes);
|
||||||
|
@ -987,6 +992,7 @@ int32_t tDecodeStreamHbMsg(SDecoder* pDecoder, SStreamHbMsg* pReq) {
|
||||||
if (tDecodeI64(pDecoder, &entry.verEnd) < 0) return -1;
|
if (tDecodeI64(pDecoder, &entry.verEnd) < 0) return -1;
|
||||||
if (tDecodeI64(pDecoder, &entry.activeCheckpointId) < 0) return -1;
|
if (tDecodeI64(pDecoder, &entry.activeCheckpointId) < 0) return -1;
|
||||||
if (tDecodeI8(pDecoder, (int8_t*)&entry.checkpointFailed) < 0) return -1;
|
if (tDecodeI8(pDecoder, (int8_t*)&entry.checkpointFailed) < 0) return -1;
|
||||||
|
if (tDecodeI32(pDecoder, &entry.chkpointTransId) < 0) return -1;
|
||||||
|
|
||||||
entry.id.taskId = taskId;
|
entry.id.taskId = taskId;
|
||||||
taosArrayPush(pReq->pTaskStatus, &entry);
|
taosArrayPush(pReq->pTaskStatus, &entry);
|
||||||
|
@ -1060,68 +1066,20 @@ static void addUpdateNodeIntoHbMsg(SStreamTask* pTask, SStreamHbMsg* pMsg) {
|
||||||
taosThreadMutexUnlock(&pTask->lock);
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
void metaHbToMnode(void* param, void* tmrId) {
|
static int32_t metaHeartbeatToMnodeImpl(SStreamMeta* pMeta) {
|
||||||
int64_t rid = *(int64_t*)param;
|
|
||||||
|
|
||||||
SStreamMeta* pMeta = taosAcquireRef(streamMetaId, rid);
|
|
||||||
if (pMeta == NULL) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// need to stop, stop now
|
|
||||||
if (pMeta->pHbInfo->stopFlag == STREAM_META_WILL_STOP) {
|
|
||||||
pMeta->pHbInfo->stopFlag = STREAM_META_OK_TO_STOP;
|
|
||||||
stDebug("vgId:%d jump out of meta timer", pMeta->vgId);
|
|
||||||
taosReleaseRef(streamMetaId, rid);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// not leader not send msg
|
|
||||||
if (pMeta->role != NODE_ROLE_LEADER) {
|
|
||||||
stInfo("vgId:%d role:%d not leader not send hb to mnode", pMeta->vgId, pMeta->role);
|
|
||||||
taosReleaseRef(streamMetaId, rid);
|
|
||||||
pMeta->pHbInfo->hbStart = 0;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// set the hb start time
|
|
||||||
if (pMeta->pHbInfo->hbStart == 0) {
|
|
||||||
pMeta->pHbInfo->hbStart = taosGetTimestampMs();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!waitForEnoughDuration(pMeta->pHbInfo)) {
|
|
||||||
taosTmrReset(metaHbToMnode, META_HB_CHECK_INTERVAL, param, streamTimer, &pMeta->pHbInfo->hbTmr);
|
|
||||||
taosReleaseRef(streamMetaId, rid);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
stDebug("vgId:%d build stream task hb, leader:%d", pMeta->vgId, (pMeta->role == NODE_ROLE_LEADER));
|
|
||||||
|
|
||||||
SStreamHbMsg hbMsg = {0};
|
SStreamHbMsg hbMsg = {0};
|
||||||
SEpSet epset = {0};
|
SEpSet epset = {0};
|
||||||
bool hasMnodeEpset = false;
|
bool hasMnodeEpset = false;
|
||||||
int64_t stage = 0;
|
int32_t numOfTasks = streamMetaGetNumOfTasks(pMeta);
|
||||||
|
|
||||||
streamMetaRLock(pMeta);
|
|
||||||
|
|
||||||
int32_t numOfTasks = streamMetaGetNumOfTasks(pMeta);
|
|
||||||
hbMsg.vgId = pMeta->vgId;
|
hbMsg.vgId = pMeta->vgId;
|
||||||
stage = pMeta->stage;
|
|
||||||
|
|
||||||
SArray* pIdList = taosArrayDup(pMeta->pTaskList, NULL);
|
|
||||||
|
|
||||||
streamMetaRUnLock(pMeta);
|
|
||||||
|
|
||||||
hbMsg.pTaskStatus = taosArrayInit(numOfTasks, sizeof(STaskStatusEntry));
|
hbMsg.pTaskStatus = taosArrayInit(numOfTasks, sizeof(STaskStatusEntry));
|
||||||
hbMsg.pUpdateNodes = taosArrayInit(numOfTasks, sizeof(int32_t));
|
hbMsg.pUpdateNodes = taosArrayInit(numOfTasks, sizeof(int32_t));
|
||||||
|
|
||||||
for (int32_t i = 0; i < numOfTasks; ++i) {
|
for (int32_t i = 0; i < numOfTasks; ++i) {
|
||||||
STaskId* pId = taosArrayGet(pIdList, i);
|
STaskId* pId = taosArrayGet(pMeta->pTaskList, i);
|
||||||
|
|
||||||
streamMetaRLock(pMeta);
|
|
||||||
SStreamTask** pTask = taosHashGet(pMeta->pTasksMap, pId, sizeof(*pId));
|
SStreamTask** pTask = taosHashGet(pMeta->pTasksMap, pId, sizeof(*pId));
|
||||||
streamMetaRUnLock(pMeta);
|
|
||||||
|
|
||||||
if (pTask == NULL) {
|
if (pTask == NULL) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -1135,7 +1093,7 @@ void metaHbToMnode(void* param, void* tmrId) {
|
||||||
.id = *pId,
|
.id = *pId,
|
||||||
.status = streamTaskGetStatus(*pTask, NULL),
|
.status = streamTaskGetStatus(*pTask, NULL),
|
||||||
.nodeId = hbMsg.vgId,
|
.nodeId = hbMsg.vgId,
|
||||||
.stage = stage,
|
.stage = pMeta->stage,
|
||||||
.inputQUsed = SIZE_IN_MiB(streamQueueGetItemSize((*pTask)->inputq.queue)),
|
.inputQUsed = SIZE_IN_MiB(streamQueueGetItemSize((*pTask)->inputq.queue)),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -1148,6 +1106,11 @@ void metaHbToMnode(void* param, void* tmrId) {
|
||||||
if ((*pTask)->chkInfo.checkpointingId != 0) {
|
if ((*pTask)->chkInfo.checkpointingId != 0) {
|
||||||
entry.checkpointFailed = ((*pTask)->chkInfo.failedId >= (*pTask)->chkInfo.checkpointingId);
|
entry.checkpointFailed = ((*pTask)->chkInfo.failedId >= (*pTask)->chkInfo.checkpointingId);
|
||||||
entry.activeCheckpointId = (*pTask)->chkInfo.checkpointingId;
|
entry.activeCheckpointId = (*pTask)->chkInfo.checkpointingId;
|
||||||
|
entry.chkpointTransId = (*pTask)->chkInfo.transId;
|
||||||
|
|
||||||
|
if (entry.checkpointFailed) {
|
||||||
|
stInfo("s-task:%s send kill checkpoint trans info, transId:%d", (*pTask)->id.idStr, (*pTask)->chkInfo.transId);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((*pTask)->exec.pWalReader != NULL) {
|
if ((*pTask)->exec.pWalReader != NULL) {
|
||||||
|
@ -1190,30 +1153,70 @@ void metaHbToMnode(void* param, void* tmrId) {
|
||||||
}
|
}
|
||||||
tEncoderClear(&encoder);
|
tEncoderClear(&encoder);
|
||||||
|
|
||||||
SRpcMsg msg = {
|
SRpcMsg msg = {.info.noResp = 1};
|
||||||
.info.noResp = 1,
|
|
||||||
};
|
|
||||||
initRpcMsg(&msg, TDMT_MND_STREAM_HEARTBEAT, buf, tlen);
|
initRpcMsg(&msg, TDMT_MND_STREAM_HEARTBEAT, buf, tlen);
|
||||||
|
|
||||||
pMeta->pHbInfo->hbCount += 1;
|
pMeta->pHbInfo->hbCount += 1;
|
||||||
|
|
||||||
stDebug("vgId:%d build and send hb to mnode, numOfTasks:%d total:%d", pMeta->vgId, hbMsg.numOfTasks,
|
stDebug("vgId:%d build and send hb to mnode, numOfTasks:%d total:%d", pMeta->vgId, hbMsg.numOfTasks,
|
||||||
pMeta->pHbInfo->hbCount);
|
pMeta->pHbInfo->hbCount);
|
||||||
|
|
||||||
tmsgSendReq(&epset, &msg);
|
tmsgSendReq(&epset, &msg);
|
||||||
} else {
|
} else {
|
||||||
stDebug("vgId:%d no tasks and no mnd epset, not send stream hb to mnode", pMeta->vgId);
|
stDebug("vgId:%d no tasks and no mnd epset, not send stream hb to mnode", pMeta->vgId);
|
||||||
}
|
}
|
||||||
|
|
||||||
_end:
|
_end:
|
||||||
streamMetaClearHbMsg(&hbMsg);
|
streamMetaClearHbMsg(&hbMsg);
|
||||||
taosArrayDestroy(pIdList);
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
void metaHbToMnode(void* param, void* tmrId) {
|
||||||
|
int64_t rid = *(int64_t*)param;
|
||||||
|
|
||||||
|
SStreamMeta* pMeta = taosAcquireRef(streamMetaId, rid);
|
||||||
|
if (pMeta == NULL) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// need to stop, stop now
|
||||||
|
if (pMeta->pHbInfo->stopFlag == STREAM_META_WILL_STOP) {
|
||||||
|
pMeta->pHbInfo->stopFlag = STREAM_META_OK_TO_STOP;
|
||||||
|
stDebug("vgId:%d jump out of meta timer", pMeta->vgId);
|
||||||
|
taosReleaseRef(streamMetaId, rid);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// not leader not send msg
|
||||||
|
if (pMeta->role != NODE_ROLE_LEADER) {
|
||||||
|
stInfo("vgId:%d role:%d not leader not send hb to mnode", pMeta->vgId, pMeta->role);
|
||||||
|
taosReleaseRef(streamMetaId, rid);
|
||||||
|
pMeta->pHbInfo->hbStart = 0;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// set the hb start time
|
||||||
|
if (pMeta->pHbInfo->hbStart == 0) {
|
||||||
|
pMeta->pHbInfo->hbStart = taosGetTimestampMs();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!waitForEnoughDuration(pMeta->pHbInfo)) {
|
||||||
|
taosTmrReset(metaHbToMnode, META_HB_CHECK_INTERVAL, param, streamTimer, &pMeta->pHbInfo->hbTmr);
|
||||||
|
taosReleaseRef(streamMetaId, rid);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
stDebug("vgId:%d build stream task hb, leader:%d", pMeta->vgId, (pMeta->role == NODE_ROLE_LEADER));
|
||||||
|
streamMetaRLock(pMeta);
|
||||||
|
metaHeartbeatToMnodeImpl(pMeta);
|
||||||
|
streamMetaRUnLock(pMeta);
|
||||||
|
|
||||||
taosTmrReset(metaHbToMnode, META_HB_CHECK_INTERVAL, param, streamTimer, &pMeta->pHbInfo->hbTmr);
|
taosTmrReset(metaHbToMnode, META_HB_CHECK_INTERVAL, param, streamTimer, &pMeta->pHbInfo->hbTmr);
|
||||||
taosReleaseRef(streamMetaId, rid);
|
taosReleaseRef(streamMetaId, rid);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool streamMetaTaskInTimer(SStreamMeta* pMeta) {
|
bool streamMetaTaskInTimer(SStreamMeta* pMeta) {
|
||||||
bool inTimer = false;
|
bool inTimer = false;
|
||||||
streamMetaWLock(pMeta);
|
streamMetaRLock(pMeta);
|
||||||
|
|
||||||
void* pIter = NULL;
|
void* pIter = NULL;
|
||||||
while (1) {
|
while (1) {
|
||||||
|
@ -1224,11 +1227,12 @@ bool streamMetaTaskInTimer(SStreamMeta* pMeta) {
|
||||||
|
|
||||||
SStreamTask* pTask = *(SStreamTask**)pIter;
|
SStreamTask* pTask = *(SStreamTask**)pIter;
|
||||||
if (pTask->status.timerActive >= 1) {
|
if (pTask->status.timerActive >= 1) {
|
||||||
|
stDebug("s-task:%s in timer, blocking tasks in vgId:%d restart", pTask->id.idStr, pMeta->vgId);
|
||||||
inTimer = true;
|
inTimer = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
streamMetaWUnLock(pMeta);
|
streamMetaRUnLock(pMeta);
|
||||||
return inTimer;
|
return inTimer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1287,26 +1291,37 @@ void streamMetaResetStartInfo(STaskStartInfo* pStartInfo) {
|
||||||
taosHashClear(pStartInfo->pFailedTaskSet);
|
taosHashClear(pStartInfo->pFailedTaskSet);
|
||||||
pStartInfo->tasksWillRestart = 0;
|
pStartInfo->tasksWillRestart = 0;
|
||||||
pStartInfo->readyTs = 0;
|
pStartInfo->readyTs = 0;
|
||||||
|
|
||||||
// reset the sentinel flag value to be 0
|
// reset the sentinel flag value to be 0
|
||||||
atomic_store_32(&pStartInfo->taskStarting, 0);
|
pStartInfo->taskStarting = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void streamMetaRLock(SStreamMeta* pMeta) {
|
void streamMetaRLock(SStreamMeta* pMeta) {
|
||||||
stTrace("vgId:%d meta-rlock", pMeta->vgId);
|
stTrace("vgId:%d meta-rlock", pMeta->vgId);
|
||||||
taosRLockLatch(&pMeta->lock);
|
taosThreadRwlockRdlock(&pMeta->lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
void streamMetaRUnLock(SStreamMeta* pMeta) {
|
void streamMetaRUnLock(SStreamMeta* pMeta) {
|
||||||
stTrace("vgId:%d meta-runlock", pMeta->vgId);
|
stTrace("vgId:%d meta-runlock", pMeta->vgId);
|
||||||
taosRUnLockLatch(&pMeta->lock);
|
int32_t code = taosThreadRwlockUnlock(&pMeta->lock);
|
||||||
|
if (code != TSDB_CODE_SUCCESS) {
|
||||||
|
stError("vgId:%d meta-runlock failed, code:%d", pMeta->vgId, code);
|
||||||
|
} else {
|
||||||
|
stDebug("vgId:%d meta-runlock completed", pMeta->vgId);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void streamMetaWLock(SStreamMeta* pMeta) {
|
void streamMetaWLock(SStreamMeta* pMeta) {
|
||||||
stTrace("vgId:%d meta-wlock", pMeta->vgId);
|
stTrace("vgId:%d meta-wlock", pMeta->vgId);
|
||||||
taosWLockLatch(&pMeta->lock);
|
taosThreadRwlockWrlock(&pMeta->lock);
|
||||||
|
stTrace("vgId:%d meta-wlock completed", pMeta->vgId);
|
||||||
}
|
}
|
||||||
|
|
||||||
void streamMetaWUnLock(SStreamMeta* pMeta) {
|
void streamMetaWUnLock(SStreamMeta* pMeta) {
|
||||||
stTrace("vgId:%d meta-wunlock", pMeta->vgId);
|
stTrace("vgId:%d meta-wunlock", pMeta->vgId);
|
||||||
taosWUnLockLatch(&pMeta->lock);
|
taosThreadRwlockUnlock(&pMeta->lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void execHelper(struct SSchedMsg* pSchedMsg) {
|
static void execHelper(struct SSchedMsg* pSchedMsg) {
|
||||||
__async_exec_fn_t execFn = (__async_exec_fn_t)pSchedMsg->ahandle;
|
__async_exec_fn_t execFn = (__async_exec_fn_t)pSchedMsg->ahandle;
|
||||||
int32_t code = execFn(pSchedMsg->thandle);
|
int32_t code = execFn(pSchedMsg->thandle);
|
||||||
|
@ -1323,3 +1338,165 @@ int32_t streamMetaAsyncExec(SStreamMeta* pMeta, __stream_async_exec_fn_t fn, voi
|
||||||
schedMsg.msg = code;
|
schedMsg.msg = code;
|
||||||
return taosScheduleTask(pMeta->qHandle, &schedMsg);
|
return taosScheduleTask(pMeta->qHandle, &schedMsg);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SArray* streamMetaSendMsgBeforeCloseTasks(SStreamMeta* pMeta) {
|
||||||
|
SArray* pTaskList = taosArrayDup(pMeta->pTaskList, NULL);
|
||||||
|
|
||||||
|
bool sendMsg = pMeta->sendMsgBeforeClosing;
|
||||||
|
if (!sendMsg) {
|
||||||
|
stDebug("vgId:%d no need to send msg to mnode before closing tasks", pMeta->vgId);
|
||||||
|
return pTaskList;
|
||||||
|
}
|
||||||
|
|
||||||
|
stDebug("vgId:%d send msg to mnode before closing all tasks", pMeta->vgId);
|
||||||
|
|
||||||
|
// send hb msg to mnode before closing all tasks.
|
||||||
|
int32_t numOfTasks = taosArrayGetSize(pTaskList);
|
||||||
|
for (int32_t i = 0; i < numOfTasks; ++i) {
|
||||||
|
SStreamTaskId* pTaskId = taosArrayGet(pTaskList, i);
|
||||||
|
SStreamTask* pTask = streamMetaAcquireTaskNoLock(pMeta, pTaskId->streamId, pTaskId->taskId);
|
||||||
|
if (pTask == NULL) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
taosThreadMutexLock(&pTask->lock);
|
||||||
|
char* p = NULL;
|
||||||
|
ETaskStatus s = streamTaskGetStatus(pTask, &p);
|
||||||
|
if (s == TASK_STATUS__CK) {
|
||||||
|
streamTaskSetCheckpointFailedId(pTask);
|
||||||
|
stDebug("s-task:%s mark the checkpoint:%"PRId64" failed", pTask->id.idStr, pTask->chkInfo.checkpointingId);
|
||||||
|
} else {
|
||||||
|
stDebug("s-task:%s status:%s not reset the checkpoint", pTask->id.idStr, p);
|
||||||
|
}
|
||||||
|
|
||||||
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
}
|
||||||
|
|
||||||
|
metaHeartbeatToMnodeImpl(pMeta);
|
||||||
|
pMeta->sendMsgBeforeClosing = false;
|
||||||
|
return pTaskList;
|
||||||
|
}
|
||||||
|
|
||||||
|
void streamMetaUpdateStageRole(SStreamMeta* pMeta, int64_t stage, bool isLeader) {
|
||||||
|
streamMetaWLock(pMeta);
|
||||||
|
|
||||||
|
int64_t prevStage = pMeta->stage;
|
||||||
|
pMeta->stage = stage;
|
||||||
|
|
||||||
|
// mark the sign to send msg before close all tasks
|
||||||
|
if ((!isLeader) && (pMeta->role == NODE_ROLE_LEADER)) {
|
||||||
|
pMeta->sendMsgBeforeClosing = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
pMeta->role = (isLeader)? NODE_ROLE_LEADER:NODE_ROLE_FOLLOWER;
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
|
|
||||||
|
if (isLeader) {
|
||||||
|
stInfo("vgId:%d update meta stage:%" PRId64 ", prev:%" PRId64 " leader:%d, start to send Hb", pMeta->vgId,
|
||||||
|
prevStage, stage, isLeader);
|
||||||
|
streamMetaStartHb(pMeta);
|
||||||
|
} else {
|
||||||
|
stInfo("vgId:%d update meta stage:%" PRId64 " prev:%" PRId64 " leader:%d sendMsg beforeClosing:%d", pMeta->vgId,
|
||||||
|
prevStage, stage, isLeader, pMeta->sendMsgBeforeClosing);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t streamMetaStopAllTasks(SStreamMeta* pMeta) {
|
||||||
|
streamMetaRLock(pMeta);
|
||||||
|
|
||||||
|
int32_t num = taosArrayGetSize(pMeta->pTaskList);
|
||||||
|
stDebug("vgId:%d stop all %d stream task(s)", pMeta->vgId, num);
|
||||||
|
if (num == 0) {
|
||||||
|
streamMetaRUnLock(pMeta);
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
// send hb msg to mnode before closing all tasks.
|
||||||
|
SArray* pTaskList = streamMetaSendMsgBeforeCloseTasks(pMeta);
|
||||||
|
int32_t numOfTasks = taosArrayGetSize(pTaskList);
|
||||||
|
|
||||||
|
for (int32_t i = 0; i < numOfTasks; ++i) {
|
||||||
|
SStreamTaskId* pTaskId = taosArrayGet(pTaskList, i);
|
||||||
|
SStreamTask* pTask = streamMetaAcquireTaskNoLock(pMeta, pTaskId->streamId, pTaskId->taskId);
|
||||||
|
if (pTask == NULL) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
streamTaskStop(pTask);
|
||||||
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
}
|
||||||
|
|
||||||
|
taosArrayDestroy(pTaskList);
|
||||||
|
|
||||||
|
streamMetaRUnLock(pMeta);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32_t streamMetaStartAllTasks(SStreamMeta* pMeta) {
|
||||||
|
int32_t code = TSDB_CODE_SUCCESS;
|
||||||
|
int32_t vgId = pMeta->vgId;
|
||||||
|
|
||||||
|
int32_t numOfTasks = taosArrayGetSize(pMeta->pTaskList);
|
||||||
|
stInfo("vgId:%d start to check all %d stream task(s) downstream status", vgId, numOfTasks);
|
||||||
|
if (numOfTasks == 0) {
|
||||||
|
stInfo("vgId:%d start tasks completed", pMeta->vgId);
|
||||||
|
return TSDB_CODE_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
SArray* pTaskList = NULL;
|
||||||
|
streamMetaWLock(pMeta);
|
||||||
|
pTaskList = taosArrayDup(pMeta->pTaskList, NULL);
|
||||||
|
taosHashClear(pMeta->startInfo.pReadyTaskSet);
|
||||||
|
taosHashClear(pMeta->startInfo.pFailedTaskSet);
|
||||||
|
pMeta->startInfo.startTs = taosGetTimestampMs();
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
|
|
||||||
|
// broadcast the check downstream tasks msg
|
||||||
|
int64_t now = taosGetTimestampMs();
|
||||||
|
|
||||||
|
for (int32_t i = 0; i < numOfTasks; ++i) {
|
||||||
|
SStreamTaskId* pTaskId = taosArrayGet(pTaskList, i);
|
||||||
|
|
||||||
|
SStreamTask* pTask = streamMetaAcquireTask(pMeta, pTaskId->streamId, pTaskId->taskId);
|
||||||
|
if (pTask == NULL) {
|
||||||
|
stError("vgId:%d failed to acquire task:0x%x during start tasks", pMeta->vgId, pTaskId->taskId);
|
||||||
|
streamMetaUpdateTaskDownstreamStatus(pMeta, pTaskId->streamId, pTaskId->taskId, 0, now, false);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// fill-history task can only be launched by related stream tasks.
|
||||||
|
STaskExecStatisInfo* pInfo = &pTask->execInfo;
|
||||||
|
if (pTask->info.fillHistory == 1) {
|
||||||
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (pTask->status.downstreamReady == 1) {
|
||||||
|
if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
||||||
|
stDebug("s-task:%s downstream ready, no need to check downstream, check only related fill-history task",
|
||||||
|
pTask->id.idStr);
|
||||||
|
streamLaunchFillHistoryTask(pTask);
|
||||||
|
}
|
||||||
|
|
||||||
|
streamMetaUpdateTaskDownstreamStatus(pMeta, pTaskId->streamId, pTaskId->taskId, pInfo->init, pInfo->start, true);
|
||||||
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
EStreamTaskEvent event = (HAS_RELATED_FILLHISTORY_TASK(pTask)) ? TASK_EVENT_INIT_STREAM_SCANHIST : TASK_EVENT_INIT;
|
||||||
|
int32_t ret = streamTaskHandleEvent(pTask->status.pSM, event);
|
||||||
|
if (ret != TSDB_CODE_SUCCESS) {
|
||||||
|
stError("vgId:%d failed to handle event:%d", pMeta->vgId, event);
|
||||||
|
code = ret;
|
||||||
|
|
||||||
|
streamMetaUpdateTaskDownstreamStatus(pMeta, pTaskId->streamId, pTaskId->taskId, pInfo->init, pInfo->start, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
streamMetaReleaseTask(pMeta, pTask);
|
||||||
|
}
|
||||||
|
|
||||||
|
stInfo("vgId:%d start tasks completed", pMeta->vgId);
|
||||||
|
taosArrayDestroy(pTaskList);
|
||||||
|
return code;
|
||||||
|
}
|
|
@ -48,9 +48,9 @@ static void tryLaunchHistoryTask(void* param, void* tmrId);
|
||||||
static void doProcessDownstreamReadyRsp(SStreamTask* pTask);
|
static void doProcessDownstreamReadyRsp(SStreamTask* pTask);
|
||||||
|
|
||||||
int32_t streamTaskSetReady(SStreamTask* pTask) {
|
int32_t streamTaskSetReady(SStreamTask* pTask) {
|
||||||
char* p = NULL;
|
char* p = NULL;
|
||||||
int32_t numOfDowns = streamTaskGetNumOfDownstream(pTask);
|
int32_t numOfDowns = streamTaskGetNumOfDownstream(pTask);
|
||||||
ETaskStatus status = streamTaskGetStatus(pTask, &p);
|
ETaskStatus status = streamTaskGetStatus(pTask, &p);
|
||||||
|
|
||||||
if ((status == TASK_STATUS__SCAN_HISTORY || status == TASK_STATUS__STREAM_SCAN_HISTORY) &&
|
if ((status == TASK_STATUS__SCAN_HISTORY || status == TASK_STATUS__STREAM_SCAN_HISTORY) &&
|
||||||
pTask->info.taskLevel != TASK_LEVEL__SOURCE) {
|
pTask->info.taskLevel != TASK_LEVEL__SOURCE) {
|
||||||
|
@ -66,9 +66,6 @@ int32_t streamTaskSetReady(SStreamTask* pTask) {
|
||||||
int64_t el = (pTask->execInfo.start - pTask->execInfo.init);
|
int64_t el = (pTask->execInfo.start - pTask->execInfo.init);
|
||||||
stDebug("s-task:%s all %d downstream ready, init completed, elapsed time:%" PRId64 "ms, task status:%s",
|
stDebug("s-task:%s all %d downstream ready, init completed, elapsed time:%" PRId64 "ms, task status:%s",
|
||||||
pTask->id.idStr, numOfDowns, el, p);
|
pTask->id.idStr, numOfDowns, el, p);
|
||||||
|
|
||||||
streamMetaUpdateTaskDownstreamStatus(pTask->pMeta, pTask->id.streamId, pTask->id.taskId, pTask->execInfo.init,
|
|
||||||
pTask->execInfo.start, true);
|
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -209,7 +206,11 @@ void streamTaskCheckDownstream(SStreamTask* pTask) {
|
||||||
|
|
||||||
int32_t numOfVgs = taosArrayGetSize(vgInfo);
|
int32_t numOfVgs = taosArrayGetSize(vgInfo);
|
||||||
pTask->notReadyTasks = numOfVgs;
|
pTask->notReadyTasks = numOfVgs;
|
||||||
pTask->checkReqIds = taosArrayInit(numOfVgs, sizeof(int64_t));
|
if (pTask->checkReqIds == NULL) {
|
||||||
|
pTask->checkReqIds = taosArrayInit(numOfVgs, sizeof(int64_t));
|
||||||
|
} else {
|
||||||
|
taosArrayClear(pTask->checkReqIds);
|
||||||
|
}
|
||||||
|
|
||||||
stDebug("s-task:%s check %d downstream tasks, ver:%" PRId64 "-%" PRId64 " window:%" PRId64 "-%" PRId64,
|
stDebug("s-task:%s check %d downstream tasks, ver:%" PRId64 "-%" PRId64 " window:%" PRId64 "-%" PRId64,
|
||||||
pTask->id.idStr, numOfVgs, pRange->range.minVer, pRange->range.maxVer, pWindow->skey, pWindow->ekey);
|
pTask->id.idStr, numOfVgs, pRange->range.minVer, pRange->range.maxVer, pWindow->skey, pWindow->ekey);
|
||||||
|
@ -312,9 +313,24 @@ int32_t streamTaskCheckStatus(SStreamTask* pTask, int32_t upstreamTaskId, int32_
|
||||||
stError("s-task:%s receive check msg from upstream task:0x%x(vgId:%d), new stage received:%" PRId64
|
stError("s-task:%s receive check msg from upstream task:0x%x(vgId:%d), new stage received:%" PRId64
|
||||||
", prev:%" PRId64,
|
", prev:%" PRId64,
|
||||||
id, upstreamTaskId, vgId, stage, pInfo->stage);
|
id, upstreamTaskId, vgId, stage, pInfo->stage);
|
||||||
|
// record the checkpoint failure id and sent to mnode
|
||||||
|
taosThreadMutexLock(&pTask->lock);
|
||||||
|
ETaskStatus status = streamTaskGetStatus(pTask, NULL);
|
||||||
|
if (status == TASK_STATUS__CK) {
|
||||||
|
streamTaskSetCheckpointFailedId(pTask);
|
||||||
|
}
|
||||||
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pInfo->stage != stage) {
|
if (pInfo->stage != stage) {
|
||||||
|
|
||||||
|
taosThreadMutexLock(&pTask->lock);
|
||||||
|
ETaskStatus status = streamTaskGetStatus(pTask, NULL);
|
||||||
|
if (status == TASK_STATUS__CK) {
|
||||||
|
streamTaskSetCheckpointFailedId(pTask);
|
||||||
|
}
|
||||||
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
|
||||||
return TASK_UPSTREAM_NEW_STAGE;
|
return TASK_UPSTREAM_NEW_STAGE;
|
||||||
} else if (pTask->status.downstreamReady != 1) {
|
} else if (pTask->status.downstreamReady != 1) {
|
||||||
stDebug("s-task:%s vgId:%d leader:%d, downstream not ready", id, vgId, (pTask->pMeta->role == NODE_ROLE_LEADER));
|
stDebug("s-task:%s vgId:%d leader:%d, downstream not ready", id, vgId, (pTask->pMeta->role == NODE_ROLE_LEADER));
|
||||||
|
@ -363,10 +379,11 @@ int32_t streamTaskOnScanhistoryTaskReady(SStreamTask* pTask) {
|
||||||
stDebug("s-task:%s enter into scan-history data stage, status:%s", id, p);
|
stDebug("s-task:%s enter into scan-history data stage, status:%s", id, p);
|
||||||
streamTaskStartScanHistory(pTask);
|
streamTaskStartScanHistory(pTask);
|
||||||
|
|
||||||
// start the related fill-history task, when current task is ready
|
// NOTE: there will be an deadlock if launch fill history here.
|
||||||
if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
// // start the related fill-history task, when current task is ready
|
||||||
streamLaunchFillHistoryTask(pTask);
|
// if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
||||||
}
|
// streamLaunchFillHistoryTask(pTask);
|
||||||
|
// }
|
||||||
|
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
@ -380,6 +397,17 @@ void doProcessDownstreamReadyRsp(SStreamTask* pTask) {
|
||||||
}
|
}
|
||||||
|
|
||||||
streamTaskOnHandleEventSuccess(pTask->status.pSM, event);
|
streamTaskOnHandleEventSuccess(pTask->status.pSM, event);
|
||||||
|
|
||||||
|
int64_t initTs = pTask->execInfo.init;
|
||||||
|
int64_t startTs = pTask->execInfo.start;
|
||||||
|
streamMetaUpdateTaskDownstreamStatus(pTask->pMeta, pTask->id.streamId, pTask->id.taskId, initTs, startTs, true);
|
||||||
|
|
||||||
|
// start the related fill-history task, when current task is ready
|
||||||
|
// not invoke in success callback due to the deadlock.
|
||||||
|
if (HAS_RELATED_FILLHISTORY_TASK(pTask)) {
|
||||||
|
stDebug("s-task:%s try to launch related fill-history task", pTask->id.idStr);
|
||||||
|
streamLaunchFillHistoryTask(pTask);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void addIntoNodeUpdateList(SStreamTask* pTask, int32_t nodeId) {
|
static void addIntoNodeUpdateList(SStreamTask* pTask, int32_t nodeId) {
|
||||||
|
@ -436,8 +464,7 @@ int32_t streamProcessCheckRsp(SStreamTask* pTask, const SStreamTaskCheckRsp* pRs
|
||||||
ASSERT(left >= 0);
|
ASSERT(left >= 0);
|
||||||
|
|
||||||
if (left == 0) {
|
if (left == 0) {
|
||||||
taosArrayDestroy(pTask->checkReqIds);
|
pTask->checkReqIds = taosArrayDestroy(pTask->checkReqIds);;
|
||||||
pTask->checkReqIds = NULL;
|
|
||||||
|
|
||||||
doProcessDownstreamReadyRsp(pTask);
|
doProcessDownstreamReadyRsp(pTask);
|
||||||
} else {
|
} else {
|
||||||
|
@ -458,8 +485,7 @@ int32_t streamProcessCheckRsp(SStreamTask* pTask, const SStreamTaskCheckRsp* pRs
|
||||||
if (pRsp->status == TASK_UPSTREAM_NEW_STAGE) {
|
if (pRsp->status == TASK_UPSTREAM_NEW_STAGE) {
|
||||||
stError("s-task:%s vgId:%d self vnode-transfer/leader-change/restart detected, old stage:%" PRId64
|
stError("s-task:%s vgId:%d self vnode-transfer/leader-change/restart detected, old stage:%" PRId64
|
||||||
", current stage:%" PRId64
|
", current stage:%" PRId64
|
||||||
", "
|
", not check wait for downstream task nodeUpdate, and all tasks restart",
|
||||||
"not check wait for downstream task nodeUpdate, and all tasks restart",
|
|
||||||
id, pRsp->upstreamNodeId, pRsp->oldStage, pTask->pMeta->stage);
|
id, pRsp->upstreamNodeId, pRsp->oldStage, pTask->pMeta->stage);
|
||||||
addIntoNodeUpdateList(pTask, pRsp->upstreamNodeId);
|
addIntoNodeUpdateList(pTask, pRsp->upstreamNodeId);
|
||||||
} else {
|
} else {
|
||||||
|
@ -1096,19 +1122,23 @@ int32_t streamMetaUpdateTaskDownstreamStatus(SStreamMeta* pMeta, int64_t streamI
|
||||||
pStartInfo->readyTs = taosGetTimestampMs();
|
pStartInfo->readyTs = taosGetTimestampMs();
|
||||||
pStartInfo->elapsedTime = (pStartInfo->startTs != 0) ? pStartInfo->readyTs - pStartInfo->startTs : 0;
|
pStartInfo->elapsedTime = (pStartInfo->startTs != 0) ? pStartInfo->readyTs - pStartInfo->startTs : 0;
|
||||||
|
|
||||||
stDebug("vgId:%d all %d task(s) check downstream completed, last completed task:0x%x startTs:%" PRId64
|
stDebug("vgId:%d all %d task(s) check downstream completed, last completed task:0x%x (succ:%d) startTs:%" PRId64
|
||||||
", readyTs:%" PRId64 " total elapsed time:%.2fs",
|
", readyTs:%" PRId64 " total elapsed time:%.2fs",
|
||||||
pMeta->vgId, numOfTotal, taskId, pStartInfo->startTs, pStartInfo->readyTs,
|
pMeta->vgId, numOfTotal, taskId, ready, pStartInfo->startTs, pStartInfo->readyTs,
|
||||||
pStartInfo->elapsedTime / 1000.0);
|
pStartInfo->elapsedTime / 1000.0);
|
||||||
|
|
||||||
// print the initialization elapsed time and info
|
// print the initialization elapsed time and info
|
||||||
displayStatusInfo(pMeta, pStartInfo->pReadyTaskSet, true);
|
displayStatusInfo(pMeta, pStartInfo->pReadyTaskSet, true);
|
||||||
displayStatusInfo(pMeta, pStartInfo->pFailedTaskSet, false);
|
displayStatusInfo(pMeta, pStartInfo->pFailedTaskSet, false);
|
||||||
streamMetaResetStartInfo(pStartInfo);
|
streamMetaResetStartInfo(pStartInfo);
|
||||||
|
streamMetaWUnLock(pMeta);
|
||||||
|
|
||||||
|
pStartInfo->completeFn(pMeta);
|
||||||
} else {
|
} else {
|
||||||
stDebug("vgId:%d recv check down results:%d, total:%d", pMeta->vgId, numOfRecv, numOfTotal);
|
streamMetaWUnLock(pMeta);
|
||||||
|
stDebug("vgId:%d recv check downstream results, s-task:0x%x succ:%d, received:%d, total:%d", pMeta->vgId, taskId,
|
||||||
|
ready, numOfRecv, numOfTotal);
|
||||||
}
|
}
|
||||||
|
|
||||||
streamMetaWUnLock(pMeta);
|
|
||||||
return TSDB_CODE_SUCCESS;
|
return TSDB_CODE_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
|
@ -796,5 +796,6 @@ void streamTaskStatusCopy(STaskStatusEntry* pDst, const STaskStatusEntry* pSrc)
|
||||||
pDst->sinkDataSize = pSrc->sinkDataSize;
|
pDst->sinkDataSize = pSrc->sinkDataSize;
|
||||||
pDst->activeCheckpointId = pSrc->activeCheckpointId;
|
pDst->activeCheckpointId = pSrc->activeCheckpointId;
|
||||||
pDst->checkpointFailed = pSrc->checkpointFailed;
|
pDst->checkpointFailed = pSrc->checkpointFailed;
|
||||||
|
pDst->chkpointTransId = pSrc->chkpointTransId;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -160,6 +160,45 @@ static STaskStateTrans* streamTaskFindTransform(ETaskStatus state, const EStream
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int32_t doHandleWaitingEvent(SStreamTaskSM* pSM, const char* pEventName, SStreamTask* pTask) {
|
||||||
|
int32_t code = TSDB_CODE_SUCCESS;
|
||||||
|
int64_t el = (taosGetTimestampMs() - pSM->startTs);
|
||||||
|
stDebug("s-task:%s handle event:%s completed, elapsed time:%" PRId64 "ms state:%s -> %s", pTask->id.idStr,
|
||||||
|
pEventName, el, pSM->prev.state.name, pSM->current.name);
|
||||||
|
|
||||||
|
SAttachedEventInfo* pEvtInfo = taosArrayGet(pSM->pWaitingEventList, 0);
|
||||||
|
|
||||||
|
// OK, let's handle the attached event, since the task has reached the required status now
|
||||||
|
if (pSM->current.state == pEvtInfo->status) {
|
||||||
|
stDebug("s-task:%s handle the event:%s in waiting list, state:%s", pTask->id.idStr,
|
||||||
|
GET_EVT_NAME(pEvtInfo->event), pSM->current.name);
|
||||||
|
|
||||||
|
// remove it
|
||||||
|
taosArrayPop(pSM->pWaitingEventList);
|
||||||
|
|
||||||
|
STaskStateTrans* pNextTrans = streamTaskFindTransform(pSM->current.state, pEvtInfo->event);
|
||||||
|
ASSERT(pSM->pActiveTrans == NULL && pNextTrans != NULL);
|
||||||
|
|
||||||
|
pSM->pActiveTrans = pNextTrans;
|
||||||
|
pSM->startTs = taosGetTimestampMs();
|
||||||
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
|
||||||
|
code = pNextTrans->pAction(pSM->pTask);
|
||||||
|
if (pNextTrans->autoInvokeEndFn) {
|
||||||
|
return streamTaskOnHandleEventSuccess(pSM, pNextTrans->event);
|
||||||
|
} else {
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
stDebug("s-task:%s state:%s event:%s in waiting list, req state:%s not fulfilled, put it back", pTask->id.idStr,
|
||||||
|
pSM->current.name, GET_EVT_NAME(pEvtInfo->event),
|
||||||
|
StreamTaskStatusList[pEvtInfo->status].name);
|
||||||
|
}
|
||||||
|
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
|
||||||
void streamTaskRestoreStatus(SStreamTask* pTask) {
|
void streamTaskRestoreStatus(SStreamTask* pTask) {
|
||||||
SStreamTaskSM* pSM = pTask->status.pSM;
|
SStreamTaskSM* pSM = pTask->status.pSM;
|
||||||
|
|
||||||
|
@ -175,7 +214,13 @@ void streamTaskRestoreStatus(SStreamTask* pTask) {
|
||||||
pSM->prev.evt = 0;
|
pSM->prev.evt = 0;
|
||||||
|
|
||||||
pSM->startTs = taosGetTimestampMs();
|
pSM->startTs = taosGetTimestampMs();
|
||||||
stDebug("s-task:%s restore status, %s -> %s", pTask->id.idStr, pSM->prev.state.name, pSM->current.name);
|
|
||||||
|
if (taosArrayGetSize(pSM->pWaitingEventList) > 0) {
|
||||||
|
stDebug("s-task:%s restore status, %s -> %s, and then handle waiting event", pTask->id.idStr, pSM->prev.state.name, pSM->current.name);
|
||||||
|
doHandleWaitingEvent(pSM, "restore-pause/halt", pTask);
|
||||||
|
} else {
|
||||||
|
stDebug("s-task:%s restore status, %s -> %s", pTask->id.idStr, pSM->prev.state.name, pSM->current.name);
|
||||||
|
}
|
||||||
|
|
||||||
taosThreadMutexUnlock(&pTask->lock);
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
}
|
}
|
||||||
|
@ -343,39 +388,7 @@ int32_t streamTaskOnHandleEventSuccess(SStreamTaskSM* pSM, EStreamTaskEvent even
|
||||||
pTrans->pSuccAction(pTask);
|
pTrans->pSuccAction(pTask);
|
||||||
|
|
||||||
if (taosArrayGetSize(pSM->pWaitingEventList) > 0) {
|
if (taosArrayGetSize(pSM->pWaitingEventList) > 0) {
|
||||||
int64_t el = (taosGetTimestampMs() - pSM->startTs);
|
doHandleWaitingEvent(pSM, GET_EVT_NAME(pTrans->event), pTask);
|
||||||
stDebug("s-task:%s handle event:%s completed, elapsed time:%" PRId64 "ms state:%s -> %s", pTask->id.idStr,
|
|
||||||
GET_EVT_NAME(pTrans->event), el, pSM->prev.state.name, pSM->current.name);
|
|
||||||
|
|
||||||
SAttachedEventInfo* pEvtInfo = taosArrayGet(pSM->pWaitingEventList, 0);
|
|
||||||
|
|
||||||
// OK, let's handle the attached event, since the task has reached the required status now
|
|
||||||
if (pSM->current.state == pEvtInfo->status) {
|
|
||||||
stDebug("s-task:%s handle the event:%s in waiting list, state:%s", pTask->id.idStr,
|
|
||||||
GET_EVT_NAME(pEvtInfo->event), pSM->current.name);
|
|
||||||
|
|
||||||
// remove it
|
|
||||||
taosArrayPop(pSM->pWaitingEventList);
|
|
||||||
|
|
||||||
STaskStateTrans* pNextTrans = streamTaskFindTransform(pSM->current.state, pEvtInfo->event);
|
|
||||||
ASSERT(pSM->pActiveTrans == NULL && pNextTrans != NULL);
|
|
||||||
|
|
||||||
pSM->pActiveTrans = pNextTrans;
|
|
||||||
pSM->startTs = taosGetTimestampMs();
|
|
||||||
taosThreadMutexUnlock(&pTask->lock);
|
|
||||||
|
|
||||||
int32_t code = pNextTrans->pAction(pSM->pTask);
|
|
||||||
if (pNextTrans->autoInvokeEndFn) {
|
|
||||||
return streamTaskOnHandleEventSuccess(pSM, pNextTrans->event);
|
|
||||||
} else {
|
|
||||||
return code;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
taosThreadMutexUnlock(&pTask->lock);
|
|
||||||
stDebug("s-task:%s state:%s event:%s in waiting list, req state:%s not fulfilled, put it back", pTask->id.idStr,
|
|
||||||
pSM->current.name, GET_EVT_NAME(pEvtInfo->event),
|
|
||||||
StreamTaskStatusList[pEvtInfo->status].name);
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
taosThreadMutexUnlock(&pTask->lock);
|
taosThreadMutexUnlock(&pTask->lock);
|
||||||
|
|
||||||
|
|
|
@ -1162,9 +1162,12 @@ int32_t syncNodeRestore(SSyncNode* pSyncNode) {
|
||||||
ASSERTS(pSyncNode->pLogStore != NULL, "log store not created");
|
ASSERTS(pSyncNode->pLogStore != NULL, "log store not created");
|
||||||
ASSERTS(pSyncNode->pLogBuf != NULL, "ring log buffer not created");
|
ASSERTS(pSyncNode->pLogBuf != NULL, "ring log buffer not created");
|
||||||
|
|
||||||
|
taosThreadMutexLock(&pSyncNode->pLogBuf->mutex);
|
||||||
SyncIndex lastVer = pSyncNode->pLogStore->syncLogLastIndex(pSyncNode->pLogStore);
|
SyncIndex lastVer = pSyncNode->pLogStore->syncLogLastIndex(pSyncNode->pLogStore);
|
||||||
SyncIndex commitIndex = pSyncNode->pLogStore->syncLogCommitIndex(pSyncNode->pLogStore);
|
SyncIndex commitIndex = pSyncNode->pLogStore->syncLogCommitIndex(pSyncNode->pLogStore);
|
||||||
SyncIndex endIndex = pSyncNode->pLogBuf->endIndex;
|
SyncIndex endIndex = pSyncNode->pLogBuf->endIndex;
|
||||||
|
taosThreadMutexUnlock(&pSyncNode->pLogBuf->mutex);
|
||||||
|
|
||||||
if (lastVer != -1 && endIndex != lastVer + 1) {
|
if (lastVer != -1 && endIndex != lastVer + 1) {
|
||||||
terrno = TSDB_CODE_WAL_LOG_INCOMPLETE;
|
terrno = TSDB_CODE_WAL_LOG_INCOMPLETE;
|
||||||
sError("vgId:%d, failed to restore sync node since %s. expected lastLogIndex:%" PRId64 ", lastVer:%" PRId64 "",
|
sError("vgId:%d, failed to restore sync node since %s. expected lastLogIndex:%" PRId64 ", lastVer:%" PRId64 "",
|
||||||
|
|
|
@ -1087,7 +1087,10 @@ static int32_t syncSnapSenderExchgSnapInfo(SSyncNode *pSyncNode, SSyncSnapshotSe
|
||||||
|
|
||||||
// sender
|
// sender
|
||||||
static int32_t syncNodeOnSnapshotPrepRsp(SSyncNode *pSyncNode, SSyncSnapshotSender *pSender, SyncSnapshotRsp *pMsg) {
|
static int32_t syncNodeOnSnapshotPrepRsp(SSyncNode *pSyncNode, SSyncSnapshotSender *pSender, SyncSnapshotRsp *pMsg) {
|
||||||
|
int32_t code = -1;
|
||||||
SSnapshot snapshot = {0};
|
SSnapshot snapshot = {0};
|
||||||
|
|
||||||
|
taosThreadMutexLock(&pSender->pSndBuf->mutex);
|
||||||
pSyncNode->pFsm->FpGetSnapshotInfo(pSyncNode->pFsm, &snapshot);
|
pSyncNode->pFsm->FpGetSnapshotInfo(pSyncNode->pFsm, &snapshot);
|
||||||
|
|
||||||
// prepare <begin, end>
|
// prepare <begin, end>
|
||||||
|
@ -1103,20 +1106,24 @@ static int32_t syncNodeOnSnapshotPrepRsp(SSyncNode *pSyncNode, SSyncSnapshotSend
|
||||||
// start reader
|
// start reader
|
||||||
if (pMsg->payloadType == TDMT_SYNC_PREP_SNAPSHOT_REPLY) {
|
if (pMsg->payloadType == TDMT_SYNC_PREP_SNAPSHOT_REPLY) {
|
||||||
if (syncSnapSenderExchgSnapInfo(pSyncNode, pSender, pMsg) != 0) {
|
if (syncSnapSenderExchgSnapInfo(pSyncNode, pSender, pMsg) != 0) {
|
||||||
return -1;
|
goto _out;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t code = pSyncNode->pFsm->FpSnapshotStartRead(pSyncNode->pFsm, &pSender->snapshotParam, &pSender->pReader);
|
code = pSyncNode->pFsm->FpSnapshotStartRead(pSyncNode->pFsm, &pSender->snapshotParam, &pSender->pReader);
|
||||||
if (code != 0) {
|
if (code != 0) {
|
||||||
sSError(pSender, "prepare snapshot failed since %s", terrstr());
|
sSError(pSender, "prepare snapshot failed since %s", terrstr());
|
||||||
return -1;
|
goto _out;
|
||||||
}
|
}
|
||||||
|
|
||||||
// update next index
|
// update next index
|
||||||
syncIndexMgrSetIndex(pSyncNode->pNextIndex, &pMsg->srcId, snapshot.lastApplyIndex + 1);
|
syncIndexMgrSetIndex(pSyncNode->pNextIndex, &pMsg->srcId, snapshot.lastApplyIndex + 1);
|
||||||
|
|
||||||
return snapshotSend(pSender);
|
code = snapshotSend(pSender);
|
||||||
|
|
||||||
|
_out:
|
||||||
|
taosThreadMutexUnlock(&pSender->pSndBuf->mutex);
|
||||||
|
return code;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int32_t snapshotSenderSignatureCmp(SSyncSnapshotSender *pSender, SyncSnapshotRsp *pMsg) {
|
static int32_t snapshotSenderSignatureCmp(SSyncSnapshotSender *pSender, SyncSnapshotRsp *pMsg) {
|
||||||
|
|
|
@ -72,7 +72,7 @@ TEST(osTest, osSystem) {
|
||||||
const int sysLen = 64;
|
const int sysLen = 64;
|
||||||
char osSysName[sysLen];
|
char osSysName[sysLen];
|
||||||
int ret = taosGetOsReleaseName(osSysName, NULL, NULL, sysLen);
|
int ret = taosGetOsReleaseName(osSysName, NULL, NULL, sysLen);
|
||||||
printf("os systeme name:%s\n", osSysName);
|
printf("os system name:%s\n", osSysName);
|
||||||
ASSERT_EQ(ret, 0);
|
ASSERT_EQ(ret, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -286,6 +286,7 @@ TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_CLOG_IS_NULL, "Transaction commitlog
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_NETWORK_UNAVAILL, "Unable to establish connection While execute transaction and will continue in the background")
|
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_NETWORK_UNAVAILL, "Unable to establish connection While execute transaction and will continue in the background")
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_MND_LAST_TRANS_NOT_FINISHED, "Last Transaction not finished")
|
TAOS_DEFINE_ERROR(TSDB_CODE_MND_LAST_TRANS_NOT_FINISHED, "Last Transaction not finished")
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_SYNC_TIMEOUT, "Sync timeout While execute transaction and will continue in the background")
|
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_SYNC_TIMEOUT, "Sync timeout While execute transaction and will continue in the background")
|
||||||
|
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_CTX_SWITCH, "Transaction context switch")
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_UNKNOW_ERROR, "Unknown transaction error")
|
TAOS_DEFINE_ERROR(TSDB_CODE_MND_TRANS_UNKNOW_ERROR, "Unknown transaction error")
|
||||||
|
|
||||||
// mnode-mq
|
// mnode-mq
|
||||||
|
@ -622,6 +623,7 @@ TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_DUP_TIMESTAMP, "Duplicate timestamps
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_FORMAT_ERR, "Func to_timestamp failed for format mismatch")
|
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_FORMAT_ERR, "Func to_timestamp failed for format mismatch")
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_TS_ERR, "Func to_timestamp failed for wrong timestamp")
|
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_TS_ERR, "Func to_timestamp failed for wrong timestamp")
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_NOT_SUPPORTED, "Func to_timestamp failed for unsupported timestamp format")
|
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_TIMESTAMP_FAILED_NOT_SUPPORTED, "Func to_timestamp failed for unsupported timestamp format")
|
||||||
|
TAOS_DEFINE_ERROR(TSDB_CODE_FUNC_TO_CHAR_NOT_SUPPORTED, "Func to_char failed for unsupported format")
|
||||||
|
|
||||||
//udf
|
//udf
|
||||||
TAOS_DEFINE_ERROR(TSDB_CODE_UDF_STOPPING, "udf is stopping")
|
TAOS_DEFINE_ERROR(TSDB_CODE_UDF_STOPPING, "udf is stopping")
|
||||||
|
|
|
@ -337,14 +337,10 @@ static int32_t taosOpenNewLogFile() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void taosResetLog() {
|
void taosResetLog() {
|
||||||
char lastName[LOG_FILE_NAME_LEN + 20];
|
|
||||||
sprintf(lastName, "%s.%d", tsLogObj.logName, tsLogObj.flag);
|
|
||||||
|
|
||||||
// force create a new log file
|
// force create a new log file
|
||||||
tsLogObj.lines = tsNumOfLogLines + 10;
|
tsLogObj.lines = tsNumOfLogLines + 10;
|
||||||
|
|
||||||
taosOpenNewLogFile();
|
taosOpenNewLogFile();
|
||||||
(void)taosRemoveFile(lastName);
|
|
||||||
|
|
||||||
uInfo("==================================");
|
uInfo("==================================");
|
||||||
uInfo(" reset log file ");
|
uInfo(" reset log file ");
|
||||||
|
|
|
@ -0,0 +1,58 @@
|
||||||
|
{
|
||||||
|
"filetype": "insert",
|
||||||
|
"cfgdir": "/etc/taos",
|
||||||
|
"host": "127.0.0.1",
|
||||||
|
"port": 6030,
|
||||||
|
"user": "root",
|
||||||
|
"password": "taosdata",
|
||||||
|
"connection_pool_size": 8,
|
||||||
|
"num_of_records_per_req": 2000,
|
||||||
|
"thread_count": 2,
|
||||||
|
"create_table_thread_count": 1,
|
||||||
|
"confirm_parameter_prompt": "no",
|
||||||
|
"databases": [
|
||||||
|
{
|
||||||
|
"dbinfo": {
|
||||||
|
"name": "db",
|
||||||
|
"drop": "yes",
|
||||||
|
"vgroups": 2,
|
||||||
|
"replica": 1,
|
||||||
|
"duration":"1d",
|
||||||
|
"keep": "3d,6d,30d"
|
||||||
|
},
|
||||||
|
"super_tables": [
|
||||||
|
{
|
||||||
|
"name": "stb",
|
||||||
|
"child_table_exists": "no",
|
||||||
|
"childtable_count": 4,
|
||||||
|
"insert_rows": 1000000,
|
||||||
|
"childtable_prefix": "d",
|
||||||
|
"insert_mode": "taosc",
|
||||||
|
"timestamp_step": 1000,
|
||||||
|
"start_timestamp":"now-12d",
|
||||||
|
"columns": [
|
||||||
|
{ "type": "bool", "name": "bc"},
|
||||||
|
{ "type": "float", "name": "fc" },
|
||||||
|
{ "type": "double", "name": "dc"},
|
||||||
|
{ "type": "tinyint", "name": "ti", "values":["1"]},
|
||||||
|
{ "type": "smallint", "name": "si" },
|
||||||
|
{ "type": "int", "name": "ic" },
|
||||||
|
{ "type": "bigint", "name": "bi" },
|
||||||
|
{ "type": "utinyint", "name": "uti"},
|
||||||
|
{ "type": "usmallint", "name": "usi"},
|
||||||
|
{ "type": "uint", "name": "ui" },
|
||||||
|
{ "type": "ubigint", "name": "ubi"},
|
||||||
|
{ "type": "binary", "name": "bin", "len": 32},
|
||||||
|
{ "type": "nchar", "name": "nch", "len": 64}
|
||||||
|
],
|
||||||
|
"tags": [
|
||||||
|
{"type": "tinyint", "name": "groupid","max": 10,"min": 1},
|
||||||
|
{"name": "location","type": "binary", "len": 16, "values":
|
||||||
|
["San Francisco", "Los Angles", "San Diego", "San Jose", "Palo Alto", "Campbell", "Mountain View","Sunnyvale", "Santa Clara", "Cupertino"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
|
@ -15,26 +15,62 @@ import sys
|
||||||
import time
|
import time
|
||||||
|
|
||||||
import taos
|
import taos
|
||||||
|
import frame
|
||||||
|
import frame.etool
|
||||||
|
|
||||||
from frame.log import *
|
from frame.log import *
|
||||||
from frame.cases import *
|
from frame.cases import *
|
||||||
from frame.sql import *
|
from frame.sql import *
|
||||||
|
from frame.caseBase import *
|
||||||
|
from frame import *
|
||||||
|
|
||||||
class TDTestCase:
|
|
||||||
# init
|
class TDTestCase(TBase):
|
||||||
def init(self, conn, logSql, replicaVar=1):
|
|
||||||
self.replicaVar = int(replicaVar)
|
|
||||||
tdLog.debug(f"start to excute {__file__}")
|
def insertData(self):
|
||||||
tdSql.init(conn.cursor(), True)
|
tdLog.info(f"insert data.")
|
||||||
|
# taosBenchmark run
|
||||||
|
json = etool.curFile(__file__, "mlevel_basic.json")
|
||||||
|
etool.runBenchmark(json=json)
|
||||||
|
|
||||||
|
tdSql.execute(f"use {self.db}")
|
||||||
|
# set insert data information
|
||||||
|
self.childtable_count = 4
|
||||||
|
self.insert_rows = 1000000
|
||||||
|
self.timestamp_step = 1000
|
||||||
|
|
||||||
|
def doAction(self):
|
||||||
|
tdLog.info(f"do action.")
|
||||||
|
self.flushDb()
|
||||||
|
self.trimDb()
|
||||||
|
self.compactDb()
|
||||||
|
|
||||||
# run
|
# run
|
||||||
def run(self):
|
def run(self):
|
||||||
# check two db query result same
|
tdLog.debug(f"start to excute {__file__}")
|
||||||
tdLog.info(f"hello world.")
|
|
||||||
|
# insert data
|
||||||
|
self.insertData()
|
||||||
|
|
||||||
|
# check insert data correct
|
||||||
|
self.checkInsertCorrect()
|
||||||
|
|
||||||
|
# save
|
||||||
|
self.snapshotAgg()
|
||||||
|
|
||||||
|
# do action
|
||||||
|
self.doAction()
|
||||||
|
|
||||||
|
# check save agg result correct
|
||||||
|
self.checkAggCorrect()
|
||||||
|
|
||||||
|
# check insert correct again
|
||||||
|
self.checkInsertCorrect()
|
||||||
|
|
||||||
# stop
|
|
||||||
def stop(self):
|
|
||||||
tdSql.close()
|
|
||||||
tdLog.success(f"{__file__} successfully executed")
|
tdLog.success(f"{__file__} successfully executed")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
tdCases.addLinux(__file__, TDTestCase())
|
tdCases.addLinux(__file__, TDTestCase())
|
||||||
tdCases.addWindows(__file__, TDTestCase())
|
tdCases.addWindows(__file__, TDTestCase())
|
|
@ -0,0 +1,106 @@
|
||||||
|
###################################################################
|
||||||
|
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
||||||
|
# All rights reserved.
|
||||||
|
#
|
||||||
|
# This file is proprietary and confidential to TAOS Technologies.
|
||||||
|
# No part of this file may be reproduced, stored, transmitted,
|
||||||
|
# disclosed or used in any form or by any means other than as
|
||||||
|
# expressly provided by the written permission from Jianhui Tao
|
||||||
|
#
|
||||||
|
###################################################################
|
||||||
|
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
import datetime
|
||||||
|
|
||||||
|
from frame.log import *
|
||||||
|
from frame.sql import *
|
||||||
|
|
||||||
|
# test case base
|
||||||
|
class TBase:
|
||||||
|
|
||||||
|
#
|
||||||
|
# frame call
|
||||||
|
#
|
||||||
|
|
||||||
|
# init
|
||||||
|
def init(self, conn, logSql, replicaVar=1):
|
||||||
|
# save param
|
||||||
|
self.replicaVar = int(replicaVar)
|
||||||
|
tdSql.init(conn.cursor(), True)
|
||||||
|
|
||||||
|
# record server information
|
||||||
|
self.dnodeNum = 0
|
||||||
|
self.mnodeNum = 0
|
||||||
|
self.mLevel = 0
|
||||||
|
self.mLevelDisk = 0
|
||||||
|
|
||||||
|
# test case information
|
||||||
|
self.db = "db"
|
||||||
|
self.stb = "stb"
|
||||||
|
|
||||||
|
# variant in taosBenchmark json
|
||||||
|
self.childtable_count = 2
|
||||||
|
self.insert_rows = 1000000
|
||||||
|
self.timestamp_step = 1000
|
||||||
|
|
||||||
|
# sql
|
||||||
|
self.sqlSum = f"select sum(ic) from {self.stb}"
|
||||||
|
self.sqlMax = f"select max(ic) from {self.stb}"
|
||||||
|
self.sqlMin = f"select min(ic) from {self.stb}"
|
||||||
|
self.sqlAvg = f"select avg(ic) from {self.stb}"
|
||||||
|
|
||||||
|
|
||||||
|
# stop
|
||||||
|
def stop(self):
|
||||||
|
tdSql.close()
|
||||||
|
|
||||||
|
|
||||||
|
#
|
||||||
|
# db action
|
||||||
|
#
|
||||||
|
|
||||||
|
def trimDb(self):
|
||||||
|
tdSql.execute(f"trim database {self.db}")
|
||||||
|
|
||||||
|
def compactDb(self):
|
||||||
|
tdSql.execute(f"compact database {self.db}")
|
||||||
|
|
||||||
|
def flushDb(self):
|
||||||
|
tdSql.execute(f"flush database {self.db}")
|
||||||
|
|
||||||
|
#
|
||||||
|
# check db correct
|
||||||
|
#
|
||||||
|
|
||||||
|
# basic
|
||||||
|
def checkInsertCorrect(self):
|
||||||
|
# check count
|
||||||
|
sql = f"select count(*) from {self.stb}"
|
||||||
|
tdSql.checkAgg(sql, self.childtable_count * self.insert_rows)
|
||||||
|
|
||||||
|
# check child table count
|
||||||
|
sql = f" select count(*) from (select count(*) as cnt , tbname from {self.stb} group by tbname) where cnt = {self.insert_rows} "
|
||||||
|
tdSql.checkAgg(sql, self.childtable_count)
|
||||||
|
|
||||||
|
# check step
|
||||||
|
sql = f"select count(*) from (select diff(ts) as dif from {self.stb} partition by tbname) where dif != {self.timestamp_step}"
|
||||||
|
tdSql.checkAgg(sql, 0)
|
||||||
|
|
||||||
|
# save agg result
|
||||||
|
def snapshotAgg(self):
|
||||||
|
|
||||||
|
self.sum = tdSql.getFirstValue(self.sqlSum)
|
||||||
|
self.avg = tdSql.getFirstValue(self.sqlAvg)
|
||||||
|
self.min = tdSql.getFirstValue(self.sqlMin)
|
||||||
|
self.max = tdSql.getFirstValue(self.sqlMax)
|
||||||
|
|
||||||
|
# check agg
|
||||||
|
def checkAggCorrect(self):
|
||||||
|
tdSql.checkAgg(self.sqlSum, self.sum)
|
||||||
|
tdSql.checkAgg(self.sqlAvg, self.avg)
|
||||||
|
tdSql.checkAgg(self.sqlMin, self.min)
|
||||||
|
tdSql.checkAgg(self.sqlMax, self.max)
|
|
@ -23,7 +23,7 @@ import taos
|
||||||
from frame.log import *
|
from frame.log import *
|
||||||
from frame.sql import *
|
from frame.sql import *
|
||||||
from frame.cases import *
|
from frame.cases import *
|
||||||
from frame.dnodes import *
|
from frame.server.dnodes import *
|
||||||
from frame.common import *
|
from frame.common import *
|
||||||
from frame.constant import *
|
from frame.constant import *
|
||||||
from dataclasses import dataclass,field
|
from dataclasses import dataclass,field
|
||||||
|
|
|
@ -1,502 +0,0 @@
|
||||||
###################################################################
|
|
||||||
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
|
||||||
# All rights reserved.
|
|
||||||
#
|
|
||||||
# This file is proprietary and confidential to TAOS Technologies.
|
|
||||||
# No part of this file may be reproduced, stored, transmitted,
|
|
||||||
# disclosed or used in any form or by any means other than as
|
|
||||||
# expressly provided by the written permission from Jianhui Tao
|
|
||||||
#
|
|
||||||
###################################################################
|
|
||||||
|
|
||||||
# -*- coding: utf-8 -*-
|
|
||||||
|
|
||||||
import sys
|
|
||||||
import os
|
|
||||||
import os.path
|
|
||||||
import subprocess
|
|
||||||
from frame.log import *
|
|
||||||
|
|
||||||
|
|
||||||
class TDSimClient:
|
|
||||||
def __init__(self):
|
|
||||||
self.testCluster = False
|
|
||||||
|
|
||||||
self.cfgDict = {
|
|
||||||
"numOfLogLines": "100000000",
|
|
||||||
"numOfThreadsPerCore": "2.0",
|
|
||||||
"locale": "en_US.UTF-8",
|
|
||||||
"charset": "UTF-8",
|
|
||||||
"asyncLog": "0",
|
|
||||||
"minTablesPerVnode": "4",
|
|
||||||
"maxTablesPerVnode": "1000",
|
|
||||||
"tableIncStepPerVnode": "10000",
|
|
||||||
"maxVgroupsPerDb": "1000",
|
|
||||||
"sdbDebugFlag": "143",
|
|
||||||
"rpcDebugFlag": "135",
|
|
||||||
"tmrDebugFlag": "131",
|
|
||||||
"cDebugFlag": "135",
|
|
||||||
"udebugFlag": "135",
|
|
||||||
"jnidebugFlag": "135",
|
|
||||||
"qdebugFlag": "135",
|
|
||||||
"telemetryReporting": "0",
|
|
||||||
}
|
|
||||||
def init(self, path):
|
|
||||||
self.__init__()
|
|
||||||
self.path = path
|
|
||||||
|
|
||||||
def getLogDir(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","psim","log")
|
|
||||||
return self.logDir
|
|
||||||
|
|
||||||
def getCfgDir(self):
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","psim","cfg")
|
|
||||||
return self.cfgDir
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def addExtraCfg(self, option, value):
|
|
||||||
self.cfgDict.update({option: value})
|
|
||||||
|
|
||||||
def cfg(self, option, value):
|
|
||||||
cmd = "echo %s %s >> %s" % (option, value, self.cfgPath)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def deploy(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","psim","log")
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","psim","cfg")
|
|
||||||
self.cfgPath = os.path.join(self.path,"sim","psim","cfg","taos.cfg")
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "touch " + self.cfgPath
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.cfg("masterIp", "192.168.0.1")
|
|
||||||
self.cfg("secondIp", "192.168.0.2")
|
|
||||||
self.cfg("logDir", self.logDir)
|
|
||||||
|
|
||||||
for key, value in self.cfgDict.items():
|
|
||||||
self.cfg(key, value)
|
|
||||||
|
|
||||||
tdLog.debug("psim is deployed and configured by %s" % (self.cfgPath))
|
|
||||||
|
|
||||||
|
|
||||||
class TDDnode:
|
|
||||||
def __init__(self, index):
|
|
||||||
self.index = index
|
|
||||||
self.running = 0
|
|
||||||
self.deployed = 0
|
|
||||||
self.testCluster = False
|
|
||||||
self.valgrind = 0
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
self.path = path
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def setValgrind(self, value):
|
|
||||||
self.valgrind = value
|
|
||||||
|
|
||||||
def getDataSize(self):
|
|
||||||
totalSize = 0
|
|
||||||
|
|
||||||
if (self.deployed == 1):
|
|
||||||
for dirpath, dirnames, filenames in os.walk(self.dataDir):
|
|
||||||
for f in filenames:
|
|
||||||
fp = os.path.join(dirpath, f)
|
|
||||||
|
|
||||||
if not os.path.islink(fp):
|
|
||||||
totalSize = totalSize + os.path.getsize(fp)
|
|
||||||
|
|
||||||
return totalSize
|
|
||||||
|
|
||||||
def deploy(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","dnode%d" % self.index, "log")
|
|
||||||
self.dataDir = os.path.join(self.path,"sim","dnode%d" % self.index, "data")
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg")
|
|
||||||
self.cfgPath = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg","taos.cfg")
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.dataDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.dataDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "touch " + self.cfgPath
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.startIP()
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.cfg("masterIp", "192.168.0.1")
|
|
||||||
self.cfg("secondIp", "192.168.0.2")
|
|
||||||
self.cfg("publicIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("internalIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("privateIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("dataDir", self.dataDir)
|
|
||||||
self.cfg("logDir", self.logDir)
|
|
||||||
self.cfg("numOfLogLines", "100000000")
|
|
||||||
self.cfg("mnodeEqualVnodeNum", "0")
|
|
||||||
self.cfg("walLevel", "2")
|
|
||||||
self.cfg("fsync", "1000")
|
|
||||||
self.cfg("statusInterval", "1")
|
|
||||||
self.cfg("numOfMnodes", "3")
|
|
||||||
self.cfg("numOfThreadsPerCore", "2.0")
|
|
||||||
self.cfg("monitor", "0")
|
|
||||||
self.cfg("maxVnodeConnections", "30000")
|
|
||||||
self.cfg("maxMgmtConnections", "30000")
|
|
||||||
self.cfg("maxMeterConnections", "30000")
|
|
||||||
self.cfg("maxShellConns", "30000")
|
|
||||||
self.cfg("locale", "en_US.UTF-8")
|
|
||||||
self.cfg("charset", "UTF-8")
|
|
||||||
self.cfg("asyncLog", "0")
|
|
||||||
self.cfg("anyIp", "0")
|
|
||||||
self.cfg("dDebugFlag", "135")
|
|
||||||
self.cfg("mDebugFlag", "135")
|
|
||||||
self.cfg("sdbDebugFlag", "135")
|
|
||||||
self.cfg("rpcDebugFlag", "135")
|
|
||||||
self.cfg("tmrDebugFlag", "131")
|
|
||||||
self.cfg("cDebugFlag", "135")
|
|
||||||
self.cfg("httpDebugFlag", "135")
|
|
||||||
self.cfg("monitorDebugFlag", "135")
|
|
||||||
self.cfg("udebugFlag", "135")
|
|
||||||
self.cfg("jnidebugFlag", "135")
|
|
||||||
self.cfg("qdebugFlag", "135")
|
|
||||||
self.deployed = 1
|
|
||||||
tdLog.debug(
|
|
||||||
"dnode:%d is deployed and configured by %s" %
|
|
||||||
(self.index, self.cfgPath))
|
|
||||||
|
|
||||||
def getBuildPath(self):
|
|
||||||
selfPath = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
|
|
||||||
if ("community" in selfPath):
|
|
||||||
projPath = selfPath[:selfPath.find("community")]
|
|
||||||
else:
|
|
||||||
projPath = selfPath[:selfPath.find("tests")]
|
|
||||||
|
|
||||||
for root, dirs, files in os.walk(projPath):
|
|
||||||
if ("taosd" in files):
|
|
||||||
rootRealPath = os.path.dirname(os.path.realpath(root))
|
|
||||||
if ("packaging" not in rootRealPath):
|
|
||||||
buildPath = root[:len(root)-len("/build/bin")]
|
|
||||||
break
|
|
||||||
return buildPath
|
|
||||||
|
|
||||||
def start(self):
|
|
||||||
buildPath = self.getBuildPath()
|
|
||||||
|
|
||||||
if (buildPath == ""):
|
|
||||||
tdLog.exit("taosd not found!")
|
|
||||||
else:
|
|
||||||
tdLog.info("taosd found in %s" % buildPath)
|
|
||||||
|
|
||||||
binPath = buildPath + "/build/bin/taosd"
|
|
||||||
|
|
||||||
if self.deployed == 0:
|
|
||||||
tdLog.exit("dnode:%d is not deployed" % (self.index))
|
|
||||||
|
|
||||||
if self.valgrind == 0:
|
|
||||||
cmd = "nohup %s -c %s > /dev/null 2>&1 & " % (
|
|
||||||
binPath, self.cfgDir)
|
|
||||||
else:
|
|
||||||
valgrindCmdline = "valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes"
|
|
||||||
|
|
||||||
cmd = "nohup %s %s -c %s 2>&1 & " % (
|
|
||||||
valgrindCmdline, binPath, self.cfgDir)
|
|
||||||
|
|
||||||
print(cmd)
|
|
||||||
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
self.running = 1
|
|
||||||
tdLog.debug("dnode:%d is running with %s " % (self.index, cmd))
|
|
||||||
|
|
||||||
tdLog.debug("wait 5 seconds for the dnode:%d to start." % (self.index))
|
|
||||||
time.sleep(5)
|
|
||||||
|
|
||||||
def stop(self):
|
|
||||||
if self.valgrind == 0:
|
|
||||||
toBeKilled = "taosd"
|
|
||||||
else:
|
|
||||||
toBeKilled = "valgrind.bin"
|
|
||||||
|
|
||||||
if self.running != 0:
|
|
||||||
psCmd = "ps -ef|grep -w %s| grep -v grep | awk '{print $2}'" % toBeKilled
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -INT %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
for port in range(6030, 6041):
|
|
||||||
fuserCmd = "fuser -k -n tcp %d" % port
|
|
||||||
os.system(fuserCmd)
|
|
||||||
if self.valgrind:
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
self.running = 0
|
|
||||||
tdLog.debug("dnode:%d is stopped by kill -INT" % (self.index))
|
|
||||||
|
|
||||||
def forcestop(self):
|
|
||||||
if self.valgrind == 0:
|
|
||||||
toBeKilled = "taosd"
|
|
||||||
else:
|
|
||||||
toBeKilled = "valgrind.bin"
|
|
||||||
|
|
||||||
if self.running != 0:
|
|
||||||
psCmd = "ps -ef|grep -w %s| grep -v grep | awk '{print $2}'" % toBeKilled
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -KILL %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
for port in range(6030, 6041):
|
|
||||||
fuserCmd = "fuser -k -n tcp %d" % port
|
|
||||||
os.system(fuserCmd)
|
|
||||||
if self.valgrind:
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
self.running = 0
|
|
||||||
tdLog.debug("dnode:%d is stopped by kill -KILL" % (self.index))
|
|
||||||
|
|
||||||
def startIP(self):
|
|
||||||
cmd = "sudo ifconfig lo:%d 192.168.0.%d up" % (self.index, self.index)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def stopIP(self):
|
|
||||||
cmd = "sudo ifconfig lo:%d 192.168.0.%d down" % (
|
|
||||||
self.index, self.index)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def cfg(self, option, value):
|
|
||||||
cmd = "echo %s %s >> %s" % (option, value, self.cfgPath)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def getDnodeRootDir(self, index):
|
|
||||||
dnodeRootDir = os.path.join(self.path,"sim","psim","dnode%d" % index)
|
|
||||||
return dnodeRootDir
|
|
||||||
|
|
||||||
def getDnodesRootDir(self):
|
|
||||||
dnodesRootDir = os.path.join(self.path,"sim","psim")
|
|
||||||
return dnodesRootDir
|
|
||||||
|
|
||||||
|
|
||||||
class TDDnodes:
|
|
||||||
def __init__(self):
|
|
||||||
self.dnodes = []
|
|
||||||
self.dnodes.append(TDDnode(1))
|
|
||||||
self.dnodes.append(TDDnode(2))
|
|
||||||
self.dnodes.append(TDDnode(3))
|
|
||||||
self.dnodes.append(TDDnode(4))
|
|
||||||
self.dnodes.append(TDDnode(5))
|
|
||||||
self.dnodes.append(TDDnode(6))
|
|
||||||
self.dnodes.append(TDDnode(7))
|
|
||||||
self.dnodes.append(TDDnode(8))
|
|
||||||
self.dnodes.append(TDDnode(9))
|
|
||||||
self.dnodes.append(TDDnode(10))
|
|
||||||
self.simDeployed = False
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
psCmd = "ps -ef|grep -w taosd| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
psCmd = "ps -ef|grep -w valgrind.bin| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
binPath = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
binPath = binPath + "/../../../debug/"
|
|
||||||
tdLog.debug("binPath %s" % (binPath))
|
|
||||||
binPath = os.path.realpath(binPath)
|
|
||||||
tdLog.debug("binPath real path %s" % (binPath))
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/lib/libtaos.so /usr/local/lib/taos/" % (binPath)
|
|
||||||
# tdLog.debug(cmd)
|
|
||||||
# os.system(cmd)
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/bin/taos /usr/local/bin/taos/" % (binPath)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
# tdLog.debug("execute %s" % (cmd))
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/bin/taosd /usr/local/bin/taos/" % (binPath)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
# tdLog.debug("execute %s" % (cmd))
|
|
||||||
|
|
||||||
if path == "":
|
|
||||||
# self.path = os.path.expanduser('~')
|
|
||||||
self.path = os.path.abspath(binPath + "../../")
|
|
||||||
else:
|
|
||||||
self.path = os.path.realpath(path)
|
|
||||||
|
|
||||||
for i in range(len(self.dnodes)):
|
|
||||||
self.dnodes[i].init(self.path)
|
|
||||||
|
|
||||||
self.sim = TDSimClient()
|
|
||||||
self.sim.init(self.path)
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def setValgrind(self, value):
|
|
||||||
self.valgrind = value
|
|
||||||
|
|
||||||
def deploy(self, index):
|
|
||||||
self.sim.setTestCluster(self.testCluster)
|
|
||||||
|
|
||||||
if (self.simDeployed == False):
|
|
||||||
self.sim.deploy()
|
|
||||||
self.simDeployed = True
|
|
||||||
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].setTestCluster(self.testCluster)
|
|
||||||
self.dnodes[index - 1].setValgrind(self.valgrind)
|
|
||||||
self.dnodes[index - 1].deploy()
|
|
||||||
|
|
||||||
def cfg(self, index, option, value):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].cfg(option, value)
|
|
||||||
|
|
||||||
def start(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].start()
|
|
||||||
|
|
||||||
def stop(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].stop()
|
|
||||||
|
|
||||||
def getDataSize(self, index):
|
|
||||||
self.check(index)
|
|
||||||
return self.dnodes[index - 1].getDataSize()
|
|
||||||
|
|
||||||
def forcestop(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].forcestop()
|
|
||||||
|
|
||||||
def startIP(self, index):
|
|
||||||
self.check(index)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.dnodes[index - 1].startIP()
|
|
||||||
|
|
||||||
def stopIP(self, index):
|
|
||||||
self.check(index)
|
|
||||||
|
|
||||||
if self.dnodes[index - 1].testCluster:
|
|
||||||
self.dnodes[index - 1].stopIP()
|
|
||||||
|
|
||||||
def check(self, index):
|
|
||||||
if index < 1 or index > 10:
|
|
||||||
tdLog.exit("index:%d should on a scale of [1, 10]" % (index))
|
|
||||||
|
|
||||||
def stopAll(self):
|
|
||||||
tdLog.info("stop all dnodes")
|
|
||||||
for i in range(len(self.dnodes)):
|
|
||||||
self.dnodes[i].stop()
|
|
||||||
|
|
||||||
psCmd = "ps -ef | grep -w taosd | grep 'root' | grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
if processID:
|
|
||||||
cmd = "sudo systemctl stop taosd"
|
|
||||||
os.system(cmd)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
psCmd = "ps -ef|grep -w taosd| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
psCmd = "ps -ef|grep -w valgrind.bin| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def getDnodesRootDir(self):
|
|
||||||
dnodesRootDir = "%s/sim" % (self.path)
|
|
||||||
return dnodesRootDir
|
|
||||||
|
|
||||||
def getSimCfgPath(self):
|
|
||||||
return self.sim.getCfgDir()
|
|
||||||
|
|
||||||
def getSimLogPath(self):
|
|
||||||
return self.sim.getLogDir()
|
|
||||||
|
|
||||||
def addSimExtraCfg(self, option, value):
|
|
||||||
self.sim.addExtraCfg(option, value)
|
|
||||||
|
|
||||||
|
|
||||||
tdDnodes = TDDnodes()
|
|
|
@ -1,500 +0,0 @@
|
||||||
###################################################################
|
|
||||||
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
|
||||||
# All rights reserved.
|
|
||||||
#
|
|
||||||
# This file is proprietary and confidential to TAOS Technologies.
|
|
||||||
# No part of this file may be reproduced, stored, transmitted,
|
|
||||||
# disclosed or used in any form or by any means other than as
|
|
||||||
# expressly provided by the written permission from Jianhui Tao
|
|
||||||
#
|
|
||||||
###################################################################
|
|
||||||
|
|
||||||
# -*- coding: utf-8 -*-
|
|
||||||
|
|
||||||
import sys
|
|
||||||
import os
|
|
||||||
import os.path
|
|
||||||
import subprocess
|
|
||||||
from frame.log import *
|
|
||||||
|
|
||||||
|
|
||||||
class TDSimClient:
|
|
||||||
def __init__(self):
|
|
||||||
self.testCluster = False
|
|
||||||
|
|
||||||
self.cfgDict = {
|
|
||||||
"numOfLogLines": "100000000",
|
|
||||||
"numOfThreadsPerCore": "2.0",
|
|
||||||
"locale": "en_US.UTF-8",
|
|
||||||
"charset": "UTF-8",
|
|
||||||
"asyncLog": "0",
|
|
||||||
"anyIp": "0",
|
|
||||||
"sdbDebugFlag": "135",
|
|
||||||
"rpcDebugFlag": "135",
|
|
||||||
"tmrDebugFlag": "131",
|
|
||||||
"cDebugFlag": "135",
|
|
||||||
"udebugFlag": "135",
|
|
||||||
"jnidebugFlag": "135",
|
|
||||||
"qdebugFlag": "135",
|
|
||||||
"telemetryReporting": "0",
|
|
||||||
}
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
self.__init__()
|
|
||||||
self.path = path
|
|
||||||
|
|
||||||
def getLogDir(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","psim","log")
|
|
||||||
return self.logDir
|
|
||||||
|
|
||||||
def getCfgDir(self):
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","psim","cfg")
|
|
||||||
return self.cfgDir
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def addExtraCfg(self, option, value):
|
|
||||||
self.cfgDict.update({option: value})
|
|
||||||
|
|
||||||
def cfg(self, option, value):
|
|
||||||
cmd = "echo %s %s >> %s" % (option, value, self.cfgPath)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def deploy(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","psim","log")
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","psim","cfg")
|
|
||||||
self.cfgPath = os.path.join(self.path,"sim","psim","cfg","taos.cfg")
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "touch " + self.cfgPath
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.cfg("masterIp", "192.168.0.1")
|
|
||||||
self.cfg("secondIp", "192.168.0.2")
|
|
||||||
self.cfg("logDir", self.logDir)
|
|
||||||
|
|
||||||
for key, value in self.cfgDict.items():
|
|
||||||
self.cfg(key, value)
|
|
||||||
|
|
||||||
tdLog.debug("psim is deployed and configured by %s" % (self.cfgPath))
|
|
||||||
|
|
||||||
|
|
||||||
class TDDnode:
|
|
||||||
def __init__(self, index):
|
|
||||||
self.index = index
|
|
||||||
self.running = 0
|
|
||||||
self.deployed = 0
|
|
||||||
self.testCluster = False
|
|
||||||
self.valgrind = 0
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
self.path = path
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def setValgrind(self, value):
|
|
||||||
self.valgrind = value
|
|
||||||
|
|
||||||
def getDataSize(self):
|
|
||||||
totalSize = 0
|
|
||||||
|
|
||||||
if (self.deployed == 1):
|
|
||||||
for dirpath, dirnames, filenames in os.walk(self.dataDir):
|
|
||||||
for f in filenames:
|
|
||||||
fp = os.path.join(dirpath, f)
|
|
||||||
|
|
||||||
if not os.path.islink(fp):
|
|
||||||
totalSize = totalSize + os.path.getsize(fp)
|
|
||||||
|
|
||||||
return totalSize
|
|
||||||
|
|
||||||
def deploy(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","dnode%d" % self.index, "log")
|
|
||||||
self.dataDir = os.path.join(self.path,"sim","dnode%d" % self.index, "data")
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg")
|
|
||||||
self.cfgPath = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg","taos.cfg")
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.dataDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.dataDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "touch " + self.cfgPath
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.startIP()
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.cfg("masterIp", "192.168.0.1")
|
|
||||||
self.cfg("secondIp", "192.168.0.2")
|
|
||||||
self.cfg("publicIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("internalIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("privateIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("dataDir", self.dataDir)
|
|
||||||
self.cfg("logDir", self.logDir)
|
|
||||||
self.cfg("numOfLogLines", "100000000")
|
|
||||||
self.cfg("mnodeEqualVnodeNum", "0")
|
|
||||||
self.cfg("walLevel", "2")
|
|
||||||
self.cfg("fsync", "1000")
|
|
||||||
self.cfg("statusInterval", "1")
|
|
||||||
self.cfg("numOfMnodes", "3")
|
|
||||||
self.cfg("numOfThreadsPerCore", "2.0")
|
|
||||||
self.cfg("monitor", "0")
|
|
||||||
self.cfg("maxVnodeConnections", "30000")
|
|
||||||
self.cfg("maxMgmtConnections", "30000")
|
|
||||||
self.cfg("maxMeterConnections", "30000")
|
|
||||||
self.cfg("maxShellConns", "30000")
|
|
||||||
self.cfg("locale", "en_US.UTF-8")
|
|
||||||
self.cfg("charset", "UTF-8")
|
|
||||||
self.cfg("asyncLog", "0")
|
|
||||||
self.cfg("anyIp", "0")
|
|
||||||
self.cfg("dDebugFlag", "135")
|
|
||||||
self.cfg("mDebugFlag", "135")
|
|
||||||
self.cfg("sdbDebugFlag", "135")
|
|
||||||
self.cfg("rpcDebugFlag", "135")
|
|
||||||
self.cfg("tmrDebugFlag", "131")
|
|
||||||
self.cfg("cDebugFlag", "135")
|
|
||||||
self.cfg("httpDebugFlag", "135")
|
|
||||||
self.cfg("monitorDebugFlag", "135")
|
|
||||||
self.cfg("udebugFlag", "135")
|
|
||||||
self.cfg("jnidebugFlag", "135")
|
|
||||||
self.cfg("qdebugFlag", "135")
|
|
||||||
self.deployed = 1
|
|
||||||
tdLog.debug(
|
|
||||||
"dnode:%d is deployed and configured by %s" %
|
|
||||||
(self.index, self.cfgPath))
|
|
||||||
|
|
||||||
def getBuildPath(self):
|
|
||||||
selfPath = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
|
|
||||||
if ("community" in selfPath):
|
|
||||||
projPath = selfPath[:selfPath.find("community")]
|
|
||||||
else:
|
|
||||||
projPath = selfPath[:selfPath.find("tests")]
|
|
||||||
|
|
||||||
for root, dirs, files in os.walk(projPath):
|
|
||||||
if ("taosd" in files):
|
|
||||||
rootRealPath = os.path.dirname(os.path.realpath(root))
|
|
||||||
if ("packaging" not in rootRealPath):
|
|
||||||
buildPath = root[:len(root)-len("/build/bin")]
|
|
||||||
break
|
|
||||||
return buildPath
|
|
||||||
|
|
||||||
def start(self):
|
|
||||||
buildPath = self.getBuildPath()
|
|
||||||
|
|
||||||
if (buildPath == ""):
|
|
||||||
tdLog.exit("taosd not found!")
|
|
||||||
else:
|
|
||||||
tdLog.info("taosd found in %s" % buildPath)
|
|
||||||
|
|
||||||
binPath = buildPath + "/build/bin/taosd"
|
|
||||||
|
|
||||||
if self.deployed == 0:
|
|
||||||
tdLog.exit("dnode:%d is not deployed" % (self.index))
|
|
||||||
|
|
||||||
if self.valgrind == 0:
|
|
||||||
cmd = "nohup %s -c %s --random-file-fail-factor 0 > /dev/null 2>&1 & " % (
|
|
||||||
binPath, self.cfgDir)
|
|
||||||
else:
|
|
||||||
valgrindCmdline = "valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes"
|
|
||||||
|
|
||||||
cmd = "nohup %s %s -c %s 2>&1 & " % (
|
|
||||||
valgrindCmdline, binPath, self.cfgDir)
|
|
||||||
|
|
||||||
print(cmd)
|
|
||||||
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
self.running = 1
|
|
||||||
tdLog.debug("dnode:%d is running with %s " % (self.index, cmd))
|
|
||||||
|
|
||||||
tdLog.debug("wait 5 seconds for the dnode:%d to start." % (self.index))
|
|
||||||
time.sleep(5)
|
|
||||||
|
|
||||||
def stop(self):
|
|
||||||
if self.valgrind == 0:
|
|
||||||
toBeKilled = "taosd"
|
|
||||||
else:
|
|
||||||
toBeKilled = "valgrind.bin"
|
|
||||||
|
|
||||||
if self.running != 0:
|
|
||||||
psCmd = "ps -ef|grep -w %s| grep -v grep | awk '{print $2}'" % toBeKilled
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -INT %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
for port in range(6030, 6041):
|
|
||||||
fuserCmd = "fuser -k -n tcp %d" % port
|
|
||||||
os.system(fuserCmd)
|
|
||||||
if self.valgrind:
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
self.running = 0
|
|
||||||
tdLog.debug("dnode:%d is stopped by kill -INT" % (self.index))
|
|
||||||
|
|
||||||
def forcestop(self):
|
|
||||||
if self.valgrind == 0:
|
|
||||||
toBeKilled = "taosd"
|
|
||||||
else:
|
|
||||||
toBeKilled = "valgrind.bin"
|
|
||||||
|
|
||||||
if self.running != 0:
|
|
||||||
psCmd = "ps -ef|grep -w %s| grep -v grep | awk '{print $2}'" % toBeKilled
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -KILL %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
for port in range(6030, 6041):
|
|
||||||
fuserCmd = "fuser -k -n tcp %d" % port
|
|
||||||
os.system(fuserCmd)
|
|
||||||
if self.valgrind:
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
self.running = 0
|
|
||||||
tdLog.debug("dnode:%d is stopped by kill -KILL" % (self.index))
|
|
||||||
|
|
||||||
def startIP(self):
|
|
||||||
cmd = "sudo ifconfig lo:%d 192.168.0.%d up" % (self.index, self.index)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def stopIP(self):
|
|
||||||
cmd = "sudo ifconfig lo:%d 192.168.0.%d down" % (
|
|
||||||
self.index, self.index)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def cfg(self, option, value):
|
|
||||||
cmd = "echo %s %s >> %s" % (option, value, self.cfgPath)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def getDnodeRootDir(self, index):
|
|
||||||
dnodeRootDir = os.path.join(self.path,"sim","psim","dnode%d" % index)
|
|
||||||
return dnodeRootDir
|
|
||||||
|
|
||||||
def getDnodesRootDir(self):
|
|
||||||
dnodesRootDir = os.path.join(self.path,"sim","psim")
|
|
||||||
return dnodesRootDir
|
|
||||||
|
|
||||||
|
|
||||||
class TDDnodes:
|
|
||||||
def __init__(self):
|
|
||||||
self.dnodes = []
|
|
||||||
self.dnodes.append(TDDnode(1))
|
|
||||||
self.dnodes.append(TDDnode(2))
|
|
||||||
self.dnodes.append(TDDnode(3))
|
|
||||||
self.dnodes.append(TDDnode(4))
|
|
||||||
self.dnodes.append(TDDnode(5))
|
|
||||||
self.dnodes.append(TDDnode(6))
|
|
||||||
self.dnodes.append(TDDnode(7))
|
|
||||||
self.dnodes.append(TDDnode(8))
|
|
||||||
self.dnodes.append(TDDnode(9))
|
|
||||||
self.dnodes.append(TDDnode(10))
|
|
||||||
self.simDeployed = False
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
psCmd = "ps -ef|grep -w taosd| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
psCmd = "ps -ef|grep -w valgrind.bin| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
binPath = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
binPath = binPath + "/../../../debug/"
|
|
||||||
tdLog.debug("binPath %s" % (binPath))
|
|
||||||
binPath = os.path.realpath(binPath)
|
|
||||||
tdLog.debug("binPath real path %s" % (binPath))
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/lib/libtaos.so /usr/local/lib/taos/" % (binPath)
|
|
||||||
# tdLog.debug(cmd)
|
|
||||||
# os.system(cmd)
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/bin/taos /usr/local/bin/taos/" % (binPath)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
# tdLog.debug("execute %s" % (cmd))
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/bin/taosd /usr/local/bin/taos/" % (binPath)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
# tdLog.debug("execute %s" % (cmd))
|
|
||||||
|
|
||||||
if path == "":
|
|
||||||
# self.path = os.path.expanduser('~')
|
|
||||||
self.path = os.path.abspath(binPath + "../../")
|
|
||||||
else:
|
|
||||||
self.path = os.path.realpath(path)
|
|
||||||
|
|
||||||
for i in range(len(self.dnodes)):
|
|
||||||
self.dnodes[i].init(self.path)
|
|
||||||
|
|
||||||
self.sim = TDSimClient()
|
|
||||||
self.sim.init(self.path)
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def setValgrind(self, value):
|
|
||||||
self.valgrind = value
|
|
||||||
|
|
||||||
def deploy(self, index):
|
|
||||||
self.sim.setTestCluster(self.testCluster)
|
|
||||||
|
|
||||||
if (self.simDeployed == False):
|
|
||||||
self.sim.deploy()
|
|
||||||
self.simDeployed = True
|
|
||||||
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].setTestCluster(self.testCluster)
|
|
||||||
self.dnodes[index - 1].setValgrind(self.valgrind)
|
|
||||||
self.dnodes[index - 1].deploy()
|
|
||||||
|
|
||||||
def cfg(self, index, option, value):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].cfg(option, value)
|
|
||||||
|
|
||||||
def start(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].start()
|
|
||||||
|
|
||||||
def stop(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].stop()
|
|
||||||
|
|
||||||
def getDataSize(self, index):
|
|
||||||
self.check(index)
|
|
||||||
return self.dnodes[index - 1].getDataSize()
|
|
||||||
|
|
||||||
def forcestop(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].forcestop()
|
|
||||||
|
|
||||||
def startIP(self, index):
|
|
||||||
self.check(index)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.dnodes[index - 1].startIP()
|
|
||||||
|
|
||||||
def stopIP(self, index):
|
|
||||||
self.check(index)
|
|
||||||
|
|
||||||
if self.dnodes[index - 1].testCluster:
|
|
||||||
self.dnodes[index - 1].stopIP()
|
|
||||||
|
|
||||||
def check(self, index):
|
|
||||||
if index < 1 or index > 10:
|
|
||||||
tdLog.exit("index:%d should on a scale of [1, 10]" % (index))
|
|
||||||
|
|
||||||
def stopAll(self):
|
|
||||||
tdLog.info("stop all dnodes")
|
|
||||||
for i in range(len(self.dnodes)):
|
|
||||||
self.dnodes[i].stop()
|
|
||||||
|
|
||||||
psCmd = "ps -ef | grep -w taosd | grep 'root' | grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
if processID:
|
|
||||||
cmd = "sudo systemctl stop taosd"
|
|
||||||
os.system(cmd)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
psCmd = "ps -ef|grep -w taosd| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
psCmd = "ps -ef|grep -w valgrind.bin| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def getDnodesRootDir(self):
|
|
||||||
dnodesRootDir = "%s/sim" % (self.path)
|
|
||||||
return dnodesRootDir
|
|
||||||
|
|
||||||
def getSimCfgPath(self):
|
|
||||||
return self.sim.getCfgDir()
|
|
||||||
|
|
||||||
def getSimLogPath(self):
|
|
||||||
return self.sim.getLogDir()
|
|
||||||
|
|
||||||
def addSimExtraCfg(self, option, value):
|
|
||||||
self.sim.addExtraCfg(option, value)
|
|
||||||
|
|
||||||
|
|
||||||
tdDnodes = TDDnodes()
|
|
|
@ -1,497 +0,0 @@
|
||||||
###################################################################
|
|
||||||
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
|
||||||
# All rights reserved.
|
|
||||||
#
|
|
||||||
# This file is proprietary and confidential to TAOS Technologies.
|
|
||||||
# No part of this file may be reproduced, stored, transmitted,
|
|
||||||
# disclosed or used in any form or by any means other than as
|
|
||||||
# expressly provided by the written permission from Jianhui Tao
|
|
||||||
#
|
|
||||||
###################################################################
|
|
||||||
|
|
||||||
# -*- coding: utf-8 -*-
|
|
||||||
|
|
||||||
import sys
|
|
||||||
import os
|
|
||||||
import os.path
|
|
||||||
import subprocess
|
|
||||||
from frame.log import *
|
|
||||||
|
|
||||||
|
|
||||||
class TDSimClient:
|
|
||||||
def __init__(self):
|
|
||||||
self.testCluster = False
|
|
||||||
|
|
||||||
self.cfgDict = {
|
|
||||||
"numOfLogLines": "100000000",
|
|
||||||
"locale": "en_US.UTF-8",
|
|
||||||
"charset": "UTF-8",
|
|
||||||
"asyncLog": "0",
|
|
||||||
"rpcDebugFlag": "135",
|
|
||||||
"tmrDebugFlag": "131",
|
|
||||||
"cDebugFlag": "135",
|
|
||||||
"udebugFlag": "135",
|
|
||||||
"jnidebugFlag": "135",
|
|
||||||
"qdebugFlag": "135",
|
|
||||||
"telemetryReporting": "0",
|
|
||||||
}
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
self.__init__()
|
|
||||||
self.path = path
|
|
||||||
|
|
||||||
def getLogDir(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","psim","log")
|
|
||||||
return self.logDir
|
|
||||||
|
|
||||||
def getCfgDir(self):
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","psim","cfg")
|
|
||||||
return self.cfgDir
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def addExtraCfg(self, option, value):
|
|
||||||
self.cfgDict.update({option: value})
|
|
||||||
|
|
||||||
def cfg(self, option, value):
|
|
||||||
cmd = "echo %s %s >> %s" % (option, value, self.cfgPath)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def deploy(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","psim","log")
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","psim","cfg")
|
|
||||||
self.cfgPath = os.path.join(self.path,"sim","psim","cfg","taos.cfg")
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "touch " + self.cfgPath
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.cfg("masterIp", "192.168.0.1")
|
|
||||||
self.cfg("secondIp", "192.168.0.2")
|
|
||||||
self.cfg("logDir", self.logDir)
|
|
||||||
|
|
||||||
for key, value in self.cfgDict.items():
|
|
||||||
self.cfg(key, value)
|
|
||||||
|
|
||||||
tdLog.debug("psim is deployed and configured by %s" % (self.cfgPath))
|
|
||||||
|
|
||||||
|
|
||||||
class TDDnode:
|
|
||||||
def __init__(self, index):
|
|
||||||
self.index = index
|
|
||||||
self.running = 0
|
|
||||||
self.deployed = 0
|
|
||||||
self.testCluster = False
|
|
||||||
self.valgrind = 0
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
self.path = path
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def setValgrind(self, value):
|
|
||||||
self.valgrind = value
|
|
||||||
|
|
||||||
def getDataSize(self):
|
|
||||||
totalSize = 0
|
|
||||||
|
|
||||||
if (self.deployed == 1):
|
|
||||||
for dirpath, dirnames, filenames in os.walk(self.dataDir):
|
|
||||||
for f in filenames:
|
|
||||||
fp = os.path.join(dirpath, f)
|
|
||||||
|
|
||||||
if not os.path.islink(fp):
|
|
||||||
totalSize = totalSize + os.path.getsize(fp)
|
|
||||||
|
|
||||||
return totalSize
|
|
||||||
|
|
||||||
def deploy(self):
|
|
||||||
self.logDir = os.path.join(self.path,"sim","dnode%d" % self.index, "log")
|
|
||||||
self.dataDir = os.path.join(self.path,"sim","dnode%d" % self.index, "data")
|
|
||||||
self.cfgDir = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg")
|
|
||||||
self.cfgPath = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg","taos.cfg")
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.dataDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "rm -rf " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.dataDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.logDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "mkdir -p " + self.cfgDir
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
cmd = "touch " + self.cfgPath
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.startIP()
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.cfg("masterIp", "192.168.0.1")
|
|
||||||
self.cfg("secondIp", "192.168.0.2")
|
|
||||||
self.cfg("publicIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("internalIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("privateIp", "192.168.0.%d" % (self.index))
|
|
||||||
self.cfg("dataDir", self.dataDir)
|
|
||||||
self.cfg("logDir", self.logDir)
|
|
||||||
self.cfg("numOfLogLines", "100000000")
|
|
||||||
self.cfg("mnodeEqualVnodeNum", "0")
|
|
||||||
self.cfg("walLevel", "2")
|
|
||||||
self.cfg("fsync", "1000")
|
|
||||||
self.cfg("statusInterval", "1")
|
|
||||||
self.cfg("numOfMnodes", "3")
|
|
||||||
self.cfg("numOfThreadsPerCore", "2.0")
|
|
||||||
self.cfg("monitor", "0")
|
|
||||||
self.cfg("maxVnodeConnections", "30000")
|
|
||||||
self.cfg("maxMgmtConnections", "30000")
|
|
||||||
self.cfg("maxMeterConnections", "30000")
|
|
||||||
self.cfg("maxShellConns", "30000")
|
|
||||||
self.cfg("locale", "en_US.UTF-8")
|
|
||||||
self.cfg("charset", "UTF-8")
|
|
||||||
self.cfg("asyncLog", "0")
|
|
||||||
self.cfg("anyIp", "0")
|
|
||||||
self.cfg("dDebugFlag", "135")
|
|
||||||
self.cfg("mDebugFlag", "135")
|
|
||||||
self.cfg("sdbDebugFlag", "135")
|
|
||||||
self.cfg("rpcDebugFlag", "135")
|
|
||||||
self.cfg("tmrDebugFlag", "131")
|
|
||||||
self.cfg("cDebugFlag", "135")
|
|
||||||
self.cfg("httpDebugFlag", "135")
|
|
||||||
self.cfg("monitorDebugFlag", "135")
|
|
||||||
self.cfg("udebugFlag", "135")
|
|
||||||
self.cfg("jnidebugFlag", "135")
|
|
||||||
self.cfg("qdebugFlag", "135")
|
|
||||||
self.deployed = 1
|
|
||||||
tdLog.debug(
|
|
||||||
"dnode:%d is deployed and configured by %s" %
|
|
||||||
(self.index, self.cfgPath))
|
|
||||||
|
|
||||||
def getBuildPath(self):
|
|
||||||
selfPath = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
|
|
||||||
if ("community" in selfPath):
|
|
||||||
projPath = selfPath[:selfPath.find("community")]
|
|
||||||
else:
|
|
||||||
projPath = selfPath[:selfPath.find("tests")]
|
|
||||||
|
|
||||||
for root, dirs, files in os.walk(projPath):
|
|
||||||
if ("taosd" in files):
|
|
||||||
rootRealPath = os.path.dirname(os.path.realpath(root))
|
|
||||||
if ("packaging" not in rootRealPath):
|
|
||||||
buildPath = root[:len(root)-len("/build/bin")]
|
|
||||||
break
|
|
||||||
return buildPath
|
|
||||||
|
|
||||||
def start(self):
|
|
||||||
buildPath = self.getBuildPath()
|
|
||||||
|
|
||||||
if (buildPath == ""):
|
|
||||||
tdLog.exit("taosd not found!")
|
|
||||||
else:
|
|
||||||
tdLog.info("taosd found in %s" % buildPath)
|
|
||||||
|
|
||||||
binPath = buildPath + "/build/bin/taosd"
|
|
||||||
|
|
||||||
if self.deployed == 0:
|
|
||||||
tdLog.exit("dnode:%d is not deployed" % (self.index))
|
|
||||||
|
|
||||||
if self.valgrind == 0:
|
|
||||||
cmd = "nohup %s -c %s --alloc-random-fail --random-file-fail-factor 5 > /dev/null 2>&1 & " % (
|
|
||||||
binPath, self.cfgDir)
|
|
||||||
else:
|
|
||||||
valgrindCmdline = "valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes"
|
|
||||||
|
|
||||||
cmd = "nohup %s %s -c %s 2>&1 & " % (
|
|
||||||
valgrindCmdline, binPath, self.cfgDir)
|
|
||||||
|
|
||||||
print(cmd)
|
|
||||||
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
self.running = 1
|
|
||||||
tdLog.debug("dnode:%d is running with %s " % (self.index, cmd))
|
|
||||||
|
|
||||||
tdLog.debug("wait 5 seconds for the dnode:%d to start." % (self.index))
|
|
||||||
time.sleep(5)
|
|
||||||
|
|
||||||
def stop(self):
|
|
||||||
if self.valgrind == 0:
|
|
||||||
toBeKilled = "taosd"
|
|
||||||
else:
|
|
||||||
toBeKilled = "valgrind.bin"
|
|
||||||
|
|
||||||
if self.running != 0:
|
|
||||||
psCmd = "ps -ef|grep -w %s| grep -v grep | awk '{print $2}'" % toBeKilled
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -INT %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
for port in range(6030, 6041):
|
|
||||||
fuserCmd = "fuser -k -n tcp %d" % port
|
|
||||||
os.system(fuserCmd)
|
|
||||||
if self.valgrind:
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
self.running = 0
|
|
||||||
tdLog.debug("dnode:%d is stopped by kill -INT" % (self.index))
|
|
||||||
|
|
||||||
def forcestop(self):
|
|
||||||
if self.valgrind == 0:
|
|
||||||
toBeKilled = "taosd"
|
|
||||||
else:
|
|
||||||
toBeKilled = "valgrind.bin"
|
|
||||||
|
|
||||||
if self.running != 0:
|
|
||||||
psCmd = "ps -ef|grep -w %s| grep -v grep | awk '{print $2}'" % toBeKilled
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -KILL %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
for port in range(6030, 6041):
|
|
||||||
fuserCmd = "fuser -k -n tcp %d" % port
|
|
||||||
os.system(fuserCmd)
|
|
||||||
if self.valgrind:
|
|
||||||
time.sleep(2)
|
|
||||||
|
|
||||||
self.running = 0
|
|
||||||
tdLog.debug("dnode:%d is stopped by kill -KILL" % (self.index))
|
|
||||||
|
|
||||||
def startIP(self):
|
|
||||||
cmd = "sudo ifconfig lo:%d 192.168.0.%d up" % (self.index, self.index)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def stopIP(self):
|
|
||||||
cmd = "sudo ifconfig lo:%d 192.168.0.%d down" % (
|
|
||||||
self.index, self.index)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def cfg(self, option, value):
|
|
||||||
cmd = "echo %s %s >> %s" % (option, value, self.cfgPath)
|
|
||||||
if os.system(cmd) != 0:
|
|
||||||
tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def getDnodeRootDir(self, index):
|
|
||||||
dnodeRootDir = os.path.join(self.path,"sim","psim","dnode%d" % index)
|
|
||||||
return dnodeRootDir
|
|
||||||
|
|
||||||
def getDnodesRootDir(self):
|
|
||||||
dnodesRootDir = os.path.join(self.path,"sim","psim")
|
|
||||||
return dnodesRootDir
|
|
||||||
|
|
||||||
|
|
||||||
class TDDnodes:
|
|
||||||
def __init__(self):
|
|
||||||
self.dnodes = []
|
|
||||||
self.dnodes.append(TDDnode(1))
|
|
||||||
self.dnodes.append(TDDnode(2))
|
|
||||||
self.dnodes.append(TDDnode(3))
|
|
||||||
self.dnodes.append(TDDnode(4))
|
|
||||||
self.dnodes.append(TDDnode(5))
|
|
||||||
self.dnodes.append(TDDnode(6))
|
|
||||||
self.dnodes.append(TDDnode(7))
|
|
||||||
self.dnodes.append(TDDnode(8))
|
|
||||||
self.dnodes.append(TDDnode(9))
|
|
||||||
self.dnodes.append(TDDnode(10))
|
|
||||||
self.simDeployed = False
|
|
||||||
|
|
||||||
def init(self, path):
|
|
||||||
psCmd = "ps -ef|grep -w taosd| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
psCmd = "ps -ef|grep -w valgrind.bin| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
binPath = os.path.dirname(os.path.realpath(__file__))
|
|
||||||
binPath = binPath + "/../../../debug/"
|
|
||||||
tdLog.debug("binPath %s" % (binPath))
|
|
||||||
binPath = os.path.realpath(binPath)
|
|
||||||
tdLog.debug("binPath real path %s" % (binPath))
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/lib/libtaos.so /usr/local/lib/taos/" % (binPath)
|
|
||||||
# tdLog.debug(cmd)
|
|
||||||
# os.system(cmd)
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/bin/taos /usr/local/bin/taos/" % (binPath)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
# tdLog.debug("execute %s" % (cmd))
|
|
||||||
|
|
||||||
# cmd = "sudo cp %s/build/bin/taosd /usr/local/bin/taos/" % (binPath)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
# tdLog.debug("execute %s" % (cmd))
|
|
||||||
|
|
||||||
if path == "":
|
|
||||||
# self.path = os.path.expanduser('~')
|
|
||||||
self.path = os.path.abspath(binPath + "../../")
|
|
||||||
else:
|
|
||||||
self.path = os.path.realpath(path)
|
|
||||||
|
|
||||||
for i in range(len(self.dnodes)):
|
|
||||||
self.dnodes[i].init(self.path)
|
|
||||||
|
|
||||||
self.sim = TDSimClient()
|
|
||||||
self.sim.init(self.path)
|
|
||||||
|
|
||||||
def setTestCluster(self, value):
|
|
||||||
self.testCluster = value
|
|
||||||
|
|
||||||
def setValgrind(self, value):
|
|
||||||
self.valgrind = value
|
|
||||||
|
|
||||||
def deploy(self, index):
|
|
||||||
self.sim.setTestCluster(self.testCluster)
|
|
||||||
|
|
||||||
if (self.simDeployed == False):
|
|
||||||
self.sim.deploy()
|
|
||||||
self.simDeployed = True
|
|
||||||
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].setTestCluster(self.testCluster)
|
|
||||||
self.dnodes[index - 1].setValgrind(self.valgrind)
|
|
||||||
self.dnodes[index - 1].deploy()
|
|
||||||
|
|
||||||
def cfg(self, index, option, value):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].cfg(option, value)
|
|
||||||
|
|
||||||
def start(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].start()
|
|
||||||
|
|
||||||
def stop(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].stop()
|
|
||||||
|
|
||||||
def getDataSize(self, index):
|
|
||||||
self.check(index)
|
|
||||||
return self.dnodes[index - 1].getDataSize()
|
|
||||||
|
|
||||||
def forcestop(self, index):
|
|
||||||
self.check(index)
|
|
||||||
self.dnodes[index - 1].forcestop()
|
|
||||||
|
|
||||||
def startIP(self, index):
|
|
||||||
self.check(index)
|
|
||||||
|
|
||||||
if self.testCluster:
|
|
||||||
self.dnodes[index - 1].startIP()
|
|
||||||
|
|
||||||
def stopIP(self, index):
|
|
||||||
self.check(index)
|
|
||||||
|
|
||||||
if self.dnodes[index - 1].testCluster:
|
|
||||||
self.dnodes[index - 1].stopIP()
|
|
||||||
|
|
||||||
def check(self, index):
|
|
||||||
if index < 1 or index > 10:
|
|
||||||
tdLog.exit("index:%d should on a scale of [1, 10]" % (index))
|
|
||||||
|
|
||||||
def stopAll(self):
|
|
||||||
tdLog.info("stop all dnodes")
|
|
||||||
for i in range(len(self.dnodes)):
|
|
||||||
self.dnodes[i].stop()
|
|
||||||
|
|
||||||
psCmd = "ps -ef | grep -w taosd | grep 'root' | grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
if processID:
|
|
||||||
cmd = "sudo systemctl stop taosd"
|
|
||||||
os.system(cmd)
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
psCmd = "ps -ef|grep -w taosd| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
psCmd = "ps -ef|grep -w valgrind.bin| grep -v grep | awk '{print $2}'"
|
|
||||||
processID = subprocess.check_output(psCmd, shell=True).decode("utf-8")
|
|
||||||
while(processID):
|
|
||||||
killCmd = "kill -TERM %s > /dev/null 2>&1" % processID
|
|
||||||
os.system(killCmd)
|
|
||||||
time.sleep(1)
|
|
||||||
processID = subprocess.check_output(
|
|
||||||
psCmd, shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
# if os.system(cmd) != 0 :
|
|
||||||
# tdLog.exit(cmd)
|
|
||||||
|
|
||||||
def getDnodesRootDir(self):
|
|
||||||
dnodesRootDir = "%s/sim" % (self.path)
|
|
||||||
return dnodesRootDir
|
|
||||||
|
|
||||||
def getSimCfgPath(self):
|
|
||||||
return self.sim.getCfgDir()
|
|
||||||
|
|
||||||
def getSimLogPath(self):
|
|
||||||
return self.sim.getLogDir()
|
|
||||||
|
|
||||||
def addSimExtraCfg(self, option, value):
|
|
||||||
self.sim.addExtraCfg(option, value)
|
|
||||||
|
|
||||||
|
|
||||||
tdDnodes = TDDnodes()
|
|
|
@ -0,0 +1,36 @@
|
||||||
|
###################################################################
|
||||||
|
# Copyright (c) 2023 by TAOS Technologies, Inc.
|
||||||
|
# All rights reserved.
|
||||||
|
#
|
||||||
|
# This file is proprietary and confidential to TAOS Technologies.
|
||||||
|
# No part of this file may be reproduced, stored, transmitted,
|
||||||
|
# disclosed or used in any form or by any means other than as
|
||||||
|
# expressly provided by the written permission from Jianhui Tao
|
||||||
|
#
|
||||||
|
###################################################################
|
||||||
|
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
#
|
||||||
|
# about system funciton extension
|
||||||
|
#
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
import datetime
|
||||||
|
import platform
|
||||||
|
|
||||||
|
# if windows platform return True
|
||||||
|
def isWin():
|
||||||
|
return platform.system().lower() == 'windows'
|
||||||
|
|
||||||
|
# wait util execute file finished
|
||||||
|
def exe(file):
|
||||||
|
return os.system(file)
|
||||||
|
|
||||||
|
# execute file and return immediately
|
||||||
|
def exeNoWait(file):
|
||||||
|
print("exe no wait")
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,53 @@
|
||||||
|
###################################################################
|
||||||
|
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
||||||
|
# All rights reserved.
|
||||||
|
#
|
||||||
|
# This file is proprietary and confidential to TAOS Technologies.
|
||||||
|
# No part of this file may be reproduced, stored, transmitted,
|
||||||
|
# disclosed or used in any form or by any means other than as
|
||||||
|
# expressly provided by the written permission from Jianhui Tao
|
||||||
|
#
|
||||||
|
###################################################################
|
||||||
|
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
#
|
||||||
|
# about path function extension
|
||||||
|
#
|
||||||
|
|
||||||
|
import os
|
||||||
|
from frame.log import *
|
||||||
|
|
||||||
|
# build/bin path
|
||||||
|
binDir = ""
|
||||||
|
|
||||||
|
def binPath():
|
||||||
|
global binDir
|
||||||
|
|
||||||
|
if binDir != "":
|
||||||
|
return binDir
|
||||||
|
|
||||||
|
selfPath = os.path.dirname(os.path.realpath(__file__))
|
||||||
|
|
||||||
|
if ("community/tests" in selfPath):
|
||||||
|
projPath = selfPath[:selfPath.find("community/tests")]
|
||||||
|
else:
|
||||||
|
projPath = selfPath[:selfPath.find("TDengine/tests")]
|
||||||
|
|
||||||
|
for root, dirs, files in os.walk(projPath):
|
||||||
|
if ("taosd" in files):
|
||||||
|
rootRealPath = os.path.dirname(os.path.realpath(root))
|
||||||
|
if ("packaging" not in rootRealPath):
|
||||||
|
buildPath = root[:len(root)-len("/build/bin")]
|
||||||
|
break
|
||||||
|
# check
|
||||||
|
if (buildPath == ""):
|
||||||
|
tdLog.exit("taosd not found!")
|
||||||
|
else:
|
||||||
|
tdLog.info(f"taosd found in {buildPath}")
|
||||||
|
# return
|
||||||
|
binDir = buildPath + "/build/bin/"
|
||||||
|
return binDir
|
||||||
|
|
||||||
|
def binFile(filename):
|
||||||
|
return binPath() + filename
|
|
@ -0,0 +1,23 @@
|
||||||
|
###################################################################
|
||||||
|
# Copyright (c) 2023 by TAOS Technologies, Inc.
|
||||||
|
# All rights reserved.
|
||||||
|
#
|
||||||
|
# This file is proprietary and confidential to TAOS Technologies.
|
||||||
|
# No part of this file may be reproduced, stored, transmitted,
|
||||||
|
# disclosed or used in any form or by any means other than as
|
||||||
|
# expressly provided by the written permission from Jianhui Tao
|
||||||
|
#
|
||||||
|
###################################################################
|
||||||
|
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
#
|
||||||
|
# about tools funciton extension
|
||||||
|
#
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
import datetime
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,46 @@
|
||||||
|
###################################################################
|
||||||
|
# Copyright (c) 2023 by TAOS Technologies, Inc.
|
||||||
|
# All rights reserved.
|
||||||
|
#
|
||||||
|
# This file is proprietary and confidential to TAOS Technologies.
|
||||||
|
# No part of this file may be reproduced, stored, transmitted,
|
||||||
|
# disclosed or used in any form or by any means other than as
|
||||||
|
# expressly provided by the written permission from Jianhui Tao
|
||||||
|
#
|
||||||
|
###################################################################
|
||||||
|
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
#
|
||||||
|
# about system funciton extension
|
||||||
|
#
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
import datetime
|
||||||
|
import frame.epath
|
||||||
|
import frame.eos
|
||||||
|
from frame.log import *
|
||||||
|
|
||||||
|
# run taosBenchmark with command or json file mode
|
||||||
|
def runBenchmark(command = "", json = "") :
|
||||||
|
# get taosBenchmark path
|
||||||
|
bmFile = frame.epath.binFile("taosBenchmark")
|
||||||
|
if frame.eos.isWin():
|
||||||
|
bmFile += ".exe"
|
||||||
|
|
||||||
|
# run
|
||||||
|
if command != "":
|
||||||
|
frame.eos.exe(bmFile + " " + command)
|
||||||
|
if json != "":
|
||||||
|
cmd = f"{bmFile} -f {json}"
|
||||||
|
print(cmd)
|
||||||
|
status = frame.eos.exe(cmd)
|
||||||
|
if status !=0:
|
||||||
|
tdLog.exit(f"run failed {cmd} status={status}")
|
||||||
|
|
||||||
|
|
||||||
|
# get current directory file name
|
||||||
|
def curFile(fullPath, filename):
|
||||||
|
return os.path.dirname(fullPath) + "/" + filename
|
|
@ -1,83 +0,0 @@
|
||||||
###################################################################
|
|
||||||
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
|
||||||
# All rights reserved.
|
|
||||||
#
|
|
||||||
# This file is proprietary and confidential to TAOS Technologies.
|
|
||||||
# No part of this file may be reproduced, stored, transmitted,
|
|
||||||
# disclosed or used in any form or by any means other than as
|
|
||||||
# expressly provided by the written permission from Jianhui Tao
|
|
||||||
#
|
|
||||||
###################################################################
|
|
||||||
|
|
||||||
# -*- coding: utf-8 -*-
|
|
||||||
|
|
||||||
|
|
||||||
import os
|
|
||||||
from frame.log import *
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
class TDFindPath:
|
|
||||||
"""This class is for finding path within TDengine
|
|
||||||
"""
|
|
||||||
def __init__(self):
|
|
||||||
self.file = ""
|
|
||||||
|
|
||||||
|
|
||||||
def init(self, file):
|
|
||||||
"""[summary]
|
|
||||||
|
|
||||||
Args:
|
|
||||||
file (str): the file location you want to start the query. Generally using __file__
|
|
||||||
"""
|
|
||||||
self.file = file
|
|
||||||
|
|
||||||
def getTaosdemoPath(self):
|
|
||||||
"""for finding the path of directory containing taosdemo
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
str: the path to directory containing taosdemo
|
|
||||||
"""
|
|
||||||
selfPath = os.path.dirname(os.path.realpath(self.file))
|
|
||||||
|
|
||||||
if ("community" in selfPath):
|
|
||||||
projPath = selfPath[:selfPath.find("community")]
|
|
||||||
else:
|
|
||||||
projPath = selfPath[:selfPath.find("tests")]
|
|
||||||
|
|
||||||
for root, dirs, files in os.walk(projPath):
|
|
||||||
if ("taosd" in files):
|
|
||||||
rootRealPath = os.path.dirname(os.path.realpath(root))
|
|
||||||
if ("packaging" not in rootRealPath):
|
|
||||||
buildPath = root[:len(root)-len("/build/bin")]
|
|
||||||
break
|
|
||||||
if (buildPath == ""):
|
|
||||||
tdLog.exit("taosd not found!")
|
|
||||||
else:
|
|
||||||
tdLog.info(f"taosd found in {buildPath}")
|
|
||||||
return buildPath + "/build/bin/"
|
|
||||||
|
|
||||||
def getTDenginePath(self):
|
|
||||||
"""for finding the root path of TDengine
|
|
||||||
|
|
||||||
Returns:
|
|
||||||
str: the root path of TDengine
|
|
||||||
"""
|
|
||||||
selfPath = os.path.dirname(os.path.realpath(self.file))
|
|
||||||
|
|
||||||
if ("community" in selfPath):
|
|
||||||
projPath = selfPath[:selfPath.find("community")]
|
|
||||||
else:
|
|
||||||
projPath = selfPath[:selfPath.find("tests")]
|
|
||||||
print(projPath)
|
|
||||||
for root, dirs, files in os.walk(projPath):
|
|
||||||
if ("sim" in dirs):
|
|
||||||
print(root)
|
|
||||||
rootRealPath = os.path.realpath(root)
|
|
||||||
if (rootRealPath == ""):
|
|
||||||
tdLog.exit("TDengine not found!")
|
|
||||||
else:
|
|
||||||
tdLog.info(f"TDengine found in {rootRealPath}")
|
|
||||||
return rootRealPath
|
|
||||||
|
|
||||||
tdFindPath = TDFindPath()
|
|
|
@ -8,7 +8,7 @@ import socket
|
||||||
from frame.log import *
|
from frame.log import *
|
||||||
from frame.sql import *
|
from frame.sql import *
|
||||||
from frame.cases import *
|
from frame.cases import *
|
||||||
from frame.dnodes import *
|
from frame.server.dnodes import *
|
||||||
from frame.common import *
|
from frame.common import *
|
||||||
|
|
||||||
class ClusterDnodes(TDDnodes):
|
class ClusterDnodes(TDDnodes):
|
||||||
|
@ -35,17 +35,21 @@ class ConfigureyCluster:
|
||||||
self.startPort = 6030
|
self.startPort = 6030
|
||||||
self.portStep = 100
|
self.portStep = 100
|
||||||
self.mnodeNums = 0
|
self.mnodeNums = 0
|
||||||
|
self.level = 0
|
||||||
|
self.disk = 0
|
||||||
|
|
||||||
def configure_cluster(self ,dnodeNums=5,mnodeNums=0,independentMnode=True,startPort=6030,portStep=100,hostname="%s"%hostname):
|
def configure_cluster(self ,dnodeNums=5, mnodeNums=0, independentMnode=True, startPort=6030, portStep=100, hostname="%s"%hostname, level=1, disk=1):
|
||||||
self.startPort=int(startPort)
|
self.startPort=int(startPort)
|
||||||
self.portStep=int(portStep)
|
self.portStep=int(portStep)
|
||||||
self.hostname=hostname
|
self.hostname=hostname
|
||||||
self.dnodeNums = int(dnodeNums)
|
self.dnodeNums = int(dnodeNums)
|
||||||
self.mnodeNums = int(mnodeNums)
|
self.mnodeNums = int(mnodeNums)
|
||||||
|
self.level = int(level)
|
||||||
|
self.disk = int(disk)
|
||||||
self.dnodes = []
|
self.dnodes = []
|
||||||
startPort_sec = int(startPort+portStep)
|
startPort_sec = int(startPort+portStep)
|
||||||
for num in range(1, (self.dnodeNums+1)):
|
for num in range(1, (self.dnodeNums+1)):
|
||||||
dnode = TDDnode(num)
|
dnode = TDDnode(num, self.level, self.disk)
|
||||||
dnode.addExtraCfg("firstEp", f"{hostname}:{self.startPort}")
|
dnode.addExtraCfg("firstEp", f"{hostname}:{self.startPort}")
|
||||||
dnode.addExtraCfg("fqdn", f"{hostname}")
|
dnode.addExtraCfg("fqdn", f"{hostname}")
|
||||||
dnode.addExtraCfg("serverPort", f"{self.startPort + (num-1)*self.portStep}")
|
dnode.addExtraCfg("serverPort", f"{self.startPort + (num-1)*self.portStep}")
|
|
@ -115,8 +115,11 @@ class TDSimClient:
|
||||||
|
|
||||||
|
|
||||||
class TDDnode:
|
class TDDnode:
|
||||||
def __init__(self, index):
|
def __init__(self, index=1, level=1, disk=1):
|
||||||
self.index = index
|
self.index = index
|
||||||
|
self.level = level
|
||||||
|
self.disk = disk
|
||||||
|
self.dataDir = []
|
||||||
self.running = 0
|
self.running = 0
|
||||||
self.deployed = 0
|
self.deployed = 0
|
||||||
self.testCluster = False
|
self.testCluster = False
|
||||||
|
@ -209,14 +212,30 @@ class TDDnode:
|
||||||
self.remote_conn.run("python3 ./test.py %s -d %s -e %s"%(valgrindStr,remoteCfgDictStr,execCmdStr))
|
self.remote_conn.run("python3 ./test.py %s -d %s -e %s"%(valgrindStr,remoteCfgDictStr,execCmdStr))
|
||||||
|
|
||||||
def deploy(self, *updatecfgDict):
|
def deploy(self, *updatecfgDict):
|
||||||
|
# logDir
|
||||||
self.logDir = os.path.join(self.path,"sim","dnode%d" % self.index, "log")
|
self.logDir = os.path.join(self.path,"sim","dnode%d" % self.index, "log")
|
||||||
self.dataDir = os.path.join(self.path,"sim","dnode%d" % self.index, "data")
|
# dataDir
|
||||||
|
simPath = os.path.join(self.path, "sim", "dnode%d" % self.index)
|
||||||
|
primary = 1
|
||||||
|
if self.level == 1 and self.disk == 1:
|
||||||
|
eDir = os.path.join(simPath, "data")
|
||||||
|
self.dataDir.append(eDir)
|
||||||
|
else:
|
||||||
|
for i in range(self.level):
|
||||||
|
for j in range(self.disk):
|
||||||
|
eDir = os.path.join(simPath, f"data{i}{j}")
|
||||||
|
self.dataDir.append(f"{eDir} {i} {primary}")
|
||||||
|
if primary == 1:
|
||||||
|
primary = 0
|
||||||
|
|
||||||
|
# taos.cfg
|
||||||
self.cfgDir = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg")
|
self.cfgDir = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg")
|
||||||
self.cfgPath = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg","taos.cfg")
|
self.cfgPath = os.path.join(self.path,"sim","dnode%d" % self.index, "cfg","taos.cfg")
|
||||||
|
|
||||||
cmd = "rm -rf " + self.dataDir
|
for eDir in self.dataDir:
|
||||||
if os.system(cmd) != 0:
|
cmd = "rm -rf " + eDir
|
||||||
tdLog.exit(cmd)
|
if os.system(cmd) != 0:
|
||||||
|
tdLog.exit(cmd)
|
||||||
|
|
||||||
cmd = "rm -rf " + self.logDir
|
cmd = "rm -rf " + self.logDir
|
||||||
if os.system(cmd) != 0:
|
if os.system(cmd) != 0:
|
||||||
|
@ -229,7 +248,8 @@ class TDDnode:
|
||||||
# cmd = "mkdir -p " + self.dataDir
|
# cmd = "mkdir -p " + self.dataDir
|
||||||
# if os.system(cmd) != 0:
|
# if os.system(cmd) != 0:
|
||||||
# tdLog.exit(cmd)
|
# tdLog.exit(cmd)
|
||||||
os.makedirs(self.dataDir)
|
for eDir in self.dataDir:
|
||||||
|
os.makedirs(eDir.split(' ')[0])
|
||||||
|
|
||||||
# cmd = "mkdir -p " + self.logDir
|
# cmd = "mkdir -p " + self.logDir
|
||||||
# if os.system(cmd) != 0:
|
# if os.system(cmd) != 0:
|
||||||
|
@ -275,7 +295,11 @@ class TDDnode:
|
||||||
self.addExtraCfg(key, value)
|
self.addExtraCfg(key, value)
|
||||||
if (self.remoteIP == ""):
|
if (self.remoteIP == ""):
|
||||||
for key, value in self.cfgDict.items():
|
for key, value in self.cfgDict.items():
|
||||||
self.cfg(key, value)
|
if type(value) == list:
|
||||||
|
for v in value:
|
||||||
|
self.cfg(key, v)
|
||||||
|
else:
|
||||||
|
self.cfg(key, value)
|
||||||
else:
|
else:
|
||||||
self.remoteExec(self.cfgDict, "tdDnodes.deploy(%d,updateCfgDict)"%self.index)
|
self.remoteExec(self.cfgDict, "tdDnodes.deploy(%d,updateCfgDict)"%self.index)
|
||||||
|
|
||||||
|
@ -887,4 +911,10 @@ class TDDnodes:
|
||||||
def getAsan(self):
|
def getAsan(self):
|
||||||
return self.asan
|
return self.asan
|
||||||
|
|
||||||
|
def setLevelDisk(self, level, disk):
|
||||||
|
for i in range(len(self.dnodes)):
|
||||||
|
self.dnodes[i].level = int(level)
|
||||||
|
self.dnodes[i].disk = int(disk)
|
||||||
|
|
||||||
|
|
||||||
tdDnodes = TDDnodes()
|
tdDnodes = TDDnodes()
|
|
@ -535,6 +535,16 @@ class TDSql:
|
||||||
tdLog.info("%s(%d) failed: sql:%s, elm:%s == expect_elm:%s" % args)
|
tdLog.info("%s(%d) failed: sql:%s, elm:%s == expect_elm:%s" % args)
|
||||||
raise Exception
|
raise Exception
|
||||||
|
|
||||||
|
# check like select count(*) ... sql
|
||||||
|
def checkAgg(self, sql, expectCnt):
|
||||||
|
self.query(sql)
|
||||||
|
self.checkData(0, 0, expectCnt)
|
||||||
|
|
||||||
|
# get first value
|
||||||
|
def getFirstValue(self, sql) :
|
||||||
|
self.query(sql)
|
||||||
|
return self.getData(0, 0)
|
||||||
|
|
||||||
def get_times(self, time_str, precision="ms"):
|
def get_times(self, time_str, precision="ms"):
|
||||||
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
||||||
if time_str[-1] not in TAOS_TIME_INIT:
|
if time_str[-1] not in TAOS_TIME_INIT:
|
||||||
|
@ -602,6 +612,7 @@ class TDSql:
|
||||||
if self.cursor.istype(col, "BIGINT UNSIGNED"):
|
if self.cursor.istype(col, "BIGINT UNSIGNED"):
|
||||||
return "BIGINT UNSIGNED"
|
return "BIGINT UNSIGNED"
|
||||||
|
|
||||||
|
'''
|
||||||
def taosdStatus(self, state):
|
def taosdStatus(self, state):
|
||||||
tdLog.sleep(5)
|
tdLog.sleep(5)
|
||||||
pstate = 0
|
pstate = 0
|
||||||
|
@ -630,6 +641,7 @@ class TDSql:
|
||||||
tdLog.exit("taosd state is %d != expect:%d" %args)
|
tdLog.exit("taosd state is %d != expect:%d" %args)
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
def haveFile(self, dir, state):
|
def haveFile(self, dir, state):
|
||||||
if os.path.exists(dir) and os.path.isdir(dir):
|
if os.path.exists(dir) and os.path.isdir(dir):
|
||||||
if not os.listdir(dir):
|
if not os.listdir(dir):
|
||||||
|
@ -644,6 +656,7 @@ class TDSql:
|
||||||
tdLog.exit("dir: %s is not empty, expect: empty" %dir)
|
tdLog.exit("dir: %s is not empty, expect: empty" %dir)
|
||||||
else:
|
else:
|
||||||
tdLog.exit("dir: %s doesn't exist" %dir)
|
tdLog.exit("dir: %s doesn't exist" %dir)
|
||||||
|
|
||||||
def createDir(self, dir):
|
def createDir(self, dir):
|
||||||
if os.path.exists(dir):
|
if os.path.exists(dir):
|
||||||
shrmtree(dir)
|
shrmtree(dir)
|
||||||
|
@ -651,5 +664,6 @@ class TDSql:
|
||||||
os.makedirs( dir, 755 )
|
os.makedirs( dir, 755 )
|
||||||
tdLog.info("dir: %s is created" %dir)
|
tdLog.info("dir: %s is created" %dir)
|
||||||
pass
|
pass
|
||||||
|
'''
|
||||||
|
|
||||||
tdSql = TDSql()
|
tdSql = TDSql()
|
||||||
|
|
|
@ -0,0 +1,27 @@
|
||||||
|
###################################################################
|
||||||
|
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
||||||
|
# All rights reserved.
|
||||||
|
#
|
||||||
|
# This file is proprietary and confidential to TAOS Technologies.
|
||||||
|
# No part of this file may be reproduced, stored, transmitted,
|
||||||
|
# disclosed or used in any form or by any means other than as
|
||||||
|
# expressly provided by the written permission from Jianhui Tao
|
||||||
|
#
|
||||||
|
###################################################################
|
||||||
|
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
import datetime
|
||||||
|
|
||||||
|
class srvCtl:
|
||||||
|
def __init__(self):
|
||||||
|
# record server information
|
||||||
|
self.dnodeNum = 0
|
||||||
|
self.mnodeNum = 0
|
||||||
|
self.mLevel = 0
|
||||||
|
self.mLevelDisk = 0
|
||||||
|
|
||||||
|
sc = srvCtl()
|
|
@ -28,9 +28,9 @@ import importlib
|
||||||
import toml
|
import toml
|
||||||
|
|
||||||
from frame.log import *
|
from frame.log import *
|
||||||
from frame.dnodes import *
|
from frame.server.dnodes import *
|
||||||
|
from frame.server.cluster import *
|
||||||
from frame.cases import *
|
from frame.cases import *
|
||||||
from frame.cluster import *
|
|
||||||
from frame.taosadapter import *
|
from frame.taosadapter import *
|
||||||
|
|
||||||
import taos
|
import taos
|
||||||
|
@ -111,8 +111,12 @@ if __name__ == "__main__":
|
||||||
asan = False
|
asan = False
|
||||||
independentMnode = False
|
independentMnode = False
|
||||||
previousCluster = False
|
previousCluster = False
|
||||||
opts, args = getopt.gnu_getopt(sys.argv[1:], 'f:p:m:l:scghrd:k:e:N:M:Q:C:RWD:n:i:aP', [
|
level = 1
|
||||||
'file=', 'path=', 'master', 'logSql', 'stop', 'cluster', 'valgrind', 'help', 'restart', 'updateCfgDict', 'killv', 'execCmd','dnodeNums','mnodeNums','queryPolicy','createDnodeNums','restful','websocket','adaptercfgupdate','replicaVar','independentMnode','previous'])
|
disk = 1
|
||||||
|
|
||||||
|
opts, args = getopt.gnu_getopt(sys.argv[1:], 'f:p:m:l:scghrd:k:e:N:M:Q:C:RWU:n:i:aP:L:D:', [
|
||||||
|
'file=', 'path=', 'master', 'logSql', 'stop', 'cluster', 'valgrind', 'help', 'restart', 'updateCfgDict', 'killv', 'execCmd','dnodeNums','mnodeNums',
|
||||||
|
'queryPolicy','createDnodeNums','restful','websocket','adaptercfgupdate','replicaVar','independentMnode',"asan",'previous','level','disk'])
|
||||||
for key, value in opts:
|
for key, value in opts:
|
||||||
if key in ['-h', '--help']:
|
if key in ['-h', '--help']:
|
||||||
tdLog.printNoPrefix(
|
tdLog.printNoPrefix(
|
||||||
|
@ -134,11 +138,13 @@ if __name__ == "__main__":
|
||||||
tdLog.printNoPrefix('-C create Dnode Numbers in one cluster')
|
tdLog.printNoPrefix('-C create Dnode Numbers in one cluster')
|
||||||
tdLog.printNoPrefix('-R restful realization form')
|
tdLog.printNoPrefix('-R restful realization form')
|
||||||
tdLog.printNoPrefix('-W websocket connection')
|
tdLog.printNoPrefix('-W websocket connection')
|
||||||
tdLog.printNoPrefix('-D taosadapter update cfg dict ')
|
tdLog.printNoPrefix('-U taosadapter update cfg dict ')
|
||||||
tdLog.printNoPrefix('-n the number of replicas')
|
tdLog.printNoPrefix('-n the number of replicas')
|
||||||
tdLog.printNoPrefix('-i independentMnode Mnode')
|
tdLog.printNoPrefix('-i independentMnode Mnode')
|
||||||
tdLog.printNoPrefix('-a address sanitizer mode')
|
tdLog.printNoPrefix('-a address sanitizer mode')
|
||||||
tdLog.printNoPrefix('-P run case with [P]revious cluster, do not create new cluster to run case.')
|
tdLog.printNoPrefix('-P run case with [P]revious cluster, do not create new cluster to run case.')
|
||||||
|
tdLog.printNoPrefix('-L set multiple level number. range 1 ~ 3')
|
||||||
|
tdLog.printNoPrefix('-D set disk number on each level. range 1 ~ 10')
|
||||||
|
|
||||||
sys.exit(0)
|
sys.exit(0)
|
||||||
|
|
||||||
|
@ -213,7 +219,7 @@ if __name__ == "__main__":
|
||||||
if key in ['-a', '--asan']:
|
if key in ['-a', '--asan']:
|
||||||
asan = True
|
asan = True
|
||||||
|
|
||||||
if key in ['-D', '--adaptercfgupdate']:
|
if key in ['-U', '--adaptercfgupdate']:
|
||||||
try:
|
try:
|
||||||
adaptercfgupdate = eval(base64.b64decode(value.encode()).decode())
|
adaptercfgupdate = eval(base64.b64decode(value.encode()).decode())
|
||||||
except:
|
except:
|
||||||
|
@ -226,6 +232,12 @@ if __name__ == "__main__":
|
||||||
if key in ['-P', '--previous']:
|
if key in ['-P', '--previous']:
|
||||||
previousCluster = True
|
previousCluster = True
|
||||||
|
|
||||||
|
if key in ['-L', '--level']:
|
||||||
|
level = value
|
||||||
|
|
||||||
|
if key in ['-D', '--disk']:
|
||||||
|
disk = value
|
||||||
|
|
||||||
#
|
#
|
||||||
# do exeCmd command
|
# do exeCmd command
|
||||||
#
|
#
|
||||||
|
@ -361,6 +373,7 @@ if __name__ == "__main__":
|
||||||
tAdapter.stop(force_kill=True)
|
tAdapter.stop(force_kill=True)
|
||||||
|
|
||||||
if dnodeNums == 1 :
|
if dnodeNums == 1 :
|
||||||
|
tdDnodes.setLevelDisk(level, disk)
|
||||||
tdDnodes.deploy(1,updateCfgDict)
|
tdDnodes.deploy(1,updateCfgDict)
|
||||||
tdDnodes.start(1)
|
tdDnodes.start(1)
|
||||||
tdCases.logSql(logSql)
|
tdCases.logSql(logSql)
|
||||||
|
@ -391,7 +404,7 @@ if __name__ == "__main__":
|
||||||
tdLog.exit(f"alter queryPolicy to {queryPolicy} failed")
|
tdLog.exit(f"alter queryPolicy to {queryPolicy} failed")
|
||||||
else :
|
else :
|
||||||
tdLog.debug("create an cluster with %s nodes and make %s dnode as independent mnode"%(dnodeNums,mnodeNums))
|
tdLog.debug("create an cluster with %s nodes and make %s dnode as independent mnode"%(dnodeNums,mnodeNums))
|
||||||
dnodeslist = cluster.configure_cluster(dnodeNums=dnodeNums, mnodeNums=mnodeNums, independentMnode=independentMnode)
|
dnodeslist = cluster.configure_cluster(dnodeNums=dnodeNums, mnodeNums=mnodeNums, independentMnode=independentMnode, level=level, disk=disk)
|
||||||
tdDnodes = ClusterDnodes(dnodeslist)
|
tdDnodes = ClusterDnodes(dnodeslist)
|
||||||
tdDnodes.init(deployPath, masterIp)
|
tdDnodes.init(deployPath, masterIp)
|
||||||
tdDnodes.setTestCluster(testCluster)
|
tdDnodes.setTestCluster(testCluster)
|
||||||
|
@ -498,6 +511,7 @@ if __name__ == "__main__":
|
||||||
else:
|
else:
|
||||||
tdLog.info("not need to query")
|
tdLog.info("not need to query")
|
||||||
else:
|
else:
|
||||||
|
# except windows
|
||||||
tdDnodes.setKillValgrind(killValgrind)
|
tdDnodes.setKillValgrind(killValgrind)
|
||||||
tdDnodes.init(deployPath, masterIp)
|
tdDnodes.init(deployPath, masterIp)
|
||||||
tdDnodes.setTestCluster(testCluster)
|
tdDnodes.setTestCluster(testCluster)
|
||||||
|
@ -529,6 +543,7 @@ if __name__ == "__main__":
|
||||||
|
|
||||||
if dnodeNums == 1 :
|
if dnodeNums == 1 :
|
||||||
# dnode is one
|
# dnode is one
|
||||||
|
tdDnodes.setLevelDisk(level, disk)
|
||||||
tdDnodes.deploy(1,updateCfgDict)
|
tdDnodes.deploy(1,updateCfgDict)
|
||||||
tdDnodes.start(1)
|
tdDnodes.start(1)
|
||||||
tdCases.logSql(logSql)
|
tdCases.logSql(logSql)
|
||||||
|
@ -574,7 +589,8 @@ if __name__ == "__main__":
|
||||||
# dnode > 1 cluster
|
# dnode > 1 cluster
|
||||||
tdLog.debug("create an cluster with %s nodes and make %s dnode as independent mnode"%(dnodeNums,mnodeNums))
|
tdLog.debug("create an cluster with %s nodes and make %s dnode as independent mnode"%(dnodeNums,mnodeNums))
|
||||||
print(independentMnode,"independentMnode valuse")
|
print(independentMnode,"independentMnode valuse")
|
||||||
dnodeslist = cluster.configure_cluster(dnodeNums=dnodeNums, mnodeNums=mnodeNums, independentMnode=independentMnode)
|
# create dnode list
|
||||||
|
dnodeslist = cluster.configure_cluster(dnodeNums=dnodeNums, mnodeNums=mnodeNums, independentMnode=independentMnode, level=level, disk=disk)
|
||||||
tdDnodes = ClusterDnodes(dnodeslist)
|
tdDnodes = ClusterDnodes(dnodeslist)
|
||||||
tdDnodes.init(deployPath, masterIp)
|
tdDnodes.init(deployPath, masterIp)
|
||||||
tdDnodes.setTestCluster(testCluster)
|
tdDnodes.setTestCluster(testCluster)
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
,,y,unit-test,bash test.sh
|
,,y,unit-test,bash test.sh
|
||||||
|
|
||||||
#army-test
|
#army-test
|
||||||
,,y,army,./pytest.sh python3 ./test.py -f empty.py
|
,,y,army,./pytest.sh python3 ./test.py -f enterprise/multi-level/mlevel_basic.py -N 3 -L 3 -D 2
|
||||||
|
|
||||||
#system test
|
#system test
|
||||||
,,y,system-test,./pytest.sh python3 ./test.py -f 8-stream/stream_basic.py
|
,,y,system-test,./pytest.sh python3 ./test.py -f 8-stream/stream_basic.py
|
||||||
|
@ -1069,6 +1069,7 @@ e
|
||||||
,,y,script,./test.sh -f tsim/query/unionall_as_table.sim
|
,,y,script,./test.sh -f tsim/query/unionall_as_table.sim
|
||||||
,,y,script,./test.sh -f tsim/query/multi_order_by.sim
|
,,y,script,./test.sh -f tsim/query/multi_order_by.sim
|
||||||
,,y,script,./test.sh -f tsim/query/sys_tbname.sim
|
,,y,script,./test.sh -f tsim/query/sys_tbname.sim
|
||||||
|
,,y,script,./test.sh -f tsim/query/sort-pre-cols.sim
|
||||||
,,y,script,./test.sh -f tsim/query/groupby.sim
|
,,y,script,./test.sh -f tsim/query/groupby.sim
|
||||||
,,y,script,./test.sh -f tsim/query/groupby_distinct.sim
|
,,y,script,./test.sh -f tsim/query/groupby_distinct.sim
|
||||||
,,y,script,./test.sh -f tsim/query/event.sim
|
,,y,script,./test.sh -f tsim/query/event.sim
|
||||||
|
|
|
@ -64,7 +64,7 @@ class TwoClients:
|
||||||
cursor2.execute("drop table t0")
|
cursor2.execute("drop table t0")
|
||||||
cursor2.execute("create table t0 using tb tags('beijing')")
|
cursor2.execute("create table t0 using tb tags('beijing')")
|
||||||
|
|
||||||
tdSql.execute("insert into t0 values(now, 2, 'test')")
|
tdSql.execute("insert into t0 values(now+1s, 2, 'test')")
|
||||||
tdSql.query("select * from tb")
|
tdSql.query("select * from tb")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
|
|
||||||
|
|
|
@ -52,10 +52,9 @@ class ConfigureyCluster:
|
||||||
dnode.addExtraCfg("secondEp", f"{hostname}:{startPort_sec}")
|
dnode.addExtraCfg("secondEp", f"{hostname}:{startPort_sec}")
|
||||||
|
|
||||||
# configure dnoe of independent mnodes
|
# configure dnoe of independent mnodes
|
||||||
if num <= self.mnodeNums and self.mnodeNums != 0 and independentMnode == True :
|
if num <= self.mnodeNums and self.mnodeNums != 0 and independentMnode == "True" :
|
||||||
tdLog.info(f"set mnode:{num} supportVnodes 0")
|
tdLog.info(f"set mnode:{num} supportVnodes 0")
|
||||||
dnode.addExtraCfg("supportVnodes", 0)
|
dnode.addExtraCfg("supportVnodes", 0)
|
||||||
# print(dnode)
|
|
||||||
self.dnodes.append(dnode)
|
self.dnodes.append(dnode)
|
||||||
return self.dnodes
|
return self.dnodes
|
||||||
|
|
||||||
|
|
|
@ -130,6 +130,7 @@ class TDDnode:
|
||||||
"locale": "en_US.UTF-8",
|
"locale": "en_US.UTF-8",
|
||||||
"charset": "UTF-8",
|
"charset": "UTF-8",
|
||||||
"asyncLog": "0",
|
"asyncLog": "0",
|
||||||
|
"DebugFlag": "131",
|
||||||
"mDebugFlag": "143",
|
"mDebugFlag": "143",
|
||||||
"dDebugFlag": "143",
|
"dDebugFlag": "143",
|
||||||
"vDebugFlag": "143",
|
"vDebugFlag": "143",
|
||||||
|
|
|
@ -78,6 +78,26 @@ class TDSql:
|
||||||
self.cursor.execute(s)
|
self.cursor.execute(s)
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
|
def execute(self, sql, queryTimes=30, show=False):
|
||||||
|
self.sql = sql
|
||||||
|
if show:
|
||||||
|
tdLog.info(sql)
|
||||||
|
i=1
|
||||||
|
while i <= queryTimes:
|
||||||
|
try:
|
||||||
|
self.affectedRows = self.cursor.execute(sql)
|
||||||
|
return self.affectedRows
|
||||||
|
except Exception as e:
|
||||||
|
tdLog.notice("Try to execute sql again, query times: %d "%i)
|
||||||
|
if i == queryTimes:
|
||||||
|
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
||||||
|
args = (caller.filename, caller.lineno, sql, repr(e))
|
||||||
|
tdLog.notice("%s(%d) failed: sql:%s, %s" % args)
|
||||||
|
raise Exception(repr(e))
|
||||||
|
i+=1
|
||||||
|
time.sleep(1)
|
||||||
|
pass
|
||||||
|
|
||||||
def error(self, sql, expectedErrno = None, expectErrInfo = None, fullMatched = True):
|
def error(self, sql, expectedErrno = None, expectErrInfo = None, fullMatched = True):
|
||||||
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
||||||
expectErrNotOccured = True
|
expectErrNotOccured = True
|
||||||
|
@ -108,7 +128,7 @@ class TDSql:
|
||||||
if expectErrInfo == self.error_info:
|
if expectErrInfo == self.error_info:
|
||||||
tdLog.info("sql:%s, expected expectErrInfo '%s' occured" % (sql, expectErrInfo))
|
tdLog.info("sql:%s, expected expectErrInfo '%s' occured" % (sql, expectErrInfo))
|
||||||
else:
|
else:
|
||||||
tdLog.exit("%s(%d) failed: sql:%s, expectErrInfo '%s' occured, but not expected errno '%s'" % (caller.filename, caller.lineno, sql, self.error_info, expectErrInfo))
|
tdLog.exit("%s(%d) failed: sql:%s, expectErrInfo '%s' occured, but not expected expectErrInfo '%s'" % (caller.filename, caller.lineno, sql, self.error_info, expectErrInfo))
|
||||||
else:
|
else:
|
||||||
if expectedErrno != None:
|
if expectedErrno != None:
|
||||||
if expectedErrno in self.errno:
|
if expectedErrno in self.errno:
|
||||||
|
@ -120,7 +140,7 @@ class TDSql:
|
||||||
if expectErrInfo in self.error_info:
|
if expectErrInfo in self.error_info:
|
||||||
tdLog.info("sql:%s, expected expectErrInfo '%s' occured" % (sql, expectErrInfo))
|
tdLog.info("sql:%s, expected expectErrInfo '%s' occured" % (sql, expectErrInfo))
|
||||||
else:
|
else:
|
||||||
tdLog.exit("%s(%d) failed: sql:%s, expectErrInfo %s occured, but not expected errno '%s'" % (caller.filename, caller.lineno, sql, self.error_info, expectErrInfo))
|
tdLog.exit("%s(%d) failed: sql:%s, expectErrInfo %s occured, but not expected expectErrInfo '%s'" % (caller.filename, caller.lineno, sql, self.error_info, expectErrInfo))
|
||||||
|
|
||||||
return self.error_info
|
return self.error_info
|
||||||
|
|
||||||
|
@ -158,6 +178,63 @@ class TDSql:
|
||||||
time.sleep(1)
|
time.sleep(1)
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
def query_success_failed(self, sql, row_tag=None, queryTimes=10, count_expected_res=None, expectErrInfo = None, fullMatched = True):
|
||||||
|
self.sql = sql
|
||||||
|
i=1
|
||||||
|
while i <= queryTimes:
|
||||||
|
try:
|
||||||
|
self.cursor.execute(sql)
|
||||||
|
self.queryResult = self.cursor.fetchall()
|
||||||
|
self.queryRows = len(self.queryResult)
|
||||||
|
self.queryCols = len(self.cursor.description)
|
||||||
|
|
||||||
|
if count_expected_res is not None:
|
||||||
|
counter = 0
|
||||||
|
while count_expected_res != self.queryResult[0][0]:
|
||||||
|
self.cursor.execute(sql)
|
||||||
|
self.queryResult = self.cursor.fetchall()
|
||||||
|
if counter < queryTimes:
|
||||||
|
counter += 0.5
|
||||||
|
time.sleep(0.5)
|
||||||
|
else:
|
||||||
|
return False
|
||||||
|
|
||||||
|
tdLog.info("query is success")
|
||||||
|
time.sleep(1)
|
||||||
|
continue
|
||||||
|
except Exception as e:
|
||||||
|
tdLog.notice("Try to query again, query times: %d "%i)
|
||||||
|
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
||||||
|
if i < queryTimes:
|
||||||
|
error_info = repr(e)
|
||||||
|
print(error_info)
|
||||||
|
self.error_info = ','.join(error_info[error_info.index('(')+1:-1].split(",")[:-1]).replace("'","")
|
||||||
|
self.queryRows = 0
|
||||||
|
self.queryCols = 0
|
||||||
|
self.queryResult = None
|
||||||
|
|
||||||
|
if fullMatched:
|
||||||
|
if expectErrInfo != None:
|
||||||
|
if expectErrInfo == self.error_info:
|
||||||
|
tdLog.info("sql:%s, expected expectErrInfo '%s' occured" % (sql, expectErrInfo))
|
||||||
|
else:
|
||||||
|
tdLog.exit("%s(%d) failed: sql:%s, expectErrInfo '%s' occured, but not expected expectErrInfo '%s'" % (caller.filename, caller.lineno, sql, self.error_info, expectErrInfo))
|
||||||
|
else:
|
||||||
|
if expectErrInfo != None:
|
||||||
|
if expectErrInfo in self.error_info:
|
||||||
|
tdLog.info("sql:%s, expected expectErrInfo '%s' occured" % (sql, expectErrInfo))
|
||||||
|
else:
|
||||||
|
tdLog.exit("%s(%d) failed: sql:%s, expectErrInfo %s occured, but not expected expectErrInfo '%s'" % (caller.filename, caller.lineno, sql, self.error_info, expectErrInfo))
|
||||||
|
|
||||||
|
return self.error_info
|
||||||
|
elif i == queryTimes:
|
||||||
|
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
||||||
|
args = (caller.filename, caller.lineno, sql, repr(e))
|
||||||
|
tdLog.notice("%s(%d) failed: sql:%s, %s" % args)
|
||||||
|
raise Exception(repr(e))
|
||||||
|
i+=1
|
||||||
|
time.sleep(1)
|
||||||
|
pass
|
||||||
|
|
||||||
def is_err_sql(self, sql):
|
def is_err_sql(self, sql):
|
||||||
err_flag = True
|
err_flag = True
|
||||||
|
@ -471,25 +548,7 @@ class TDSql:
|
||||||
time.sleep(1)
|
time.sleep(1)
|
||||||
continue
|
continue
|
||||||
|
|
||||||
def execute(self, sql, queryTimes=30, show=False):
|
|
||||||
self.sql = sql
|
|
||||||
if show:
|
|
||||||
tdLog.info(sql)
|
|
||||||
i=1
|
|
||||||
while i <= queryTimes:
|
|
||||||
try:
|
|
||||||
self.affectedRows = self.cursor.execute(sql)
|
|
||||||
return self.affectedRows
|
|
||||||
except Exception as e:
|
|
||||||
tdLog.notice("Try to execute sql again, query times: %d "%i)
|
|
||||||
if i == queryTimes:
|
|
||||||
caller = inspect.getframeinfo(inspect.stack()[1][0])
|
|
||||||
args = (caller.filename, caller.lineno, sql, repr(e))
|
|
||||||
tdLog.notice("%s(%d) failed: sql:%s, %s" % args)
|
|
||||||
raise Exception(repr(e))
|
|
||||||
i+=1
|
|
||||||
time.sleep(1)
|
|
||||||
pass
|
|
||||||
|
|
||||||
def checkAffectedRows(self, expectAffectedRows):
|
def checkAffectedRows(self, expectAffectedRows):
|
||||||
if self.affectedRows != expectAffectedRows:
|
if self.affectedRows != expectAffectedRows:
|
||||||
|
|
|
@ -0,0 +1,17 @@
|
||||||
|
|
||||||
|
system sh/stop_dnodes.sh
|
||||||
|
system sh/deploy.sh -n dnode1 -i 1
|
||||||
|
system sh/exec.sh -n dnode1 -s start
|
||||||
|
sql connect
|
||||||
|
|
||||||
|
sql create database d
|
||||||
|
sql use d
|
||||||
|
sql create table st(ts timestamp, v int) tags(lj json)
|
||||||
|
sql insert into ct1 using st tags('{"instance":"200"}') values(now, 1)(now+1s, 2);
|
||||||
|
sql insert into ct2 using st tags('{"instance":"200"}') values(now+2s, 3)(now+3s, 4);
|
||||||
|
sql select to_char(ts, 'yyyy-mm-dd hh24:mi:ss') as time, irate(v) from st group by to_char(ts, 'yyyy-mm-dd hh24:mi:ss'), lj->'instance' order by time;
|
||||||
|
print $data01
|
||||||
|
if $data01 != 0.000000000 then
|
||||||
|
return -1
|
||||||
|
endi
|
||||||
|
system sh/exec.sh -n dnode1 -s stop -x SIGINT
|
|
@ -327,4 +327,40 @@ if $rows != 1 then
|
||||||
goto loop17
|
goto loop17
|
||||||
endi
|
endi
|
||||||
|
|
||||||
|
sql create database test2 vgroups 4;
|
||||||
|
sql use test2;
|
||||||
|
sql create stable st(ts timestamp,a int,b int,c int) tags(ta int,tb int,tc int);
|
||||||
|
sql create table t1 using st tags(1,1,1);
|
||||||
|
sql create table t2 using st tags(2,2,2);
|
||||||
|
sql create stream streams4 trigger at_once ignore update 0 ignore expired 0 into streamt4 as select _wstart, count(*) c1, count(a) c2 from st session(ts, 2s) ;
|
||||||
|
|
||||||
|
sql insert into t1 values(1648791255100,1,2,3);
|
||||||
|
sql insert into t1 values(1648791255300,1,2,3);
|
||||||
|
|
||||||
|
sleep 1000
|
||||||
|
|
||||||
|
sql insert into t1 values(1648791253000,1,2,3) (1648791254000,1,2,3);
|
||||||
|
|
||||||
|
$loop_count = 0
|
||||||
|
loop18:
|
||||||
|
sleep 1000
|
||||||
|
sql select * from streamt4;
|
||||||
|
|
||||||
|
$loop_count = $loop_count + 1
|
||||||
|
if $loop_count == 10 then
|
||||||
|
return -1
|
||||||
|
endi
|
||||||
|
|
||||||
|
if $rows != 1 then
|
||||||
|
print =====rows=$rows
|
||||||
|
goto loop18
|
||||||
|
endi
|
||||||
|
|
||||||
|
if $data01 != 4 then
|
||||||
|
print =====data01=$data01
|
||||||
|
goto loop18
|
||||||
|
endi
|
||||||
|
|
||||||
|
print =====over
|
||||||
|
|
||||||
system sh/exec.sh -n dnode1 -s stop -x SIGINT
|
system sh/exec.sh -n dnode1 -s stop -x SIGINT
|
||||||
|
|
|
@ -215,6 +215,12 @@ class TDTestCase:
|
||||||
self.svr_check(item["name"], item["alias"], item["except_values"], True)
|
self.svr_check(item["name"], item["alias"], item["except_values"], True)
|
||||||
else:
|
else:
|
||||||
raise Exception(f"unknown key: {key}")
|
raise Exception(f"unknown key: {key}")
|
||||||
|
# reset log
|
||||||
|
path = os.sep.join([tdDnodes.getDnodesRootDir(), "dnode1", "log", "taosdlog.*"])
|
||||||
|
tdSql.execute("alter all dnodes 'resetlog';")
|
||||||
|
r = subprocess.Popen("cat {} | grep 'reset log file'".format(path), shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
|
||||||
|
stdout, stderr = r.communicate()
|
||||||
|
assert('reset log file' in stdout.decode())
|
||||||
|
|
||||||
def stop(self):
|
def stop(self):
|
||||||
tdSql.close()
|
tdSql.close()
|
||||||
|
|
|
@ -26,12 +26,10 @@ class TDTestCase:
|
||||||
self.file1 = f"{self.testcasePath}/b.csv"
|
self.file1 = f"{self.testcasePath}/b.csv"
|
||||||
self.file2 = f"{self.testcasePath}/c.csv"
|
self.file2 = f"{self.testcasePath}/c.csv"
|
||||||
|
|
||||||
#os.system("rm -rf %s/b.csv" %self.testcasePath)
|
|
||||||
tdLog.debug(f"start to excute {__file__}")
|
tdLog.debug(f"start to excute {__file__}")
|
||||||
tdSql.init(conn.cursor(), logSql)
|
tdSql.init(conn.cursor(), logSql)
|
||||||
|
|
||||||
def check_count(self, rows, records):
|
def check_count(self, rows, records):
|
||||||
tdSql.execute(f"use {self.db};")
|
|
||||||
tdSql.query(f"select tbname,count(*) from {self.stable0} group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from {self.stable0} group by tbname order by tbname;")
|
||||||
tdSql.checkRows(rows)
|
tdSql.checkRows(rows)
|
||||||
for i in range(rows):
|
for i in range(rows):
|
||||||
|
@ -39,13 +37,6 @@ class TDTestCase:
|
||||||
|
|
||||||
def reset_tb(self):
|
def reset_tb(self):
|
||||||
# create database and tables
|
# create database and tables
|
||||||
# os.system("taos -s 'drop database if exists d1;'")
|
|
||||||
# os.system("taos -s 'create database d1;use d1;create stable meters (ts timestamp, current float, voltage int, phase float) tags (location binary(64), groupId int);'")
|
|
||||||
# os.system(f"taos -s 'use d1;create table d2001 using meters(groupId) tags(5);'")
|
|
||||||
# res = os.system(f"taos -s 'use d1;create table d2002 using meters(groupId) tags(6);'")
|
|
||||||
# if (0 != res):
|
|
||||||
# tdLog.exit(f"create tb error")
|
|
||||||
|
|
||||||
tdSql.execute(f"drop database if exists {self.db};")
|
tdSql.execute(f"drop database if exists {self.db};")
|
||||||
tdSql.execute(f"create database {self.db};")
|
tdSql.execute(f"create database {self.db};")
|
||||||
tdSql.execute(f"use {self.db};")
|
tdSql.execute(f"use {self.db};")
|
||||||
|
@ -54,13 +45,14 @@ class TDTestCase:
|
||||||
tdSql.execute(f"create table {self.tb2} {self.tag2};")
|
tdSql.execute(f"create table {self.tb2} {self.tag2};")
|
||||||
tdSql.execute(f"create stable {self.stable1} (ts timestamp , q_int int , q_bigint bigint , q_smallint smallint , q_tinyint tinyint , q_float float , q_double double , q_bool bool , q_binary binary(100) , q_nchar nchar(100) , q_ts timestamp , q_int_null int , q_bigint_null bigint , q_smallint_null smallint , q_tinyint_null tinyint, q_float_null float , q_double_null double , q_bool_null bool , q_binary_null binary(20) , q_nchar_null nchar(20) , q_ts_null timestamp) tags(loc nchar(100) , t_int int , t_bigint bigint , t_smallint smallint , t_tinyint tinyint, t_bool bool , t_binary binary(100) , t_nchar nchar(100) ,t_float float , t_double double , t_ts timestamp);")
|
tdSql.execute(f"create stable {self.stable1} (ts timestamp , q_int int , q_bigint bigint , q_smallint smallint , q_tinyint tinyint , q_float float , q_double double , q_bool bool , q_binary binary(100) , q_nchar nchar(100) , q_ts timestamp , q_int_null int , q_bigint_null bigint , q_smallint_null smallint , q_tinyint_null tinyint, q_float_null float , q_double_null double , q_bool_null bool , q_binary_null binary(20) , q_nchar_null nchar(20) , q_ts_null timestamp) tags(loc nchar(100) , t_int int , t_bigint bigint , t_smallint smallint , t_tinyint tinyint, t_bool bool , t_binary binary(100) , t_nchar nchar(100) ,t_float float , t_double double , t_ts timestamp);")
|
||||||
tdSql.execute(f"create stable {self.stable2} (ts timestamp , q_int int , q_bigint bigint , q_smallint smallint , q_tinyint tinyint , q_float float , q_double double , q_bool bool , q_binary binary(100) , q_nchar nchar(100) , q_ts timestamp , q_int_null int , q_bigint_null bigint , q_smallint_null smallint , q_tinyint_null tinyint, q_float_null float , q_double_null double , q_bool_null bool , q_binary_null binary(20) , q_nchar_null nchar(20) , q_ts_null timestamp) tags(loc nchar(100) , t_int int , t_bigint bigint , t_smallint smallint , t_tinyint tinyint, t_bool bool , t_binary binary(100) , t_nchar nchar(100) ,t_float float , t_double double , t_ts timestamp);")
|
tdSql.execute(f"create stable {self.stable2} (ts timestamp , q_int int , q_bigint bigint , q_smallint smallint , q_tinyint tinyint , q_float float , q_double double , q_bool bool , q_binary binary(100) , q_nchar nchar(100) , q_ts timestamp , q_int_null int , q_bigint_null bigint , q_smallint_null smallint , q_tinyint_null tinyint, q_float_null float , q_double_null double , q_bool_null bool , q_binary_null binary(20) , q_nchar_null nchar(20) , q_ts_null timestamp) tags(loc nchar(100) , t_int int , t_bigint bigint , t_smallint smallint , t_tinyint tinyint, t_bool bool , t_binary binary(100) , t_nchar nchar(100) ,t_float float , t_double double , t_ts timestamp);")
|
||||||
|
tdSql.execute(f"create table {self.stable1}_1 using {self.stable1}(t_int) tags(1);")
|
||||||
|
tdSql.execute(f"create table {self.stable2}_1 using {self.stable2}(t_int) tags(2);")
|
||||||
|
|
||||||
def test(self, sql):
|
def test(self, sql):
|
||||||
sql = f"use {self.db};" + sql
|
# sql = f"use {self.db};" + sql
|
||||||
res = os.system(f'taos -s "{sql}"')
|
# os.system(f'taos -s "{sql}"')
|
||||||
# if (0 != res):
|
print(f'{sql}\n')
|
||||||
# tdLog.exit(f"taos sql error")
|
tdSql.execute(sql, 1)
|
||||||
|
|
||||||
|
|
||||||
def check(self):
|
def check(self):
|
||||||
# same table, auto create + create
|
# same table, auto create + create
|
||||||
|
@ -95,13 +87,8 @@ class TDTestCase:
|
||||||
sql = f"insert into {self.tb1} file '{self.file1}' {self.tb2} file '{self.file2}';"
|
sql = f"insert into {self.tb1} file '{self.file1}' {self.tb2} file '{self.file2}';"
|
||||||
self.test(sql)
|
self.test(sql)
|
||||||
|
|
||||||
# bigNum = 1010000
|
self.check_count(2, [2010000, 1000000])
|
||||||
# self.check_count(5, [2100, 2100, bigNum, bigNum, bigNum])
|
|
||||||
|
|
||||||
result = os.popen("taos -s 'select count(*) from %s.%s'" %(self.db, self.tb1))
|
|
||||||
res = result.read()
|
|
||||||
if (f"OK" in res):
|
|
||||||
tdLog.info(f"check count success")
|
|
||||||
|
|
||||||
def make_csv(self, filepath, once, qtime, startts):
|
def make_csv(self, filepath, once, qtime, startts):
|
||||||
f = open(filepath, 'w')
|
f = open(filepath, 'w')
|
||||||
|
@ -118,10 +105,8 @@ class TDTestCase:
|
||||||
|
|
||||||
def test_mix(self):
|
def test_mix(self):
|
||||||
#forbid use both value and file in one insert
|
#forbid use both value and file in one insert
|
||||||
result = os.popen(f"insert into {self.tb1} file '{self.file2}' {self.tb2} values('2021-07-13 14:06:34.630', 10.2, 219, 0.32);")
|
self.make_csv(self.file2, 10, 10, self.ts)
|
||||||
res = result.read()
|
tdSql.error(f"insert into {self.tb1} file '{self.file2}' {self.tb2} values('2021-07-13 14:06:34.630', 10.2, 219, 0.32);")
|
||||||
if (f"error" in res):
|
|
||||||
tdLog.info(f"forbid success")
|
|
||||||
|
|
||||||
def test_bigcsv(self):
|
def test_bigcsv(self):
|
||||||
# prepare csv
|
# prepare csv
|
||||||
|
@ -144,7 +129,6 @@ class TDTestCase:
|
||||||
self.test(sql)
|
self.test(sql)
|
||||||
print("end insert to table")
|
print("end insert to table")
|
||||||
|
|
||||||
#tdSql.execute(f"use d1;")
|
|
||||||
tdSql.query(f"select tbname,count(*) from {self.stable0} group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from {self.stable0} group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, rowNum1)
|
tdSql.checkData(0, 1, rowNum1)
|
||||||
|
@ -160,7 +144,7 @@ class TDTestCase:
|
||||||
ts = startts + offset
|
ts = startts + offset
|
||||||
rows = []
|
rows = []
|
||||||
for i in range(once):
|
for i in range(once):
|
||||||
rows.append([table_name, ts + i, offset + i, 'NULL'])
|
rows.append([f"\'{table_name}\'", ts + i, offset + i, 'NULL'])
|
||||||
writer.writerows(rows)
|
writer.writerows(rows)
|
||||||
f.close()
|
f.close()
|
||||||
print(datetime.now(), filepath, " ready!")
|
print(datetime.now(), filepath, " ready!")
|
||||||
|
@ -171,22 +155,22 @@ class TDTestCase:
|
||||||
once = 10000
|
once = 10000
|
||||||
qtime1 = 101
|
qtime1 = 101
|
||||||
qtime2 = 100
|
qtime2 = 100
|
||||||
# rowNum1 = qtime1 * once
|
|
||||||
# rowNum2 = qtime2 * once
|
|
||||||
child_1 = f"{self.stable1}_1"
|
child_1 = f"{self.stable1}_1"
|
||||||
child_2 = f"{self.stable2}_1"
|
child_2 = f"{self.stable2}_1"
|
||||||
self.make_stable_csv(self.file1, once, qtime1, self.ts - 86400000, child_1)
|
self.make_stable_csv(self.file1, once, qtime1, self.ts - 86400000, child_1)
|
||||||
self.make_stable_csv(self.file2, once, qtime2, self.ts, child_2)
|
self.make_stable_csv(self.file2, once, qtime2, self.ts, child_2)
|
||||||
print("end stable_csv data prepare")
|
print("end stable_csv data prepare")
|
||||||
|
|
||||||
# insert create child table of stable
|
|
||||||
sql = f"insert into {self.db}.{self.stable1}(tbname,ts,q_int,q_binary) file '{self.file1}' {self.db}.{self.stable2}(tbname,ts,q_int,q_binary) file '{self.file2}';"
|
sql = f"insert into {self.db}.{self.stable1}(tbname,ts,q_int,q_binary) file '{self.file1}' {self.db}.{self.stable2}(tbname,ts,q_int,q_binary) file '{self.file2}';"
|
||||||
self.test(sql)
|
self.test(sql)
|
||||||
print("end insert to stable")
|
print("end insert to stable")
|
||||||
|
|
||||||
#tdSql.execute(f"insert into {self.db}.{child_1}(ts, q_int) values(now, 1);")
|
tdSql.query(f"select tbname,count(*) from {self.stable1} group by tbname;")
|
||||||
tdSql.query(f"select tbname,count(*) from {self.stable1} group by tbname order by tbname;")
|
tdSql.checkRows(1)
|
||||||
tdSql.checkRows(0)
|
tdSql.checkData(0, 1, qtime1 * once)
|
||||||
|
tdSql.query(f"select tbname,count(*) from {self.stable2} group by tbname;")
|
||||||
|
tdSql.checkRows(1)
|
||||||
|
tdSql.checkData(0, 1, qtime2 * once)
|
||||||
print("check stable success")
|
print("check stable success")
|
||||||
|
|
||||||
def run(self):
|
def run(self):
|
||||||
|
@ -194,8 +178,10 @@ class TDTestCase:
|
||||||
self.reset_tb()
|
self.reset_tb()
|
||||||
self.test_stable_csv()
|
self.test_stable_csv()
|
||||||
self.test_bigcsv()
|
self.test_bigcsv()
|
||||||
self.test_mix()
|
|
||||||
self.check()
|
self.check()
|
||||||
|
self.test_mix()
|
||||||
|
os.system(f"rm -rf {self.file1}")
|
||||||
|
os.system(f"rm -rf {self.file2}")
|
||||||
tdSql.close()
|
tdSql.close()
|
||||||
|
|
||||||
def stop(self):
|
def stop(self):
|
||||||
|
|
|
@ -52,7 +52,7 @@ class TDTestCase:
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 0, i + 1)
|
tdSql.checkData(0, 0, i + 1)
|
||||||
tdSql.checkData(0, 1, 'debugFlag')
|
tdSql.checkData(0, 1, 'debugFlag')
|
||||||
tdSql.checkData(0, 2, 0)
|
tdSql.checkData(0, 2, 131)
|
||||||
|
|
||||||
tdSql.query("show dnode 1 variables like '%debugFlag'")
|
tdSql.query("show dnode 1 variables like '%debugFlag'")
|
||||||
tdSql.checkRows(23)
|
tdSql.checkRows(23)
|
||||||
|
|
|
@ -88,12 +88,12 @@ class TDTestCase:
|
||||||
tdSql.execute(
|
tdSql.execute(
|
||||||
f"create table {dbname}.ntb_null(ts timestamp,c1 int,c2 double,c3 float,c4 bool)")
|
f"create table {dbname}.ntb_null(ts timestamp,c1 int,c2 double,c3 float,c4 bool)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, 1, 1.0, NULL, NULL)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now, 1, 1.0, NULL, NULL)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, NULL, 2.0, 2.0, NULL)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now+1s, NULL, 2.0, 2.0, NULL)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, 2, NULL, NULL, false)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now+2s, 2, NULL, NULL, false)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, NULL, 1.0, 1.0, NULL)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now+3s, NULL, 1.0, 1.0, NULL)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, NULL, 3.0, NULL, true)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now+4s, NULL, 3.0, NULL, true)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, 3, NULL, 3.0, NULL)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now+5s, 3, NULL, 3.0, NULL)")
|
||||||
tdSql.execute(f"insert into {dbname}.ntb_null values(now, 1, NULL, NULL, true)")
|
tdSql.execute(f"insert into {dbname}.ntb_null values(now+6s, 1, NULL, NULL, true)")
|
||||||
|
|
||||||
tdSql.query(f"select diff(c1) from {dbname}.ntb_null")
|
tdSql.query(f"select diff(c1) from {dbname}.ntb_null")
|
||||||
tdSql.checkRows(6)
|
tdSql.checkRows(6)
|
||||||
|
|
|
@ -28,7 +28,7 @@ class TDTestCase:
|
||||||
def init(self, conn, logSql, replicaVar=1):
|
def init(self, conn, logSql, replicaVar=1):
|
||||||
self.replicaVar = int(replicaVar)
|
self.replicaVar = int(replicaVar)
|
||||||
tdLog.debug(f"start to excute {__file__}")
|
tdLog.debug(f"start to excute {__file__}")
|
||||||
tdSql.init(conn.cursor(), False)
|
tdSql.init(conn.cursor(), True)
|
||||||
|
|
||||||
def create_database(self,tsql, dbName,dropFlag=1,vgroups=2,replica=1, duration:str='1d'):
|
def create_database(self,tsql, dbName,dropFlag=1,vgroups=2,replica=1, duration:str='1d'):
|
||||||
if dropFlag == 1:
|
if dropFlag == 1:
|
||||||
|
@ -284,6 +284,8 @@ class TDTestCase:
|
||||||
tdSql.checkData(0, 3, 1001)
|
tdSql.checkData(0, 3, 1001)
|
||||||
tdSql.checkData(0, 4, "2018-11-25 19:30:00.000")
|
tdSql.checkData(0, 4, "2018-11-25 19:30:00.000")
|
||||||
|
|
||||||
|
tdSql.query("select last(ts) from meters partition by tbname")
|
||||||
|
tdSql.query("select last(ts) from meters partition by t1")
|
||||||
sql_template = 'select %s from meters partition by tbname'
|
sql_template = 'select %s from meters partition by tbname'
|
||||||
select_items = ["ts, last(c10), c10, ts", "ts, ts, last(c10), c10, tbname", "last(c10), c10, ts"]
|
select_items = ["ts, last(c10), c10, ts", "ts, ts, last(c10), c10, tbname", "last(c10), c10, ts"]
|
||||||
has_last_row_scan_res = [1,1,1]
|
has_last_row_scan_res = [1,1,1]
|
||||||
|
@ -339,44 +341,12 @@ class TDTestCase:
|
||||||
tdSql.checkData(0, 0, '999')
|
tdSql.checkData(0, 0, '999')
|
||||||
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c1; alter table test.meters add column c12 int"])
|
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c1; alter table test.meters add column c12 int"])
|
||||||
p.check_returncode()
|
p.check_returncode()
|
||||||
tdSql.query("select last(c1) from meters", queryTimes=1)
|
tdSql.query_success_failed("select ts, last(c1), c1, ts, c1 from meters", queryTimes=10, expectErrInfo="Invalid column name: c1")
|
||||||
tdSql.checkData(0, 0, None)
|
tdSql.query('select last(c12), c12, ts from meters', queryTimes=1)
|
||||||
tdSql.query('select last(*) from meters', queryTimes=1)
|
|
||||||
print(str(tdSql.queryResult))
|
|
||||||
tdSql.checkData(0, 1, None)
|
|
||||||
tdSql.query('select last(c1), c1, ts from meters', queryTimes=1)
|
|
||||||
tdSql.checkRows(1)
|
|
||||||
tdSql.checkData(0, 0, None)
|
|
||||||
tdSql.checkData(0, 1, None)
|
|
||||||
tdSql.checkData(0, 2, None)
|
|
||||||
|
|
||||||
try:
|
|
||||||
tdSql.query('select ts, last(c1), c1, ts, c1 from meters', queryTimes=1)
|
|
||||||
except Exception as e:
|
|
||||||
if str(e).count('Invalid column name') == 1:
|
|
||||||
print('column has been dropped, the cache has been updated: %s' % (str(e)))
|
|
||||||
return
|
|
||||||
else:
|
|
||||||
raise
|
|
||||||
tdSql.checkRows(1)
|
|
||||||
tdSql.checkCols(5)
|
|
||||||
tdSql.checkData(0, 0, None)
|
|
||||||
tdSql.checkData(0, 1, None)
|
|
||||||
tdSql.checkData(0, 2, None)
|
|
||||||
tdSql.checkData(0, 3, None)
|
|
||||||
tdSql.checkData(0, 4, None)
|
|
||||||
|
|
||||||
try:
|
|
||||||
tdSql.query('select last(c1), last(c2), last(c3) from meters', queryTimes=1)
|
|
||||||
except Exception as e:
|
|
||||||
if str(e).count('Invalid column name') == 1:
|
|
||||||
print('column has been dropped, the cache has been updated: %s' % (str(e)))
|
|
||||||
return
|
|
||||||
else:
|
|
||||||
raise
|
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkCols(3)
|
tdSql.checkCols(3)
|
||||||
tdSql.checkData(0, 0, None)
|
tdSql.checkData(0, 0, None)
|
||||||
|
tdSql.checkData(0, 1, None)
|
||||||
|
|
||||||
def test_cache_scan_with_drop_column(self):
|
def test_cache_scan_with_drop_column(self):
|
||||||
tdSql.query('select last(*) from meters')
|
tdSql.query('select last(*) from meters')
|
||||||
|
@ -401,49 +371,48 @@ class TDTestCase:
|
||||||
tdSql.checkData(0, 10, None)
|
tdSql.checkData(0, 10, None)
|
||||||
|
|
||||||
def test_cache_scan_last_row_with_drop_column2(self):
|
def test_cache_scan_last_row_with_drop_column2(self):
|
||||||
tdSql.query('select last_row(c1) from meters')
|
tdSql.query('select last_row(c2) from meters')
|
||||||
print(str(tdSql.queryResult))
|
print(str(tdSql.queryResult))
|
||||||
tdSql.checkCols(1)
|
tdSql.checkCols(1)
|
||||||
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c1; alter table test.meters add column c11 int"])
|
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c2; alter table test.meters add column c1 int"])
|
||||||
p.check_returncode()
|
p.check_returncode()
|
||||||
tdSql.query('select last_row(c1) from meters', queryTimes=1)
|
tdSql.query_success_failed("select ts, last_row(c2), c12, ts, c12 from meters", queryTimes=10, expectErrInfo="Invalid column name: c2")
|
||||||
print(str(tdSql.queryResult))
|
tdSql.query('select last(c1), c1, ts from meters', queryTimes=1)
|
||||||
tdSql.checkCols(1)
|
tdSql.checkRows(1)
|
||||||
|
tdSql.checkCols(3)
|
||||||
tdSql.checkData(0, 0, None)
|
tdSql.checkData(0, 0, None)
|
||||||
|
tdSql.checkData(0, 1, None)
|
||||||
|
|
||||||
def test_cache_scan_last_row_with_partition_by(self):
|
def test_cache_scan_last_row_with_partition_by(self):
|
||||||
tdSql.query('select last(c1) from meters partition by t1')
|
tdSql.query('select last(c1) from meters partition by t1')
|
||||||
print(str(tdSql.queryResult))
|
print(str(tdSql.queryResult))
|
||||||
tdSql.checkCols(1)
|
tdSql.checkCols(1)
|
||||||
tdSql.checkRows(5)
|
tdSql.checkRows(2)
|
||||||
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c1; alter table test.meters add column c11 int"])
|
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c1; alter table test.meters add column c2 int"])
|
||||||
p.check_returncode()
|
p.check_returncode()
|
||||||
tdSql.query('select last_row(c1) from meters partition by t1', queryTimes=1)
|
tdSql.query_success_failed('select last(c1) from meters partition by t1', queryTimes=10, expectErrInfo="Invalid column name: c1")
|
||||||
|
tdSql.query('select last(c2), c2, ts from meters', queryTimes=1)
|
||||||
print(str(tdSql.queryResult))
|
print(str(tdSql.queryResult))
|
||||||
tdSql.checkCols(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkRows(5)
|
tdSql.checkCols(3)
|
||||||
tdSql.checkData(0, 0, None)
|
tdSql.checkData(0, 0, None)
|
||||||
tdSql.checkData(1, 0, None)
|
tdSql.checkData(0, 1, None)
|
||||||
tdSql.checkData(2, 0, None)
|
|
||||||
tdSql.checkData(3, 0, None)
|
|
||||||
tdSql.checkData(4, 0, None)
|
|
||||||
|
|
||||||
def test_cache_scan_last_row_with_partition_by_tbname(self):
|
def test_cache_scan_last_row_with_partition_by_tbname(self):
|
||||||
tdSql.query('select last(c1) from meters partition by tbname', queryTimes=1)
|
tdSql.query('select last(c2) from meters partition by tbname')
|
||||||
print(str(tdSql.queryResult))
|
print(str(tdSql.queryResult))
|
||||||
tdSql.checkCols(1)
|
tdSql.checkCols(1)
|
||||||
tdSql.checkRows(10)
|
tdSql.checkRows(10)
|
||||||
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c1; alter table test.meters add column c11 int"])
|
p = subprocess.run(["taos", '-s', "alter table test.meters drop column c2; alter table test.meters add column c1 int"])
|
||||||
p.check_returncode()
|
p.check_returncode()
|
||||||
tdSql.query('select last_row(c1) from meters partition by tbname', queryTimes=1)
|
tdSql.query_success_failed('select last_row(c2) from meters partition by tbname', queryTimes=10, expectErrInfo="Invalid column name: c2")
|
||||||
|
tdSql.query('select last(c1), c1, ts from meters', queryTimes=1)
|
||||||
print(str(tdSql.queryResult))
|
print(str(tdSql.queryResult))
|
||||||
tdSql.checkCols(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkRows(10)
|
tdSql.checkCols(3)
|
||||||
tdSql.checkData(0, 0, None)
|
tdSql.checkData(0, 0, None)
|
||||||
tdSql.checkData(1, 0, None)
|
tdSql.checkData(0, 1, None)
|
||||||
tdSql.checkData(2, 0, None)
|
|
||||||
tdSql.checkData(3, 0, None)
|
|
||||||
tdSql.checkData(4, 0, None)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -455,9 +424,9 @@ class TDTestCase:
|
||||||
self.test_cache_scan_with_drop_and_add_column2()
|
self.test_cache_scan_with_drop_and_add_column2()
|
||||||
#self.test_cache_scan_with_drop_column()
|
#self.test_cache_scan_with_drop_column()
|
||||||
#self.test_cache_scan_last_row_with_drop_column()
|
#self.test_cache_scan_last_row_with_drop_column()
|
||||||
#self.test_cache_scan_last_row_with_drop_column2()
|
self.test_cache_scan_last_row_with_drop_column2()
|
||||||
#self.test_cache_scan_last_row_with_partition_by()
|
self.test_cache_scan_last_row_with_partition_by()
|
||||||
#self.test_cache_scan_last_row_with_partition_by_tbname()
|
self.test_cache_scan_last_row_with_partition_by_tbname()
|
||||||
|
|
||||||
def stop(self):
|
def stop(self):
|
||||||
tdSql.close()
|
tdSql.close()
|
||||||
|
|
|
@ -1113,157 +1113,106 @@ class TDTestCase:
|
||||||
tdLog.debug("test insert data into stable")
|
tdLog.debug("test insert data into stable")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 100);
|
tdSql.checkData(0, 1, 100)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname) values(now,'stable_1_1');")
|
tdSql.query(f"insert into nested.stable_1 (ts,tbname) values(now,'stable_1_1');")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 101);
|
tdSql.checkData(0, 1, 101)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_int) values(now,'stable_1_1',1);")
|
qlist = ['q_int', 'q_bigint', 'q_smallint', 'q_tinyint', 'q_float', 'q_double', 'q_bool', 'q_binary', 'q_nchar', 'q_ts']
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bigint) values(now,'stable_1_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_smallint) values(now,'stable_1_1',1);")
|
coulmn_name = qlist[i]
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_tinyint) values(now,'stable_1_1',1);")
|
tdSql.execute(f"insert into nested.stable_1 (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_1_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_float) values(now,'stable_1_1',1);")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;",queryTimes=5)
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_double) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bool) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_binary) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_nchar) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_ts) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 111);
|
tdSql.checkData(0, 1, 111)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_int_null) values(now,'stable_1_1',1);")
|
q_null_list = ['q_int_null', 'q_bigint_null', 'q_smallint_null', 'q_tinyint_null', 'q_float_null', 'q_double_null', 'q_bool_null', 'q_binary_null', 'q_nchar_null', 'q_ts_null']
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bigint_null) values(now,'stable_1_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_smallint_null) values(now,'stable_1_1',1);")
|
coulmn_name = q_null_list[i]
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_tinyint_null) values(now,'stable_1_1',1);")
|
tdSql.execute(f"insert into nested.stable_1 (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_1_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_float_null) values(now,'stable_1_1',1);")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;",queryTimes=5)
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_double_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bool_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_binary_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_nchar_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_ts_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 121);
|
tdSql.checkData(0, 1, 121)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname) values(now,'stable_null_data_1');")
|
tdSql.query(f"insert into nested.stable_null_data (ts,tbname) values(now,'stable_null_data_1');")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_data_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_data_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 1);
|
tdSql.checkData(0, 1, 1)
|
||||||
|
|
||||||
|
for i in range(10):
|
||||||
|
coulmn_name = qlist[i]
|
||||||
|
tdSql.execute(f"insert into nested.stable_null_data (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_data_1',1);")
|
||||||
|
|
||||||
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;",queryTimes=5)
|
||||||
|
tdSql.checkRows(1)
|
||||||
|
tdSql.checkData(0, 1, 11)
|
||||||
|
|
||||||
|
for i in range(10):
|
||||||
|
coulmn_name = q_null_list[i]
|
||||||
|
tdSql.execute(f"insert into nested.stable_null_data (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_data_1',1);")
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_int) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bigint) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_smallint) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_tinyint) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_float) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_double) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bool) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_binary) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_nchar) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_ts) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 11);
|
tdSql.checkData(0, 1, 21)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_int_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bigint_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_smallint_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_tinyint_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_float_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_double_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bool_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_binary_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_nchar_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_ts_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
|
||||||
tdSql.checkRows(1)
|
|
||||||
tdSql.checkData(0, 1, 21);
|
|
||||||
|
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname) values(now,'stable_null_childtable_1');")
|
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname) values(now,'stable_null_childtable_1');")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 1);
|
tdSql.checkData(0, 1, 1)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_int) values(now,'stable_null_childtable_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bigint) values(now,'stable_null_childtable_1',1);")
|
coulmn_name = qlist[i]
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_smallint) values(now,'stable_null_childtable_1',1);")
|
tdSql.execute(f"insert into nested.stable_null_childtable (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_childtable_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_tinyint) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_float) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_double) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bool) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_binary) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_nchar) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_ts) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 11);
|
tdSql.checkData(0, 1, 11)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_int_null) values(now,'stable_null_childtable_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bigint_null) values(now,'stable_null_childtable_1',1);")
|
coulmn_name = q_null_list[i]
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_smallint_null) values(now,'stable_null_childtable_1',1);")
|
tdSql.execute(f"insert into nested.stable_null_childtable (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_childtable_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_tinyint_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_float_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_double_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bool_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_binary_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_nchar_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_ts_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 21);
|
tdSql.checkData(0, 1, 21)
|
||||||
|
|
||||||
def TS_3932_flushdb(self):
|
def TS_3932_flushdb(self):
|
||||||
tdLog.debug("test flush db and insert data into stable")
|
tdLog.debug("test flush db and insert data into stable")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 121);
|
tdSql.checkData(0, 1, 121)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
|
qlist = ['q_int', 'q_bigint', 'q_smallint', 'q_tinyint', 'q_float', 'q_double', 'q_bool', 'q_binary', 'q_nchar', 'q_ts']
|
||||||
|
q_null_list = ['q_int_null', 'q_bigint_null', 'q_smallint_null', 'q_tinyint_null', 'q_float_null', 'q_double_null', 'q_bool_null', 'q_binary_null', 'q_nchar_null', 'q_ts_null']
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname) values(now,'stable_1_1');")
|
tdSql.query(f"insert into nested.stable_1 (ts,tbname) values(now,'stable_1_1');")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 122);
|
tdSql.checkData(0, 1, 122)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_int) values(now,'stable_1_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bigint) values(now,'stable_1_1',1);")
|
coulmn_name = qlist[i]
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_smallint) values(now,'stable_1_1',1);")
|
tdSql.execute(f"insert into nested.stable_1 (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_1_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_tinyint) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_float) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_double) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bool) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_binary) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_nchar) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_ts) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 132);
|
tdSql.checkData(0, 1, 132)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_int_null) values(now,'stable_1_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bigint_null) values(now,'stable_1_1',1);")
|
coulmn_name = q_null_list[i]
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_smallint_null) values(now,'stable_1_1',1);")
|
tdSql.execute(f"insert into nested.stable_1 (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_1_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_tinyint_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_float_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_double_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_bool_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_binary_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_nchar_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_ts_null) values(now,'stable_1_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_1 group by tbname order by tbname;")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 1, 142);
|
tdSql.checkData(0, 1, 142)
|
||||||
tdSql.checkData(1, 1, 200);
|
tdSql.checkData(1, 1, 200)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_1 (ts,tbname,q_int) values(now,'stable_1_1',1) \
|
tdSql.execute(f"insert into nested.stable_1 (ts,tbname,q_int) values(now,'stable_1_1',1) \
|
||||||
nested.stable_1 (ts,tbname,q_bigint) values(now+1a,'stable_1_1',1)\
|
nested.stable_1 (ts,tbname,q_bigint) values(now+1a,'stable_1_1',1)\
|
||||||
nested.stable_1 (ts,tbname,q_smallint) values(now+2a,'stable_1_1',1)\
|
nested.stable_1 (ts,tbname,q_smallint) values(now+2a,'stable_1_1',1)\
|
||||||
nested.stable_1 (ts,tbname,q_tinyint) values(now+3a,'stable_1_1',1)\
|
nested.stable_1 (ts,tbname,q_tinyint) values(now+3a,'stable_1_1',1)\
|
||||||
|
@ -1283,33 +1232,20 @@ class TDTestCase:
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 22);
|
tdSql.checkData(0, 1, 22);
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_int) values(now,'stable_null_data_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bigint) values(now,'stable_null_data_1',1);")
|
coulmn_name = qlist[i]
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_smallint) values(now,'stable_null_data_1',1);")
|
tdSql.execute(f"insert into nested.stable_null_data (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_data_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_tinyint) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_float) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_double) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bool) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_binary) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_nchar) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_ts) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 32);
|
tdSql.checkData(0, 1, 32)
|
||||||
|
|
||||||
|
for i in range(10):
|
||||||
|
coulmn_name = q_null_list[i]
|
||||||
|
tdSql.execute(f"insert into nested.stable_null_data (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_data_1',1);")
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_int_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bigint_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_smallint_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_tinyint_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_float_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_double_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_bool_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_binary_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_nchar_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_ts_null) values(now,'stable_null_data_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_data group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 42);
|
tdSql.checkData(0, 1, 42)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_int) values(now,'stable_null_data_1',1) \
|
tdSql.query(f"insert into nested.stable_null_data (ts,tbname,q_int) values(now,'stable_null_data_1',1) \
|
||||||
nested.stable_null_data (ts,tbname,q_bigint) values(now+1a,'stable_null_data_1',1)\
|
nested.stable_null_data (ts,tbname,q_bigint) values(now+1a,'stable_null_data_1',1)\
|
||||||
|
@ -1330,32 +1266,18 @@ class TDTestCase:
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname) values(now,'stable_null_childtable_1');")
|
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname) values(now,'stable_null_childtable_1');")
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 22);
|
tdSql.checkData(0, 1, 22)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_int) values(now,'stable_null_childtable_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bigint) values(now,'stable_null_childtable_1',1);")
|
coulmn_name = qlist[i]
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_smallint) values(now,'stable_null_childtable_1',1);")
|
tdSql.execute(f"insert into nested.stable_null_childtable (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_childtable_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_tinyint) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_float) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_double) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bool) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_binary) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_nchar) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_ts) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 32);
|
tdSql.checkData(0, 1, 32)
|
||||||
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_int_null) values(now,'stable_null_childtable_1',1);")
|
for i in range(10):
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bigint_null) values(now,'stable_null_childtable_1',1);")
|
coulmn_name = q_null_list[i]
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_smallint_null) values(now,'stable_null_childtable_1',1);")
|
tdSql.execute(f"insert into nested.stable_null_childtable (ts, tbname, {coulmn_name}) values(now+{i}s,'stable_null_childtable_1',1);")
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_tinyint_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_float_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_double_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_bool_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_binary_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_nchar_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"insert into nested.stable_null_childtable (ts,tbname,q_ts_null) values(now,'stable_null_childtable_1',1);")
|
|
||||||
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
tdSql.query(f"select tbname,count(*) from nested.stable_null_childtable group by tbname order by tbname;")
|
||||||
tdSql.checkRows(1)
|
tdSql.checkRows(1)
|
||||||
tdSql.checkData(0, 1, 42);
|
tdSql.checkData(0, 1, 42);
|
||||||
|
|
|
@ -19,8 +19,8 @@
|
||||||
//
|
//
|
||||||
// The prefix search tree is a efficient storage words and search words tree, it support 95 visible ascii code character
|
// The prefix search tree is a efficient storage words and search words tree, it support 95 visible ascii code character
|
||||||
//
|
//
|
||||||
#define FIRST_ASCII 40 // first visible char is '0'
|
#define FIRST_ASCII 32 // first visible char is '0'
|
||||||
#define LAST_ASCII 122 // last visilbe char is 'z'
|
#define LAST_ASCII 126 // last visilbe char is 'z'
|
||||||
|
|
||||||
// capacity save char is 95
|
// capacity save char is 95
|
||||||
#define CHAR_CNT (LAST_ASCII - FIRST_ASCII + 1)
|
#define CHAR_CNT (LAST_ASCII - FIRST_ASCII + 1)
|
||||||
|
|
|
@ -95,7 +95,7 @@ bool insertToTree(STire* tire, char* word, int len) {
|
||||||
STireNode** nodes = tire->root.d;
|
STireNode** nodes = tire->root.d;
|
||||||
for (int i = 0; i < len; i++) {
|
for (int i = 0; i < len; i++) {
|
||||||
m = word[i] - FIRST_ASCII;
|
m = word[i] - FIRST_ASCII;
|
||||||
if (m < 0 || m > CHAR_CNT) {
|
if (m < 0 || m >= CHAR_CNT) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue