From 696bad4b1b95a4eb1a287d332fc565f995b7d911 Mon Sep 17 00:00:00 2001 From: huolibo Date: Thu, 11 Aug 2022 17:48:01 +0800 Subject: [PATCH 01/47] fix(driver): get raw block length --- source/client/src/TMQConnector.c | 2 +- source/client/src/TSDBJNIConnector.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/source/client/src/TMQConnector.c b/source/client/src/TMQConnector.c index 3755a591e3..b000dd6a32 100644 --- a/source/client/src/TMQConnector.c +++ b/source/client/src/TMQConnector.c @@ -322,7 +322,7 @@ JNIEXPORT jint JNICALL Java_com_taosdata_jdbc_tmq_TMQConnector_fetchRawBlockImp( (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfRowsFp, (jint)numOfRows); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfColsFp, (jint)numOfFields); - int32_t len = *(int32_t *)data; + int32_t len = *(int32_t *)(data + 4); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetByteArrayFp, jniFromNCharToByteArray(env, (char *)data, len)); return JNI_SUCCESS; } diff --git a/source/client/src/TSDBJNIConnector.c b/source/client/src/TSDBJNIConnector.c index 37041da695..e027066d10 100644 --- a/source/client/src/TSDBJNIConnector.c +++ b/source/client/src/TSDBJNIConnector.c @@ -592,7 +592,7 @@ JNIEXPORT jint JNICALL Java_com_taosdata_jdbc_TSDBJNIConnector_fetchBlockImp(JNI (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfRowsFp, (jint)numOfRows); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfColsFp, (jint)numOfFields); - int32_t len = *(int32_t *)data; + int32_t len = *(int32_t *)(data + 4); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetByteArrayFp, jniFromNCharToByteArray(env, (char *)data, len)); return JNI_SUCCESS; From 283ce988b5fbd7ef9446fbf347bf5206f9b23b77 Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Thu, 11 Aug 2022 20:04:20 +0800 Subject: [PATCH 02/47] fix: fix taosc crash issue --- source/libs/catalog/src/ctgUtil.c | 4 ++-- source/os/src/osMemory.c | 1 + 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/source/libs/catalog/src/ctgUtil.c b/source/libs/catalog/src/ctgUtil.c index 7b81343358..e28234ab76 100644 --- a/source/libs/catalog/src/ctgUtil.c +++ b/source/libs/catalog/src/ctgUtil.c @@ -916,7 +916,7 @@ int32_t ctgGetVgInfosFromHashValue(SCatalog *pCtg, SCtgTaskReq* tReq, SDBVgInfo int32_t vgNum = taosHashGetSize(dbInfo->vgHash); if (vgNum <= 0) { ctgError("db vgroup cache invalid, db:%s, vgroup number:%d", dbFName, vgNum); - CTG_ERR_RET(TSDB_CODE_TSC_DB_NOT_SELECTED); + CTG_ERR_RET(TSDB_CODE_CTG_INTERNAL_ERROR); } tableNameHashFp fp = NULL; @@ -931,6 +931,7 @@ int32_t ctgGetVgInfosFromHashValue(SCatalog *pCtg, SCtgTaskReq* tReq, SDBVgInfo for (int32_t i = 0; i < tbNum; ++i) { vgInfo = taosMemoryMalloc(sizeof(SVgroupInfo)); if (NULL == vgInfo) { + taosHashCancelIterate(dbInfo->vgHash, pIter); CTG_ERR_RET(TSDB_CODE_OUT_OF_MEMORY); } @@ -980,7 +981,6 @@ int32_t ctgGetVgInfosFromHashValue(SCatalog *pCtg, SCtgTaskReq* tReq, SDBVgInfo if (NULL == p) { ctgError("no hash range found for hash value [%u], db:%s, numOfVgId:%d", hashValue, dbFName, taosHashGetSize(dbInfo->vgHash)); - ASSERT(0); taosArrayDestroy(pVgList); CTG_ERR_RET(TSDB_CODE_CTG_INTERNAL_ERROR); } diff --git a/source/os/src/osMemory.c b/source/os/src/osMemory.c index 07575336a1..5d17536874 100644 --- a/source/os/src/osMemory.c +++ b/source/os/src/osMemory.c @@ -302,6 +302,7 @@ void *taosMemoryStrDup(const char *ptr) { } void taosMemoryFree(void *ptr) { + if (NULL == ptr) return; #ifdef USE_TD_MEMORY TdMemoryInfoPtr pTdMemoryInfo = (TdMemoryInfoPtr)((char *)ptr - sizeof(TdMemoryInfo)); if (pTdMemoryInfo->symbol == TD_MEMORY_SYMBOL) { From 98c267b4bfac1f8ce7e63c82549aa900f14e8c89 Mon Sep 17 00:00:00 2001 From: huolibo Date: Fri, 12 Aug 2022 09:59:30 +0800 Subject: [PATCH 03/47] fix(driver): adapter windows --- source/client/src/TMQConnector.c | 2 +- source/client/src/TSDBJNIConnector.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/source/client/src/TMQConnector.c b/source/client/src/TMQConnector.c index b000dd6a32..17d3a212c4 100644 --- a/source/client/src/TMQConnector.c +++ b/source/client/src/TMQConnector.c @@ -322,7 +322,7 @@ JNIEXPORT jint JNICALL Java_com_taosdata_jdbc_tmq_TMQConnector_fetchRawBlockImp( (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfRowsFp, (jint)numOfRows); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfColsFp, (jint)numOfFields); - int32_t len = *(int32_t *)(data + 4); + int32_t len = *(int32_t *)(((char *)data) + 4); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetByteArrayFp, jniFromNCharToByteArray(env, (char *)data, len)); return JNI_SUCCESS; } diff --git a/source/client/src/TSDBJNIConnector.c b/source/client/src/TSDBJNIConnector.c index e027066d10..b5a6ebadee 100644 --- a/source/client/src/TSDBJNIConnector.c +++ b/source/client/src/TSDBJNIConnector.c @@ -592,7 +592,7 @@ JNIEXPORT jint JNICALL Java_com_taosdata_jdbc_TSDBJNIConnector_fetchBlockImp(JNI (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfRowsFp, (jint)numOfRows); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetNumOfColsFp, (jint)numOfFields); - int32_t len = *(int32_t *)(data + 4); + int32_t len = *(int32_t *)(((char *)data) + 4); (*env)->CallVoidMethod(env, rowobj, g_blockdataSetByteArrayFp, jniFromNCharToByteArray(env, (char *)data, len)); return JNI_SUCCESS; From 3c27c8b8fd3fa1e7d3e792afbde52471ed6f6f6b Mon Sep 17 00:00:00 2001 From: slzhou Date: Fri, 12 Aug 2022 10:20:09 +0800 Subject: [PATCH 04/47] fix: sample/top/bottom is not allowed with fill clause --- source/libs/function/src/builtins.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/source/libs/function/src/builtins.c b/source/libs/function/src/builtins.c index 42df5cacfe..d937ddce7e 100644 --- a/source/libs/function/src/builtins.c +++ b/source/libs/function/src/builtins.c @@ -2176,7 +2176,7 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = { { .name = "top", .type = FUNCTION_TYPE_TOP, - .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC | FUNC_MGT_MULTI_ROWS_FUNC | FUNC_MGT_KEEP_ORDER_FUNC | FUNC_MGT_FORBID_STREAM_FUNC, + .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC | FUNC_MGT_MULTI_ROWS_FUNC | FUNC_MGT_KEEP_ORDER_FUNC | FUNC_MGT_FORBID_STREAM_FUNC | FUNC_MGT_FORBID_FILL_FUNC, .translateFunc = translateTopBot, .getEnvFunc = getTopBotFuncEnv, .initFunc = topBotFunctionSetup, @@ -2191,7 +2191,7 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = { { .name = "bottom", .type = FUNCTION_TYPE_BOTTOM, - .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC | FUNC_MGT_MULTI_ROWS_FUNC | FUNC_MGT_KEEP_ORDER_FUNC | FUNC_MGT_FORBID_STREAM_FUNC, + .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC | FUNC_MGT_MULTI_ROWS_FUNC | FUNC_MGT_KEEP_ORDER_FUNC | FUNC_MGT_FORBID_STREAM_FUNC | FUNC_MGT_FORBID_FILL_FUNC, .translateFunc = translateTopBot, .getEnvFunc = getTopBotFuncEnv, .initFunc = topBotFunctionSetup, @@ -2589,7 +2589,7 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = { { .name = "sample", .type = FUNCTION_TYPE_SAMPLE, - .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC | FUNC_MGT_MULTI_ROWS_FUNC | FUNC_MGT_KEEP_ORDER_FUNC | FUNC_MGT_FORBID_STREAM_FUNC, + .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC | FUNC_MGT_MULTI_ROWS_FUNC | FUNC_MGT_KEEP_ORDER_FUNC | FUNC_MGT_FORBID_STREAM_FUNC | FUNC_MGT_FORBID_FILL_FUNC, .translateFunc = translateSample, .getEnvFunc = getSampleFuncEnv, .initFunc = sampleFunctionSetup, From c50a9e840dc8760da96266b61427862ab4399d38 Mon Sep 17 00:00:00 2001 From: jiacy-jcy Date: Fri, 12 Aug 2022 10:37:39 +0800 Subject: [PATCH 05/47] add windows install and uninstall --- docs/zh/05-get-started/03-package.md | 20 +++++++++++--------- docs/zh/17-operation/01-pkg-install.md | 2 +- 2 files changed, 12 insertions(+), 10 deletions(-) diff --git a/docs/zh/05-get-started/03-package.md b/docs/zh/05-get-started/03-package.md index c03a25ef58..1ff24559f7 100644 --- a/docs/zh/05-get-started/03-package.md +++ b/docs/zh/05-get-started/03-package.md @@ -46,8 +46,8 @@ apt-get 方式只适用于 Debian 或 Ubuntu 系统 -1、从官网下载获得 deb 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.deb; -2、进入到 TDengine-server-3.0.0.0-Linux-x64.deb 安装包所在目录,执行如下的安装命令: +1. 从官网下载获得 deb 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.deb; +2. 进入到 TDengine-server-3.0.0.0-Linux-x64.deb 安装包所在目录,执行如下的安装命令: ```bash sudo dpkg -i TDengine-server-3.0.0.0-Linux-x64.deb @@ -57,8 +57,8 @@ sudo dpkg -i TDengine-server-3.0.0.0-Linux-x64.deb -1、从官网下载获得 rpm 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.rpm; -2、进入到 TDengine-server-3.0.0.0-Linux-x64.rpm 安装包所在目录,执行如下的安装命令: +1. 从官网下载获得 rpm 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.rpm; +2. 进入到 TDengine-server-3.0.0.0-Linux-x64.rpm 安装包所在目录,执行如下的安装命令: ```bash sudo rpm -ivh TDengine-server-3.0.0.0-Linux-x64.rpm @@ -68,8 +68,8 @@ sudo rpm -ivh TDengine-server-3.0.0.0-Linux-x64.rpm -1、从官网下载获得 tar.gz 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.tar.gz; -2、进入到 TDengine-server-3.0.0.0-Linux-x64.tar.gz 安装包所在目录,先解压文件后,进入子目录,执行其中的 install.sh 安装脚本: +1. 从官网下载获得 tar.gz 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.tar.gz; +2. 进入到 TDengine-server-3.0.0.0-Linux-x64.tar.gz 安装包所在目录,先解压文件后,进入子目录,执行其中的 install.sh 安装脚本: ```bash tar -zxvf TDengine-server-3.0.0.0-Linux-x64.tar.gz @@ -89,7 +89,9 @@ install.sh 安装脚本在执行过程中,会通过命令行交互界面询问 -TODO + +1. 从官网下载获得 exe 安装程序,例如 TDengine-server-3.0.0.0-Windows-x64.exe; +2. 运行 TDengine-server-3.0.0.0-Windows-x64.exe 来安装 TDengine。 @@ -152,14 +154,14 @@ systemctl 命令汇总: -TODO +安装后,在 C:\TDengine 目录下,运行 taosd.exe 来启动 TDengine 服务进程。 ## TDengine 命令行 (CLI) -为便于检查 TDengine 的状态,执行数据库 (Database) 的各种即席(Ad Hoc)查询,TDengine 提供一命令行应用程序(以下简称为 TDengine CLI) taos。要进入 TDengine 命令行,您只要在安装有 TDengine 的 Linux 终端执行 `taos` 即可。 +为便于检查 TDengine 的状态,执行数据库 (Database) 的各种即席(Ad Hoc)查询,TDengine 提供一命令行应用程序(以下简称为 TDengine CLI) taos。要进入 TDengine 命令行,您只要在安装有 TDengine 的 Linux 终端执行 `taos` 即可,也可以在安装有 TDengine 的 Windows 终端的 C:\TDengine 目录下,运行 taos.exe 来启动 TDengine 命令行。 ```bash taos diff --git a/docs/zh/17-operation/01-pkg-install.md b/docs/zh/17-operation/01-pkg-install.md index 533a01542a..5e4cc93130 100644 --- a/docs/zh/17-operation/01-pkg-install.md +++ b/docs/zh/17-operation/01-pkg-install.md @@ -86,7 +86,7 @@ TDengine is removed successfully! -TODO +在 C:\TDengine 目录下,通过运行 unins000.exe 卸载程序来卸载 TDengine。 From 9cd7c54e252606290bdb1b1ee77003c162ffbd9b Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 10:41:02 +0800 Subject: [PATCH 06/47] fix: fix task sched crash issue --- include/util/tsched.h | 21 ++++++++++++++- source/libs/index/src/index.c | 2 +- source/libs/qcom/src/queryUtil.c | 10 +++---- source/util/src/tsched.c | 46 ++++++++++++++------------------ source/util/src/ttimer.c | 2 +- 5 files changed, 47 insertions(+), 34 deletions(-) diff --git a/include/util/tsched.h b/include/util/tsched.h index 3bf740f528..347cacd191 100644 --- a/include/util/tsched.h +++ b/include/util/tsched.h @@ -17,6 +17,7 @@ #define _TD_UTIL_SCHED_H_ #include "os.h" +#include "tdef.h" #ifdef __cplusplus extern "C" { @@ -30,6 +31,24 @@ typedef struct SSchedMsg { void *thandle; } SSchedMsg; + +typedef struct { + char label[TSDB_LABEL_LEN]; + tsem_t emptySem; + tsem_t fullSem; + TdThreadMutex queueMutex; + int32_t fullSlot; + int32_t emptySlot; + int32_t queueSize; + int32_t numOfThreads; + TdThread *qthread; + SSchedMsg *queue; + int8_t stop; + void *pTmrCtrl; + void *pTimer; +} SSchedQueue; + + /** * Create a thread-safe ring-buffer based task queue and return the instance. A thread * pool will be created to consume the messages in the queue. @@ -38,7 +57,7 @@ typedef struct SSchedMsg { * @param label the label of the queue * @return the created queue scheduler */ -void *taosInitScheduler(int32_t capacity, int32_t numOfThreads, const char *label); +void *taosInitScheduler(int32_t capacity, int32_t numOfThreads, const char *label, SSchedQueue* pSched); /** * Create a thread-safe ring-buffer based task queue and return the instance. diff --git a/source/libs/index/src/index.c b/source/libs/index/src/index.c index 850ddd4970..eac585c2e6 100644 --- a/source/libs/index/src/index.c +++ b/source/libs/index/src/index.c @@ -62,7 +62,7 @@ static void indexDestroy(void* sIdx); void indexInit() { // refactor later - indexQhandle = taosInitScheduler(INDEX_QUEUE_SIZE, INDEX_NUM_OF_THREADS, "index"); + indexQhandle = taosInitScheduler(INDEX_QUEUE_SIZE, INDEX_NUM_OF_THREADS, "index", NULL); indexRefMgt = taosOpenRef(1000, indexDestroy); } void indexCleanup() { diff --git a/source/libs/qcom/src/queryUtil.c b/source/libs/qcom/src/queryUtil.c index 41333e7756..5143aa4af1 100644 --- a/source/libs/qcom/src/queryUtil.c +++ b/source/libs/qcom/src/queryUtil.c @@ -96,12 +96,12 @@ bool tIsValidSchema(struct SSchema* pSchema, int32_t numOfCols, int32_t numOfTag return true; } -static void* pTaskQueue = NULL; +static SSchedQueue pTaskQueue = {0}; int32_t initTaskQueue() { int32_t queueSize = tsMaxShellConns * 2; - pTaskQueue = taosInitScheduler(queueSize, tsNumOfTaskQueueThreads, "tsc"); - if (NULL == pTaskQueue) { + void *p = taosInitScheduler(queueSize, tsNumOfTaskQueueThreads, "tsc", &pTaskQueue); + if (NULL == p) { qError("failed to init task queue"); return -1; } @@ -111,7 +111,7 @@ int32_t initTaskQueue() { } int32_t cleanupTaskQueue() { - taosCleanUpScheduler(pTaskQueue); + taosCleanUpScheduler(&pTaskQueue); return 0; } @@ -134,7 +134,7 @@ int32_t taosAsyncExec(__async_exec_fn_t execFn, void* execParam, int32_t* code) schedMsg.thandle = execParam; schedMsg.msg = code; - taosScheduleTask(pTaskQueue, &schedMsg); + taosScheduleTask(&pTaskQueue, &schedMsg); return 0; } diff --git a/source/util/src/tsched.c b/source/util/src/tsched.c index 9abce966f5..89471c4347 100644 --- a/source/util/src/tsched.c +++ b/source/util/src/tsched.c @@ -22,30 +22,16 @@ #define DUMP_SCHEDULER_TIME_WINDOW 30000 // every 30sec, take a snap shot of task queue. -typedef struct { - char label[TSDB_LABEL_LEN]; - tsem_t emptySem; - tsem_t fullSem; - TdThreadMutex queueMutex; - int32_t fullSlot; - int32_t emptySlot; - int32_t queueSize; - int32_t numOfThreads; - TdThread *qthread; - SSchedMsg *queue; - bool stop; - void *pTmrCtrl; - void *pTimer; -} SSchedQueue; - static void *taosProcessSchedQueue(void *param); static void taosDumpSchedulerStatus(void *qhandle, void *tmrId); -void *taosInitScheduler(int32_t queueSize, int32_t numOfThreads, const char *label) { - SSchedQueue *pSched = (SSchedQueue *)taosMemoryCalloc(sizeof(SSchedQueue), 1); - if (pSched == NULL) { - uError("%s: no enough memory for pSched", label); - return NULL; +void *taosInitScheduler(int32_t queueSize, int32_t numOfThreads, const char *label, SSchedQueue *pSched) { + if (NULL == pSched) { + pSched = (SSchedQueue *)taosMemoryCalloc(sizeof(SSchedQueue), 1); + if (pSched == NULL) { + uError("%s: no enough memory for pSched", label); + return NULL; + } } pSched->queue = (SSchedMsg *)taosMemoryCalloc(sizeof(SSchedMsg), queueSize); @@ -86,7 +72,7 @@ void *taosInitScheduler(int32_t queueSize, int32_t numOfThreads, const char *lab return NULL; } - pSched->stop = false; + atomic_store_8(&pSched->stop, 0); for (int32_t i = 0; i < numOfThreads; ++i) { TdThreadAttr attr; taosThreadAttrInit(&attr); @@ -107,7 +93,7 @@ void *taosInitScheduler(int32_t queueSize, int32_t numOfThreads, const char *lab } void *taosInitSchedulerWithInfo(int32_t queueSize, int32_t numOfThreads, const char *label, void *tmrCtrl) { - SSchedQueue *pSched = taosInitScheduler(queueSize, numOfThreads, label); + SSchedQueue *pSched = taosInitScheduler(queueSize, numOfThreads, label, NULL); if (tmrCtrl != NULL && pSched != NULL) { pSched->pTmrCtrl = tmrCtrl; @@ -131,7 +117,7 @@ void *taosProcessSchedQueue(void *scheduler) { uFatal("wait %s fullSem failed(%s)", pSched->label, strerror(errno)); ASSERT(0); } - if (pSched->stop) { + if (atomic_load_8(&pSched->stop)) { break; } @@ -172,6 +158,11 @@ void taosScheduleTask(void *queueScheduler, SSchedMsg *pMsg) { return; } + if (atomic_load_8(&pSched->stop)) { + uError("sched is already stopped, msg:%p is dropped", pMsg); + return; + } + if ((ret = tsem_wait(&pSched->emptySem)) != 0) { uFatal("wait %s emptySem failed(%s)", pSched->label, strerror(errno)); ASSERT(0); @@ -202,7 +193,10 @@ void taosCleanUpScheduler(void *param) { uDebug("start to cleanup %s schedQsueue", pSched->label); - pSched->stop = true; + atomic_store_8(&pSched->stop, 1); + + taosMsleep(200); + for (int32_t i = 0; i < pSched->numOfThreads; ++i) { if (taosCheckPthreadValid(pSched->qthread[i])) { tsem_post(&pSched->fullSem); @@ -226,7 +220,7 @@ void taosCleanUpScheduler(void *param) { if (pSched->queue) taosMemoryFree(pSched->queue); if (pSched->qthread) taosMemoryFree(pSched->qthread); - taosMemoryFree(pSched); // fix memory leak + //taosMemoryFree(pSched); } // for debug purpose, dump the scheduler status every 1min. diff --git a/source/util/src/ttimer.c b/source/util/src/ttimer.c index 7256331c85..ff5ac1b217 100644 --- a/source/util/src/ttimer.c +++ b/source/util/src/ttimer.c @@ -555,7 +555,7 @@ static void taosTmrModuleInit(void) { return; } - tmrQhandle = taosInitScheduler(10000, taosTmrThreads, "tmr"); + tmrQhandle = taosInitScheduler(10000, taosTmrThreads, "tmr", NULL); taosInitTimer(taosTimerLoopFunc, MSECONDS_PER_TICK); tmrDebug("timer module is initialized, number of threads: %d", taosTmrThreads); From effb4f20d3ce5c8b4f0c9bbbd6b062533a25e3dc Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 11:00:21 +0800 Subject: [PATCH 07/47] fix: fix taosd put blocks to sink error --- source/libs/executor/src/dataDispatcher.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/source/libs/executor/src/dataDispatcher.c b/source/libs/executor/src/dataDispatcher.c index 977adcaa5e..20396046ba 100644 --- a/source/libs/executor/src/dataDispatcher.c +++ b/source/libs/executor/src/dataDispatcher.c @@ -101,12 +101,14 @@ static void toDataCacheEntry(SDataDispatchHandle* pHandle, const SInputData* pIn } static bool allocBuf(SDataDispatchHandle* pDispatcher, const SInputData* pInput, SDataDispatchBuf* pBuf) { +/* uint32_t capacity = pDispatcher->pManager->cfg.maxDataBlockNumPerQuery; if (taosQueueItemSize(pDispatcher->pDataBlocks) > capacity) { qError("SinkNode queue is full, no capacity, max:%d, current:%d, no capacity", capacity, taosQueueItemSize(pDispatcher->pDataBlocks)); return false; } +*/ pBuf->allocSize = sizeof(SDataCacheEntry) + blockGetEncodeSize(pInput->pData); From e2d950e3873925643276bd514816ac65aac7ed9f Mon Sep 17 00:00:00 2001 From: slzhou Date: Fri, 12 Aug 2022 11:08:56 +0800 Subject: [PATCH 08/47] fix: modify sample test case that sample is not supported with fill --- tests/system-test/2-query/sample.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/system-test/2-query/sample.py b/tests/system-test/2-query/sample.py index f09265c300..6ea938156a 100644 --- a/tests/system-test/2-query/sample.py +++ b/tests/system-test/2-query/sample.py @@ -515,7 +515,7 @@ class TDTestCase: # "condition": "where ts>0 and ts < now interval(1h) fill(next)" # } # self.checksample(**err45) # interval - tdSql.query("select sample( c1 , 1 ) from t1 where ts>0 and ts < now interval(1h) fill(next)") + tdSql.error("select sample( c1 , 1 ) from t1 where ts>0 and ts < now interval(1h) fill(next)") err46 = { "table_expr": "t1", "condition": "group by c6" From bd929582f5c9e989398148b76182e0a6cb6cf7c5 Mon Sep 17 00:00:00 2001 From: yihaoDeng Date: Fri, 12 Aug 2022 11:22:41 +0800 Subject: [PATCH 09/47] fix operator double free --- source/libs/executor/src/executorimpl.c | 37 ++++--- source/libs/executor/src/timewindowoperator.c | 103 ++++++++---------- 2 files changed, 67 insertions(+), 73 deletions(-) diff --git a/source/libs/executor/src/executorimpl.c b/source/libs/executor/src/executorimpl.c index 9e485e7684..59b3328f62 100644 --- a/source/libs/executor/src/executorimpl.c +++ b/source/libs/executor/src/executorimpl.c @@ -1433,7 +1433,8 @@ static void setExecutionContext(SOperatorInfo* pOperator, int32_t numOfOutput, u pAggInfo->groupId = groupId; } -static void doUpdateNumOfRows(SqlFunctionCtx* pCtx, SResultRow* pRow, int32_t numOfExprs, const int32_t* rowCellOffset) { +static void doUpdateNumOfRows(SqlFunctionCtx* pCtx, SResultRow* pRow, int32_t numOfExprs, + const int32_t* rowCellOffset) { bool returnNotNull = false; for (int32_t j = 0; j < numOfExprs; ++j) { struct SResultRowEntryInfo* pResInfo = getResultEntryInfo(pRow, j, rowCellOffset); @@ -1613,7 +1614,7 @@ void doBuildResultDatablock(SOperatorInfo* pOperator, SOptrBasicInfo* pbInfo, SG if (!pbInfo->mergeResultBlock) { doCopyToSDataBlock(pTaskInfo, pBlock, &pOperator->exprSupp, pBuf, pGroupResInfo); } else { - while(hasRemainResults(pGroupResInfo)) { + while (hasRemainResults(pGroupResInfo)) { doCopyToSDataBlock(pTaskInfo, pBlock, &pOperator->exprSupp, pBuf, pGroupResInfo); if (pBlock->info.rows >= pOperator->resultInfo.threshold) { break; @@ -2062,10 +2063,10 @@ void updateLoadRemoteInfo(SLoadRemoteDataInfo* pInfo, int32_t numOfRows, int32_t } int32_t extractDataBlockFromFetchRsp(SSDataBlock* pRes, char* pData, int32_t numOfOutput, SArray* pColList, - char** pNextStart) { + char** pNextStart) { if (pColList == NULL) { // data from other sources blockDataCleanup(pRes); - *pNextStart = (char*) blockDecode(pRes, pData); + *pNextStart = (char*)blockDecode(pRes, pData); } else { // extract data according to pColList ASSERT(numOfOutput == taosArrayGetSize(pColList)); char* pStart = pData; @@ -2161,9 +2162,9 @@ static void concurrentlyLoadRemoteDataImpl(SOperatorInfo* pOperator, SExchangeIn } SRetrieveTableRsp* pRetrieveRsp = pDataInfo->pRsp; - int32_t index = 0; - char* pStart = pRetrieveRsp->data; - while(index++ < pRetrieveRsp->numOfBlocks) { + int32_t index = 0; + char* pStart = pRetrieveRsp->data; + while (index++ < pRetrieveRsp->numOfBlocks) { SSDataBlock* pb = createOneDataBlock(pExchangeInfo->pDummyBlock, false); code = extractDataBlockFromFetchRsp(pb, pStart, pRetrieveRsp->numOfCols, NULL, &pStart); if (code != 0) { @@ -2177,8 +2178,10 @@ static void concurrentlyLoadRemoteDataImpl(SOperatorInfo* pOperator, SExchangeIn updateLoadRemoteInfo(pLoadInfo, pRetrieveRsp->numOfRows, pRetrieveRsp->compLen, startTs, pOperator); if (pRsp->completed == 1) { - qDebug("%s fetch msg rsp from vgId:%d, taskId:0x%" PRIx64 " execId:%d" - " index:%d completed, blocks:%d, numOfRows:%d, rowsOfSource:%" PRIu64 ", totalRows:%" PRIu64 ", total:%.2f Kb," + qDebug("%s fetch msg rsp from vgId:%d, taskId:0x%" PRIx64 + " execId:%d" + " index:%d completed, blocks:%d, numOfRows:%d, rowsOfSource:%" PRIu64 ", totalRows:%" PRIu64 + ", total:%.2f Kb," " completed:%d try next %d/%" PRIzu, GET_TASKID(pTaskInfo), pSource->addr.nodeId, pSource->taskId, pSource->execId, i, pRsp->numOfBlocks, pRsp->numOfRows, pDataInfo->totalRows, pLoadInfo->totalRows, pLoadInfo->totalSize / 1024.0, @@ -2186,9 +2189,10 @@ static void concurrentlyLoadRemoteDataImpl(SOperatorInfo* pOperator, SExchangeIn completed += 1; pDataInfo->status = EX_SOURCE_DATA_EXHAUSTED; } else { - qDebug("%s fetch msg rsp from vgId:%d, taskId:0x%" PRIx64 " execId:%d blocks:%d, numOfRows:%d, totalRows:%" PRIu64 - ", total:%.2f Kb", GET_TASKID(pTaskInfo), pSource->addr.nodeId, pSource->taskId, pSource->execId, - pRsp->numOfBlocks, pRsp->numOfRows, pLoadInfo->totalRows, pLoadInfo->totalSize/1024.0); + qDebug("%s fetch msg rsp from vgId:%d, taskId:0x%" PRIx64 + " execId:%d blocks:%d, numOfRows:%d, totalRows:%" PRIu64 ", total:%.2f Kb", + GET_TASKID(pTaskInfo), pSource->addr.nodeId, pSource->taskId, pSource->execId, pRsp->numOfBlocks, + pRsp->numOfRows, pLoadInfo->totalRows, pLoadInfo->totalSize / 1024.0); } taosMemoryFreeClear(pDataInfo->pRsp); @@ -3521,7 +3525,7 @@ SOperatorInfo* createAggregateOperatorInfo(SOperatorInfo* downstream, SExprInfo* goto _error; } - size_t keyBufSize = sizeof(int64_t) + sizeof(int64_t) + POINTER_BYTES; + size_t keyBufSize = sizeof(int64_t) + sizeof(int64_t) + POINTER_BYTES; initResultSizeInfo(&pOperator->resultInfo, 4096); int32_t code = initAggInfo(&pOperator->exprSupp, &pInfo->aggSup, pExprInfo, numOfCols, keyBufSize, pTaskInfo->id.str); @@ -3562,7 +3566,6 @@ SOperatorInfo* createAggregateOperatorInfo(SOperatorInfo* downstream, SExprInfo* return pOperator; _error: destroyAggOperatorInfo(pInfo, numOfCols); - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = TSDB_CODE_OUT_OF_MEMORY; return NULL; @@ -4175,7 +4178,8 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo int32_t tsSlotId = ((SColumnNode*)pIntervalPhyNode->window.pTspk)->slotId; pOptr = createMergeAlignedIntervalOperatorInfo(ops[0], pExprInfo, num, pResBlock, &interval, tsSlotId, - pPhyNode->pConditions, pIntervalPhyNode->window.mergeDataBlock, pTaskInfo); + pPhyNode->pConditions, pIntervalPhyNode->window.mergeDataBlock, + pTaskInfo); } else if (QUERY_NODE_PHYSICAL_PLAN_MERGE_INTERVAL == type) { SMergeIntervalPhysiNode* pIntervalPhyNode = (SMergeIntervalPhysiNode*)pPhyNode; @@ -4190,7 +4194,8 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo .precision = ((SColumnNode*)pIntervalPhyNode->window.pTspk)->node.resType.precision}; int32_t tsSlotId = ((SColumnNode*)pIntervalPhyNode->window.pTspk)->slotId; - pOptr = createMergeIntervalOperatorInfo(ops[0], pExprInfo, num, pResBlock, &interval, tsSlotId, pIntervalPhyNode->window.mergeDataBlock, pTaskInfo); + pOptr = createMergeIntervalOperatorInfo(ops[0], pExprInfo, num, pResBlock, &interval, tsSlotId, + pIntervalPhyNode->window.mergeDataBlock, pTaskInfo); } else if (QUERY_NODE_PHYSICAL_PLAN_STREAM_SEMI_INTERVAL == type) { int32_t children = 0; pOptr = createStreamFinalIntervalOperatorInfo(ops[0], pPhyNode, pTaskInfo, children); diff --git a/source/libs/executor/src/timewindowoperator.c b/source/libs/executor/src/timewindowoperator.c index b4489a92fb..5485e166f4 100644 --- a/source/libs/executor/src/timewindowoperator.c +++ b/source/libs/executor/src/timewindowoperator.c @@ -97,7 +97,8 @@ static void doKeepTuple(SWindowRowsSup* pRowSup, int64_t ts, uint64_t groupId) { pRowSup->groupId = groupId; } -static void doKeepNewWindowStartInfo(SWindowRowsSup* pRowSup, const int64_t* tsList, int32_t rowIndex, uint64_t groupId) { +static void doKeepNewWindowStartInfo(SWindowRowsSup* pRowSup, const int64_t* tsList, int32_t rowIndex, + uint64_t groupId) { pRowSup->startRowIndex = rowIndex; pRowSup->numOfRows = 0; pRowSup->win.skey = tsList[rowIndex]; @@ -869,7 +870,8 @@ static int32_t saveWinResult(int64_t ts, int32_t pageId, int32_t offset, uint64_ } static int32_t saveWinResultRow(SResultRow* result, uint64_t groupId, SHashObj* pUpdatedMap) { - return saveWinResult(result->win.skey, result->pageId, result->offset, groupId, pUpdatedMap);; + return saveWinResult(result->win.skey, result->pageId, result->offset, groupId, pUpdatedMap); + ; } static int32_t saveResultRow(SResultRow* result, uint64_t groupId, SArray* pUpdated) { @@ -910,9 +912,9 @@ int32_t compareWinRes(void* pKey, void* data, int32_t index) { static void removeDeleteResults(SHashObj* pUpdatedMap, SArray* pDelWins) { if (!pUpdatedMap || taosHashGetSize(pUpdatedMap) == 0) { return; - } + } int32_t delSize = taosArrayGetSize(pDelWins); - void* pIte = NULL; + void* pIte = NULL; while ((pIte = taosHashIterate(pUpdatedMap, pIte)) != NULL) { SResKeyPos* pResKey = (SResKeyPos*)pIte; int32_t index = binarySearchCom(pDelWins, delSize, pResKey, TSDB_ORDER_DESC, compareWinRes); @@ -1592,9 +1594,9 @@ static SSDataBlock* doStreamIntervalAgg(SOperatorInfo* pOperator) { SOperatorInfo* downstream = pOperator->pDownstream[0]; - SArray* pUpdated = taosArrayInit(4, POINTER_BYTES); // SResKeyPos + SArray* pUpdated = taosArrayInit(4, POINTER_BYTES); // SResKeyPos _hash_fn_t hashFn = taosGetDefaultHashFunction(TSDB_DATA_TYPE_TIMESTAMP); - SHashObj* pUpdatedMap = taosHashInit(1024, hashFn, false, HASH_NO_LOCK); + SHashObj* pUpdatedMap = taosHashInit(1024, hashFn, false, HASH_NO_LOCK); while (1) { SSDataBlock* pBlock = downstream->fpSet.getNextFn(downstream); if (pBlock == NULL) { @@ -1874,7 +1876,6 @@ SOperatorInfo* createIntervalOperatorInfo(SOperatorInfo* downstream, SExprInfo* _error: destroyIntervalOperatorInfo(pInfo, numOfCols); - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -1931,7 +1932,6 @@ SOperatorInfo* createStreamIntervalOperatorInfo(SOperatorInfo* downstream, SExpr _error: destroyIntervalOperatorInfo(pInfo, numOfCols); - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -1965,7 +1965,7 @@ static void doSessionWindowAggImpl(SOperatorInfo* pOperator, SSessionAggOperator doKeepNewWindowStartInfo(pRowSup, tsList, j, gid); doKeepTuple(pRowSup, tsList[j], gid); } else if ((tsList[j] - pRowSup->prevTs >= 0) && tsList[j] - pRowSup->prevTs <= gap || - (pRowSup->prevTs - tsList[j] >= 0 ) && (pRowSup->prevTs - tsList[j] <= gap)) { + (pRowSup->prevTs - tsList[j] >= 0) && (pRowSup->prevTs - tsList[j] <= gap)) { // The gap is less than the threshold, so it belongs to current session window that has been opened already. doKeepTuple(pRowSup, tsList[j], gid); if (j == 0 && pRowSup->startRowIndex != 0) { @@ -2118,7 +2118,7 @@ static void doKeepNextRows(STimeSliceOperatorInfo* pSliceInfo, const SSDataBlock static void doKeepLinearInfo(STimeSliceOperatorInfo* pSliceInfo, const SSDataBlock* pBlock, int32_t rowIndex, bool isLastRow) { int32_t numOfCols = taosArrayGetSize(pBlock->pDataBlock); - bool fillLastPoint = pSliceInfo->fillLastPoint; + bool fillLastPoint = pSliceInfo->fillLastPoint; for (int32_t i = 0; i < numOfCols; ++i) { SColumnInfoData* pColInfoData = taosArrayGet(pBlock->pDataBlock, i); SColumnInfoData* pTsCol = taosArrayGet(pBlock->pDataBlock, pSliceInfo->tsCol.slotId); @@ -2150,11 +2150,9 @@ static void doKeepLinearInfo(STimeSliceOperatorInfo* pSliceInfo, const SSDataBlo } pSliceInfo->fillLastPoint = isLastRow ? true : false; - } -static void genInterpolationResult(STimeSliceOperatorInfo* pSliceInfo, SExprSupp* pExprSup, - SSDataBlock* pResBlock) { +static void genInterpolationResult(STimeSliceOperatorInfo* pSliceInfo, SExprSupp* pExprSup, SSDataBlock* pResBlock) { int32_t rows = pResBlock->info.rows; // todo set the correct primary timestamp column @@ -2165,7 +2163,7 @@ static void genInterpolationResult(STimeSliceOperatorInfo* pSliceInfo, SExprSupp int32_t srcSlot = pExprInfo->base.pParam[0].pCol->slotId; int32_t dstSlot = pExprInfo->base.resSchema.slotId; - //SColumnInfoData* pSrc = taosArrayGet(pBlock->pDataBlock, srcSlot); + // SColumnInfoData* pSrc = taosArrayGet(pBlock->pDataBlock, srcSlot); SColumnInfoData* pDst = taosArrayGet(pResBlock->pDataBlock, dstSlot); switch (pSliceInfo->fillType) { @@ -2181,15 +2179,15 @@ static void genInterpolationResult(STimeSliceOperatorInfo* pSliceInfo, SExprSupp if (pDst->info.type == TSDB_DATA_TYPE_FLOAT) { float v = 0; GET_TYPED_DATA(v, float, pVar->nType, &pVar->i); - colDataAppend(pDst, rows, (char *)&v, false); + colDataAppend(pDst, rows, (char*)&v, false); } else if (pDst->info.type == TSDB_DATA_TYPE_DOUBLE) { double v = 0; GET_TYPED_DATA(v, double, pVar->nType, &pVar->i); - colDataAppend(pDst, rows, (char *)&v, false); + colDataAppend(pDst, rows, (char*)&v, false); } else if (IS_SIGNED_NUMERIC_TYPE(pDst->info.type)) { int64_t v = 0; GET_TYPED_DATA(v, int64_t, pVar->nType, &pVar->i); - colDataAppend(pDst, rows, (char *)&v, false); + colDataAppend(pDst, rows, (char*)&v, false); } pResBlock->info.rows += 1; break; @@ -2198,8 +2196,8 @@ static void genInterpolationResult(STimeSliceOperatorInfo* pSliceInfo, SExprSupp case TSDB_FILL_LINEAR: { SFillLinearInfo* pLinearInfo = taosArrayGet(pSliceInfo->pLinearInfo, srcSlot); - SPoint start = pLinearInfo->start; - SPoint end = pLinearInfo->end; + SPoint start = pLinearInfo->start; + SPoint end = pLinearInfo->end; SPoint current = {.key = pSliceInfo->current}; current.val = taosMemoryCalloc(pLinearInfo->bytes, 1); @@ -2212,7 +2210,7 @@ static void genInterpolationResult(STimeSliceOperatorInfo* pSliceInfo, SExprSupp colDataAppendNULL(pDst, rows); } else { taosGetLinearInterpolationVal(¤t, pLinearInfo->type, &start, &end, pLinearInfo->type); - colDataAppend(pDst, rows, (char *)current.val, false); + colDataAppend(pDst, rows, (char*)current.val, false); } pResBlock->info.rows += 1; @@ -2317,11 +2315,11 @@ static int32_t initFillLinearInfo(STimeSliceOperatorInfo* pInfo, SSDataBlock* pB SFillLinearInfo linearInfo = {0}; linearInfo.start.key = INT64_MIN; - linearInfo.end.key = INT64_MAX; + linearInfo.end.key = INT64_MAX; linearInfo.start.val = taosMemoryCalloc(1, pColInfo->info.bytes); - linearInfo.end.val = taosMemoryCalloc(1, pColInfo->info.bytes); - linearInfo.hasNull = false; - linearInfo.type = pColInfo->info.type; + linearInfo.end.val = taosMemoryCalloc(1, pColInfo->info.bytes); + linearInfo.hasNull = false; + linearInfo.type = pColInfo->info.type; linearInfo.bytes = pColInfo->info.bytes; taosArrayPush(pInfo->pLinearInfo, &linearInfo); } @@ -2399,7 +2397,7 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { for (int32_t i = 0; i < pBlock->info.rows; ++i) { int64_t ts = *(int64_t*)colDataGetData(pTsCol, i); - if (i == 0 && needToFillLastPoint(pSliceInfo)) { // first row in current block + if (i == 0 && needToFillLastPoint(pSliceInfo)) { // first row in current block doKeepLinearInfo(pSliceInfo, pBlock, i, false); while (pSliceInfo->current < ts && pSliceInfo->current <= pSliceInfo->win.ekey) { genInterpolationResult(pSliceInfo, &pOperator->exprSupp, pResBlock); @@ -2445,8 +2443,8 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { if (nextTs > pSliceInfo->current) { while (pSliceInfo->current < nextTs && pSliceInfo->current <= pSliceInfo->win.ekey) { genInterpolationResult(pSliceInfo, &pOperator->exprSupp, pResBlock); - pSliceInfo->current = - taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); + pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, + pInterval->precision); if (pResBlock->info.rows >= pResBlock->info.capacity) { break; } @@ -2457,11 +2455,11 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { break; } } - } else {// it is the last row of current block - //store ts value as start, and calculate interp value when processing next block + } else { // it is the last row of current block + // store ts value as start, and calculate interp value when processing next block doKeepLinearInfo(pSliceInfo, pBlock, i, true); } - } else { // non-linear interpolation + } else { // non-linear interpolation pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); if (pSliceInfo->current > pSliceInfo->win.ekey) { @@ -2480,15 +2478,15 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { if (pSliceInfo->fillType == TSDB_FILL_LINEAR) { doKeepLinearInfo(pSliceInfo, pBlock, i, false); // no need to increate pSliceInfo->current here - //pSliceInfo->current = + // pSliceInfo->current = // taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); if (i < pBlock->info.rows - 1) { int64_t nextTs = *(int64_t*)colDataGetData(pTsCol, i + 1); if (nextTs > pSliceInfo->current) { while (pSliceInfo->current < nextTs && pSliceInfo->current <= pSliceInfo->win.ekey) { genInterpolationResult(pSliceInfo, &pOperator->exprSupp, pResBlock); - pSliceInfo->current = - taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); + pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, + pInterval->precision); if (pResBlock->info.rows >= pResBlock->info.capacity) { break; } @@ -2500,7 +2498,7 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { } } } - } else { // non-linear interpolation + } else { // non-linear interpolation if (i < pBlock->info.rows - 1) { // in case of interpolation window starts and ends between two datapoints, fill(next) need to interpolate doKeepNextRows(pSliceInfo, pBlock, i + 1); @@ -2508,8 +2506,8 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { if (nextTs > pSliceInfo->current) { while (pSliceInfo->current < nextTs && pSliceInfo->current <= pSliceInfo->win.ekey) { genInterpolationResult(pSliceInfo, &pOperator->exprSupp, pResBlock); - pSliceInfo->current = - taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); + pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, + pInterval->precision); if (pResBlock->info.rows >= pResBlock->info.capacity) { break; } @@ -2556,7 +2554,6 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { pResBlock->info.rows += 1; doKeepPrevRows(pSliceInfo, pBlock, i); - if (pSliceInfo->fillType == TSDB_FILL_LINEAR) { doKeepLinearInfo(pSliceInfo, pBlock, i, false); pSliceInfo->current = @@ -2566,8 +2563,8 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { if (nextTs > pSliceInfo->current) { while (pSliceInfo->current < nextTs && pSliceInfo->current <= pSliceInfo->win.ekey) { genInterpolationResult(pSliceInfo, &pOperator->exprSupp, pResBlock); - pSliceInfo->current = - taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); + pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, + pInterval->precision); if (pResBlock->info.rows >= pResBlock->info.capacity) { break; } @@ -2579,7 +2576,7 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { } } } - } else { // non-linear interpolation + } else { // non-linear interpolation pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); @@ -2595,12 +2592,12 @@ static SSDataBlock* doTimeslice(SOperatorInfo* pOperator) { } } } - } // check if need to interpolate after last datablock // except for fill(next), fill(linear) - while (pSliceInfo->current <= pSliceInfo->win.ekey && pSliceInfo->fillType != TSDB_FILL_NEXT && pSliceInfo->fillType != TSDB_FILL_LINEAR) { + while (pSliceInfo->current <= pSliceInfo->win.ekey && pSliceInfo->fillType != TSDB_FILL_NEXT && + pSliceInfo->fillType != TSDB_FILL_LINEAR) { genInterpolationResult(pSliceInfo, &pOperator->exprSupp, pResBlock); pSliceInfo->current = taosTimeAdd(pSliceInfo->current, pInterval->interval, pInterval->intervalUnit, pInterval->precision); @@ -2795,7 +2792,6 @@ _error: destroySWindowOperatorInfo(pInfo, numOfCols); } - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -3432,7 +3428,6 @@ SOperatorInfo* createStreamFinalIntervalOperatorInfo(SOperatorInfo* downstream, _error: destroyStreamFinalIntervalOperatorInfo(pInfo, numOfCols); - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -3617,7 +3612,6 @@ _error: destroyStreamSessionAggOperatorInfo(pInfo, numOfCols); } - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -3735,8 +3729,8 @@ SResultWindowInfo* getSessionTimeWindow(SStreamAggSupporter* pAggSup, TSKEY star return insertNewSessionWindow(pWinInfos, startTs, index + 1); } -int32_t updateSessionWindowInfo(SResultWindowInfo* pWinInfo, TSKEY* pStartTs, TSKEY* pEndTs, uint64_t groupId,int32_t rows, - int32_t start, int64_t gap, SHashObj* pStDeleted) { +int32_t updateSessionWindowInfo(SResultWindowInfo* pWinInfo, TSKEY* pStartTs, TSKEY* pEndTs, uint64_t groupId, + int32_t rows, int32_t start, int64_t gap, SHashObj* pStDeleted) { for (int32_t i = start; i < rows; ++i) { if (!isInWindow(pWinInfo, pStartTs[i], gap) && (!pEndTs || !isInWindow(pWinInfo, pEndTs[i], gap))) { return i - start; @@ -3913,8 +3907,8 @@ static void doStreamSessionAggImpl(SOperatorInfo* pOperator, SSDataBlock* pSData } int32_t winIndex = 0; SResultWindowInfo* pCurWin = getSessionTimeWindow(pAggSup, startTsCols[i], endTsCols[i], groupId, gap, &winIndex); - winRows = - updateSessionWindowInfo(pCurWin, startTsCols, endTsCols, groupId, pSDataBlock->info.rows, i, pInfo->gap, pStDeleted); + winRows = updateSessionWindowInfo(pCurWin, startTsCols, endTsCols, groupId, pSDataBlock->info.rows, i, pInfo->gap, + pStDeleted); code = doOneWindowAgg(pInfo, pSDataBlock, pCurWin, &pResult, i, winRows, numOfOutput, pOperator); if (code != TSDB_CODE_SUCCESS || pResult == NULL) { longjmp(pTaskInfo->env, TSDB_CODE_QRY_OUT_OF_MEMORY); @@ -4021,7 +4015,7 @@ void doBuildDeleteDataBlock(SHashObj* pStDeleted, SSDataBlock* pBlock, void** It blockDataEnsureCapacity(pBlock, size); size_t keyLen = 0; while (((*Ite) = taosHashIterate(pStDeleted, *Ite)) != NULL) { - SWinRes* res = *Ite; + SWinRes* res = *Ite; SColumnInfoData* pTsCol = taosArrayGet(pBlock->pDataBlock, START_TS_COLUMN_INDEX); colDataAppend(pTsCol, pBlock->info.rows, (const char*)&res->ts, false); SColumnInfoData* pGpCol = taosArrayGet(pBlock->pDataBlock, GROUPID_COLUMN_INDEX); @@ -4152,7 +4146,7 @@ static void copyDeleteWindowInfo(SArray* pResWins, SHashObj* pStDeleted) { int32_t size = taosArrayGetSize(pResWins); for (int32_t i = 0; i < size; i++) { SResultWindowInfo* pWinInfo = taosArrayGet(pResWins, i); - SWinRes res = {.ts = pWinInfo->win.skey, .groupId = pWinInfo->groupId}; + SWinRes res = {.ts = pWinInfo->win.skey, .groupId = pWinInfo->groupId}; taosHashPut(pStDeleted, &pWinInfo->pos, sizeof(SResultRowPosition), &res, sizeof(SWinRes)); } } @@ -4449,7 +4443,6 @@ _error: destroyStreamSessionAggOperatorInfo(pInfo, pOperator->exprSupp.numOfExprs); } - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -4886,7 +4879,6 @@ SOperatorInfo* createStreamStateAggOperatorInfo(SOperatorInfo* downstream, SPhys _error: destroyStreamStateOperatorInfo(pInfo, numOfCols); - taosMemoryFreeClear(pInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -4996,7 +4988,6 @@ static void doMergeAlignedIntervalAggImpl(SOperatorInfo* pOperatorInfo, SResultR tsCols, pBlock->info.rows, numOfOutput, iaInfo->inputOrder); } - static void doMergeAlignedIntervalAgg(SOperatorInfo* pOperator) { SExecTaskInfo* pTaskInfo = pOperator->pTaskInfo; @@ -5071,7 +5062,7 @@ static SSDataBlock* mergeAlignedIntervalAgg(SOperatorInfo* pOperator) { blockDataCleanup(pRes); if (iaInfo->binfo.mergeResultBlock) { - while(1) { + while (1) { if (pOperator->status == OP_EXEC_DONE) { break; } @@ -5161,7 +5152,6 @@ SOperatorInfo* createMergeAlignedIntervalOperatorInfo(SOperatorInfo* downstream, _error: destroyMergeAlignedIntervalOperatorInfo(miaInfo, numOfCols); - taosMemoryFreeClear(miaInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; @@ -5466,7 +5456,6 @@ SOperatorInfo* createMergeIntervalOperatorInfo(SOperatorInfo* downstream, SExprI _error: destroyMergeIntervalOperatorInfo(miaInfo, numOfCols); - taosMemoryFreeClear(miaInfo); taosMemoryFreeClear(pOperator); pTaskInfo->code = code; return NULL; From d5072a8f323899edfb763ab397bfe6f59a67cfbc Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 11:36:49 +0800 Subject: [PATCH 10/47] fix: fix sched handler memory leak issue --- source/libs/index/src/index.c | 1 + source/util/src/ttimer.c | 1 + 2 files changed, 2 insertions(+) diff --git a/source/libs/index/src/index.c b/source/libs/index/src/index.c index eac585c2e6..be64a8b44d 100644 --- a/source/libs/index/src/index.c +++ b/source/libs/index/src/index.c @@ -68,6 +68,7 @@ void indexInit() { void indexCleanup() { // refacto later taosCleanUpScheduler(indexQhandle); + taosMemoryFreeClear(indexQhandle); taosCloseRef(indexRefMgt); } diff --git a/source/util/src/ttimer.c b/source/util/src/ttimer.c index ff5ac1b217..3a868c7f97 100644 --- a/source/util/src/ttimer.c +++ b/source/util/src/ttimer.c @@ -606,6 +606,7 @@ void taosTmrCleanUp(void* handle) { taosUninitTimer(); taosCleanUpScheduler(tmrQhandle); + taosMemoryFreeClear(tmrQhandle); for (int32_t i = 0; i < tListLen(wheels); i++) { time_wheel_t* wheel = wheels + i; From 4a34342af4edc77be0d3d23ea8654e94db897a6a Mon Sep 17 00:00:00 2001 From: Minglei Jin Date: Fri, 12 Aug 2022 12:39:44 +0800 Subject: [PATCH 11/47] fix: remove old no ref entry --- source/util/src/tlrucache.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/util/src/tlrucache.c b/source/util/src/tlrucache.c index 28e15dc9a3..83cfbb2ad1 100644 --- a/source/util/src/tlrucache.c +++ b/source/util/src/tlrucache.c @@ -391,7 +391,7 @@ static LRUStatus taosLRUCacheShardInsertEntry(SLRUCacheShard *shard, SLRUEntry * assert(TAOS_LRU_ENTRY_IN_CACHE(old)); TAOS_LRU_ENTRY_SET_IN_CACHE(old, false); - if (!TAOS_LRU_ENTRY_HAS_REFS(e)) { + if (!TAOS_LRU_ENTRY_HAS_REFS(old)) { taosLRUCacheShardLRURemove(shard, old); assert(shard->usage >= old->totalCharge); shard->usage -= old->totalCharge; From 9ec8a1e44edf4908719150a2d607230e75b32393 Mon Sep 17 00:00:00 2001 From: wade zhang <95411902+gccgdb1234@users.noreply.github.com> Date: Fri, 12 Aug 2022 13:03:14 +0800 Subject: [PATCH 12/47] Update 25-grant.md --- docs/zh/12-taos-sql/25-grant.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/zh/12-taos-sql/25-grant.md b/docs/zh/12-taos-sql/25-grant.md index 0c290350cc..c41a3fcfc9 100644 --- a/docs/zh/12-taos-sql/25-grant.md +++ b/docs/zh/12-taos-sql/25-grant.md @@ -8,7 +8,7 @@ title: 权限管理 ## 创建用户 ```sql -CREATE USER use_name PASS password; +CREATE USER use_name PASS 'password'; ``` 创建用户。 @@ -91,4 +91,4 @@ priv_level : { ``` -收回对用户的授权。 \ No newline at end of file +收回对用户的授权。 From b6f90d205cb5fc9277f11ea0552f24b402760065 Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 13:29:07 +0800 Subject: [PATCH 13/47] Update 01-docker.md --- docs/zh/05-get-started/01-docker.md | 17 +++-------------- 1 file changed, 3 insertions(+), 14 deletions(-) diff --git a/docs/zh/05-get-started/01-docker.md b/docs/zh/05-get-started/01-docker.md index 66ad82adb8..814784b649 100644 --- a/docs/zh/05-get-started/01-docker.md +++ b/docs/zh/05-get-started/01-docker.md @@ -3,7 +3,7 @@ sidebar_label: Docker title: 通过 Docker 快速体验 TDengine --- :::info -如果您希望对 TDengine 贡献代码或对内部实现感兴趣,请参考我们的 [TDengine GitHub 主页](https://github.com/taosdata/TDengine) 下载源码构建和安装. +如果您希望为 TDengine 贡献代码或对内部技术实现感兴趣,请参考[TDengine GitHub 主页](https://github.com/taosdata/TDengine) 下载源码构建和安装. ::: 本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。 @@ -32,18 +32,7 @@ docker exec -it bash 然后就可以执行相关的 Linux 命令操作和访问 TDengine -:::info - -Docker 工具自身的下载请参考 [Docker 官网文档](https://docs.docker.com/get-docker/)。 - -安装完毕后可以在命令行终端查看 Docker 版本。如果版本号正常输出,则说明 Docker 环境已经安装成功。 - -```bash -$ docker -v -Docker version 20.10.3, build 48d30b5 -``` - -::: +注: Docker 工具自身的下载和使用请参考 [Docker 官网文档](https://docs.docker.com/get-docker/)。 ## 运行 TDengine CLI @@ -109,4 +98,4 @@ taos> select avg(current), max(voltage), min(phase) from test.d10 interval(10s); ## 其它 -更多关于在 Docker 环境下使用 TDengine 的细节,请参考 [在 Docker 下使用 TDengine](../../reference/docker) \ No newline at end of file +更多关于在 Docker 环境下使用 TDengine 的细节,请参考 [在 Docker 下使用 TDengine](../../reference/docker) From eaf1ad2f3941a1ddaa8ea341c83e9a70557e841a Mon Sep 17 00:00:00 2001 From: wade zhang <95411902+gccgdb1234@users.noreply.github.com> Date: Fri, 12 Aug 2022 13:32:51 +0800 Subject: [PATCH 14/47] Update 01-docker.md --- docs/en/05-get-started/01-docker.md | 15 +-------------- 1 file changed, 1 insertion(+), 14 deletions(-) diff --git a/docs/en/05-get-started/01-docker.md b/docs/en/05-get-started/01-docker.md index 08d897ec07..14f5a88000 100644 --- a/docs/en/05-get-started/01-docker.md +++ b/docs/en/05-get-started/01-docker.md @@ -32,19 +32,6 @@ docker exec -it bash 然后就可以执行相关的 Linux 命令操作和访问 TDengine -:::info - -Docker 工具自身的下载请参考 [Docker 官网文档](https://docs.docker.com/get-docker/)。 - -安装完毕后可以在命令行终端查看 Docker 版本。如果版本号正常输出,则说明 Docker 环境已经安装成功。 - -```bash -$ docker -v -Docker version 20.10.3, build 48d30b5 -``` - -::: - ## 运行 TDengine CLI 进入容器,执行 taos @@ -113,4 +100,4 @@ taos> select avg(current), max(voltage), min(phase) from test.d10 interval(10s); ## 其它 -更多关于在 Docker 环境下使用 TDengine 的细节,请参考 [在 Docker 下使用 TDengine](../../reference/docker) \ No newline at end of file +更多关于在 Docker 环境下使用 TDengine 的细节,请参考 [在 Docker 下使用 TDengine](../../reference/docker) From f0a6061458ce6121a8aab0b1a1268290868e7198 Mon Sep 17 00:00:00 2001 From: Shuduo Sang Date: Fri, 12 Aug 2022 13:33:48 +0800 Subject: [PATCH 15/47] feat: update taostools 53a0103 for3.0 (#16038) * feat: update taos-tools for 3.0 [TD-14141] * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools for 3.0 * feat: update taos-tools 8e3b3ee * fix: remove submodules * feat: update taos-tools c529299 * feat: update taos-tools 9dc2fec for 3.0 * fix: optim upx * feat: update taos-tools f4e456a for 3.0 * feat: update taos-tools 2a2def1 for 3.0 * feat: update taos-tools c9cc20f for 3.0 * feat: update taostoosl 8a5e336 for 3.0 * feat: update taostools 3c7dafe for 3.0 * feat: update taos-tools 2d68404 for 3.0 * feat: update taos-tools 57bdfbf for 3.0 * fix: jenkinsfile2 to upgrade pip * feat: update taostoosl 11d23e5 for 3.0 * feat: update taostools 43924b8 for 3.0 * feat: update taostools 53a0103 for 3.0 --- cmake/taostools_CMakeLists.txt.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmake/taostools_CMakeLists.txt.in b/cmake/taostools_CMakeLists.txt.in index 989f90a150..3a6eb3c25a 100644 --- a/cmake/taostools_CMakeLists.txt.in +++ b/cmake/taostools_CMakeLists.txt.in @@ -2,7 +2,7 @@ # taos-tools ExternalProject_Add(taos-tools GIT_REPOSITORY https://github.com/taosdata/taos-tools.git - GIT_TAG 43924b8 + GIT_TAG 53a0103 SOURCE_DIR "${TD_SOURCE_DIR}/tools/taos-tools" BINARY_DIR "" #BUILD_IN_SOURCE TRUE From 7a17cf087abe24375bac328856249ab578571793 Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 13:35:34 +0800 Subject: [PATCH 16/47] fix: fix sysdb user authentication failure --- source/libs/catalog/src/ctgCache.c | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/source/libs/catalog/src/ctgCache.c b/source/libs/catalog/src/ctgCache.c index 930361419e..6935489ff4 100644 --- a/source/libs/catalog/src/ctgCache.c +++ b/source/libs/catalog/src/ctgCache.c @@ -581,6 +581,20 @@ _return: } int32_t ctgChkAuthFromCache(SCatalog* pCtg, char* user, char* dbFName, AUTH_TYPE type, bool *inCache, bool *pass) { + char *p = strchr(dbFName, '.'); + if (p) { + ++p; + } else { + p = dbFName; + } + + if (IS_SYS_DBNAME(p)) { + *inCache = true; + *pass = true; + ctgDebug("sysdb %s, pass", dbFName); + return TSDB_CODE_SUCCESS; + } + SCtgUserAuth *pUser = (SCtgUserAuth *)taosHashGet(pCtg->userCache, user, strlen(user)); if (NULL == pUser) { ctgDebug("user not in cache, user:%s", user); From d4e11c06207e39ef6a08d76807f8b43e6a776aa6 Mon Sep 17 00:00:00 2001 From: yihaoDeng Date: Fri, 12 Aug 2022 13:40:24 +0800 Subject: [PATCH 17/47] fix operator double free --- source/libs/executor/src/executorimpl.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/source/libs/executor/src/executorimpl.c b/source/libs/executor/src/executorimpl.c index 59b3328f62..353c721534 100644 --- a/source/libs/executor/src/executorimpl.c +++ b/source/libs/executor/src/executorimpl.c @@ -4249,8 +4249,7 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo ASSERT(0); } taosMemoryFree(ops); - - pOptr->resultDataBlockId = pPhyNode->pOutputDataBlockDesc->dataBlockId; + if (pOptr) pOptr->resultDataBlockId = pPhyNode->pOutputDataBlockDesc->dataBlockId; return pOptr; } From 422ab15bc325beaab7d8a3eaca406d7849c6df34 Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 13:46:17 +0800 Subject: [PATCH 18/47] Update README.md --- README.md | 28 +++++++--------------------- 1 file changed, 7 insertions(+), 21 deletions(-) diff --git a/README.md b/README.md index 65dafdf8fb..339c1e5178 100644 --- a/README.md +++ b/README.md @@ -26,14 +26,14 @@ TDengine is an open source, cloud native time-series database optimized for Inte - Simplified Solution: Through built-in caching, stream processing and data subscription features, TDengine provides a simplified solution for time-series data processing. It reduces system design complexity and operation costs significantly. -- Cloud Native: Through native distributed design, sharding and partitioning, separation of compute and storage, RAFT, support for kubernetes deployment and full observability, TDengine can be deployed on public, private or hybrid clouds. - -- Open Source: TDengine’s core modules, including cluster feature, are all available under open source licenses. It has gathered 18.8k stars on GitHub, an active developer community, and over 137k running instances worldwide. +- Cloud Native: Through native distributed design, sharding and partitioning, separation of compute and storage, RAFT, support for kubernetes deployment and full observability, TDengine is a cloud native Time-Series Database and can be deployed on public, private or hybrid clouds. - Ease of Use: For administrators, TDengine significantly reduces the effort to deploy and maintain. For developers, it provides a simple interface, simplified solution and seamless integrations for third party tools. For data users, it gives easy data access. - Easy Data Analytics: Through super tables, storage and compute separation, data partitioning by time interval, pre-computation and other means, TDengine makes it easy to explore, format, and get access to data in a highly efficient way. +- Open Source: TDengine’s core modules, including cluster feature, are all available under open source licenses. It has gathered 18.8k stars on GitHub, an active developer community, and over 137k running instances worldwide. + # Documentation For user manual, system design and architecture, please refer to [TDengine Documentation](https://docs.tdengine.com) (中文版请点击[这里](https://docs.taosdata.com)) @@ -42,6 +42,8 @@ For user manual, system design and architecture, please refer to [TDengine Docum At the moment, TDengine server supports running on Linux, Windows, and macOS systems. You can choose to [install from packages](https://www.taosdata.com/en/getting-started/#Install-from-Package) or build it from the source code. This quick guide is for installation from the source only. +We provide a few useful tools such as taosBenchmark (was named taosdemo) and taosdump. They were part of TDengine. By default, TDengine compiling does not include taosTools. You can use 'cmake .. -DBUILD_TOOLS=true' to make them be compiled with TDengine. + To build TDengine, use [CMake](https://cmake.org/) 3.0.2 or higher versions in the project directory. ## Install build dependencies @@ -54,9 +56,6 @@ sudo apt-get install -y gcc cmake build-essential git libssl-dev #### Install build dependencies for taosTools -We provide a few useful tools such as taosBenchmark (was named taosdemo) and taosdump. They were part of TDengine. From TDengine 2.4.0.0, taosBenchmark and taosdump were not released together with TDengine. -By default, TDengine compiling does not include taosTools. You can use 'cmake .. -DBUILD_TOOLS=true' to make them be compiled with TDengine. - To build the [taosTools](https://github.com/taosdata/taos-tools) on Ubuntu/Debian, the following packages need to be installed. ```bash @@ -172,7 +171,7 @@ cmake .. -DCPUTYPE=aarch64 && cmake --build . ### On Windows platform If you use the Visual Studio 2013, please open a command window by executing "cmd.exe". -Please specify "amd64" for 64 bits Windows or specify "x86" is for 32 bits Windows when you execute vcvarsall.bat. +Please specify "amd64" for 64 bits Windows or specify "x86" for 32 bits Windows when you execute vcvarsall.bat. ```cmd mkdir debug && cd debug @@ -184,7 +183,7 @@ nmake If you use the Visual Studio 2019 or 2017: please open a command window by executing "cmd.exe". -Please specify "x64" for 64 bits Windows or specify "x86" is for 32 bits Windows when you execute vcvarsall.bat. +Please specify "x64" for 64 bits Windows or specify "x86" for 32 bits Windows when you execute vcvarsall.bat. ```cmd mkdir debug && cd debug @@ -237,19 +236,6 @@ taos If TDengine shell connects the server successfully, welcome messages and version info are printed. Otherwise, an error message is shown. -### Install TDengine by apt-get - -If you use Debian or Ubuntu system, you can use 'apt-get' command to install TDengine from official repository. Please use following commands to setup: - -``` -wget -qO - http://repos.taosdata.com/tdengine.key | sudo apt-key add - -echo "deb [arch=amd64] http://repos.taosdata.com/tdengine-stable stable main" | sudo tee /etc/apt/sources.list.d/tdengine-stable.list -[Optional] echo "deb [arch=amd64] http://repos.taosdata.com/tdengine-beta beta main" | sudo tee /etc/apt/sources.list.d/tdengine-beta.list -sudo apt-get update -apt-cache policy tdengine -sudo apt-get install tdengine -``` - ## On Windows platform After building successfully, TDengine can be installed by: From 062bc1c4c6091ac2492f2a992e86fe78ef5f985b Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 14:01:39 +0800 Subject: [PATCH 19/47] Update README.md --- README.md | 13 +++---------- 1 file changed, 3 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 339c1e5178..c97b8b486e 100644 --- a/README.md +++ b/README.md @@ -89,7 +89,7 @@ Note: Since snappy lacks pkg-config support (refer to [link](https://github.com/ ### Setup golang environment -TDengine includes a few components developed by Go language. Please refer to golang.org official documentation for golang environment setup. +TDengine includes a few components like taosAdapter developed by Go language. Please refer to golang.org official documentation for golang environment setup. Please use version 1.14+. For the user in China, we recommend using a proxy to accelerate package downloading. @@ -100,7 +100,7 @@ go env -w GOPROXY=https://goproxy.cn,direct ### Setup rust environment -TDengine includees a few compoments developed by Rust language. Please refer to rust-lang.org official documentation for rust environment setup. +TDengine includes a few compoments developed by Rust language. Please refer to rust-lang.org official documentation for rust environment setup. ## Get the source codes @@ -139,14 +139,7 @@ cmake .. -DBUILD_TOOLS=true make ``` -Note TDengine 2.3.x.0 and later use a component named 'taosAdapter' to play http daemon role by default instead of the http daemon embedded in the early version of TDengine. The taosAdapter is programmed by go language. If you pull TDengine source code to the latest from an existing codebase, please execute 'git submodule update --init --recursive' to pull taosAdapter source code. Please install go language version 1.14 or above for compiling taosAdapter. If you meet difficulties regarding 'go mod', especially you are from China, you can use a proxy to solve the problem. - -``` -go env -w GO111MODULE=on -go env -w GOPROXY=https://goproxy.cn,direct -``` - -The embedded http daemon still be built from TDengine source code by default. Or you can use the following command to choose to build taosAdapter. +Note TDengine 2.3.x.0 and later use a component named 'taosAdapter' to play http daemon role. If you pull TDengine source code to the latest from an existing codebase, please execute 'git submodule update --init --recursive' to pull taosAdapter source code, and use the following command to choose to build taosAdapter. ``` cmake .. -DBUILD_HTTP=false From 229d8986b9ab6bbba9ce5ec3a67472d2ab007b57 Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 14:08:11 +0800 Subject: [PATCH 20/47] Update README-CN.md --- README-CN.md | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/README-CN.md b/README-CN.md index dc9bce481f..b12b811a7c 100644 --- a/README-CN.md +++ b/README-CN.md @@ -19,7 +19,7 @@ # TDengine 简介 -TDengine 是一款开源、高性能、云原生的时序数据库 (Time-Series Database, TSDB)。TDengine 能被广泛运用于物联网、工业互联网、车联网、IT 运维、金融等领域。除核心的时序数据库功能外,TDengine 还提供缓存、数据订阅、流式计算等功能,是一极简的时序数据处理平台,最大程度的减小系统设计的复杂度,降低研发和运营成本。TDengine 的主要优势如下: +TDengine 是一款开源、高性能、云原生的时序数据库 (Time-Series Database, TSDB)。TDengine 能被广泛运用于物联网、工业互联网、车联网、IT 运维、金融等领域。除核心的时序数据库功能外,TDengine 还提供缓存、数据订阅、流式计算等功能,是一极简的时序数据处理平台,最大程度的减小系统设计的复杂度,降低研发和运营成本。与其他时序数据库相比,TDengine 的主要优势如下: - 高性能:通过创新的存储引擎设计,无论是数据写入还是查询,TDengine 的性能比通用数据库快 10 倍以上,也远超其他时序数据库,存储空间不及通用数据库的1/10。 @@ -42,6 +42,8 @@ TDengine 是一款开源、高性能、云原生的时序数据库 (Time-Series TDengine 目前可以在 Linux、 Windows 等平台上安装和运行。任何 OS 的应用也可以选择 taosAdapter 的 RESTful 接口连接服务端 taosd。CPU 支持 X64/ARM64,后续会支持 MIPS64、Alpha64、ARM32、RISC-V 等 CPU 架构。 用户可根据需求选择通过[源码](https://www.taosdata.com/cn/getting-started/#通过源码安装)或者[安装包](https://www.taosdata.com/cn/getting-started/#通过安装包安装)来安装。本快速指南仅适用于通过源码安装。 + +TDengine 还提供一组辅助工具软件 taosTools,目前它包含 taosBenchmark(曾命名为 taosdemo)和 taosdump 两个软件。默认 TDengine 编译不包含 taosTools, 您可以在编译 TDengine 时使用`cmake .. -DBUILD_TOOLS=true` 来同时编译 taosTools。 ## 安装工具 @@ -53,10 +55,6 @@ sudo apt-get install -y gcc cmake build-essential git libssl-dev #### 为 taos-tools 安装编译需要的软件 -taosTools 是用于 TDengine 的辅助工具软件集合。目前它包含 taosBenchmark(曾命名为 taosdemo)和 taosdump 两个软件。 - -默认 TDengine 编译不包含 taosTools。您可以在编译 TDengine 时使用`cmake .. -DBUILD_TOOLS=true` 来同时编译 taosTools。 - 为了在 Ubuntu/Debian 系统上编译 [taos-tools](https://github.com/taosdata/taos-tools) 需要安装如下软件: ```bash @@ -104,7 +102,7 @@ sudo yum config-manager --set-enabled Powertools ### 设置 golang 开发环境 -TDengine 包含数个使用 Go 语言开发的组件,请参考 golang.org 官方文档设置 go 开发环境。 +TDengine 包含数个使用 Go 语言开发的组件,比如taosAdapter, 请参考 golang.org 官方文档设置 go 开发环境。 请使用 1.14 及以上版本。对于中国用户,我们建议使用代理来加速软件包下载。 From 4cd681520e77e205223b88ea5954171ca3c2778d Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 14:10:12 +0800 Subject: [PATCH 21/47] Update README-CN.md --- README-CN.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README-CN.md b/README-CN.md index b12b811a7c..d1545101a0 100644 --- a/README-CN.md +++ b/README-CN.md @@ -111,7 +111,7 @@ go env -w GO111MODULE=on go env -w GOPROXY=https://goproxy.cn,direct ``` -默认情况下,内嵌的 http 服务仍然可以从 TDengine 源码构建。当然您也可以使用以下命令选择构建 taosAdapter 作为 RESTful 接口的服务。 +缺省是不会构建 taosAdapter, 但您可以使用以下命令选择构建 taosAdapter 作为 RESTful 接口的服务。 ``` cmake .. -DBUILD_HTTP=false From 1a217470cadfda442d7f67dfdb8190592f5d368e Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 14:13:37 +0800 Subject: [PATCH 22/47] Update README-CN.md --- README-CN.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README-CN.md b/README-CN.md index d1545101a0..37bde323c8 100644 --- a/README-CN.md +++ b/README-CN.md @@ -41,7 +41,7 @@ TDengine 是一款开源、高性能、云原生的时序数据库 (Time-Series TDengine 目前可以在 Linux、 Windows 等平台上安装和运行。任何 OS 的应用也可以选择 taosAdapter 的 RESTful 接口连接服务端 taosd。CPU 支持 X64/ARM64,后续会支持 MIPS64、Alpha64、ARM32、RISC-V 等 CPU 架构。 -用户可根据需求选择通过[源码](https://www.taosdata.com/cn/getting-started/#通过源码安装)或者[安装包](https://www.taosdata.com/cn/getting-started/#通过安装包安装)来安装。本快速指南仅适用于通过源码安装。 +用户可根据需求选择通过源码、[容器](https://docs.taosdata.com/3.0/get-started/docker/)、[安装包](https://docs.taosdata.com/3.0/get-started/package/)或[Kubenetes](https://docs.taosdata.com/3.0/deployment/k8s/)来安装。本快速指南仅适用于通过源码安装。 TDengine 还提供一组辅助工具软件 taosTools,目前它包含 taosBenchmark(曾命名为 taosdemo)和 taosdump 两个软件。默认 TDengine 编译不包含 taosTools, 您可以在编译 TDengine 时使用`cmake .. -DBUILD_TOOLS=true` 来同时编译 taosTools。 From 7d6cbafa00ad48825d59ce036e2f2065798fb639 Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 14:15:41 +0800 Subject: [PATCH 23/47] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index c97b8b486e..69076b4081 100644 --- a/README.md +++ b/README.md @@ -36,7 +36,7 @@ TDengine is an open source, cloud native time-series database optimized for Inte # Documentation -For user manual, system design and architecture, please refer to [TDengine Documentation](https://docs.tdengine.com) (中文版请点击[这里](https://docs.taosdata.com)) +For user manual, system design and architecture, please refer to [TDengine Documentation](https://docs.tdengine.com) ([中文版](https://docs.taosdata.com)) # Building From 7a8088e475ba52ac61b76ee302b347ee4b96b9e9 Mon Sep 17 00:00:00 2001 From: Jeff Tao Date: Fri, 12 Aug 2022 14:17:02 +0800 Subject: [PATCH 24/47] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 69076b4081..dcb9f4416a 100644 --- a/README.md +++ b/README.md @@ -40,7 +40,7 @@ For user manual, system design and architecture, please refer to [TDengine Docum # Building -At the moment, TDengine server supports running on Linux, Windows, and macOS systems. You can choose to [install from packages](https://www.taosdata.com/en/getting-started/#Install-from-Package) or build it from the source code. This quick guide is for installation from the source only. +At the moment, TDengine server supports running on Linux, Windows, and macOS systems. You can choose to [install from packages](https://www.tdengine.com/getting-started/#Install-from-Package) or build it from the source code. This quick guide is for installation from the source only. We provide a few useful tools such as taosBenchmark (was named taosdemo) and taosdump. They were part of TDengine. By default, TDengine compiling does not include taosTools. You can use 'cmake .. -DBUILD_TOOLS=true' to make them be compiled with TDengine. From c8884698b1dee7636fff8609d2aa634a9b6f9ece Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 14:21:07 +0800 Subject: [PATCH 25/47] doc: hide error code temporarily --- .../03-connector/{01-error-code.md => _01-error-code.md} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename docs/zh/14-reference/03-connector/{01-error-code.md => _01-error-code.md} (100%) diff --git a/docs/zh/14-reference/03-connector/01-error-code.md b/docs/zh/14-reference/03-connector/_01-error-code.md similarity index 100% rename from docs/zh/14-reference/03-connector/01-error-code.md rename to docs/zh/14-reference/03-connector/_01-error-code.md From 3b0ee85c99e0b5325e8f96bcc221c814724a23dd Mon Sep 17 00:00:00 2001 From: wade zhang <95411902+gccgdb1234@users.noreply.github.com> Date: Fri, 12 Aug 2022 14:28:37 +0800 Subject: [PATCH 26/47] Update java.mdx --- docs/zh/14-reference/03-connector/java.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/zh/14-reference/03-connector/java.mdx b/docs/zh/14-reference/03-connector/java.mdx index 7a107bd04d..e33d09c1ce 100644 --- a/docs/zh/14-reference/03-connector/java.mdx +++ b/docs/zh/14-reference/03-connector/java.mdx @@ -358,7 +358,7 @@ JDBC 连接器可能报错的错误码包括 3 种:JDBC driver 本身的报错 具体的错误码请参考: - [TDengine Java Connector](https://github.com/taosdata/taos-connector-jdbc/blob/main/src/main/java/com/taosdata/jdbc/TSDBErrorNumbers.java) -- [TDengine_ERROR_CODE](../error-code) + ### 通过参数绑定写入数据 From d9eae4dd4c0d16f7e8dbf8df8abc48b82a2c9722 Mon Sep 17 00:00:00 2001 From: slzhou Date: Fri, 12 Aug 2022 14:54:12 +0800 Subject: [PATCH 27/47] fix : fix error caused by empty vgroups when no user tables --- source/libs/parser/src/parTranslater.c | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/source/libs/parser/src/parTranslater.c b/source/libs/parser/src/parTranslater.c index 5c49a6e0ab..74f0023269 100644 --- a/source/libs/parser/src/parTranslater.c +++ b/source/libs/parser/src/parTranslater.c @@ -1817,7 +1817,17 @@ static int32_t setVnodeSysTableVgroupList(STranslateContext* pCxt, SName* pName, code = getDBVgInfoImpl(pCxt, pName, &vgroupList); } - if (TSDB_CODE_SUCCESS == code && 0 == strcmp(pRealTable->table.tableName, TSDB_INS_TABLE_TABLES)) { + if (TSDB_CODE_SUCCESS == code && + 0 == strcmp(pRealTable->table.dbName, TSDB_INFORMATION_SCHEMA_DB) && + 0 == strcmp(pRealTable->table.tableName, TSDB_INS_TABLE_TAGS) && + isSelectStmt(pCxt->pCurrStmt) && + 0 == taosArrayGetSize(vgroupList)) { + ((SSelectStmt*)pCxt->pCurrStmt)->isEmptyResult = true; + } + + if (TSDB_CODE_SUCCESS == code && + 0 == strcmp(pRealTable->table.dbName, TSDB_INFORMATION_SCHEMA_DB) && + 0 == strcmp(pRealTable->table.tableName, TSDB_INS_TABLE_TABLES)) { code = addMnodeToVgroupList(&pCxt->pParseCxt->mgmtEpSet, &vgroupList); } From 46edeec3149d9b44c73fdc69c3fac5017ce2735d Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 14:55:31 +0800 Subject: [PATCH 28/47] fix: fix case issues --- source/dnode/mnode/impl/src/mndShow.c | 2 +- tests/script/tsim/user/privilege_sysinfo.sim | 14 +++++++------- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/source/dnode/mnode/impl/src/mndShow.c b/source/dnode/mnode/impl/src/mndShow.c index 05d0fe66c3..9499c90c57 100644 --- a/source/dnode/mnode/impl/src/mndShow.c +++ b/source/dnode/mnode/impl/src/mndShow.c @@ -238,7 +238,7 @@ static int32_t mndProcessRetrieveSysTableReq(SRpcMsg *pReq) { } else { memcpy(pReq->info.conn.user, TSDB_DEFAULT_USER, strlen(TSDB_DEFAULT_USER) + 1); } - if (mndCheckShowPrivilege(pMnode, pReq->info.conn.user, pShow->type, retrieveReq.db) != 0) { + if (retrieveReq.db[0] && mndCheckShowPrivilege(pMnode, pReq->info.conn.user, pShow->type, retrieveReq.db) != 0) { return -1; } diff --git a/tests/script/tsim/user/privilege_sysinfo.sim b/tests/script/tsim/user/privilege_sysinfo.sim index 718083f0d9..25c1a84db6 100644 --- a/tests/script/tsim/user/privilege_sysinfo.sim +++ b/tests/script/tsim/user/privilege_sysinfo.sim @@ -45,19 +45,19 @@ sql_error drop database db sql_error use db sql_error alter database db replica 1; sql_error show db.vgroups -sql_error select * from information_schema.ins_stables where db_name = 'db' -sql_error select * from information_schema.ins_tables where db_name = 'db' +sql select * from information_schema.ins_stables where db_name = 'db' +sql select * from information_schema.ins_tables where db_name = 'db' print =============== check show -sql_error select * from information_schema.ins_users +sql select * from information_schema.ins_users sql_error show cluster -sql_error select * from information_schema.ins_dnodes -sql_error select * from information_schema.ins_mnodes +sql select * from information_schema.ins_dnodes +sql select * from information_schema.ins_mnodes sql_error show snodes -sql_error select * from information_schema.ins_qnodes +sql select * from information_schema.ins_qnodes sql_error show bnodes sql_error show grants sql_error show dnode 1 variables; sql show variables; -system sh/exec.sh -n dnode1 -s stop -x SIGINT \ No newline at end of file +system sh/exec.sh -n dnode1 -s stop -x SIGINT From de225e6f97a162df107db885dd17ab73ffc62563 Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 15:35:19 +0800 Subject: [PATCH 29/47] doc: refine 07-tmq.md --- docs/zh/07-develop/07-tmq.md | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 459b88085f..1d63d4970d 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -4,6 +4,9 @@ description: "数据订阅与推送服务。写入到 TDengine 中的时序数 title: 数据订阅 --- +import Tabs from "@theme/Tabs"; +import TabItem from "@theme/TabItem"; + 为了帮助应用实时获取写入 TDengine 的数据,或者以事件到达顺序处理数据,TDengine提供了类似消息队列产品的数据订阅、消费接口。这样在很多场景下,采用 TDengine 的时序数据处理系统不再需要集成消息队列产品,比如 kafka, 从而简化系统设计的复杂度,降低运营维护成本。 与 kafka 一样,你需要定义 topic, 但 TDengine 的 topic 是基于一个已经存在的超级表、子表或普通表的查询条件,即一个 SELECT 语句。你可以使用 SQL 对标签、表名、列、表达式等条件进行过滤,以及对数据进行标量函数与 UDF 计算(不包括数据聚合)。与其他消息队列软件相比,这是 TDengine 数据订阅功能的最大的优势,它提供了更大的灵活性,数据的颗粒度可以由应用随时调整,而且数据的过滤与预处理交给 TDengine,而不是应用完成,有效的减少传输的数据量与应用的复杂度。 @@ -243,4 +246,37 @@ TMQ支持多种订阅类型: show subscriptions; ``` +## 示例代码 +本节展示各种语言的示例代码。 + + + +TODO + + + +TODO + + + +TODO + + + +TODO + + + +TODO + + + +TODO + + + +TODO + + + From c47e387d13f6f1c9e1f02558c852f34a5d27d49e Mon Sep 17 00:00:00 2001 From: Shengliang Guan Date: Fri, 12 Aug 2022 15:57:07 +0800 Subject: [PATCH 30/47] fix: deadlock of mnode if its state changed --- source/dnode/mnode/impl/src/mndSync.c | 12 ++++++++++-- tests/script/tsim/show/basic.sim | 2 ++ 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/source/dnode/mnode/impl/src/mndSync.c b/source/dnode/mnode/impl/src/mndSync.c index 37d5aeb62d..6a78d2f018 100644 --- a/source/dnode/mnode/impl/src/mndSync.c +++ b/source/dnode/mnode/impl/src/mndSync.c @@ -170,12 +170,20 @@ static void mndBecomeFollower(struct SSyncFSM *pFsm) { SMnode *pMnode = pFsm->data; mDebug("vgId:1, become follower"); - // clear old leader resource + if (pMnode->syncMgmt.transId != 0) { + pMnode->syncMgmt.transId = 0; + tsem_post(&pMnode->syncMgmt.syncSem); + } } static void mndBecomeLeader(struct SSyncFSM *pFsm) { - SMnode *pMnode = pFsm->data; mDebug("vgId:1, become leader"); + SMnode *pMnode = pFsm->data; + + if (pMnode->syncMgmt.transId != 0) { + pMnode->syncMgmt.transId = 0; + tsem_post(&pMnode->syncMgmt.syncSem); + } } SSyncFSM *mndSyncMakeFsm(SMnode *pMnode) { diff --git a/tests/script/tsim/show/basic.sim b/tests/script/tsim/show/basic.sim index 162e74ea14..274476e17c 100644 --- a/tests/script/tsim/show/basic.sim +++ b/tests/script/tsim/show/basic.sim @@ -210,6 +210,8 @@ if $rows != 3 then return -1 endi +sql_error select * from performance_schema.PERF_OFFSETS; + sql show create stable stb; if $rows != 1 then return -1 From 2ff73d44d86d7f760e0b646dd000f12c86244ba7 Mon Sep 17 00:00:00 2001 From: zhaoyanggh Date: Fri, 12 Aug 2022 16:07:00 +0800 Subject: [PATCH 31/47] docs: add tmq example in python --- docs/examples/python/tmq_example.py | 59 +++++++++++++++++++++++++++++ docs/zh/07-develop/07-tmq.md | 2 +- 2 files changed, 60 insertions(+), 1 deletion(-) create mode 100644 docs/examples/python/tmq_example.py diff --git a/docs/examples/python/tmq_example.py b/docs/examples/python/tmq_example.py new file mode 100644 index 0000000000..1f6da3d1b6 --- /dev/null +++ b/docs/examples/python/tmq_example.py @@ -0,0 +1,59 @@ +import taos +from taos.tmq import * + +conn = taos.connect() + +# create database +conn.execute("drop database if exists py_tmq") +conn.execute("create database if not exists py_tmq vgroups 2") + +# create table and stables +conn.select_db("py_tmq") +conn.execute("create stable if not exists stb1 (ts timestamp, c1 int, c2 float, c3 binary(10)) tags(t1 int)") +conn.execute("create table if not exists tb1 using stb1 tags(1)") +conn.execute("create table if not exists tb2 using stb1 tags(2)") +conn.execute("create table if not exists tb3 using stb1 tags(3)") + +# create topic +conn.execute("drop topic if exists topic_ctb_column") +conn.execute("create topic if not exists topic_ctb_column as select ts, c1, c2, c3 from stb1") + +# set consumer configure options +conf = TaosTmqConf() +conf.set("group.id", "tg2") +conf.set("td.connect.user", "root") +conf.set("td.connect.pass", "taosdata") +conf.set("enable.auto.commit", "true") +conf.set("msg.with.table.name", "true") + +def tmq_commit_cb_print(tmq, resp, offset, param=None): + print(f"commit: {resp}, tmq: {tmq}, offset: {offset}, param: {param}") + +conf.set_auto_commit_cb(tmq_commit_cb_print, None) + +# build consumer +tmq = conf.new_consumer() + +# build topic list +topic_list = TaosTmqList() +topic_list.append("topic_ctb_column") + +# subscribe consumer +tmq.subscribe(topic_list) + +# check subscriptions +sub_list = tmq.subscription() +print("subscribed topics: ",sub_list) + +# start subscribe +while 1: + res = tmq.poll(1000) + if res: + topic = res.get_topic_name() + vg = res.get_vgroup_id() + db = res.get_db_name() + print(f"topic: {topic}\nvgroup id: {vg}\ndb: {db}") + for row in res: + print(row) + tb = res.get_table_name() + print(f"from table: {tb}") diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 1d63d4970d..8295653db4 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -268,7 +268,7 @@ TODO -TODO +{{#include docs/examples/python/tmq_example.py}} From 392cd9f7f8d6aff404499e6935e2b6df0aa2e0e1 Mon Sep 17 00:00:00 2001 From: plum-lihui Date: Fri, 12 Aug 2022 16:09:25 +0800 Subject: [PATCH 32/47] docs:modify c example code --- docs/zh/07-develop/07-tmq.md | 340 +++++++++++++++++++++++++++++------ 1 file changed, 285 insertions(+), 55 deletions(-) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 1d63d4970d..90865ae200 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -54,7 +54,7 @@ DLL_EXPORT void tmq_conf_destroy(tmq_conf_t *conf); DLL_EXPORT void tmq_conf_set_auto_commit_cb(tmq_conf_t *conf, tmq_commit_cb *cb, void *param); ``` -这些 API 的文档请见 [C/C++ Connector](/reference/connector/cpp),下面介绍一下它们的具体用法(超级表和子表结构请参考“数据建模”一节),完整的示例代码可以在 [tmq.c](https://github.com/taosdata/TDengine/blob/3.0/examples/c/tmq.c) 看到。 +这些 API 的文档请见 [C/C++ Connector](/reference/connector/cpp),下面介绍一下它们的具体用法(超级表和子表结构请参考“数据建模”一节),完整的示例代码请见下面C语言的示例代码。 ## 写入数据 @@ -65,13 +65,9 @@ drop database if exists tmqdb; create database tmqdb; create table tmqdb.stb (ts timestamp, c1 int, c2 float, c3 varchar(16) tags(t1 int, t3 varchar(16)); create table tmqdb.ctb0 using tmqdb.stb tags(0, "subtable0"); -create table tmqdb.ctb1 using tmqdb.stb tags(1, "subtable1"); -create table tmqdb.ctb2 using tmqdb.stb tags(2, "subtable2"); -create table tmqdb.ctb3 using tmqdb.stb tags(3, "subtable3"); +create table tmqdb.ctb1 using tmqdb.stb tags(1, "subtable1"); insert into tmqdb.ctb0 values(now, 0, 0, 'a0')(now+1s, 0, 0, 'a00'); insert into tmqdb.ctb1 values(now, 1, 1, 'a1')(now+1s, 11, 11, 'a11'); -insert into tmqdb.ctb2 values(now, 2, 2, 'a1')(now+1s, 22, 22, 'a22'); -insert into tmqdb.ctb3 values(now, 3, 3, 'a1')(now+1s, 33, 33, 'a33'); ``` ## 创建topic: @@ -133,7 +129,6 @@ TMQ支持多种订阅类型: tmq_t* tmq = tmq_consumer_new(conf, NULL, 0); tmq_conf_destroy(conf); - return tmq; ``` 上述配置中包括consumer group ID,如果多个 consumer 指定的 consumer group ID一样,则自动形成一个consumer group,共享消费进度。 @@ -146,66 +141,23 @@ TMQ支持多种订阅类型: ```sql tmq_list_t* topicList = tmq_list_new(); tmq_list_append(topicList, "topicName"); - return topicList; ``` ## 启动订阅并开始消费 -```sql +``` /* 启动订阅 */ tmq_subscribe(tmq, topicList); tmq_list_destroy(topicList); /* 循环poll消息 */ - int32_t totalRows = 0; - int32_t msgCnt = 0; - int32_t timeOut = 5000; while (running) { TAOS_RES* tmqmsg = tmq_consumer_poll(tmq, timeOut); - if (tmqmsg) { - msgCnt++; - totalRows += msg_process(tmqmsg); - taos_free_result(tmqmsg); - } else { - break; - } - } - - fprintf(stderr, "%d msg consumed, include %d rows\n", msgCnt, totalRows); + msg_process(tmqmsg); + } ``` -这里是一个 **while** 循环,每调用一次tmq_consumer_poll(),获取一个消息,该消息与普通查询返回的结果集完全相同,可以使用相同的解析API完成消息内容的解析: - -```sql - static int32_t msg_process(TAOS_RES* msg) { - char buf[1024]; - int32_t rows = 0; - - const char* topicName = tmq_get_topic_name(msg); - const char* dbName = tmq_get_db_name(msg); - int32_t vgroupId = tmq_get_vgroup_id(msg); - - printf("topic: %s\n", topicName); - printf("db: %s\n", dbName); - printf("vgroup id: %d\n", vgroupId); - - while (1) { - TAOS_ROW row = taos_fetch_row(msg); - if (row == NULL) break; - - TAOS_FIELD* fields = taos_fetch_fields(msg); - int32_t numOfFields = taos_field_count(msg); - int32_t* length = taos_fetch_lengths(msg); - int32_t precision = taos_result_precision(msg); - const char* tbName = tmq_get_table_name(msg); - rows++; - taos_print_row(buf, row, fields, numOfFields); - printf("row content from %s: %s\n", (tbName != NULL ? tbName : "null table"), buf); - } - - return rows; -} -``` +这里是一个 **while** 循环,每调用一次tmq_consumer_poll(),获取一个消息,该消息与普通查询返回的结果集完全相同,可以使用相同的解析API完成消息内容的解析。 ## 结束消费 @@ -252,7 +204,285 @@ TMQ支持多种订阅类型: -TODO + +// A simple demo for asynchronous subscription. +// compile with: +// gcc -o tmq tmq.c -ltaos + + + +#include +#include +#include +#include +#include +#include "taos.h" + +static int running = 1; +static char dbName[64] = "tmqdb"; +static char stbName[64] = "stb"; +static char topicName[64] = "topicname"; + +static int32_t msg_process(TAOS_RES* msg) { + char buf[1024]; + int32_t rows = 0; + + const char* topicName = tmq_get_topic_name(msg); + const char* dbName = tmq_get_db_name(msg); + int32_t vgroupId = tmq_get_vgroup_id(msg); + + printf("topic: %s\n", topicName); + printf("db: %s\n", dbName); + printf("vgroup id: %d\n", vgroupId); + + while (1) { + TAOS_ROW row = taos_fetch_row(msg); + if (row == NULL) break; + + TAOS_FIELD* fields = taos_fetch_fields(msg); + int32_t numOfFields = taos_field_count(msg); + int32_t* length = taos_fetch_lengths(msg); + int32_t precision = taos_result_precision(msg); + const char* tbName = tmq_get_table_name(msg); + rows++; + taos_print_row(buf, row, fields, numOfFields); + printf("row content from %s: %s\n", (tbName != NULL ? tbName : "table null"), buf); + } + + return rows; +} + +static int32_t init_env() { + TAOS* pConn = taos_connect("localhost", "root", "taosdata", NULL, 0); + if (pConn == NULL) { + return -1; + } + + TAOS_RES* pRes; + // drop database if exists + printf("create database\n"); + pRes = taos_query(pConn, "drop database if exists tmqdb"); + if (taos_errno(pRes) != 0) { + printf("error in drop tmqdb, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + // create database + pRes = taos_query(pConn, "create database tmqdb"); + if (taos_errno(pRes) != 0) { + printf("error in create tmqdb, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + // create super table + printf("create super table\n"); + pRes = taos_query( + pConn, "create table tmqdb.stb (ts timestamp, c1 int, c2 float, c3 varchar(16)) tags(t1 int, t3 varchar(16))"); + if (taos_errno(pRes) != 0) { + printf("failed to create super table stb, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + // create sub tables + printf("create sub tables\n"); + pRes = taos_query(pConn, "create table tmqdb.ctb0 using tmqdb.stb tags(0, 'subtable0')"); + if (taos_errno(pRes) != 0) { + printf("failed to create super table ctb0, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "create table tmqdb.ctb1 using tmqdb.stb tags(1, 'subtable1')"); + if (taos_errno(pRes) != 0) { + printf("failed to create super table ctb1, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "create table tmqdb.ctb2 using tmqdb.stb tags(2, 'subtable2')"); + if (taos_errno(pRes) != 0) { + printf("failed to create super table ctb2, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "create table tmqdb.ctb3 using tmqdb.stb tags(3, 'subtable3')"); + if (taos_errno(pRes) != 0) { + printf("failed to create super table ctb3, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + // insert data + printf("insert data into sub tables\n"); + pRes = taos_query(pConn, "insert into tmqdb.ctb0 values(now, 0, 0, 'a0')(now+1s, 0, 0, 'a00')"); + if (taos_errno(pRes) != 0) { + printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "insert into tmqdb.ctb1 values(now, 1, 1, 'a1')(now+1s, 11, 11, 'a11')"); + if (taos_errno(pRes) != 0) { + printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "insert into tmqdb.ctb2 values(now, 2, 2, 'a1')(now+1s, 22, 22, 'a22')"); + if (taos_errno(pRes) != 0) { + printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "insert into tmqdb.ctb3 values(now, 3, 3, 'a1')(now+1s, 33, 33, 'a33')"); + if (taos_errno(pRes) != 0) { + printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + taos_close(pConn); + return 0; +} + +int32_t create_topic() { + printf("create topic\n"); + TAOS_RES* pRes; + TAOS* pConn = taos_connect("localhost", "root", "taosdata", NULL, 0); + if (pConn == NULL) { + return -1; + } + + pRes = taos_query(pConn, "use tmqdb"); + if (taos_errno(pRes) != 0) { + printf("error in use tmqdb, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + pRes = taos_query(pConn, "create topic topicname as select ts, c1, c2, c3 from tmqdb.stb where c1 > 1"); + if (taos_errno(pRes) != 0) { + printf("failed to create topic topicname, reason:%s\n", taos_errstr(pRes)); + return -1; + } + taos_free_result(pRes); + + taos_close(pConn); + return 0; +} + +void tmq_commit_cb_print(tmq_t* tmq, int32_t code, void* param) { + printf("tmq_commit_cb_print() code: %d, tmq: %p, param: %p\n", code, tmq, param); +} + +tmq_t* build_consumer() { + tmq_conf_res_t code; + tmq_conf_t* conf = tmq_conf_new(); + code = tmq_conf_set(conf, "enable.auto.commit", "true"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "auto.commit.interval.ms", "1000"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "group.id", "cgrpName"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "client.id", "user defined name"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "td.connect.user", "root"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "td.connect.pass", "taosdata"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "auto.offset.reset", "earliest"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "experimental.snapshot.enable", "true"); + if (TMQ_CONF_OK != code) return NULL; + code = tmq_conf_set(conf, "msg.with.table.name", "true"); + if (TMQ_CONF_OK != code) return NULL; + + tmq_conf_set_auto_commit_cb(conf, tmq_commit_cb_print, NULL); + + tmq_t* tmq = tmq_consumer_new(conf, NULL, 0); + tmq_conf_destroy(conf); + return tmq; +} + +tmq_list_t* build_topic_list() { + tmq_list_t* topicList = tmq_list_new(); + int32_t code = tmq_list_append(topicList, "topicname"); + if (code) { + return NULL; + } + return topicList; +} + +void basic_consume_loop(tmq_t* tmq, tmq_list_t* topicList) { + int32_t code; + + if ((code = tmq_subscribe(tmq, topicList))) { + fprintf(stderr, "%% Failed to tmq_subscribe(): %s\n", tmq_err2str(code)); + return; + } + + int32_t totalRows = 0; + int32_t msgCnt = 0; + int32_t timeout = 5000; + while (running) { + TAOS_RES* tmqmsg = tmq_consumer_poll(tmq, timeout); + if (tmqmsg) { + msgCnt++; + totalRows += msg_process(tmqmsg); + taos_free_result(tmqmsg); + /*} else {*/ + /*break;*/ + } + } + + fprintf(stderr, "%d msg consumed, include %d rows\n", msgCnt, totalRows); +} + +int main(int argc, char* argv[]) { + int32_t code; + + if (init_env() < 0) { + return -1; + } + + if (create_topic() < 0) { + return -1; + } + + tmq_t* tmq = build_consumer(); + if (NULL == tmq) { + fprintf(stderr, "%% build_consumer() fail!\n"); + return -1; + } + + tmq_list_t* topic_list = build_topic_list(); + if (NULL == topic_list) { + return -1; + } + + basic_consume_loop(tmq, topic_list); + + code = tmq_unsubscribe(tmq); + if (code) { + fprintf(stderr, "%% Failed to unsubscribe: %s\n", tmq_err2str(code)); + } else { + fprintf(stderr, "%% unsubscribe\n"); + } + + code = tmq_consumer_close(tmq); + if (code) { + fprintf(stderr, "%% Failed to close consumer: %s\n", tmq_err2str(code)); + } else { + fprintf(stderr, "%% Consumer closed\n"); + } + + return 0; +} From c7dc747be54037f76b50b9521791be6b758b379a Mon Sep 17 00:00:00 2001 From: wade zhang <95411902+gccgdb1234@users.noreply.github.com> Date: Fri, 12 Aug 2022 16:11:25 +0800 Subject: [PATCH 33/47] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index dcb9f4416a..e34dc583c8 100644 --- a/README.md +++ b/README.md @@ -20,7 +20,7 @@ English | [简体中文](README-CN.md) | We are hiring, check [here](https://tde # What is TDengine? -TDengine is an open source, cloud native time-series database optimized for Internet of Things (IoT), Connected Cars, and Industrial IoT. It enables efficient, real-time data ingestion, processing, and monitoring of TB and even PB scale data per day, generated by billions of sensors and data collectors. TDengine differentiates itself from other TSDBs with the following advantages.: +TDengine is an open source, high performance, cloud native time-series database optimized for Internet of Things (IoT), Connected Cars, and Industrial IoT. It enables efficient, real-time data ingestion, processing, and monitoring of TB and even PB scale data per day, generated by billions of sensors and data collectors. TDengine differentiates itself from other TSDBs with the following advantages.: - High-Performance: TDengine is the only time-series database to solve the high cardinality issue to support billions of data collection points while out performing other time-series databases for data ingestion, querying and data compression. From db7768fed51fa192c27faca573bfa972d1bf8da7 Mon Sep 17 00:00:00 2001 From: wade zhang <95411902+gccgdb1234@users.noreply.github.com> Date: Fri, 12 Aug 2022 16:15:41 +0800 Subject: [PATCH 34/47] Update 07-tmq.md --- docs/zh/07-develop/07-tmq.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 90865ae200..72f3714a10 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -205,6 +205,7 @@ TMQ支持多种订阅类型: +```c // A simple demo for asynchronous subscription. // compile with: // gcc -o tmq tmq.c -ltaos @@ -483,6 +484,7 @@ int main(int argc, char* argv[]) { return 0; } +``` From 5d471bf6855f6d0e11769abc8605264976f9074f Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 16:27:26 +0800 Subject: [PATCH 35/47] doc: replace c sample with #include --- docs/zh/07-develop/07-tmq.md | 280 +---------------------------------- 1 file changed, 2 insertions(+), 278 deletions(-) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 72f3714a10..3ff90d242d 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -206,288 +206,12 @@ TMQ支持多种订阅类型: ```c -// A simple demo for asynchronous subscription. -// compile with: -// gcc -o tmq tmq.c -ltaos - - - -#include -#include -#include -#include -#include -#include "taos.h" - -static int running = 1; -static char dbName[64] = "tmqdb"; -static char stbName[64] = "stb"; -static char topicName[64] = "topicname"; - -static int32_t msg_process(TAOS_RES* msg) { - char buf[1024]; - int32_t rows = 0; - - const char* topicName = tmq_get_topic_name(msg); - const char* dbName = tmq_get_db_name(msg); - int32_t vgroupId = tmq_get_vgroup_id(msg); - - printf("topic: %s\n", topicName); - printf("db: %s\n", dbName); - printf("vgroup id: %d\n", vgroupId); - - while (1) { - TAOS_ROW row = taos_fetch_row(msg); - if (row == NULL) break; - - TAOS_FIELD* fields = taos_fetch_fields(msg); - int32_t numOfFields = taos_field_count(msg); - int32_t* length = taos_fetch_lengths(msg); - int32_t precision = taos_result_precision(msg); - const char* tbName = tmq_get_table_name(msg); - rows++; - taos_print_row(buf, row, fields, numOfFields); - printf("row content from %s: %s\n", (tbName != NULL ? tbName : "table null"), buf); - } - - return rows; -} - -static int32_t init_env() { - TAOS* pConn = taos_connect("localhost", "root", "taosdata", NULL, 0); - if (pConn == NULL) { - return -1; - } - - TAOS_RES* pRes; - // drop database if exists - printf("create database\n"); - pRes = taos_query(pConn, "drop database if exists tmqdb"); - if (taos_errno(pRes) != 0) { - printf("error in drop tmqdb, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - // create database - pRes = taos_query(pConn, "create database tmqdb"); - if (taos_errno(pRes) != 0) { - printf("error in create tmqdb, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - // create super table - printf("create super table\n"); - pRes = taos_query( - pConn, "create table tmqdb.stb (ts timestamp, c1 int, c2 float, c3 varchar(16)) tags(t1 int, t3 varchar(16))"); - if (taos_errno(pRes) != 0) { - printf("failed to create super table stb, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - // create sub tables - printf("create sub tables\n"); - pRes = taos_query(pConn, "create table tmqdb.ctb0 using tmqdb.stb tags(0, 'subtable0')"); - if (taos_errno(pRes) != 0) { - printf("failed to create super table ctb0, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "create table tmqdb.ctb1 using tmqdb.stb tags(1, 'subtable1')"); - if (taos_errno(pRes) != 0) { - printf("failed to create super table ctb1, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "create table tmqdb.ctb2 using tmqdb.stb tags(2, 'subtable2')"); - if (taos_errno(pRes) != 0) { - printf("failed to create super table ctb2, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "create table tmqdb.ctb3 using tmqdb.stb tags(3, 'subtable3')"); - if (taos_errno(pRes) != 0) { - printf("failed to create super table ctb3, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - // insert data - printf("insert data into sub tables\n"); - pRes = taos_query(pConn, "insert into tmqdb.ctb0 values(now, 0, 0, 'a0')(now+1s, 0, 0, 'a00')"); - if (taos_errno(pRes) != 0) { - printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "insert into tmqdb.ctb1 values(now, 1, 1, 'a1')(now+1s, 11, 11, 'a11')"); - if (taos_errno(pRes) != 0) { - printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "insert into tmqdb.ctb2 values(now, 2, 2, 'a1')(now+1s, 22, 22, 'a22')"); - if (taos_errno(pRes) != 0) { - printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "insert into tmqdb.ctb3 values(now, 3, 3, 'a1')(now+1s, 33, 33, 'a33')"); - if (taos_errno(pRes) != 0) { - printf("failed to insert into ctb0, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - taos_close(pConn); - return 0; -} - -int32_t create_topic() { - printf("create topic\n"); - TAOS_RES* pRes; - TAOS* pConn = taos_connect("localhost", "root", "taosdata", NULL, 0); - if (pConn == NULL) { - return -1; - } - - pRes = taos_query(pConn, "use tmqdb"); - if (taos_errno(pRes) != 0) { - printf("error in use tmqdb, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - pRes = taos_query(pConn, "create topic topicname as select ts, c1, c2, c3 from tmqdb.stb where c1 > 1"); - if (taos_errno(pRes) != 0) { - printf("failed to create topic topicname, reason:%s\n", taos_errstr(pRes)); - return -1; - } - taos_free_result(pRes); - - taos_close(pConn); - return 0; -} - -void tmq_commit_cb_print(tmq_t* tmq, int32_t code, void* param) { - printf("tmq_commit_cb_print() code: %d, tmq: %p, param: %p\n", code, tmq, param); -} - -tmq_t* build_consumer() { - tmq_conf_res_t code; - tmq_conf_t* conf = tmq_conf_new(); - code = tmq_conf_set(conf, "enable.auto.commit", "true"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "auto.commit.interval.ms", "1000"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "group.id", "cgrpName"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "client.id", "user defined name"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "td.connect.user", "root"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "td.connect.pass", "taosdata"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "auto.offset.reset", "earliest"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "experimental.snapshot.enable", "true"); - if (TMQ_CONF_OK != code) return NULL; - code = tmq_conf_set(conf, "msg.with.table.name", "true"); - if (TMQ_CONF_OK != code) return NULL; - - tmq_conf_set_auto_commit_cb(conf, tmq_commit_cb_print, NULL); - - tmq_t* tmq = tmq_consumer_new(conf, NULL, 0); - tmq_conf_destroy(conf); - return tmq; -} - -tmq_list_t* build_topic_list() { - tmq_list_t* topicList = tmq_list_new(); - int32_t code = tmq_list_append(topicList, "topicname"); - if (code) { - return NULL; - } - return topicList; -} - -void basic_consume_loop(tmq_t* tmq, tmq_list_t* topicList) { - int32_t code; - - if ((code = tmq_subscribe(tmq, topicList))) { - fprintf(stderr, "%% Failed to tmq_subscribe(): %s\n", tmq_err2str(code)); - return; - } - - int32_t totalRows = 0; - int32_t msgCnt = 0; - int32_t timeout = 5000; - while (running) { - TAOS_RES* tmqmsg = tmq_consumer_poll(tmq, timeout); - if (tmqmsg) { - msgCnt++; - totalRows += msg_process(tmqmsg); - taos_free_result(tmqmsg); - /*} else {*/ - /*break;*/ - } - } - - fprintf(stderr, "%d msg consumed, include %d rows\n", msgCnt, totalRows); -} - -int main(int argc, char* argv[]) { - int32_t code; - - if (init_env() < 0) { - return -1; - } - - if (create_topic() < 0) { - return -1; - } - - tmq_t* tmq = build_consumer(); - if (NULL == tmq) { - fprintf(stderr, "%% build_consumer() fail!\n"); - return -1; - } - - tmq_list_t* topic_list = build_topic_list(); - if (NULL == topic_list) { - return -1; - } - - basic_consume_loop(tmq, topic_list); - - code = tmq_unsubscribe(tmq); - if (code) { - fprintf(stderr, "%% Failed to unsubscribe: %s\n", tmq_err2str(code)); - } else { - fprintf(stderr, "%% unsubscribe\n"); - } - - code = tmq_consumer_close(tmq); - if (code) { - fprintf(stderr, "%% Failed to close consumer: %s\n", tmq_err2str(code)); - } else { - fprintf(stderr, "%% Consumer closed\n"); - } - - return 0; -} +{{#include examples/c/tmq.c}} ``` + TODO From 1d9331e257f69090343cb645bb1e1ff0d7e3425a Mon Sep 17 00:00:00 2001 From: Shengliang Guan Date: Fri, 12 Aug 2022 16:32:03 +0800 Subject: [PATCH 36/47] fix: deadlock of mnode if its state changed --- source/dnode/mnode/impl/inc/mndInt.h | 3 ++- source/dnode/mnode/impl/src/mndSync.c | 17 +++++++++++++++++ 2 files changed, 19 insertions(+), 1 deletion(-) diff --git a/source/dnode/mnode/impl/inc/mndInt.h b/source/dnode/mnode/impl/inc/mndInt.h index f72b69a7de..505a1384ef 100644 --- a/source/dnode/mnode/impl/inc/mndInt.h +++ b/source/dnode/mnode/impl/inc/mndInt.h @@ -87,10 +87,11 @@ typedef struct { typedef struct { tsem_t syncSem; int64_t sync; - bool standby; SReplica replica; int32_t errCode; int32_t transId; + SRWLatch lock; + int8_t standby; int8_t leaderTransferFinish; } SSyncMgmt; diff --git a/source/dnode/mnode/impl/src/mndSync.c b/source/dnode/mnode/impl/src/mndSync.c index 6a78d2f018..03e5c2b3a2 100644 --- a/source/dnode/mnode/impl/src/mndSync.c +++ b/source/dnode/mnode/impl/src/mndSync.c @@ -60,15 +60,19 @@ void mndSyncCommitMsg(struct SSyncFSM *pFsm, const SRpcMsg *pMsg, SFsmCbMeta cbM sdbSetApplyInfo(pMnode->pSdb, cbMeta.index, cbMeta.term, cbMeta.lastConfigIndex); } + taosRLockLatch(&pMgmt->lock); if (transId <= 0) { + taosRUnLockLatch(&pMgmt->lock); mError("trans:%d, invalid commit msg", transId); } else if (transId == pMgmt->transId) { + taosRUnLockLatch(&pMgmt->lock); if (pMgmt->errCode != 0) { mError("trans:%d, failed to propose since %s", transId, tstrerror(pMgmt->errCode)); } pMgmt->transId = 0; tsem_post(&pMgmt->syncSem); } else { + taosRUnLockLatch(&pMgmt->lock); STrans *pTrans = mndAcquireTrans(pMnode, transId); if (pTrans != NULL) { mDebug("trans:%d, execute in mnode which not leader", transId); @@ -115,6 +119,7 @@ void mndReConfig(struct SSyncFSM *pFsm, const SRpcMsg *pMsg, SReConfigCbMeta cbM mInfo("trans:-1, sync reconfig is proposed, saved:%d code:0x%x, index:%" PRId64 " term:%" PRId64, pMgmt->transId, cbMeta.code, cbMeta.index, cbMeta.term); + taosWLockLatch(&pMgmt->lock); if (pMgmt->transId == -1) { if (pMgmt->errCode != 0) { mError("trans:-1, failed to propose sync reconfig since %s", tstrerror(pMgmt->errCode)); @@ -122,6 +127,7 @@ void mndReConfig(struct SSyncFSM *pFsm, const SRpcMsg *pMsg, SReConfigCbMeta cbM pMgmt->transId = 0; tsem_post(&pMgmt->syncSem); } + taosWUnLockLatch(&pMgmt->lock); } int32_t mndSnapshotStartRead(struct SSyncFSM *pFsm, void *pParam, void **ppReader) { @@ -170,20 +176,24 @@ static void mndBecomeFollower(struct SSyncFSM *pFsm) { SMnode *pMnode = pFsm->data; mDebug("vgId:1, become follower"); + taosWLockLatch(&pMnode->syncMgmt.lock); if (pMnode->syncMgmt.transId != 0) { pMnode->syncMgmt.transId = 0; tsem_post(&pMnode->syncMgmt.syncSem); } + taosWUnLockLatch(&pMnode->syncMgmt.lock); } static void mndBecomeLeader(struct SSyncFSM *pFsm) { mDebug("vgId:1, become leader"); SMnode *pMnode = pFsm->data; + taosWLockLatch(&pMnode->syncMgmt.lock); if (pMnode->syncMgmt.transId != 0) { pMnode->syncMgmt.transId = 0; tsem_post(&pMnode->syncMgmt.syncSem); } + taosWUnLockLatch(&pMnode->syncMgmt.lock); } SSyncFSM *mndSyncMakeFsm(SMnode *pMnode) { @@ -210,6 +220,8 @@ SSyncFSM *mndSyncMakeFsm(SMnode *pMnode) { int32_t mndInitSync(SMnode *pMnode) { SSyncMgmt *pMgmt = &pMnode->syncMgmt; + taosInitRWLatch(&pMgmt->lock); + pMgmt->transId = 0; SSyncInfo syncInfo = {.vgId = 1, .FpSendMsg = mndSyncSendMsg, .FpEqMsg = mndSyncEqMsg}; snprintf(syncInfo.path, sizeof(syncInfo.path), "%s%ssync", pMnode->path, TD_DIRSEP); @@ -262,11 +274,14 @@ int32_t mndSyncPropose(SMnode *pMnode, SSdbRaw *pRaw, int32_t transId) { memcpy(req.pCont, pRaw, req.contLen); pMgmt->errCode = 0; + taosWLockLatch(&pMgmt->lock); pMgmt->transId = transId; + taosWUnLockLatch(&pMgmt->lock); mTrace("trans:%d, will be proposed", pMgmt->transId); const bool isWeak = false; int32_t code = syncPropose(pMgmt->sync, &req, isWeak); + if (code == 0) { tsem_wait(&pMgmt->syncSem); } else if (code == -1 && terrno == TSDB_CODE_SYN_NOT_LEADER) { @@ -294,10 +309,12 @@ void mndSyncStart(SMnode *pMnode) { } void mndSyncStop(SMnode *pMnode) { + taosWLockLatch(&pMnode->syncMgmt.lock); if (pMnode->syncMgmt.transId != 0) { pMnode->syncMgmt.transId = 0; tsem_post(&pMnode->syncMgmt.syncSem); } + taosWUnLockLatch(&pMnode->syncMgmt.lock); } bool mndIsMaster(SMnode *pMnode) { From 4f90578270761d1fe4b4d057c4635a0b22800125 Mon Sep 17 00:00:00 2001 From: Shengliang Guan Date: Fri, 12 Aug 2022 16:32:11 +0800 Subject: [PATCH 37/47] fix: deadlock of vnode if its state changed --- source/dnode/vnode/src/inc/vnodeInt.h | 3 ++- source/dnode/vnode/src/vnd/vnodeOpen.c | 3 ++- source/dnode/vnode/src/vnd/vnodeSync.c | 24 +++++++++++++++++++----- 3 files changed, 23 insertions(+), 7 deletions(-) diff --git a/source/dnode/vnode/src/inc/vnodeInt.h b/source/dnode/vnode/src/inc/vnodeInt.h index 43bb92ec23..700c6cf8a3 100644 --- a/source/dnode/vnode/src/inc/vnodeInt.h +++ b/source/dnode/vnode/src/inc/vnodeInt.h @@ -308,7 +308,8 @@ struct SVnode { SSink* pSink; tsem_t canCommit; int64_t sync; - int32_t blockCount; + SRWLatch lock; + bool blocked; bool restored; tsem_t syncSem; SQHandle* pQuery; diff --git a/source/dnode/vnode/src/vnd/vnodeOpen.c b/source/dnode/vnode/src/vnd/vnodeOpen.c index 1ba74ac3be..4ee5c4760c 100644 --- a/source/dnode/vnode/src/vnd/vnodeOpen.c +++ b/source/dnode/vnode/src/vnd/vnodeOpen.c @@ -85,7 +85,8 @@ SVnode *vnodeOpen(const char *path, STfs *pTfs, SMsgCb msgCb) { pVnode->state.commitTerm = info.state.commitTerm; pVnode->pTfs = pTfs; pVnode->msgCb = msgCb; - pVnode->blockCount = 0; + taosInitRWLatch(&pVnode->lock); + pVnode->blocked = false; tsem_init(&pVnode->syncSem, 0, 0); tsem_init(&(pVnode->canCommit), 0, 1); diff --git a/source/dnode/vnode/src/vnd/vnodeSync.c b/source/dnode/vnode/src/vnd/vnodeSync.c index 7ac124fdd3..50d32f5f5e 100644 --- a/source/dnode/vnode/src/vnd/vnodeSync.c +++ b/source/dnode/vnode/src/vnd/vnodeSync.c @@ -28,20 +28,28 @@ static inline bool vnodeIsMsgWeak(tmsg_t type) { return false; } static inline void vnodeWaitBlockMsg(SVnode *pVnode, const SRpcMsg *pMsg) { if (vnodeIsMsgBlock(pMsg->msgType)) { const STraceId *trace = &pMsg->info.traceId; - vGTrace("vgId:%d, msg:%p wait block, type:%s", pVnode->config.vgId, pMsg, TMSG_INFO(pMsg->msgType)); - pVnode->blockCount = 1; - tsem_wait(&pVnode->syncSem); + taosWLockLatch(&pVnode->lock); + if (!pVnode->blocked) { + vGTrace("vgId:%d, msg:%p wait block, type:%s", pVnode->config.vgId, pMsg, TMSG_INFO(pMsg->msgType)); + pVnode->blocked = true; + taosWUnLockLatch(&pVnode->lock); + tsem_wait(&pVnode->syncSem); + } else { + taosWUnLockLatch(&pVnode->lock); + } } } static inline void vnodePostBlockMsg(SVnode *pVnode, const SRpcMsg *pMsg) { if (vnodeIsMsgBlock(pMsg->msgType)) { const STraceId *trace = &pMsg->info.traceId; - if (pVnode->blockCount) { + taosWLockLatch(&pVnode->lock); + if (pVnode->blocked) { vGTrace("vgId:%d, msg:%p post block, type:%s", pVnode->config.vgId, pMsg, TMSG_INFO(pMsg->msgType)); - pVnode->blockCount = 0; + pVnode->blocked = false; tsem_post(&pVnode->syncSem); } + taosWUnLockLatch(&pVnode->lock); } } @@ -677,6 +685,12 @@ static void vnodeBecomeFollower(struct SSyncFSM *pFsm) { vDebug("vgId:%d, become follower", pVnode->config.vgId); // clear old leader resource + taosWLockLatch(&pVnode->lock); + if (pVnode->blocked) { + pVnode->blocked = false; + tsem_post(&pVnode->syncSem); + } + taosWUnLockLatch(&pVnode->lock); } static void vnodeBecomeLeader(struct SSyncFSM *pFsm) { From 76d02583dd89dd089416d20ee4f5587f5a335e2a Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 16:33:47 +0800 Subject: [PATCH 38/47] doc: fix syntax error --- docs/zh/07-develop/07-tmq.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index f4dd1cf3ae..372d458c36 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -224,7 +224,11 @@ TODO + +```python {{#include docs/examples/python/tmq_example.py}} +``` + From 8ed6342eb4bef0a350310dcacbcbd66f13e07537 Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 16:53:57 +0800 Subject: [PATCH 39/47] doc: correct download link --- docs/zh/05-get-started/03-package.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/docs/zh/05-get-started/03-package.md b/docs/zh/05-get-started/03-package.md index 1ff24559f7..63698aab50 100644 --- a/docs/zh/05-get-started/03-package.md +++ b/docs/zh/05-get-started/03-package.md @@ -46,7 +46,7 @@ apt-get 方式只适用于 Debian 或 Ubuntu 系统 -1. 从官网下载获得 deb 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.deb; +1. 从 [发布历史页面](../../releases) 下载获得 deb 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.deb; 2. 进入到 TDengine-server-3.0.0.0-Linux-x64.deb 安装包所在目录,执行如下的安装命令: ```bash @@ -57,7 +57,7 @@ sudo dpkg -i TDengine-server-3.0.0.0-Linux-x64.deb -1. 从官网下载获得 rpm 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.rpm; +1. 从 [发布历史页面](../../releases) 下载获得 rpm 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.rpm; 2. 进入到 TDengine-server-3.0.0.0-Linux-x64.rpm 安装包所在目录,执行如下的安装命令: ```bash @@ -68,7 +68,7 @@ sudo rpm -ivh TDengine-server-3.0.0.0-Linux-x64.rpm -1. 从官网下载获得 tar.gz 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.tar.gz; +1. 从 [发布历史页面](../../releases) 下载获得 tar.gz 安装包,例如 TDengine-server-3.0.0.0-Linux-x64.tar.gz; 2. 进入到 TDengine-server-3.0.0.0-Linux-x64.tar.gz 安装包所在目录,先解压文件后,进入子目录,执行其中的 install.sh 安装脚本: ```bash @@ -90,7 +90,7 @@ install.sh 安装脚本在执行过程中,会通过命令行交互界面询问 -1. 从官网下载获得 exe 安装程序,例如 TDengine-server-3.0.0.0-Windows-x64.exe; +1. 从 [发布历史页面](../../releases) 下载获得 exe 安装程序,例如 TDengine-server-3.0.0.0-Windows-x64.exe; 2. 运行 TDengine-server-3.0.0.0-Windows-x64.exe 来安装 TDengine。 From 47c9309a2cfee1fb9dd6e4acc56ad4db6ece2331 Mon Sep 17 00:00:00 2001 From: jiajingbin Date: Fri, 12 Aug 2022 16:57:37 +0800 Subject: [PATCH 40/47] docs: update 06-stream.md for stream-computing --- docs/zh/07-develop/06-stream.md | 111 +++++++++++++------------------- 1 file changed, 44 insertions(+), 67 deletions(-) diff --git a/docs/zh/07-develop/06-stream.md b/docs/zh/07-develop/06-stream.md index dbf8684008..5217fa8389 100644 --- a/docs/zh/07-develop/06-stream.md +++ b/docs/zh/07-develop/06-stream.md @@ -29,100 +29,77 @@ stream_options: { 首先准备数据,完成建库、建一张超级表和多张子表操作 ```sql -drop database if exists stream_db; -create database stream_db; +DROP DATABASE IF EXISTS power; +CREATE DATABASE power; +USE power; -create stable stream_db.meters (ts timestamp, current float, voltage int) TAGS (location varchar(64), groupId int); +CREATE STABLE meters (ts timestamp, current float, voltage int, phase float) TAGS (location binary(64), groupId int); -create table stream_db.d1001 using stream_db.meters tags("beijing", 1); -create table stream_db.d1002 using stream_db.meters tags("guangzhou", 2); -create table stream_db.d1003 using stream_db.meters tags("shanghai", 3); +CREATE TABLE d1001 USING meters TAGS ("California.SanFrancisco", 2); +CREATE TABLE d1002 USING meters TAGS ("California.SanFrancisco", 3); +CREATE TABLE d1003 USING meters TAGS ("California.LosAngeles", 2); +CREATE TABLE d1004 USING meters TAGS ("California.LosAngeles", 3); ``` ### 创建流 ```sql -create stream stream1 into stream_db.stream1_output_stb as select _wstart as start, _wend as end, max(current) as max_current from stream_db.meters where voltage <= 220 and ts > now - 12h interval (1h); +create stream current_stream into current_stream_output_stb as select _wstart as start, _wend as end, max(current) as max_current from meters where voltage <= 220 and ts > now - 12h interval (1h); ``` ### 写入数据 ```sql -insert into stream_db.d1001 values(now-14h, 10.3, 210); -insert into stream_db.d1001 values(now-13h, 13.5, 216); -insert into stream_db.d1001 values(now-12h, 12.5, 219); -insert into stream_db.d1002 values(now-11h, 14.7, 221); -insert into stream_db.d1002 values(now-10h, 10.5, 218); -insert into stream_db.d1002 values(now-9h, 11.2, 220); -insert into stream_db.d1003 values(now-8h, 11.5, 217); -insert into stream_db.d1003 values(now-7h, 12.3, 227); -insert into stream_db.d1003 values(now-6h, 12.3, 215); +insert into d1001 values(now-13h, 10.30000, 219, 0.31000); +insert into d1001 values(now-11h, 12.60000, 218, 0.33000); +insert into d1001 values(now-10h, 12.30000, 221, 0.31000); +insert into d1002 values(now-9h, 10.30000, 218, 0.25000); +insert into d1003 values(now-8h, 11.80000, 221, 0.28000); +insert into d1003 values(now-7h, 13.40000, 223, 0.29000); +insert into d1004 values(now-6h, 10.80000, 223, 0.29000); +insert into d1004 values(now-5h, 11.50000, 221, 0.35000); ``` ### 查询以观查结果 + ```sql -taos> select * from stream_db.stream1_output_stb; - start | end | max_current | group_id | -=================================================================================================== - 2022-08-09 14:00:00.000 | 2022-08-09 15:00:00.000 | 10.50000 | 0 | - 2022-08-09 15:00:00.000 | 2022-08-09 16:00:00.000 | 11.20000 | 0 | - 2022-08-09 16:00:00.000 | 2022-08-09 17:00:00.000 | 11.50000 | 0 | - 2022-08-09 18:00:00.000 | 2022-08-09 19:00:00.000 | 12.30000 | 0 | -Query OK, 4 rows in database (0.012033s) +taos> select start, end, max_current from current_stream_output_stb; + start | end | max_current | +=========================================================================== + 2022-08-12 04:00:00.000 | 2022-08-12 05:00:00.000 | 12.60000 | + 2022-08-12 06:00:00.000 | 2022-08-12 07:00:00.000 | 10.30000 | +Query OK, 2 rows in database (0.009580s) ``` ## 示例二 -某运营商平台要采集机房所有服务器的系统资源指标,包含 cpu、内存、网络延迟等,采集后需要对数据进行四舍五入运算,将地域和服务器名以下划线拼接,然后将结果按时间排序并以服务器名分组输出到新的数据表中。 + +依然以示例一中的数据为基础,我们已经采集到了每个智能电表的电流和电压数据,现在要求出功率,并将地域和电表名以符号 "." 拼接,然后以电表名称分组输出到新的数据表中。 ### 创建 DB 和原始数据表 -首先准备数据,完成建库、建一张超级表和多张子表操作 -```sql -drop database if exists stream_db; -create database stream_db; - -create stable stream_db.idc (ts timestamp, cpu float, mem float, latency float) TAGS (location varchar(64), groupId int); - -create table stream_db.server01 using stream_db.idc tags("beijing", 1); -create table stream_db.server02 using stream_db.idc tags("shanghai", 2); -create table stream_db.server03 using stream_db.idc tags("beijing", 2); -create table stream_db.server04 using stream_db.idc tags("tianjin", 3); -create table stream_db.server05 using stream_db.idc tags("shanghai", 1); -``` +参考示例一 [创建 DB 和原始数据表](#创建-db-和原始数据表) ### 创建流 ```sql -create stream stream2 into stream_db.stream2_output_stb as select ts, concat_ws("_", location, tbname) as server_location, round(cpu) as cpu, round(mem) as mem, round(latency) as latency from stream_db.idc partition by tbname order by ts; +create stream power_stream into power_stream_output_stb as select ts, concat_ws(".", location, tbname) as meter_location, current*voltage as meter_power from meters partition by tbname; ``` ### 写入数据 -```sql -insert into stream_db.server01 values(now-14h, 50.9, 654.8, 23.11); -insert into stream_db.server01 values(now-13h, 13.5, 221.2, 11.22); -insert into stream_db.server02 values(now-12h, 154.7, 218.3, 22.33); -insert into stream_db.server02 values(now-11h, 120.5, 111.5, 5.55); -insert into stream_db.server03 values(now-10h, 101.5, 125.6, 5.99); -insert into stream_db.server03 values(now-9h, 12.3, 165.6, 6.02); -insert into stream_db.server04 values(now-8h, 160.9, 120.7, 43.51); -insert into stream_db.server04 values(now-7h, 240.9, 520.7, 54.55); -insert into stream_db.server05 values(now-6h, 190.9, 320.7, 55.43); -insert into stream_db.server05 values(now-5h, 110.9, 600.7, 35.54); -``` + +参考示例一 [写入数据](#写入数据) + ### 查询以观查结果 ```sql -taos> select ts, server_location, cpu, mem, latency from stream_db.stream2_output_stb; - ts | server_location | cpu | mem | latency | -================================================================================================================================ - 2022-08-09 21:24:56.785 | beijing_server01 | 51.00000 | 655.00000 | 23.00000 | - 2022-08-09 22:24:56.795 | beijing_server01 | 14.00000 | 221.00000 | 11.00000 | - 2022-08-09 23:24:56.806 | shanghai_server02 | 155.00000 | 218.00000 | 22.00000 | - 2022-08-10 00:24:56.815 | shanghai_server02 | 121.00000 | 112.00000 | 6.00000 | - 2022-08-10 01:24:56.826 | beijing_server03 | 102.00000 | 126.00000 | 6.00000 | - 2022-08-10 02:24:56.838 | beijing_server03 | 12.00000 | 166.00000 | 6.00000 | - 2022-08-10 03:24:56.846 | tianjin_server04 | 161.00000 | 121.00000 | 44.00000 | - 2022-08-10 04:24:56.853 | tianjin_server04 | 241.00000 | 521.00000 | 55.00000 | - 2022-08-10 05:24:56.866 | shanghai_server05 | 191.00000 | 321.00000 | 55.00000 | - 2022-08-10 06:24:57.301 | shanghai_server05 | 111.00000 | 601.00000 | 36.00000 | -Query OK, 10 rows in database (0.022950s) -``` - +taos> select ts, meter_location, meter_power from power_stream_output_stb; + ts | meter_location | meter_power | +======================================================================================= + 2022-08-12 07:44:47.817 | California.SanFrancisco.d1002 | 2245.400041580 | + 2022-08-12 08:44:47.826 | California.LosAngeles.d1003 | 2607.800042152 | + 2022-08-12 09:44:47.833 | California.LosAngeles.d1003 | 2988.199914932 | + 2022-08-12 03:44:47.791 | California.SanFrancisco.d1001 | 2255.700041771 | + 2022-08-12 05:44:47.800 | California.SanFrancisco.d1001 | 2746.800083160 | + 2022-08-12 06:44:47.809 | California.SanFrancisco.d1001 | 2718.300042152 | + 2022-08-12 10:44:47.840 | California.LosAngeles.d1004 | 2408.400042534 | + 2022-08-12 11:44:48.379 | California.LosAngeles.d1004 | 2541.500000000 | +Query OK, 8 rows in database (0.014788s) +``` \ No newline at end of file From 1d7c2ac9e3a2eb6f22e6d4d815d13139645dfd42 Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 17:10:26 +0800 Subject: [PATCH 41/47] fix: fix dumplicated ctg callback issue --- source/libs/catalog/src/ctgAsync.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/source/libs/catalog/src/ctgAsync.c b/source/libs/catalog/src/ctgAsync.c index f279d87815..64ca85edf4 100644 --- a/source/libs/catalog/src/ctgAsync.c +++ b/source/libs/catalog/src/ctgAsync.c @@ -1105,6 +1105,7 @@ int32_t ctgHandleGetTbMetasRsp(SCtgTaskReq* tReq, int32_t reqType, const SDataBu SName* pName = ctgGetFetchName(ctx->pNames, pFetch); int32_t flag = pFetch->flag; int32_t* vgId = &pFetch->vgId; + bool taskDone = false; CTG_ERR_JRET(ctgProcessRspMsg(pMsgCtx->out, reqType, pMsg->pData, pMsg->len, rspCode, pMsgCtx->target)); @@ -1250,6 +1251,7 @@ int32_t ctgHandleGetTbMetasRsp(SCtgTaskReq* tReq, int32_t reqType, const SDataBu pOut->tbMeta = NULL; if (0 == atomic_sub_fetch_32(&ctx->fetchNum, 1)) { TSWAP(pTask->res, ctx->pResList); + taskDone = true; } _return: @@ -1264,10 +1266,11 @@ _return: pRes->pRes = NULL; if (0 == atomic_sub_fetch_32(&ctx->fetchNum, 1)) { TSWAP(pTask->res, ctx->pResList); + taskDone = true; } } - if (pTask->res) { + if (pTask->res && taskDone) { ctgHandleTaskEnd(pTask, code); } @@ -1354,6 +1357,7 @@ int32_t ctgHandleGetTbHashsRsp(SCtgTaskReq* tReq, int32_t reqType, const SDataBu SCatalog* pCtg = pTask->pJob->pCtg; SCtgMsgCtx* pMsgCtx = CTG_GET_TASK_MSGCTX(pTask, tReq->msgIdx); SCtgFetch* pFetch = taosArrayGet(ctx->pFetchs, tReq->msgIdx); + bool taskDone = false; CTG_ERR_JRET(ctgProcessRspMsg(pMsgCtx->out, reqType, pMsg->pData, pMsg->len, rspCode, pMsgCtx->target)); @@ -1377,6 +1381,7 @@ int32_t ctgHandleGetTbHashsRsp(SCtgTaskReq* tReq, int32_t reqType, const SDataBu if (0 == atomic_sub_fetch_32(&ctx->fetchNum, 1)) { TSWAP(pTask->res, ctx->pResList); + taskDone = true; } _return: @@ -1392,10 +1397,11 @@ _return: if (0 == atomic_sub_fetch_32(&ctx->fetchNum, 1)) { TSWAP(pTask->res, ctx->pResList); + taskDone = true; } } - if (pTask->res) { + if (pTask->res && taskDone) { ctgHandleTaskEnd(pTask, code); } From 20baf373a082378e475852fa5733ee055674ad31 Mon Sep 17 00:00:00 2001 From: dapan1121 <72057773+dapan1121@users.noreply.github.com> Date: Fri, 12 Aug 2022 17:37:11 +0800 Subject: [PATCH 42/47] Update 01-arch.md --- docs/zh/21-tdinternal/01-arch.md | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/docs/zh/21-tdinternal/01-arch.md b/docs/zh/21-tdinternal/01-arch.md index e60debc87f..0807fb8a90 100644 --- a/docs/zh/21-tdinternal/01-arch.md +++ b/docs/zh/21-tdinternal/01-arch.md @@ -241,15 +241,16 @@ dataDir /mnt/data6 2 0 ## 数据查询 -TDengine 提供了多种多样针对表和超级表的查询处理功能,除了常规的聚合查询之外,还提供针对时序数据的窗口查询、统计聚合等功能。TDengine 的查询处理需要客户端、vnode、mnode 节点协同完成。 +TDengine 提供了多种多样针对表和超级表的查询处理功能,除了常规的聚合查询之外,还提供针对时序数据的窗口查询、统计聚合等功能。TDengine 的查询处理需要客户端、vnode、qnode、mnode 节点协同完成,一个复杂的超级表聚合查询可能需要多个 vnode 和 qnode 节点公共分担查询和计算任务。 -### 单表查询 +### 查询基本流程 -SQL 语句的解析和校验工作在客户端完成。解析 SQL 语句并生成抽象语法树(Abstract Syntax Tree,AST),然后对其进行校验和检查。以及向管理节点(mnode)请求查询中指定表的元数据信息(table metadata)。 - -根据元数据信息中的 End Point 信息,将查询请求序列化后发送到该表所在的数据节点(dnode)。dnode 接收到查询请求后,识别出该查询请求指向的虚拟节点(vnode),将消息转发到 vnode 的查询执行队列。vnode 的查询执行线程建立基础的查询执行环境,并立即返回该查询请求,同时开始执行该查询。 - -客户端在获取查询结果的时候,dnode 的查询执行队列中的工作线程会等待 vnode 执行线程执行完成,才能将查询结果返回到请求的客户端。 +1. 客户端解析输入 SQL 语句并生成抽象语法树(Abstract Syntax Tree,AST),然后根据元数据信息对其进行校验和检查。在此期间,元数据管理模块(Catalog)会向管理节点(mnode)或 vnode 请求查询中指定库和表的元数据信息(table metadata)。 +2. 在通过校验检查后,客户端将生成分布式的查询计划并对查询计划进行优化处理。 +3. 客户端根据配置的查询策略进行任务调度处理,一个查询子任务会根据其数据亲缘关系或负载信息调度到某个 vnode 或 qnode 所属的数据节点(dnode)进行处理。 +4. dnode 接收到查询请求后,识别出该查询请求指向的虚拟节点(vnode)或查询节点(qnode),将消息转发到 vnode 或 qnode 的查询执行队列。 +5. vnode 或 qnode 的查询执行线程建立基础的查询执行环境,并立即执行该查询,在得到部分可获取查询结果后通知客户端。 +6. 客户端将启动下级查询任务或直接获取查询结果。 ### 按时间轴聚合、降采样、插值 From 1a868167a4c9d3e251963bd43b97d2ff7863c6b1 Mon Sep 17 00:00:00 2001 From: Shuduo Sang Date: Fri, 12 Aug 2022 17:37:33 +0800 Subject: [PATCH 43/47] docs: update connector tmq page for3.0 (#16045) * docs: update connector for 3.0 * docs: remove continous query from connector doc * docs: update readme connector part * docs: fill tabs of tmq.md --- docs/zh/07-develop/07-tmq.md | 21 +++++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 372d458c36..960acb487a 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -6,6 +6,16 @@ title: 数据订阅 import Tabs from "@theme/Tabs"; import TabItem from "@theme/TabItem"; +import Tabs from "@theme/Tabs"; +import TabItem from "@theme/TabItem"; +import Java from "./_sub_java.mdx"; +import Python from "./_sub_python.mdx"; +import Go from "./_sub_go.mdx"; +import Rust from "./_sub_rust.mdx"; +import Node from "./_sub_node.mdx"; +import CSharp from "./_sub_cs.mdx"; +import CDemo from "./_sub_c.mdx"; + 为了帮助应用实时获取写入 TDengine 的数据,或者以事件到达顺序处理数据,TDengine提供了类似消息队列产品的数据订阅、消费接口。这样在很多场景下,采用 TDengine 的时序数据处理系统不再需要集成消息队列产品,比如 kafka, 从而简化系统设计的复杂度,降低运营维护成本。 @@ -211,16 +221,15 @@ TMQ支持多种订阅类型: - -TODO + -TODO + -TODO + @@ -232,11 +241,11 @@ TODO -TODO + -TODO + From 46f1e362956cbcf7293b5adec1fe2854029eaa77 Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 17:47:46 +0800 Subject: [PATCH 44/47] doc: remove duplicate imports --- docs/zh/07-develop/07-tmq.md | 2 -- 1 file changed, 2 deletions(-) diff --git a/docs/zh/07-develop/07-tmq.md b/docs/zh/07-develop/07-tmq.md index 960acb487a..25d468cad3 100644 --- a/docs/zh/07-develop/07-tmq.md +++ b/docs/zh/07-develop/07-tmq.md @@ -4,8 +4,6 @@ description: "数据订阅与推送服务。写入到 TDengine 中的时序数 title: 数据订阅 --- -import Tabs from "@theme/Tabs"; -import TabItem from "@theme/TabItem"; import Tabs from "@theme/Tabs"; import TabItem from "@theme/TabItem"; import Java from "./_sub_java.mdx"; From 269f139f7f5088727e90854b071bb3a754c032ac Mon Sep 17 00:00:00 2001 From: Shuduo Sang Date: Fri, 12 Aug 2022 17:51:10 +0800 Subject: [PATCH 45/47] docs: update connector doc for3.0 (#16055) * docs: update connector for 3.0 * docs: remove continous query from connector doc * docs: update readme connector part * docs: fill tabs of tmq.md * docs: fix 07-tmq.md From 339a77ea2f509d0b9413109cdc996cc79e04ff3f Mon Sep 17 00:00:00 2001 From: gccgdb1234 Date: Fri, 12 Aug 2022 18:05:25 +0800 Subject: [PATCH 46/47] doc: fix broken links --- docs/zh/07-develop/04-query-data/index.mdx | 6 +++--- docs/zh/21-tdinternal/01-arch.md | 2 -- 2 files changed, 3 insertions(+), 5 deletions(-) diff --git a/docs/zh/07-develop/04-query-data/index.mdx b/docs/zh/07-develop/04-query-data/index.mdx index eecda92744..68f49d9f2b 100644 --- a/docs/zh/07-develop/04-query-data/index.mdx +++ b/docs/zh/07-develop/04-query-data/index.mdx @@ -43,7 +43,7 @@ Query OK, 2 row(s) in set (0.001100s) 为满足物联网场景的需求,TDengine 支持几个特殊的函数,比如 twa(时间加权平均),spread (最大值与最小值的差),last_row(最后一条记录)等,更多与物联网场景相关的函数将添加进来。 -具体的查询语法请看 [TAOS SQL 的数据查询](/taos-sql/select) 章节。 +具体的查询语法请看 [TAOS SQL 的数据查询](../../taos-sql/select) 章节。 ## 多表聚合查询 @@ -74,7 +74,7 @@ taos> SELECT count(*), max(current) FROM meters where groupId = 2 and ts > now - Query OK, 1 row(s) in set (0.002136s) ``` -在 [TAOS SQL 的数据查询](/taos-sql/select) 一章,查询类操作都会注明是否支持超级表。 +在 [TAOS SQL 的数据查询](../../taos-sql/select) 一章,查询类操作都会注明是否支持超级表。 ## 降采样查询、插值 @@ -121,7 +121,7 @@ Query OK, 5 row(s) in set (0.001521s) 如果一个时间间隔里,没有采集的数据,TDengine 还提供插值计算的功能。 -语法规则细节请见 [TAOS SQL 的按时间窗口切分聚合](/taos-sql/interval) 章节。 +语法规则细节请见 [TAOS SQL 的按时间窗口切分聚合](../../taos-sql/distinguished) 章节。 ## 示例代码 diff --git a/docs/zh/21-tdinternal/01-arch.md b/docs/zh/21-tdinternal/01-arch.md index 0807fb8a90..0a90781c05 100644 --- a/docs/zh/21-tdinternal/01-arch.md +++ b/docs/zh/21-tdinternal/01-arch.md @@ -162,8 +162,6 @@ Vnode 会保持一个数据版本号(version),对内存数据进行持久 一个 vnode 启动时,角色(leader、follower)是不定的,数据是处于未同步状态,它需要与虚拟节点组内其他节点建立 TCP 连接,并互相交换 status,按照标准的 raft 一致性算法完成选主。 -更多的关于数据复制的流程,请见[《TDengine 3.0 数据复制模块设计》](/tdinternal/replica/)。 - ### 同步复制 对于数据一致性要求更高的场景,异步数据复制提供的最终一致性无法满足要求。因此 TDengine 提供同步复制的机制供用户选择。在创建数据库时,除指定副本数 replica 之外,用户还需要指定新的参数 strict。如果 strict 等于 1,它表示每次 leader 转发给副本时,需要等待半数以上副本达成一致后,才能通知应用,数据在 follower 已经写入成功。如果在一定的时间内,得不到半数以上副本的确认,leader vnode 将返回错误给应用。 From cc9e90976b8c0e252cf71a208a5729a804d38bf1 Mon Sep 17 00:00:00 2001 From: dapan1121 Date: Fri, 12 Aug 2022 18:10:34 +0800 Subject: [PATCH 47/47] docs: add stable query description --- docs/zh/21-tdinternal/01-arch.md | 14 ++++++++------ docs/zh/21-tdinternal/multi_tables.webp | Bin 15674 -> 196192 bytes 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/docs/zh/21-tdinternal/01-arch.md b/docs/zh/21-tdinternal/01-arch.md index 0807fb8a90..f145e2b691 100644 --- a/docs/zh/21-tdinternal/01-arch.md +++ b/docs/zh/21-tdinternal/01-arch.md @@ -280,12 +280,14 @@ TDengine 对每个数据采集点单独建表,但在实际应用中经常需
图 5 多表聚合查询原理图
-1. 应用将一个查询条件发往系统; -2. taosc 将超级表的名字发往 meta node(管理节点); -3. 管理节点将超级表所拥有的 vnode 列表发回 taosc; -4. taosc 将计算的请求连同标签过滤条件发往这些 vnode 对应的多个数据节点; -5. 每个 vnode 先在内存里查找出自己节点里符合标签过滤条件的表的集合,然后扫描存储的时序数据,完成相应的聚合计算,将结果返回给 taosc; -6. taosc 将多个数据节点返回的结果做最后的聚合,将其返回给应用。 +1. 客户端从 mnode 获取库和表的元数据信息; +2. mnode 返回请求的元数据信息; +3. 客户端向超级表所属的每个 vnode 发送查询请求; +4. vnode 启动本地查询,在获得查询结果后返回查询响应; +5. 客户端向聚合节点 (在本例中为 qnode)发送查询请求; +6. qnode 向每个 vnode 节点发送数据请求消息来拉取数据; +7. vnode 返回本节点的查询计算结果; +8. qnode 完成多节点数据聚合后将最终查询结果返回给客户端; 由于 TDengine 在 vnode 内将标签数据与时序数据分离存储,通过在内存里过滤标签数据,先找到需要参与聚合操作的表的集合,将需要扫描的数据集大幅减少,大幅提升聚合计算速度。同时,由于数据分布在多个 vnode/dnode,聚合计算操作在多个 vnode 里并发进行,又进一步提升了聚合的速度。 对普通表的聚合函数以及绝大部分操作都适用于超级表,语法完全一样,细节请看 TAOS SQL。 diff --git a/docs/zh/21-tdinternal/multi_tables.webp b/docs/zh/21-tdinternal/multi_tables.webp index 8f649e34a3a62d1b11b4403b2e743ff6b5e47be2..481020a5f718e2ad3f1265b2785ddff8ad9ee292 100644 GIT binary patch literal 196192 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

#x!=5&~Gh1g+ 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 R8SX#B{b#uU4ELXzk^oDe4k!Qs literal 15674 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