Merge branch 'develop' of github.com:taosdata/TDengine into dev/chr
This commit is contained in:
commit
1b78353009
|
@ -131,10 +131,10 @@ cmake .. -DCPUTYPE=mips64 && cmake --build .
|
|||
### On Windows platform
|
||||
|
||||
If you use the Visual Studio 2013, please open a command window by executing "cmd.exe".
|
||||
Please specify "x86_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" is for 32 bits Windows when you execute vcvarsall.bat.
|
||||
```cmd
|
||||
mkdir debug && cd debug
|
||||
"C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\vcvarsall.bat" < x86_amd64 | x86 >
|
||||
"C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\vcvarsall.bat" < amd64 | x86 >
|
||||
cmake .. -G "NMake Makefiles"
|
||||
nmake
|
||||
```
|
||||
|
|
|
@ -32,7 +32,7 @@ ELSEIF (TD_WINDOWS)
|
|||
#INSTALL(TARGETS taos RUNTIME DESTINATION driver)
|
||||
#INSTALL(TARGETS shell RUNTIME DESTINATION .)
|
||||
IF (TD_MVN_INSTALLED)
|
||||
INSTALL(FILES ${LIBRARY_OUTPUT_PATH}/taos-jdbcdriver-2.0.29.jar DESTINATION connector/jdbc)
|
||||
INSTALL(FILES ${LIBRARY_OUTPUT_PATH}/taos-jdbcdriver-2.0.30.jar DESTINATION connector/jdbc)
|
||||
ENDIF ()
|
||||
ELSEIF (TD_DARWIN)
|
||||
SET(TD_MAKE_INSTALL_SH "${TD_COMMUNITY_DIR}/packaging/tools/make_install.sh")
|
||||
|
|
|
@ -361,6 +361,7 @@ public void setShort(int columnIndex, ArrayList<Short> list) throws SQLException
|
|||
public void setString(int columnIndex, ArrayList<String> list, int size) throws SQLException
|
||||
public void setNString(int columnIndex, ArrayList<String> list, int size) throws SQLException
|
||||
```
|
||||
其中 setString 和 setNString 都要求用户在 size 参数里声明表定义中对应列的列宽。
|
||||
|
||||
### <a class="anchor" id="subscribe"></a>订阅
|
||||
|
||||
|
|
|
@ -301,7 +301,7 @@ TDengine的异步API均采用非阻塞调用模式。应用程序可以用多线
|
|||
2. 调用 `taos_stmt_prepare` 解析 INSERT 语句;
|
||||
3. 如果 INSERT 语句中预留了表名但没有预留 TAGS,那么调用 `taos_stmt_set_tbname` 来设置表名;
|
||||
4. 如果 INSERT 语句中既预留了表名又预留了 TAGS(例如 INSERT 语句采取的是自动建表的方式),那么调用 `taos_stmt_set_tbname_tags` 来设置表名和 TAGS 的值;
|
||||
5. 调用 `taos_stmt_bind_param_batch` 以多列的方式设置 VALUES 的值;
|
||||
5. 调用 `taos_stmt_bind_param_batch` 以多列的方式设置 VALUES 的值,或者调用 `taos_stmt_bind_param` 以单行的方式设置 VALUES 的值;
|
||||
6. 调用 `taos_stmt_add_batch` 把当前绑定的参数加入批处理;
|
||||
7. 可以重复第 3~6 步,为批处理加入更多的数据行;
|
||||
8. 调用 `taos_stmt_execute` 执行已经准备好的批处理指令;
|
||||
|
@ -338,17 +338,17 @@ typedef struct TAOS_BIND {
|
|||
|
||||
- `int taos_stmt_set_tbname(TAOS_STMT* stmt, const char* name)`
|
||||
|
||||
(2.1.1.0 版本新增)
|
||||
(2.1.1.0 版本新增,仅支持用于替换 INSERT 语句中的参数值)
|
||||
当 SQL 语句中的表名使用了 `?` 占位时,可以使用此函数绑定一个具体的表名。
|
||||
|
||||
- `int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags)`
|
||||
|
||||
(2.1.2.0 版本新增)
|
||||
(2.1.2.0 版本新增,仅支持用于替换 INSERT 语句中的参数值)
|
||||
当 SQL 语句中的表名和 TAGS 都使用了 `?` 占位时,可以使用此函数绑定具体的表名和具体的 TAGS 取值。最典型的使用场景是使用了自动建表功能的 INSERT 语句(目前版本不支持指定具体的 TAGS 列)。tags 参数中的列数量需要与 SQL 语句中要求的 TAGS 数量完全一致。
|
||||
|
||||
- `int taos_stmt_bind_param_batch(TAOS_STMT* stmt, TAOS_MULTI_BIND* bind)`
|
||||
|
||||
(2.1.1.0 版本新增)
|
||||
(2.1.1.0 版本新增,仅支持用于替换 INSERT 语句中的参数值)
|
||||
以多列的方式传递待绑定的数据,需要保证这里传递的数据列的顺序、列的数量与 SQL 语句中的 VALUES 参数完全一致。TAOS_MULTI_BIND 的具体定义如下:
|
||||
|
||||
```c
|
||||
|
|
|
@ -1306,7 +1306,7 @@ SELECT AVG(current), MAX(current), LEASTSQUARES(current, start_val, step_val), P
|
|||
- 数据库名最大长度为 32
|
||||
- 表名最大长度为 192,每行数据最大长度 16k 个字符(注意:数据行内每个 BINARY/NCHAR 类型的列还会额外占用 2 个字节的存储位置)
|
||||
- 列名最大长度为 64,最多允许 1024 列,最少需要 2 列,第一列必须是时间戳
|
||||
- 标签最多允许 128 个,可以 1 个,标签总长度不超过 16k 个字符
|
||||
- 标签名最大长度为 64,最多允许 128 个,可以 1 个,一个表中标签值的总长度不超过 16k 个字符
|
||||
- SQL 语句最大长度 65480 个字符,但可通过系统配置参数 maxSQLLength 修改,最长可配置为 1M
|
||||
- SELECT 语句的查询结果,最多允许返回 1024 列(语句中的函数调用可能也会占用一些列空间),超限时需要显式指定较少的返回数据列,以避免语句执行报错。
|
||||
- 库的数目,超级表的数目、表的数目,系统不做限制,仅受系统资源限制
|
||||
|
|
|
@ -123,6 +123,7 @@ int32_t tscGetDataBlockFromList(SHashObj* pHashList, int64_t id, int32_t size, i
|
|||
*/
|
||||
bool tscIsPointInterpQuery(SQueryInfo* pQueryInfo);
|
||||
bool tscIsTWAQuery(SQueryInfo* pQueryInfo);
|
||||
bool tscIsDiffQuery(SQueryInfo* pQueryInfo);
|
||||
bool tscIsSessionWindowQuery(SQueryInfo* pQueryInfo);
|
||||
bool tscIsSecondStageQuery(SQueryInfo* pQueryInfo);
|
||||
bool tsIsArithmeticQueryOnAggResult(SQueryInfo* pQueryInfo);
|
||||
|
@ -132,7 +133,6 @@ bool hasTagValOutput(SQueryInfo* pQueryInfo);
|
|||
bool timeWindowInterpoRequired(SQueryInfo *pQueryInfo);
|
||||
bool isStabledev(SQueryInfo* pQueryInfo);
|
||||
bool isTsCompQuery(SQueryInfo* pQueryInfo);
|
||||
bool isSimpleAggregate(SQueryInfo* pQueryInfo);
|
||||
bool isBlockDistQuery(SQueryInfo* pQueryInfo);
|
||||
bool isSimpleAggregateRv(SQueryInfo* pQueryInfo);
|
||||
|
||||
|
@ -214,7 +214,7 @@ void tscColumnListDestroy(SArray* pColList);
|
|||
void tscColumnListCopy(SArray* dst, const SArray* src, uint64_t tableUid);
|
||||
void tscColumnListCopyAll(SArray* dst, const SArray* src);
|
||||
|
||||
void convertQueryResult(SSqlRes* pRes, SQueryInfo* pQueryInfo);
|
||||
void convertQueryResult(SSqlRes* pRes, SQueryInfo* pQueryInfo, uint64_t objId);
|
||||
|
||||
void tscDequoteAndTrimToken(SStrToken* pToken);
|
||||
int32_t tscValidateName(SStrToken* pToken);
|
||||
|
@ -329,9 +329,7 @@ STableMeta* tscTableMetaDup(STableMeta* pTableMeta);
|
|||
SVgroupsInfo* tscVgroupsInfoDup(SVgroupsInfo* pVgroupsInfo);
|
||||
|
||||
int32_t tscCreateQueryFromQueryInfo(SQueryInfo* pQueryInfo, SQueryAttr* pQueryAttr, void* addr);
|
||||
|
||||
void tsCreateSQLFunctionCtx(SQueryInfo* pQueryInfo, SQLFunctionCtx* pCtx, SSchema* pSchema);
|
||||
void* createQInfoFromQueryNode(SQueryInfo* pQueryInfo, STableGroupInfo* pTableGroupInfo, SOperatorInfo* pOperator, char* sql, void* addr, int32_t stage);
|
||||
void* createQInfoFromQueryNode(SQueryInfo* pQueryInfo, STableGroupInfo* pTableGroupInfo, SOperatorInfo* pOperator, char* sql, void* addr, int32_t stage, uint64_t qId);
|
||||
|
||||
void* malloc_throw(size_t size);
|
||||
void* calloc_throw(size_t nmemb, size_t size);
|
||||
|
|
|
@ -320,7 +320,7 @@ int32_t tscCreateResPointerInfo(SSqlRes *pRes, SQueryInfo *pQueryInfo);
|
|||
void tscSetResRawPtr(SSqlRes* pRes, SQueryInfo* pQueryInfo);
|
||||
void tscSetResRawPtrRv(SSqlRes* pRes, SQueryInfo* pQueryInfo, SSDataBlock* pBlock);
|
||||
|
||||
void handleDownstreamOperator(SSqlObj** pSqlList, int32_t numOfUpstream, SQueryInfo* px, SSqlRes* pOutput);
|
||||
void handleDownstreamOperator(SSqlObj** pSqlList, int32_t numOfUpstream, SQueryInfo* px, SSqlObj* pParent);
|
||||
void destroyTableNameList(SInsertStatementParam* pInsertParam);
|
||||
|
||||
void tscResetSqlCmd(SSqlCmd *pCmd, bool removeMeta);
|
||||
|
|
|
@ -144,7 +144,7 @@ static void tscAsyncFetchRowsProxy(void *param, TAOS_RES *tres, int numOfRows) {
|
|||
}
|
||||
|
||||
// local merge has handle this situation during super table non-projection query.
|
||||
if (pCmd->command != TSDB_SQL_RETRIEVE_LOCALMERGE) {
|
||||
if (pCmd->command != TSDB_SQL_RETRIEVE_GLOBALMERGE) {
|
||||
pRes->numOfClauseTotal += pRes->numOfRows;
|
||||
}
|
||||
|
||||
|
@ -174,7 +174,7 @@ static void tscProcessAsyncRetrieveImpl(void *param, TAOS_RES *tres, int numOfRo
|
|||
}
|
||||
|
||||
pSql->fp = fp;
|
||||
if (pCmd->command != TSDB_SQL_RETRIEVE_LOCALMERGE && pCmd->command < TSDB_SQL_LOCAL) {
|
||||
if (pCmd->command != TSDB_SQL_RETRIEVE_GLOBALMERGE && pCmd->command < TSDB_SQL_LOCAL) {
|
||||
pCmd->command = (pCmd->command > TSDB_SQL_MGMT) ? TSDB_SQL_RETRIEVE : TSDB_SQL_FETCH;
|
||||
}
|
||||
|
||||
|
@ -257,14 +257,14 @@ void taos_fetch_rows_a(TAOS_RES *tres, __async_cb_func_t fp, void *param) {
|
|||
}
|
||||
|
||||
return;
|
||||
} else if (pCmd->command == TSDB_SQL_RETRIEVE || pCmd->command == TSDB_SQL_RETRIEVE_LOCALMERGE) {
|
||||
} else if (pCmd->command == TSDB_SQL_RETRIEVE || pCmd->command == TSDB_SQL_RETRIEVE_GLOBALMERGE) {
|
||||
// in case of show command, return no data
|
||||
(*pSql->fetchFp)(param, pSql, 0);
|
||||
} else {
|
||||
assert(0);
|
||||
}
|
||||
} else { // current query is not completed, continue retrieve from node
|
||||
if (pCmd->command != TSDB_SQL_RETRIEVE_LOCALMERGE && pCmd->command < TSDB_SQL_LOCAL) {
|
||||
if (pCmd->command != TSDB_SQL_RETRIEVE_GLOBALMERGE && pCmd->command < TSDB_SQL_LOCAL) {
|
||||
pCmd->command = (pCmd->command > TSDB_SQL_MGMT) ? TSDB_SQL_RETRIEVE : TSDB_SQL_FETCH;
|
||||
}
|
||||
|
||||
|
|
|
@ -323,7 +323,7 @@ TAOS_ROW tscFetchRow(void *param) {
|
|||
// current data set are exhausted, fetch more data from node
|
||||
if (pRes->row >= pRes->numOfRows && (pRes->completed != true || hasMoreVnodesToTry(pSql) || hasMoreClauseToTry(pSql)) &&
|
||||
(pCmd->command == TSDB_SQL_RETRIEVE ||
|
||||
pCmd->command == TSDB_SQL_RETRIEVE_LOCALMERGE ||
|
||||
pCmd->command == TSDB_SQL_RETRIEVE_GLOBALMERGE ||
|
||||
pCmd->command == TSDB_SQL_TABLE_JOIN_RETRIEVE ||
|
||||
pCmd->command == TSDB_SQL_FETCH ||
|
||||
pCmd->command == TSDB_SQL_SHOW ||
|
||||
|
|
|
@ -78,6 +78,16 @@ typedef struct STscStmt {
|
|||
SNormalStmt normal;
|
||||
} STscStmt;
|
||||
|
||||
#define STMT_RET(c) do { \
|
||||
int32_t _code = c; \
|
||||
if (pStmt && pStmt->pSql) { pStmt->pSql->res.code = _code; } else {terrno = _code;} \
|
||||
return _code; \
|
||||
} while (0)
|
||||
|
||||
static int32_t invalidOperationMsg(char* dstBuffer, const char* errMsg) {
|
||||
return tscInvalidOperationMsg(dstBuffer, errMsg, NULL);
|
||||
}
|
||||
|
||||
static int normalStmtAddPart(SNormalStmt* stmt, bool isParam, char* str, uint32_t len) {
|
||||
uint16_t size = stmt->numParts + 1;
|
||||
if (size > stmt->sizeParts) {
|
||||
|
@ -163,8 +173,8 @@ static int normalStmtBindParam(STscStmt* stmt, TAOS_BIND* bind) {
|
|||
break;
|
||||
|
||||
default:
|
||||
tscDebug("0x%"PRIx64" bind column%d: type mismatch or invalid", stmt->pSql->self, i);
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
tscError("0x%"PRIx64" bind column%d: type mismatch or invalid", stmt->pSql->self, i);
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "bind type mismatch or invalid");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -727,6 +737,7 @@ static int doBindParam(STableDataBlocks* pBlock, char* data, SParamInfo* param,
|
|||
#endif
|
||||
|
||||
if (bind->buffer_type != param->type) {
|
||||
tscError("column type mismatch");
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
}
|
||||
|
||||
|
@ -754,6 +765,7 @@ static int doBindParam(STableDataBlocks* pBlock, char* data, SParamInfo* param,
|
|||
|
||||
case TSDB_DATA_TYPE_BINARY:
|
||||
if ((*bind->length) > (uintptr_t)param->bytes) {
|
||||
tscError("column length is too big");
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
}
|
||||
size = (short)*bind->length;
|
||||
|
@ -763,6 +775,7 @@ static int doBindParam(STableDataBlocks* pBlock, char* data, SParamInfo* param,
|
|||
case TSDB_DATA_TYPE_NCHAR: {
|
||||
int32_t output = 0;
|
||||
if (!taosMbsToUcs4(bind->buffer, *bind->length, varDataVal(data + param->offset), param->bytes - VARSTR_HEADER_SIZE, &output)) {
|
||||
tscError("convert nchar failed");
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
}
|
||||
varDataSetLen(data + param->offset, output);
|
||||
|
@ -787,6 +800,7 @@ static int doBindParam(STableDataBlocks* pBlock, char* data, SParamInfo* param,
|
|||
|
||||
static int doBindBatchParam(STableDataBlocks* pBlock, SParamInfo* param, TAOS_MULTI_BIND* bind, int32_t rowNum) {
|
||||
if (bind->buffer_type != param->type || !isValidDataType(param->type)) {
|
||||
tscError("column mismatch or invalid");
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
}
|
||||
|
||||
|
@ -892,8 +906,8 @@ static int insertStmtBindParam(STscStmt* stmt, TAOS_BIND* bind) {
|
|||
|
||||
int code = doBindParam(pBlock, data, param, &bind[param->idx], 1);
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
tscDebug("0x%"PRIx64" bind column %d: type mismatch or invalid", pStmt->pSql->self, param->idx);
|
||||
return code;
|
||||
tscDebug("0x%"PRIx64" bind column %d: type mismatch or invalid", pStmt->pSql->self, param->idx);
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "bind column type mismatch or invalid");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -957,13 +971,13 @@ static int insertStmtBindParamBatch(STscStmt* stmt, TAOS_MULTI_BIND* bind, int c
|
|||
SParamInfo* param = &pBlock->params[j];
|
||||
if (bind[param->idx].num != rowNum) {
|
||||
tscError("0x%"PRIx64" param %d: num[%d:%d] not match", pStmt->pSql->self, param->idx, rowNum, bind[param->idx].num);
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "bind row num mismatch");
|
||||
}
|
||||
|
||||
int code = doBindBatchParam(pBlock, param, &bind[param->idx], pCmd->batchSize);
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
tscError("0x%"PRIx64" bind column %d: type mismatch or invalid", pStmt->pSql->self, param->idx);
|
||||
return code;
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "bind column type mismatch or invalid");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -974,7 +988,7 @@ static int insertStmtBindParamBatch(STscStmt* stmt, TAOS_MULTI_BIND* bind, int c
|
|||
int code = doBindBatchParam(pBlock, param, bind, pCmd->batchSize);
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
tscError("0x%"PRIx64" bind column %d: type mismatch or invalid", pStmt->pSql->self, param->idx);
|
||||
return code;
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "bind column type mismatch or invalid");
|
||||
}
|
||||
|
||||
if (colIdx == (pBlock->numOfParams - 1)) {
|
||||
|
@ -993,7 +1007,7 @@ static int insertStmtUpdateBatch(STscStmt* stmt) {
|
|||
|
||||
if (pCmd->batchSize > INT16_MAX) {
|
||||
tscError("too many record:%d", pCmd->batchSize);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "too many records");
|
||||
}
|
||||
|
||||
if (taosHashGetSize(pCmd->insertParam.pTableBlockHashList) == 0) {
|
||||
|
@ -1057,7 +1071,8 @@ static int insertStmtReset(STscStmt* pStmt) {
|
|||
static int insertStmtExecute(STscStmt* stmt) {
|
||||
SSqlCmd* pCmd = &stmt->pSql->cmd;
|
||||
if (pCmd->batchSize == 0) {
|
||||
return TSDB_CODE_TSC_INVALID_VALUE;
|
||||
tscError("no records bind");
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&stmt->pSql->cmd), "no records bind");
|
||||
}
|
||||
|
||||
if (taosHashGetSize(pCmd->insertParam.pTableBlockHashList) == 0) {
|
||||
|
@ -1174,7 +1189,7 @@ static int insertBatchStmtExecute(STscStmt* pStmt) {
|
|||
|
||||
if(pStmt->mtb.nameSet == false) {
|
||||
tscError("0x%"PRIx64" no table name set", pStmt->pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "no table name set");
|
||||
}
|
||||
|
||||
pStmt->pSql->retry = pStmt->pSql->maxRetry + 1; //no retry
|
||||
|
@ -1215,7 +1230,8 @@ int stmtParseInsertTbTags(SSqlObj* pSql, STscStmt* pStmt) {
|
|||
int32_t index = 0;
|
||||
SStrToken sToken = tStrGetToken(pCmd->insertParam.sql, &index, false);
|
||||
if (sToken.n == 0) {
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
tscError("table is is expected, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "table name is expected", pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
if (sToken.n == 1 && sToken.type == TK_QUESTION) {
|
||||
|
@ -1237,24 +1253,28 @@ int stmtParseInsertTbTags(SSqlObj* pSql, STscStmt* pStmt) {
|
|||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
if (sToken.n <= 0 || sToken.type != TK_USING) {
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "keywords USING is expected", sToken.z);
|
||||
if (sToken.n <= 0 || sToken.type != TK_USING) {
|
||||
tscError("keywords USING is expected, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "keywords USING is expected", sToken.z ? sToken.z : pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
sToken = tStrGetToken(pCmd->insertParam.sql, &index, false);
|
||||
if (sToken.n <= 0 || ((sToken.type != TK_ID) && (sToken.type != TK_STRING))) {
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "invalid token", sToken.z);
|
||||
tscError("invalid token, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "invalid token", sToken.z ? sToken.z : pCmd->insertParam.sql);
|
||||
}
|
||||
pStmt->mtb.stbname = sToken;
|
||||
|
||||
sToken = tStrGetToken(pCmd->insertParam.sql, &index, false);
|
||||
if (sToken.n <= 0 || sToken.type != TK_TAGS) {
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "keyword TAGS expected", sToken.z);
|
||||
tscError("keyword TAGS expected, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "keyword TAGS expected", sToken.z ? sToken.z : pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
sToken = tStrGetToken(pCmd->insertParam.sql, &index, false);
|
||||
if (sToken.n <= 0 || sToken.type != TK_LP) {
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, ") expected", sToken.z);
|
||||
tscError("( expected, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "( expected", sToken.z ? sToken.z : pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
pStmt->mtb.tags = taosArrayInit(4, sizeof(SStrToken));
|
||||
|
@ -1264,7 +1284,8 @@ int stmtParseInsertTbTags(SSqlObj* pSql, STscStmt* pStmt) {
|
|||
while (loopCont) {
|
||||
sToken = tStrGetToken(pCmd->insertParam.sql, &index, false);
|
||||
if (sToken.n <= 0) {
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
tscError("unexpected sql end, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "unexpected sql end", pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
switch (sToken.type) {
|
||||
|
@ -1272,7 +1293,8 @@ int stmtParseInsertTbTags(SSqlObj* pSql, STscStmt* pStmt) {
|
|||
loopCont = 0;
|
||||
break;
|
||||
case TK_VALUES:
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
tscError("unexpected token values, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "unexpected token", sToken.z);
|
||||
case TK_QUESTION:
|
||||
pStmt->mtb.tagSet = false; //continue
|
||||
default:
|
||||
|
@ -1282,12 +1304,14 @@ int stmtParseInsertTbTags(SSqlObj* pSql, STscStmt* pStmt) {
|
|||
}
|
||||
|
||||
if (taosArrayGetSize(pStmt->mtb.tags) <= 0) {
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
tscError("no tags, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "no tags", pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
sToken = tStrGetToken(pCmd->insertParam.sql, &index, false);
|
||||
if (sToken.n <= 0 || (sToken.type != TK_VALUES && sToken.type != TK_LP)) {
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
tscError("sql error, sql:%s", pCmd->insertParam.sql);
|
||||
return tscSQLSyntaxErrMsg(pCmd->payload, "sql error", sToken.z ? sToken.z : pCmd->insertParam.sql);
|
||||
}
|
||||
|
||||
pStmt->mtb.values = sToken;
|
||||
|
@ -1329,8 +1353,8 @@ int stmtGenInsertStatement(SSqlObj* pSql, STscStmt* pStmt, const char* name, TAO
|
|||
} else {
|
||||
if (tags[j].buffer == NULL) {
|
||||
free(str);
|
||||
tscError("empty");
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
tscError("empty tag value in params");
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "empty tag value in params");
|
||||
}
|
||||
|
||||
ret = converToStr(str + len, tags[j].buffer_type, tags[j].buffer, tags[j].length ? (int32_t)*tags[j].length : -1, &l);
|
||||
|
@ -1387,13 +1411,15 @@ int stmtGenInsertStatement(SSqlObj* pSql, STscStmt* pStmt, const char* name, TAO
|
|||
|
||||
TAOS_STMT* taos_stmt_init(TAOS* taos) {
|
||||
STscObj* pObj = (STscObj*)taos;
|
||||
STscStmt* pStmt = NULL;
|
||||
|
||||
if (pObj == NULL || pObj->signature != pObj) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
tscError("connection disconnected");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
STscStmt* pStmt = calloc(1, sizeof(STscStmt));
|
||||
pStmt = calloc(1, sizeof(STscStmt));
|
||||
if (pStmt == NULL) {
|
||||
terrno = TSDB_CODE_TSC_OUT_OF_MEMORY;
|
||||
tscError("failed to allocate memory for statement");
|
||||
|
@ -1410,6 +1436,14 @@ TAOS_STMT* taos_stmt_init(TAOS* taos) {
|
|||
return NULL;
|
||||
}
|
||||
|
||||
if (TSDB_CODE_SUCCESS != tscAllocPayload(&pSql->cmd, TSDB_DEFAULT_PAYLOAD_SIZE)) {
|
||||
free(pSql);
|
||||
free(pStmt);
|
||||
terrno = TSDB_CODE_TSC_OUT_OF_MEMORY;
|
||||
tscError("failed to malloc payload buffer");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
tsem_init(&pSql->rspSem, 0, 0);
|
||||
pSql->signature = pSql;
|
||||
pSql->pTscObj = pObj;
|
||||
|
@ -1425,13 +1459,12 @@ int taos_stmt_prepare(TAOS_STMT* stmt, const char* sql, unsigned long length) {
|
|||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
|
||||
if (stmt == NULL || pStmt->taos == NULL || pStmt->pSql == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (pStmt->last != STMT_INIT) {
|
||||
tscError("prepare status error, last:%d", pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "prepare status error"));
|
||||
}
|
||||
|
||||
pStmt->last = STMT_PREPARE;
|
||||
|
@ -1447,17 +1480,11 @@ int taos_stmt_prepare(TAOS_STMT* stmt, const char* sql, unsigned long length) {
|
|||
|
||||
pCmd->insertParam.insertType = TSDB_QUERY_TYPE_STMT_INSERT;
|
||||
|
||||
if (TSDB_CODE_SUCCESS != tscAllocPayload(pCmd, TSDB_DEFAULT_PAYLOAD_SIZE)) {
|
||||
tscError("%p failed to malloc payload buffer", pSql);
|
||||
return TSDB_CODE_TSC_OUT_OF_MEMORY;
|
||||
}
|
||||
|
||||
pSql->sqlstr = realloc(pSql->sqlstr, sqlLen + 1);
|
||||
|
||||
if (pSql->sqlstr == NULL) {
|
||||
tscError("%p failed to malloc sql string buffer", pSql);
|
||||
free(pCmd->payload);
|
||||
return TSDB_CODE_TSC_OUT_OF_MEMORY;
|
||||
STMT_RET(TSDB_CODE_TSC_OUT_OF_MEMORY);
|
||||
}
|
||||
|
||||
pRes->qId = 0;
|
||||
|
@ -1476,11 +1503,11 @@ int taos_stmt_prepare(TAOS_STMT* stmt, const char* sql, unsigned long length) {
|
|||
|
||||
int32_t ret = stmtParseInsertTbTags(pSql, pStmt);
|
||||
if (ret != TSDB_CODE_SUCCESS) {
|
||||
return ret;
|
||||
STMT_RET(ret);
|
||||
}
|
||||
|
||||
if (pStmt->multiTbInsert) {
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
}
|
||||
|
||||
memset(&pStmt->mtb, 0, sizeof(pStmt->mtb));
|
||||
|
@ -1489,14 +1516,14 @@ int taos_stmt_prepare(TAOS_STMT* stmt, const char* sql, unsigned long length) {
|
|||
if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) {
|
||||
// wait for the callback function to post the semaphore
|
||||
tsem_wait(&pSql->rspSem);
|
||||
return pSql->res.code;
|
||||
STMT_RET(pSql->res.code);
|
||||
}
|
||||
|
||||
return code;
|
||||
STMT_RET(code);
|
||||
}
|
||||
|
||||
pStmt->isInsert = false;
|
||||
return normalStmtPrepare(pStmt);
|
||||
STMT_RET(normalStmtPrepare(pStmt));
|
||||
}
|
||||
|
||||
int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags) {
|
||||
|
@ -1505,25 +1532,22 @@ int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags
|
|||
SSqlCmd* pCmd = &pSql->cmd;
|
||||
|
||||
if (stmt == NULL || pStmt->pSql == NULL || pStmt->taos == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (name == NULL) {
|
||||
terrno = TSDB_CODE_TSC_APP_ERROR;
|
||||
tscError("0x%"PRIx64" name is NULL", pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "name is NULL"));
|
||||
}
|
||||
|
||||
if (pStmt->multiTbInsert == false || !tscIsInsertData(pSql->sqlstr)) {
|
||||
terrno = TSDB_CODE_TSC_APP_ERROR;
|
||||
tscError("0x%"PRIx64" not multi table insert", pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
tscError("0x%"PRIx64" not multiple table insert", pSql->self);
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "not multiple table insert"));
|
||||
}
|
||||
|
||||
if (pStmt->last == STMT_INIT || pStmt->last == STMT_BIND || pStmt->last == STMT_BIND_COL) {
|
||||
tscError("0x%"PRIx64" settbname status error, last:%d", pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
tscError("0x%"PRIx64" set_tbname_tags status error, last:%d", pSql->self, pStmt->last);
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "set_tbname_tags status error"));
|
||||
}
|
||||
|
||||
pStmt->last = STMT_SETTBNAME;
|
||||
|
@ -1535,7 +1559,7 @@ int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags
|
|||
STableDataBlocks** t1 = (STableDataBlocks**)taosHashGet(pStmt->mtb.pTableBlockHashList, (const char*)&pStmt->mtb.currentUid, sizeof(pStmt->mtb.currentUid));
|
||||
if (t1 == NULL) {
|
||||
tscError("0x%"PRIx64" no table data block in hash list, uid:%" PRId64 , pSql->self, pStmt->mtb.currentUid);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(TSDB_CODE_TSC_APP_ERROR);
|
||||
}
|
||||
|
||||
SSubmitBlk* pBlk = (SSubmitBlk*) (*t1)->pData;
|
||||
|
@ -1544,7 +1568,7 @@ int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags
|
|||
taosHashPut(pCmd->insertParam.pTableBlockHashList, (void *)&pStmt->mtb.currentUid, sizeof(pStmt->mtb.currentUid), (void*)t1, POINTER_BYTES);
|
||||
|
||||
tscDebug("0x%"PRIx64" table:%s is already prepared, uid:%" PRIu64, pSql->self, name, pStmt->mtb.currentUid);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
}
|
||||
|
||||
if (pStmt->mtb.tagSet) {
|
||||
|
@ -1552,12 +1576,12 @@ int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags
|
|||
} else {
|
||||
if (tags == NULL) {
|
||||
tscError("No tags set");
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "no tags set"));
|
||||
}
|
||||
|
||||
int32_t ret = stmtGenInsertStatement(pSql, pStmt, name, tags);
|
||||
if (ret != TSDB_CODE_SUCCESS) {
|
||||
return ret;
|
||||
STMT_RET(ret);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1591,7 +1615,7 @@ int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags
|
|||
code = tscGetDataBlockFromList(pCmd->insertParam.pTableBlockHashList, pTableMeta->id.uid, TSDB_PAYLOAD_SIZE, sizeof(SSubmitBlk),
|
||||
pTableMeta->tableInfo.rowSize, &pTableMetaInfo->name, pTableMeta, &pBlock, NULL);
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
return code;
|
||||
STMT_RET(code);
|
||||
}
|
||||
|
||||
SSubmitBlk* blk = (SSubmitBlk*)pBlock->pData;
|
||||
|
@ -1606,7 +1630,7 @@ int taos_stmt_set_tbname_tags(TAOS_STMT* stmt, const char* name, TAOS_BIND* tags
|
|||
tscDebug("0x%"PRIx64" table:%s is prepared, uid:%" PRIx64, pSql->self, name, pStmt->mtb.currentUid);
|
||||
}
|
||||
|
||||
return code;
|
||||
STMT_RET(code);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1639,35 +1663,34 @@ int taos_stmt_close(TAOS_STMT* stmt) {
|
|||
}
|
||||
|
||||
taos_free_result(pStmt->pSql);
|
||||
free(pStmt);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
tfree(pStmt);
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
}
|
||||
|
||||
int taos_stmt_bind_param(TAOS_STMT* stmt, TAOS_BIND* bind) {
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
if (stmt == NULL || pStmt->pSql == NULL || pStmt->taos == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (pStmt->isInsert) {
|
||||
if (pStmt->multiTbInsert) {
|
||||
if (pStmt->last != STMT_SETTBNAME && pStmt->last != STMT_ADD_BATCH) {
|
||||
tscError("0x%"PRIx64" bind param status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "bind param status error"));
|
||||
}
|
||||
} else {
|
||||
if (pStmt->last != STMT_PREPARE && pStmt->last != STMT_ADD_BATCH && pStmt->last != STMT_EXECUTE) {
|
||||
tscError("0x%"PRIx64" bind param status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "bind param status error"));
|
||||
}
|
||||
}
|
||||
|
||||
pStmt->last = STMT_BIND;
|
||||
|
||||
return insertStmtBindParam(pStmt, bind);
|
||||
STMT_RET(insertStmtBindParam(pStmt, bind));
|
||||
} else {
|
||||
return normalStmtBindParam(pStmt, bind);
|
||||
STMT_RET(normalStmtBindParam(pStmt, bind));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1676,69 +1699,67 @@ int taos_stmt_bind_param_batch(TAOS_STMT* stmt, TAOS_MULTI_BIND* bind) {
|
|||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
|
||||
if (stmt == NULL || pStmt->pSql == NULL || pStmt->taos == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (bind == NULL || bind->num <= 0 || bind->num > INT16_MAX) {
|
||||
tscError("0x%"PRIx64" invalid parameter", pStmt->pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "invalid bind param"));
|
||||
}
|
||||
|
||||
if (!pStmt->isInsert) {
|
||||
tscError("0x%"PRIx64" not or invalid batch insert", pStmt->pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "not or invalid batch insert"));
|
||||
}
|
||||
|
||||
if (pStmt->multiTbInsert) {
|
||||
if (pStmt->last != STMT_SETTBNAME && pStmt->last != STMT_ADD_BATCH) {
|
||||
tscError("0x%"PRIx64" bind param status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "bind param status error"));
|
||||
}
|
||||
} else {
|
||||
if (pStmt->last != STMT_PREPARE && pStmt->last != STMT_ADD_BATCH && pStmt->last != STMT_EXECUTE) {
|
||||
tscError("0x%"PRIx64" bind param status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "bind param status error"));
|
||||
}
|
||||
}
|
||||
|
||||
pStmt->last = STMT_BIND;
|
||||
|
||||
return insertStmtBindParamBatch(pStmt, bind, -1);
|
||||
STMT_RET(insertStmtBindParamBatch(pStmt, bind, -1));
|
||||
}
|
||||
|
||||
int taos_stmt_bind_single_param_batch(TAOS_STMT* stmt, TAOS_MULTI_BIND* bind, int colIdx) {
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
if (stmt == NULL || pStmt->pSql == NULL || pStmt->taos == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (bind == NULL || bind->num <= 0 || bind->num > INT16_MAX) {
|
||||
tscError("0x%"PRIx64" invalid parameter", pStmt->pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "invalid bind param"));
|
||||
}
|
||||
|
||||
if (!pStmt->isInsert) {
|
||||
tscError("0x%"PRIx64" not or invalid batch insert", pStmt->pSql->self);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "not or invalid batch insert"));
|
||||
}
|
||||
|
||||
if (pStmt->multiTbInsert) {
|
||||
if (pStmt->last != STMT_SETTBNAME && pStmt->last != STMT_ADD_BATCH && pStmt->last != STMT_BIND_COL) {
|
||||
tscError("0x%"PRIx64" bind param status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "bind param status error"));
|
||||
}
|
||||
} else {
|
||||
if (pStmt->last != STMT_PREPARE && pStmt->last != STMT_ADD_BATCH && pStmt->last != STMT_BIND_COL && pStmt->last != STMT_EXECUTE) {
|
||||
tscError("0x%"PRIx64" bind param status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "bind param status error"));
|
||||
}
|
||||
}
|
||||
|
||||
pStmt->last = STMT_BIND_COL;
|
||||
|
||||
return insertStmtBindParamBatch(pStmt, bind, colIdx);
|
||||
STMT_RET(insertStmtBindParamBatch(pStmt, bind, colIdx));
|
||||
}
|
||||
|
||||
|
||||
|
@ -1746,44 +1767,42 @@ int taos_stmt_bind_single_param_batch(TAOS_STMT* stmt, TAOS_MULTI_BIND* bind, in
|
|||
int taos_stmt_add_batch(TAOS_STMT* stmt) {
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
if (stmt == NULL || pStmt->pSql == NULL || pStmt->taos == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (pStmt->isInsert) {
|
||||
if (pStmt->last != STMT_BIND && pStmt->last != STMT_BIND_COL) {
|
||||
tscError("0x%"PRIx64" add batch status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "add batch status error"));
|
||||
}
|
||||
|
||||
pStmt->last = STMT_ADD_BATCH;
|
||||
|
||||
return insertStmtAddBatch(pStmt);
|
||||
STMT_RET(insertStmtAddBatch(pStmt));
|
||||
}
|
||||
|
||||
return TSDB_CODE_COM_OPS_NOT_SUPPORT;
|
||||
STMT_RET(TSDB_CODE_COM_OPS_NOT_SUPPORT);
|
||||
}
|
||||
|
||||
int taos_stmt_reset(TAOS_STMT* stmt) {
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
if (pStmt->isInsert) {
|
||||
return insertStmtReset(pStmt);
|
||||
STMT_RET(insertStmtReset(pStmt));
|
||||
}
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
}
|
||||
|
||||
int taos_stmt_execute(TAOS_STMT* stmt) {
|
||||
int ret = 0;
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
if (stmt == NULL || pStmt->pSql == NULL || pStmt->taos == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (pStmt->isInsert) {
|
||||
if (pStmt->last != STMT_ADD_BATCH) {
|
||||
tscError("0x%"PRIx64" exec status error, last:%d", pStmt->pSql->self, pStmt->last);
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "exec status error"));
|
||||
}
|
||||
|
||||
pStmt->last = STMT_EXECUTE;
|
||||
|
@ -1809,7 +1828,7 @@ int taos_stmt_execute(TAOS_STMT* stmt) {
|
|||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
STMT_RET(ret);
|
||||
}
|
||||
|
||||
TAOS_RES *taos_stmt_use_result(TAOS_STMT* stmt) {
|
||||
|
@ -1833,32 +1852,30 @@ int taos_stmt_is_insert(TAOS_STMT *stmt, int *insert) {
|
|||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
|
||||
if (stmt == NULL || pStmt->taos == NULL || pStmt->pSql == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (insert) *insert = pStmt->isInsert;
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
}
|
||||
|
||||
int taos_stmt_num_params(TAOS_STMT *stmt, int *nums) {
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
|
||||
if (stmt == NULL || pStmt->taos == NULL || pStmt->pSql == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (pStmt->isInsert) {
|
||||
SSqlObj* pSql = pStmt->pSql;
|
||||
SSqlCmd *pCmd = &pSql->cmd;
|
||||
*nums = pCmd->insertParam.numOfParams;
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
} else {
|
||||
SNormalStmt* normal = &pStmt->normal;
|
||||
*nums = normal->numParams;
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1866,8 +1883,7 @@ int taos_stmt_get_param(TAOS_STMT *stmt, int idx, int *type, int *bytes) {
|
|||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
|
||||
if (stmt == NULL || pStmt->taos == NULL || pStmt->pSql == NULL) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
return TSDB_CODE_TSC_DISCONNECTED;
|
||||
STMT_RET(TSDB_CODE_TSC_DISCONNECTED);
|
||||
}
|
||||
|
||||
if (pStmt->isInsert) {
|
||||
|
@ -1884,24 +1900,37 @@ int taos_stmt_get_param(TAOS_STMT *stmt, int idx, int *type, int *bytes) {
|
|||
tscGetDataBlockFromList(pCmd->insertParam.pTableBlockHashList, pTableMeta->id.uid, TSDB_PAYLOAD_SIZE, sizeof(SSubmitBlk),
|
||||
pTableMeta->tableInfo.rowSize, &pTableMetaInfo->name, pTableMeta, &pBlock, NULL);
|
||||
if (ret != 0) {
|
||||
// todo handle error
|
||||
STMT_RET(ret);
|
||||
}
|
||||
|
||||
if (idx<0 || idx>=pBlock->numOfParams) {
|
||||
tscError("0x%"PRIx64" param %d: out of range", pStmt->pSql->self, idx);
|
||||
abort();
|
||||
STMT_RET(invalidOperationMsg(tscGetErrorMsgPayload(&pStmt->pSql->cmd), "idx out of range"));
|
||||
}
|
||||
|
||||
SParamInfo* param = &pBlock->params[idx];
|
||||
if (type) *type = param->type;
|
||||
if (bytes) *bytes = param->bytes;
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
STMT_RET(TSDB_CODE_SUCCESS);
|
||||
} else {
|
||||
return TSDB_CODE_TSC_APP_ERROR;
|
||||
STMT_RET(TSDB_CODE_COM_OPS_NOT_SUPPORT);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
char *taos_stmt_errstr(TAOS_STMT *stmt) {
|
||||
STscStmt* pStmt = (STscStmt*)stmt;
|
||||
|
||||
if (stmt == NULL) {
|
||||
return (char*) tstrerror(terrno);
|
||||
}
|
||||
|
||||
return taos_errstr(pStmt->pSql);
|
||||
}
|
||||
|
||||
|
||||
|
||||
const char *taos_data_type(int type) {
|
||||
switch (type) {
|
||||
case TSDB_DATA_TYPE_NULL: return "TSDB_DATA_TYPE_NULL";
|
||||
|
|
|
@ -63,6 +63,9 @@ static SExprInfo* doAddProjectCol(SQueryInfo* pQueryInfo, int32_t colIndex, int3
|
|||
static int32_t setShowInfo(SSqlObj* pSql, SSqlInfo* pInfo);
|
||||
static char* getAccountId(SSqlObj* pSql);
|
||||
|
||||
static bool serializeExprListToVariant(SArray* pList, tVariant **dest, int16_t colType);
|
||||
static int32_t validateParamOfRelationIn(tVariant *pVar, int32_t colType);
|
||||
|
||||
static bool has(SArray* pFieldList, int32_t startIdx, const char* name);
|
||||
static char* cloneCurrentDBName(SSqlObj* pSql);
|
||||
static int32_t getDelimiterIndex(SStrToken* pTableName);
|
||||
|
@ -134,14 +137,97 @@ static bool validateDebugFlag(int32_t v);
|
|||
static int32_t checkQueryRangeForFill(SSqlCmd* pCmd, SQueryInfo* pQueryInfo);
|
||||
static int32_t loadAllTableMeta(SSqlObj* pSql, struct SSqlInfo* pInfo);
|
||||
|
||||
static bool isTimeWindowQuery(SQueryInfo* pQueryInfo) {
|
||||
static bool isTimeWindowQuery(SQueryInfo* pQueryInfo) {
|
||||
return pQueryInfo->interval.interval > 0 || pQueryInfo->sessionWindow.gap > 0;
|
||||
}
|
||||
|
||||
|
||||
int16_t getNewResColId(SSqlCmd* pCmd) {
|
||||
return pCmd->resColumnId--;
|
||||
}
|
||||
|
||||
// serialize expr in exprlist to binary
|
||||
// formate "type | size | value"
|
||||
bool serializeExprListToVariant(SArray* pList, tVariant **dst, int16_t colType) {
|
||||
bool ret = false;
|
||||
if (!pList || pList->size <= 0) {
|
||||
return ret;
|
||||
}
|
||||
if (colType == TSDB_DATA_TYPE_DOUBLE || colType == TSDB_DATA_TYPE_FLOAT) {
|
||||
return ret;
|
||||
}
|
||||
|
||||
tSqlExprItem* item = (tSqlExprItem *)taosArrayGet(pList, 0);
|
||||
int32_t firstTokenType = item->pNode->token.type;
|
||||
int32_t type = firstTokenType;
|
||||
|
||||
//nchar to binary and
|
||||
toTSDBType(type);
|
||||
if (type != colType && (type != TSDB_DATA_TYPE_BINARY || colType != TSDB_DATA_TYPE_NCHAR)) {
|
||||
return false;
|
||||
}
|
||||
type = colType;
|
||||
|
||||
SBufferWriter bw = tbufInitWriter( NULL, false );
|
||||
tbufEnsureCapacity(&bw, 512);
|
||||
|
||||
int32_t size = (int32_t)(pList->size);
|
||||
tbufWriteUint32(&bw, type);
|
||||
tbufWriteInt32(&bw, size);
|
||||
|
||||
for (int32_t i = 0; i < size; i++) {
|
||||
tSqlExpr* pSub = ((tSqlExprItem*)(taosArrayGet(pList, i)))->pNode;
|
||||
|
||||
// check all the token type in expr list same or not
|
||||
if (firstTokenType != pSub->token.type) {
|
||||
break;
|
||||
}
|
||||
|
||||
toTSDBType(pSub->token.type);
|
||||
|
||||
tVariant var;
|
||||
tVariantCreate(&var, &pSub->token);
|
||||
if (type == TSDB_DATA_TYPE_BOOL || type == TSDB_DATA_TYPE_TINYINT || type == TSDB_DATA_TYPE_SMALLINT
|
||||
|| type == TSDB_DATA_TYPE_BIGINT || type == TSDB_DATA_TYPE_INT) {
|
||||
tbufWriteInt64(&bw, var.i64);
|
||||
} else if (type == TSDB_DATA_TYPE_DOUBLE || type == TSDB_DATA_TYPE_FLOAT) {
|
||||
tbufWriteDouble(&bw, var.dKey);
|
||||
} else if (type == TSDB_DATA_TYPE_BINARY){
|
||||
tbufWriteBinary(&bw, var.pz, var.nLen);
|
||||
} else if (type == TSDB_DATA_TYPE_NCHAR) {
|
||||
char *buf = (char *)calloc(1, (var.nLen + 1)*TSDB_NCHAR_SIZE);
|
||||
if (tVariantDump(&var, buf, type, false) != TSDB_CODE_SUCCESS) {
|
||||
free(buf);
|
||||
tVariantDestroy(&var);
|
||||
break;
|
||||
}
|
||||
tbufWriteBinary(&bw, buf, twcslen((wchar_t *)buf) * TSDB_NCHAR_SIZE);
|
||||
free(buf);
|
||||
}
|
||||
tVariantDestroy(&var);
|
||||
|
||||
if (i == size - 1) { ret = true;}
|
||||
}
|
||||
|
||||
if (ret == true) {
|
||||
if ((*dst = calloc(1, sizeof(tVariant))) != NULL) {
|
||||
tVariantCreateFromBinary(*dst, tbufGetData(&bw, false), tbufTell(&bw), TSDB_DATA_TYPE_BINARY);
|
||||
} else {
|
||||
ret = false;
|
||||
}
|
||||
}
|
||||
tbufCloseWriter(&bw);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int32_t validateParamOfRelationIn(tVariant *pVar, int32_t colType) {
|
||||
if (pVar->nType != TSDB_DATA_TYPE_BINARY) {
|
||||
return -1;
|
||||
}
|
||||
SBufferReader br = tbufInitReader(pVar->pz, pVar->nLen, false);
|
||||
return colType == TSDB_DATA_TYPE_NCHAR ? 0 : (tbufReadUint32(&br) == colType ? 0: -1);
|
||||
}
|
||||
|
||||
static uint8_t convertOptr(SStrToken *pToken) {
|
||||
switch (pToken->type) {
|
||||
case TK_LT:
|
||||
|
@ -162,6 +248,7 @@ static uint8_t convertOptr(SStrToken *pToken) {
|
|||
return TSDB_RELATION_EQUAL;
|
||||
case TK_PLUS:
|
||||
return TSDB_BINARY_OP_ADD;
|
||||
|
||||
case TK_MINUS:
|
||||
return TSDB_BINARY_OP_SUBTRACT;
|
||||
case TK_STAR:
|
||||
|
@ -177,6 +264,8 @@ static uint8_t convertOptr(SStrToken *pToken) {
|
|||
return TSDB_RELATION_ISNULL;
|
||||
case TK_NOTNULL:
|
||||
return TSDB_RELATION_NOTNULL;
|
||||
case TK_IN:
|
||||
return TSDB_RELATION_IN;
|
||||
default: { return 0; }
|
||||
}
|
||||
}
|
||||
|
@ -2157,11 +2246,14 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col
|
|||
case TSDB_FUNC_MIN:
|
||||
case TSDB_FUNC_MAX:
|
||||
case TSDB_FUNC_DIFF:
|
||||
case TSDB_FUNC_DERIVATIVE:
|
||||
case TSDB_FUNC_STDDEV:
|
||||
case TSDB_FUNC_LEASTSQR: {
|
||||
// 1. valid the number of parameters
|
||||
if (pItem->pNode->pParam == NULL || (functionId != TSDB_FUNC_LEASTSQR && taosArrayGetSize(pItem->pNode->pParam) != 1) ||
|
||||
(functionId == TSDB_FUNC_LEASTSQR && taosArrayGetSize(pItem->pNode->pParam) != 3)) {
|
||||
int32_t numOfParams = (pItem->pNode->pParam == NULL)? 0: (int32_t) taosArrayGetSize(pItem->pNode->pParam);
|
||||
if (pItem->pNode->pParam == NULL ||
|
||||
(functionId != TSDB_FUNC_LEASTSQR && functionId != TSDB_FUNC_DERIVATIVE && numOfParams != 1) ||
|
||||
((functionId == TSDB_FUNC_LEASTSQR || functionId == TSDB_FUNC_DERIVATIVE) && numOfParams != 3)) {
|
||||
/* no parameters or more than one parameter for function */
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg2);
|
||||
}
|
||||
|
@ -2182,11 +2274,13 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col
|
|||
|
||||
// 2. check if sql function can be applied on this column data type
|
||||
pTableMetaInfo = tscGetMetaInfo(pQueryInfo, index.tableIndex);
|
||||
STableComInfo info = tscGetTableInfo(pTableMetaInfo->pTableMeta);
|
||||
|
||||
SSchema* pSchema = tscGetTableColumnSchema(pTableMetaInfo->pTableMeta, index.columnIndex);
|
||||
|
||||
if (!IS_NUMERIC_TYPE(pSchema->type)) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg1);
|
||||
} else if (IS_UNSIGNED_NUMERIC_TYPE(pSchema->type) && functionId == TSDB_FUNC_DIFF) {
|
||||
} else if (IS_UNSIGNED_NUMERIC_TYPE(pSchema->type) && (functionId == TSDB_FUNC_DIFF || functionId == TSDB_FUNC_DERIVATIVE)) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg9);
|
||||
}
|
||||
|
||||
|
@ -2200,11 +2294,11 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col
|
|||
}
|
||||
|
||||
// set the first column ts for diff query
|
||||
if (functionId == TSDB_FUNC_DIFF) {
|
||||
if (functionId == TSDB_FUNC_DIFF || functionId == TSDB_FUNC_DERIVATIVE) {
|
||||
colIndex += 1;
|
||||
SColumnIndex indexTS = {.tableIndex = index.tableIndex, .columnIndex = 0};
|
||||
SExprInfo* pExpr = tscExprAppend(pQueryInfo, TSDB_FUNC_TS_DUMMY, &indexTS, TSDB_DATA_TYPE_TIMESTAMP, TSDB_KEYSIZE,
|
||||
getNewResColId(pCmd), TSDB_KEYSIZE, false);
|
||||
SExprInfo* pExpr = tscExprAppend(pQueryInfo, TSDB_FUNC_TS_DUMMY, &indexTS, TSDB_DATA_TYPE_TIMESTAMP,
|
||||
TSDB_KEYSIZE, getNewResColId(pCmd), TSDB_KEYSIZE, false);
|
||||
|
||||
SColumnList ids = createColumnList(1, 0, 0);
|
||||
insertResultField(pQueryInfo, 0, &ids, TSDB_KEYSIZE, TSDB_DATA_TYPE_TIMESTAMP, aAggs[TSDB_FUNC_TS_DUMMY].name, pExpr);
|
||||
|
@ -2230,12 +2324,29 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col
|
|||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
}
|
||||
|
||||
tscExprAddParams(&pExpr->base, val, TSDB_DATA_TYPE_DOUBLE, sizeof(double));
|
||||
tscExprAddParams(&pExpr->base, val, TSDB_DATA_TYPE_DOUBLE, DOUBLE_BYTES);
|
||||
} else if (functionId == TSDB_FUNC_IRATE) {
|
||||
STableComInfo info = tscGetTableInfo(pTableMetaInfo->pTableMeta);
|
||||
int64_t prec = info.precision;
|
||||
|
||||
tscExprAddParams(&pExpr->base, (char*)&prec, TSDB_DATA_TYPE_BIGINT, LONG_BYTES);
|
||||
} else if (functionId == TSDB_FUNC_DERIVATIVE) {
|
||||
char val[8] = {0};
|
||||
|
||||
int64_t tickPerSec = 0;
|
||||
if (tVariantDump(&pParamElem[1].pNode->value, (char*) &tickPerSec, TSDB_DATA_TYPE_BIGINT, true) < 0) {
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
}
|
||||
|
||||
if (info.precision == TSDB_TIME_PRECISION_MILLI) {
|
||||
tickPerSec /= 1000;
|
||||
}
|
||||
|
||||
tscExprAddParams(&pExpr->base, (char*) &tickPerSec, TSDB_DATA_TYPE_BIGINT, LONG_BYTES);
|
||||
memset(val, 0, tListLen(val));
|
||||
if (tVariantDump(&pParamElem[2].pNode->value, val, TSDB_DATA_TYPE_BIGINT, true) < 0) {
|
||||
return TSDB_CODE_TSC_INVALID_OPERATION;
|
||||
}
|
||||
|
||||
tscExprAddParams(&pExpr->base, val, TSDB_DATA_TYPE_BIGINT, LONG_BYTES);
|
||||
}
|
||||
|
||||
SColumnList ids = createColumnList(1, index.tableIndex, index.columnIndex);
|
||||
|
@ -2935,8 +3046,8 @@ void tscRestoreFuncForSTableQuery(SQueryInfo* pQueryInfo) {
|
|||
}
|
||||
|
||||
bool hasUnsupportFunctionsForSTableQuery(SSqlCmd* pCmd, SQueryInfo* pQueryInfo) {
|
||||
const char* msg1 = "TWA not allowed to apply to super table directly";
|
||||
const char* msg2 = "TWA only support group by tbname for super table query";
|
||||
const char* msg1 = "TWA/Diff not allowed to apply to super table directly";
|
||||
const char* msg2 = "TWA/Diff only support group by tbname for super table query";
|
||||
const char* msg3 = "function not support for super table query";
|
||||
|
||||
// filter sql function not supported by metric query yet.
|
||||
|
@ -2949,7 +3060,7 @@ bool hasUnsupportFunctionsForSTableQuery(SSqlCmd* pCmd, SQueryInfo* pQueryInfo)
|
|||
}
|
||||
}
|
||||
|
||||
if (tscIsTWAQuery(pQueryInfo)) {
|
||||
if (tscIsTWAQuery(pQueryInfo) || tscIsDiffQuery(pQueryInfo)) {
|
||||
if (pQueryInfo->groupbyExpr.numOfGroupCols == 0) {
|
||||
invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg1);
|
||||
return true;
|
||||
|
@ -3207,6 +3318,25 @@ static int32_t doExtractColumnFilterInfo(SSqlCmd* pCmd, SQueryInfo* pQueryInfo,
|
|||
retVal = tVariantDump(&pRight->value, (char*)&pColumnFilter->upperBndd, colType, false);
|
||||
|
||||
// TK_GT,TK_GE,TK_EQ,TK_NE are based on the pColumn->lowerBndd
|
||||
} else if (pExpr->tokenId == TK_IN) {
|
||||
tVariant *pVal;
|
||||
if (pRight->tokenId != TK_SET || !serializeExprListToVariant(pRight->pParam, &pVal, colType) || colType == TSDB_DATA_TYPE_TIMESTAMP) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg);
|
||||
}
|
||||
if (validateParamOfRelationIn(pVal, colType) != TSDB_CODE_SUCCESS) {
|
||||
tVariantDestroy(pVal);
|
||||
free(pVal);
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg);
|
||||
}
|
||||
pColumnFilter->pz = (int64_t)calloc(1, pVal->nLen + 1);
|
||||
pColumnFilter->len = pVal->nLen;
|
||||
pColumnFilter->filterstr = 1;
|
||||
memcpy((char *)(pColumnFilter->pz), (char *)(pVal->pz), pVal->nLen);
|
||||
//retVal = tVariantDump(pVal, (char *)(pColumnFilter->pz), TSDB_DATA_TYPE_BINARY, false);
|
||||
|
||||
tVariantDestroy(pVal);
|
||||
free(pVal);
|
||||
|
||||
} else if (colType == TSDB_DATA_TYPE_BINARY) {
|
||||
pColumnFilter->pz = (int64_t)calloc(1, bufLen * TSDB_NCHAR_SIZE);
|
||||
pColumnFilter->len = pRight->value.nLen;
|
||||
|
@ -3255,6 +3385,9 @@ static int32_t doExtractColumnFilterInfo(SSqlCmd* pCmd, SQueryInfo* pQueryInfo,
|
|||
case TK_NOTNULL:
|
||||
pColumnFilter->lowerRelOptr = TSDB_RELATION_NOTNULL;
|
||||
break;
|
||||
case TK_IN:
|
||||
pColumnFilter->lowerRelOptr = TSDB_RELATION_IN;
|
||||
break;
|
||||
default:
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg);
|
||||
}
|
||||
|
@ -3370,7 +3503,7 @@ static int32_t extractColumnFilterInfo(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, SC
|
|||
&& pExpr->tokenId != TK_ISNULL
|
||||
&& pExpr->tokenId != TK_NOTNULL
|
||||
&& pExpr->tokenId != TK_LIKE
|
||||
) {
|
||||
&& pExpr->tokenId != TK_IN) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg2);
|
||||
}
|
||||
} else {
|
||||
|
@ -3380,7 +3513,7 @@ static int32_t extractColumnFilterInfo(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, SC
|
|||
|
||||
if (pSchema->type == TSDB_DATA_TYPE_BOOL) {
|
||||
int32_t t = pExpr->tokenId;
|
||||
if (t != TK_EQ && t != TK_NE && t != TK_NOTNULL && t != TK_ISNULL) {
|
||||
if (t != TK_EQ && t != TK_NE && t != TK_NOTNULL && t != TK_ISNULL && t != TK_IN) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg3);
|
||||
}
|
||||
}
|
||||
|
@ -4422,7 +4555,11 @@ static int32_t validateTagCondExpr(SSqlCmd* pCmd, tExprNode *p) {
|
|||
free(tmp);
|
||||
} else {
|
||||
double tmp;
|
||||
retVal = tVariantDump(vVariant, (char*)&tmp, schemaType, false);
|
||||
if (p->_node.optr == TSDB_RELATION_IN) {
|
||||
retVal = validateParamOfRelationIn(vVariant, schemaType);
|
||||
} else {
|
||||
retVal = tVariantDump(vVariant, (char*)&tmp, schemaType, false);
|
||||
}
|
||||
}
|
||||
|
||||
if (retVal != TSDB_CODE_SUCCESS) {
|
||||
|
@ -6376,7 +6513,7 @@ int32_t doFunctionsCompatibleCheck(SSqlCmd* pCmd, SQueryInfo* pQueryInfo) {
|
|||
}
|
||||
|
||||
if (IS_MULTIOUTPUT(aAggs[functId].status) && functId != TSDB_FUNC_TOP && functId != TSDB_FUNC_BOTTOM &&
|
||||
functId != TSDB_FUNC_TAGPRJ && functId != TSDB_FUNC_PRJ) {
|
||||
functId != TSDB_FUNC_DIFF && functId != TSDB_FUNC_TAGPRJ && functId != TSDB_FUNC_PRJ) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), msg1);
|
||||
}
|
||||
|
||||
|
@ -6858,7 +6995,7 @@ int32_t doCheckForStream(SSqlObj* pSql, SSqlInfo* pInfo) {
|
|||
const char* msg6 = "from missing in subclause";
|
||||
const char* msg7 = "time interval is required";
|
||||
const char* msg8 = "the first column should be primary timestamp column";
|
||||
|
||||
|
||||
SSqlCmd* pCmd = &pSql->cmd;
|
||||
SQueryInfo* pQueryInfo = tscGetQueryInfo(pCmd);
|
||||
assert(pQueryInfo->numOfTables == 1);
|
||||
|
@ -7812,14 +7949,15 @@ int32_t validateSqlNode(SSqlObj* pSql, SSqlNode* pSqlNode, SQueryInfo* pQueryInf
|
|||
}
|
||||
|
||||
{ // set the query info
|
||||
pQueryInfo->projectionQuery = tscIsProjectionQuery(pQueryInfo);
|
||||
pQueryInfo->hasFilter = tscHasColumnFilter(pQueryInfo);
|
||||
pQueryInfo->simpleAgg = isSimpleAggregateRv(pQueryInfo);
|
||||
pQueryInfo->onlyTagQuery = onlyTagPrjFunction(pQueryInfo);
|
||||
pQueryInfo->groupbyColumn = tscGroupbyColumn(pQueryInfo);
|
||||
pQueryInfo->projectionQuery = tscIsProjectionQuery(pQueryInfo);
|
||||
pQueryInfo->hasFilter = tscHasColumnFilter(pQueryInfo);
|
||||
pQueryInfo->simpleAgg = isSimpleAggregateRv(pQueryInfo);
|
||||
pQueryInfo->onlyTagQuery = onlyTagPrjFunction(pQueryInfo);
|
||||
pQueryInfo->groupbyColumn = tscGroupbyColumn(pQueryInfo);
|
||||
|
||||
pQueryInfo->arithmeticOnAgg = tsIsArithmeticQueryOnAggResult(pQueryInfo);
|
||||
pQueryInfo->arithmeticOnAgg = tsIsArithmeticQueryOnAggResult(pQueryInfo);
|
||||
pQueryInfo->orderProjectQuery = tscOrderedProjectionQueryOnSTable(pQueryInfo, 0);
|
||||
pQueryInfo->diffQuery = tscIsDiffQuery(pQueryInfo);
|
||||
|
||||
SExprInfo** p = NULL;
|
||||
int32_t numOfExpr = 0;
|
||||
|
@ -7930,6 +8068,24 @@ int32_t exprTreeFromSqlExpr(SSqlCmd* pCmd, tExprNode **pExpr, const tSqlExpr* pS
|
|||
}
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
} else if (pSqlExpr->tokenId == TK_SET) {
|
||||
int32_t type = -1;
|
||||
STableMeta* pTableMeta = tscGetMetaInfo(pQueryInfo, 0)->pTableMeta;
|
||||
if (pCols != NULL) {
|
||||
SColIndex* idx = taosArrayGet(pCols, 0);
|
||||
SSchema* pSchema = tscGetTableColumnSchema(pTableMeta, idx->colIndex);
|
||||
if (pSchema != NULL) {
|
||||
type = pSchema->type;
|
||||
}
|
||||
}
|
||||
|
||||
tVariant *pVal;
|
||||
if (serializeExprListToVariant(pSqlExpr->pParam, &pVal, type) == false) {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), "not support filter expression");
|
||||
}
|
||||
*pExpr = calloc(1, sizeof(tExprNode));
|
||||
(*pExpr)->nodeType = TSQL_NODE_VALUE;
|
||||
(*pExpr)->pVal = pVal;
|
||||
} else {
|
||||
return invalidOperationMsg(tscGetErrorMsgPayload(pCmd), "not support filter expression");
|
||||
}
|
||||
|
|
|
@ -1588,7 +1588,7 @@ int tscProcessLocalRetrieveRsp(SSqlObj *pSql) {
|
|||
return tscLocalResultCommonBuilder(pSql, numOfRes);
|
||||
}
|
||||
|
||||
int tscProcessRetrieveLocalMergeRsp(SSqlObj *pSql) {
|
||||
int tscProcessRetrieveGlobalMergeRsp(SSqlObj *pSql) {
|
||||
SSqlRes *pRes = &pSql->res;
|
||||
SSqlCmd* pCmd = &pSql->cmd;
|
||||
|
||||
|
@ -1615,12 +1615,13 @@ int tscProcessRetrieveLocalMergeRsp(SSqlObj *pSql) {
|
|||
taosArrayPush(group, &tableKeyInfo);
|
||||
taosArrayPush(tableGroupInfo.pGroupList, &group);
|
||||
|
||||
pQueryInfo->pQInfo = createQInfoFromQueryNode(pQueryInfo, &tableGroupInfo, NULL, NULL, pRes->pMerger, MERGE_STAGE);
|
||||
tscDebug("0x%"PRIx64" create QInfo 0x%"PRIx64" to execute query processing", pSql->self, pSql->self);
|
||||
pQueryInfo->pQInfo = createQInfoFromQueryNode(pQueryInfo, &tableGroupInfo, NULL, NULL, pRes->pMerger, MERGE_STAGE, pSql->self);
|
||||
}
|
||||
|
||||
uint64_t localQueryId = 0;
|
||||
uint64_t localQueryId = pSql->self;
|
||||
qTableQuery(pQueryInfo->pQInfo, &localQueryId);
|
||||
convertQueryResult(pRes, pQueryInfo);
|
||||
convertQueryResult(pRes, pQueryInfo, pSql->self);
|
||||
|
||||
code = pRes->code;
|
||||
if (pRes->code == TSDB_CODE_SUCCESS) {
|
||||
|
@ -2689,7 +2690,7 @@ void tscInitMsgsFp() {
|
|||
|
||||
tscProcessMsgRsp[TSDB_SQL_RETRIEVE_EMPTY_RESULT] = tscProcessEmptyResultRsp;
|
||||
|
||||
tscProcessMsgRsp[TSDB_SQL_RETRIEVE_LOCALMERGE] = tscProcessRetrieveLocalMergeRsp;
|
||||
tscProcessMsgRsp[TSDB_SQL_RETRIEVE_GLOBALMERGE] = tscProcessRetrieveGlobalMergeRsp;
|
||||
|
||||
tscProcessMsgRsp[TSDB_SQL_ALTER_TABLE] = tscProcessAlterTableMsgRsp;
|
||||
tscProcessMsgRsp[TSDB_SQL_ALTER_DB] = tscProcessAlterDbMsgRsp;
|
||||
|
|
|
@ -456,7 +456,7 @@ static bool needToFetchNewBlock(SSqlObj* pSql) {
|
|||
|
||||
return (pRes->completed != true || hasMoreVnodesToTry(pSql) || hasMoreClauseToTry(pSql)) &&
|
||||
(pCmd->command == TSDB_SQL_RETRIEVE ||
|
||||
pCmd->command == TSDB_SQL_RETRIEVE_LOCALMERGE ||
|
||||
pCmd->command == TSDB_SQL_RETRIEVE_GLOBALMERGE ||
|
||||
pCmd->command == TSDB_SQL_TABLE_JOIN_RETRIEVE ||
|
||||
pCmd->command == TSDB_SQL_FETCH ||
|
||||
pCmd->command == TSDB_SQL_SHOW ||
|
||||
|
|
|
@ -1977,9 +1977,8 @@ void tscHandleMasterJoinQuery(SSqlObj* pSql) {
|
|||
}
|
||||
|
||||
memset(pSql->subState.states, 0, sizeof(*pSql->subState.states) * pSql->subState.numOfSub);
|
||||
tscDebug("0x%"PRIx64" reset all sub states to 0", pSql->self);
|
||||
tscDebug("0x%"PRIx64" reset all sub states to 0, start subquery, total:%d", pSql->self, pQueryInfo->numOfTables);
|
||||
|
||||
tscDebug("0x%"PRIx64" start subquery, total:%d", pSql->self, pQueryInfo->numOfTables);
|
||||
for (int32_t i = 0; i < pQueryInfo->numOfTables; ++i) {
|
||||
SJoinSupporter *pSupporter = tscCreateJoinSupporter(pSql, i);
|
||||
if (pSupporter == NULL) { // failed to create support struct, abort current query
|
||||
|
@ -2424,7 +2423,7 @@ int32_t tscHandleMasterSTableQuery(SSqlObj *pSql) {
|
|||
|
||||
// pRes->code check only serves in launching metric sub-queries
|
||||
if (pRes->code == TSDB_CODE_TSC_QUERY_CANCELLED) {
|
||||
pCmd->command = TSDB_SQL_RETRIEVE_LOCALMERGE; // enable the abort of kill super table function.
|
||||
pCmd->command = TSDB_SQL_RETRIEVE_GLOBALMERGE; // enable the abort of kill super table function.
|
||||
return pRes->code;
|
||||
}
|
||||
|
||||
|
@ -2780,7 +2779,7 @@ static void tscAllDataRetrievedFromDnode(SRetrieveSupport *trsupport, SSqlObj* p
|
|||
if (code == TSDB_CODE_SUCCESS && trsupport->pExtMemBuffer == NULL) {
|
||||
pParentSql->cmd.command = TSDB_SQL_RETRIEVE_EMPTY_RESULT; // no result, set the result empty
|
||||
} else {
|
||||
pParentSql->cmd.command = TSDB_SQL_RETRIEVE_LOCALMERGE;
|
||||
pParentSql->cmd.command = TSDB_SQL_RETRIEVE_GLOBALMERGE;
|
||||
}
|
||||
|
||||
tscCreateResPointerInfo(&pParentSql->res, pPQueryInfo);
|
||||
|
@ -3502,7 +3501,7 @@ static UNUSED_FUNC bool tscHasRemainDataInSubqueryResultSet(SSqlObj *pSql) {
|
|||
}
|
||||
|
||||
void* createQInfoFromQueryNode(SQueryInfo* pQueryInfo, STableGroupInfo* pTableGroupInfo, SOperatorInfo* pSourceOperator,
|
||||
char* sql, void* merger, int32_t stage) {
|
||||
char* sql, void* merger, int32_t stage, uint64_t qId) {
|
||||
assert(pQueryInfo != NULL);
|
||||
SQInfo *pQInfo = (SQInfo *)calloc(1, sizeof(SQInfo));
|
||||
if (pQInfo == NULL) {
|
||||
|
@ -3511,7 +3510,7 @@ void* createQInfoFromQueryNode(SQueryInfo* pQueryInfo, STableGroupInfo* pTableGr
|
|||
|
||||
// to make sure third party won't overwrite this structure
|
||||
pQInfo->signature = pQInfo;
|
||||
|
||||
pQInfo->qId = qId;
|
||||
SQueryRuntimeEnv *pRuntimeEnv = &pQInfo->runtimeEnv;
|
||||
SQueryAttr *pQueryAttr = &pQInfo->query;
|
||||
|
||||
|
|
|
@ -222,6 +222,8 @@ bool tscIsProjectionQueryOnSTable(SQueryInfo* pQueryInfo, int32_t tableIndex) {
|
|||
functionId != TSDB_FUNC_TS &&
|
||||
functionId != TSDB_FUNC_ARITHM &&
|
||||
functionId != TSDB_FUNC_TS_COMP &&
|
||||
functionId != TSDB_FUNC_DIFF &&
|
||||
functionId != TSDB_FUNC_TS_DUMMY &&
|
||||
functionId != TSDB_FUNC_TID_TAG) {
|
||||
return false;
|
||||
}
|
||||
|
@ -434,6 +436,23 @@ bool tscIsTWAQuery(SQueryInfo* pQueryInfo) {
|
|||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool tscIsDiffQuery(SQueryInfo* pQueryInfo) {
|
||||
size_t num = tscNumOfExprs(pQueryInfo);
|
||||
for(int32_t i = 0; i < num; ++i) {
|
||||
SExprInfo* pExpr = tscExprGet(pQueryInfo, i);
|
||||
if (pExpr == NULL || pExpr->base.functionId == TSDB_FUNC_TS_DUMMY) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pExpr->base.functionId == TSDB_FUNC_DIFF) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool tscIsSessionWindowQuery(SQueryInfo* pQueryInfo) {
|
||||
return pQueryInfo->sessionWindow.gap > 0;
|
||||
}
|
||||
|
@ -467,42 +486,12 @@ bool tscNeedReverseScan(SQueryInfo* pQueryInfo) {
|
|||
return false;
|
||||
}
|
||||
|
||||
bool isSimpleAggregate(SQueryInfo* pQueryInfo) {
|
||||
if (pQueryInfo->interval.interval > 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Note:top/bottom query is fixed output query
|
||||
if (tscIsTopBotQuery(pQueryInfo) || tscGroupbyColumn(pQueryInfo) || isTsCompQuery(pQueryInfo)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
size_t numOfExprs = tscNumOfExprs(pQueryInfo);
|
||||
for (int32_t i = 0; i < numOfExprs; ++i) {
|
||||
SExprInfo* pExpr = tscExprGet(pQueryInfo, i);
|
||||
if (pExpr == NULL) {
|
||||
continue;
|
||||
}
|
||||
|
||||
int32_t functionId = pExpr->base.functionId;
|
||||
if (functionId == TSDB_FUNC_TS || functionId == TSDB_FUNC_TS_DUMMY) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!IS_MULTIOUTPUT(aAggs[functionId].status)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool isSimpleAggregateRv(SQueryInfo* pQueryInfo) {
|
||||
if (pQueryInfo->interval.interval > 0 || pQueryInfo->sessionWindow.gap > 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (tscGroupbyColumn(pQueryInfo) || isTsCompQuery(pQueryInfo)) {
|
||||
if (tscIsDiffQuery(pQueryInfo)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -518,13 +507,13 @@ bool isSimpleAggregateRv(SQueryInfo* pQueryInfo) {
|
|||
continue;
|
||||
}
|
||||
|
||||
if (!IS_MULTIOUTPUT(aAggs[functionId].status)) {
|
||||
if ((!IS_MULTIOUTPUT(aAggs[functionId].status)) ||
|
||||
(functionId == TSDB_FUNC_TOP || functionId == TSDB_FUNC_BOTTOM || functionId == TSDB_FUNC_TS_COMP)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
bool isBlockDistQuery(SQueryInfo* pQueryInfo) {
|
||||
|
@ -812,6 +801,7 @@ static void fetchNextBlockIfCompleted(SOperatorInfo* pOperator, bool* newgroup)
|
|||
for (int32_t i = 0; i < pOperator->numOfUpstream; ++i) {
|
||||
SJoinStatus* pStatus = &pJoinInfo->status[i];
|
||||
if (pStatus->pBlock == NULL || pStatus->index >= pStatus->pBlock->info.rows) {
|
||||
tscDebug("Retrieve nest query result, index:%d, total:%d", i, pOperator->numOfUpstream);
|
||||
pStatus->pBlock = pOperator->upstream[i]->exec(pOperator->upstream[i], newgroup);
|
||||
pStatus->index = 0;
|
||||
|
||||
|
@ -1056,7 +1046,7 @@ SOperatorInfo* createJoinOperatorInfo(SOperatorInfo** pUpstream, int32_t numOfUp
|
|||
return pOperator;
|
||||
}
|
||||
|
||||
void convertQueryResult(SSqlRes* pRes, SQueryInfo* pQueryInfo) {
|
||||
void convertQueryResult(SSqlRes* pRes, SQueryInfo* pQueryInfo, uint64_t objId) {
|
||||
// set the correct result
|
||||
SSDataBlock* p = pQueryInfo->pQInfo->runtimeEnv.outputBuf;
|
||||
pRes->numOfRows = (p != NULL)? p->info.rows: 0;
|
||||
|
@ -1066,6 +1056,7 @@ void convertQueryResult(SSqlRes* pRes, SQueryInfo* pQueryInfo) {
|
|||
tscSetResRawPtrRv(pRes, pQueryInfo, p);
|
||||
}
|
||||
|
||||
tscDebug("0x%"PRIx64" retrieve result in pRes, numOfRows:%d", objId, pRes->numOfRows);
|
||||
pRes->row = 0;
|
||||
pRes->completed = (pRes->numOfRows == 0);
|
||||
}
|
||||
|
@ -1088,7 +1079,9 @@ static void createInputDataFilterInfo(SQueryInfo* px, int32_t numOfCol1, int32_t
|
|||
tfree(tableCols);
|
||||
}
|
||||
|
||||
void handleDownstreamOperator(SSqlObj** pSqlObjList, int32_t numOfUpstream, SQueryInfo* px, SSqlRes* pOutput) {
|
||||
void handleDownstreamOperator(SSqlObj** pSqlObjList, int32_t numOfUpstream, SQueryInfo* px, SSqlObj* pSql) {
|
||||
SSqlRes* pOutput = &pSql->res;
|
||||
|
||||
// handle the following query process
|
||||
if (px->pQInfo == NULL) {
|
||||
SColumnInfo* pColumnInfo = extractColumnInfoFromResult(px->colList);
|
||||
|
@ -1168,7 +1161,9 @@ void handleDownstreamOperator(SSqlObj** pSqlObjList, int32_t numOfUpstream, SQue
|
|||
}
|
||||
}
|
||||
|
||||
px->pQInfo = createQInfoFromQueryNode(px, &tableGroupInfo, pSourceOperator, NULL, NULL, MASTER_SCAN);
|
||||
tscDebug("0x%"PRIx64" create QInfo 0x%"PRIx64" to execute the main query while all nest queries are ready", pSql->self, pSql->self);
|
||||
px->pQInfo = createQInfoFromQueryNode(px, &tableGroupInfo, pSourceOperator, NULL, NULL, MASTER_SCAN, pSql->self);
|
||||
|
||||
tfree(pColumnInfo);
|
||||
tfree(schema);
|
||||
|
||||
|
@ -1176,9 +1171,9 @@ void handleDownstreamOperator(SSqlObj** pSqlObjList, int32_t numOfUpstream, SQue
|
|||
pSourceOperator->pRuntimeEnv = &px->pQInfo->runtimeEnv;
|
||||
}
|
||||
|
||||
uint64_t qId = 0;
|
||||
uint64_t qId = pSql->self;
|
||||
qTableQuery(px->pQInfo, &qId);
|
||||
convertQueryResult(pOutput, px);
|
||||
convertQueryResult(pOutput, px, pSql->self);
|
||||
}
|
||||
|
||||
static void tscDestroyResPointerInfo(SSqlRes* pRes) {
|
||||
|
@ -1374,7 +1369,7 @@ void tscFreeSqlObj(SSqlObj* pSql) {
|
|||
|
||||
SSqlCmd* pCmd = &pSql->cmd;
|
||||
int32_t cmd = pCmd->command;
|
||||
if (cmd < TSDB_SQL_INSERT || cmd == TSDB_SQL_RETRIEVE_LOCALMERGE || cmd == TSDB_SQL_RETRIEVE_EMPTY_RESULT ||
|
||||
if (cmd < TSDB_SQL_INSERT || cmd == TSDB_SQL_RETRIEVE_GLOBALMERGE || cmd == TSDB_SQL_RETRIEVE_EMPTY_RESULT ||
|
||||
cmd == TSDB_SQL_TABLE_JOIN_RETRIEVE) {
|
||||
tscRemoveFromSqlList(pSql);
|
||||
}
|
||||
|
@ -2177,6 +2172,7 @@ size_t tscNumOfExprs(SQueryInfo* pQueryInfo) {
|
|||
return taosArrayGetSize(pQueryInfo->exprList);
|
||||
}
|
||||
|
||||
// todo REFACTOR
|
||||
void tscExprAddParams(SSqlExpr* pExpr, char* argument, int32_t type, int32_t bytes) {
|
||||
assert (pExpr != NULL || argument != NULL || bytes != 0);
|
||||
|
||||
|
@ -3278,7 +3274,6 @@ SSqlObj* createSubqueryObj(SSqlObj* pSql, int16_t tableIndex, __async_cb_func_t
|
|||
pNewQueryInfo->numOfTables = 0;
|
||||
pNewQueryInfo->pTableMetaInfo = NULL;
|
||||
pNewQueryInfo->bufLen = pQueryInfo->bufLen;
|
||||
|
||||
pNewQueryInfo->buf = malloc(pQueryInfo->bufLen);
|
||||
if (pNewQueryInfo->buf == NULL) {
|
||||
terrno = TSDB_CODE_TSC_OUT_OF_MEMORY;
|
||||
|
@ -3438,7 +3433,7 @@ void doRetrieveSubqueryData(SSchedMsg *pMsg) {
|
|||
}
|
||||
|
||||
SQueryInfo *pQueryInfo = tscGetQueryInfo(&pSql->cmd);
|
||||
handleDownstreamOperator(pSql->pSubs, pSql->subState.numOfSub, pQueryInfo, &pSql->res);
|
||||
handleDownstreamOperator(pSql->pSubs, pSql->subState.numOfSub, pQueryInfo, pSql);
|
||||
|
||||
pSql->res.qId = -1;
|
||||
if (pSql->res.code == TSDB_CODE_SUCCESS) {
|
||||
|
@ -3468,13 +3463,12 @@ static void tscSubqueryRetrieveCallback(void* param, TAOS_RES* tres, int code) {
|
|||
}
|
||||
|
||||
pParentSql->cmd.active = pParentSql->cmd.pQueryInfo;
|
||||
|
||||
SSchedMsg schedMsg = {0};
|
||||
schedMsg.fp = doRetrieveSubqueryData;
|
||||
schedMsg.ahandle = (void *)pParentSql;
|
||||
schedMsg.thandle = (void *)1;
|
||||
schedMsg.msg = 0;
|
||||
taosScheduleTask(tscQhandle, &schedMsg);
|
||||
pParentSql->res.qId = -1;
|
||||
if (pSql->res.code == TSDB_CODE_SUCCESS) {
|
||||
(*pSql->fp)(pParentSql->param, pParentSql, pParentSql->res.numOfRows);
|
||||
} else {
|
||||
tscAsyncResultOnError(pParentSql);
|
||||
}
|
||||
}
|
||||
|
||||
// todo handle the failure
|
||||
|
@ -4238,7 +4232,8 @@ int32_t tscCreateQueryFromQueryInfo(SQueryInfo* pQueryInfo, SQueryAttr* pQueryAt
|
|||
pQueryAttr->hasTagResults = hasTagValOutput(pQueryInfo);
|
||||
pQueryAttr->stabledev = isStabledev(pQueryInfo);
|
||||
pQueryAttr->tsCompQuery = isTsCompQuery(pQueryInfo);
|
||||
pQueryAttr->simpleAgg = isSimpleAggregate(pQueryInfo);
|
||||
pQueryAttr->diffQuery = tscIsDiffQuery(pQueryInfo);
|
||||
pQueryAttr->simpleAgg = isSimpleAggregateRv(pQueryInfo);
|
||||
pQueryAttr->needReverseScan = tscNeedReverseScan(pQueryInfo);
|
||||
pQueryAttr->stableQuery = QUERY_IS_STABLE_QUERY(pQueryInfo->type);
|
||||
pQueryAttr->groupbyColumn = (!pQueryInfo->stateWindow) && tscGroupbyColumn(pQueryInfo);
|
||||
|
@ -4257,7 +4252,6 @@ int32_t tscCreateQueryFromQueryInfo(SQueryInfo* pQueryInfo, SQueryAttr* pQueryAt
|
|||
pQueryAttr->fillType = pQueryInfo->fillType;
|
||||
pQueryAttr->havingNum = pQueryInfo->havingFieldNum;
|
||||
|
||||
|
||||
if (pQueryInfo->order.order == TSDB_ORDER_ASC) { // TODO refactor
|
||||
pQueryAttr->window = pQueryInfo->window;
|
||||
} else {
|
||||
|
|
|
@ -76,7 +76,7 @@ enum {
|
|||
// SQL below for client local
|
||||
TSDB_DEFINE_SQL_TYPE( TSDB_SQL_LOCAL, "local" )
|
||||
TSDB_DEFINE_SQL_TYPE( TSDB_SQL_DESCRIBE_TABLE, "describe-table" )
|
||||
TSDB_DEFINE_SQL_TYPE( TSDB_SQL_RETRIEVE_LOCALMERGE, "retrieve-localmerge" )
|
||||
TSDB_DEFINE_SQL_TYPE( TSDB_SQL_RETRIEVE_GLOBALMERGE, "retrieve-globalmerge" )
|
||||
TSDB_DEFINE_SQL_TYPE( TSDB_SQL_TABLE_JOIN_RETRIEVE, "join-retrieve" )
|
||||
|
||||
TSDB_DEFINE_SQL_TYPE( TSDB_SQL_SHOW_CREATE_TABLE, "show-create-table")
|
||||
|
|
|
@ -94,6 +94,8 @@ bool exprTreeApplyFilter(tExprNode *pExpr, const void *pItem, SExprTraverseSupp
|
|||
void arithmeticTreeTraverse(tExprNode *pExprs, int32_t numOfRows, char *pOutput, void *param, int32_t order,
|
||||
char *(*cb)(void *, const char*, int32_t));
|
||||
|
||||
void buildFilterSetFromBinary(void **q, const char *buf, int32_t len);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -466,6 +466,32 @@ tExprNode* exprTreeFromTableName(const char* tbnameCond) {
|
|||
return expr;
|
||||
}
|
||||
|
||||
void buildFilterSetFromBinary(void **q, const char *buf, int32_t len) {
|
||||
SBufferReader br = tbufInitReader(buf, len, false);
|
||||
uint32_t type = tbufReadUint32(&br);
|
||||
SHashObj *pObj = taosHashInit(256, taosGetDefaultHashFunction(type), true, false);
|
||||
int dummy = -1;
|
||||
int32_t sz = tbufReadInt32(&br);
|
||||
for (int32_t i = 0; i < sz; i++) {
|
||||
if (type == TSDB_DATA_TYPE_BOOL || type == TSDB_DATA_TYPE_TINYINT || type == TSDB_DATA_TYPE_SMALLINT || type == TSDB_DATA_TYPE_BIGINT || type == TSDB_DATA_TYPE_INT) {
|
||||
int64_t val = tbufReadInt64(&br);
|
||||
taosHashPut(pObj, (char *)&val, sizeof(val), &dummy, sizeof(dummy));
|
||||
} else if (type == TSDB_DATA_TYPE_DOUBLE || type == TSDB_DATA_TYPE_FLOAT) {
|
||||
double val = tbufReadDouble(&br);
|
||||
taosHashPut(pObj, (char *)&val, sizeof(val), &dummy, sizeof(dummy));
|
||||
} else if (type == TSDB_DATA_TYPE_BINARY) {
|
||||
size_t t = 0;
|
||||
const char *val = tbufReadBinary(&br, &t);
|
||||
taosHashPut(pObj, (char *)val, t, &dummy, sizeof(dummy));
|
||||
} else if (type == TSDB_DATA_TYPE_NCHAR) {
|
||||
size_t t = 0;
|
||||
const char *val = tbufReadBinary(&br, &t);
|
||||
taosHashPut(pObj, (char *)val, t, &dummy, sizeof(dummy));
|
||||
}
|
||||
}
|
||||
*q = (void *)pObj;
|
||||
}
|
||||
|
||||
tExprNode* exprdup(tExprNode* pNode) {
|
||||
if (pNode == NULL) {
|
||||
return NULL;
|
||||
|
|
|
@ -8,10 +8,9 @@ IF (TD_MVN_INSTALLED)
|
|||
ADD_CUSTOM_COMMAND(OUTPUT ${JDBC_CMD_NAME}
|
||||
POST_BUILD
|
||||
COMMAND mvn -Dmaven.test.skip=true install -f ${CMAKE_CURRENT_SOURCE_DIR}/pom.xml
|
||||
COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/target/taos-jdbcdriver-2.0.29.jar ${LIBRARY_OUTPUT_PATH}
|
||||
COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/target/taos-jdbcdriver-2.0.30.jar ${LIBRARY_OUTPUT_PATH}
|
||||
COMMAND mvn -Dmaven.test.skip=true clean -f ${CMAKE_CURRENT_SOURCE_DIR}/pom.xml
|
||||
COMMENT "build jdbc driver")
|
||||
ADD_CUSTOM_TARGET(${JDBC_TARGET_NAME} ALL WORKING_DIRECTORY ${EXECUTABLE_OUTPUT_PATH} DEPENDS ${JDBC_CMD_NAME})
|
||||
ENDIF ()
|
||||
|
||||
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
|
||||
<groupId>com.taosdata.jdbc</groupId>
|
||||
<artifactId>taos-jdbcdriver</artifactId>
|
||||
<version>2.0.29</version>
|
||||
<version>2.0.30</version>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<name>JDBCDriver</name>
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
<modelVersion>4.0.0</modelVersion>
|
||||
<groupId>com.taosdata.jdbc</groupId>
|
||||
<artifactId>taos-jdbcdriver</artifactId>
|
||||
<version>2.0.29</version>
|
||||
<version>2.0.30</version>
|
||||
<packaging>jar</packaging>
|
||||
<name>JDBCDriver</name>
|
||||
<url>https://github.com/taosdata/TDengine/tree/master/src/connector/jdbc</url>
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -1,5 +1,7 @@
|
|||
package com.taosdata.jdbc;
|
||||
|
||||
import com.sun.org.apache.xpath.internal.operations.Bool;
|
||||
|
||||
import java.sql.ParameterMetaData;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Timestamp;
|
||||
|
@ -49,6 +51,22 @@ public abstract class AbstractParameterMetaData extends WrapperImpl implements P
|
|||
if (param < 1 && param >= parameters.length)
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_PARAMETER_INDEX_OUT_RANGE);
|
||||
|
||||
if (parameters[param - 1] instanceof Boolean)
|
||||
return TSDBConstants.BOOLEAN_PRECISION;
|
||||
if (parameters[param - 1] instanceof Byte)
|
||||
return TSDBConstants.TINYINT_PRECISION;
|
||||
if (parameters[param - 1] instanceof Short)
|
||||
return TSDBConstants.SMALLINT_PRECISION;
|
||||
if (parameters[param - 1] instanceof Integer)
|
||||
return TSDBConstants.INT_PRECISION;
|
||||
if (parameters[param - 1] instanceof Long)
|
||||
return TSDBConstants.BIGINT_PRECISION;
|
||||
if (parameters[param - 1] instanceof Timestamp)
|
||||
return TSDBConstants.TIMESTAMP_MS_PRECISION;
|
||||
if (parameters[param - 1] instanceof Float)
|
||||
return TSDBConstants.FLOAT_PRECISION;
|
||||
if (parameters[param - 1] instanceof Double)
|
||||
return TSDBConstants.DOUBLE_PRECISION;
|
||||
if (parameters[param - 1] instanceof String)
|
||||
return ((String) parameters[param - 1]).length();
|
||||
if (parameters[param - 1] instanceof byte[])
|
||||
|
@ -60,6 +78,11 @@ public abstract class AbstractParameterMetaData extends WrapperImpl implements P
|
|||
public int getScale(int param) throws SQLException {
|
||||
if (param < 1 && param >= parameters.length)
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_PARAMETER_INDEX_OUT_RANGE);
|
||||
|
||||
if (parameters[param - 1] instanceof Float)
|
||||
return TSDBConstants.FLOAT_SCALE;
|
||||
if (parameters[param - 1] instanceof Double)
|
||||
return TSDBConstants.DOUBLE_SCALE;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -66,10 +66,16 @@ public abstract class AbstractResultSet extends WrapperImpl implements ResultSet
|
|||
public abstract byte[] getBytes(int columnIndex) throws SQLException;
|
||||
|
||||
@Override
|
||||
public abstract Date getDate(int columnIndex) throws SQLException;
|
||||
public Date getDate(int columnIndex) throws SQLException {
|
||||
Timestamp timestamp = getTimestamp(columnIndex);
|
||||
return timestamp == null ? null : new Date(timestamp.getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public abstract Time getTime(int columnIndex) throws SQLException;
|
||||
public Time getTime(int columnIndex) throws SQLException {
|
||||
Timestamp timestamp = getTimestamp(columnIndex);
|
||||
return timestamp == null ? null : new Time(timestamp.getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public abstract Timestamp getTimestamp(int columnIndex) throws SQLException;
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -41,15 +41,15 @@ public abstract class TSDBConstants {
|
|||
public static final int TSDB_DATA_TYPE_BINARY = 8;
|
||||
public static final int TSDB_DATA_TYPE_TIMESTAMP = 9;
|
||||
public static final int TSDB_DATA_TYPE_NCHAR = 10;
|
||||
/*
|
||||
系统增加新的无符号数据类型,分别是:
|
||||
unsigned tinyint, 数值范围:0-254, NULL 为255
|
||||
unsigned smallint,数值范围: 0-65534, NULL 为65535
|
||||
unsigned int,数值范围:0-4294967294,NULL 为4294967295u
|
||||
unsigned bigint,数值范围:0-18446744073709551614u,NULL 为18446744073709551615u。
|
||||
example:
|
||||
create table tb(ts timestamp, a tinyint unsigned, b smallint unsigned, c int unsigned, d bigint unsigned);
|
||||
*/
|
||||
/**
|
||||
* 系统增加新的无符号数据类型,分别是:
|
||||
* unsigned tinyint, 数值范围:0-254, NULL 为255
|
||||
* unsigned smallint,数值范围: 0-65534, NULL 为65535
|
||||
* unsigned int,数值范围:0-4294967294,NULL 为4294967295u
|
||||
* unsigned bigint,数值范围:0-18446744073709551614u,NULL 为18446744073709551615u。
|
||||
* example:
|
||||
* create table tb(ts timestamp, a tinyint unsigned, b smallint unsigned, c int unsigned, d bigint unsigned);
|
||||
*/
|
||||
public static final int TSDB_DATA_TYPE_UTINYINT = 11; //unsigned tinyint
|
||||
public static final int TSDB_DATA_TYPE_USMALLINT = 12; //unsigned smallint
|
||||
public static final int TSDB_DATA_TYPE_UINT = 13; //unsigned int
|
||||
|
@ -57,6 +57,47 @@ public abstract class TSDBConstants {
|
|||
// nchar column max length
|
||||
public static final int maxFieldSize = 16 * 1024;
|
||||
|
||||
// precision for data types
|
||||
public static final int BOOLEAN_PRECISION = 1;
|
||||
public static final int TINYINT_PRECISION = 4;
|
||||
public static final int SMALLINT_PRECISION = 6;
|
||||
public static final int INT_PRECISION = 11;
|
||||
public static final int BIGINT_PRECISION = 20;
|
||||
public static final int FLOAT_PRECISION = 12;
|
||||
public static final int DOUBLE_PRECISION = 22;
|
||||
public static final int TIMESTAMP_MS_PRECISION = 23;
|
||||
public static final int TIMESTAMP_US_PRECISION = 26;
|
||||
// scale for data types
|
||||
public static final int FLOAT_SCALE = 31;
|
||||
public static final int DOUBLE_SCALE = 31;
|
||||
|
||||
public static int typeName2JdbcType(String type) {
|
||||
switch (type.toUpperCase()) {
|
||||
case "TIMESTAMP":
|
||||
return Types.TIMESTAMP;
|
||||
case "INT":
|
||||
return Types.INTEGER;
|
||||
case "BIGINT":
|
||||
return Types.BIGINT;
|
||||
case "FLOAT":
|
||||
return Types.FLOAT;
|
||||
case "DOUBLE":
|
||||
return Types.DOUBLE;
|
||||
case "BINARY":
|
||||
return Types.BINARY;
|
||||
case "SMALLINT":
|
||||
return Types.SMALLINT;
|
||||
case "TINYINT":
|
||||
return Types.TINYINT;
|
||||
case "BOOL":
|
||||
return Types.BOOLEAN;
|
||||
case "NCHAR":
|
||||
return Types.NCHAR;
|
||||
default:
|
||||
return Types.NULL;
|
||||
}
|
||||
}
|
||||
|
||||
public static int taosType2JdbcType(int taosType) throws SQLException {
|
||||
switch (taosType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
|
@ -88,7 +129,7 @@ public abstract class TSDBConstants {
|
|||
}
|
||||
|
||||
public static String taosType2JdbcTypeName(int taosType) throws SQLException {
|
||||
switch (taosType){
|
||||
switch (taosType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
return "BOOL";
|
||||
case TSDBConstants.TSDB_DATA_TYPE_UTINYINT:
|
||||
|
@ -119,7 +160,7 @@ public abstract class TSDBConstants {
|
|||
}
|
||||
|
||||
public static int jdbcType2TaosType(int jdbcType) throws SQLException {
|
||||
switch (jdbcType){
|
||||
switch (jdbcType) {
|
||||
case Types.BOOLEAN:
|
||||
return TSDBConstants.TSDB_DATA_TYPE_BOOL;
|
||||
case Types.TINYINT:
|
||||
|
@ -145,7 +186,7 @@ public abstract class TSDBConstants {
|
|||
}
|
||||
|
||||
public static String jdbcType2TaosTypeName(int jdbcType) throws SQLException {
|
||||
switch (jdbcType){
|
||||
switch (jdbcType) {
|
||||
case Types.BOOLEAN:
|
||||
return "BOOL";
|
||||
case Types.TINYINT:
|
||||
|
|
|
@ -16,13 +16,13 @@
|
|||
*/
|
||||
package com.taosdata.jdbc;
|
||||
|
||||
import com.taosdata.jdbc.utils.TaosInfo;
|
||||
|
||||
import java.nio.ByteBuffer;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.SQLWarning;
|
||||
import java.util.List;
|
||||
|
||||
import com.taosdata.jdbc.utils.TaosInfo;
|
||||
|
||||
/**
|
||||
* JNI connector
|
||||
*/
|
||||
|
@ -30,10 +30,10 @@ public class TSDBJNIConnector {
|
|||
private static volatile Boolean isInitialized = false;
|
||||
|
||||
private TaosInfo taosInfo = TaosInfo.getInstance();
|
||||
|
||||
|
||||
// Connection pointer used in C
|
||||
private long taos = TSDBConstants.JNI_NULL_POINTER;
|
||||
|
||||
|
||||
// result set status in current connection
|
||||
private boolean isResultsetClosed;
|
||||
|
||||
|
@ -194,7 +194,9 @@ public class TSDBJNIConnector {
|
|||
* Get schema metadata
|
||||
*/
|
||||
public int getSchemaMetaData(long resultSet, List<ColumnMetaData> columnMetaData) {
|
||||
return this.getSchemaMetaDataImp(this.taos, resultSet, columnMetaData);
|
||||
int ret = this.getSchemaMetaDataImp(this.taos, resultSet, columnMetaData);
|
||||
columnMetaData.stream().forEach(column -> column.setColIndex(column.getColIndex() + 1));
|
||||
return ret;
|
||||
}
|
||||
|
||||
private native int getSchemaMetaDataImp(long connection, long resultSet, List<ColumnMetaData> columnMetaData);
|
||||
|
@ -221,7 +223,7 @@ public class TSDBJNIConnector {
|
|||
*/
|
||||
public void closeConnection() throws SQLException {
|
||||
int code = this.closeConnectionImp(this.taos);
|
||||
|
||||
|
||||
if (code < 0) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_JNI_CONNECTION_NULL);
|
||||
} else if (code == 0) {
|
||||
|
@ -229,7 +231,7 @@ public class TSDBJNIConnector {
|
|||
} else {
|
||||
throw new SQLException("Undefined error code returned by TDengine when closing a connection");
|
||||
}
|
||||
|
||||
|
||||
// invoke closeConnectionImpl only here
|
||||
taosInfo.connect_close_increment();
|
||||
}
|
||||
|
@ -274,67 +276,76 @@ public class TSDBJNIConnector {
|
|||
}
|
||||
|
||||
private native int validateCreateTableSqlImp(long connection, byte[] sqlBytes);
|
||||
|
||||
public long prepareStmt(String sql) throws SQLException {
|
||||
Long stmt = prepareStmtImp(sql.getBytes(), this.taos);
|
||||
if (stmt == TSDBConstants.JNI_TDENGINE_ERROR) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_SQL);
|
||||
} else if (stmt == TSDBConstants.JNI_CONNECTION_NULL) {
|
||||
|
||||
public long prepareStmt(String sql) throws SQLException {
|
||||
Long stmt;
|
||||
try {
|
||||
stmt = prepareStmtImp(sql.getBytes(), this.taos);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_ENCODING);
|
||||
}
|
||||
|
||||
if (stmt == TSDBConstants.JNI_CONNECTION_NULL) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_JNI_CONNECTION_NULL);
|
||||
} else if (stmt == TSDBConstants.JNI_SQL_NULL) {
|
||||
}
|
||||
|
||||
if (stmt == TSDBConstants.JNI_SQL_NULL) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_JNI_SQL_NULL);
|
||||
} else if (stmt == TSDBConstants.JNI_OUT_OF_MEMORY) {
|
||||
}
|
||||
|
||||
if (stmt == TSDBConstants.JNI_OUT_OF_MEMORY) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_JNI_OUT_OF_MEMORY);
|
||||
}
|
||||
|
||||
return stmt;
|
||||
|
||||
return stmt;
|
||||
}
|
||||
|
||||
|
||||
private native long prepareStmtImp(byte[] sql, long con);
|
||||
|
||||
|
||||
public void setBindTableName(long stmt, String tableName) throws SQLException {
|
||||
int code = setBindTableNameImp(stmt, tableName, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
int code = setBindTableNameImp(stmt, tableName, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNKNOWN, "failed to set table name");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
private native int setBindTableNameImp(long stmt, String name, long conn);
|
||||
|
||||
|
||||
public void setBindTableNameAndTags(long stmt, String tableName, int numOfTags, ByteBuffer tags, ByteBuffer typeList, ByteBuffer lengthList, ByteBuffer nullList) throws SQLException {
|
||||
int code = setTableNameTagsImp(stmt, tableName, numOfTags, tags.array(), typeList.array(), lengthList.array(),
|
||||
nullList.array(), this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNKNOWN, "failed to bind table name and corresponding tags");
|
||||
}
|
||||
int code = setTableNameTagsImp(stmt, tableName, numOfTags, tags.array(), typeList.array(), lengthList.array(),
|
||||
nullList.array(), this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNKNOWN, "failed to bind table name and corresponding tags");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private native int setTableNameTagsImp(long stmt, String name, int numOfTags, byte[] tags, byte[] typeList, byte[] lengthList, byte[] nullList, long conn);
|
||||
|
||||
public void bindColumnDataArray(long stmt, ByteBuffer colDataList, ByteBuffer lengthList, ByteBuffer isNullList, int type, int bytes, int numOfRows,int columnIndex) throws SQLException {
|
||||
int code = bindColDataImp(stmt, colDataList.array(), lengthList.array(), isNullList.array(), type, bytes, numOfRows, columnIndex, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
|
||||
public void bindColumnDataArray(long stmt, ByteBuffer colDataList, ByteBuffer lengthList, ByteBuffer isNullList, int type, int bytes, int numOfRows, int columnIndex) throws SQLException {
|
||||
int code = bindColDataImp(stmt, colDataList.array(), lengthList.array(), isNullList.array(), type, bytes, numOfRows, columnIndex, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNKNOWN, "failed to bind column data");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
private native int bindColDataImp(long stmt, byte[] colDataList, byte[] lengthList, byte[] isNullList, int type, int bytes, int numOfRows, int columnIndex, long conn);
|
||||
|
||||
|
||||
public void executeBatch(long stmt) throws SQLException {
|
||||
int code = executeBatchImp(stmt, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
int code = executeBatchImp(stmt, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNKNOWN, "failed to execute batch bind");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private native int executeBatchImp(long stmt, long con);
|
||||
|
||||
|
||||
public void closeBatch(long stmt) throws SQLException {
|
||||
int code = closeStmt(stmt, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
int code = closeStmt(stmt, this.taos);
|
||||
if (code != TSDBConstants.JNI_SUCCESS) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNKNOWN, "failed to close batch bind");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private native int closeStmt(long stmt, long con);
|
||||
}
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -133,9 +133,10 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.getString(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = this.rowData.getString(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getString(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -147,9 +148,10 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.getBoolean(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = this.rowData.getBoolean(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getBoolean(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -161,9 +163,10 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return (byte) this.blockData.getInt(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = (byte) this.rowData.getInt(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = (byte) this.rowData.getInt(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -175,9 +178,10 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return (short) this.blockData.getInt(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = (short) this.rowData.getInt(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = (short) this.rowData.getInt(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -189,9 +193,11 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.getInt(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = this.rowData.getInt(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getInt(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -203,13 +209,15 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.getLong(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
Object value = this.rowData.get(columnIndex - 1);
|
||||
if (value instanceof Timestamp)
|
||||
Object value = this.rowData.getObject(columnIndex);
|
||||
if (value instanceof Timestamp) {
|
||||
res = ((Timestamp) value).getTime();
|
||||
else
|
||||
res = this.rowData.getLong(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
} else {
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getLong(columnIndex, nativeType);
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -221,9 +229,11 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return (float) this.blockData.getDouble(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
if (!lastWasNull)
|
||||
res = this.rowData.getFloat(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getFloat(columnIndex, nativeType);
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
@ -235,9 +245,10 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.getDouble(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = this.rowData.getDouble(columnIndex - 1, this.columnMetaDataList.get(columnIndex - 1).getColType());
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getDouble(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -245,34 +256,27 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
public byte[] getBytes(int columnIndex) throws SQLException {
|
||||
checkAvailability(columnIndex, this.columnMetaDataList.size());
|
||||
|
||||
Object value = this.rowData.get(columnIndex - 1);
|
||||
Object value = this.rowData.getObject(columnIndex);
|
||||
if (value == null)
|
||||
return null;
|
||||
|
||||
int colType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
switch (colType) {
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
return Longs.toByteArray((Long) value);
|
||||
return Longs.toByteArray((long) value);
|
||||
case TSDBConstants.TSDB_DATA_TYPE_INT:
|
||||
return Ints.toByteArray((int) value);
|
||||
case TSDBConstants.TSDB_DATA_TYPE_SMALLINT:
|
||||
return Shorts.toByteArray((Short) value);
|
||||
return Shorts.toByteArray((short) value);
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TINYINT:
|
||||
return new byte[]{(byte) value};
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BINARY:
|
||||
return (byte[]) value;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_NCHAR:
|
||||
default:
|
||||
return value.toString().getBytes();
|
||||
}
|
||||
return value.toString().getBytes();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Date getDate(int columnIndex) throws SQLException {
|
||||
Timestamp timestamp = getTimestamp(columnIndex);
|
||||
return timestamp == null ? null : new Date(timestamp.getTime());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Time getTime(int columnIndex) throws SQLException {
|
||||
Timestamp timestamp = getTimestamp(columnIndex);
|
||||
return timestamp == null ? null : new Time(timestamp.getTime());
|
||||
}
|
||||
|
||||
public Timestamp getTimestamp(int columnIndex) throws SQLException {
|
||||
|
@ -282,9 +286,10 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.getTimestamp(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
res = this.rowData.getTimestamp(columnIndex - 1);
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
res = this.rowData.getTimestamp(columnIndex, nativeType);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -304,13 +309,9 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return this.blockData.get(columnIndex - 1);
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
if (!lastWasNull) {
|
||||
int colType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
if (colType == TSDBConstants.TSDB_DATA_TYPE_BINARY)
|
||||
res = ((String) this.rowData.get(columnIndex - 1)).getBytes();
|
||||
else
|
||||
res = this.rowData.get(columnIndex - 1);
|
||||
res = this.rowData.getObject(columnIndex);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
@ -318,7 +319,7 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
public int findColumn(String columnLabel) throws SQLException {
|
||||
for (ColumnMetaData colMetaData : this.columnMetaDataList) {
|
||||
if (colMetaData.getColName() != null && colMetaData.getColName().equalsIgnoreCase(columnLabel)) {
|
||||
return colMetaData.getColIndex() + 1;
|
||||
return colMetaData.getColIndex();
|
||||
}
|
||||
}
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||
|
@ -329,25 +330,25 @@ public class TSDBResultSet extends AbstractResultSet implements ResultSet {
|
|||
if (this.getBatchFetch())
|
||||
return new BigDecimal(this.blockData.getLong(columnIndex - 1));
|
||||
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex - 1);
|
||||
this.lastWasNull = this.rowData.wasNull(columnIndex);
|
||||
BigDecimal res = null;
|
||||
if (!lastWasNull) {
|
||||
int colType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
switch (colType) {
|
||||
int nativeType = this.columnMetaDataList.get(columnIndex - 1).getColType();
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TINYINT:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_SMALLINT:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_INT:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
res = new BigDecimal(Long.valueOf(this.rowData.get(columnIndex - 1).toString()));
|
||||
res = new BigDecimal(Long.valueOf(this.rowData.getObject(columnIndex).toString()));
|
||||
break;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
res = new BigDecimal(Double.valueOf(this.rowData.get(columnIndex - 1).toString()));
|
||||
res = new BigDecimal(Double.valueOf(this.rowData.getObject(columnIndex).toString()));
|
||||
break;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
return new BigDecimal(((Timestamp) this.rowData.get(columnIndex - 1)).getTime());
|
||||
return new BigDecimal(((Timestamp) this.rowData.getObject(columnIndex)).getTime());
|
||||
default:
|
||||
res = new BigDecimal(this.rowData.get(columnIndex - 1).toString());
|
||||
res = new BigDecimal(this.rowData.getObject(columnIndex).toString());
|
||||
}
|
||||
}
|
||||
return res;
|
||||
|
|
|
@ -113,6 +113,7 @@ public class TSDBResultSetMetaData extends WrapperImpl implements ResultSetMetaD
|
|||
|
||||
ColumnMetaData columnMetaData = this.colMetaDataList.get(column - 1);
|
||||
switch (columnMetaData.getColType()) {
|
||||
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
return 5;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
|
|
|
@ -14,6 +14,8 @@
|
|||
*****************************************************************************/
|
||||
package com.taosdata.jdbc;
|
||||
|
||||
import com.taosdata.jdbc.utils.NullType;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Timestamp;
|
||||
|
@ -22,11 +24,13 @@ import java.util.ArrayList;
|
|||
import java.util.Collections;
|
||||
|
||||
public class TSDBResultSetRowData {
|
||||
|
||||
private ArrayList<Object> data;
|
||||
private int colSize = 0;
|
||||
private int colSize;
|
||||
|
||||
public TSDBResultSetRowData(int colSize) {
|
||||
this.setColSize(colSize);
|
||||
this.colSize = colSize;
|
||||
this.clear();
|
||||
}
|
||||
|
||||
public void clear() {
|
||||
|
@ -41,68 +45,104 @@ public class TSDBResultSetRowData {
|
|||
}
|
||||
|
||||
public boolean wasNull(int col) {
|
||||
return data.get(col) == null;
|
||||
return data.get(col - 1) == null;
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setBooleanValue(int col, boolean value) {
|
||||
setBoolean(col - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setBoolean(int col, boolean value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
public boolean getBoolean(int col, int srcType) throws SQLException {
|
||||
Object obj = data.get(col);
|
||||
public boolean getBoolean(int col, int nativeType) throws SQLException {
|
||||
Object obj = data.get(col - 1);
|
||||
|
||||
switch (srcType) {
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
return (Boolean) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
return ((Float) obj) == 1.0 ? Boolean.TRUE : Boolean.FALSE;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
return ((Double) obj) == 1.0 ? Boolean.TRUE : Boolean.FALSE;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TINYINT:
|
||||
return ((Byte) obj) == 1 ? Boolean.TRUE : Boolean.FALSE;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_SMALLINT:
|
||||
return ((Short) obj) == 1 ? Boolean.TRUE : Boolean.FALSE;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_INT:
|
||||
return ((Integer) obj) == 1 ? Boolean.TRUE : Boolean.FALSE;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
return ((Long) obj) == 1L ? Boolean.TRUE : Boolean.FALSE;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BINARY:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_NCHAR: {
|
||||
return obj.toString().contains("1");
|
||||
}
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setByteValue(int colIndex, byte value) {
|
||||
setByte(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setByte(int col, byte value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setShortValue(int colIndex, short value) {
|
||||
setShort(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setShort(int col, short value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setIntValue(int colIndex, int value) {
|
||||
setInt(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setInt(int col, int value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
public int getInt(int col, int srcType) throws SQLException {
|
||||
Object obj = data.get(col);
|
||||
public int getInt(int col, int nativeType) throws SQLException {
|
||||
Object obj = data.get(col - 1);
|
||||
if (obj == null)
|
||||
return NullType.getIntNull();
|
||||
|
||||
switch (srcType) {
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
return Boolean.TRUE.equals(obj) ? 1 : 0;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
return ((Float) obj).intValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
return ((Double) obj).intValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TINYINT:
|
||||
return (Byte) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_SMALLINT:
|
||||
return (Short) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_INT:
|
||||
return (Integer) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
return ((Long) obj).intValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_NCHAR:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BINARY:
|
||||
|
@ -131,33 +171,46 @@ public class TSDBResultSetRowData {
|
|||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_NUMERIC_VALUE_OUT_OF_RANGE);
|
||||
return Long.valueOf(value).intValue();
|
||||
}
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
return ((Float) obj).intValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
return ((Double) obj).intValue();
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setLongValue(int colIndex, long value) {
|
||||
setLong(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setLong(int col, long value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
public long getLong(int col, int srcType) throws SQLException {
|
||||
Object obj = data.get(col);
|
||||
public long getLong(int col, int nativeType) throws SQLException {
|
||||
Object obj = data.get(col - 1);
|
||||
if (obj == null) {
|
||||
return NullType.getBigIntNull();
|
||||
}
|
||||
|
||||
switch (srcType) {
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
return Boolean.TRUE.equals(obj) ? 1 : 0;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
return ((Float) obj).longValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
return ((Double) obj).longValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TINYINT:
|
||||
return (Byte) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_SMALLINT:
|
||||
return (Short) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_INT:
|
||||
return (Integer) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
return (Long) obj;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_NCHAR:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BINARY:
|
||||
|
@ -186,19 +239,35 @@ public class TSDBResultSetRowData {
|
|||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_NUMERIC_VALUE_OUT_OF_RANGE);
|
||||
return value;
|
||||
}
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
return ((Float) obj).longValue();
|
||||
case TSDBConstants.TSDB_DATA_TYPE_DOUBLE:
|
||||
return ((Double) obj).longValue();
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setFloatValue(int colIndex, float value) {
|
||||
setFloat(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setFloat(int col, float value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
public float getFloat(int col, int srcType) {
|
||||
Object obj = data.get(col);
|
||||
public float getFloat(int col, int nativeType) {
|
||||
Object obj = data.get(col - 1);
|
||||
if (obj == null)
|
||||
return NullType.getFloatNull();
|
||||
|
||||
switch (srcType) {
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
return Boolean.TRUE.equals(obj) ? 1 : 0;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
|
@ -214,19 +283,31 @@ public class TSDBResultSetRowData {
|
|||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
return (Long) obj;
|
||||
default:
|
||||
return NullType.getFloatNull();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setDoubleValue(int colIndex, double value) {
|
||||
setDouble(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setDouble(int col, double value) {
|
||||
data.set(col, value);
|
||||
}
|
||||
|
||||
public double getDouble(int col, int srcType) {
|
||||
Object obj = data.get(col);
|
||||
public double getDouble(int col, int nativeType) {
|
||||
Object obj = data.get(col - 1);
|
||||
if (obj == null)
|
||||
return NullType.getDoubleNull();
|
||||
|
||||
switch (srcType) {
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BOOL:
|
||||
return Boolean.TRUE.equals(obj) ? 1 : 0;
|
||||
case TSDBConstants.TSDB_DATA_TYPE_FLOAT:
|
||||
|
@ -242,16 +323,46 @@ public class TSDBResultSetRowData {
|
|||
case TSDBConstants.TSDB_DATA_TYPE_TIMESTAMP:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
return (Long) obj;
|
||||
default:
|
||||
return NullType.getDoubleNull();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setStringValue(int colIndex, String value) {
|
||||
data.set(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setString(int col, String value) {
|
||||
data.set(col, value);
|
||||
// TODO:
|
||||
// !!!NOTE!!!
|
||||
// this is very confusing problem which related to JNI-method implementation,
|
||||
// the JNI method return a String(encoded in UTF) for BINARY value, which means the JNI method will invoke
|
||||
// this setString(int, String) to handle BINARY value, we need to build a byte[] with default charsetEncoding
|
||||
data.set(col, value == null ? null : value.getBytes());
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setByteArrayValue(int colIndex, byte[] value) {
|
||||
setByteArray(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setByteArray(int col, byte[] value) {
|
||||
// TODO:
|
||||
// !!!NOTE!!!
|
||||
// this is very confusing problem which related to JNI-method implementation,
|
||||
// the JNI method return a byte[] for NCHAR value, which means the JNI method will invoke
|
||||
// this setByteArr(int, byte[]) to handle NCHAR value, we need to build a String with charsetEncoding by TaosGlobalConfig
|
||||
try {
|
||||
data.set(col, new String(value, TaosGlobalConfig.getCharset()));
|
||||
} catch (Exception e) {
|
||||
|
@ -259,47 +370,56 @@ public class TSDBResultSetRowData {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The original type may not be a string type, but will be converted to by calling this method
|
||||
*
|
||||
* @param col column index
|
||||
* @return
|
||||
*/
|
||||
public String getString(int col, int srcType) {
|
||||
switch (srcType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BINARY:
|
||||
case TSDBConstants.TSDB_DATA_TYPE_NCHAR:
|
||||
return (String) data.get(col);
|
||||
public String getString(int col, int nativeType) {
|
||||
Object obj = data.get(col - 1);
|
||||
if (obj == null)
|
||||
return null;
|
||||
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_UTINYINT: {
|
||||
Byte value = new Byte(String.valueOf(data.get(col)));
|
||||
Byte value = new Byte(String.valueOf(obj));
|
||||
if (value >= 0)
|
||||
return value.toString();
|
||||
return Integer.toString(value & 0xff);
|
||||
}
|
||||
case TSDBConstants.TSDB_DATA_TYPE_USMALLINT: {
|
||||
Short value = new Short(String.valueOf(data.get(col)));
|
||||
Short value = new Short(String.valueOf(obj));
|
||||
if (value >= 0)
|
||||
return value.toString();
|
||||
return Integer.toString(value & 0xffff);
|
||||
}
|
||||
case TSDBConstants.TSDB_DATA_TYPE_UINT: {
|
||||
Integer value = new Integer(String.valueOf(data.get(col)));
|
||||
Integer value = new Integer(String.valueOf(obj));
|
||||
if (value >= 0)
|
||||
return value.toString();
|
||||
return Long.toString(value & 0xffffffffl);
|
||||
}
|
||||
case TSDBConstants.TSDB_DATA_TYPE_UBIGINT: {
|
||||
Long value = new Long(String.valueOf(data.get(col)));
|
||||
Long value = new Long(String.valueOf(obj));
|
||||
if (value >= 0)
|
||||
return value.toString();
|
||||
long lowValue = value & 0x7fffffffffffffffL;
|
||||
return BigDecimal.valueOf(lowValue).add(BigDecimal.valueOf(Long.MAX_VALUE)).add(BigDecimal.valueOf(1)).toString();
|
||||
}
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BINARY:
|
||||
return new String((byte[]) obj);
|
||||
case TSDBConstants.TSDB_DATA_TYPE_NCHAR:
|
||||
return (String) obj;
|
||||
default:
|
||||
return String.valueOf(data.get(col));
|
||||
return String.valueOf(obj);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* $$$ this method is invoked by databaseMetaDataResultSet and so on which use a index start from 1 in JDBC api
|
||||
*/
|
||||
public void setTimestampValue(int colIndex, long value) {
|
||||
setTimestamp(colIndex - 1, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* !!! this method is invoked by JNI method and the index start from 0 in C implementations
|
||||
*/
|
||||
public void setTimestamp(int col, long ts) {
|
||||
//TODO: this implementation contains logical error
|
||||
// when precision is us the (long ts) is 16 digital number
|
||||
|
@ -316,28 +436,20 @@ public class TSDBResultSetRowData {
|
|||
}
|
||||
}
|
||||
|
||||
public Timestamp getTimestamp(int col) {
|
||||
return (Timestamp) data.get(col);
|
||||
public Timestamp getTimestamp(int col, int nativeType) {
|
||||
Object obj = data.get(col - 1);
|
||||
if (obj == null)
|
||||
return null;
|
||||
switch (nativeType) {
|
||||
case TSDBConstants.TSDB_DATA_TYPE_BIGINT:
|
||||
return new Timestamp((Long) obj);
|
||||
default:
|
||||
return (Timestamp) obj;
|
||||
}
|
||||
}
|
||||
|
||||
public Object get(int col) {
|
||||
return data.get(col);
|
||||
public Object getObject(int col) {
|
||||
return data.get(col - 1);
|
||||
}
|
||||
|
||||
public int getColSize() {
|
||||
return colSize;
|
||||
}
|
||||
|
||||
private void setColSize(int colSize) {
|
||||
this.colSize = colSize;
|
||||
this.clear();
|
||||
}
|
||||
|
||||
public ArrayList<Object> getData() {
|
||||
return data;
|
||||
}
|
||||
|
||||
public void setData(ArrayList<Object> data) {
|
||||
this.data = (ArrayList<Object>) data.clone();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -32,14 +32,15 @@ public class TSDBStatement extends AbstractStatement {
|
|||
}
|
||||
|
||||
public ResultSet executeQuery(String sql) throws SQLException {
|
||||
// check if closed
|
||||
if (isClosed()) {
|
||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||
}
|
||||
|
||||
//TODO: 如果在executeQuery方法中执行insert语句,那么先执行了SQL,再通过pSql来检查是否为一个insert语句,但这个insert SQL已经执行成功了
|
||||
|
||||
// execute query
|
||||
//TODO:
|
||||
// this is an unreasonable implementation, if the paratemer is a insert statement,
|
||||
// the JNI connector will execute the sql at first and return a pointer: pSql,
|
||||
// we use this pSql and invoke the isUpdateQuery(long pSql) method to decide .
|
||||
// but the insert sql is already executed in database.
|
||||
//execute query
|
||||
long pSql = this.connection.getConnector().executeQuery(sql);
|
||||
// if pSql is create/insert/update/delete/alter SQL
|
||||
if (this.connection.getConnector().isUpdateQuery(pSql)) {
|
||||
|
|
|
@ -95,16 +95,7 @@ public class Utils {
|
|||
public static String getNativeSql(String rawSql, Object[] parameters) {
|
||||
// toLowerCase
|
||||
String preparedSql = rawSql.trim().toLowerCase();
|
||||
|
||||
String[] clause = new String[0];
|
||||
if (SqlSyntaxValidator.isInsertSql(preparedSql)) {
|
||||
// insert or import
|
||||
clause = new String[]{"values\\s*\\(.*?\\)", "tags\\s*\\(.*?\\)"};
|
||||
}
|
||||
if (SqlSyntaxValidator.isSelectSql(preparedSql)) {
|
||||
// select
|
||||
clause = new String[]{"where\\s*.*"};
|
||||
}
|
||||
String[] clause = new String[]{"values\\s*\\(.*?\\)", "tags\\s*\\(.*?\\)", "where\\s*.*"};
|
||||
Map<Integer, Integer> placeholderPositions = new HashMap<>();
|
||||
RangeSet<Integer> clauseRangeSet = TreeRangeSet.create();
|
||||
findPlaceholderPosition(preparedSql, placeholderPositions);
|
||||
|
|
|
@ -32,20 +32,34 @@ public class TSDBConnectionTest {
|
|||
}
|
||||
|
||||
@Test
|
||||
public void subscribe() {
|
||||
public void runSubscribe() {
|
||||
try {
|
||||
// given
|
||||
TSDBConnection unwrap = conn.unwrap(TSDBConnection.class);
|
||||
TSDBSubscribe subscribe = unwrap.subscribe("topic1", "select * from log.log", false);
|
||||
// when
|
||||
TSDBResultSet rs = subscribe.consume();
|
||||
ResultSetMetaData metaData = rs.getMetaData();
|
||||
for (int count = 0; count < 10 && rs.next(); count++) {
|
||||
for (int i = 1; i <= metaData.getColumnCount(); i++) {
|
||||
String value = rs.getString(i);
|
||||
System.out.print(metaData.getColumnLabel(i) + ":" + value + "\t");
|
||||
}
|
||||
System.out.println();
|
||||
}
|
||||
|
||||
// then
|
||||
Assert.assertNotNull(rs);
|
||||
Assert.assertEquals(4, metaData.getColumnCount());
|
||||
Assert.assertEquals("ts", metaData.getColumnLabel(1));
|
||||
Assert.assertEquals("level", metaData.getColumnLabel(2));
|
||||
Assert.assertEquals("content", metaData.getColumnLabel(3));
|
||||
Assert.assertEquals("ipaddr", metaData.getColumnLabel(4));
|
||||
rs.next();
|
||||
// row 1
|
||||
{
|
||||
Assert.assertNotNull(rs.getTimestamp(1));
|
||||
Assert.assertNotNull(rs.getTimestamp("ts"));
|
||||
Assert.assertNotNull(rs.getByte(2));
|
||||
Assert.assertNotNull(rs.getByte("level"));
|
||||
Assert.assertNotNull(rs.getString(3));
|
||||
Assert.assertNotNull(rs.getString("content"));
|
||||
Assert.assertNotNull(rs.getString(4));
|
||||
Assert.assertNotNull(rs.getString("ipaddr"));
|
||||
}
|
||||
subscribe.close(false);
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
|
|
|
@ -7,9 +7,11 @@ import java.util.Properties;
|
|||
|
||||
public class TSDBDatabaseMetaDataTest {
|
||||
private static final String host = "127.0.0.1";
|
||||
private static final String url = "jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata";
|
||||
private static Connection connection;
|
||||
private static TSDBDatabaseMetaData metaData;
|
||||
|
||||
|
||||
@Test
|
||||
public void unwrap() throws SQLException {
|
||||
TSDBDatabaseMetaData unwrap = metaData.unwrap(TSDBDatabaseMetaData.class);
|
||||
|
@ -33,7 +35,7 @@ public class TSDBDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getURL() throws SQLException {
|
||||
Assert.assertEquals("jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata", metaData.getURL());
|
||||
Assert.assertEquals(url, metaData.getURL());
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -627,17 +629,32 @@ public class TSDBDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getTables() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
ResultSet tables = metaData.getTables("log", "", null, null);
|
||||
ResultSetMetaData metaData = tables.getMetaData();
|
||||
while (tables.next()) {
|
||||
System.out.print(metaData.getColumnLabel(1) + ":" + tables.getString(1) + "\t");
|
||||
System.out.print(metaData.getColumnLabel(3) + ":" + tables.getString(3) + "\t");
|
||||
System.out.print(metaData.getColumnLabel(4) + ":" + tables.getString(4) + "\t");
|
||||
System.out.print(metaData.getColumnLabel(5) + ":" + tables.getString(5) + "\n");
|
||||
ResultSet rs = metaData.getTables("log", "", null, null);
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
Assert.assertNotNull(rs);
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", rs.getString(1));
|
||||
Assert.assertEquals("log", rs.getString("TABLE_CAT"));
|
||||
// TABLE_SCHEM
|
||||
Assert.assertEquals("TABLE_SCHEM", meta.getColumnLabel(2));
|
||||
Assert.assertEquals(null, rs.getString(2));
|
||||
Assert.assertEquals(null, rs.getString("TABLE_SCHEM"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertNotNull(rs.getString(3));
|
||||
Assert.assertNotNull(rs.getString("TABLE_NAME"));
|
||||
// TABLE_TYPE
|
||||
Assert.assertEquals("TABLE_TYPE", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("TABLE", rs.getString(4));
|
||||
Assert.assertEquals("TABLE", rs.getString("TABLE_TYPE"));
|
||||
// REMARKS
|
||||
Assert.assertEquals("REMARKS", meta.getColumnLabel(5));
|
||||
Assert.assertEquals("", rs.getString(5));
|
||||
Assert.assertEquals("", rs.getString("REMARKS"));
|
||||
}
|
||||
System.out.println();
|
||||
Assert.assertNotNull(tables);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -647,46 +664,130 @@ public class TSDBDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getCatalogs() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet catalogs = metaData.getCatalogs();
|
||||
ResultSetMetaData meta = catalogs.getMetaData();
|
||||
while (catalogs.next()) {
|
||||
for (int i = 1; i <= meta.getColumnCount(); i++) {
|
||||
System.out.print(meta.getColumnLabel(i) + ": " + catalogs.getString(i));
|
||||
}
|
||||
System.out.println();
|
||||
ResultSet rs = metaData.getCatalogs();
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertNotNull(rs.getString(1));
|
||||
Assert.assertNotNull(rs.getString("TABLE_CAT"));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getTableTypes() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet tableTypes = metaData.getTableTypes();
|
||||
while (tableTypes.next()) {
|
||||
System.out.println(tableTypes.getString("TABLE_TYPE"));
|
||||
tableTypes.next();
|
||||
// tableTypes: table
|
||||
{
|
||||
Assert.assertEquals("TABLE", tableTypes.getString(1));
|
||||
Assert.assertEquals("TABLE", tableTypes.getString("TABLE_TYPE"));
|
||||
}
|
||||
tableTypes.next();
|
||||
// tableTypes: stable
|
||||
{
|
||||
Assert.assertEquals("STABLE", tableTypes.getString(1));
|
||||
Assert.assertEquals("STABLE", tableTypes.getString("TABLE_TYPE"));
|
||||
}
|
||||
Assert.assertNotNull(metaData.getTableTypes());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getColumns() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
// when
|
||||
ResultSet columns = metaData.getColumns("log", "", "dn", "");
|
||||
// then
|
||||
ResultSetMetaData meta = columns.getMetaData();
|
||||
while (columns.next()) {
|
||||
System.out.print(meta.getColumnLabel(1) + ": " + columns.getString(1) + "\t");
|
||||
System.out.print(meta.getColumnLabel(3) + ": " + columns.getString(3) + "\t");
|
||||
System.out.print(meta.getColumnLabel(4) + ": " + columns.getString(4) + "\t");
|
||||
System.out.print(meta.getColumnLabel(5) + ": " + columns.getString(5) + "\t");
|
||||
System.out.print(meta.getColumnLabel(6) + ": " + columns.getString(6) + "\t");
|
||||
System.out.print(meta.getColumnLabel(7) + ": " + columns.getString(7) + "\t");
|
||||
System.out.print(meta.getColumnLabel(9) + ": " + columns.getString(9) + "\t");
|
||||
System.out.print(meta.getColumnLabel(10) + ": " + columns.getString(10) + "\t");
|
||||
System.out.print(meta.getColumnLabel(11) + ": " + columns.getString(11) + "\n");
|
||||
System.out.print(meta.getColumnLabel(12) + ": " + columns.getString(12) + "\n");
|
||||
columns.next();
|
||||
// column: 1
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", columns.getString(1));
|
||||
Assert.assertEquals("log", columns.getString("TABLE_CAT"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn", columns.getString(3));
|
||||
Assert.assertEquals("dn", columns.getString("TABLE_NAME"));
|
||||
// COLUMN_NAME
|
||||
Assert.assertEquals("COLUMN_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("ts", columns.getString(4));
|
||||
Assert.assertEquals("ts", columns.getString("COLUMN_NAME"));
|
||||
// DATA_TYPE
|
||||
Assert.assertEquals("DATA_TYPE", meta.getColumnLabel(5));
|
||||
Assert.assertEquals(Types.TIMESTAMP, columns.getInt(5));
|
||||
Assert.assertEquals(Types.TIMESTAMP, columns.getInt("DATA_TYPE"));
|
||||
// TYPE_NAME
|
||||
Assert.assertEquals("TYPE_NAME", meta.getColumnLabel(6));
|
||||
Assert.assertEquals("TIMESTAMP", columns.getString(6));
|
||||
Assert.assertEquals("TIMESTAMP", columns.getString("TYPE_NAME"));
|
||||
// COLUMN_SIZE
|
||||
Assert.assertEquals("COLUMN_SIZE", meta.getColumnLabel(7));
|
||||
Assert.assertEquals(26, columns.getInt(7));
|
||||
Assert.assertEquals(26, columns.getInt("COLUMN_SIZE"));
|
||||
// DECIMAL_DIGITS
|
||||
Assert.assertEquals("DECIMAL_DIGITS", meta.getColumnLabel(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt("DECIMAL_DIGITS"));
|
||||
Assert.assertEquals(null, columns.getString(9));
|
||||
Assert.assertEquals(null, columns.getString("DECIMAL_DIGITS"));
|
||||
// NUM_PREC_RADIX
|
||||
Assert.assertEquals("NUM_PREC_RADIX", meta.getColumnLabel(10));
|
||||
Assert.assertEquals(10, columns.getInt(10));
|
||||
Assert.assertEquals(10, columns.getInt("NUM_PREC_RADIX"));
|
||||
// NULLABLE
|
||||
Assert.assertEquals("NULLABLE", meta.getColumnLabel(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNoNulls, columns.getInt(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNoNulls, columns.getInt("NULLABLE"));
|
||||
// REMARKS
|
||||
Assert.assertEquals("REMARKS", meta.getColumnLabel(12));
|
||||
Assert.assertEquals(null, columns.getString(12));
|
||||
Assert.assertEquals(null, columns.getString("REMARKS"));
|
||||
}
|
||||
columns.next();
|
||||
// column: 2
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", columns.getString(1));
|
||||
Assert.assertEquals("log", columns.getString("TABLE_CAT"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn", columns.getString(3));
|
||||
Assert.assertEquals("dn", columns.getString("TABLE_NAME"));
|
||||
// COLUMN_NAME
|
||||
Assert.assertEquals("COLUMN_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("cpu_taosd", columns.getString(4));
|
||||
Assert.assertEquals("cpu_taosd", columns.getString("COLUMN_NAME"));
|
||||
// DATA_TYPE
|
||||
Assert.assertEquals("DATA_TYPE", meta.getColumnLabel(5));
|
||||
Assert.assertEquals(Types.FLOAT, columns.getInt(5));
|
||||
Assert.assertEquals(Types.FLOAT, columns.getInt("DATA_TYPE"));
|
||||
// TYPE_NAME
|
||||
Assert.assertEquals("TYPE_NAME", meta.getColumnLabel(6));
|
||||
Assert.assertEquals("FLOAT", columns.getString(6));
|
||||
Assert.assertEquals("FLOAT", columns.getString("TYPE_NAME"));
|
||||
// COLUMN_SIZE
|
||||
Assert.assertEquals("COLUMN_SIZE", meta.getColumnLabel(7));
|
||||
Assert.assertEquals(12, columns.getInt(7));
|
||||
Assert.assertEquals(12, columns.getInt("COLUMN_SIZE"));
|
||||
// DECIMAL_DIGITS
|
||||
Assert.assertEquals("DECIMAL_DIGITS", meta.getColumnLabel(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt("DECIMAL_DIGITS"));
|
||||
Assert.assertEquals(null, columns.getString(9));
|
||||
Assert.assertEquals(null, columns.getString("DECIMAL_DIGITS"));
|
||||
// NUM_PREC_RADIX
|
||||
Assert.assertEquals("NUM_PREC_RADIX", meta.getColumnLabel(10));
|
||||
Assert.assertEquals(10, columns.getInt(10));
|
||||
Assert.assertEquals(10, columns.getInt("NUM_PREC_RADIX"));
|
||||
// NULLABLE
|
||||
Assert.assertEquals("NULLABLE", meta.getColumnLabel(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNullable, columns.getInt(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNullable, columns.getInt("NULLABLE"));
|
||||
// REMARKS
|
||||
Assert.assertEquals("REMARKS", meta.getColumnLabel(12));
|
||||
Assert.assertEquals(null, columns.getString(12));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -712,17 +813,35 @@ public class TSDBDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getPrimaryKeys() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet rs = metaData.getPrimaryKeys("log", "", "dn1");
|
||||
while (rs.next()) {
|
||||
System.out.println("TABLE_NAME: " + rs.getString("TABLE_NAME"));
|
||||
System.out.println("COLUMN_NAME: " + rs.getString("COLUMN_NAME"));
|
||||
System.out.println("KEY_SEQ: " + rs.getString("KEY_SEQ"));
|
||||
System.out.println("PK_NAME: " + rs.getString("PK_NAME"));
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", rs.getString(1));
|
||||
Assert.assertEquals("log", rs.getString("TABLE_CAT"));
|
||||
// TABLE_SCHEM
|
||||
Assert.assertEquals("TABLE_SCHEM", meta.getColumnLabel(2));
|
||||
Assert.assertEquals(null, rs.getString(2));
|
||||
Assert.assertEquals(null, rs.getString("TABLE_SCHEM"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn1", rs.getString(3));
|
||||
Assert.assertEquals("dn1", rs.getString("TABLE_NAME"));
|
||||
// COLUMN_NAME
|
||||
Assert.assertEquals("COLUMN_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("ts", rs.getString(4));
|
||||
Assert.assertEquals("ts", rs.getString("COLUMN_NAME"));
|
||||
// KEY_SEQ
|
||||
Assert.assertEquals("KEY_SEQ", meta.getColumnLabel(5));
|
||||
Assert.assertEquals(1, rs.getShort(5));
|
||||
Assert.assertEquals(1, rs.getShort("KEY_SEQ"));
|
||||
// DATA_TYPE
|
||||
Assert.assertEquals("PK_NAME", meta.getColumnLabel(6));
|
||||
Assert.assertEquals("ts", rs.getString(6));
|
||||
Assert.assertEquals("ts", rs.getString("PK_NAME"));
|
||||
}
|
||||
|
||||
Assert.assertNotNull(rs);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -847,14 +966,27 @@ public class TSDBDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getSuperTables() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet rs = metaData.getSuperTables("log", "", "dn1");
|
||||
while (rs.next()) {
|
||||
System.out.println("TABLE_NAME: " + rs.getString("TABLE_NAME"));
|
||||
System.out.println("SUPERTABLE_NAME: " + rs.getString("SUPERTABLE_NAME"));
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", rs.getString(1));
|
||||
Assert.assertEquals("log", rs.getString("TABLE_CAT"));
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_SCHEM", meta.getColumnLabel(2));
|
||||
Assert.assertEquals(null, rs.getString(2));
|
||||
Assert.assertEquals(null, rs.getString("TABLE_SCHEM"));
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn1", rs.getString(3));
|
||||
Assert.assertEquals("dn1", rs.getString("TABLE_NAME"));
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("SUPERTABLE_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("dn", rs.getString(4));
|
||||
Assert.assertEquals("dn", rs.getString("SUPERTABLE_NAME"));
|
||||
}
|
||||
Assert.assertNotNull(rs);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -951,15 +1083,12 @@ public class TSDBDatabaseMetaDataTest {
|
|||
@BeforeClass
|
||||
public static void beforeClass() {
|
||||
try {
|
||||
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
||||
Properties properties = new Properties();
|
||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||
connection = DriverManager.getConnection("jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata", properties);
|
||||
connection = DriverManager.getConnection(url, properties);
|
||||
metaData = connection.getMetaData().unwrap(TSDBDatabaseMetaData.class);
|
||||
} catch (ClassNotFoundException e) {
|
||||
e.printStackTrace();
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
|
|
@ -45,9 +45,9 @@ public class TSDBJNIConnectorTest {
|
|||
rowData = new TSDBResultSetRowData(columnSize);
|
||||
// iterate resultSet
|
||||
for (int i = 0; next(connector, pSql); i++) {
|
||||
System.out.println("col[" + i + "] size: " + rowData.getColSize());
|
||||
rowData.getData().stream().forEach(col -> System.out.print(col + "\t"));
|
||||
System.out.println();
|
||||
// System.out.println("col[" + i + "] size: " + rowData.getColSize());
|
||||
// rowData.getData().stream().forEach(col -> System.out.print(col + "\t"));
|
||||
// System.out.println();
|
||||
}
|
||||
// close resultSet
|
||||
code = connector.freeResultSet(pSql);
|
||||
|
|
|
@ -54,16 +54,17 @@ public class TSDBParameterMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getPrecision() throws SQLException {
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(1));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(2));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(3));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(4));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(5));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(6));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(7));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(8));
|
||||
Assert.assertEquals(5, parameterMetaData_insert.getPrecision(9));
|
||||
Assert.assertEquals(5, parameterMetaData_insert.getPrecision(10));
|
||||
//create table weather(ts timestamp, f1 int, f2 bigint, f3 float, f4 double, f5 smallint, f6 tinyint, f7 bool, f8 binary(64), f9 nchar(64))
|
||||
Assert.assertEquals(TSDBConstants.TIMESTAMP_MS_PRECISION, parameterMetaData_insert.getPrecision(1));
|
||||
Assert.assertEquals(TSDBConstants.INT_PRECISION, parameterMetaData_insert.getPrecision(2));
|
||||
Assert.assertEquals(TSDBConstants.BIGINT_PRECISION, parameterMetaData_insert.getPrecision(3));
|
||||
Assert.assertEquals(TSDBConstants.FLOAT_PRECISION, parameterMetaData_insert.getPrecision(4));
|
||||
Assert.assertEquals(TSDBConstants.DOUBLE_PRECISION, parameterMetaData_insert.getPrecision(5));
|
||||
Assert.assertEquals(TSDBConstants.SMALLINT_PRECISION, parameterMetaData_insert.getPrecision(6));
|
||||
Assert.assertEquals(TSDBConstants.TINYINT_PRECISION, parameterMetaData_insert.getPrecision(7));
|
||||
Assert.assertEquals(TSDBConstants.BOOLEAN_PRECISION, parameterMetaData_insert.getPrecision(8));
|
||||
Assert.assertEquals("hello".getBytes().length, parameterMetaData_insert.getPrecision(9));
|
||||
Assert.assertEquals("涛思数据".length(), parameterMetaData_insert.getPrecision(10));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -71,8 +72,8 @@ public class TSDBParameterMetaDataTest {
|
|||
Assert.assertEquals(0, parameterMetaData_insert.getScale(1));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(2));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(3));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(4));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(5));
|
||||
Assert.assertEquals(31, parameterMetaData_insert.getScale(4));
|
||||
Assert.assertEquals(31, parameterMetaData_insert.getScale(5));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(6));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(7));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(8));
|
||||
|
@ -124,10 +125,16 @@ public class TSDBParameterMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getParameterMode() throws SQLException {
|
||||
for (int i = 1; i <= parameterMetaData_insert.getParameterCount(); i++) {
|
||||
int parameterMode = parameterMetaData_insert.getParameterMode(i);
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMode);
|
||||
}
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(1));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(2));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(3));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(4));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(5));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(6));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(7));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(8));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(9));
|
||||
Assert.assertEquals(ParameterMetaData.parameterModeUnknown, parameterMetaData_insert.getParameterMode(10));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -144,7 +151,6 @@ public class TSDBParameterMetaDataTest {
|
|||
@BeforeClass
|
||||
public static void beforeClass() {
|
||||
try {
|
||||
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
||||
conn = DriverManager.getConnection("jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata");
|
||||
try (Statement stmt = conn.createStatement()) {
|
||||
stmt.execute("drop database if exists test_pstmt");
|
||||
|
@ -164,7 +170,7 @@ public class TSDBParameterMetaDataTest {
|
|||
pstmt_insert.setObject(7, Byte.MAX_VALUE);
|
||||
pstmt_insert.setObject(8, true);
|
||||
pstmt_insert.setObject(9, "hello".getBytes());
|
||||
pstmt_insert.setObject(10, "Hello");
|
||||
pstmt_insert.setObject(10, "涛思数据");
|
||||
parameterMetaData_insert = pstmt_insert.getParameterMetaData();
|
||||
|
||||
pstmt_select = conn.prepareStatement(sql_select);
|
||||
|
@ -173,7 +179,7 @@ public class TSDBParameterMetaDataTest {
|
|||
pstmt_select.setInt(3, 0);
|
||||
parameterMetaData_select = pstmt_select.getParameterMetaData();
|
||||
|
||||
} catch (ClassNotFoundException | SQLException e) {
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -14,6 +14,7 @@ import java.math.BigDecimal;
|
|||
import java.sql.*;
|
||||
import java.text.ParseException;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.Arrays;
|
||||
|
||||
public class TSDBResultSetTest {
|
||||
|
||||
|
@ -133,7 +134,7 @@ public class TSDBResultSetTest {
|
|||
Assert.assertEquals(3.1415926, Double.valueOf(new String(f5)), 0.000000f);
|
||||
|
||||
byte[] f6 = rs.getBytes("f6");
|
||||
Assert.assertEquals("abc", new String(f6));
|
||||
Assert.assertTrue(Arrays.equals("abc".getBytes(), f6));
|
||||
|
||||
byte[] f7 = rs.getBytes("f7");
|
||||
Assert.assertEquals((short) 10, Shorts.fromByteArray(f7));
|
||||
|
@ -176,8 +177,7 @@ public class TSDBResultSetTest {
|
|||
rs.getAsciiStream("f1");
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||
public void getUnicodeStream() throws SQLException {
|
||||
rs.getUnicodeStream("f1");
|
||||
}
|
||||
|
@ -646,7 +646,6 @@ public class TSDBResultSetTest {
|
|||
@BeforeClass
|
||||
public static void beforeClass() {
|
||||
try {
|
||||
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
||||
conn = DriverManager.getConnection("jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata");
|
||||
stmt = conn.createStatement();
|
||||
stmt.execute("create database if not exists restful_test");
|
||||
|
@ -656,10 +655,9 @@ public class TSDBResultSetTest {
|
|||
stmt.execute("insert into restful_test.weather values('2021-01-01 00:00:00.000', 1, 100, 3.1415, 3.1415926, 'abc', 10, 10, true, '涛思数据')");
|
||||
rs = stmt.executeQuery("select * from restful_test.weather");
|
||||
rs.next();
|
||||
} catch (ClassNotFoundException | SQLException e) {
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
|
|
|
@ -387,15 +387,12 @@ public class TSDBStatementTest {
|
|||
@BeforeClass
|
||||
public static void beforeClass() {
|
||||
try {
|
||||
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
||||
Properties properties = new Properties();
|
||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||
conn = DriverManager.getConnection("jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata", properties);
|
||||
stmt = conn.createStatement();
|
||||
} catch (ClassNotFoundException e) {
|
||||
e.printStackTrace();
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
|
|
@ -10,6 +10,7 @@ import java.sql.*;
|
|||
import java.util.Properties;
|
||||
|
||||
public class RestfulDatabaseMetaDataTest {
|
||||
|
||||
private static final String host = "127.0.0.1";
|
||||
private static final String url = "jdbc:TAOS-RS://" + host + ":6041/?user=root&password=taosdata";
|
||||
private static Connection connection;
|
||||
|
@ -632,17 +633,32 @@ public class RestfulDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getTables() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
ResultSet tables = metaData.getTables("log", "", null, null);
|
||||
ResultSetMetaData metaData = tables.getMetaData();
|
||||
while (tables.next()) {
|
||||
System.out.print(metaData.getColumnLabel(1) + ":" + tables.getString(1) + "\t");
|
||||
System.out.print(metaData.getColumnLabel(3) + ":" + tables.getString(3) + "\t");
|
||||
System.out.print(metaData.getColumnLabel(4) + ":" + tables.getString(4) + "\t");
|
||||
System.out.print(metaData.getColumnLabel(5) + ":" + tables.getString(5) + "\n");
|
||||
ResultSet rs = metaData.getTables("log", "", null, null);
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
Assert.assertNotNull(rs);
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", rs.getString(1));
|
||||
Assert.assertEquals("log", rs.getString("TABLE_CAT"));
|
||||
// TABLE_SCHEM
|
||||
Assert.assertEquals("TABLE_SCHEM", meta.getColumnLabel(2));
|
||||
Assert.assertEquals(null, rs.getString(2));
|
||||
Assert.assertEquals(null, rs.getString("TABLE_SCHEM"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertNotNull(rs.getString(3));
|
||||
Assert.assertNotNull(rs.getString("TABLE_NAME"));
|
||||
// TABLE_TYPE
|
||||
Assert.assertEquals("TABLE_TYPE", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("TABLE", rs.getString(4));
|
||||
Assert.assertEquals("TABLE", rs.getString("TABLE_TYPE"));
|
||||
// REMARKS
|
||||
Assert.assertEquals("REMARKS", meta.getColumnLabel(5));
|
||||
Assert.assertEquals("", rs.getString(5));
|
||||
Assert.assertEquals("", rs.getString("REMARKS"));
|
||||
}
|
||||
System.out.println();
|
||||
Assert.assertNotNull(tables);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -652,46 +668,130 @@ public class RestfulDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getCatalogs() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet catalogs = metaData.getCatalogs();
|
||||
ResultSetMetaData meta = catalogs.getMetaData();
|
||||
while (catalogs.next()) {
|
||||
for (int i = 1; i <= meta.getColumnCount(); i++) {
|
||||
System.out.print(meta.getColumnLabel(i) + ": " + catalogs.getString(i));
|
||||
}
|
||||
System.out.println();
|
||||
ResultSet rs = metaData.getCatalogs();
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertNotNull(rs.getString(1));
|
||||
Assert.assertNotNull(rs.getString("TABLE_CAT"));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getTableTypes() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet tableTypes = metaData.getTableTypes();
|
||||
while (tableTypes.next()) {
|
||||
System.out.println(tableTypes.getString("TABLE_TYPE"));
|
||||
tableTypes.next();
|
||||
// tableTypes: table
|
||||
{
|
||||
Assert.assertEquals("TABLE", tableTypes.getString(1));
|
||||
Assert.assertEquals("TABLE", tableTypes.getString("TABLE_TYPE"));
|
||||
}
|
||||
tableTypes.next();
|
||||
// tableTypes: stable
|
||||
{
|
||||
Assert.assertEquals("STABLE", tableTypes.getString(1));
|
||||
Assert.assertEquals("STABLE", tableTypes.getString("TABLE_TYPE"));
|
||||
}
|
||||
Assert.assertNotNull(metaData.getTableTypes());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getColumns() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
// when
|
||||
ResultSet columns = metaData.getColumns("log", "", "dn", "");
|
||||
// then
|
||||
ResultSetMetaData meta = columns.getMetaData();
|
||||
while (columns.next()) {
|
||||
System.out.print(meta.getColumnLabel(1) + ": " + columns.getString(1) + "\t");
|
||||
System.out.print(meta.getColumnLabel(3) + ": " + columns.getString(3) + "\t");
|
||||
System.out.print(meta.getColumnLabel(4) + ": " + columns.getString(4) + "\t");
|
||||
System.out.print(meta.getColumnLabel(5) + ": " + columns.getString(5) + "\t");
|
||||
System.out.print(meta.getColumnLabel(6) + ": " + columns.getString(6) + "\t");
|
||||
System.out.print(meta.getColumnLabel(7) + ": " + columns.getString(7) + "\t");
|
||||
System.out.print(meta.getColumnLabel(9) + ": " + columns.getString(9) + "\t");
|
||||
System.out.print(meta.getColumnLabel(10) + ": " + columns.getString(10) + "\t");
|
||||
System.out.print(meta.getColumnLabel(11) + ": " + columns.getString(11) + "\n");
|
||||
System.out.print(meta.getColumnLabel(12) + ": " + columns.getString(12) + "\n");
|
||||
columns.next();
|
||||
// column: 1
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", columns.getString(1));
|
||||
Assert.assertEquals("log", columns.getString("TABLE_CAT"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn", columns.getString(3));
|
||||
Assert.assertEquals("dn", columns.getString("TABLE_NAME"));
|
||||
// COLUMN_NAME
|
||||
Assert.assertEquals("COLUMN_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("ts", columns.getString(4));
|
||||
Assert.assertEquals("ts", columns.getString("COLUMN_NAME"));
|
||||
// DATA_TYPE
|
||||
Assert.assertEquals("DATA_TYPE", meta.getColumnLabel(5));
|
||||
Assert.assertEquals(Types.TIMESTAMP, columns.getInt(5));
|
||||
Assert.assertEquals(Types.TIMESTAMP, columns.getInt("DATA_TYPE"));
|
||||
// TYPE_NAME
|
||||
Assert.assertEquals("TYPE_NAME", meta.getColumnLabel(6));
|
||||
Assert.assertEquals("TIMESTAMP", columns.getString(6));
|
||||
Assert.assertEquals("TIMESTAMP", columns.getString("TYPE_NAME"));
|
||||
// COLUMN_SIZE
|
||||
Assert.assertEquals("COLUMN_SIZE", meta.getColumnLabel(7));
|
||||
Assert.assertEquals(26, columns.getInt(7));
|
||||
Assert.assertEquals(26, columns.getInt("COLUMN_SIZE"));
|
||||
// DECIMAL_DIGITS
|
||||
Assert.assertEquals("DECIMAL_DIGITS", meta.getColumnLabel(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt("DECIMAL_DIGITS"));
|
||||
Assert.assertEquals(null, columns.getString(9));
|
||||
Assert.assertEquals(null, columns.getString("DECIMAL_DIGITS"));
|
||||
// NUM_PREC_RADIX
|
||||
Assert.assertEquals("NUM_PREC_RADIX", meta.getColumnLabel(10));
|
||||
Assert.assertEquals(10, columns.getInt(10));
|
||||
Assert.assertEquals(10, columns.getInt("NUM_PREC_RADIX"));
|
||||
// NULLABLE
|
||||
Assert.assertEquals("NULLABLE", meta.getColumnLabel(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNoNulls, columns.getInt(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNoNulls, columns.getInt("NULLABLE"));
|
||||
// REMARKS
|
||||
Assert.assertEquals("REMARKS", meta.getColumnLabel(12));
|
||||
Assert.assertEquals(null, columns.getString(12));
|
||||
Assert.assertEquals(null, columns.getString("REMARKS"));
|
||||
}
|
||||
columns.next();
|
||||
// column: 2
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", columns.getString(1));
|
||||
Assert.assertEquals("log", columns.getString("TABLE_CAT"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn", columns.getString(3));
|
||||
Assert.assertEquals("dn", columns.getString("TABLE_NAME"));
|
||||
// COLUMN_NAME
|
||||
Assert.assertEquals("COLUMN_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("cpu_taosd", columns.getString(4));
|
||||
Assert.assertEquals("cpu_taosd", columns.getString("COLUMN_NAME"));
|
||||
// DATA_TYPE
|
||||
Assert.assertEquals("DATA_TYPE", meta.getColumnLabel(5));
|
||||
Assert.assertEquals(Types.FLOAT, columns.getInt(5));
|
||||
Assert.assertEquals(Types.FLOAT, columns.getInt("DATA_TYPE"));
|
||||
// TYPE_NAME
|
||||
Assert.assertEquals("TYPE_NAME", meta.getColumnLabel(6));
|
||||
Assert.assertEquals("FLOAT", columns.getString(6));
|
||||
Assert.assertEquals("FLOAT", columns.getString("TYPE_NAME"));
|
||||
// COLUMN_SIZE
|
||||
Assert.assertEquals("COLUMN_SIZE", meta.getColumnLabel(7));
|
||||
Assert.assertEquals(12, columns.getInt(7));
|
||||
Assert.assertEquals(12, columns.getInt("COLUMN_SIZE"));
|
||||
// DECIMAL_DIGITS
|
||||
Assert.assertEquals("DECIMAL_DIGITS", meta.getColumnLabel(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt(9));
|
||||
Assert.assertEquals(Integer.MIN_VALUE, columns.getInt("DECIMAL_DIGITS"));
|
||||
Assert.assertEquals(null, columns.getString(9));
|
||||
Assert.assertEquals(null, columns.getString("DECIMAL_DIGITS"));
|
||||
// NUM_PREC_RADIX
|
||||
Assert.assertEquals("NUM_PREC_RADIX", meta.getColumnLabel(10));
|
||||
Assert.assertEquals(10, columns.getInt(10));
|
||||
Assert.assertEquals(10, columns.getInt("NUM_PREC_RADIX"));
|
||||
// NULLABLE
|
||||
Assert.assertEquals("NULLABLE", meta.getColumnLabel(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNullable, columns.getInt(11));
|
||||
Assert.assertEquals(DatabaseMetaData.columnNullable, columns.getInt("NULLABLE"));
|
||||
// REMARKS
|
||||
Assert.assertEquals("REMARKS", meta.getColumnLabel(12));
|
||||
Assert.assertEquals(null, columns.getString(12));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -717,17 +817,35 @@ public class RestfulDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getPrimaryKeys() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet rs = metaData.getPrimaryKeys("log", "", "dn1");
|
||||
while (rs.next()) {
|
||||
System.out.println("TABLE_NAME: " + rs.getString("TABLE_NAME"));
|
||||
System.out.println("COLUMN_NAME: " + rs.getString("COLUMN_NAME"));
|
||||
System.out.println("KEY_SEQ: " + rs.getString("KEY_SEQ"));
|
||||
System.out.println("PK_NAME: " + rs.getString("PK_NAME"));
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", rs.getString(1));
|
||||
Assert.assertEquals("log", rs.getString("TABLE_CAT"));
|
||||
// TABLE_SCHEM
|
||||
Assert.assertEquals("TABLE_SCHEM", meta.getColumnLabel(2));
|
||||
Assert.assertEquals(null, rs.getString(2));
|
||||
Assert.assertEquals(null, rs.getString("TABLE_SCHEM"));
|
||||
// TABLE_NAME
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn1", rs.getString(3));
|
||||
Assert.assertEquals("dn1", rs.getString("TABLE_NAME"));
|
||||
// COLUMN_NAME
|
||||
Assert.assertEquals("COLUMN_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("ts", rs.getString(4));
|
||||
Assert.assertEquals("ts", rs.getString("COLUMN_NAME"));
|
||||
// KEY_SEQ
|
||||
Assert.assertEquals("KEY_SEQ", meta.getColumnLabel(5));
|
||||
Assert.assertEquals(1, rs.getShort(5));
|
||||
Assert.assertEquals(1, rs.getShort("KEY_SEQ"));
|
||||
// DATA_TYPE
|
||||
Assert.assertEquals("PK_NAME", meta.getColumnLabel(6));
|
||||
Assert.assertEquals("ts", rs.getString(6));
|
||||
Assert.assertEquals("ts", rs.getString("PK_NAME"));
|
||||
}
|
||||
|
||||
Assert.assertNotNull(rs);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -852,14 +970,27 @@ public class RestfulDatabaseMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getSuperTables() throws SQLException {
|
||||
System.out.println("****************************************************");
|
||||
|
||||
ResultSet rs = metaData.getSuperTables("log", "", "dn1");
|
||||
while (rs.next()) {
|
||||
System.out.println("TABLE_NAME: " + rs.getString("TABLE_NAME"));
|
||||
System.out.println("SUPERTABLE_NAME: " + rs.getString("SUPERTABLE_NAME"));
|
||||
ResultSetMetaData meta = rs.getMetaData();
|
||||
rs.next();
|
||||
{
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_CAT", meta.getColumnLabel(1));
|
||||
Assert.assertEquals("log", rs.getString(1));
|
||||
Assert.assertEquals("log", rs.getString("TABLE_CAT"));
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_SCHEM", meta.getColumnLabel(2));
|
||||
Assert.assertEquals(null, rs.getString(2));
|
||||
Assert.assertEquals(null, rs.getString("TABLE_SCHEM"));
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("TABLE_NAME", meta.getColumnLabel(3));
|
||||
Assert.assertEquals("dn1", rs.getString(3));
|
||||
Assert.assertEquals("dn1", rs.getString("TABLE_NAME"));
|
||||
// TABLE_CAT
|
||||
Assert.assertEquals("SUPERTABLE_NAME", meta.getColumnLabel(4));
|
||||
Assert.assertEquals("dn", rs.getString(4));
|
||||
Assert.assertEquals("dn", rs.getString("SUPERTABLE_NAME"));
|
||||
}
|
||||
Assert.assertNotNull(rs);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
|
@ -54,16 +54,17 @@ public class RestfulParameterMetaDataTest {
|
|||
|
||||
@Test
|
||||
public void getPrecision() throws SQLException {
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(1));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(2));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(3));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(4));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(5));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(6));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(7));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getPrecision(8));
|
||||
Assert.assertEquals(5, parameterMetaData_insert.getPrecision(9));
|
||||
Assert.assertEquals(5, parameterMetaData_insert.getPrecision(10));
|
||||
//create table weather(ts timestamp, f1 int, f2 bigint, f3 float, f4 double, f5 smallint, f6 tinyint, f7 bool, f8 binary(64), f9 nchar(64))
|
||||
Assert.assertEquals(TSDBConstants.TIMESTAMP_MS_PRECISION, parameterMetaData_insert.getPrecision(1));
|
||||
Assert.assertEquals(TSDBConstants.INT_PRECISION, parameterMetaData_insert.getPrecision(2));
|
||||
Assert.assertEquals(TSDBConstants.BIGINT_PRECISION, parameterMetaData_insert.getPrecision(3));
|
||||
Assert.assertEquals(TSDBConstants.FLOAT_PRECISION, parameterMetaData_insert.getPrecision(4));
|
||||
Assert.assertEquals(TSDBConstants.DOUBLE_PRECISION, parameterMetaData_insert.getPrecision(5));
|
||||
Assert.assertEquals(TSDBConstants.SMALLINT_PRECISION, parameterMetaData_insert.getPrecision(6));
|
||||
Assert.assertEquals(TSDBConstants.TINYINT_PRECISION, parameterMetaData_insert.getPrecision(7));
|
||||
Assert.assertEquals(TSDBConstants.BOOLEAN_PRECISION, parameterMetaData_insert.getPrecision(8));
|
||||
Assert.assertEquals("hello".getBytes().length, parameterMetaData_insert.getPrecision(9));
|
||||
Assert.assertEquals("涛思数据".length(), parameterMetaData_insert.getPrecision(10));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -71,8 +72,8 @@ public class RestfulParameterMetaDataTest {
|
|||
Assert.assertEquals(0, parameterMetaData_insert.getScale(1));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(2));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(3));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(4));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(5));
|
||||
Assert.assertEquals(31, parameterMetaData_insert.getScale(4));
|
||||
Assert.assertEquals(31, parameterMetaData_insert.getScale(5));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(6));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(7));
|
||||
Assert.assertEquals(0, parameterMetaData_insert.getScale(8));
|
||||
|
@ -164,7 +165,7 @@ public class RestfulParameterMetaDataTest {
|
|||
pstmt_insert.setObject(7, Byte.MAX_VALUE);
|
||||
pstmt_insert.setObject(8, true);
|
||||
pstmt_insert.setObject(9, "hello".getBytes());
|
||||
pstmt_insert.setObject(10, "Hello");
|
||||
pstmt_insert.setObject(10, "涛思数据");
|
||||
parameterMetaData_insert = pstmt_insert.getParameterMetaData();
|
||||
|
||||
pstmt_select = conn.prepareStatement(sql_select);
|
||||
|
|
|
@ -124,6 +124,7 @@ int taos_stmt_add_batch(TAOS_STMT *stmt);
|
|||
int taos_stmt_execute(TAOS_STMT *stmt);
|
||||
TAOS_RES * taos_stmt_use_result(TAOS_STMT *stmt);
|
||||
int taos_stmt_close(TAOS_STMT *stmt);
|
||||
char * taos_stmt_errstr(TAOS_STMT *stmt);
|
||||
|
||||
DLL_EXPORT TAOS_RES *taos_query(TAOS *taos, const char *sql);
|
||||
DLL_EXPORT TAOS_ROW taos_fetch_row(TAOS_RES *res);
|
||||
|
|
|
@ -66,17 +66,19 @@ extern "C" {
|
|||
#define TSDB_FUNC_RATE 29
|
||||
#define TSDB_FUNC_IRATE 30
|
||||
#define TSDB_FUNC_TID_TAG 31
|
||||
#define TSDB_FUNC_BLKINFO 32
|
||||
#define TSDB_FUNC_DERIVATIVE 32
|
||||
#define TSDB_FUNC_BLKINFO 33
|
||||
|
||||
#define TSDB_FUNC_HISTOGRAM 33
|
||||
#define TSDB_FUNC_HLL 34
|
||||
#define TSDB_FUNC_MODE 35
|
||||
#define TSDB_FUNC_SAMPLE 36
|
||||
#define TSDB_FUNC_CEIL 37
|
||||
#define TSDB_FUNC_FLOOR 38
|
||||
#define TSDB_FUNC_ROUND 39
|
||||
#define TSDB_FUNC_MAVG 40
|
||||
#define TSDB_FUNC_CSUM 41
|
||||
|
||||
#define TSDB_FUNC_HISTOGRAM 34
|
||||
#define TSDB_FUNC_HLL 35
|
||||
#define TSDB_FUNC_MODE 36
|
||||
#define TSDB_FUNC_SAMPLE 37
|
||||
#define TSDB_FUNC_CEIL 38
|
||||
#define TSDB_FUNC_FLOOR 39
|
||||
#define TSDB_FUNC_ROUND 40
|
||||
#define TSDB_FUNC_MAVG 41
|
||||
#define TSDB_FUNC_CSUM 42
|
||||
|
||||
#define TSDB_FUNCSTATE_SO 0x1u // single output
|
||||
#define TSDB_FUNCSTATE_MO 0x2u // dynamic number of output, not multinumber of output e.g., TOP/BOTTOM
|
||||
|
|
|
@ -113,6 +113,7 @@ typedef struct SColumnFilterElem {
|
|||
int16_t bytes; // column length
|
||||
__filter_func_t fp;
|
||||
SColumnFilterInfo filterInfo;
|
||||
void *q;
|
||||
} SColumnFilterElem;
|
||||
|
||||
typedef struct SSingleColumnFilterInfo {
|
||||
|
@ -185,6 +186,7 @@ typedef struct SQueryAttr {
|
|||
bool queryBlockDist; // if query data block distribution
|
||||
bool stabledev; // super table stddev query
|
||||
bool tsCompQuery; // is tscomp query
|
||||
bool diffQuery; // is diff query
|
||||
bool simpleAgg;
|
||||
bool pointInterpQuery; // point interpolation query
|
||||
bool needReverseScan; // need reverse scan
|
||||
|
@ -245,6 +247,7 @@ typedef struct SQueryRuntimeEnv {
|
|||
void* pQueryHandle;
|
||||
|
||||
int32_t prevGroupId; // previous executed group id
|
||||
bool enableGroupData;
|
||||
SDiskbasedResultBuf* pResultBuf; // query result buffer based on blocked-wised disk file
|
||||
SHashObj* pResultRowHashTable; // quick locate the window object for each result
|
||||
char* keyBuf; // window key buffer
|
||||
|
@ -386,6 +389,7 @@ typedef struct STableScanInfo {
|
|||
int64_t elapsedTime;
|
||||
|
||||
int32_t tableIndex;
|
||||
int32_t prevGroupId; // previous table group id
|
||||
} STableScanInfo;
|
||||
|
||||
typedef struct STagScanInfo {
|
||||
|
|
|
@ -138,6 +138,7 @@ typedef struct SQueryInfo {
|
|||
bool hasFilter;
|
||||
bool onlyTagQuery;
|
||||
bool orderProjectQuery;
|
||||
bool diffQuery;
|
||||
bool stateWindow;
|
||||
} SQueryInfo;
|
||||
|
||||
|
|
|
@ -161,6 +161,14 @@ typedef struct SRateInfo {
|
|||
bool isIRate; // true for IRate functions, false for Rate functions
|
||||
} SRateInfo;
|
||||
|
||||
typedef struct SDerivInfo {
|
||||
double prevValue; // previous value
|
||||
TSKEY prevTs; // previous timestamp
|
||||
bool ignoreNegative;// ignore the negative value
|
||||
int64_t tsWindow; // time window for derivative
|
||||
bool valueSet; // the value has been set already
|
||||
} SDerivInfo;
|
||||
|
||||
int32_t getResultDataInfo(int32_t dataType, int32_t dataBytes, int32_t functionId, int32_t param, int16_t *type,
|
||||
int16_t *bytes, int32_t *interBytes, int16_t extLength, bool isSuperTable) {
|
||||
if (!isValidDataType(dataType)) {
|
||||
|
@ -189,7 +197,9 @@ int32_t getResultDataInfo(int32_t dataType, int32_t dataBytes, int32_t functionI
|
|||
*bytes = (int16_t)(dataBytes + sizeof(int16_t) + sizeof(int64_t) + sizeof(int32_t) + sizeof(int32_t) + VARSTR_HEADER_SIZE);
|
||||
*interBytes = 0;
|
||||
return TSDB_CODE_SUCCESS;
|
||||
} else if (functionId == TSDB_FUNC_BLKINFO) {
|
||||
}
|
||||
|
||||
if (functionId == TSDB_FUNC_BLKINFO) {
|
||||
*type = TSDB_DATA_TYPE_BINARY;
|
||||
*bytes = 16384;
|
||||
*interBytes = 0;
|
||||
|
@ -216,7 +226,14 @@ int32_t getResultDataInfo(int32_t dataType, int32_t dataBytes, int32_t functionI
|
|||
*interBytes = POINTER_BYTES;
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
if (functionId == TSDB_FUNC_DERIVATIVE) {
|
||||
*type = TSDB_DATA_TYPE_DOUBLE;
|
||||
*bytes = sizeof(double); // this results is compressed ts data, only one byte
|
||||
*interBytes = sizeof(SDerivInfo);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
if (isSuperTable) {
|
||||
if (functionId == TSDB_FUNC_MIN || functionId == TSDB_FUNC_MAX) {
|
||||
*type = TSDB_DATA_TYPE_BINARY;
|
||||
|
@ -3393,7 +3410,7 @@ enum {
|
|||
};
|
||||
|
||||
static bool diff_function_setup(SQLFunctionCtx *pCtx) {
|
||||
if (function_setup(pCtx)) {
|
||||
if (!function_setup(pCtx)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -3402,206 +3419,194 @@ static bool diff_function_setup(SQLFunctionCtx *pCtx) {
|
|||
return false;
|
||||
}
|
||||
|
||||
// TODO difference in date column
|
||||
static void diff_function(SQLFunctionCtx *pCtx) {
|
||||
static bool deriv_function_setup(SQLFunctionCtx *pCtx) {
|
||||
if (!function_setup(pCtx)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// diff function require the value is set to -1
|
||||
SResultRowCellInfo *pResInfo = GET_RES_INFO(pCtx);
|
||||
SDerivInfo* pDerivInfo = GET_ROWCELL_INTERBUF(pResInfo);
|
||||
|
||||
pDerivInfo->ignoreNegative = pCtx->param[2].i64;
|
||||
pDerivInfo->prevTs = -1;
|
||||
pDerivInfo->tsWindow = pCtx->param[0].i64;
|
||||
pDerivInfo->valueSet = false;
|
||||
return false;
|
||||
}
|
||||
|
||||
static void deriv_function(SQLFunctionCtx *pCtx) {
|
||||
SResultRowCellInfo *pResInfo = GET_RES_INFO(pCtx);
|
||||
SDerivInfo* pDerivInfo = GET_ROWCELL_INTERBUF(pResInfo);
|
||||
|
||||
void *data = GET_INPUT_DATA_LIST(pCtx);
|
||||
bool isFirstBlock = (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED);
|
||||
|
||||
bool isFirstBlock = (pDerivInfo->valueSet == false);
|
||||
|
||||
int32_t notNullElems = 0;
|
||||
|
||||
|
||||
int32_t step = GET_FORWARD_DIRECTION_FACTOR(pCtx->order);
|
||||
int32_t i = (pCtx->order == TSDB_ORDER_ASC) ? 0 : pCtx->size - 1;
|
||||
|
||||
TSKEY* pTimestamp = pCtx->ptsOutputBuf;
|
||||
TSKEY* tsList = GET_TS_LIST(pCtx);
|
||||
|
||||
TSKEY *pTimestamp = pCtx->ptsOutputBuf;
|
||||
TSKEY *tsList = GET_TS_LIST(pCtx);
|
||||
|
||||
double *pOutput = (double *)pCtx->pOutput;
|
||||
|
||||
switch (pCtx->inputType) {
|
||||
case TSDB_DATA_TYPE_INT: {
|
||||
int32_t *pData = (int32_t *)data;
|
||||
int32_t *pOutput = (int32_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
if (pCtx->hasNull && isNull((const char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
} else if ((i == 0 && pCtx->order == TSDB_ORDER_ASC) || (i == pCtx->size - 1 && pCtx->order == TSDB_ORDER_DESC)) {
|
||||
*pOutput = (int32_t)(pData[i] - pCtx->param[1].i64);
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
|
||||
if (!pDerivInfo->valueSet) { // initial value is not set yet
|
||||
pDerivInfo->valueSet = true;
|
||||
} else {
|
||||
*pOutput = (int32_t)(pData[i] - pCtx->param[1].i64); // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
*pOutput = ((pData[i] - pDerivInfo->prevValue) * pDerivInfo->tsWindow) / (tsList[i] - pDerivInfo->prevTs);
|
||||
if (pDerivInfo->ignoreNegative && *pOutput < 0) {
|
||||
} else {
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
|
||||
pDerivInfo->prevValue = pData[i];
|
||||
pDerivInfo->prevTs = tsList[i];
|
||||
notNullElems++;
|
||||
}
|
||||
|
||||
break;
|
||||
};
|
||||
|
||||
case TSDB_DATA_TYPE_BIGINT: {
|
||||
int64_t *pData = (int64_t *)data;
|
||||
int64_t *pOutput = (int64_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
if (pCtx->hasNull && isNull((const char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
} else if ((i == 0 && pCtx->order == TSDB_ORDER_ASC) || (i == pCtx->size - 1 && pCtx->order == TSDB_ORDER_DESC)) {
|
||||
*pOutput = pData[i] - pCtx->param[1].i64;
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
|
||||
if (!pDerivInfo->valueSet) { // initial value is not set yet
|
||||
pDerivInfo->valueSet = true;
|
||||
} else {
|
||||
*pOutput = pData[i] - pCtx->param[1].i64;
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
*pOutput = ((pData[i] - pDerivInfo->prevValue) * pDerivInfo->tsWindow) / (tsList[i] - pDerivInfo->prevTs);
|
||||
if (pDerivInfo->ignoreNegative && *pOutput < 0) {
|
||||
} else {
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
|
||||
pDerivInfo->prevValue = (double) pData[i];
|
||||
pDerivInfo->prevTs = tsList[i];
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case TSDB_DATA_TYPE_DOUBLE: {
|
||||
double *pData = (double *)data;
|
||||
double *pOutput = (double *)pCtx->pOutput;
|
||||
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
if (pCtx->hasNull && isNull((const char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
pCtx->param[1].dKey = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
} else if ((i == 0 && pCtx->order == TSDB_ORDER_ASC) || (i == pCtx->size - 1 && pCtx->order == TSDB_ORDER_DESC)) {
|
||||
*pOutput = pData[i] - pCtx->param[1].dKey;
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
|
||||
if (!pDerivInfo->valueSet) { // initial value is not set yet
|
||||
pDerivInfo->valueSet = true;
|
||||
} else {
|
||||
*pOutput = pData[i] - pCtx->param[1].dKey;
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
*pOutput = ((pData[i] - pDerivInfo->prevValue) * pDerivInfo->tsWindow) / (tsList[i] - pDerivInfo->prevTs);
|
||||
if (pDerivInfo->ignoreNegative && *pOutput < 0) {
|
||||
} else {
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
}
|
||||
|
||||
pCtx->param[1].dKey = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
|
||||
pDerivInfo->prevValue = pData[i];
|
||||
pDerivInfo->prevTs = tsList[i];
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case TSDB_DATA_TYPE_FLOAT: {
|
||||
float *pData = (float *)data;
|
||||
float *pOutput = (float *)pCtx->pOutput;
|
||||
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
if (pCtx->hasNull && isNull((const char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
pCtx->param[1].dKey = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
} else if ((i == 0 && pCtx->order == TSDB_ORDER_ASC) || (i == pCtx->size - 1 && pCtx->order == TSDB_ORDER_DESC)) {
|
||||
*pOutput = (float)(pData[i] - pCtx->param[1].dKey);
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
|
||||
if (!pDerivInfo->valueSet) { // initial value is not set yet
|
||||
pDerivInfo->valueSet = true;
|
||||
} else {
|
||||
*pOutput = (float)(pData[i] - pCtx->param[1].dKey);
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
*pOutput = ((pData[i] - pDerivInfo->prevValue) * pDerivInfo->tsWindow) / (tsList[i] - pDerivInfo->prevTs);
|
||||
if (pDerivInfo->ignoreNegative && *pOutput < 0) {
|
||||
} else {
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
}
|
||||
|
||||
// keep the last value, the remain may be all null
|
||||
pCtx->param[1].dKey = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
|
||||
pDerivInfo->prevValue = pData[i];
|
||||
pDerivInfo->prevTs = tsList[i];
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case TSDB_DATA_TYPE_SMALLINT: {
|
||||
int16_t *pData = (int16_t *)data;
|
||||
int16_t *pOutput = (int16_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
if (pCtx->hasNull && isNull((const char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
} else if ((i == 0 && pCtx->order == TSDB_ORDER_ASC) || (i == pCtx->size - 1 && pCtx->order == TSDB_ORDER_DESC)) {
|
||||
*pOutput = (int16_t)(pData[i] - pCtx->param[1].i64);
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
|
||||
if (!pDerivInfo->valueSet) { // initial value is not set yet
|
||||
pDerivInfo->valueSet = true;
|
||||
} else {
|
||||
*pOutput = (int16_t)(pData[i] - pCtx->param[1].i64);
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
*pOutput = ((pData[i] - pDerivInfo->prevValue) * pDerivInfo->tsWindow) / (tsList[i] - pDerivInfo->prevTs);
|
||||
if (pDerivInfo->ignoreNegative && *pOutput < 0) {
|
||||
} else {
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
|
||||
pDerivInfo->prevValue = pData[i];
|
||||
pDerivInfo->prevTs = tsList[i];
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case TSDB_DATA_TYPE_TINYINT: {
|
||||
int8_t *pData = (int8_t *)data;
|
||||
int8_t *pOutput = (int8_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
} else if ((i == 0 && pCtx->order == TSDB_ORDER_ASC) || (i == pCtx->size - 1 && pCtx->order == TSDB_ORDER_DESC)) {
|
||||
*pOutput = (int8_t)(pData[i] - pCtx->param[1].i64);
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
|
||||
if (!pDerivInfo->valueSet) { // initial value is not set yet
|
||||
pDerivInfo->valueSet = true;
|
||||
} else {
|
||||
*pOutput = (int8_t)(pData[i] - pCtx->param[1].i64);
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
*pOutput = ((pData[i] - pDerivInfo->prevValue) * pDerivInfo->tsWindow) / (tsList[i] - pDerivInfo->prevTs);
|
||||
if (pDerivInfo->ignoreNegative && *pOutput < 0) {
|
||||
} else {
|
||||
*pTimestamp = tsList[i];
|
||||
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
|
||||
pDerivInfo->prevValue = pData[i];
|
||||
pDerivInfo->prevTs = tsList[i];
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
|
@ -3609,9 +3614,9 @@ static void diff_function(SQLFunctionCtx *pCtx) {
|
|||
default:
|
||||
qError("error input type");
|
||||
}
|
||||
|
||||
// initial value is not set yet
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED || notNullElems <= 0) {
|
||||
|
||||
// initial value is not set yet, all data block are null
|
||||
if (!pDerivInfo->valueSet || notNullElems <= 0) {
|
||||
/*
|
||||
* 1. current block and blocks before are full of null
|
||||
* 2. current block may be null value
|
||||
|
@ -3619,7 +3624,6 @@ static void diff_function(SQLFunctionCtx *pCtx) {
|
|||
assert(pCtx->hasNull);
|
||||
} else {
|
||||
int32_t forwardStep = (isFirstBlock) ? notNullElems - 1 : notNullElems;
|
||||
|
||||
GET_RES_INFO(pCtx)->numOfRes += forwardStep;
|
||||
}
|
||||
}
|
||||
|
@ -3636,19 +3640,184 @@ static void diff_function(SQLFunctionCtx *pCtx) {
|
|||
} \
|
||||
} while (0);
|
||||
|
||||
// TODO difference in date column
|
||||
static void diff_function(SQLFunctionCtx *pCtx) {
|
||||
void *data = GET_INPUT_DATA_LIST(pCtx);
|
||||
bool isFirstBlock = (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED);
|
||||
|
||||
int32_t notNullElems = 0;
|
||||
|
||||
int32_t step = GET_FORWARD_DIRECTION_FACTOR(pCtx->order);
|
||||
int32_t i = (pCtx->order == TSDB_ORDER_ASC) ? 0 : pCtx->size - 1;
|
||||
|
||||
TSKEY* pTimestamp = pCtx->ptsOutputBuf;
|
||||
TSKEY* tsList = GET_TS_LIST(pCtx);
|
||||
|
||||
switch (pCtx->inputType) {
|
||||
case TSDB_DATA_TYPE_INT: {
|
||||
int32_t *pData = (int32_t *)data;
|
||||
int32_t *pOutput = (int32_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
*pOutput = (int32_t)(pData[i] - pCtx->param[1].i64); // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
};
|
||||
case TSDB_DATA_TYPE_BIGINT: {
|
||||
int64_t *pData = (int64_t *)data;
|
||||
int64_t *pOutput = (int64_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
*pOutput = pData[i] - pCtx->param[1].i64; // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case TSDB_DATA_TYPE_DOUBLE: {
|
||||
double *pData = (double *)data;
|
||||
double *pOutput = (double *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
*pOutput = pData[i] - pCtx->param[1].dKey; // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
|
||||
pCtx->param[1].dKey = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case TSDB_DATA_TYPE_FLOAT: {
|
||||
float *pData = (float *)data;
|
||||
float *pOutput = (float *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
*pOutput = (float)(pData[i] - pCtx->param[1].dKey); // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
|
||||
pCtx->param[1].dKey = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case TSDB_DATA_TYPE_SMALLINT: {
|
||||
int16_t *pData = (int16_t *)data;
|
||||
int16_t *pOutput = (int16_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((const char*) &pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
*pOutput = (int16_t)(pData[i] - pCtx->param[1].i64); // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case TSDB_DATA_TYPE_TINYINT: {
|
||||
int8_t *pData = (int8_t *)data;
|
||||
int8_t *pOutput = (int8_t *)pCtx->pOutput;
|
||||
|
||||
for (; i < pCtx->size && i >= 0; i += step) {
|
||||
if (pCtx->hasNull && isNull((char *)&pData[i], pCtx->inputType)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
*pOutput = (int8_t)(pData[i] - pCtx->param[1].i64); // direct previous may be null
|
||||
*pTimestamp = tsList[i];
|
||||
pOutput += 1;
|
||||
pTimestamp += 1;
|
||||
}
|
||||
|
||||
pCtx->param[1].i64 = pData[i];
|
||||
pCtx->param[1].nType = pCtx->inputType;
|
||||
notNullElems++;
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
qError("error input type");
|
||||
}
|
||||
|
||||
// initial value is not set yet
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED || notNullElems <= 0) {
|
||||
/*
|
||||
* 1. current block and blocks before are full of null
|
||||
* 2. current block may be null value
|
||||
*/
|
||||
assert(pCtx->hasNull);
|
||||
} else {
|
||||
int32_t forwardStep = (isFirstBlock) ? notNullElems - 1 : notNullElems;
|
||||
|
||||
GET_RES_INFO(pCtx)->numOfRes += forwardStep;
|
||||
}
|
||||
}
|
||||
|
||||
static void diff_function_f(SQLFunctionCtx *pCtx, int32_t index) {
|
||||
char *pData = GET_INPUT_DATA(pCtx, index);
|
||||
if (pCtx->hasNull && isNull(pData, pCtx->inputType)) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// the output start from the second source element
|
||||
if (pCtx->param[1].nType != INITIAL_VALUE_NOT_ASSIGNED) { // initial value is set
|
||||
GET_RES_INFO(pCtx)->numOfRes += 1;
|
||||
}
|
||||
|
||||
|
||||
int32_t step = 1/*GET_FORWARD_DIRECTION_FACTOR(pCtx->order)*/;
|
||||
|
||||
|
||||
switch (pCtx->inputType) {
|
||||
case TSDB_DATA_TYPE_INT: {
|
||||
if (pCtx->param[1].nType == INITIAL_VALUE_NOT_ASSIGNED) { // initial value is not set yet
|
||||
|
@ -3684,7 +3853,7 @@ static void diff_function_f(SQLFunctionCtx *pCtx, int32_t index) {
|
|||
default:
|
||||
qError("error input type");
|
||||
}
|
||||
|
||||
|
||||
if (GET_RES_INFO(pCtx)->numOfRes > 0) {
|
||||
pCtx->pOutput += pCtx->outputBytes * step;
|
||||
pCtx->ptsOutputBuf = (char *)pCtx->ptsOutputBuf + TSDB_KEYSIZE * step;
|
||||
|
@ -4606,7 +4775,7 @@ static void rate_function_f(SQLFunctionCtx *pCtx, int32_t index) {
|
|||
|
||||
pRateInfo->lastValue = v;
|
||||
pRateInfo->lastKey = primaryKey[index];
|
||||
|
||||
|
||||
SET_VAL(pCtx, 1, 1);
|
||||
|
||||
// set has result flag
|
||||
|
@ -4630,7 +4799,7 @@ static void rate_func_copy(SQLFunctionCtx *pCtx) {
|
|||
static void rate_finalizer(SQLFunctionCtx *pCtx) {
|
||||
SResultRowCellInfo *pResInfo = GET_RES_INFO(pCtx);
|
||||
SRateInfo *pRateInfo = (SRateInfo *)GET_ROWCELL_INTERBUF(pResInfo);
|
||||
|
||||
|
||||
if (pRateInfo->hasResult != DATA_SET_FLAG) {
|
||||
setNull(pCtx->pOutput, TSDB_DATA_TYPE_DOUBLE, sizeof(double));
|
||||
return;
|
||||
|
@ -5215,7 +5384,7 @@ SAggFunctionInfo aAggs[] = {{
|
|||
"diff",
|
||||
TSDB_FUNC_DIFF,
|
||||
TSDB_FUNC_INVALID_ID,
|
||||
TSDB_FUNCSTATE_MO | TSDB_FUNCSTATE_NEED_TS,
|
||||
TSDB_FUNCSTATE_MO | TSDB_FUNCSTATE_STABLE | TSDB_FUNCSTATE_NEED_TS,
|
||||
diff_function_setup,
|
||||
diff_function,
|
||||
diff_function_f,
|
||||
|
@ -5315,8 +5484,20 @@ SAggFunctionInfo aAggs[] = {{
|
|||
noop1,
|
||||
dataBlockRequired,
|
||||
},
|
||||
{ //32
|
||||
"derivative", // return table id and the corresponding tags for join match and subscribe
|
||||
TSDB_FUNC_DERIVATIVE,
|
||||
TSDB_FUNC_INVALID_ID,
|
||||
TSDB_FUNCSTATE_MO | TSDB_FUNCSTATE_STABLE | TSDB_FUNCSTATE_NEED_TS,
|
||||
deriv_function_setup,
|
||||
deriv_function,
|
||||
noop2,
|
||||
doFinalizer,
|
||||
noop1,
|
||||
dataBlockRequired,
|
||||
},
|
||||
{
|
||||
// 32
|
||||
// 33
|
||||
"_block_dist", // return table id and the corresponding tags for join match and subscribe
|
||||
TSDB_FUNC_BLKINFO,
|
||||
TSDB_FUNC_BLKINFO,
|
||||
|
|
|
@ -1681,6 +1681,8 @@ static int32_t setupQueryRuntimeEnv(SQueryRuntimeEnv *pRuntimeEnv, int32_t numOf
|
|||
SQueryAttr *pQueryAttr = pRuntimeEnv->pQueryAttr;
|
||||
|
||||
pRuntimeEnv->prevGroupId = INT32_MIN;
|
||||
pRuntimeEnv->enableGroupData = false;
|
||||
|
||||
pRuntimeEnv->pQueryAttr = pQueryAttr;
|
||||
|
||||
pRuntimeEnv->pResultRowHashTable = taosHashInit(numOfTables, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_NO_LOCK);
|
||||
|
@ -2652,7 +2654,7 @@ int32_t loadDataBlockOnDemand(SQueryRuntimeEnv* pRuntimeEnv, STableScanInfo* pTa
|
|||
pTableScanInfo->rowCellInfoOffset) != TSDB_CODE_SUCCESS) {
|
||||
longjmp(pRuntimeEnv->env, TSDB_CODE_QRY_OUT_OF_MEMORY);
|
||||
}
|
||||
} else if (pQueryAttr->stableQuery && (!pQueryAttr->tsCompQuery)) { // stable aggregate, not interval aggregate or normal column aggregate
|
||||
} else if (pQueryAttr->stableQuery && (!pQueryAttr->tsCompQuery) && (!pQueryAttr->diffQuery)) { // stable aggregate, not interval aggregate or normal column aggregate
|
||||
doSetTableGroupOutputBuf(pRuntimeEnv, pTableScanInfo->pResultRowInfo, pTableScanInfo->pCtx,
|
||||
pTableScanInfo->rowCellInfoOffset, pTableScanInfo->numOfOutput,
|
||||
pRuntimeEnv->current->groupIndex);
|
||||
|
@ -3119,8 +3121,8 @@ void setDefaultOutputBuf(SQueryRuntimeEnv *pRuntimeEnv, SOptrBasicInfo *pInfo, i
|
|||
assert(pCtx[i].pOutput != NULL);
|
||||
|
||||
// set the timestamp output buffer for top/bottom/diff query
|
||||
int32_t functionId = pCtx[i].functionId;
|
||||
if (functionId == TSDB_FUNC_TOP || functionId == TSDB_FUNC_BOTTOM || functionId == TSDB_FUNC_DIFF) {
|
||||
int32_t fid = pCtx[i].functionId;
|
||||
if (fid == TSDB_FUNC_TOP || fid == TSDB_FUNC_BOTTOM || fid == TSDB_FUNC_DIFF || fid == TSDB_FUNC_DERIVATIVE) {
|
||||
pCtx[i].ptsOutputBuf = pCtx[0].pOutput;
|
||||
}
|
||||
}
|
||||
|
@ -4271,6 +4273,14 @@ static SSDataBlock* doTableScanImpl(void* param, bool* newgroup) {
|
|||
|
||||
pRuntimeEnv->current = *pTableQueryInfo;
|
||||
doTableQueryInfoTimeWindowCheck(pQueryAttr, *pTableQueryInfo);
|
||||
|
||||
if (pRuntimeEnv->enableGroupData) {
|
||||
if(pTableScanInfo->prevGroupId != -1 && pTableScanInfo->prevGroupId != (*pTableQueryInfo)->groupIndex) {
|
||||
*newgroup = true;
|
||||
}
|
||||
}
|
||||
|
||||
pTableScanInfo->prevGroupId = (*pTableQueryInfo)->groupIndex;
|
||||
}
|
||||
|
||||
// this function never returns error?
|
||||
|
@ -4417,6 +4427,7 @@ SOperatorInfo* createTableScanOperator(void* pTsdbQueryHandle, SQueryRuntimeEnv*
|
|||
pInfo->reverseTimes = 0;
|
||||
pInfo->order = pRuntimeEnv->pQueryAttr->order.order;
|
||||
pInfo->current = 0;
|
||||
// pInfo->prevGroupId = -1;
|
||||
|
||||
SOperatorInfo* pOperator = calloc(1, sizeof(SOperatorInfo));
|
||||
pOperator->name = "TableScanOperator";
|
||||
|
@ -4439,6 +4450,8 @@ SOperatorInfo* createTableSeqScanOperator(void* pTsdbQueryHandle, SQueryRuntimeE
|
|||
pInfo->reverseTimes = 0;
|
||||
pInfo->order = pRuntimeEnv->pQueryAttr->order.order;
|
||||
pInfo->current = 0;
|
||||
pInfo->prevGroupId = -1;
|
||||
pRuntimeEnv->enableGroupData = true;
|
||||
|
||||
SOperatorInfo* pOperator = calloc(1, sizeof(SOperatorInfo));
|
||||
pOperator->name = "TableSeqScanOperator";
|
||||
|
@ -4543,6 +4556,7 @@ SOperatorInfo* createDataBlocksOptScanInfo(void* pTsdbQueryHandle, SQueryRuntime
|
|||
pInfo->reverseTimes = reverseTime;
|
||||
pInfo->current = 0;
|
||||
pInfo->order = pRuntimeEnv->pQueryAttr->order.order;
|
||||
// pInfo->prevGroupId = -1;
|
||||
|
||||
SOperatorInfo* pOptr = calloc(1, sizeof(SOperatorInfo));
|
||||
pOptr->name = "DataBlocksOptimizedScanOperator";
|
||||
|
@ -4921,10 +4935,17 @@ static SSDataBlock* doArithmeticOperation(void* param, bool* newgroup) {
|
|||
}
|
||||
|
||||
// Return result of the previous group in the firstly.
|
||||
if (*newgroup && pRes->info.rows > 0) {
|
||||
pArithInfo->existDataBlock = pBlock;
|
||||
clearNumOfRes(pInfo->pCtx, pOperator->numOfOutput);
|
||||
return pInfo->pRes;
|
||||
if (*newgroup) {
|
||||
if (pRes->info.rows > 0) {
|
||||
pArithInfo->existDataBlock = pBlock;
|
||||
clearNumOfRes(pInfo->pCtx, pOperator->numOfOutput);
|
||||
return pInfo->pRes;
|
||||
} else { // init output buffer for a new group data
|
||||
for (int32_t j = 0; j < pOperator->numOfOutput; ++j) {
|
||||
aAggs[pInfo->pCtx[j].functionId].xFinalize(&pInfo->pCtx[j]);
|
||||
}
|
||||
initCtxOutputBuffer(pInfo->pCtx, pOperator->numOfOutput);
|
||||
}
|
||||
}
|
||||
|
||||
STableQueryInfo* pTableQueryInfo = pRuntimeEnv->current;
|
||||
|
@ -6921,6 +6942,10 @@ int32_t doCreateFilterInfo(SColumnInfo* pCols, int32_t numOfCols, int32_t numOfF
|
|||
}
|
||||
|
||||
pSingleColFilter->bytes = pCols[i].bytes;
|
||||
|
||||
if (lower == TSDB_RELATION_IN) {
|
||||
buildFilterSetFromBinary(&pSingleColFilter->q, (char *)(pSingleColFilter->filterInfo.pz), (int32_t)(pSingleColFilter->filterInfo.len));
|
||||
}
|
||||
}
|
||||
|
||||
j++;
|
||||
|
@ -6933,6 +6958,9 @@ int32_t doCreateFilterInfo(SColumnInfo* pCols, int32_t numOfCols, int32_t numOfF
|
|||
void* doDestroyFilterInfo(SSingleColumnFilterInfo* pFilterInfo, int32_t numOfFilterCols) {
|
||||
for (int32_t i = 0; i < numOfFilterCols; ++i) {
|
||||
if (pFilterInfo[i].numOfFilters > 0) {
|
||||
if (pFilterInfo[i].pFilters->filterInfo.lowerRelOptr == TSDB_RELATION_IN) {
|
||||
taosHashCleanup((SHashObj *)(pFilterInfo[i].pFilters->q));
|
||||
}
|
||||
tfree(pFilterInfo[i].pFilters);
|
||||
}
|
||||
}
|
||||
|
@ -7442,7 +7470,6 @@ int32_t doDumpQueryResult(SQInfo *pQInfo, char *data) {
|
|||
doCopyQueryResultToMsg(pQInfo, (int32_t)pRuntimeEnv->outputBuf->info.rows, data);
|
||||
}
|
||||
|
||||
pRuntimeEnv->resultInfo.total += pRuntimeEnv->outputBuf->info.rows;
|
||||
qDebug("QInfo:0x%"PRIx64" current numOfRes rows:%d, total:%" PRId64, pQInfo->qId,
|
||||
pRuntimeEnv->outputBuf->info.rows, pRuntimeEnv->resultInfo.total);
|
||||
|
||||
|
|
|
@ -253,6 +253,27 @@ bool isNullOperator(SColumnFilterElem *pFilter, const char* minval, const char*
|
|||
bool notNullOperator(SColumnFilterElem *pFilter, const char* minval, const char* maxval, int16_t type) {
|
||||
return true;
|
||||
}
|
||||
bool inOperator(SColumnFilterElem *pFilter, const char* minval, const char* maxval, int16_t type) {
|
||||
if (type == TSDB_DATA_TYPE_BOOL || type == TSDB_DATA_TYPE_TINYINT || type == TSDB_DATA_TYPE_SMALLINT || type == TSDB_DATA_TYPE_BIGINT || type == TSDB_DATA_TYPE_INT) {
|
||||
int64_t minv = -1, maxv = -1;
|
||||
GET_TYPED_DATA(minv, int64_t, type, minval);
|
||||
GET_TYPED_DATA(maxv, int64_t, type, maxval);
|
||||
if (minv == maxv) {
|
||||
return NULL != taosHashGet((SHashObj *)pFilter->q, (char *)&minv, sizeof(minv));
|
||||
}
|
||||
return true;
|
||||
} else if (type == TSDB_DATA_TYPE_DOUBLE || type == TSDB_DATA_TYPE_DOUBLE) {
|
||||
double v;
|
||||
GET_TYPED_DATA(v, double, type, minval);
|
||||
return NULL != taosHashGet((SHashObj *)pFilter->q, (char *)&v, sizeof(v));
|
||||
} else if (type == TSDB_DATA_TYPE_BINARY) {
|
||||
return NULL != taosHashGet((SHashObj *)pFilter->q, varDataVal(minval), varDataLen(minval));
|
||||
} else if (type == TSDB_DATA_TYPE_NCHAR){
|
||||
return NULL != taosHashGet((SHashObj *)pFilter->q, varDataVal(minval), varDataLen(minval));
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
bool rangeFilter_ii(SColumnFilterElem *pFilter, const char *minval, const char *maxval, int16_t type) {
|
||||
|
@ -389,6 +410,7 @@ bool (*filterOperators[])(SColumnFilterElem *pFilter, const char* minval, const
|
|||
likeOperator,
|
||||
isNullOperator,
|
||||
notNullOperator,
|
||||
inOperator,
|
||||
};
|
||||
|
||||
bool (*rangeFilterOperators[])(SColumnFilterElem *pFilter, const char* minval, const char* maxval, int16_t type) = {
|
||||
|
@ -397,6 +419,7 @@ bool (*rangeFilterOperators[])(SColumnFilterElem *pFilter, const char* minval, c
|
|||
rangeFilter_ie,
|
||||
rangeFilter_ei,
|
||||
rangeFilter_ii,
|
||||
|
||||
};
|
||||
|
||||
__filter_func_t getFilterOperator(int32_t lowerOptr, int32_t upperOptr) {
|
||||
|
|
|
@ -531,7 +531,7 @@ SArray* createTableScanPlan(SQueryAttr* pQueryAttr) {
|
|||
} else {
|
||||
if (pQueryAttr->queryBlockDist) {
|
||||
op = OP_TableBlockInfoScan;
|
||||
} else if (pQueryAttr->tsCompQuery || pQueryAttr->pointInterpQuery) {
|
||||
} else if (pQueryAttr->tsCompQuery || pQueryAttr->pointInterpQuery || pQueryAttr->diffQuery) {
|
||||
op = OP_TableSeqScan;
|
||||
} else if (pQueryAttr->needReverseScan) {
|
||||
op = OP_DataBlocksOptScan;
|
||||
|
@ -605,7 +605,7 @@ SArray* createExecOperatorPlan(SQueryAttr* pQueryAttr) {
|
|||
taosArrayPush(plan, &op);
|
||||
}
|
||||
} else if (pQueryAttr->simpleAgg) {
|
||||
if (pQueryAttr->stableQuery && !pQueryAttr->tsCompQuery) {
|
||||
if (pQueryAttr->stableQuery && !pQueryAttr->tsCompQuery && !pQueryAttr->diffQuery) {
|
||||
op = OP_MultiTableAggregate;
|
||||
} else {
|
||||
op = OP_Aggregate;
|
||||
|
|
|
@ -241,15 +241,16 @@ bool qTableQuery(qinfo_t qinfo, uint64_t *qId) {
|
|||
|
||||
bool newgroup = false;
|
||||
pRuntimeEnv->outputBuf = pRuntimeEnv->proot->exec(pRuntimeEnv->proot, &newgroup);
|
||||
pRuntimeEnv->resultInfo.total += GET_NUM_OF_RESULTS(pRuntimeEnv);
|
||||
|
||||
if (isQueryKilled(pQInfo)) {
|
||||
qDebug("QInfo:0x%"PRIx64" query is killed", pQInfo->qId);
|
||||
} else if (GET_NUM_OF_RESULTS(pRuntimeEnv) == 0) {
|
||||
qDebug("QInfo:0x%"PRIx64" over, %u tables queried, %"PRId64" rows are returned", pQInfo->qId, pRuntimeEnv->tableqinfoGroupInfo.numOfTables,
|
||||
qDebug("QInfo:0x%"PRIx64" over, %u tables queried, total %"PRId64" rows returned", pQInfo->qId, pRuntimeEnv->tableqinfoGroupInfo.numOfTables,
|
||||
pRuntimeEnv->resultInfo.total);
|
||||
} else {
|
||||
qDebug("QInfo:0x%"PRIx64" query paused, %d rows returned, numOfTotal:%" PRId64 " rows",
|
||||
pQInfo->qId, GET_NUM_OF_RESULTS(pRuntimeEnv), pRuntimeEnv->resultInfo.total + GET_NUM_OF_RESULTS(pRuntimeEnv));
|
||||
qDebug("QInfo:0x%"PRIx64" query paused, %d rows returned, total:%" PRId64 " rows", pQInfo->qId,
|
||||
GET_NUM_OF_RESULTS(pRuntimeEnv), pRuntimeEnv->resultInfo.total);
|
||||
}
|
||||
|
||||
return doBuildResCheck(pQInfo);
|
||||
|
|
|
@ -2397,6 +2397,8 @@ static void destroyHelper(void* param) {
|
|||
tQueryInfo* pInfo = (tQueryInfo*)param;
|
||||
if (pInfo->optr != TSDB_RELATION_IN) {
|
||||
tfree(pInfo->q);
|
||||
} else {
|
||||
taosHashCleanup((SHashObj *)(pInfo->q));
|
||||
}
|
||||
|
||||
free(param);
|
||||
|
@ -3155,11 +3157,23 @@ void filterPrepare(void* expr, void* param) {
|
|||
|
||||
pInfo->sch = *pSchema;
|
||||
pInfo->optr = pExpr->_node.optr;
|
||||
pInfo->compare = getComparFunc(pSchema->type, pInfo->optr);
|
||||
pInfo->compare = getComparFunc(pInfo->sch.type, pInfo->optr);
|
||||
pInfo->indexed = pTSSchema->columns->colId == pInfo->sch.colId;
|
||||
|
||||
if (pInfo->optr == TSDB_RELATION_IN) {
|
||||
pInfo->q = (char*) pCond->arr;
|
||||
int dummy = -1;
|
||||
SHashObj *pObj = NULL;
|
||||
if (pInfo->sch.colId == TSDB_TBNAME_COLUMN_INDEX) {
|
||||
pObj = taosHashInit(256, taosGetDefaultHashFunction(pInfo->sch.type), true, false);
|
||||
SArray *arr = (SArray *)(pCond->arr);
|
||||
for (size_t i = 0; i < taosArrayGetSize(arr); i++) {
|
||||
char* p = taosArrayGetP(arr, i);
|
||||
taosHashPut(pObj, varDataVal(p),varDataLen(p), &dummy, sizeof(dummy));
|
||||
}
|
||||
} else {
|
||||
buildFilterSetFromBinary((void **)&pObj, pCond->pz, pCond->nLen);
|
||||
}
|
||||
pInfo->q = (char *)pObj;
|
||||
} else if (pCond != NULL) {
|
||||
uint32_t size = pCond->nLen * TSDB_NCHAR_SIZE;
|
||||
if (size < (uint32_t)pSchema->bytes) {
|
||||
|
@ -3330,6 +3344,20 @@ static bool tableFilterFp(const void* pNode, void* param) {
|
|||
} else if (pInfo->optr == TSDB_RELATION_NOTNULL) {
|
||||
return (val != NULL) && (!isNull(val, pInfo->sch.type));
|
||||
}
|
||||
} else if (pInfo->optr == TSDB_RELATION_IN) {
|
||||
int type = pInfo->sch.type;
|
||||
if (type == TSDB_DATA_TYPE_BOOL || type == TSDB_DATA_TYPE_TINYINT || type == TSDB_DATA_TYPE_SMALLINT || type == TSDB_DATA_TYPE_BIGINT || type == TSDB_DATA_TYPE_INT) {
|
||||
int64_t v;
|
||||
GET_TYPED_DATA(v, int64_t, pInfo->sch.type, val);
|
||||
return NULL != taosHashGet((SHashObj *)pInfo->q, (char *)&v, sizeof(v));
|
||||
} else if (type == TSDB_DATA_TYPE_DOUBLE || type == TSDB_DATA_TYPE_DOUBLE) {
|
||||
double v;
|
||||
GET_TYPED_DATA(v, double, pInfo->sch.type, val);
|
||||
return NULL != taosHashGet((SHashObj *)pInfo->q, (char *)&v, sizeof(v));
|
||||
} else if (type == TSDB_DATA_TYPE_BINARY || type == TSDB_DATA_TYPE_NCHAR){
|
||||
return NULL != taosHashGet((SHashObj *)pInfo->q, varDataVal(val), varDataLen(val));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
int32_t ret = 0;
|
||||
|
@ -3672,14 +3700,18 @@ static int32_t setQueryCond(tQueryInfo *queryColInfo, SQueryCond* pCond) {
|
|||
|
||||
if (optr == TSDB_RELATION_GREATER || optr == TSDB_RELATION_GREATER_EQUAL ||
|
||||
optr == TSDB_RELATION_EQUAL || optr == TSDB_RELATION_NOT_EQUAL) {
|
||||
pCond->start = calloc(1, sizeof(SEndPoint));
|
||||
pCond->start = calloc(1, sizeof(SEndPoint));
|
||||
pCond->start->optr = queryColInfo->optr;
|
||||
pCond->start->v = queryColInfo->q;
|
||||
pCond->start->v = queryColInfo->q;
|
||||
} else if (optr == TSDB_RELATION_LESS || optr == TSDB_RELATION_LESS_EQUAL) {
|
||||
pCond->end = calloc(1, sizeof(SEndPoint));
|
||||
pCond->end = calloc(1, sizeof(SEndPoint));
|
||||
pCond->end->optr = queryColInfo->optr;
|
||||
pCond->end->v = queryColInfo->q;
|
||||
} else if (optr == TSDB_RELATION_IN || optr == TSDB_RELATION_LIKE) {
|
||||
pCond->end->v = queryColInfo->q;
|
||||
} else if (optr == TSDB_RELATION_IN) {
|
||||
pCond->start = calloc(1, sizeof(SEndPoint));
|
||||
pCond->start->optr = queryColInfo->optr;
|
||||
pCond->start->v = queryColInfo->q;
|
||||
} else if (optr == TSDB_RELATION_LIKE) {
|
||||
assert(0);
|
||||
}
|
||||
|
||||
|
@ -3764,6 +3796,19 @@ static void queryIndexedColumn(SSkipList* pSkipList, tQueryInfo* pQueryInfo, SAr
|
|||
taosArrayPush(result, &info);
|
||||
}
|
||||
|
||||
} else if (optr == TSDB_RELATION_IN) {
|
||||
while(tSkipListIterNext(iter)) {
|
||||
SSkipListNode* pNode = tSkipListIterGet(iter);
|
||||
|
||||
int32_t ret = pQueryInfo->compare(SL_GET_NODE_KEY(pSkipList, pNode), cond.start->v);
|
||||
if (ret != 0) {
|
||||
break;
|
||||
}
|
||||
|
||||
STableKeyInfo info = {.pTable = (void*)SL_GET_NODE_DATA(pNode), .lastKey = TSKEY_INITIAL_VAL};
|
||||
taosArrayPush(result, &info);
|
||||
}
|
||||
|
||||
} else {
|
||||
assert(0);
|
||||
}
|
||||
|
@ -3857,7 +3902,7 @@ void getTableListfromSkipList(tExprNode *pExpr, SSkipList *pSkipList, SArray *re
|
|||
param->setupInfoFn(pExpr, param->pExtInfo);
|
||||
|
||||
tQueryInfo *pQueryInfo = pExpr->_node.info;
|
||||
if (pQueryInfo->indexed && pQueryInfo->optr != TSDB_RELATION_LIKE) {
|
||||
if (pQueryInfo->indexed && (pQueryInfo->optr != TSDB_RELATION_LIKE && pQueryInfo->optr != TSDB_RELATION_IN)) {
|
||||
queryIndexedColumn(pSkipList, pQueryInfo, result);
|
||||
} else {
|
||||
queryIndexlessColumn(pSkipList, pQueryInfo, result, param->nodeFilterFn);
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
#include "ttype.h"
|
||||
#include "tcompare.h"
|
||||
#include "tarray.h"
|
||||
#include "hash.h"
|
||||
|
||||
int32_t compareInt32Val(const void *pLeft, const void *pRight) {
|
||||
int32_t left = GET_INT32_VAL(pLeft), right = GET_INT32_VAL(pRight);
|
||||
|
@ -291,9 +292,12 @@ int32_t taosArrayCompareString(const void* a, const void* b) {
|
|||
return compareLenPrefixedStr(x, y);
|
||||
}
|
||||
|
||||
static int32_t compareFindStrInArray(const void* pLeft, const void* pRight) {
|
||||
const SArray* arr = (const SArray*) pRight;
|
||||
return taosArraySearchString(arr, pLeft, taosArrayCompareString, TD_EQ) == NULL ? 0 : 1;
|
||||
//static int32_t compareFindStrInArray(const void* pLeft, const void* pRight) {
|
||||
// const SArray* arr = (const SArray*) pRight;
|
||||
// return taosArraySearchString(arr, pLeft, taosArrayCompareString, TD_EQ) == NULL ? 0 : 1;
|
||||
//}
|
||||
static int32_t compareFindItemInSet(const void *pLeft, const void* pRight) {
|
||||
return NULL != taosHashGet((SHashObj *)pRight, varDataVal(pLeft), varDataLen(pLeft)) ? 1 : 0;
|
||||
}
|
||||
|
||||
static int32_t compareWStrPatternComp(const void* pLeft, const void* pRight) {
|
||||
|
@ -325,7 +329,7 @@ __compar_fn_t getComparFunc(int32_t type, int32_t optr) {
|
|||
if (optr == TSDB_RELATION_LIKE) { /* wildcard query using like operator */
|
||||
comparFn = compareStrPatternComp;
|
||||
} else if (optr == TSDB_RELATION_IN) {
|
||||
comparFn = compareFindStrInArray;
|
||||
comparFn = compareFindItemInSet;
|
||||
} else { /* normal relational comparFn */
|
||||
comparFn = compareLenPrefixedStr;
|
||||
}
|
||||
|
|
|
@ -342,7 +342,9 @@ void verify_prepare(TAOS* taos) {
|
|||
sql = "insert into m1 values(?,?,?,?,?,?,?,?,?,?)";
|
||||
code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0){
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. code:0x%x\033[0m\n", code);
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
v.ts = 1591060628000;
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
|
@ -365,8 +367,8 @@ void verify_prepare(TAOS* taos) {
|
|||
taos_stmt_add_batch(stmt);
|
||||
}
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("\033[31mfailed to execute insert statement.error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
printf("\033[31mfailed to execute insert statement.\033[0m\n");
|
||||
return;
|
||||
}
|
||||
taos_stmt_close(stmt);
|
||||
|
@ -378,8 +380,8 @@ void verify_prepare(TAOS* taos) {
|
|||
v.v2 = 15;
|
||||
taos_stmt_bind_param(stmt, params + 2);
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("\033[31mfailed to execute select statement.error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
printf("\033[31mfailed to execute select statement.\033[0m\n");
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -530,12 +532,16 @@ void verify_prepare2(TAOS* taos) {
|
|||
sql = "insert into ? (ts, b, v1, v2, v4, v8, f4, f8, bin, blob) values(?,?,?,?,?,?,?,?,?,?)";
|
||||
code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0) {
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. code:0x%x\033[0m\n", code);
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
code = taos_stmt_set_tbname(stmt, "m1");
|
||||
if (code != 0){
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. code:0x%x\033[0m\n", code);
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
int64_t ts = 1591060628000;
|
||||
|
@ -569,7 +575,8 @@ void verify_prepare2(TAOS* taos) {
|
|||
taos_stmt_add_batch(stmt);
|
||||
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("\033[31mfailed to execute insert statement.\033[0m\n");
|
||||
printf("\033[31mfailed to execute insert statement.error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -596,7 +603,8 @@ void verify_prepare2(TAOS* taos) {
|
|||
|
||||
taos_stmt_bind_param(stmt, qparams);
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("\033[31mfailed to execute select statement.\033[0m\n");
|
||||
printf("\033[31mfailed to execute select statement.error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -776,12 +784,16 @@ void verify_prepare3(TAOS* taos) {
|
|||
sql = "insert into ? using st1 tags(?,?) values(?,?,?,?,?,?,?,?,?,?)";
|
||||
code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0){
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. code:0x%x\033[0m\n", code);
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
code = taos_stmt_set_tbname_tags(stmt, "m1", tags);
|
||||
if (code != 0){
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. code:0x%x\033[0m\n", code);
|
||||
printf("\033[31mfailed to execute taos_stmt_prepare. error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
int64_t ts = 1591060628000;
|
||||
|
@ -815,7 +827,8 @@ void verify_prepare3(TAOS* taos) {
|
|||
taos_stmt_add_batch(stmt);
|
||||
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("\033[31mfailed to execute insert statement.\033[0m\n");
|
||||
printf("\033[31mfailed to execute insert statement.error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
taos_stmt_close(stmt);
|
||||
|
@ -842,7 +855,8 @@ void verify_prepare3(TAOS* taos) {
|
|||
|
||||
taos_stmt_bind_param(stmt, qparams);
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("\033[31mfailed to execute select statement.\033[0m\n");
|
||||
printf("\033[31mfailed to execute select statement.error:%s\033[0m\n", taos_stmt_errstr(stmt));
|
||||
taos_stmt_close(stmt);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,163 @@
|
|||
###################################################################
|
||||
# Copyright (c) 2016 by TAOS Technologies, Inc.
|
||||
# All rights reserved.
|
||||
#
|
||||
# This file is proprietary and confidential to TAOS Technologies.
|
||||
# No part of this file may be reproduced, stored, transmitted,
|
||||
# disclosed or used in any form or by any means other than as
|
||||
# expressly provided by the written permission from Jianhui Tao
|
||||
#
|
||||
###################################################################
|
||||
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
import sys
|
||||
import taos
|
||||
from util.log import tdLog
|
||||
from util.cases import tdCases
|
||||
from util.sql import tdSql
|
||||
from util.dnodes import tdDnodes
|
||||
|
||||
class TDTestCase:
|
||||
def init(self, conn, logSql):
|
||||
tdLog.debug("start to execute %s" % __file__)
|
||||
tdSql.init(conn.cursor(), logSql)
|
||||
|
||||
self.ts = 1538548685000
|
||||
|
||||
def run(self):
|
||||
tdSql.prepare()
|
||||
|
||||
print("==============step1")
|
||||
tdSql.execute(
|
||||
"create table if not exists st (ts timestamp, tagtype int) tags(dev nchar(50))")
|
||||
tdSql.execute(
|
||||
'CREATE TABLE if not exists dev_001 using st tags("dev_01")')
|
||||
tdSql.execute(
|
||||
'CREATE TABLE if not exists dev_002 using st tags("dev_02")')
|
||||
|
||||
print("==============step2")
|
||||
tdSql.error("select * from db.st where ts in ('2020-05-13 10:00:00.000')")
|
||||
|
||||
tdSql.execute(
|
||||
"""INSERT INTO dev_001(ts, tagtype) VALUES('2020-05-13 10:00:00.000', 1),
|
||||
('2020-05-13 10:00:00.001', 1)
|
||||
dev_002 VALUES('2020-05-13 10:00:00.001', 1)""")
|
||||
|
||||
# TAG nchar
|
||||
tdSql.query('select count(ts) from db.st where dev in ("dev_01")')
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 2)
|
||||
|
||||
tdSql.query('select count(ts) from db.st where dev in ("dev_01", "dev_01")')
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 2)
|
||||
|
||||
tdSql.query('select count(ts) from db.st where dev in ("dev_01", "dev_01", "dev_02")')
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 3)
|
||||
|
||||
|
||||
# colume int
|
||||
tdSql.query("select count(ts) from db.st where tagtype in (1)")
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 3)
|
||||
|
||||
tdSql.query("select count(ts) from db.st where tagtype in (1, 2)")
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 3)
|
||||
tdSql.execute(
|
||||
"""INSERT INTO dev_001(ts, tagtype) VALUES('2020-05-13 10:00:01.000', 2),
|
||||
('2020-05-13 10:00:02.001', 2)
|
||||
dev_002 VALUES('2020-05-13 10:00:03.001', 2)""")
|
||||
|
||||
tdSql.query("select count(ts) from db.st where tagtype in (1, 2)")
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 6)
|
||||
|
||||
tdSql.execute("create table tb(ts timestamp, c1 int, c2 binary(10), c3 nchar(10), c4 float, c5 bool)")
|
||||
for i in range(10):
|
||||
tdSql.execute("insert into tb values(%d, %d, 'binary%d', 'nchar%d', %f, %d)" % (self.ts + i, i, i, i, i + 0.1, i % 2))
|
||||
|
||||
#binary
|
||||
tdSql.query('select count(ts) from db.tb where c2 in ("binary1")')
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 1)
|
||||
|
||||
tdSql.query('select count(ts) from db.tb where c2 in ("binary1", "binary2", "binary1")')
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 2)
|
||||
|
||||
#bool
|
||||
#tdSql.query('select count(ts) from db.tb where c5 in (true)')
|
||||
#tdSql.checkRows(1)
|
||||
#tdSql.checkData(0, 0, 5)
|
||||
|
||||
#float
|
||||
#tdSql.query('select count(ts) from db.tb where c4 in (0.1)')
|
||||
#tdSql.checkRows(1)
|
||||
#tdSql.checkData(0, 0, 1)
|
||||
|
||||
#nchar
|
||||
tdSql.query('select count(ts) from db.tb where c3 in ("nchar0")')
|
||||
tdSql.checkRows(1)
|
||||
tdSql.checkData(0, 0, 1)
|
||||
|
||||
|
||||
#tdSql.query("select tbname, dev from dev_001")
|
||||
#tdSql.checkRows(1)
|
||||
#tdSql.checkData(0, 0, 'dev_001')
|
||||
#tdSql.checkData(0, 1, 'dev_01')
|
||||
|
||||
#tdSql.query("select tbname, dev, tagtype from dev_001")
|
||||
#tdSql.checkRows(2)
|
||||
|
||||
### test case for https://jira.taosdata.com:18080/browse/TD-1930
|
||||
#tdSql.execute("create table tb(ts timestamp, c1 int, c2 binary(10), c3 nchar(10), c4 float, c5 bool)")
|
||||
#for i in range(10):
|
||||
# tdSql.execute("insert into tb values(%d, %d, 'binary%d', 'nchar%d', %f, %d)" % (self.ts + i, i, i, i, i + 0.1, i % 2))
|
||||
#
|
||||
#tdSql.error("select * from tb where c2 = binary2")
|
||||
#tdSql.error("select * from tb where c3 = nchar2")
|
||||
|
||||
#tdSql.query("select * from tb where c2 = 'binary2' ")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
#tdSql.query("select * from tb where c3 = 'nchar2' ")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
#tdSql.query("select * from tb where c1 = '2' ")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
#tdSql.query("select * from tb where c1 = 2 ")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
#tdSql.query("select * from tb where c4 = '0.1' ")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
#tdSql.query("select * from tb where c4 = 0.1 ")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
#tdSql.query("select * from tb where c5 = true ")
|
||||
#tdSql.checkRows(5)
|
||||
|
||||
#tdSql.query("select * from tb where c5 = 'true' ")
|
||||
#tdSql.checkRows(5)
|
||||
|
||||
## For jira: https://jira.taosdata.com:18080/browse/TD-2850
|
||||
#tdSql.execute("create database 'Test' ")
|
||||
#tdSql.execute("use 'Test' ")
|
||||
#tdSql.execute("create table 'TB'(ts timestamp, 'Col1' int) tags('Tag1' int)")
|
||||
#tdSql.execute("insert into 'Tb0' using tb tags(1) values(now, 1)")
|
||||
#tdSql.query("select * from tb")
|
||||
#tdSql.checkRows(1)
|
||||
|
||||
|
||||
|
||||
def stop(self):
|
||||
tdSql.close()
|
||||
tdLog.success("%s successfully executed" % __file__)
|
||||
|
||||
|
||||
tdCases.addWindows(__file__, TDTestCase())
|
||||
tdCases.addLinux(__file__, TDTestCase())
|
|
@ -1458,6 +1458,160 @@ int stmt_funcb_autoctb3(TAOS_STMT *stmt) {
|
|||
|
||||
|
||||
|
||||
|
||||
//1 tables 10 records
|
||||
int stmt_funcb_autoctb4(TAOS_STMT *stmt) {
|
||||
struct {
|
||||
int64_t *ts;
|
||||
int8_t b[10];
|
||||
int8_t v1[10];
|
||||
int16_t v2[10];
|
||||
int32_t v4[10];
|
||||
int64_t v8[10];
|
||||
float f4[10];
|
||||
double f8[10];
|
||||
char bin[10][40];
|
||||
} v = {0};
|
||||
|
||||
v.ts = malloc(sizeof(int64_t) * 1 * 10);
|
||||
|
||||
int *lb = malloc(10 * sizeof(int));
|
||||
|
||||
TAOS_BIND *tags = calloc(1, sizeof(TAOS_BIND) * 9 * 1);
|
||||
TAOS_MULTI_BIND *params = calloc(1, sizeof(TAOS_MULTI_BIND) * 1*5);
|
||||
|
||||
// int one_null = 1;
|
||||
int one_not_null = 0;
|
||||
|
||||
char* is_null = malloc(sizeof(char) * 10);
|
||||
char* no_null = malloc(sizeof(char) * 10);
|
||||
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
lb[i] = 40;
|
||||
no_null[i] = 0;
|
||||
is_null[i] = (i % 10 == 2) ? 1 : 0;
|
||||
v.b[i] = (int8_t)(i % 2);
|
||||
v.v1[i] = (int8_t)((i+1) % 2);
|
||||
v.v2[i] = (int16_t)i;
|
||||
v.v4[i] = (int32_t)(i+1);
|
||||
v.v8[i] = (int64_t)(i+2);
|
||||
v.f4[i] = (float)(i+3);
|
||||
v.f8[i] = (double)(i+4);
|
||||
memset(v.bin[i], '0'+i%10, 40);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 5; i+=5) {
|
||||
params[i+0].buffer_type = TSDB_DATA_TYPE_TIMESTAMP;
|
||||
params[i+0].buffer_length = sizeof(int64_t);
|
||||
params[i+0].buffer = &v.ts[10*i/10];
|
||||
params[i+0].length = NULL;
|
||||
params[i+0].is_null = no_null;
|
||||
params[i+0].num = 10;
|
||||
|
||||
params[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
params[i+1].buffer_length = sizeof(int8_t);
|
||||
params[i+1].buffer = v.b;
|
||||
params[i+1].length = NULL;
|
||||
params[i+1].is_null = is_null;
|
||||
params[i+1].num = 10;
|
||||
|
||||
params[i+2].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
params[i+2].buffer_length = sizeof(int32_t);
|
||||
params[i+2].buffer = v.v4;
|
||||
params[i+2].length = NULL;
|
||||
params[i+2].is_null = is_null;
|
||||
params[i+2].num = 10;
|
||||
|
||||
params[i+3].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
params[i+3].buffer_length = sizeof(int64_t);
|
||||
params[i+3].buffer = v.v8;
|
||||
params[i+3].length = NULL;
|
||||
params[i+3].is_null = is_null;
|
||||
params[i+3].num = 10;
|
||||
|
||||
params[i+4].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
params[i+4].buffer_length = sizeof(double);
|
||||
params[i+4].buffer = v.f8;
|
||||
params[i+4].length = NULL;
|
||||
params[i+4].is_null = is_null;
|
||||
params[i+4].num = 10;
|
||||
}
|
||||
|
||||
int64_t tts = 1591060628000;
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
v.ts[i] = tts + i;
|
||||
}
|
||||
|
||||
|
||||
for (int i = 0; i < 1; ++i) {
|
||||
tags[i+0].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
tags[i+0].buffer = v.b;
|
||||
tags[i+0].is_null = &one_not_null;
|
||||
tags[i+0].length = NULL;
|
||||
|
||||
tags[i+1].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
tags[i+1].buffer = v.v2;
|
||||
tags[i+1].is_null = &one_not_null;
|
||||
tags[i+1].length = NULL;
|
||||
|
||||
tags[i+2].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
tags[i+2].buffer = v.f4;
|
||||
tags[i+2].is_null = &one_not_null;
|
||||
tags[i+2].length = NULL;
|
||||
|
||||
tags[i+3].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
tags[i+3].buffer = v.bin;
|
||||
tags[i+3].is_null = &one_not_null;
|
||||
tags[i+3].length = (uintptr_t *)lb;
|
||||
}
|
||||
|
||||
|
||||
unsigned long long starttime = getCurrentTime();
|
||||
|
||||
char *sql = "insert into ? using stb1 tags(1,?,2,?,4,?,6.0,?,'b') (ts,b,v4,v8,f8) values(?,?,?,?,?)";
|
||||
int code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_prepare. code:0x%x\n", code);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
int id = 0;
|
||||
for (int zz = 0; zz < 1; zz++) {
|
||||
char buf[32];
|
||||
sprintf(buf, "m%d", zz);
|
||||
code = taos_stmt_set_tbname_tags(stmt, buf, tags);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_set_tbname_tags. code:0x%x\n", code);
|
||||
}
|
||||
|
||||
taos_stmt_bind_param_batch(stmt, params + id * 5);
|
||||
taos_stmt_add_batch(stmt);
|
||||
}
|
||||
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("failed to execute insert statement.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
++id;
|
||||
|
||||
unsigned long long endtime = getCurrentTime();
|
||||
printf("insert total %d records, used %u seconds, avg:%u useconds\n", 10, (endtime-starttime)/1000000UL, (endtime-starttime)/(10));
|
||||
|
||||
free(v.ts);
|
||||
free(lb);
|
||||
free(params);
|
||||
free(is_null);
|
||||
free(no_null);
|
||||
free(tags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
//1 tables 10 records
|
||||
int stmt_funcb_autoctb_e1(TAOS_STMT *stmt) {
|
||||
struct {
|
||||
|
@ -1606,7 +1760,7 @@ int stmt_funcb_autoctb_e1(TAOS_STMT *stmt) {
|
|||
char *sql = "insert into ? using stb1 (id1,id2,id3,id4,id5,id6,id7,id8,id9) tags(1,?,2,?,4,?,6.0,?,'b') values(?,?,?,?,?,?,?,?,?,?)";
|
||||
int code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_prepare. code:0x%x\n", code);
|
||||
printf("failed to execute taos_stmt_prepare. error:%s\n", taos_stmt_errstr(stmt));
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
@ -1824,6 +1978,224 @@ int stmt_funcb_autoctb_e2(TAOS_STMT *stmt) {
|
|||
exit(1);
|
||||
}
|
||||
|
||||
int id = 0;
|
||||
for (int zz = 0; zz < 1; zz++) {
|
||||
char buf[32];
|
||||
sprintf(buf, "m%d", zz);
|
||||
code = taos_stmt_set_tbname_tags(stmt, buf, NULL);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_set_tbname_tags. code:%s\n", taos_stmt_errstr(stmt));
|
||||
return -1;
|
||||
}
|
||||
|
||||
taos_stmt_bind_param_batch(stmt, params + id * 10);
|
||||
taos_stmt_add_batch(stmt);
|
||||
}
|
||||
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("failed to execute insert statement.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
++id;
|
||||
|
||||
unsigned long long endtime = getCurrentTime();
|
||||
printf("insert total %d records, used %u seconds, avg:%u useconds\n", 10, (endtime-starttime)/1000000UL, (endtime-starttime)/(10));
|
||||
|
||||
free(v.ts);
|
||||
free(lb);
|
||||
free(params);
|
||||
free(is_null);
|
||||
free(no_null);
|
||||
free(tags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
//1 tables 10 records
|
||||
int stmt_funcb_autoctb_e3(TAOS_STMT *stmt) {
|
||||
struct {
|
||||
int64_t *ts;
|
||||
int8_t b[10];
|
||||
int8_t v1[10];
|
||||
int16_t v2[10];
|
||||
int32_t v4[10];
|
||||
int64_t v8[10];
|
||||
float f4[10];
|
||||
double f8[10];
|
||||
char bin[10][40];
|
||||
} v = {0};
|
||||
|
||||
v.ts = malloc(sizeof(int64_t) * 1 * 10);
|
||||
|
||||
int *lb = malloc(10 * sizeof(int));
|
||||
|
||||
TAOS_BIND *tags = calloc(1, sizeof(TAOS_BIND) * 9 * 1);
|
||||
TAOS_MULTI_BIND *params = calloc(1, sizeof(TAOS_MULTI_BIND) * 1*10);
|
||||
|
||||
// int one_null = 1;
|
||||
int one_not_null = 0;
|
||||
|
||||
char* is_null = malloc(sizeof(char) * 10);
|
||||
char* no_null = malloc(sizeof(char) * 10);
|
||||
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
lb[i] = 40;
|
||||
no_null[i] = 0;
|
||||
is_null[i] = (i % 10 == 2) ? 1 : 0;
|
||||
v.b[i] = (int8_t)(i % 2);
|
||||
v.v1[i] = (int8_t)((i+1) % 2);
|
||||
v.v2[i] = (int16_t)i;
|
||||
v.v4[i] = (int32_t)(i+1);
|
||||
v.v8[i] = (int64_t)(i+2);
|
||||
v.f4[i] = (float)(i+3);
|
||||
v.f8[i] = (double)(i+4);
|
||||
memset(v.bin[i], '0'+i%10, 40);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 10; i+=10) {
|
||||
params[i+0].buffer_type = TSDB_DATA_TYPE_TIMESTAMP;
|
||||
params[i+0].buffer_length = sizeof(int64_t);
|
||||
params[i+0].buffer = &v.ts[10*i/10];
|
||||
params[i+0].length = NULL;
|
||||
params[i+0].is_null = no_null;
|
||||
params[i+0].num = 10;
|
||||
|
||||
params[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
params[i+1].buffer_length = sizeof(int8_t);
|
||||
params[i+1].buffer = v.b;
|
||||
params[i+1].length = NULL;
|
||||
params[i+1].is_null = is_null;
|
||||
params[i+1].num = 10;
|
||||
|
||||
params[i+2].buffer_type = TSDB_DATA_TYPE_TINYINT;
|
||||
params[i+2].buffer_length = sizeof(int8_t);
|
||||
params[i+2].buffer = v.v1;
|
||||
params[i+2].length = NULL;
|
||||
params[i+2].is_null = is_null;
|
||||
params[i+2].num = 10;
|
||||
|
||||
params[i+3].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
params[i+3].buffer_length = sizeof(int16_t);
|
||||
params[i+3].buffer = v.v2;
|
||||
params[i+3].length = NULL;
|
||||
params[i+3].is_null = is_null;
|
||||
params[i+3].num = 10;
|
||||
|
||||
params[i+4].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
params[i+4].buffer_length = sizeof(int32_t);
|
||||
params[i+4].buffer = v.v4;
|
||||
params[i+4].length = NULL;
|
||||
params[i+4].is_null = is_null;
|
||||
params[i+4].num = 10;
|
||||
|
||||
params[i+5].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
params[i+5].buffer_length = sizeof(int64_t);
|
||||
params[i+5].buffer = v.v8;
|
||||
params[i+5].length = NULL;
|
||||
params[i+5].is_null = is_null;
|
||||
params[i+5].num = 10;
|
||||
|
||||
params[i+6].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
params[i+6].buffer_length = sizeof(float);
|
||||
params[i+6].buffer = v.f4;
|
||||
params[i+6].length = NULL;
|
||||
params[i+6].is_null = is_null;
|
||||
params[i+6].num = 10;
|
||||
|
||||
params[i+7].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
params[i+7].buffer_length = sizeof(double);
|
||||
params[i+7].buffer = v.f8;
|
||||
params[i+7].length = NULL;
|
||||
params[i+7].is_null = is_null;
|
||||
params[i+7].num = 10;
|
||||
|
||||
params[i+8].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
params[i+8].buffer_length = 40;
|
||||
params[i+8].buffer = v.bin;
|
||||
params[i+8].length = lb;
|
||||
params[i+8].is_null = is_null;
|
||||
params[i+8].num = 10;
|
||||
|
||||
params[i+9].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
params[i+9].buffer_length = 40;
|
||||
params[i+9].buffer = v.bin;
|
||||
params[i+9].length = lb;
|
||||
params[i+9].is_null = is_null;
|
||||
params[i+9].num = 10;
|
||||
|
||||
}
|
||||
|
||||
int64_t tts = 1591060628000;
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
v.ts[i] = tts + i;
|
||||
}
|
||||
|
||||
|
||||
for (int i = 0; i < 1; ++i) {
|
||||
tags[i+0].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
tags[i+0].buffer = v.v4;
|
||||
tags[i+0].is_null = &one_not_null;
|
||||
tags[i+0].length = NULL;
|
||||
|
||||
tags[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
tags[i+1].buffer = v.b;
|
||||
tags[i+1].is_null = &one_not_null;
|
||||
tags[i+1].length = NULL;
|
||||
|
||||
tags[i+2].buffer_type = TSDB_DATA_TYPE_TINYINT;
|
||||
tags[i+2].buffer = v.v1;
|
||||
tags[i+2].is_null = &one_not_null;
|
||||
tags[i+2].length = NULL;
|
||||
|
||||
tags[i+3].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
tags[i+3].buffer = v.v2;
|
||||
tags[i+3].is_null = &one_not_null;
|
||||
tags[i+3].length = NULL;
|
||||
|
||||
tags[i+4].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
tags[i+4].buffer = v.v8;
|
||||
tags[i+4].is_null = &one_not_null;
|
||||
tags[i+4].length = NULL;
|
||||
|
||||
tags[i+5].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
tags[i+5].buffer = v.f4;
|
||||
tags[i+5].is_null = &one_not_null;
|
||||
tags[i+5].length = NULL;
|
||||
|
||||
tags[i+6].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
tags[i+6].buffer = v.f8;
|
||||
tags[i+6].is_null = &one_not_null;
|
||||
tags[i+6].length = NULL;
|
||||
|
||||
tags[i+7].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
tags[i+7].buffer = v.bin;
|
||||
tags[i+7].is_null = &one_not_null;
|
||||
tags[i+7].length = (uintptr_t *)lb;
|
||||
|
||||
tags[i+8].buffer_type = TSDB_DATA_TYPE_NCHAR;
|
||||
tags[i+8].buffer = v.bin;
|
||||
tags[i+8].is_null = &one_not_null;
|
||||
tags[i+8].length = (uintptr_t *)lb;
|
||||
}
|
||||
|
||||
|
||||
unsigned long long starttime = getCurrentTime();
|
||||
|
||||
char *sql = "insert into ? using stb1 (id1,id2,id3,id4,id5,id6,id7,id8,id9) tags(?,?,?,?,?,?,?,?,?) values(?,?,?,?,?,?,?,?,?,?)";
|
||||
int code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_prepare. code:%s\n", taos_stmt_errstr(stmt));
|
||||
return -1;
|
||||
//exit(1);
|
||||
}
|
||||
|
||||
int id = 0;
|
||||
for (int zz = 0; zz < 1; zz++) {
|
||||
char buf[32];
|
||||
|
@ -1860,6 +2232,458 @@ int stmt_funcb_autoctb_e2(TAOS_STMT *stmt) {
|
|||
|
||||
|
||||
|
||||
|
||||
//1 tables 10 records
|
||||
int stmt_funcb_autoctb_e4(TAOS_STMT *stmt) {
|
||||
struct {
|
||||
int64_t *ts;
|
||||
int8_t b[10];
|
||||
int8_t v1[10];
|
||||
int16_t v2[10];
|
||||
int32_t v4[10];
|
||||
int64_t v8[10];
|
||||
float f4[10];
|
||||
double f8[10];
|
||||
char bin[10][40];
|
||||
} v = {0};
|
||||
|
||||
v.ts = malloc(sizeof(int64_t) * 1 * 10);
|
||||
|
||||
int *lb = malloc(10 * sizeof(int));
|
||||
|
||||
TAOS_BIND *tags = calloc(1, sizeof(TAOS_BIND) * 9 * 1);
|
||||
TAOS_MULTI_BIND *params = calloc(1, sizeof(TAOS_MULTI_BIND) * 1*10);
|
||||
|
||||
// int one_null = 1;
|
||||
int one_not_null = 0;
|
||||
|
||||
char* is_null = malloc(sizeof(char) * 10);
|
||||
char* no_null = malloc(sizeof(char) * 10);
|
||||
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
lb[i] = 40;
|
||||
no_null[i] = 0;
|
||||
is_null[i] = (i % 10 == 2) ? 1 : 0;
|
||||
v.b[i] = (int8_t)(i % 2);
|
||||
v.v1[i] = (int8_t)((i+1) % 2);
|
||||
v.v2[i] = (int16_t)i;
|
||||
v.v4[i] = (int32_t)(i+1);
|
||||
v.v8[i] = (int64_t)(i+2);
|
||||
v.f4[i] = (float)(i+3);
|
||||
v.f8[i] = (double)(i+4);
|
||||
memset(v.bin[i], '0'+i%10, 40);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 10; i+=10) {
|
||||
params[i+0].buffer_type = TSDB_DATA_TYPE_TIMESTAMP;
|
||||
params[i+0].buffer_length = sizeof(int64_t);
|
||||
params[i+0].buffer = &v.ts[10*i/10];
|
||||
params[i+0].length = NULL;
|
||||
params[i+0].is_null = no_null;
|
||||
params[i+0].num = 10;
|
||||
|
||||
params[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
params[i+1].buffer_length = sizeof(int8_t);
|
||||
params[i+1].buffer = v.b;
|
||||
params[i+1].length = NULL;
|
||||
params[i+1].is_null = is_null;
|
||||
params[i+1].num = 10;
|
||||
|
||||
params[i+2].buffer_type = TSDB_DATA_TYPE_TINYINT;
|
||||
params[i+2].buffer_length = sizeof(int8_t);
|
||||
params[i+2].buffer = v.v1;
|
||||
params[i+2].length = NULL;
|
||||
params[i+2].is_null = is_null;
|
||||
params[i+2].num = 10;
|
||||
|
||||
params[i+3].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
params[i+3].buffer_length = sizeof(int16_t);
|
||||
params[i+3].buffer = v.v2;
|
||||
params[i+3].length = NULL;
|
||||
params[i+3].is_null = is_null;
|
||||
params[i+3].num = 10;
|
||||
|
||||
params[i+4].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
params[i+4].buffer_length = sizeof(int32_t);
|
||||
params[i+4].buffer = v.v4;
|
||||
params[i+4].length = NULL;
|
||||
params[i+4].is_null = is_null;
|
||||
params[i+4].num = 10;
|
||||
|
||||
params[i+5].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
params[i+5].buffer_length = sizeof(int64_t);
|
||||
params[i+5].buffer = v.v8;
|
||||
params[i+5].length = NULL;
|
||||
params[i+5].is_null = is_null;
|
||||
params[i+5].num = 10;
|
||||
|
||||
params[i+6].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
params[i+6].buffer_length = sizeof(float);
|
||||
params[i+6].buffer = v.f4;
|
||||
params[i+6].length = NULL;
|
||||
params[i+6].is_null = is_null;
|
||||
params[i+6].num = 10;
|
||||
|
||||
params[i+7].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
params[i+7].buffer_length = sizeof(double);
|
||||
params[i+7].buffer = v.f8;
|
||||
params[i+7].length = NULL;
|
||||
params[i+7].is_null = is_null;
|
||||
params[i+7].num = 10;
|
||||
|
||||
params[i+8].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
params[i+8].buffer_length = 40;
|
||||
params[i+8].buffer = v.bin;
|
||||
params[i+8].length = lb;
|
||||
params[i+8].is_null = is_null;
|
||||
params[i+8].num = 10;
|
||||
|
||||
params[i+9].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
params[i+9].buffer_length = 40;
|
||||
params[i+9].buffer = v.bin;
|
||||
params[i+9].length = lb;
|
||||
params[i+9].is_null = is_null;
|
||||
params[i+9].num = 10;
|
||||
|
||||
}
|
||||
|
||||
int64_t tts = 1591060628000;
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
v.ts[i] = tts + i;
|
||||
}
|
||||
|
||||
|
||||
for (int i = 0; i < 1; ++i) {
|
||||
tags[i+0].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
tags[i+0].buffer = v.v4;
|
||||
tags[i+0].is_null = &one_not_null;
|
||||
tags[i+0].length = NULL;
|
||||
|
||||
tags[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
tags[i+1].buffer = v.b;
|
||||
tags[i+1].is_null = &one_not_null;
|
||||
tags[i+1].length = NULL;
|
||||
|
||||
tags[i+2].buffer_type = TSDB_DATA_TYPE_TINYINT;
|
||||
tags[i+2].buffer = v.v1;
|
||||
tags[i+2].is_null = &one_not_null;
|
||||
tags[i+2].length = NULL;
|
||||
|
||||
tags[i+3].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
tags[i+3].buffer = v.v2;
|
||||
tags[i+3].is_null = &one_not_null;
|
||||
tags[i+3].length = NULL;
|
||||
|
||||
tags[i+4].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
tags[i+4].buffer = v.v8;
|
||||
tags[i+4].is_null = &one_not_null;
|
||||
tags[i+4].length = NULL;
|
||||
|
||||
tags[i+5].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
tags[i+5].buffer = v.f4;
|
||||
tags[i+5].is_null = &one_not_null;
|
||||
tags[i+5].length = NULL;
|
||||
|
||||
tags[i+6].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
tags[i+6].buffer = v.f8;
|
||||
tags[i+6].is_null = &one_not_null;
|
||||
tags[i+6].length = NULL;
|
||||
|
||||
tags[i+7].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
tags[i+7].buffer = v.bin;
|
||||
tags[i+7].is_null = &one_not_null;
|
||||
tags[i+7].length = (uintptr_t *)lb;
|
||||
|
||||
tags[i+8].buffer_type = TSDB_DATA_TYPE_NCHAR;
|
||||
tags[i+8].buffer = v.bin;
|
||||
tags[i+8].is_null = &one_not_null;
|
||||
tags[i+8].length = (uintptr_t *)lb;
|
||||
}
|
||||
|
||||
|
||||
unsigned long long starttime = getCurrentTime();
|
||||
|
||||
char *sql = "insert into ? using stb1 tags(?,?,?,?,?,?,?,?,?) values(?,?,?,?,?,?,?,?,?,?)";
|
||||
int code = taos_stmt_prepare(stmt, sql, 0);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_prepare. code:%s\n", taos_stmt_errstr(stmt));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
int id = 0;
|
||||
for (int zz = 0; zz < 1; zz++) {
|
||||
char buf[32];
|
||||
sprintf(buf, "m%d", zz);
|
||||
code = taos_stmt_set_tbname_tags(stmt, buf, tags);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_set_tbname_tags. error:%s\n", taos_stmt_errstr(stmt));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
code = taos_stmt_bind_param_batch(stmt, params + id * 10);
|
||||
if (code != 0) {
|
||||
printf("failed to execute taos_stmt_bind_param_batch. error:%s\n", taos_stmt_errstr(stmt));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
code = taos_stmt_bind_param_batch(stmt, params + id * 10);
|
||||
if (code != 0) {
|
||||
printf("failed to execute taos_stmt_bind_param_batch. error:%s\n", taos_stmt_errstr(stmt));
|
||||
return -1;
|
||||
}
|
||||
|
||||
taos_stmt_add_batch(stmt);
|
||||
}
|
||||
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("failed to execute insert statement.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
++id;
|
||||
|
||||
unsigned long long endtime = getCurrentTime();
|
||||
printf("insert total %d records, used %u seconds, avg:%u useconds\n", 10, (endtime-starttime)/1000000UL, (endtime-starttime)/(10));
|
||||
|
||||
free(v.ts);
|
||||
free(lb);
|
||||
free(params);
|
||||
free(is_null);
|
||||
free(no_null);
|
||||
free(tags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
//1 tables 10 records
|
||||
int stmt_funcb_autoctb_e5(TAOS_STMT *stmt) {
|
||||
struct {
|
||||
int64_t *ts;
|
||||
int8_t b[10];
|
||||
int8_t v1[10];
|
||||
int16_t v2[10];
|
||||
int32_t v4[10];
|
||||
int64_t v8[10];
|
||||
float f4[10];
|
||||
double f8[10];
|
||||
char bin[10][40];
|
||||
} v = {0};
|
||||
|
||||
v.ts = malloc(sizeof(int64_t) * 1 * 10);
|
||||
|
||||
int *lb = malloc(10 * sizeof(int));
|
||||
|
||||
TAOS_BIND *tags = calloc(1, sizeof(TAOS_BIND) * 9 * 1);
|
||||
TAOS_MULTI_BIND *params = calloc(1, sizeof(TAOS_MULTI_BIND) * 1*10);
|
||||
|
||||
// int one_null = 1;
|
||||
int one_not_null = 0;
|
||||
|
||||
char* is_null = malloc(sizeof(char) * 10);
|
||||
char* no_null = malloc(sizeof(char) * 10);
|
||||
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
lb[i] = 40;
|
||||
no_null[i] = 0;
|
||||
is_null[i] = (i % 10 == 2) ? 1 : 0;
|
||||
v.b[i] = (int8_t)(i % 2);
|
||||
v.v1[i] = (int8_t)((i+1) % 2);
|
||||
v.v2[i] = (int16_t)i;
|
||||
v.v4[i] = (int32_t)(i+1);
|
||||
v.v8[i] = (int64_t)(i+2);
|
||||
v.f4[i] = (float)(i+3);
|
||||
v.f8[i] = (double)(i+4);
|
||||
memset(v.bin[i], '0'+i%10, 40);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 10; i+=10) {
|
||||
params[i+0].buffer_type = TSDB_DATA_TYPE_TIMESTAMP;
|
||||
params[i+0].buffer_length = sizeof(int64_t);
|
||||
params[i+0].buffer = &v.ts[10*i/10];
|
||||
params[i+0].length = NULL;
|
||||
params[i+0].is_null = no_null;
|
||||
params[i+0].num = 10;
|
||||
|
||||
params[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
params[i+1].buffer_length = sizeof(int8_t);
|
||||
params[i+1].buffer = v.b;
|
||||
params[i+1].length = NULL;
|
||||
params[i+1].is_null = is_null;
|
||||
params[i+1].num = 10;
|
||||
|
||||
params[i+2].buffer_type = TSDB_DATA_TYPE_TINYINT;
|
||||
params[i+2].buffer_length = sizeof(int8_t);
|
||||
params[i+2].buffer = v.v1;
|
||||
params[i+2].length = NULL;
|
||||
params[i+2].is_null = is_null;
|
||||
params[i+2].num = 10;
|
||||
|
||||
params[i+3].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
params[i+3].buffer_length = sizeof(int16_t);
|
||||
params[i+3].buffer = v.v2;
|
||||
params[i+3].length = NULL;
|
||||
params[i+3].is_null = is_null;
|
||||
params[i+3].num = 10;
|
||||
|
||||
params[i+4].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
params[i+4].buffer_length = sizeof(int32_t);
|
||||
params[i+4].buffer = v.v4;
|
||||
params[i+4].length = NULL;
|
||||
params[i+4].is_null = is_null;
|
||||
params[i+4].num = 10;
|
||||
|
||||
params[i+5].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
params[i+5].buffer_length = sizeof(int64_t);
|
||||
params[i+5].buffer = v.v8;
|
||||
params[i+5].length = NULL;
|
||||
params[i+5].is_null = is_null;
|
||||
params[i+5].num = 10;
|
||||
|
||||
params[i+6].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
params[i+6].buffer_length = sizeof(float);
|
||||
params[i+6].buffer = v.f4;
|
||||
params[i+6].length = NULL;
|
||||
params[i+6].is_null = is_null;
|
||||
params[i+6].num = 10;
|
||||
|
||||
params[i+7].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
params[i+7].buffer_length = sizeof(double);
|
||||
params[i+7].buffer = v.f8;
|
||||
params[i+7].length = NULL;
|
||||
params[i+7].is_null = is_null;
|
||||
params[i+7].num = 10;
|
||||
|
||||
params[i+8].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
params[i+8].buffer_length = 40;
|
||||
params[i+8].buffer = v.bin;
|
||||
params[i+8].length = lb;
|
||||
params[i+8].is_null = is_null;
|
||||
params[i+8].num = 10;
|
||||
|
||||
params[i+9].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
params[i+9].buffer_length = 40;
|
||||
params[i+9].buffer = v.bin;
|
||||
params[i+9].length = lb;
|
||||
params[i+9].is_null = is_null;
|
||||
params[i+9].num = 10;
|
||||
|
||||
}
|
||||
|
||||
int64_t tts = 1591060628000;
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
v.ts[i] = tts + i;
|
||||
}
|
||||
|
||||
|
||||
for (int i = 0; i < 1; ++i) {
|
||||
tags[i+0].buffer_type = TSDB_DATA_TYPE_INT;
|
||||
tags[i+0].buffer = v.v4;
|
||||
tags[i+0].is_null = &one_not_null;
|
||||
tags[i+0].length = NULL;
|
||||
|
||||
tags[i+1].buffer_type = TSDB_DATA_TYPE_BOOL;
|
||||
tags[i+1].buffer = v.b;
|
||||
tags[i+1].is_null = &one_not_null;
|
||||
tags[i+1].length = NULL;
|
||||
|
||||
tags[i+2].buffer_type = TSDB_DATA_TYPE_TINYINT;
|
||||
tags[i+2].buffer = v.v1;
|
||||
tags[i+2].is_null = &one_not_null;
|
||||
tags[i+2].length = NULL;
|
||||
|
||||
tags[i+3].buffer_type = TSDB_DATA_TYPE_SMALLINT;
|
||||
tags[i+3].buffer = v.v2;
|
||||
tags[i+3].is_null = &one_not_null;
|
||||
tags[i+3].length = NULL;
|
||||
|
||||
tags[i+4].buffer_type = TSDB_DATA_TYPE_BIGINT;
|
||||
tags[i+4].buffer = v.v8;
|
||||
tags[i+4].is_null = &one_not_null;
|
||||
tags[i+4].length = NULL;
|
||||
|
||||
tags[i+5].buffer_type = TSDB_DATA_TYPE_FLOAT;
|
||||
tags[i+5].buffer = v.f4;
|
||||
tags[i+5].is_null = &one_not_null;
|
||||
tags[i+5].length = NULL;
|
||||
|
||||
tags[i+6].buffer_type = TSDB_DATA_TYPE_DOUBLE;
|
||||
tags[i+6].buffer = v.f8;
|
||||
tags[i+6].is_null = &one_not_null;
|
||||
tags[i+6].length = NULL;
|
||||
|
||||
tags[i+7].buffer_type = TSDB_DATA_TYPE_BINARY;
|
||||
tags[i+7].buffer = v.bin;
|
||||
tags[i+7].is_null = &one_not_null;
|
||||
tags[i+7].length = (uintptr_t *)lb;
|
||||
|
||||
tags[i+8].buffer_type = TSDB_DATA_TYPE_NCHAR;
|
||||
tags[i+8].buffer = v.bin;
|
||||
tags[i+8].is_null = &one_not_null;
|
||||
tags[i+8].length = (uintptr_t *)lb;
|
||||
}
|
||||
|
||||
|
||||
unsigned long long starttime = getCurrentTime();
|
||||
|
||||
char *sql = "insert into ? using stb1 tags(?,?,?,?,?,?,?,?,?) values(?,?,?,?,?,?,?,?,?,?)";
|
||||
int code = taos_stmt_prepare(NULL, sql, 0);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_prepare. code:%s\n", taos_stmt_errstr(NULL));
|
||||
return -1;
|
||||
}
|
||||
|
||||
int id = 0;
|
||||
for (int zz = 0; zz < 1; zz++) {
|
||||
char buf[32];
|
||||
sprintf(buf, "m%d", zz);
|
||||
code = taos_stmt_set_tbname_tags(stmt, buf, tags);
|
||||
if (code != 0){
|
||||
printf("failed to execute taos_stmt_set_tbname_tags. error:%s\n", taos_stmt_errstr(stmt));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
code = taos_stmt_bind_param_batch(stmt, params + id * 10);
|
||||
if (code != 0) {
|
||||
printf("failed to execute taos_stmt_bind_param_batch. error:%s\n", taos_stmt_errstr(stmt));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
code = taos_stmt_bind_param_batch(stmt, params + id * 10);
|
||||
if (code != 0) {
|
||||
printf("failed to execute taos_stmt_bind_param_batch. error:%s\n", taos_stmt_errstr(stmt));
|
||||
return -1;
|
||||
}
|
||||
|
||||
taos_stmt_add_batch(stmt);
|
||||
}
|
||||
|
||||
if (taos_stmt_execute(stmt) != 0) {
|
||||
printf("failed to execute insert statement.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
++id;
|
||||
|
||||
unsigned long long endtime = getCurrentTime();
|
||||
printf("insert total %d records, used %u seconds, avg:%u useconds\n", 10, (endtime-starttime)/1000000UL, (endtime-starttime)/(10));
|
||||
|
||||
free(v.ts);
|
||||
free(lb);
|
||||
free(params);
|
||||
free(is_null);
|
||||
free(no_null);
|
||||
free(tags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//300 tables 60 records
|
||||
int stmt_funcb1(TAOS_STMT *stmt) {
|
||||
struct {
|
||||
|
@ -3375,6 +4199,9 @@ void check_result(TAOS *taos, char *tname, int printr, int expected) {
|
|||
char sql[255] = "SELECT * FROM ";
|
||||
TAOS_RES *result;
|
||||
|
||||
//FORCE NO PRINT
|
||||
printr = 0;
|
||||
|
||||
strcat(sql, tname);
|
||||
|
||||
result = taos_query(taos, sql);
|
||||
|
@ -3835,7 +4662,7 @@ void* runcase(void *par) {
|
|||
#endif
|
||||
|
||||
|
||||
#if 1
|
||||
#if 1
|
||||
prepare(taos, 1, 1);
|
||||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
@ -3859,9 +4686,9 @@ void* runcase(void *par) {
|
|||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb start\n");
|
||||
printf("1t+10r+bm+autoctb1 start\n");
|
||||
stmt_funcb_autoctb1(stmt);
|
||||
printf("1t+10r+bm+autoctb end\n");
|
||||
printf("1t+10r+bm+autoctb1 end\n");
|
||||
printf("check result start\n");
|
||||
check_result(taos, "m0", 1, 10);
|
||||
printf("check result end\n");
|
||||
|
@ -3874,9 +4701,9 @@ void* runcase(void *par) {
|
|||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb start\n");
|
||||
printf("1t+10r+bm+autoctb2 start\n");
|
||||
stmt_funcb_autoctb2(stmt);
|
||||
printf("1t+10r+bm+autoctb end\n");
|
||||
printf("1t+10r+bm+autoctb2 end\n");
|
||||
printf("check result start\n");
|
||||
check_result(taos, "m0", 1, 10);
|
||||
printf("check result end\n");
|
||||
|
@ -3890,9 +4717,9 @@ void* runcase(void *par) {
|
|||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb start\n");
|
||||
printf("1t+10r+bm+autoctb3 start\n");
|
||||
stmt_funcb_autoctb3(stmt);
|
||||
printf("1t+10r+bm+autoctb end\n");
|
||||
printf("1t+10r+bm+autoctb3 end\n");
|
||||
printf("check result start\n");
|
||||
check_result(taos, "m0", 1, 10);
|
||||
printf("check result end\n");
|
||||
|
@ -3900,11 +4727,27 @@ void* runcase(void *par) {
|
|||
|
||||
#endif
|
||||
|
||||
|
||||
#if 1
|
||||
prepare(taos, 1, 0);
|
||||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb4 start\n");
|
||||
stmt_funcb_autoctb4(stmt);
|
||||
printf("1t+10r+bm+autoctb4 end\n");
|
||||
printf("check result start\n");
|
||||
check_result(taos, "m0", 1, 10);
|
||||
printf("check result end\n");
|
||||
taos_stmt_close(stmt);
|
||||
#endif
|
||||
|
||||
|
||||
#if 1
|
||||
prepare(taos, 1, 0);
|
||||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb+e1 start\n");
|
||||
stmt_funcb_autoctb_e1(stmt);
|
||||
printf("1t+10r+bm+autoctb+e1 end\n");
|
||||
|
@ -3930,6 +4773,52 @@ void* runcase(void *par) {
|
|||
|
||||
#endif
|
||||
|
||||
#if 1
|
||||
prepare(taos, 1, 0);
|
||||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb+e3 start\n");
|
||||
stmt_funcb_autoctb_e3(stmt);
|
||||
printf("1t+10r+bm+autoctb+e3 end\n");
|
||||
printf("check result start\n");
|
||||
//check_result(taos, "m0", 1, 0);
|
||||
printf("check result end\n");
|
||||
taos_stmt_close(stmt);
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if 1
|
||||
prepare(taos, 1, 0);
|
||||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb+e4 start\n");
|
||||
stmt_funcb_autoctb_e4(stmt);
|
||||
printf("1t+10r+bm+autoctb+e4 end\n");
|
||||
printf("check result start\n");
|
||||
//check_result(taos, "m0", 1, 0);
|
||||
printf("check result end\n");
|
||||
taos_stmt_close(stmt);
|
||||
|
||||
#endif
|
||||
|
||||
#if 1
|
||||
prepare(taos, 1, 0);
|
||||
|
||||
stmt = taos_stmt_init(taos);
|
||||
|
||||
printf("1t+10r+bm+autoctb+e5 start\n");
|
||||
stmt_funcb_autoctb_e5(stmt);
|
||||
printf("1t+10r+bm+autoctb+e5 end\n");
|
||||
printf("check result start\n");
|
||||
//check_result(taos, "m0", 1, 0);
|
||||
printf("check result end\n");
|
||||
taos_stmt_close(stmt);
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#if 1
|
||||
prepare(taos, 1, 1);
|
||||
|
@ -4138,6 +5027,8 @@ void* runcase(void *par) {
|
|||
|
||||
#endif
|
||||
|
||||
printf("test end\n");
|
||||
|
||||
return NULL;
|
||||
|
||||
}
|
||||
|
|
|
@ -1811,10 +1811,6 @@ if $data09 != 3 then
|
|||
return -1
|
||||
endi
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
sql select st0.*,st1.* from st0, st1 where st1.id1=st0.id1 and st0.ts=st1.ts and st1.ts=st0.ts and st0.id1=st1.id1 order by st0.ts limit 5 offset 5
|
||||
if $rows != 5 then
|
||||
return -1
|
||||
|
@ -2294,7 +2290,6 @@ if $data19 != 9925 then
|
|||
return -1
|
||||
endi
|
||||
|
||||
|
||||
sql_error select tb0_1.*, tb1_1.* from tb0_1, tb1_1 where tb0_1.f1=tb1_1.f1;
|
||||
sql_error select tb0_1.*, tb1_1.* from tb0_1, tb1_1 where tb0_1.ts=tb1_1.ts and tb0_1.id1=tb1_1.id2;
|
||||
sql_error select tb0_5.*, tb1_5.*,tb2_5.*,tb3_5.*,tb4_5.*,tb5_5.*, tb6_5.*,tb7_5.*,tb8_5.*,tb9_5.*,tba_5.* from tb0_5, tb1_5, tb2_5, tb3_5, tb4_5,tb5_5, tb6_5, tb7_5, tb8_5, tb9_5, tba_5 where tb9_5.ts=tb8_5.ts and tb8_5.ts=tb7_5.ts and tb7_5.ts=tb6_5.ts and tb6_5.ts=tb5_5.ts and tb5_5.ts=tb4_5.ts and tb4_5.ts=tb3_5.ts and tb3_5.ts=tb2_5.ts and tb2_5.ts=tb1_5.ts and tb1_5.ts=tb0_5.ts and tb0_5.ts=tba_5.ts;
|
||||
|
@ -2317,10 +2312,4 @@ sql_error select last(*) from st0, st1 where st0.ts=st1.ts and st0.id1=st1.id1 g
|
|||
sql_error select st0.*,st1.*,st2.*,st3.*,st4.*,st5.*,st6.*,st7.*,st8.*,st9.* from st0,st1,st2,st3,st4,st5,st6,st7,st8,st9 where st0.ts=st2.ts and st0.ts=st4.ts and st0.ts=st6.ts and st0.ts=st8.ts and st1.ts=st3.ts and st3.ts=st5.ts and st5.ts=st7.ts and st7.ts=st9.ts and st0.id1=st2.id1 and st0.id1=st4.id1 and st0.id1=st6.id1 and st0.id1=st8.id1 and st1.id1=st3.id1 and st3.id1=st5.id1 and st5.id1=st7.id1 and st7.id1=st9.id1;
|
||||
sql_error select st0.*,st1.*,st2.*,st3.*,st4.*,st5.*,st6.*,st7.*,st8.*,st9.* from st0,st1,st2,st3,st4,st5,st6,st7,st8,st9,sta where st0.ts=st2.ts and st0.ts=st4.ts and st0.ts=st6.ts and st0.ts=st8.ts and st1.ts=st3.ts and st3.ts=st5.ts and st5.ts=st7.ts and st7.ts=st9.ts and st0.ts=st1.ts and st0.id1=st2.id1 and st0.id1=st4.id1 and st0.id1=st6.id1 and st0.id1=st8.id1 and st1.id1=st3.id1 and st3.id1=st5.id1 and st5.id1=st7.id1 and st7.id1=st9.id1 and st0.id1=st1.id1 and st0.id1=sta.id1 and st0.ts=sta.ts;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
system sh/exec.sh -n dnode1 -s stop -x SIGINT
|
||||
|
|
|
@ -9,7 +9,7 @@ sql connect
|
|||
print ======================== dnode1 start
|
||||
|
||||
$db = testdb
|
||||
|
||||
sql drop database if exists $db
|
||||
sql create database $db cachelast 2
|
||||
sql use $db
|
||||
|
||||
|
|
|
@ -39,6 +39,7 @@ run general/parser/slimit1.sim
|
|||
run general/parser/slimit_alter_tags.sim
|
||||
run general/parser/tbnameIn.sim
|
||||
run general/parser/join.sim
|
||||
#run general/parser/join_multitables.sim
|
||||
run general/parser/join_multivnode.sim
|
||||
run general/parser/join_manyblocks.sim
|
||||
run general/parser/projection_limit_offset.sim
|
||||
|
|
|
@ -151,18 +151,12 @@ sql_error select last(*) from wh_mt1 where c5 in ('1')
|
|||
sql_error select last(*) from wh_mt1_tb1 where c5 in ('1')
|
||||
sql_error select last(*) from wh_mt1 where c6 in ('1')
|
||||
sql_error select last(*) from wh_mt1_tb1 where c6 in ('1')
|
||||
sql_error select last(*) from wh_mt1 where c7 in ('binary')
|
||||
sql_error select last(*) from wh_mt1_tb1 where c7 in ('binary')
|
||||
sql_error select last(*) from wh_mt1 where c8 in ('nchar')
|
||||
sql_error select last(*) from wh_mt1_tb1 where c9 in (true, false)
|
||||
#sql_error select last(*) from wh_mt1 where c7 in ('binary')
|
||||
#sql_error select last(*) from wh_mt1_tb1 where c7 in ('binary')
|
||||
#sql_error select last(*) from wh_mt1 where c8 in ('nchar')
|
||||
#sql_error select last(*) from wh_mt1_tb1 where c9 in (true, false)
|
||||
sql_error select last(*) from wh_mt1 where c10 in ('2019-01-01 00:00:00.000')
|
||||
sql_error select last(*) from wh_mt1_tb1 where c10 in ('2019-01-01 00:00:00.000')
|
||||
sql_error select last(*) from wh_mt1 where t1 in ('binary')
|
||||
sql_error select last(*) from wh_mt1 where t2 in (1)
|
||||
sql_error select last(*) from wh_mt1 where t3 in (1)
|
||||
sql_error select last(*) from wh_mt1 where t4 in (1)
|
||||
sql_error select last(*) from wh_mt1 where t5 in (1)
|
||||
sql_error select last(*) from wh_mt1 where t6 in (1)
|
||||
sql select last(*) from wh_mt1 where c1 = 1
|
||||
if $rows != 1 then
|
||||
return -1
|
||||
|
@ -359,4 +353,4 @@ if $rows != 0 then
|
|||
endi
|
||||
|
||||
|
||||
system sh/exec.sh -n dnode1 -s stop -x SIGINT
|
||||
system sh/exec.sh -n dnode1 -s stop -x SIGINT
|
||||
|
|
Loading…
Reference in New Issue