diff --git a/.travis.yml b/.travis.yml index 8c57085296..9aac6c597c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -34,6 +34,7 @@ matrix: - psmisc - unixodbc - unixodbc-dev + - mono-complete before_script: - export TZ=Asia/Harbin @@ -59,6 +60,18 @@ matrix: pip3 install guppy3 pip3 install --user ${TRAVIS_BUILD_DIR}/src/connector/python/linux/python3/ + cd ${TRAVIS_BUILD_DIR}/tests/examples/C#/taosdemo + mcs -out:taosdemo *.cs || travis_terminate $? + pkill -TERM -x taosd + fuser -k -n tcp 6030 + sleep 1 + ${TRAVIS_BUILD_DIR}/debug/build/bin/taosd -c ${TRAVIS_BUILD_DIR}/debug/test/cfg > /dev/null & + sleep 5 + mono taosdemo -Q DEFAULT -y || travis_terminate $? + pkill -KILL -x taosd + fuser -k -n tcp 6030 + sleep 1 + cd ${TRAVIS_BUILD_DIR}/tests ./test-all.sh smoke || travis_terminate $? sleep 1 @@ -74,6 +87,7 @@ matrix: ./valgrind-test.sh 2>&1 > mem-error-out.log sleep 1 + # Color setting RED='\033[0;31m' GREEN='\033[1;32m' diff --git a/CMakeLists.txt b/CMakeLists.txt index eb2b1cceb4..0c474a355d 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) IF (CMAKE_VERSION VERSION_LESS 3.0) PROJECT(TDengine CXX) SET(PROJECT_VERSION_MAJOR "${LIB_MAJOR_VERSION}") diff --git a/cmake/install.inc b/cmake/install.inc index 55b3fa188f..b0e5c71022 100755 --- a/cmake/install.inc +++ b/cmake/install.inc @@ -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.15-dist.jar DESTINATION connector/jdbc) + INSTALL(FILES ${LIBRARY_OUTPUT_PATH}/taos-jdbcdriver-2.0.16-dist.jar DESTINATION connector/jdbc) ENDIF () ELSEIF (TD_DARWIN) SET(TD_MAKE_INSTALL_SH "${TD_COMMUNITY_DIR}/packaging/tools/make_install.sh") diff --git a/cmake/version.inc b/cmake/version.inc index 49f01d00bc..0509a5ce1b 100644 --- a/cmake/version.inc +++ b/cmake/version.inc @@ -4,7 +4,7 @@ PROJECT(TDengine) IF (DEFINED VERNUMBER) SET(TD_VER_NUMBER ${VERNUMBER}) ELSE () - SET(TD_VER_NUMBER "2.0.13.0") + SET(TD_VER_NUMBER "2.0.14.0") ENDIF () IF (DEFINED VERCOMPATIBLE) diff --git a/deps/CMakeLists.txt b/deps/CMakeLists.txt index 8c6c73c440..1d725add21 100644 --- a/deps/CMakeLists.txt +++ b/deps/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) ADD_SUBDIRECTORY(zlib-1.2.11) diff --git a/deps/MQTT-C/CMakeLists.txt b/deps/MQTT-C/CMakeLists.txt index 15b3552521..36ede467ac 100644 --- a/deps/MQTT-C/CMakeLists.txt +++ b/deps/MQTT-C/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) # MQTT-C build options option(MQTT_C_OpenSSL_SUPPORT "Build MQTT-C with OpenSSL support?" OFF) diff --git a/deps/MsvcLibX/CMakeLists.txt b/deps/MsvcLibX/CMakeLists.txt index 4428579e1c..c02e4c7a4d 100644 --- a/deps/MsvcLibX/CMakeLists.txt +++ b/deps/MsvcLibX/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_WINDOWS) diff --git a/deps/iconv/CMakeLists.txt b/deps/iconv/CMakeLists.txt index 286070fa90..f26f109735 100644 --- a/deps/iconv/CMakeLists.txt +++ b/deps/iconv/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_WINDOWS) diff --git a/deps/pthread/CMakeLists.txt b/deps/pthread/CMakeLists.txt index 04e5be7472..dcd9ed0358 100644 --- a/deps/pthread/CMakeLists.txt +++ b/deps/pthread/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_WINDOWS) diff --git a/deps/regex/CMakeLists.txt b/deps/regex/CMakeLists.txt index 054b093d07..c7e983b992 100644 --- a/deps/regex/CMakeLists.txt +++ b/deps/regex/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_WINDOWS) diff --git a/deps/wepoll/CMakeLists.txt b/deps/wepoll/CMakeLists.txt index a81fd782bb..a8b3411221 100644 --- a/deps/wepoll/CMakeLists.txt +++ b/deps/wepoll/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_WINDOWS) diff --git a/deps/zlib-1.2.11/CMakeLists.txt b/deps/zlib-1.2.11/CMakeLists.txt index f83aa70085..a8750471d6 100644 --- a/deps/zlib-1.2.11/CMakeLists.txt +++ b/deps/zlib-1.2.11/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_WINDOWS) diff --git a/documentation20/webdocs/markdowndocs/TAOS SQL-ch.md b/documentation20/webdocs/markdowndocs/TAOS SQL-ch.md index b75ef6b190..946eec53ad 100644 --- a/documentation20/webdocs/markdowndocs/TAOS SQL-ch.md +++ b/documentation20/webdocs/markdowndocs/TAOS SQL-ch.md @@ -68,7 +68,9 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic 2) UPDATE 标志数据库支持更新相同时间戳数据; 3) 数据库名最大长度为33; + 4) 一条SQL 语句的最大长度为65480个字符; + 5) 数据库还有更多与存储相关的配置参数,请参见系统管理。 - **显示系统当前参数** @@ -119,6 +121,7 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic **Tips**: 以上所有参数修改后都可以用show databases来确认是否修改成功。 - **显示系统所有数据库** + ```mysql SHOW DATABASES; ``` @@ -130,10 +133,15 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic CREATE TABLE [IF NOT EXISTS] tb_name (timestamp_field_name TIMESTAMP, field1_name data_type1 [, field2_name data_type2 ...]); ``` 说明: + 1) 表的第一个字段必须是TIMESTAMP,并且系统自动将其设为主键; + 2) 表名最大长度为192; + 3) 表的每行长度不能超过16k个字符; + 4) 子表名只能由字母、数字和下划线组成,且不能以数字开头 + 5) 使用数据类型binary或nchar,需指定其最长的字节数,如binary(20),表示20字节; - **以超级表为模板创建数据表** @@ -149,7 +157,12 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic CREATE TABLE [IF NOT EXISTS] tb_name1 USING stb_name TAGS (tag_value1, ...) tb_name2 USING stb_name TAGS (tag_value2, ...) ...; ``` 以更快的速度批量创建大量数据表。(服务器端 2.0.14 及以上版本) - 说明:批量建表方式要求数据表必须以超级表为模板。 + + 说明: + + 1)批量建表方式要求数据表必须以超级表为模板。 + + 2)在不超出 SQL 语句长度限制的前提下,单条语句中的建表数量建议控制在 1000~3000 之间,将会获得比较理想的建表速度。 - **删除数据表** @@ -164,7 +177,9 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic ``` 显示当前数据库下的所有数据表信息。 + 说明:可在like中使用通配符进行名称的匹配,这一通配符字符串最长不能超过24字节。 + 通配符匹配:1)’%’ (百分号)匹配0到任意个字符;2)’\_’下划线匹配一个字符。 - **在线修改显示字符宽度** @@ -185,7 +200,9 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic ALTER TABLE tb_name ADD COLUMN field_name data_type; ``` 说明: + 1) 列的最大个数为1024,最小个数为2; + 2) 列名最大长度为64; - **表删除列** @@ -204,9 +221,13 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic 创建STable, 与创建表的SQL语法相似,但需指定TAGS字段的名称和类型 说明: + 1) TAGS 列的数据类型不能是timestamp类型; + 2) TAGS 列名不能与其他列名相同; + 3) TAGS 列名不能为预留关键字; + 4) TAGS 最多允许128个,至少1个,总长度不超过16k个字符。 - **删除超级表** @@ -333,7 +354,9 @@ SELECT select_expr [, select_expr ...] [LIMIT limit_val [, OFFSET offset_val]] [>> export_file] ``` + 说明:针对 insert 类型的 SQL 语句,我们采用的流式解析策略,在发现后面的错误之前,前面正确的部分SQL仍会执行。下面的sql中,insert语句是无效的,但是d1001仍会被创建。 + ```mysql taos> CREATE TABLE meters(ts TIMESTAMP, current FLOAT, voltage INT, phase FLOAT) TAGS(location BINARY(30), groupId INT); Query OK, 0 row(s) affected (0.008245s) @@ -614,10 +637,20 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT COUNT([*|field_name]) FROM tb_name [WHERE clause]; ``` 功能说明:统计表/超级表中记录行数或某列的非空值个数。 + 返回结果数据类型:长整型INT64。 + 应用字段:应用全部字段。 + 适用于:表、超级表。 - 说明:1)可以使用星号*来替代具体的字段,使用星号(*)返回全部记录数量。2)针对同一表的(不包含NULL值)字段查询结果均相同。3)如果统计对象是具体的列,则返回该列中非NULL值的记录数量。 + + 说明: + + 1)可以使用星号*来替代具体的字段,使用星号(*)返回全部记录数量。 + + 2)针对同一表的(不包含NULL值)字段查询结果均相同。 + + 3)如果统计对象是具体的列,则返回该列中非NULL值的记录数量。 示例: ```mysql @@ -639,8 +672,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT AVG(field_name) FROM tb_name [WHERE clause]; ``` 功能说明:统计表/超级表中某列的平均值。 + 返回结果数据类型:双精度浮点数Double。 + 应用字段:不能应用在timestamp、binary、nchar、bool字段。 + 适用于:表、超级表。 示例: @@ -663,8 +699,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT TWA(field_name) FROM tb_name WHERE clause; ``` 功能说明:时间加权平均函数。统计表/超级表中某列在一段时间内的时间加权平均。 + 返回结果数据类型:双精度浮点数Double。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 适用于:表、超级表。 - **SUM** @@ -672,8 +711,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT SUM(field_name) FROM tb_name [WHERE clause]; ``` 功能说明:统计表/超级表中某列的和。 + 返回结果数据类型:双精度浮点数Double和长整型INT64。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 适用于:表、超级表。 示例: @@ -696,8 +738,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT STDDEV(field_name) FROM tb_name [WHERE clause]; ``` 功能说明:统计表中某列的均方差。 + 返回结果数据类型:双精度浮点数Double。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 适用于:表。 示例: @@ -714,9 +759,13 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT LEASTSQUARES(field_name, start_val, step_val) FROM tb_name [WHERE clause]; ``` 功能说明:统计表中某列的值是主键(时间戳)的拟合直线方程。start_val是自变量初始值,step_val是自变量的步长值。 + 返回结果数据类型:字符串表达式(斜率, 截距)。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 说明:自变量是时间戳,因变量是该列的值。 + 适用于:表。 示例: @@ -735,7 +784,9 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT MIN(field_name) FROM {tb_name | stb_name} [WHERE clause]; ``` 功能说明:统计表/超级表中某列的值最小值。 + 返回结果数据类型:同应用的字段。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 示例: @@ -758,7 +809,9 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT MAX(field_name) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表/超级表中某列的值最大值。 + 返回结果数据类型:同应用的字段。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 示例: @@ -781,9 +834,18 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT FIRST(field_name) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表/超级表中某列的值最先写入的非NULL值。 + 返回结果数据类型:同应用的字段。 + 应用字段:所有字段。 - 说明:1)如果要返回各个列的首个(时间戳最小)非NULL值,可以使用FIRST(\*);2) 如果结果集中的某列全部为NULL值,则该列的返回结果也是NULL;3) 如果结果集中所有列全部为NULL值,则不返回结果。 + + 说明: + + 1)如果要返回各个列的首个(时间戳最小)非NULL值,可以使用FIRST(\*); + + 2) 如果结果集中的某列全部为NULL值,则该列的返回结果也是NULL; + + 3) 如果结果集中所有列全部为NULL值,则不返回结果。 示例: ```mysql @@ -805,9 +867,16 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT LAST(field_name) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表/超级表中某列的值最后写入的非NULL值。 + 返回结果数据类型:同应用的字段。 + 应用字段:所有字段。 - 说明:1)如果要返回各个列的最后(时间戳最大)一个非NULL值,可以使用LAST(\*);2)如果结果集中的某列全部为NULL值,则该列的返回结果也是NULL;如果结果集中所有列全部为NULL值,则不返回结果。 + + 说明: + + 1)如果要返回各个列的最后(时间戳最大)一个非NULL值,可以使用LAST(\*); + + 2)如果结果集中的某列全部为NULL值,则该列的返回结果也是NULL;如果结果集中所有列全部为NULL值,则不返回结果。 示例: ```mysql @@ -829,9 +898,16 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT TOP(field_name, K) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明: 统计表/超级表中某列的值最大*k*个非NULL值。若多于k个列值并列最大,则返回时间戳小的。 + 返回结果数据类型:同应用的字段。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 - 说明:1)*k*值取值范围1≤*k*≤100;2)系统同时返回该记录关联的时间戳列。 + + 说明: + + 1)*k*值取值范围1≤*k*≤100; + + 2)系统同时返回该记录关联的时间戳列。 示例: ```mysql @@ -856,9 +932,16 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT BOTTOM(field_name, K) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表/超级表中某列的值最小*k*个非NULL值。若多于k个列值并列最小,则返回时间戳小的。 + 返回结果数据类型:同应用的字段。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 - 说明:1)*k*值取值范围1≤*k*≤100;2)系统同时返回该记录关联的时间戳列。 + + 说明: + + 1)*k*值取值范围1≤*k*≤100; + + 2)系统同时返回该记录关联的时间戳列。 示例: ```mysql @@ -882,8 +965,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT PERCENTILE(field_name, P) FROM { tb_name } [WHERE clause]; ``` 功能说明:统计表中某列的值百分比分位数。 + 返回结果数据类型: 双精度浮点数Double。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 说明:*P*值取值范围0≤*P*≤100,为0的时候等同于MIN,为100的时候等同于MAX。 示例: @@ -900,9 +986,13 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT APERCENTILE(field_name, P) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表中某列的值百分比分位数,与PERCENTILE函数相似,但是返回近似结果。 + 返回结果数据类型: 双精度浮点数Double。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 说明:*P*值取值范围0≤*P*≤100,为0的时候等同于MIN,为100的时候等同于MAX。推荐使用```APERCENTILE```函数,该函数性能远胜于```PERCENTILE```函数 + ```mysql taos> SELECT APERCENTILE(current, 20) FROM d1001; apercentile(current, 20) | @@ -916,8 +1006,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT LAST_ROW(field_name) FROM { tb_name | stb_name }; ``` 功能说明:返回表(超级表)的最后一条记录。 + 返回结果数据类型:同应用的字段。 + 应用字段:所有字段。 + 说明:与last函数不同,last_row不支持时间范围限制,强制返回最后一条记录。 示例: @@ -941,8 +1034,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT DIFF(field_name) FROM tb_name [WHERE clause]; ``` 功能说明:统计表中某列的值与前一行对应值的差。 + 返回结果数据类型: 同应用字段。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 + 说明:输出结果行数是范围内总行数减一,第一行没有结果输出。 示例: @@ -960,8 +1056,11 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT SPREAD(field_name) FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表/超级表中某列的最大值和最小值之差。 + 返回结果数据类型: 双精度浮点数。 + 应用字段:不能应用在binary、nchar、bool类型字段。 + 说明:可用于TIMESTAMP字段,此时表示记录的时间覆盖范围。 示例: @@ -985,9 +1084,16 @@ TDengine支持针对数据的聚合查询。提供支持的聚合和选择函数 SELECT field_name [+|-|*|/|%][Value|field_name] FROM { tb_name | stb_name } [WHERE clause]; ``` 功能说明:统计表/超级表中某列或多列间的值加、减、乘、除、取余计算结果。 + 返回结果数据类型:双精度浮点数。 + 应用字段:不能应用在timestamp、binary、nchar、bool类型字段。 - 说明:1)支持两列或多列之间进行计算,可使用括号控制计算优先级;2)NULL字段不参与计算,如果参与计算的某行中包含NULL,该行的计算结果为NULL。 + + 说明: + + 1)支持两列或多列之间进行计算,可使用括号控制计算优先级; + + 2)NULL字段不参与计算,如果参与计算的某行中包含NULL,该行的计算结果为NULL。 ```mysql taos> SELECT current + voltage * phase FROM d1001; diff --git a/documentation20/webdocs/markdowndocs/administrator-ch.md b/documentation20/webdocs/markdowndocs/administrator-ch.md index 383822789f..9eee5b2b69 100644 --- a/documentation20/webdocs/markdowndocs/administrator-ch.md +++ b/documentation20/webdocs/markdowndocs/administrator-ch.md @@ -255,7 +255,7 @@ taos -C 或 taos --dump-config CREATE USER PASS <'password'>; ``` -创建用户,并指定用户名和密码,密码需要用单引号引起来,单引号为英文半角 +创建用户,并指定用户名和密码,密码需要用单引号引起来,单引号为英文半角 ```sql DROP USER ; @@ -267,13 +267,15 @@ DROP USER ; ALTER USER PASS <'password'>; ``` -修改用户密码, 为避免被转换为小写,密码需要用单引号引用,单引号为英文半角 +修改用户密码,为避免被转换为小写,密码需要用单引号引用,单引号为英文半角 ```sql -ALTER USER PRIVILEGE ; +ALTER USER PRIVILEGE ; ``` -修改用户权限为:super/write/read,不需要添加单引号 +修改用户权限为:write 或 read,不需要添加单引号 + +说明:系统内共有 super/write/read 三种权限级别,但目前不允许通过 alter 指令把 super 权限赋予用户。 ```mysql SHOW USERS; @@ -432,11 +434,12 @@ TDengine的所有可执行文件默认存放在 _/usr/local/taos/bin_ 目录下 - 数据库名:不能包含“.”以及特殊字符,不能超过32个字符 - 表名:不能包含“.”以及特殊字符,与所属数据库名一起,不能超过192个字符 - 表的列名:不能包含特殊字符,不能超过64个字符 +- 数据库名、表名、列名,都不能以数字开头 - 表的列数:不能超过1024列 - 记录的最大长度:包括时间戳8 byte,不能超过16KB - 单条SQL语句默认最大字符串长度:65480 byte - 数据库副本数:不能超过3 -- 用户名:不能超过20个byte +- 用户名:不能超过23个byte - 用户密码:不能超过15个byte - 标签(Tags)数量:不能超过128个 - 标签的总长度:不能超过16Kbyte diff --git a/documentation20/webdocs/markdowndocs/architecture-ch.md b/documentation20/webdocs/markdowndocs/architecture-ch.md index 47fb8094b7..a666f75515 100644 --- a/documentation20/webdocs/markdowndocs/architecture-ch.md +++ b/documentation20/webdocs/markdowndocs/architecture-ch.md @@ -372,7 +372,7 @@ select count(*) from d1001 interval(1h); select count(*) from d1001 interval(1h) fill(prev); ``` -针对d1001设备采集数据统计每小时记录数,如果某一个小时不存在数据,这返回之前一个小时的统计数据。TDengine提供前向插值(prev)、线性插值(linear)、NULL值填充(NULL)、特定值填充(value)。 +针对d1001设备采集数据统计每小时记录数,如果某一个小时不存在数据,则返回之前一个小时的统计数据。TDengine提供前向插值(prev)、线性插值(linear)、NULL值填充(NULL)、特定值填充(value)。 ### 多表聚合查询 TDengine对每个数据采集点单独建表,但在实际应用中经常需要对不同的采集点数据进行聚合。为高效的进行聚合操作,TDengine引入超级表(STable)的概念。超级表用来代表一特定类型的数据采集点,它是包含多张表的表集合,集合里每张表的模式(schema)完全一致,但每张表都带有自己的静态标签,标签可以多个,可以随时增加、删除和修改。 应用可通过指定标签的过滤条件,对一个STable下的全部或部分表进行聚合或统计操作,这样大大简化应用的开发。其具体流程如下图所示: diff --git a/documentation20/webdocs/markdowndocs/cluster-ch.md b/documentation20/webdocs/markdowndocs/cluster-ch.md index 89f6a64f19..f3f6f2b300 100644 --- a/documentation20/webdocs/markdowndocs/cluster-ch.md +++ b/documentation20/webdocs/markdowndocs/cluster-ch.md @@ -218,7 +218,7 @@ SHOW MNODES; 如果一个数据节点离线,TDengine集群将自动检测到。有如下两种情况: -- 该数据节点离线超过一定时间(taos.cfg里配置参数offlineThreshold控制时长),系统将自动把该数据节点删除,产生系统报警信息,触发负载均衡流程。如果该被删除的数据节点重现上线时,它将无法加入集群,需要系统管理员重新将其添加进集群才会开始工作。 +- 该数据节点离线超过一定时间(taos.cfg里配置参数offlineThreshold控制时长),系统将自动把该数据节点删除,产生系统报警信息,触发负载均衡流程。如果该被删除的数据节点重新上线时,它将无法加入集群,需要系统管理员重新将其添加进集群才会开始工作。 - 离线后,在offlineThreshold的时长内重新上线,系统将自动启动数据恢复流程,等数据完全恢复后,该节点将开始正常工作。 **注意:**如果一个虚拟节点组(包括mnode组)里所归属的每个数据节点都处于离线或unsynced状态,必须等该虚拟节点组里的所有数据节点都上线、都能交换状态信息后,才能选出Master,该虚拟节点组才能对外提供服务。比如整个集群有3个数据节点,副本数为3,如果3个数据节点都宕机,然后2个数据节点重启,是无法工作的,只有等3个数据节点都重启成功,才能对外服务。 @@ -227,5 +227,5 @@ SHOW MNODES; 如果副本数为偶数,当一个vnode group里一半vnode不工作时,是无法从中选出master的。同理,一半mnode不工作时,是无法选出mnode的master的,因为存在“split brain”问题。为解决这个问题,TDengine引入了arbitrator的概念。Arbitrator模拟一个vnode或mnode在工作,但只简单的负责网络连接,不处理任何数据插入或访问。只要包含arbitrator在内,超过半数的vnode或mnode工作,那么该vnode group或mnode组就可以正常的提供数据插入或查询服务。比如对于副本数为2的情形,如果一个节点A离线,但另外一个节点B正常,而且能连接到arbitrator, 那么节点B就能正常工作。 -TDengine提供一个执行程序tarbitrator, 找任何一台Linux服务器运行它即可。请点击[安装包下载](https://www.taosdata.com/cn/all-downloads/),在TDengine Arbitrator Linux一节中,选择适合的版本下载并安装。该程序对系统资源几乎没有要求,只需要保证有网络连接即可。该应用的命令行参数`-p`可以指定其对外服务的端口号,缺省是6042。配置每个taosd实例时,可以在配置文件taos.cfg里将参数arbitrator设置为arbitrator的End Point。如果该参数配置了,当副本数为偶数数,系统将自动连接配置的arbitrator。如果副本数为奇数,即使配置了arbitrator, 系统也不会去建立连接。 +TDengine提供一个执行程序tarbitrator, 找任何一台Linux服务器运行它即可。请点击[安装包下载](https://www.taosdata.com/cn/all-downloads/),在TDengine Arbitrator Linux一节中,选择适合的版本下载并安装。该程序对系统资源几乎没有要求,只需要保证有网络连接即可。该应用的命令行参数`-p`可以指定其对外服务的端口号,缺省是6042。配置每个taosd实例时,可以在配置文件taos.cfg里将参数arbitrator设置为arbitrator的End Point。如果该参数配置了,当副本数为偶数时,系统将自动连接配置的arbitrator。如果副本数为奇数,即使配置了arbitrator, 系统也不会去建立连接。 diff --git a/documentation20/webdocs/markdowndocs/cluster.md b/documentation20/webdocs/markdowndocs/cluster.md index f5fa6af48c..8cf7065f72 100644 --- a/documentation20/webdocs/markdowndocs/cluster.md +++ b/documentation20/webdocs/markdowndocs/cluster.md @@ -89,6 +89,8 @@ SHOW DNODES; ``` 它将列出集群中所有的dnode,每个dnode的fqdn:port, 状态(ready, offline等),vnode数目,还未使用的vnode数目等信息。在添加或删除一个节点后,可以使用该命令查看。 +如果集群配置了Arbitrator,那么它也会在这个节点列表中显示出来,其role列的值会是“arb”。 + ###查看虚拟节点组 为充分利用多核技术,并提供scalability,数据需要分片处理。因此TDengine会将一个DB的数据切分成多份,存放在多个vnode里。这些vnode可能分布在多个dnode里,这样就实现了水平扩展。一个vnode仅仅属于一个DB,但一个DB可以有多个vnode。vnode的是mnode根据当前系统资源的情况,自动进行分配的,无需任何人工干预。 @@ -139,4 +141,6 @@ SHOW MNODES; 如果副本数为偶数,当一个vnode group里一半vnode不工作时,是无法从中选出master的。同理,一半mnode不工作时,是无法选出mnode的master的,因为存在“split brain”问题。为解决这个问题,TDengine引入了arbitrator的概念。Arbitrator模拟一个vnode或mnode在工作,但只简单的负责网络连接,不处理任何数据插入或访问。只要包含arbitrator在内,超过半数的vnode或mnode工作,那么该vnode group或mnode组就可以正常的提供数据插入或查询服务。比如对于副本数为2的情形,如果一个节点A离线,但另外一个节点B正常,而且能连接到arbitrator, 那么节点B就能正常工作。 -TDengine安装包里带有一个执行程序tarbitrator, 找任何一台Linux服务器运行它即可。该程序对系统资源几乎没有要求,只需要保证有网络连接即可。该应用的命令行参数`-p`可以指定其对外服务的端口号,缺省是6030。配置每个taosd实例时,可以在配置文件taos.cfg里将参数arbitrator设置为arbitrator的End Point。如果该参数配置了,当副本数为偶数数,系统将自动连接配置的arbitrator。 +TDengine安装包里带有一个执行程序tarbitrator, 找任何一台Linux服务器运行它即可。该程序对系统资源几乎没有要求,只需要保证有网络连接即可。该应用的命令行参数`-p`可以指定其对外服务的端口号,缺省是6030。配置每个taosd实例时,可以在配置文件taos.cfg里将参数arbitrator设置为Arbitrator的End Point。如果该参数配置了,当副本数为偶数时,系统将自动连接配置的Arbitrator。 + +在配置了Arbitrator的情况下,它也会显示在“show dnodes;”指令给出的节点列表中。 diff --git a/documentation20/webdocs/markdowndocs/connector-ch.md b/documentation20/webdocs/markdowndocs/connector-ch.md index 7848ceabc4..da9c2e5a11 100644 --- a/documentation20/webdocs/markdowndocs/connector-ch.md +++ b/documentation20/webdocs/markdowndocs/connector-ch.md @@ -252,7 +252,7 @@ C/C++的API类似于MySQL的C API。应用程序使用时,需要包含TDengine - `void taos_free_result(TAOS_RES *res)` - 释放查询结果集以及相关的资源。查询完成后,务必调用该API释放资源,否则可能导致应用内存泄露。 + 释放查询结果集以及相关的资源。查询完成后,务必调用该API释放资源,否则可能导致应用内存泄露。但也需注意,释放资源后,如果再调用`taos_consume`等获取查询结果的函数,将导致应用Crash。 - `char *taos_errstr(TAOS_RES *res)` @@ -262,11 +262,11 @@ C/C++的API类似于MySQL的C API。应用程序使用时,需要包含TDengine 获取最近一次API调用失败的原因,返回值为错误代码。 -**注意**:对于每个数据库应用,2.0及以上版本 TDengine 推荐只建立一个连接。同时在应用中将该连接 (TAOS*) 结构体传递到不同的线程共享使用。基于 TAOS 结构体发出的查询、写入等操作具有多线程安全性。C 语言的连接器可以按照需求动态建立面向数据库的新连接(该过程对用户不可见),同时建议只有在程序最后退出的时候才调用 taos_close 关闭连接。 +**注意**:2.0及以上版本 TDengine 推荐数据库应用的每个线程都建立一个独立的连接,或基于线程建立连接池。而不推荐在应用中将该连接 (TAOS\*) 结构体传递到不同的线程共享使用。基于 TAOS 结构体发出的查询、写入等操作具有多线程安全性,但 “USE statement” 等状态量有可能在线程之间相互干扰。此外,C 语言的连接器可以按照需求动态建立面向数据库的新连接(该过程对用户不可见),同时建议只有在程序最后退出的时候才调用 taos_close 关闭连接。 ### 异步查询API -同步API之外,TDengine还提供性能更高的异步调用API处理数据插入、查询操作。在软硬件环境相同的情况下,异步API处理数据插入的速度比同步API快2~4倍。异步API采用非阻塞式的调用方式,在系统真正完成某个具体数据库操作前,立即返回。调用的线程可以去处理其他工作,从而可以提升整个应用的性能。异步API在网络延迟严重的情况下,优点尤为突出。 +同步API之外,TDengine还提供性能更高的异步调用API处理数据插入、查询操作。在软硬件环境相同的情况下,异步API处理数据插入的速度比同步API快2\~4倍。异步API采用非阻塞式的调用方式,在系统真正完成某个具体数据库操作前,立即返回。调用的线程可以去处理其他工作,从而可以提升整个应用的性能。异步API在网络延迟严重的情况下,优点尤为突出。 异步API都需要应用提供相应的回调函数,回调函数参数设置如下:前两个参数都是一致的,第三个参数依不同的API而定。第一个参数param是应用调用异步API时提供给系统的,用于回调时,应用能够找回具体操作的上下文,依具体实现而定。第二个参数是SQL操作的结果集,如果为空,比如insert操作,表示没有记录返回,如果不为空,比如select操作,表示有记录返回。 @@ -425,7 +425,7 @@ cd C:\TDengine\connector\python\windows python -m pip install python3\ ``` -*如果机器上没有pip命令,用户可将src/connector/python/python3或src/connector/python/python2下的taos文件夹拷贝到应用程序的目录使用。 +* 如果机器上没有pip命令,用户可将src/connector/python/python3或src/connector/python/python2下的taos文件夹拷贝到应用程序的目录使用。 对于windows 客户端,安装TDengine windows 客户端后,将C:\TDengine\driver\taos.dll拷贝到C:\windows\system32目录下即可。 ### 使用 @@ -442,7 +442,7 @@ import taos conn = taos.connect(host="127.0.0.1", user="root", password="taosdata", config="/etc/taos") c1 = conn.cursor() ``` -*host 是TDengine 服务端所有IP, config 为客户端配置文件所在目录 +* host 是TDengine 服务端所有IP, config 为客户端配置文件所在目录 * 写入数据 ```python @@ -510,17 +510,17 @@ conn.close() 用户可通过python的帮助信息直接查看模块的使用信息,或者参考tests/examples/python中的示例程序。以下为部分常用类和方法: -- _TDengineConnection_类 +- _TDengineConnection_ 类 参考python中help(taos.TDengineConnection)。 - 这个类对应客户端和TDengine建立的一个连接。在客户端多线程的场景下,这个连接实例可以是每个线程申请一个,也可以多线程共享一个连接。 + 这个类对应客户端和TDengine建立的一个连接。在客户端多线程的场景下,推荐每个线程申请一个独立的连接实例,而不建议多线程共享一个连接。 -- _TDengineCursor_类 +- _TDengineCursor_ 类 参考python中help(taos.TDengineCursor)。 这个类对应客户端进行的写入、查询操作。在客户端多线程的场景下,这个游标实例必须保持线程独享,不能夸线程共享使用,否则会导致返回结果出现错误。 -- _connect_方法 +- _connect_ 方法 用于生成taos.TDengineConnection的实例。 @@ -800,7 +800,7 @@ go env -w GOPROXY=https://goproxy.io,direct - `sql.Open(DRIVER_NAME string, dataSourceName string) *DB` - 该API用来打开DB,返回一个类型为*DB的对象,一般情况下,DRIVER_NAME设置为字符串`taosSql`, dataSourceName设置为字符串`user:password@/tcp(host:port)/dbname`,如果客户想要用多个goroutine并发访问TDengine, 那么需要在各个goroutine中分别创建一个sql.Open对象并用之访问TDengine + 该API用来打开DB,返回一个类型为\*DB的对象,一般情况下,DRIVER_NAME设置为字符串`taosSql`, dataSourceName设置为字符串`user:password@/tcp(host:port)/dbname`,如果客户想要用多个goroutine并发访问TDengine, 那么需要在各个goroutine中分别创建一个sql.Open对象并用之访问TDengine **注意**: 该API成功创建的时候,并没有做权限等检查,只有在真正执行Query或者Exec的时候才能真正的去创建连接,并同时检查user/password/host/port是不是合法。 另外,由于整个驱动程序大部分实现都下沉到taosSql所依赖的libtaos中。所以,sql.Open本身特别轻量。 @@ -822,7 +822,7 @@ go env -w GOPROXY=https://goproxy.io,direct - `func (s *Stmt) Query(args ...interface{}) (*Rows, error)` - sql.Open内置的方法,Query executes a prepared query statement with the given arguments and returns the query results as a *Rows. + sql.Open内置的方法,Query executes a prepared query statement with the given arguments and returns the query results as a \*Rows. - `func (s *Stmt) Close() error` @@ -894,7 +894,7 @@ Node-example-raw.js 验证方法: -1. 新建安装验证目录,例如:~/tdengine-test,拷贝github上nodejsChecker.js源程序。下载地址:(https://github.com/taosdata/TDengine/tree/develop/tests/examples/nodejs/nodejsChecker.js)。 +1. 新建安装验证目录,例如:\~/tdengine-test,拷贝github上nodejsChecker.js源程序。下载地址:(https://github.com/taosdata/TDengine/tree/develop/tests/examples/nodejs/nodejsChecker.js)。 2. 在命令中执行以下命令: diff --git a/documentation20/webdocs/markdowndocs/faq-ch.md b/documentation20/webdocs/markdowndocs/faq-ch.md index a085e6159a..79139078c1 100644 --- a/documentation20/webdocs/markdowndocs/faq-ch.md +++ b/documentation20/webdocs/markdowndocs/faq-ch.md @@ -1,5 +1,19 @@ # 常见问题 +## 0. 怎么报告问题? + +如果 FAQ 中的信息不能够帮到您,需要 TDengine 技术团队的技术支持与协助,请将以下两个目录中内容打包: +1. /var/log/taos (如果没有修改过默认路径) +2. /etc/taos + +附上必要的问题描述,包括使用的 TDengine 版本信息、平台环境信息、发生该问题的执行操作、出现问题的表征及大概的时间,在 GitHub提交Issue。 + +为了保证有足够的debug信息,如果问题能够重复,请修改/etc/taos/taos.cfg文件,最后面添加一行“debugFlag 135"(不带引号本身),然后重启taosd, 重复问题,然后再递交。也可以通过如下SQL语句,临时设置taosd的日志级别。 +``` + alter dnode debugFlag 135; +``` +但系统正常运行时,请一定将debugFlag设置为131,否则会产生大量的日志信息,降低系统效率。 + ## 1. TDengine2.0之前的版本升级到2.0及以上的版本应该注意什么?☆☆☆ 2.0版本在之前版本的基础上,进行了完全的重构,配置文件和数据文件是不兼容的。在升级之前务必进行如下操作: @@ -118,16 +132,8 @@ TDengine是根据hostname唯一标志一台机器的,在数据文件从机器A - 2.0.7.0 及以后的版本,到/var/lib/taos/dnode下,修复dnodeEps.json的dnodeId对应的FQDN,重启。确保机器内所有机器的此文件是完全相同的。 - 1.x 和 2.x 版本的存储结构不兼容,需要使用迁移工具或者自己开发应用导出导入数据。 -## 17. 怎么报告问题? +## 17. TDengine 是否支持删除或更新已经写入的数据? -如果 FAQ 中的信息不能够帮到您,需要 TDengine 技术团队的技术支持与协助,请将以下两个目录中内容打包: -1. /var/log/taos -2. /etc/taos +TDengine 目前尚不支持删除功能,未来根据用户需求可能会支持。 -附上必要的问题描述,以及发生该问题的执行操作,出现问题的表征及大概的时间,在 GitHub提交Issue。 - -为了保证有足够的debug信息,如果问题能够重复,请修改/etc/taos/taos.cfg文件,最后面添加一行“debugFlag 135"(不带引号本身),然后重启taosd, 重复问题,然后再递交。也可以通过如下SQL语句,临时设置taosd的日志级别。 -``` - alter dnode debugFlag 135; -``` -但系统正常运行时,请一定将debugFlag设置为131,否则会产生大量的日志信息,降低系统效率。 +从 2.0.8.0 开始,TDengine 支持更新已经写入数据的功能。使用更新功能需要在创建数据库时使用 UPDATE 1 参数,之后可以使用 INSERT INTO 命令更新已经写入的相同时间戳数据。UPDATE 参数不支持 ALTER DATABASE 命令修改。没有使用 UPDATE 1 参数创建的数据库,写入相同时间戳的数据不会修改之前的数据,也不会报错。 \ No newline at end of file diff --git a/packaging/cfg/taos.cfg b/packaging/cfg/taos.cfg index 73fa915abd..2908a8a21e 100644 --- a/packaging/cfg/taos.cfg +++ b/packaging/cfg/taos.cfg @@ -36,6 +36,9 @@ # 0.0: only one core available. # tsRatioOfQueryCores 1.0 +# the last_row/first/last aggregator will not change the original column name in the result fields +# keepColumnName 0 + # number of management nodes in the system # numOfMnodes 3 @@ -72,9 +75,6 @@ # time interval of heart beat from shell to dnode, seconds # shellActivityTimer 3 -# time of keeping table meta data in cache, seconds -# tableMetaKeepTimer 7200 - # minimum sliding window time, milli-second # minSlidingTime 10 @@ -162,10 +162,10 @@ # stop writing logs when the disk size of the log folder is less than this value # minimalLogDirGB 0.1 -# stop writing temporary files when the disk size of the log folder is less than this value +# stop writing temporary files when the disk size of the tmp folder is less than this value # minimalTmpDirGB 0.1 -# stop writing data when the disk size of the log folder is less than this value +# if disk free space is less than this value, taosd service exit directly within startup process # minimalDataDirGB 0.1 # One mnode is equal to the number of vnode consumed diff --git a/snap/snapcraft.yaml b/snap/snapcraft.yaml index c4b2039737..102fea6b9e 100644 --- a/snap/snapcraft.yaml +++ b/snap/snapcraft.yaml @@ -1,6 +1,6 @@ name: tdengine base: core18 -version: '2.0.13.0' +version: '2.0.14.0' icon: snap/gui/t-dengine.svg summary: an open-source big data platform designed and optimized for IoT. description: | @@ -72,7 +72,7 @@ parts: - usr/bin/taosd - usr/bin/taos - usr/bin/taosdemo - - usr/lib/libtaos.so.2.0.13.0 + - usr/lib/libtaos.so.2.0.14.0 - usr/lib/libtaos.so.1 - usr/lib/libtaos.so diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 931a0a132e..04bc61ed9e 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) # Base compile diff --git a/src/balance/CMakeLists.txt b/src/balance/CMakeLists.txt index 6c26e50b87..fdc43ea32f 100644 --- a/src/balance/CMakeLists.txt +++ b/src/balance/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/mnode/inc) diff --git a/src/client/CMakeLists.txt b/src/client/CMakeLists.txt index daf7c5e534..4049c0d729 100644 --- a/src/client/CMakeLists.txt +++ b/src/client/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/client/inc/tscLog.h b/src/client/inc/tscLog.h index 5273a87ea0..f25ec02bd8 100644 --- a/src/client/inc/tscLog.h +++ b/src/client/inc/tscLog.h @@ -13,8 +13,8 @@ * along with this program. If not, see . */ -#ifndef TDENGINE_TSC_LOG_H -#define TDENGINE_TSC_LOG_H +#ifndef TDENGINE_TSCLOG_H +#define TDENGINE_TSCLOG_H #ifdef __cplusplus extern "C" { @@ -22,7 +22,7 @@ extern "C" { #include "tlog.h" -extern int32_t cDebugFlag; +extern uint32_t cDebugFlag; extern int8_t tscEmbedded; #define tscFatal(...) do { if (cDebugFlag & DEBUG_FATAL) { taosPrintLog("TSC FATAL ", tscEmbedded ? 255 : cDebugFlag, __VA_ARGS__); }} while(0) diff --git a/src/client/inc/tscSubquery.h b/src/client/inc/tscSubquery.h index d3996ccf7f..7529891635 100644 --- a/src/client/inc/tscSubquery.h +++ b/src/client/inc/tscSubquery.h @@ -13,8 +13,8 @@ * along with this program. If not, see . */ -#ifndef TDENGINE_TSCJOINPROCESS_H -#define TDENGINE_TSCJOINPROCESS_H +#ifndef TDENGINE_TSCSUBQUERY_H +#define TDENGINE_TSCSUBQUERY_H #ifdef __cplusplus extern "C" { @@ -43,8 +43,13 @@ TAOS_ROW doSetResultRowData(SSqlObj *pSql); char *getArithmeticInputSrc(void *param, const char *name, int32_t colId); +void tscLockByThread(int64_t *lockedBy); + +void tscUnlockByThread(int64_t *lockedBy); + + #ifdef __cplusplus } #endif -#endif // TDENGINE_TSCJOINPROCESS_H +#endif // TDENGINE_TSCSUBQUERY_H diff --git a/src/client/inc/tscUtil.h b/src/client/inc/tscUtil.h index 8d82c65cee..633512e324 100644 --- a/src/client/inc/tscUtil.h +++ b/src/client/inc/tscUtil.h @@ -110,7 +110,7 @@ void* tscDestroyBlockArrayList(SArray* pDataBlockList); void* tscDestroyBlockHashTable(SHashObj* pBlockHashTable); int32_t tscCopyDataBlockToPayload(SSqlObj* pSql, STableDataBlocks* pDataBlock); -int32_t tscMergeTableDataBlocks(SSqlObj* pSql); +int32_t tscMergeTableDataBlocks(SSqlObj* pSql, bool freeBlockMap); int32_t tscGetDataBlockFromList(SHashObj* pHashList, int64_t id, int32_t size, int32_t startOffset, int32_t rowSize, const char* tableId, STableMeta* pTableMeta, STableDataBlocks** dataBlocks, SArray* pBlockList); @@ -256,11 +256,11 @@ void tscSVgroupInfoCopy(SVgroupInfo* dst, const SVgroupInfo* src); * @param pPrevSql * @return */ -SSqlObj* createSimpleSubObj(SSqlObj* pSql, void (*fp)(), void* param, int32_t cmd); +SSqlObj* createSimpleSubObj(SSqlObj* pSql, __async_cb_func_t fp, void* param, int32_t cmd); void registerSqlObj(SSqlObj* pSql); -SSqlObj* createSubqueryObj(SSqlObj* pSql, int16_t tableIndex, void (*fp)(), void* param, int32_t cmd, SSqlObj* pPrevSql); +SSqlObj* createSubqueryObj(SSqlObj* pSql, int16_t tableIndex, __async_cb_func_t fp, void* param, int32_t cmd, SSqlObj* pPrevSql); void addGroupInfoForSubquery(SSqlObj* pParentObj, SSqlObj* pSql, int32_t subClauseIndex, int32_t tableIndex); void doAddGroupColumnForSubquery(SQueryInfo* pQueryInfo, int32_t tagIndex); diff --git a/src/client/inc/tschemautil.h b/src/client/inc/tschemautil.h index c881a7a763..a9dcd230a6 100644 --- a/src/client/inc/tschemautil.h +++ b/src/client/inc/tschemautil.h @@ -24,10 +24,6 @@ extern "C" { #include "tstoken.h" #include "tsclient.h" -#define VALIDNUMOFCOLS(x) ((x) >= TSDB_MIN_COLUMNS && (x) <= TSDB_MAX_COLUMNS) - -#define VALIDNUMOFTAGS(x) ((x) >= 0 && (x) <= TSDB_MAX_TAGS) - /** * get the number of tags of this table * @param pTableMeta @@ -79,26 +75,6 @@ SSchema *tscGetTableColumnSchema(const STableMeta *pMeta, int32_t colIndex); */ SSchema* tscGetColumnSchemaById(STableMeta* pTableMeta, int16_t colId); -/** - * check if the schema is valid or not, including following aspects: - * 1. number of columns - * 2. column types - * 3. column length - * 4. column names - * 5. total length - * - * @param pSchema - * @param numOfCols - * @return - */ -bool isValidSchema(struct SSchema* pSchema, int32_t numOfCols, int32_t numOfTags); - -/** - * get the schema for the "tbname" column. it is a built column - * @return - */ -SSchema tscGetTbnameColumnSchema(); - /** * create the table meta from the msg * @param pTableMetaMsg diff --git a/src/client/inc/tsclient.h b/src/client/inc/tsclient.h index a3a086ce77..652e5bdd47 100644 --- a/src/client/inc/tsclient.h +++ b/src/client/inc/tsclient.h @@ -235,7 +235,7 @@ typedef struct { int32_t numOfTablesInSubmit; }; - uint32_t insertType; + uint32_t insertType; // TODO remove it int32_t clauseIndex; // index of multiple subclause query char * curSql; // current sql, resume position of sql after parsing paused @@ -300,8 +300,8 @@ typedef struct STscObj { void * pTimer; char user[TSDB_USER_LEN]; char pass[TSDB_KEY_LEN]; - char acctId[TSDB_ACCT_LEN]; - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char acctId[TSDB_ACCT_ID_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; char sversion[TSDB_VERSION_LEN]; char writeAuth : 1; char superAuth : 1; @@ -327,8 +327,8 @@ typedef struct SSqlObj { pthread_t owner; // owner of sql object, by which it is executed STscObj *pTscObj; int64_t rpcRid; - void (*fp)(); - void (*fetchFp)(); + __async_cb_func_t fp; + __async_cb_func_t fetchFp; void *param; int64_t stime; uint32_t queryId; @@ -347,6 +347,11 @@ typedef struct SSqlObj { SSubqueryState subState; struct SSqlObj **pSubs; + int64_t metaRid; + int64_t svgroupRid; + + int64_t squeryLock; + struct SSqlObj *prev, *next; int64_t self; } SSqlObj; @@ -458,7 +463,7 @@ static FORCE_INLINE void tscGetResultColumnChr(SSqlRes* pRes, SFieldInfo* pField pRes->length[columnIndex] = pInfo->pSqlExpr->param[1].nLen; pRes->tsrow[columnIndex] = (pInfo->pSqlExpr->param[1].nType == TSDB_DATA_TYPE_NULL) ? NULL : (unsigned char*)pData; } else { - assert(bytes == tDataTypeDesc[type].nSize); + assert(bytes == tDataTypes[type].bytes); pRes->tsrow[columnIndex] = isNull(pData, type) ? NULL : (unsigned char*)&pInfo->pSqlExpr->param[1].i64; pRes->length[columnIndex] = bytes; @@ -475,7 +480,7 @@ static FORCE_INLINE void tscGetResultColumnChr(SSqlRes* pRes, SFieldInfo* pField pRes->length[columnIndex] = realLen; } else { - assert(bytes == tDataTypeDesc[type].nSize); + assert(bytes == tDataTypes[type].bytes); pRes->tsrow[columnIndex] = isNull(pData, type) ? NULL : (unsigned char*)pData; pRes->length[columnIndex] = bytes; diff --git a/src/client/src/taos.def b/src/client/src/taos.def index 49d7290ce7..43cd819061 100644 --- a/src/client/src/taos.def +++ b/src/client/src/taos.def @@ -32,7 +32,6 @@ taos_errstr taos_errno taos_query_a taos_fetch_rows_a -taos_fetch_row_a taos_subscribe taos_consume taos_unsubscribe diff --git a/src/client/src/tscAsync.c b/src/client/src/tscAsync.c index b4dd8d7714..4eae2b7a87 100644 --- a/src/client/src/tscAsync.c +++ b/src/client/src/tscAsync.c @@ -20,24 +20,19 @@ #include "trpc.h" #include "tscLog.h" #include "tscSubquery.h" -#include "tscLocalMerge.h" #include "tscUtil.h" #include "tsched.h" #include "tschemautil.h" #include "tsclient.h" -static void tscProcessFetchRow(SSchedMsg *pMsg); static void tscAsyncQueryRowsForNextVnode(void *param, TAOS_RES *tres, int numOfRows); -static void tscProcessAsyncRetrieveImpl(void *param, TAOS_RES *tres, int numOfRows, void (*fp)()); - /* * Proxy function to perform sequentially query&retrieve operation. * If sql queries upon a super table and two-stage merge procedure is not involved (when employ the projection * query), it will sequentially query&retrieve data for all vnodes */ static void tscAsyncFetchRowsProxy(void *param, TAOS_RES *tres, int numOfRows); -static void tscAsyncFetchSingleRowProxy(void *param, TAOS_RES *tres, int numOfRows); void doAsyncQuery(STscObj* pObj, SSqlObj* pSql, __async_cb_func_t fp, void* param, const char* sqlstr, size_t sqlLen) { SSqlCmd* pCmd = &pSql->cmd; @@ -148,7 +143,7 @@ static void tscAsyncFetchRowsProxy(void *param, TAOS_RES *tres, int numOfRows) { } // actual continue retrieve function with user-specified callback function -static void tscProcessAsyncRetrieveImpl(void *param, TAOS_RES *tres, int numOfRows, void (*fp)()) { +static void tscProcessAsyncRetrieveImpl(void *param, TAOS_RES *tres, int numOfRows, __async_cb_func_t fp) { SSqlObj *pSql = (SSqlObj *)tres; if (pSql == NULL) { // error tscError("sql object is NULL"); @@ -191,11 +186,6 @@ static void tscAsyncQueryRowsForNextVnode(void *param, TAOS_RES *tres, int numOf tscProcessAsyncRetrieveImpl(param, tres, numOfRows, tscAsyncFetchRowsProxy); } -void tscAsyncQuerySingleRowForNextVnode(void *param, TAOS_RES *tres, int numOfRows) { - // query completed, continue to retrieve - tscProcessAsyncRetrieveImpl(param, tres, numOfRows, tscAsyncFetchSingleRowProxy); -} - void taos_fetch_rows_a(TAOS_RES *taosa, __async_cb_func_t fp, void *param) { SSqlObj *pSql = (SSqlObj *)taosa; if (pSql == NULL || pSql->signature != pSql) { @@ -263,103 +253,6 @@ void taos_fetch_rows_a(TAOS_RES *taosa, __async_cb_func_t fp, void *param) { } } -void taos_fetch_row_a(TAOS_RES *taosa, void (*fp)(void *, TAOS_RES *, TAOS_ROW), void *param) { - SSqlObj *pSql = (SSqlObj *)taosa; - if (pSql == NULL || pSql->signature != pSql) { - tscError("sql object is NULL"); - tscQueueAsyncError(fp, param, TSDB_CODE_TSC_DISCONNECTED); - return; - } - - SSqlRes *pRes = &pSql->res; - SSqlCmd *pCmd = &pSql->cmd; - - if (pRes->qhandle == 0) { - tscError("qhandle is NULL"); - pSql->param = param; - pRes->code = TSDB_CODE_TSC_INVALID_QHANDLE; - - tscAsyncResultOnError(pSql); - return; - } - - pSql->fetchFp = fp; - pSql->param = param; - - if (pRes->row >= pRes->numOfRows) { - tscResetForNextRetrieve(pRes); - pSql->fp = tscAsyncFetchSingleRowProxy; - - if (pCmd->command != TSDB_SQL_RETRIEVE_LOCALMERGE && pCmd->command < TSDB_SQL_LOCAL) { - pCmd->command = (pCmd->command > TSDB_SQL_MGMT) ? TSDB_SQL_RETRIEVE : TSDB_SQL_FETCH; - } - - tscProcessSql(pSql); - } else { - SSchedMsg schedMsg = { 0 }; - schedMsg.fp = tscProcessFetchRow; - schedMsg.ahandle = pSql; - schedMsg.thandle = pRes->tsrow; - schedMsg.msg = NULL; - taosScheduleTask(tscQhandle, &schedMsg); - } -} - -void tscAsyncFetchSingleRowProxy(void *param, TAOS_RES *tres, int numOfRows) { - SSqlObj *pSql = (SSqlObj *)tres; - SSqlRes *pRes = &pSql->res; - SSqlCmd *pCmd = &pSql->cmd; - - SQueryInfo *pQueryInfo = tscGetQueryInfoDetail(pCmd, pCmd->clauseIndex); - - if (numOfRows == 0) { - if (hasMoreVnodesToTry(pSql)) { // sequentially retrieve data from remain vnodes. - tscTryQueryNextVnode(pSql, tscAsyncQuerySingleRowForNextVnode); - } else { - /* - * 1. has reach the limitation - * 2. no remain virtual nodes to be retrieved anymore - */ - (*pSql->fetchFp)(pSql->param, pSql, NULL); - } - return; - } - - for (int i = 0; i < pCmd->numOfCols; ++i){ - SInternalField* pSup = taosArrayGet(pQueryInfo->fieldsInfo.internalField, i); - if (pSup->pSqlExpr != NULL) { -// pRes->tsrow[i] = TSC_GET_RESPTR_BASE(pRes, pQueryInfo, i) + pSup->pSqlExpr->resBytes * pRes->row; - } else { - //todo add - } - } - - pRes->row++; - - (*pSql->fetchFp)(pSql->param, pSql, pSql->res.tsrow); -} - -void tscProcessFetchRow(SSchedMsg *pMsg) { - SSqlObj *pSql = (SSqlObj *)pMsg->ahandle; - SSqlRes *pRes = &pSql->res; - SSqlCmd *pCmd = &pSql->cmd; - - SQueryInfo *pQueryInfo = tscGetQueryInfoDetail(pCmd, pCmd->clauseIndex); - - for (int i = 0; i < pCmd->numOfCols; ++i) { - SInternalField* pSup = taosArrayGet(pQueryInfo->fieldsInfo.internalField, i); - - if (pSup->pSqlExpr != NULL) { - tscGetResultColumnChr(pRes, &pQueryInfo->fieldsInfo, i, 0); - } else { -// todo add - } - } - - pRes->row++; - (*pSql->fetchFp)(pSql->param, pSql, pRes->tsrow); -} - // this function will be executed by queue task threads, so the terrno is not valid static void tscProcessAsyncError(SSchedMsg *pMsg) { void (*fp)() = pMsg->ahandle; @@ -372,7 +265,7 @@ void tscQueueAsyncError(void(*fp), void *param, int32_t code) { int32_t* c = malloc(sizeof(int32_t)); *c = code; - SSchedMsg schedMsg = { 0 }; + SSchedMsg schedMsg = {0}; schedMsg.fp = tscProcessAsyncError; schedMsg.ahandle = fp; schedMsg.thandle = param; @@ -380,7 +273,6 @@ void tscQueueAsyncError(void(*fp), void *param, int32_t code) { taosScheduleTask(tscQhandle, &schedMsg); } - void tscAsyncResultOnError(SSqlObj *pSql) { if (pSql == NULL || pSql->signature != pSql) { tscDebug("%p SqlObj is freed, not add into queue async res", pSql); @@ -402,8 +294,10 @@ void tscAsyncResultOnError(SSqlObj *pSql) { int tscSendMsgToServer(SSqlObj *pSql); void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { - SSqlObj *pSql = (SSqlObj *)param; - if (pSql == NULL || pSql->signature != pSql) return; + SSqlObj* pSql = (SSqlObj*)taosAcquireRef(tscObjRef, (int64_t)param); + if (pSql == NULL) return; + + assert(pSql->signature == pSql && (int64_t)param == pSql->self); SSqlCmd *pCmd = &pSql->cmd; SSqlRes *pRes = &pSql->res; @@ -428,7 +322,8 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { code = tscGetTableMeta(pSql, pTableMetaInfo); assert(code == TSDB_CODE_TSC_ACTION_IN_PROGRESS || code == TSDB_CODE_SUCCESS); - if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } @@ -436,6 +331,7 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { // tscProcessSql can add error into async res tscProcessSql(pSql); + taosReleaseRef(tscObjRef, pSql->self); return; } else { // continue to process normal async query if (pCmd->parseFinished) { @@ -446,6 +342,7 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { assert(code == TSDB_CODE_TSC_ACTION_IN_PROGRESS || code == TSDB_CODE_SUCCESS); if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } @@ -458,6 +355,7 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { code = tsParseSql(pSql, true); if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } else if (code != TSDB_CODE_SUCCESS) { goto _error; @@ -468,12 +366,14 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { tscProcessSql(pSql); } + taosReleaseRef(tscObjRef, pSql->self); return; } else { tscDebug("%p continue parse sql after get table meta", pSql); code = tsParseSql(pSql, false); if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } else if (code != TSDB_CODE_SUCCESS) { goto _error; @@ -483,12 +383,14 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { STableMetaInfo* pTableMetaInfo = tscGetTableMetaInfoFromCmd(pCmd, pCmd->clauseIndex, 0); code = tscGetTableMeta(pSql, pTableMetaInfo); if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } else { assert(code == TSDB_CODE_SUCCESS); } (*pSql->fp)(pSql->param, pSql, code); + taosReleaseRef(tscObjRef, pSql->self); return; } @@ -501,6 +403,7 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { code = tscGetTableMeta(pSql, pTableMetaInfo); if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } else if (code != TSDB_CODE_SUCCESS) { goto _error; @@ -509,6 +412,7 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { if (UTIL_TABLE_IS_SUPER_TABLE(pTableMetaInfo)) { code = tscGetSTableVgroupInfo(pSql, pCmd->clauseIndex); if (code == TSDB_CODE_TSC_ACTION_IN_PROGRESS) { + taosReleaseRef(tscObjRef, pSql->self); return; } else if (code != TSDB_CODE_SUCCESS) { goto _error; @@ -521,10 +425,16 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { } (*pSql->fp)(pSql->param, pSql, code); + + taosReleaseRef(tscObjRef, pSql->self); + return; } tscDoQuery(pSql); + + taosReleaseRef(tscObjRef, pSql->self); + return; _error: @@ -532,4 +442,6 @@ void tscTableMetaCallBack(void *param, TAOS_RES *res, int code) { pSql->res.code = code; tscAsyncResultOnError(pSql); } + + taosReleaseRef(tscObjRef, pSql->self); } diff --git a/src/client/src/tscLocal.c b/src/client/src/tscLocal.c index 48380f8641..599fa86460 100644 --- a/src/client/src/tscLocal.c +++ b/src/client/src/tscLocal.c @@ -79,7 +79,7 @@ static int32_t tscSetValueToResObj(SSqlObj *pSql, int32_t rowLen) { char* dst = pRes->data + tscFieldInfoGetOffset(pQueryInfo, 0) * totalNumOfRows + pField->bytes * i; STR_WITH_MAXSIZE_TO_VARSTR(dst, pSchema[i].name, pField->bytes); - char *type = tDataTypeDesc[pSchema[i].type].aName; + char *type = tDataTypes[pSchema[i].type].name; pField = tscFieldInfoGetField(&pQueryInfo->fieldsInfo, 1); dst = pRes->data + tscFieldInfoGetOffset(pQueryInfo, 1) * totalNumOfRows + pField->bytes * i; @@ -119,7 +119,7 @@ static int32_t tscSetValueToResObj(SSqlObj *pSql, int32_t rowLen) { // type name pField = tscFieldInfoGetField(&pQueryInfo->fieldsInfo, 1); - char *type = tDataTypeDesc[pSchema[i].type].aName; + char *type = tDataTypes[pSchema[i].type].name; output = pRes->data + tscFieldInfoGetOffset(pQueryInfo, 1) * totalNumOfRows + pField->bytes * i; STR_WITH_MAXSIZE_TO_VARSTR(output, type, pField->bytes); @@ -619,9 +619,9 @@ static int32_t tscRebuildDDLForNormalTable(SSqlObj *pSql, const char *tableName, if (type == TSDB_DATA_TYPE_NCHAR) { bytes = bytes/TSDB_NCHAR_SIZE; } - snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s(%d),", pSchema[i].name, tDataTypeDesc[pSchema[i].type].aName, bytes); + snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s(%d),", pSchema[i].name, tDataTypes[pSchema[i].type].name, bytes); } else { - snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s,", pSchema[i].name, tDataTypeDesc[pSchema[i].type].aName); + snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s,", pSchema[i].name, tDataTypes[pSchema[i].type].name); } } sprintf(result + strlen(result) - 1, "%s", ")"); @@ -646,9 +646,9 @@ static int32_t tscRebuildDDLForSuperTable(SSqlObj *pSql, const char *tableName, if (type == TSDB_DATA_TYPE_NCHAR) { bytes = bytes/TSDB_NCHAR_SIZE; } - snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result),"%s %s(%d),", pSchema[i].name,tDataTypeDesc[pSchema[i].type].aName, bytes); + snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result),"%s %s(%d),", pSchema[i].name,tDataTypes[pSchema[i].type].name, bytes); } else { - snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s,", pSchema[i].name, tDataTypeDesc[type].aName); + snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s,", pSchema[i].name, tDataTypes[type].name); } } snprintf(result + strlen(result) - 1, TSDB_MAX_BINARY_LEN - strlen(result), "%s %s", ")", "TAGS ("); @@ -660,9 +660,9 @@ static int32_t tscRebuildDDLForSuperTable(SSqlObj *pSql, const char *tableName, if (type == TSDB_DATA_TYPE_NCHAR) { bytes = bytes/TSDB_NCHAR_SIZE; } - snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s(%d),", pSchema[i].name,tDataTypeDesc[pSchema[i].type].aName, bytes); + snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s(%d),", pSchema[i].name,tDataTypes[pSchema[i].type].name, bytes); } else { - snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s,", pSchema[i].name, tDataTypeDesc[type].aName); + snprintf(result + strlen(result), TSDB_MAX_BINARY_LEN - strlen(result), "%s %s,", pSchema[i].name, tDataTypes[type].name); } } sprintf(result + strlen(result) - 1, "%s", ")"); diff --git a/src/client/src/tscLocalMerge.c b/src/client/src/tscLocalMerge.c index 4aa751574c..6280cc520a 100644 --- a/src/client/src/tscLocalMerge.c +++ b/src/client/src/tscLocalMerge.c @@ -979,14 +979,13 @@ static void doFillResult(SSqlObj *pSql, SLocalReducer *pLocalReducer, bool doneO pQueryInfo->limit.offset -= newRows; pRes->numOfRows = 0; - int32_t rpoints = taosNumOfRemainRows(pFillInfo); - if (rpoints <= 0) { + if (!taosFillHasMoreResults(pFillInfo)) { if (!doneOutput) { // reduce procedure has not completed yet, but current results for fill are exhausted break; } // all output in current group are completed - int32_t totalRemainRows = (int32_t)getNumOfResWithFill(pFillInfo, actualETime, pLocalReducer->resColModel->capacity); + int32_t totalRemainRows = (int32_t)getNumOfResultsAfterFillGap(pFillInfo, actualETime, pLocalReducer->resColModel->capacity); if (totalRemainRows <= 0) { break; } @@ -1337,14 +1336,14 @@ static bool doBuildFilledResultForGroup(SSqlObj *pSql) { SLocalReducer *pLocalReducer = pRes->pLocalReducer; SFillInfo *pFillInfo = pLocalReducer->pFillInfo; - if (pFillInfo != NULL && taosNumOfRemainRows(pFillInfo) > 0) { + if (pFillInfo != NULL && taosFillHasMoreResults(pFillInfo)) { assert(pQueryInfo->fillType != TSDB_FILL_NONE); tFilePage *pFinalDataBuf = pLocalReducer->pResultBuf; int64_t etime = *(int64_t *)(pFinalDataBuf->data + TSDB_KEYSIZE * (pFillInfo->numOfRows - 1)); // the first column must be the timestamp column - int32_t rows = (int32_t) getNumOfResWithFill(pFillInfo, etime, pLocalReducer->resColModel->capacity); + int32_t rows = (int32_t) getNumOfResultsAfterFillGap(pFillInfo, etime, pLocalReducer->resColModel->capacity); if (rows > 0) { // do fill gap doFillResult(pSql, pLocalReducer, false); } @@ -1373,7 +1372,7 @@ static bool doHandleLastRemainData(SSqlObj *pSql) { ((pRes->numOfRowsGroup < pQueryInfo->limit.limit && pQueryInfo->limit.limit > 0) || (pQueryInfo->limit.limit < 0))) { int64_t etime = (pQueryInfo->order.order == TSDB_ORDER_ASC)? pQueryInfo->window.ekey : pQueryInfo->window.skey; - int32_t rows = (int32_t)getNumOfResWithFill(pFillInfo, etime, pLocalReducer->resColModel->capacity); + int32_t rows = (int32_t)getNumOfResultsAfterFillGap(pFillInfo, etime, pLocalReducer->resColModel->capacity); if (rows > 0) { doFillResult(pSql, pLocalReducer, true); } diff --git a/src/client/src/tscParseInsert.c b/src/client/src/tscParseInsert.c index dbb807ad06..0c7af5d4e3 100644 --- a/src/client/src/tscParseInsert.c +++ b/src/client/src/tscParseInsert.c @@ -762,6 +762,8 @@ static int32_t tscCheckIfCreateTable(char **sqlstr, SSqlObj *pSql) { char *sql = *sqlstr; + pSql->cmd.autoCreated = false; + // get the token of specified table index = 0; tableToken = tStrGetToken(sql, &index, false, 0, NULL); @@ -945,11 +947,15 @@ static int32_t tscCheckIfCreateTable(char **sqlstr, SSqlObj *pSql) { SKVRow row = tdGetKVRowFromBuilder(&kvRowBuilder); tdDestroyKVRowBuilder(&kvRowBuilder); if (row == NULL) { - return TSDB_CODE_TSC_OUT_OF_MEMORY; + return tscInvalidSQLErrMsg(pCmd->payload, "tag value expected", NULL); } tdSortKVRowByColIdx(row); pCmd->tagData.dataLen = kvRowLen(row); + if (pCmd->tagData.dataLen <= 0){ + return tscInvalidSQLErrMsg(pCmd->payload, "tag value expected", NULL); + } + char* pTag = realloc(pCmd->tagData.data, pCmd->tagData.dataLen); if (pTag == NULL) { return TSDB_CODE_TSC_OUT_OF_MEMORY; @@ -1275,7 +1281,7 @@ int tsParseInsertSql(SSqlObj *pSql) { } if (taosHashGetSize(pCmd->pTableBlockHashList) > 0) { // merge according to vgId - if ((code = tscMergeTableDataBlocks(pSql)) != TSDB_CODE_SUCCESS) { + if ((code = tscMergeTableDataBlocks(pSql, true)) != TSDB_CODE_SUCCESS) { goto _clean; } } @@ -1330,15 +1336,6 @@ int tsParseSql(SSqlObj *pSql, bool initial) { } if (tscIsInsertData(pSql->sqlstr)) { - /* - * Set the fp before parse the sql string, in case of getTableMeta failed, in which - * the error handle callback function can rightfully restore the user-defined callback function (fp). - */ - if (initial && (pSql->cmd.insertType != TSDB_QUERY_TYPE_STMT_INSERT)) { - pSql->fetchFp = pSql->fp; - pSql->fp = (void(*)())tscHandleMultivnodeInsert; - } - if (initial && ((ret = tsInsertInitialCheck(pSql)) != TSDB_CODE_SUCCESS)) { return ret; } @@ -1392,7 +1389,7 @@ static int doPackSendDataBlock(SSqlObj *pSql, int32_t numOfRows, STableDataBlock return tscInvalidSQLErrMsg(pCmd->payload, "too many rows in sql, total number of rows should be less than 32767", NULL); } - if ((code = tscMergeTableDataBlocks(pSql)) != TSDB_CODE_SUCCESS) { + if ((code = tscMergeTableDataBlocks(pSql, true)) != TSDB_CODE_SUCCESS) { return code; } diff --git a/src/client/src/tscPrepare.c b/src/client/src/tscPrepare.c index 981b354c8a..7c69c16b04 100644 --- a/src/client/src/tscPrepare.c +++ b/src/client/src/tscPrepare.c @@ -255,7 +255,6 @@ static char* normalStmtBuildSql(STscStmt* stmt) { //////////////////////////////////////////////////////////////////////////////// // functions for insertion statement preparation - static int doBindParam(char* data, SParamInfo* param, TAOS_BIND* bind) { if (bind->is_null != NULL && *(bind->is_null)) { setNull(data + param->offset, param->type, param->bytes); @@ -697,71 +696,52 @@ static int doBindParam(char* data, SParamInfo* param, TAOS_BIND* bind) { static int insertStmtBindParam(STscStmt* stmt, TAOS_BIND* bind) { SSqlCmd* pCmd = &stmt->pSql->cmd; - int32_t alloced = 1, binded = 0; - if (pCmd->batchSize > 0) { - alloced = (pCmd->batchSize + 1) / 2; - binded = pCmd->batchSize / 2; + STableMetaInfo* pTableMetaInfo = tscGetTableMetaInfoFromCmd(pCmd, 0, 0); + + STableMeta* pTableMeta = pTableMetaInfo->pTableMeta; + if (pCmd->pTableBlockHashList == NULL) { + pCmd->pTableBlockHashList = taosHashInit(16, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BIGINT), true, false); } - size_t size = taosArrayGetSize(pCmd->pDataBlocks); - for (int32_t i = 0; i < size; ++i) { - STableDataBlocks* pBlock = taosArrayGetP(pCmd->pDataBlocks, i); - uint32_t totalDataSize = pBlock->size - sizeof(SSubmitBlk); - uint32_t dataSize = totalDataSize / alloced; - assert(dataSize * alloced == totalDataSize); + STableDataBlocks* pBlock = NULL; - if (alloced == binded) { - totalDataSize += dataSize + sizeof(SSubmitBlk); - if (totalDataSize > pBlock->nAllocSize) { - const double factor = 1.5; - void* tmp = realloc(pBlock->pData, (uint32_t)(totalDataSize * factor)); - if (tmp == NULL) { - return TSDB_CODE_TSC_OUT_OF_MEMORY; - } - pBlock->pData = (char*)tmp; - pBlock->nAllocSize = (uint32_t)(totalDataSize * factor); - } + int32_t ret = + tscGetDataBlockFromList(pCmd->pTableBlockHashList, pTableMeta->id.uid, TSDB_PAYLOAD_SIZE, sizeof(SSubmitBlk), + pTableMeta->tableInfo.rowSize, pTableMetaInfo->name, pTableMeta, &pBlock, NULL); + if (ret != 0) { + // todo handle error + } + + uint32_t totalDataSize = sizeof(SSubmitBlk) + pCmd->batchSize * pBlock->rowSize; + if (totalDataSize > pBlock->nAllocSize) { + const double factor = 1.5; + + void* tmp = realloc(pBlock->pData, (uint32_t)(totalDataSize * factor)); + if (tmp == NULL) { + return TSDB_CODE_TSC_OUT_OF_MEMORY; } - char* data = pBlock->pData + sizeof(SSubmitBlk) + dataSize * binded; - for (uint32_t j = 0; j < pBlock->numOfParams; ++j) { - SParamInfo* param = pBlock->params + j; - int code = doBindParam(data, param, bind + param->idx); - if (code != TSDB_CODE_SUCCESS) { - tscDebug("param %d: type mismatch or invalid", param->idx); - return code; - } + pBlock->pData = (char*)tmp; + pBlock->nAllocSize = (uint32_t)(totalDataSize * factor); + } + + char* data = pBlock->pData + sizeof(SSubmitBlk) + pBlock->rowSize * pCmd->batchSize; + for (uint32_t j = 0; j < pBlock->numOfParams; ++j) { + SParamInfo* param = &pBlock->params[j]; + + int code = doBindParam(data, param, &bind[param->idx]); + if (code != TSDB_CODE_SUCCESS) { + tscDebug("param %d: type mismatch or invalid", param->idx); + return code; } } - // actual work of all data blocks is done, update block size and numOfRows. - // note we don't do this block by block during the binding process, because - // we cannot recover if something goes wrong. - pCmd->batchSize = binded * 2 + 1; - - if (binded < alloced) { - return TSDB_CODE_SUCCESS; - } - - size_t total = taosArrayGetSize(pCmd->pDataBlocks); - for (int32_t i = 0; i < total; ++i) { - STableDataBlocks* pBlock = taosArrayGetP(pCmd->pDataBlocks, i); - - uint32_t totalDataSize = pBlock->size - sizeof(SSubmitBlk); - pBlock->size += totalDataSize / alloced; - - SSubmitBlk* pSubmit = (SSubmitBlk*)pBlock->pData; - pSubmit->numOfRows += pSubmit->numOfRows / alloced; - } - return TSDB_CODE_SUCCESS; } static int insertStmtAddBatch(STscStmt* stmt) { SSqlCmd* pCmd = &stmt->pSql->cmd; - if ((pCmd->batchSize % 2) == 1) { - ++pCmd->batchSize; - } + ++pCmd->batchSize; return TSDB_CODE_SUCCESS; } @@ -793,50 +773,66 @@ static int insertStmtExecute(STscStmt* stmt) { if (pCmd->batchSize == 0) { return TSDB_CODE_TSC_INVALID_VALUE; } - if ((pCmd->batchSize % 2) == 1) { - ++pCmd->batchSize; - } - STableMetaInfo* pTableMetaInfo = tscGetTableMetaInfoFromCmd(pCmd, pCmd->clauseIndex, 0); assert(pCmd->numOfClause == 1); - - if (taosHashGetSize(pCmd->pTableBlockHashList) > 0) { - // merge according to vgid - int code = tscMergeTableDataBlocks(stmt->pSql); - if (code != TSDB_CODE_SUCCESS) { - return code; - } - - STableDataBlocks *pDataBlock = taosArrayGetP(pCmd->pDataBlocks, 0); - code = tscCopyDataBlockToPayload(stmt->pSql, pDataBlock); - if (code != TSDB_CODE_SUCCESS) { - return code; - } - - // set the next sent data vnode index in data block arraylist - pTableMetaInfo->vgroupIndex = 1; - } else { - pCmd->pDataBlocks = tscDestroyBlockArrayList(pCmd->pDataBlocks); + if (taosHashGetSize(pCmd->pTableBlockHashList) == 0) { + return TSDB_CODE_SUCCESS; } - SSqlObj *pSql = stmt->pSql; - SSqlRes *pRes = &pSql->res; - pRes->numOfRows = 0; + STableMetaInfo* pTableMetaInfo = tscGetTableMetaInfoFromCmd(pCmd, 0, 0); + + STableMeta* pTableMeta = pTableMetaInfo->pTableMeta; + if (pCmd->pTableBlockHashList == NULL) { + pCmd->pTableBlockHashList = taosHashInit(16, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BIGINT), true, false); + } + + STableDataBlocks* pBlock = NULL; + + int32_t ret = + tscGetDataBlockFromList(pCmd->pTableBlockHashList, pTableMeta->id.uid, TSDB_PAYLOAD_SIZE, sizeof(SSubmitBlk), + pTableMeta->tableInfo.rowSize, pTableMetaInfo->name, pTableMeta, &pBlock, NULL); + assert(ret == 0); + pBlock->size = sizeof(SSubmitBlk) + pCmd->batchSize * pBlock->rowSize; + SSubmitBlk* pBlk = (SSubmitBlk*) pBlock->pData; + pBlk->numOfRows = pCmd->batchSize; + pBlk->dataLen = 0; + pBlk->uid = pTableMeta->id.uid; + pBlk->tid = pTableMeta->id.tid; + + int code = tscMergeTableDataBlocks(stmt->pSql, false); + if (code != TSDB_CODE_SUCCESS) { + return code; + } + + STableDataBlocks* pDataBlock = taosArrayGetP(pCmd->pDataBlocks, 0); + code = tscCopyDataBlockToPayload(stmt->pSql, pDataBlock); + if (code != TSDB_CODE_SUCCESS) { + return code; + } + + SSqlObj* pSql = stmt->pSql; + SSqlRes* pRes = &pSql->res; + pRes->numOfRows = 0; pRes->numOfTotal = 0; - pRes->numOfClauseTotal = 0; - pRes->qhandle = 0; - - pSql->cmd.insertType = 0; - pSql->fetchFp = waitForQueryRsp; - pSql->fp = (void(*)())tscHandleMultivnodeInsert; - - tscDoQuery(pSql); + tscProcessSql(pSql); // wait for the callback function to post the semaphore tsem_wait(&pSql->rspSem); - return pSql->res.code; + // data block reset + pCmd->batchSize = 0; + for(int32_t i = 0; i < pCmd->numOfTables; ++i) { + if (pCmd->pTableNameList && pCmd->pTableNameList[i]) { + tfree(pCmd->pTableNameList[i]); + } + } + + pCmd->numOfTables = 0; + tfree(pCmd->pTableNameList); + pCmd->pDataBlocks = tscDestroyBlockArrayList(pCmd->pDataBlocks); + + return pSql->res.code; } //////////////////////////////////////////////////////////////////////////////// @@ -867,11 +863,11 @@ TAOS_STMT* taos_stmt_init(TAOS* taos) { } tsem_init(&pSql->rspSem, 0, 0); - pSql->signature = pSql; - pSql->pTscObj = pObj; - pSql->maxRetry = TSDB_MAX_REPLICA; + pSql->signature = pSql; + pSql->pTscObj = pObj; + pSql->maxRetry = TSDB_MAX_REPLICA; + pStmt->pSql = pSql; - pStmt->pSql = pSql; return pStmt; } @@ -890,7 +886,9 @@ int taos_stmt_prepare(TAOS_STMT* stmt, const char* sql, unsigned long length) { SSqlRes *pRes = &pSql->res; pSql->param = (void*) pSql; pSql->fp = waitForQueryRsp; - pSql->cmd.insertType = TSDB_QUERY_TYPE_STMT_INSERT; + pSql->fetchFp = waitForQueryRsp; + + pCmd->insertType = TSDB_QUERY_TYPE_STMT_INSERT; if (TSDB_CODE_SUCCESS != tscAllocPayload(pCmd, TSDB_DEFAULT_PAYLOAD_SIZE)) { tscError("%p failed to malloc payload buffer", pSql); @@ -956,8 +954,9 @@ int taos_stmt_bind_param(TAOS_STMT* stmt, TAOS_BIND* bind) { STscStmt* pStmt = (STscStmt*)stmt; if (pStmt->isInsert) { return insertStmtBindParam(pStmt, bind); + } else { + return normalStmtBindParam(pStmt, bind); } - return normalStmtBindParam(pStmt, bind); } int taos_stmt_add_batch(TAOS_STMT* stmt) { @@ -981,7 +980,7 @@ int taos_stmt_execute(TAOS_STMT* stmt) { STscStmt* pStmt = (STscStmt*)stmt; if (pStmt->isInsert) { ret = insertStmtExecute(pStmt); - } else { + } else { // normal stmt query char* sql = normalStmtBuildSql(pStmt); if (sql == NULL) { ret = TSDB_CODE_TSC_OUT_OF_MEMORY; @@ -995,6 +994,7 @@ int taos_stmt_execute(TAOS_STMT* stmt) { free(sql); } } + return ret; } diff --git a/src/client/src/tscSQLParser.c b/src/client/src/tscSQLParser.c index b3fb1c2d77..64268124da 100644 --- a/src/client/src/tscSQLParser.c +++ b/src/client/src/tscSQLParser.c @@ -221,7 +221,7 @@ static int32_t handlePassword(SSqlCmd* pCmd, SStrToken* pPwd) { return invalidSqlErrMsg(tscGetErrorMsgPayload(pCmd), msg1); } - if (pPwd->n >= TSDB_PASSWORD_LEN) { + if (pPwd->n >= TSDB_KEY_LEN) { return invalidSqlErrMsg(tscGetErrorMsgPayload(pCmd), msg2); } @@ -229,7 +229,7 @@ static int32_t handlePassword(SSqlCmd* pCmd, SStrToken* pPwd) { } int32_t tscToSQLCmd(SSqlObj* pSql, struct SSqlInfo* pInfo) { - if (pInfo == NULL || pSql == NULL || pSql->signature != pSql) { + if (pInfo == NULL || pSql == NULL) { return TSDB_CODE_TSC_APP_ERROR; } @@ -642,7 +642,11 @@ int32_t tscToSQLCmd(SSqlObj* pSql, struct SSqlInfo* pInfo) { } pSql->cmd.parseFinished = 1; - return tscBuildMsg[pCmd->command](pSql, pInfo); + if (tscBuildMsg[pCmd->command] != NULL) { + return tscBuildMsg[pCmd->command](pSql, pInfo); + } else { + return invalidSqlErrMsg(tscGetErrorMsgPayload(pCmd), "not support sql expression"); + } } /* @@ -1242,7 +1246,7 @@ int32_t setObjFullName(char* fullName, const char* account, SStrToken* pDB, SStr /* db name is not specified, the tableName dose not include db name */ if (pDB != NULL) { - if (pDB->n >= TSDB_ACCT_LEN + TSDB_DB_NAME_LEN || pDB->n == 0) { + if (pDB->n >= TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN || pDB->n == 0) { return TSDB_CODE_TSC_INVALID_SQL; } @@ -1738,7 +1742,7 @@ static int32_t setExprInfoForFunctions(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, SS return -1; } else { type = TSDB_DATA_TYPE_DOUBLE; - bytes = tDataTypeDesc[type].nSize; + bytes = tDataTypes[type].bytes; } } else { type = pSchema->type; @@ -1844,7 +1848,7 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col } index = (SColumnIndex){0, PRIMARYKEY_TIMESTAMP_COL_INDEX}; - int32_t size = tDataTypeDesc[TSDB_DATA_TYPE_BIGINT].nSize; + int32_t size = tDataTypes[TSDB_DATA_TYPE_BIGINT].bytes; pExpr = tscSqlExprAppend(pQueryInfo, functionID, &index, TSDB_DATA_TYPE_BIGINT, size, getNewResColId(pQueryInfo), size, false); } else if (sqlOptr == TK_INTEGER) { // select count(1) from table1 char buf[8] = {0}; @@ -1856,7 +1860,7 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col } if (val == 1) { index = (SColumnIndex){0, PRIMARYKEY_TIMESTAMP_COL_INDEX}; - int32_t size = tDataTypeDesc[TSDB_DATA_TYPE_BIGINT].nSize; + int32_t size = tDataTypes[TSDB_DATA_TYPE_BIGINT].bytes; pExpr = tscSqlExprAppend(pQueryInfo, functionID, &index, TSDB_DATA_TYPE_BIGINT, size, getNewResColId(pQueryInfo), size, false); } else { return invalidSqlErrMsg(tscGetErrorMsgPayload(pCmd), msg3); @@ -1876,12 +1880,12 @@ int32_t addExprAndResultField(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, int32_t col isTag = true; } - int32_t size = tDataTypeDesc[TSDB_DATA_TYPE_BIGINT].nSize; + int32_t size = tDataTypes[TSDB_DATA_TYPE_BIGINT].bytes; pExpr = tscSqlExprAppend(pQueryInfo, functionID, &index, TSDB_DATA_TYPE_BIGINT, size, getNewResColId(pQueryInfo), size, isTag); } } else { // count(*) is equalled to count(primary_timestamp_key) index = (SColumnIndex){0, PRIMARYKEY_TIMESTAMP_COL_INDEX}; - int32_t size = tDataTypeDesc[TSDB_DATA_TYPE_BIGINT].nSize; + int32_t size = tDataTypes[TSDB_DATA_TYPE_BIGINT].bytes; pExpr = tscSqlExprAppend(pQueryInfo, functionID, &index, TSDB_DATA_TYPE_BIGINT, size, getNewResColId(pQueryInfo), size, false); } @@ -4510,6 +4514,8 @@ int32_t parseFillClause(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, SQuerySQL* pQuery } } else if (strncasecmp(pItem->pVar.pz, "prev", 4) == 0 && pItem->pVar.nLen == 4) { pQueryInfo->fillType = TSDB_FILL_PREV; + } else if (strncasecmp(pItem->pVar.pz, "next", 4) == 0 && pItem->pVar.nLen == 4) { + pQueryInfo->fillType = TSDB_FILL_NEXT; } else if (strncasecmp(pItem->pVar.pz, "linear", 6) == 0 && pItem->pVar.nLen == 6) { pQueryInfo->fillType = TSDB_FILL_LINEAR; } else if (strncasecmp(pItem->pVar.pz, "value", 5) == 0 && pItem->pVar.nLen == 5) { @@ -4869,7 +4875,7 @@ int32_t setAlterTableInfo(SSqlObj* pSql, struct SSqlInfo* pInfo) { char name1[128] = {0}; strncpy(name1, pItem->pVar.pz, pItem->pVar.nLen); - TAOS_FIELD f = tscCreateField(TSDB_DATA_TYPE_INT, name1, tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize); + TAOS_FIELD f = tscCreateField(TSDB_DATA_TYPE_INT, name1, tDataTypes[TSDB_DATA_TYPE_INT].bytes); tscFieldInfoAppend(&pQueryInfo->fieldsInfo, &f); } else if (pAlterSQL->type == TSDB_ALTER_TABLE_CHANGE_TAG_COLUMN) { SArray* pVarList = pAlterSQL->varList; @@ -4905,14 +4911,14 @@ int32_t setAlterTableInfo(SSqlObj* pSql, struct SSqlInfo* pInfo) { char name[TSDB_COL_NAME_LEN] = {0}; strncpy(name, pItem->pVar.pz, pItem->pVar.nLen); - TAOS_FIELD f = tscCreateField(TSDB_DATA_TYPE_INT, name, tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize); + TAOS_FIELD f = tscCreateField(TSDB_DATA_TYPE_INT, name, tDataTypes[TSDB_DATA_TYPE_INT].bytes); tscFieldInfoAppend(&pQueryInfo->fieldsInfo, &f); pItem = taosArrayGet(pVarList, 1); memset(name, 0, tListLen(name)); strncpy(name, pItem->pVar.pz, pItem->pVar.nLen); - f = tscCreateField(TSDB_DATA_TYPE_INT, name, tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize); + f = tscCreateField(TSDB_DATA_TYPE_INT, name, tDataTypes[TSDB_DATA_TYPE_INT].bytes); tscFieldInfoAppend(&pQueryInfo->fieldsInfo, &f); } else if (pAlterSQL->type == TSDB_ALTER_TABLE_UPDATE_TAG_VAL) { // Note: update can only be applied to table not super table. @@ -4987,7 +4993,7 @@ int32_t setAlterTableInfo(SSqlObj* pSql, struct SSqlInfo* pInfo) { int32_t len = 0; if (pTagsSchema->type != TSDB_DATA_TYPE_BINARY && pTagsSchema->type != TSDB_DATA_TYPE_NCHAR) { - len = tDataTypeDesc[pTagsSchema->type].nSize; + len = tDataTypes[pTagsSchema->type].bytes; } else { len = varDataTLen(pUpdateMsg->data + schemaLen); } @@ -5034,7 +5040,7 @@ int32_t setAlterTableInfo(SSqlObj* pSql, struct SSqlInfo* pInfo) { char name1[TSDB_COL_NAME_LEN] = {0}; tstrncpy(name1, pItem->pVar.pz, sizeof(name1)); - TAOS_FIELD f = tscCreateField(TSDB_DATA_TYPE_INT, name1, tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize); + TAOS_FIELD f = tscCreateField(TSDB_DATA_TYPE_INT, name1, tDataTypes[TSDB_DATA_TYPE_INT].bytes); tscFieldInfoAppend(&pQueryInfo->fieldsInfo, &f); } @@ -5997,7 +6003,7 @@ int32_t doLocalQueryProcess(SSqlCmd* pCmd, SQueryInfo* pQueryInfo, SQuerySQL* pQ SColumnIndex ind = {0}; SSqlExpr* pExpr1 = tscSqlExprAppend(pQueryInfo, TSDB_FUNC_TAG_DUMMY, &ind, TSDB_DATA_TYPE_INT, - tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize, getNewResColId(pQueryInfo), tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize, false); + tDataTypes[TSDB_DATA_TYPE_INT].bytes, getNewResColId(pQueryInfo), tDataTypes[TSDB_DATA_TYPE_INT].bytes, false); const char* name = (pExprList->a[0].aliasName != NULL)? pExprList->a[0].aliasName:functionsInfo[index].name; tstrncpy(pExpr1->aliasName, name, tListLen(pExpr1->aliasName)); @@ -6101,7 +6107,9 @@ void tscPrintSelectClause(SSqlObj* pSql, int32_t subClauseIndex) { int32_t tmpLen = 0; tmpLen = sprintf(tmpBuf, "%s(uid:%" PRId64 ", %d)", aAggs[pExpr->functionId].aName, pExpr->uid, pExpr->colInfo.colId); - if (tmpLen + offset > totalBufSize) break; + + if (tmpLen + offset >= totalBufSize - 1) break; + offset += sprintf(str + offset, "%s", tmpBuf); @@ -6110,7 +6118,9 @@ void tscPrintSelectClause(SSqlObj* pSql, int32_t subClauseIndex) { } } + assert(offset < totalBufSize); str[offset] = ']'; + assert(offset < totalBufSize); tscDebug("%p select clause:%s", pSql, str); } diff --git a/src/client/src/tscSchemaUtil.c b/src/client/src/tscSchemaUtil.c index 123f0fd222..47c3cd9716 100644 --- a/src/client/src/tscSchemaUtil.c +++ b/src/client/src/tscSchemaUtil.c @@ -66,68 +66,6 @@ STableComInfo tscGetTableInfo(const STableMeta* pTableMeta) { return pTableMeta->tableInfo; } -static bool doValidateSchema(SSchema* pSchema, int32_t numOfCols, int32_t maxLen) { - int32_t rowLen = 0; - - for (int32_t i = 0; i < numOfCols; ++i) { - // 1. valid types - if (!isValidDataType(pSchema[i].type)) { - return false; - } - - // 2. valid length for each type - if (pSchema[i].type == TSDB_DATA_TYPE_BINARY) { - if (pSchema[i].bytes > TSDB_MAX_BINARY_LEN) { - return false; - } - } else if (pSchema[i].type == TSDB_DATA_TYPE_NCHAR) { - if (pSchema[i].bytes > TSDB_MAX_NCHAR_LEN) { - return false; - } - } else { - if (pSchema[i].bytes != tDataTypeDesc[pSchema[i].type].nSize) { - return false; - } - } - - // 3. valid column names - for (int32_t j = i + 1; j < numOfCols; ++j) { - if (strncasecmp(pSchema[i].name, pSchema[j].name, sizeof(pSchema[i].name) - 1) == 0) { - return false; - } - } - - rowLen += pSchema[i].bytes; - } - - return rowLen <= maxLen; -} - -bool isValidSchema(struct SSchema* pSchema, int32_t numOfCols, int32_t numOfTags) { - if (!VALIDNUMOFCOLS(numOfCols)) { - return false; - } - - if (!VALIDNUMOFTAGS(numOfTags)) { - return false; - } - - /* first column must be the timestamp, which is a primary key */ - if (pSchema[0].type != TSDB_DATA_TYPE_TIMESTAMP) { - return false; - } - - if (!doValidateSchema(pSchema, numOfCols, TSDB_MAX_BYTES_PER_ROW)) { - return false; - } - - if (!doValidateSchema(&pSchema[numOfCols], numOfTags, TSDB_MAX_TAGS_LEN)) { - return false; - } - - return true; -} - SSchema* tscGetTableColumnSchema(const STableMeta* pTableMeta, int32_t colIndex) { assert(pTableMeta != NULL); diff --git a/src/client/src/tscServer.c b/src/client/src/tscServer.c index cc2621958f..537e81413f 100644 --- a/src/client/src/tscServer.c +++ b/src/client/src/tscServer.c @@ -25,8 +25,6 @@ #include "ttimer.h" #include "tlockfree.h" -///SRpcCorEpSet tscMgmtEpSet; - int (*tscBuildMsg[TSDB_SQL_MAX])(SSqlObj *pSql, SSqlInfo *pInfo) = {0}; int (*tscProcessMsgRsp[TSDB_SQL_MAX])(SSqlObj *pSql); @@ -341,7 +339,8 @@ void tscProcessMsgFromServer(SRpcMsg *rpcMsg, SRpcEpSet *pEpSet) { if (pSql->retry > pSql->maxRetry) { tscError("%p max retry %d reached, give up", pSql, pSql->maxRetry); } else { - // wait for a little bit moment and then retry, todo do not sleep in rpc callback thread + // wait for a little bit moment and then retry + // todo do not sleep in rpc callback thread, add this process into queueu to process if (rpcMsg->code == TSDB_CODE_APP_NOT_READY || rpcMsg->code == TSDB_CODE_VND_INVALID_VGROUP_ID) { int32_t duration = getWaitingTimeInterval(pSql->retry); taosMsleep(duration); @@ -423,7 +422,7 @@ void tscProcessMsgFromServer(SRpcMsg *rpcMsg, SRpcEpSet *pEpSet) { if (shouldFree) { // in case of table-meta/vgrouplist query, automatically free it taosRemoveRef(tscObjRef, pSql->self); - tscDebug("%p sqlObj is automatically freed", pSql); + tscDebug("%p sqlObj is automatically freed", pSql); } rpcFreeCont(rpcMsg->pCont); @@ -484,9 +483,9 @@ int tscProcessSql(SSqlObj *pSql) { pSql->res.code = TSDB_CODE_TSC_APP_ERROR; return pSql->res.code; } - } else if (pCmd->command < TSDB_SQL_LOCAL) { + } else if (pCmd->command >= TSDB_SQL_LOCAL) { //pSql->epSet = tscMgmtEpSet; - } else { // local handler +// } else { // local handler return (*tscProcessMsgRsp[pCmd->command])(pSql); } @@ -1157,7 +1156,7 @@ int32_t tscBuildDropTableMsg(SSqlObj *pSql, SSqlInfo *pInfo) { SCMDropTableMsg *pDropTableMsg = (SCMDropTableMsg*)pCmd->payload; STableMetaInfo *pTableMetaInfo = tscGetTableMetaInfoFromCmd(pCmd, pCmd->clauseIndex, 0); - strcpy(pDropTableMsg->tableId, pTableMetaInfo->name); + strcpy(pDropTableMsg->tableFname, pTableMetaInfo->name); pDropTableMsg->igNotExists = pInfo->pDCLInfo->existsCheck ? 1 : 0; pCmd->msgType = TSDB_MSG_TYPE_CM_DROP_TABLE; @@ -1180,7 +1179,7 @@ int32_t tscBuildDropDnodeMsg(SSqlObj *pSql, SSqlInfo *pInfo) { return TSDB_CODE_SUCCESS; } -int32_t tscBuildDropUserMsg(SSqlObj *pSql, SSqlInfo *pInfo) { +int32_t tscBuildDropUserMsg(SSqlObj *pSql, SSqlInfo * UNUSED_PARAM(pInfo)) { SSqlCmd *pCmd = &pSql->cmd; pCmd->payloadLen = sizeof(SDropUserMsg); pCmd->msgType = TSDB_MSG_TYPE_CM_DROP_USER; @@ -1347,7 +1346,7 @@ int tscBuildCreateTableMsg(SSqlObj *pSql, SSqlInfo *pInfo) { pMsg += sizeof(SCreateTableMsg); SCreatedTableInfo* p = taosArrayGet(list, i); - strcpy(pCreate->tableId, p->fullname); + strcpy(pCreate->tableFname, p->fullname); pCreate->igExists = (p->igExist)? 1 : 0; // use dbinfo from table id without modifying current db info @@ -1360,7 +1359,7 @@ int tscBuildCreateTableMsg(SSqlObj *pSql, SSqlInfo *pInfo) { } else { // create (super) table pCreateTableMsg->numOfTables = htonl(1); // only one table will be created - strcpy(pCreateMsg->tableId, pTableMetaInfo->name); + strcpy(pCreateMsg->tableFname, pTableMetaInfo->name); // use dbinfo from table id without modifying current db info tscGetDBInfoFromTableFullName(pTableMetaInfo->name, pCreateMsg->db); @@ -1431,7 +1430,7 @@ int tscBuildAlterTableMsg(SSqlObj *pSql, SSqlInfo *pInfo) { SAlterTableMsg *pAlterTableMsg = (SAlterTableMsg *)pCmd->payload; tscGetDBInfoFromTableFullName(pTableMetaInfo->name, pAlterTableMsg->db); - strcpy(pAlterTableMsg->tableId, pTableMetaInfo->name); + strcpy(pAlterTableMsg->tableFname, pTableMetaInfo->name); pAlterTableMsg->type = htons(pAlterInfo->type); pAlterTableMsg->numOfCols = htons(tscNumOfFields(pQueryInfo)); @@ -1630,7 +1629,7 @@ int tscBuildTableMetaMsg(SSqlObj *pSql, SSqlInfo *pInfo) { STableMetaInfo *pTableMetaInfo = tscGetMetaInfo(pQueryInfo, 0); STableInfoMsg *pInfoMsg = (STableInfoMsg *)pCmd->payload; - strcpy(pInfoMsg->tableId, pTableMetaInfo->name); + strcpy(pInfoMsg->tableFname, pTableMetaInfo->name); pInfoMsg->createFlag = htons(pSql->cmd.autoCreated ? 1 : 0); char *pMsg = (char *)pInfoMsg + sizeof(STableInfoMsg); @@ -1799,7 +1798,7 @@ int tscProcessTableMetaRsp(SSqlObj *pSql) { if ((pMetaMsg->tableType != TSDB_SUPER_TABLE) && (pMetaMsg->tid <= 0 || pMetaMsg->vgroup.vgId < 2 || pMetaMsg->vgroup.numOfEps <= 0)) { tscError("invalid value in table numOfEps:%d, vgId:%d tid:%d, name:%s", pMetaMsg->vgroup.numOfEps, pMetaMsg->vgroup.vgId, - pMetaMsg->tid, pMetaMsg->tableId); + pMetaMsg->tid, pMetaMsg->tableFname); return TSDB_CODE_TSC_INVALID_VALUE; } @@ -1831,12 +1830,16 @@ int tscProcessTableMetaRsp(SSqlObj *pSql) { assert(isValidDataType(pSchema->type)); pSchema++; } - - STableMeta* pTableMeta = tscCreateTableMetaFromMsg(pMetaMsg); STableMetaInfo *pTableMetaInfo = tscGetTableMetaInfoFromCmd(&pSql->cmd, 0, 0); assert(pTableMetaInfo->pTableMeta == NULL); + STableMeta* pTableMeta = tscCreateTableMetaFromMsg(pMetaMsg); + if (!isValidSchema(pTableMeta->schema, pTableMeta->tableInfo.numOfColumns, pTableMeta->tableInfo.numOfTags)) { + tscError("%p invalid table meta from mnode, name:%s", pSql, pTableMetaInfo->name); + return TSDB_CODE_TSC_INVALID_VALUE; + } + if (pTableMeta->tableType == TSDB_CHILD_TABLE) { // check if super table hashmap or not int32_t len = (int32_t) strnlen(pTableMeta->sTableName, TSDB_TABLE_FNAME_LEN); @@ -1975,9 +1978,6 @@ int tscProcessMultiMeterMetaRsp(SSqlObj *pSql) { // // rsp += tagLen; // int32_t size = (int32_t)(rsp - ((char *)pMeta)); // Consistent with STableMeta in cache - // - // pMeta->index = 0; - // (void)taosCachePut(tscMetaCache, pMeta->tableId, (char *)pMeta, size, tsTableMetaKeepTimer); // } } @@ -1990,16 +1990,20 @@ int tscProcessMultiMeterMetaRsp(SSqlObj *pSql) { } int tscProcessSTableVgroupRsp(SSqlObj *pSql) { + // master sqlObj locates in param + SSqlObj* parent = (SSqlObj*)taosAcquireRef(tscObjRef, (int64_t)pSql->param); + if(parent == NULL) { + return pSql->res.code; + } + + assert(parent->signature == parent && (int64_t)pSql->param == parent->self); + SSqlRes* pRes = &pSql->res; // NOTE: the order of several table must be preserved. SSTableVgroupRspMsg *pStableVgroup = (SSTableVgroupRspMsg *)pRes->pRsp; pStableVgroup->numOfTables = htonl(pStableVgroup->numOfTables); char *pMsg = pRes->pRsp + sizeof(SSTableVgroupRspMsg); - - // master sqlObj locates in param - SSqlObj* parent = pSql->param; - assert(parent != NULL); SSqlCmd* pCmd = &parent->cmd; for(int32_t i = 0; i < pStableVgroup->numOfTables; ++i) { @@ -2033,6 +2037,8 @@ int tscProcessSTableVgroupRsp(SSqlObj *pSql) { pMsg += size; } + + taosReleaseRef(tscObjRef, parent->self); return pSql->res.code; } @@ -2094,7 +2100,7 @@ int tscProcessShowRsp(SSqlObj *pSql) { return 0; } -static void createHBObj(STscObj* pObj) { +static void createHbObj(STscObj* pObj) { if (pObj->hbrid != 0) { return; } @@ -2157,7 +2163,7 @@ int tscProcessConnectRsp(SSqlObj *pSql) { pObj->superAuth = pConnect->superAuth; pObj->connId = htonl(pConnect->connId); - createHBObj(pObj); + createHbObj(pObj); //launch a timer to send heartbeat to maintain the connection and send status to mnode taosTmrReset(tscProcessActivityTimer, tsShellActivityTimer * 500, (void *)pObj->rid, tscTmr, &pObj->pTimer); @@ -2326,11 +2332,15 @@ static int32_t getTableMetaFromMnode(SSqlObj *pSql, STableMetaInfo *pTableMetaIn tscDebug("%p new pSqlObj:%p to get tableMeta, auto create:%d", pSql, pNew, pNew->cmd.autoCreated); - pNew->fp = tscTableMetaCallBack; - pNew->param = pSql; - registerSqlObj(pNew); + pNew->fp = tscTableMetaCallBack; + pNew->param = (void *)pSql->self; + + tscDebug("%p metaRid from %" PRId64 " to %" PRId64 , pSql, pSql->metaRid, pNew->self); + + pSql->metaRid = pNew->self; + int32_t code = tscProcessSql(pNew); if (code == TSDB_CODE_SUCCESS) { code = TSDB_CODE_TSC_ACTION_IN_PROGRESS; // notify application that current process needs to be terminated @@ -2346,6 +2356,7 @@ int32_t tscGetTableMeta(SSqlObj *pSql, STableMetaInfo *pTableMetaInfo) { uint32_t size = tscGetTableMetaMaxSize(); pTableMetaInfo->pTableMeta = calloc(1, size); + pTableMetaInfo->pTableMeta->tableType = -1; pTableMetaInfo->pTableMeta->tableInfo.numOfColumns = -1; int32_t len = (int32_t) strlen(pTableMetaInfo->name); @@ -2445,10 +2456,15 @@ int tscGetSTableVgroupInfo(SSqlObj *pSql, int32_t clauseIndex) { pNewQueryInfo->numOfTables = pQueryInfo->numOfTables; registerSqlObj(pNew); + tscDebug("%p svgroupRid from %" PRId64 " to %" PRId64 , pSql, pSql->svgroupRid, pNew->self); + + pSql->svgroupRid = pNew->self; + + tscDebug("%p new sqlObj:%p to get vgroupInfo, numOfTables:%d", pSql, pNew, pNewQueryInfo->numOfTables); pNew->fp = tscTableMetaCallBack; - pNew->param = pSql; + pNew->param = (void *)pSql->self; code = tscProcessSql(pNew); if (code == TSDB_CODE_SUCCESS) { code = TSDB_CODE_TSC_ACTION_IN_PROGRESS; diff --git a/src/client/src/tscSql.c b/src/client/src/tscSql.c index da86b4cb19..a4f2976cad 100644 --- a/src/client/src/tscSql.c +++ b/src/client/src/tscSql.c @@ -47,7 +47,7 @@ static bool validUserName(const char* user) { } static bool validPassword(const char* passwd) { - return validImpl(passwd, TSDB_PASSWORD_LEN - 1); + return validImpl(passwd, TSDB_KEY_LEN - 1); } static SSqlObj *taosConnectImpl(const char *ip, const char *user, const char *pass, const char *auth, const char *db, @@ -238,11 +238,11 @@ TAOS *taos_connect_c(const char *ip, uint8_t ipLen, const char *user, uint8_t us uint8_t passLen, const char *db, uint8_t dbLen, uint16_t port) { char ipBuf[TSDB_EP_LEN] = {0}; char userBuf[TSDB_USER_LEN] = {0}; - char passBuf[TSDB_PASSWORD_LEN] = {0}; + char passBuf[TSDB_KEY_LEN] = {0}; char dbBuf[TSDB_DB_NAME_LEN] = {0}; strncpy(ipBuf, ip, MIN(TSDB_EP_LEN - 1, ipLen)); strncpy(userBuf, user, MIN(TSDB_USER_LEN - 1, userLen)); - strncpy(passBuf, pass, MIN(TSDB_PASSWORD_LEN - 1, passLen)); + strncpy(passBuf, pass, MIN(TSDB_KEY_LEN - 1, passLen)); strncpy(dbBuf, db, MIN(TSDB_DB_NAME_LEN - 1, dbLen)); return taos_connect(ipBuf, userBuf, passBuf, dbBuf, port); } @@ -694,6 +694,8 @@ static void tscKillSTableQuery(SSqlObj *pSql) { // set the master sqlObj flag to cancel query pSql->res.code = TSDB_CODE_TSC_QUERY_CANCELLED; + tscLockByThread(&pSql->squeryLock); + for (int i = 0; i < pSql->subState.numOfSub; ++i) { // NOTE: pSub may have been released already here SSqlObj *pSub = pSql->pSubs[i]; @@ -713,6 +715,12 @@ static void tscKillSTableQuery(SSqlObj *pSql) { taosReleaseRef(tscObjRef, pSubObj->self); } + if (pSql->subState.numOfSub <= 0) { + tscAsyncResultOnError(pSql); + } + + tscUnlockByThread(&pSql->squeryLock); + tscDebug("%p super table query cancelled", pSql); } @@ -773,6 +781,7 @@ bool taos_is_null(TAOS_RES *res, int32_t row, int32_t col) { int taos_print_row(char *str, TAOS_ROW row, TAOS_FIELD *fields, int num_fields) { int len = 0; + for (int i = 0; i < num_fields; ++i) { if (i > 0) { str[len++] = ' '; @@ -830,13 +839,15 @@ int taos_print_row(char *str, TAOS_ROW row, TAOS_FIELD *fields, int num_fields) case TSDB_DATA_TYPE_BINARY: case TSDB_DATA_TYPE_NCHAR: { - size_t xlen = 0; - for (xlen = 0; xlen < fields[i].bytes - VARSTR_HEADER_SIZE; xlen++) { - char c = ((char *)row[i])[xlen]; - if (c == 0) break; - str[len++] = c; + int32_t charLen = varDataLen((char*)row[i] - VARSTR_HEADER_SIZE); + if (fields[i].type == TSDB_DATA_TYPE_BINARY) { + assert(charLen <= fields[i].bytes); + } else { + assert(charLen <= fields[i].bytes * TSDB_NCHAR_SIZE); } - str[len] = 0; + + memcpy(str + len, row[i], charLen); + len += charLen; } break; case TSDB_DATA_TYPE_TIMESTAMP: @@ -978,7 +989,7 @@ static int tscParseTblNameList(SSqlObj *pSql, const char *tblNameList, int32_t t return code; } - if (++pCmd->count > TSDB_MULTI_METERMETA_MAX_NUM) { + if (++pCmd->count > TSDB_MULTI_TABLEMETA_MAX_NUM) { code = TSDB_CODE_TSC_INVALID_TABLE_ID_LENGTH; sprintf(pCmd->payload, "tables over the max number"); return code; diff --git a/src/client/src/tscStream.c b/src/client/src/tscStream.c index 1c85938c64..a39fbc9420 100644 --- a/src/client/src/tscStream.c +++ b/src/client/src/tscStream.c @@ -551,7 +551,6 @@ static void tscCreateStream(void *param, TAOS_RES *res, int code) { int64_t starttime = tscGetLaunchTimestamp(pStream); pCmd->command = TSDB_SQL_SELECT; - registerSqlObj(pSql); tscAddIntoStreamList(pStream); taosTmrReset(tscProcessStreamTimer, (int32_t)starttime, pStream, tscTmr, &pStream->pTimer); @@ -610,12 +609,15 @@ TAOS_STREAM *taos_open_stream(TAOS *taos, const char *sqlstr, void (*fp)(void *p pSql->fp = tscCreateStream; pSql->fetchFp = tscCreateStream; + + registerSqlObj(pSql); + int32_t code = tsParseSql(pSql, true); if (code == TSDB_CODE_SUCCESS) { tscCreateStream(pStream, pSql, code); } else if (code != TSDB_CODE_TSC_ACTION_IN_PROGRESS) { tscError("%p open stream failed, sql:%s, code:%s", pSql, sqlstr, tstrerror(pRes->code)); - tscFreeSqlObj(pSql); + taosReleaseRef(tscObjRef, pSql->self); free(pStream); return NULL; } diff --git a/src/client/src/tscSubquery.c b/src/client/src/tscSubquery.c index d4f9620630..2622246111 100644 --- a/src/client/src/tscSubquery.c +++ b/src/client/src/tscSubquery.c @@ -533,7 +533,7 @@ static void quitAllSubquery(SSqlObj* pSqlObj, SJoinSupporter* pSupporter) { freeJoinSubqueryObj(pSqlObj); } - tscDestroyJoinSupporter(pSupporter); + //tscDestroyJoinSupporter(pSupporter); } // update the query time range according to the join results on timestamp @@ -1362,9 +1362,11 @@ void tscJoinQueryCallback(void* param, TAOS_RES* tres, int code) { SJoinSupporter* pSupporter = (SJoinSupporter*)param; SSqlObj* pParentSql = pSupporter->pObj; - + // There is only one subquery and table for each subquery. SQueryInfo* pQueryInfo = tscGetQueryInfoDetail(&pSql->cmd, 0); + STableMetaInfo* pTableMetaInfo = tscGetMetaInfo(pQueryInfo, 0); + assert(pQueryInfo->numOfTables == 1 && pSql->cmd.numOfClause == 1); // retrieve actual query results from vnode during the second stage join subquery @@ -1382,7 +1384,6 @@ void tscJoinQueryCallback(void* param, TAOS_RES* tres, int code) { tscError("%p abort query, code:%s, global code:%s", pSql, tstrerror(code), tstrerror(pParentSql->res.code)); pParentSql->res.code = code; - quitAllSubquery(pParentSql, pSupporter); tscAsyncResultOnError(pParentSql); @@ -1405,9 +1406,6 @@ void tscJoinQueryCallback(void* param, TAOS_RES* tres, int code) { return; } - - STableMetaInfo* pTableMetaInfo = tscGetMetaInfo(pQueryInfo, 0); - // In case of consequence query from other vnode, do not wait for other query response here. if (!(pTableMetaInfo->vgroupIndex > 0 && tscNonOrderedProjectionQueryOnSTable(pQueryInfo, 0))) { if (atomic_sub_fetch_32(&pParentSql->subState.numOfRemain, 1) > 0) { @@ -1658,6 +1656,25 @@ static void doCleanupSubqueries(SSqlObj *pSql, int32_t numOfSubs) { } } +void tscLockByThread(int64_t *lockedBy) { + int64_t tid = taosGetSelfPthreadId(); + int i = 0; + while (atomic_val_compare_exchange_64(lockedBy, 0, tid) != 0) { + if (++i % 100 == 0) { + sched_yield(); + } + } +} + +void tscUnlockByThread(int64_t *lockedBy) { + int64_t tid = taosGetSelfPthreadId(); + if (atomic_val_compare_exchange_64(lockedBy, tid, 0) != tid) { + assert(false); + } +} + + + int32_t tscHandleMasterSTableQuery(SSqlObj *pSql) { SSqlRes *pRes = &pSql->res; SSqlCmd *pCmd = &pSql->cmd; diff --git a/src/client/src/tscUtil.c b/src/client/src/tscUtil.c index b44ebb3c98..02cd9b9692 100644 --- a/src/client/src/tscUtil.c +++ b/src/client/src/tscUtil.c @@ -468,6 +468,18 @@ void tscFreeRegisteredSqlObj(void *pSql) { } +void tscFreeMetaSqlObj(int64_t *rid){ + if (RID_VALID(*rid)) { + SSqlObj* pSql = (SSqlObj*)taosAcquireRef(tscObjRef, *rid); + if (pSql) { + taosRemoveRef(tscObjRef, *rid); + taosReleaseRef(tscObjRef, *rid); + } + + *rid = 0; + } +} + void tscFreeSqlObj(SSqlObj* pSql) { if (pSql == NULL || pSql->signature != pSql) { return; @@ -477,6 +489,9 @@ void tscFreeSqlObj(SSqlObj* pSql) { pSql->res.code = TSDB_CODE_TSC_QUERY_CANCELLED; + tscFreeMetaSqlObj(&pSql->metaRid); + tscFreeMetaSqlObj(&pSql->svgroupRid); + tscFreeSubobj(pSql); SSqlCmd* pCmd = &pSql->cmd; @@ -505,6 +520,7 @@ void tscFreeSqlObj(SSqlObj* pSql) { pCmd->allocSize = 0; tsem_destroy(&pSql->rspSem); + memset(pSql, 0, sizeof(*pSql)); free(pSql); } @@ -587,6 +603,7 @@ int32_t tscCopyDataBlockToPayload(SSqlObj* pSql, STableDataBlocks* pDataBlock) { assert(pCmd->numOfClause == 1); STableMetaInfo* pTableMetaInfo = tscGetTableMetaInfoFromCmd(pCmd, pCmd->clauseIndex, 0); + // todo refactor // set the correct table meta object, the table meta has been locked in pDataBlocks, so it must be in the cache if (pTableMetaInfo->pTableMeta != pDataBlock->pTableMeta) { tstrncpy(pTableMetaInfo->name, pDataBlock->tableName, sizeof(pTableMetaInfo->name)); @@ -673,7 +690,6 @@ int32_t tscCreateDataBlock(size_t initialSize, int32_t rowSize, int32_t startOff int32_t tscGetDataBlockFromList(SHashObj* pHashList, int64_t id, int32_t size, int32_t startOffset, int32_t rowSize, const char* tableId, STableMeta* pTableMeta, STableDataBlocks** dataBlocks, SArray* pBlockList) { *dataBlocks = NULL; - STableDataBlocks** t1 = (STableDataBlocks**)taosHashGet(pHashList, (const char*)&id, sizeof(id)); if (t1 != NULL) { *dataBlocks = *t1; @@ -769,9 +785,13 @@ static int32_t getRowExpandSize(STableMeta* pTableMeta) { return result; } -static void extractTableNameList(SSqlCmd* pCmd) { +static void extractTableNameList(SSqlCmd* pCmd, bool freeBlockMap) { pCmd->numOfTables = (int32_t) taosHashGetSize(pCmd->pTableBlockHashList); - pCmd->pTableNameList = calloc(pCmd->numOfTables, POINTER_BYTES); + if (pCmd->pTableNameList == NULL) { + pCmd->pTableNameList = calloc(pCmd->numOfTables, POINTER_BYTES); + } else { + memset(pCmd->pTableNameList, 0, pCmd->numOfTables * POINTER_BYTES); + } STableDataBlocks **p1 = taosHashIterate(pCmd->pTableBlockHashList, NULL); int32_t i = 0; @@ -781,10 +801,12 @@ static void extractTableNameList(SSqlCmd* pCmd) { p1 = taosHashIterate(pCmd->pTableBlockHashList, p1); } - pCmd->pTableBlockHashList = tscDestroyBlockHashTable(pCmd->pTableBlockHashList); + if (freeBlockMap) { + pCmd->pTableBlockHashList = tscDestroyBlockHashTable(pCmd->pTableBlockHashList); + } } -int32_t tscMergeTableDataBlocks(SSqlObj* pSql) { +int32_t tscMergeTableDataBlocks(SSqlObj* pSql, bool freeBlockMap) { const int INSERT_HEAD_SIZE = sizeof(SMsgDesc) + sizeof(SSubmitMsg); SSqlCmd* pCmd = &pSql->cmd; @@ -864,7 +886,7 @@ int32_t tscMergeTableDataBlocks(SSqlObj* pSql) { pOneTableBlock = *p; } - extractTableNameList(pCmd); + extractTableNameList(pCmd, freeBlockMap); // free the table data blocks; pCmd->pDataBlocks = pVnodeDataBlockList; @@ -1899,7 +1921,7 @@ void registerSqlObj(SSqlObj* pSql) { tscDebug("%p new SqlObj from %p, total in tscObj:%d, total:%d", pSql, pSql->pTscObj, num, total); } -SSqlObj* createSimpleSubObj(SSqlObj* pSql, void (*fp)(), void* param, int32_t cmd) { +SSqlObj* createSimpleSubObj(SSqlObj* pSql, __async_cb_func_t fp, void* param, int32_t cmd) { SSqlObj* pNew = (SSqlObj*)calloc(1, sizeof(SSqlObj)); if (pNew == NULL) { tscError("%p new subquery failed, tableIndex:%d", pSql, 0); @@ -1984,7 +2006,7 @@ static void doSetSqlExprAndResultFieldInfo(SQueryInfo* pNewQueryInfo, int64_t ui tscFieldInfoUpdateOffset(pNewQueryInfo); } -SSqlObj* createSubqueryObj(SSqlObj* pSql, int16_t tableIndex, void (*fp)(), void* param, int32_t cmd, SSqlObj* pPrevSql) { +SSqlObj* createSubqueryObj(SSqlObj* pSql, int16_t tableIndex, __async_cb_func_t fp, void* param, int32_t cmd, SSqlObj* pPrevSql) { SSqlCmd* pCmd = &pSql->cmd; SSqlObj* pNew = (SSqlObj*)calloc(1, sizeof(SSqlObj)); @@ -2180,7 +2202,7 @@ void tscDoQuery(SSqlObj* pSql) { SQueryInfo *pQueryInfo = tscGetQueryInfoDetail(pCmd, pCmd->clauseIndex); uint16_t type = pQueryInfo->type; - if (pSql->fp == (void(*)())tscHandleMultivnodeInsert) { // multi-vnodes insertion + if (TSDB_QUERY_HAS_TYPE(type, TSDB_QUERY_TYPE_INSERT)) { // multi-vnodes insertion tscHandleMultivnodeInsert(pSql); return; } @@ -2193,7 +2215,9 @@ void tscDoQuery(SSqlObj* pSql) { tscProcessSql(pSql); } else { // secondary stage join query. if (tscIsTwoStageSTableQuery(pQueryInfo, 0)) { // super table query + tscLockByThread(&pSql->squeryLock); tscHandleMasterSTableQuery(pSql); + tscUnlockByThread(&pSql->squeryLock); } else { tscProcessSql(pSql); } @@ -2202,7 +2226,9 @@ void tscDoQuery(SSqlObj* pSql) { return; } else if (tscIsTwoStageSTableQuery(pQueryInfo, 0)) { // super table query + tscLockByThread(&pSql->squeryLock); tscHandleMasterSTableQuery(pSql); + tscUnlockByThread(&pSql->squeryLock); return; } diff --git a/src/client/tests/CMakeLists.txt b/src/client/tests/CMakeLists.txt index f07af85e25..4ea0b80bf7 100644 --- a/src/client/tests/CMakeLists.txt +++ b/src/client/tests/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) FIND_PATH(HEADER_GTEST_INCLUDE_DIR gtest.h /usr/include/gtest /usr/local/include/gtest) diff --git a/src/client/tests/resultFieldTest.cpp b/src/client/tests/cliTest.cpp similarity index 58% rename from src/client/tests/resultFieldTest.cpp rename to src/client/tests/cliTest.cpp index c917f0ebaf..5cfe61d92a 100644 --- a/src/client/tests/resultFieldTest.cpp +++ b/src/client/tests/cliTest.cpp @@ -2,15 +2,117 @@ #include #include "taos.h" +#include "tglobal.h" namespace { static int64_t start_ts = 1433955661000; -} -/* test parse time function */ -TEST(testCase, result_field_test) { - taos_options(TSDB_OPTION_CONFIGDIR, "~/first/cfg"); - taos_init(); +void stmtInsertTest() { + TAOS* conn = taos_connect("ubuntu", "root", "taosdata", 0, 0); + if (conn == NULL) { + printf("Failed to connect to DB, reason:%s", taos_errstr(conn)); + exit(-1); + } + + TAOS_RES* res = taos_query(conn, "use test"); + taos_free_result(res); + + const char* sql = "insert into t1 values(?, ?, ?, ?)"; + TAOS_STMT* stmt = taos_stmt_init(conn); + + int32_t ret = taos_stmt_prepare(stmt, sql, 0); + ASSERT_EQ(ret, 0); + + //ts timestamp, k int, a binary(11), b nchar(4) + struct { + int64_t ts; + int k; + char* a; + char* b; + } v = {0}; + + TAOS_BIND params[4]; + params[0].buffer_type = TSDB_DATA_TYPE_TIMESTAMP; + params[0].buffer_length = sizeof(v.ts); + params[0].buffer = &v.ts; + params[0].length = ¶ms[0].buffer_length; + params[0].is_null = NULL; + + params[1].buffer_type = TSDB_DATA_TYPE_INT; + params[1].buffer_length = sizeof(v.k); + params[1].buffer = &v.k; + params[1].length = ¶ms[1].buffer_length; + params[1].is_null = NULL; + + params[2].buffer_type = TSDB_DATA_TYPE_BINARY; + params[2].buffer_length = sizeof(v.a); + params[2].buffer = &v.a; + params[2].is_null = NULL; + + params[3].buffer_type = TSDB_DATA_TYPE_NCHAR; + params[3].buffer_length = sizeof(v.b); + params[3].buffer = &v.b; + params[3].is_null = NULL; + + v.ts = start_ts + 20; + v.k = 123; + + char* str = "abc"; + uintptr_t len = strlen(str); + + v.a = str; + params[2].length = &len; + params[2].buffer_length = len; + params[2].buffer = str; + + char* nstr = "999"; + uintptr_t len1 = strlen(nstr); + + v.b = nstr; + params[3].buffer_length = len1; + params[3].buffer = nstr; + params[3].length = &len1; + + taos_stmt_bind_param(stmt, params); + taos_stmt_add_batch(stmt); + + if (taos_stmt_execute(stmt) != 0) { + printf("\033[31mfailed to execute insert statement.\033[0m\n"); + return; + } + + v.ts = start_ts + 30; + v.k = 911; + + str = "92"; + len = strlen(str); + + params[2].length = &len; + params[2].buffer_length = len; + params[2].buffer = str; + + nstr = "1920"; + len1 = strlen(nstr); + + params[3].buffer_length = len1; + params[3].buffer = nstr; + params[3].length = &len1; + + taos_stmt_bind_param(stmt, params); + taos_stmt_add_batch(stmt); + + ret = taos_stmt_execute(stmt); + if (ret != 0) { + printf("%p\n", ret); + printf("\033[31mfailed to execute insert statement.\033[0m\n"); + return; + } + + taos_stmt_close(stmt); + taos_close(conn); +} + +void validateResultFields() { TAOS* conn = taos_connect("ubuntu", "root", "taosdata", 0, 0); if (conn == NULL) { printf("Failed to connect to DB, reason:%s", taos_errstr(conn)); @@ -134,5 +236,31 @@ TEST(testCase, result_field_test) { ASSERT_STREQ(fields[6].name, "first(ts)"); taos_free_result(res); + + // update the configure parameter, the result field name will be changed + tsKeepOriginalColumnName = 1; + res = taos_query(conn, "select first(ts, a, k, k, b, b, ts) from t1"); + ASSERT_EQ(taos_num_fields(res), 7); + + fields = taos_fetch_fields(res); + ASSERT_EQ(fields[0].bytes, 8); + ASSERT_EQ(fields[0].type, TSDB_DATA_TYPE_TIMESTAMP); + ASSERT_STREQ(fields[0].name, "ts"); + + ASSERT_EQ(fields[2].bytes, 4); + ASSERT_EQ(fields[2].type, TSDB_DATA_TYPE_INT); + ASSERT_STREQ(fields[2].name, "k"); + + taos_free_result(res); + taos_close(conn); } +} +/* test parse time function */ +TEST(testCase, result_field_test) { + taos_options(TSDB_OPTION_CONFIGDIR, "~/first/cfg"); + taos_init(); + + validateResultFields(); + stmtInsertTest(); +} diff --git a/src/client/tests/timeParseTest.cpp b/src/client/tests/timeParseTest.cpp index bee01b5cec..d7325430cd 100644 --- a/src/client/tests/timeParseTest.cpp +++ b/src/client/tests/timeParseTest.cpp @@ -162,6 +162,10 @@ TEST(testCase, parse_time) { taosParseTime(t13, &time, strlen(t13), TSDB_TIME_PRECISION_MILLI, 0); EXPECT_EQ(time, -28800 * MILLISECOND_PER_SECOND); + + char* t = "2021-01-08T02:11:40.000+00:00"; + taosParseTime(t, &time, strlen(t), TSDB_TIME_PRECISION_MILLI, 0); + printf("%ld\n", time); } diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index 0da7bda994..df0ac79865 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/common/inc/tdataformat.h b/src/common/inc/tdataformat.h index 8d4949d9b4..43208e0e47 100644 --- a/src/common/inc/tdataformat.h +++ b/src/common/inc/tdataformat.h @@ -20,7 +20,7 @@ #include #include "talgo.h" -#include "taosdef.h" +#include "ttype.h" #include "tutil.h" #ifdef __cplusplus diff --git a/src/common/inc/tglobal.h b/src/common/inc/tglobal.h index f6a08f8198..54334d49f3 100644 --- a/src/common/inc/tglobal.h +++ b/src/common/inc/tglobal.h @@ -63,7 +63,6 @@ extern int32_t tsRetrieveBlockingModel;// retrieve threads will be blocked extern int8_t tsKeepOriginalColumnName; // client -extern int32_t tsTableMetaKeepTimer; extern int32_t tsMaxSQLStringLen; extern int8_t tsTscEnableRecordSql; extern int32_t tsMaxNumOfOrderedResults; @@ -181,7 +180,7 @@ extern int32_t tsLogKeepDays; extern int32_t dDebugFlag; extern int32_t vDebugFlag; extern int32_t mDebugFlag; -extern int32_t cDebugFlag; +extern uint32_t cDebugFlag; extern int32_t jniDebugFlag; extern int32_t tmrDebugFlag; extern int32_t sdbDebugFlag; diff --git a/src/common/inc/tname.h b/src/common/inc/tname.h index 9e0093ebfe..44f1047543 100644 --- a/src/common/inc/tname.h +++ b/src/common/inc/tname.h @@ -39,4 +39,18 @@ SColumnFilterInfo* tscFilterInfoClone(const SColumnFilterInfo* src, int32_t numO SSchema tscGetTbnameColumnSchema(); +/** + * check if the schema is valid or not, including following aspects: + * 1. number of columns + * 2. column types + * 3. column length + * 4. column names + * 5. total length + * + * @param pSchema + * @param numOfCols + * @return + */ +bool isValidSchema(struct SSchema* pSchema, int32_t numOfCols, int32_t numOfTags); + #endif // TDENGINE_NAME_H diff --git a/src/common/src/tglobal.c b/src/common/src/tglobal.c index e5c364bcaa..cfe91d3519 100644 --- a/src/common/src/tglobal.c +++ b/src/common/src/tglobal.c @@ -72,7 +72,6 @@ char tsTempDir[TSDB_FILENAME_LEN] = "/tmp/"; int32_t tsCompressMsgSize = -1; // client -int32_t tsTableMetaKeepTimer = 7200; // second int32_t tsMaxSQLStringLen = TSDB_MAX_SQL_LEN; int8_t tsTscEnableRecordSql = 0; @@ -213,7 +212,7 @@ int32_t mDebugFlag = 131; int32_t sdbDebugFlag = 131; int32_t dDebugFlag = 135; int32_t vDebugFlag = 135; -int32_t cDebugFlag = 131; +uint32_t cDebugFlag = 131; int32_t jniDebugFlag = 131; int32_t odbcDebugFlag = 131; int32_t httpDebugFlag = 131; @@ -596,16 +595,6 @@ static void doInitGlobalConfig(void) { cfg.unitType = TAOS_CFG_UTYPE_SECOND; taosInitConfigOption(cfg); - cfg.option = "tableMetaKeepTimer"; - cfg.ptr = &tsTableMetaKeepTimer; - cfg.valType = TAOS_CFG_VTYPE_INT32; - cfg.cfgType = TSDB_CFG_CTYPE_B_CONFIG | TSDB_CFG_CTYPE_B_CLIENT; - cfg.minValue = 1; - cfg.maxValue = 8640000; - cfg.ptrLength = 0; - cfg.unitType = TAOS_CFG_UTYPE_SECOND; - taosInitConfigOption(cfg); - cfg.option = "minSlidingTime"; cfg.ptr = &tsMinSlidingTime; cfg.valType = TAOS_CFG_VTYPE_INT32; diff --git a/src/common/src/tname.c b/src/common/src/tname.c index 5c351edf48..f35867ede3 100644 --- a/src/common/src/tname.c +++ b/src/common/src/tname.c @@ -6,6 +6,10 @@ #include "ttokendef.h" #include "tvariant.h" +#define VALIDNUMOFCOLS(x) ((x) >= TSDB_MIN_COLUMNS && (x) <= TSDB_MAX_COLUMNS) + +#define VALIDNUMOFTAGS(x) ((x) >= 0 && (x) <= TSDB_MAX_TAGS) + // todo refactor UNUSED_FUNC static FORCE_INLINE const char* skipSegments(const char* input, char delim, int32_t num) { for (int32_t i = 0; i < num; ++i) { @@ -62,7 +66,7 @@ SSchema tGetUserSpecifiedColumnSchema(tVariant* pVal, SStrToken* exprStr, const if (s.type == TSDB_DATA_TYPE_BINARY || s.type == TSDB_DATA_TYPE_NCHAR) { s.bytes = (int16_t)(pVal->nLen + VARSTR_HEADER_SIZE); } else { - s.bytes = tDataTypeDesc[pVal->nType].nSize; + s.bytes = tDataTypes[pVal->nType].bytes; } s.colId = TSDB_UD_COLUMN_INDEX; @@ -206,3 +210,65 @@ SSchema tscGetTbnameColumnSchema() { strcpy(s.name, TSQL_TBNAME_L); return s; } + +static bool doValidateSchema(SSchema* pSchema, int32_t numOfCols, int32_t maxLen) { + int32_t rowLen = 0; + + for (int32_t i = 0; i < numOfCols; ++i) { + // 1. valid types + if (!isValidDataType(pSchema[i].type)) { + return false; + } + + // 2. valid length for each type + if (pSchema[i].type == TSDB_DATA_TYPE_BINARY) { + if (pSchema[i].bytes > TSDB_MAX_BINARY_LEN) { + return false; + } + } else if (pSchema[i].type == TSDB_DATA_TYPE_NCHAR) { + if (pSchema[i].bytes > TSDB_MAX_NCHAR_LEN) { + return false; + } + } else { + if (pSchema[i].bytes != tDataTypes[pSchema[i].type].bytes) { + return false; + } + } + + // 3. valid column names + for (int32_t j = i + 1; j < numOfCols; ++j) { + if (strncasecmp(pSchema[i].name, pSchema[j].name, sizeof(pSchema[i].name) - 1) == 0) { + return false; + } + } + + rowLen += pSchema[i].bytes; + } + + return rowLen <= maxLen; +} + +bool isValidSchema(struct SSchema* pSchema, int32_t numOfCols, int32_t numOfTags) { + if (!VALIDNUMOFCOLS(numOfCols)) { + return false; + } + + if (!VALIDNUMOFTAGS(numOfTags)) { + return false; + } + + /* first column must be the timestamp, which is a primary key */ + if (pSchema[0].type != TSDB_DATA_TYPE_TIMESTAMP) { + return false; + } + + if (!doValidateSchema(pSchema, numOfCols, TSDB_MAX_BYTES_PER_ROW)) { + return false; + } + + if (!doValidateSchema(&pSchema[numOfCols], numOfTags, TSDB_MAX_TAGS_LEN)) { + return false; + } + + return true; +} diff --git a/src/common/src/ttypes.c b/src/common/src/ttypes.c index 8197fb1042..0d5910ea38 100644 --- a/src/common/src/ttypes.c +++ b/src/common/src/ttypes.c @@ -14,7 +14,7 @@ */ #include "os.h" -#include "taosdef.h" +#include "ttype.h" #include "ttokendef.h" #include "tscompression.h" @@ -367,7 +367,7 @@ static void getStatics_nchr(const void *pData, int32_t numOfRow, int64_t *min, i *maxIndex = 0; } -tDataTypeDescriptor tDataTypeDesc[15] = { +tDataTypeDescriptor tDataTypes[15] = { {TSDB_DATA_TYPE_NULL, 6,1, "NOTYPE", NULL, NULL, NULL}, {TSDB_DATA_TYPE_BOOL, 4, CHAR_BYTES, "BOOL", tsCompressBool, tsDecompressBool, getStatics_bool}, {TSDB_DATA_TYPE_TINYINT, 7, CHAR_BYTES, "TINYINT", tsCompressTinyint, tsDecompressTinyint, getStatics_i8}, @@ -423,58 +423,58 @@ void setNullN(char *val, int32_t type, int32_t bytes, int32_t numOfElems) { switch (type) { case TSDB_DATA_TYPE_BOOL: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint8_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_BOOL_NULL; + *(uint8_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_BOOL_NULL; } break; case TSDB_DATA_TYPE_TINYINT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint8_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_TINYINT_NULL; + *(uint8_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_TINYINT_NULL; } break; case TSDB_DATA_TYPE_SMALLINT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint16_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_SMALLINT_NULL; + *(uint16_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_SMALLINT_NULL; } break; case TSDB_DATA_TYPE_INT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint32_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_INT_NULL; + *(uint32_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_INT_NULL; } break; case TSDB_DATA_TYPE_BIGINT: case TSDB_DATA_TYPE_TIMESTAMP: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint64_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_BIGINT_NULL; + *(uint64_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_BIGINT_NULL; } break; case TSDB_DATA_TYPE_UTINYINT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint8_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_UTINYINT_NULL; + *(uint8_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_UTINYINT_NULL; } break; case TSDB_DATA_TYPE_USMALLINT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint16_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_USMALLINT_NULL; + *(uint16_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_USMALLINT_NULL; } break; case TSDB_DATA_TYPE_UINT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint32_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_UINT_NULL; + *(uint32_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_UINT_NULL; } break; case TSDB_DATA_TYPE_UBIGINT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint64_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_UBIGINT_NULL; + *(uint64_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_UBIGINT_NULL; } break; case TSDB_DATA_TYPE_FLOAT: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint32_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_FLOAT_NULL; + *(uint32_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_FLOAT_NULL; } break; case TSDB_DATA_TYPE_DOUBLE: for (int32_t i = 0; i < numOfElems; ++i) { - *(uint64_t *)(val + i * tDataTypeDesc[type].nSize) = TSDB_DATA_DOUBLE_NULL; + *(uint64_t *)(val + i * tDataTypes[type].bytes) = TSDB_DATA_DOUBLE_NULL; } break; case TSDB_DATA_TYPE_NCHAR: @@ -485,7 +485,7 @@ void setNullN(char *val, int32_t type, int32_t bytes, int32_t numOfElems) { break; default: { for (int32_t i = 0; i < numOfElems; ++i) { - *(uint32_t *)(val + i * tDataTypeDesc[TSDB_DATA_TYPE_INT].nSize) = TSDB_DATA_INT_NULL; + *(uint32_t *)(val + i * tDataTypes[TSDB_DATA_TYPE_INT].bytes) = TSDB_DATA_INT_NULL; } break; } @@ -524,15 +524,18 @@ void assignVal(char *val, const char *src, int32_t len, int32_t type) { switch (type) { case TSDB_DATA_TYPE_BOOL: case TSDB_DATA_TYPE_TINYINT: + case TSDB_DATA_TYPE_UTINYINT: *((int8_t *)val) = GET_INT8_VAL(src); break; case TSDB_DATA_TYPE_SMALLINT: + case TSDB_DATA_TYPE_USMALLINT: *((int16_t *)val) = GET_INT16_VAL(src); break; - case TSDB_DATA_TYPE_INT: { + case TSDB_DATA_TYPE_INT: + case TSDB_DATA_TYPE_UINT: *((int32_t *)val) = GET_INT32_VAL(src); break; - } + case TSDB_DATA_TYPE_FLOAT: SET_FLOAT_VAL(val, GET_FLOAT_VAL(src)); break; @@ -540,6 +543,7 @@ void assignVal(char *val, const char *src, int32_t len, int32_t type) { SET_DOUBLE_VAL(val, GET_DOUBLE_VAL(src)); break; case TSDB_DATA_TYPE_BIGINT: + case TSDB_DATA_TYPE_UBIGINT: case TSDB_DATA_TYPE_TIMESTAMP: *((int64_t *)val) = GET_INT64_VAL(src); break; diff --git a/src/common/src/tvariant.c b/src/common/src/tvariant.c index fdfa933cde..95aa576889 100644 --- a/src/common/src/tvariant.c +++ b/src/common/src/tvariant.c @@ -205,7 +205,7 @@ void tVariantAssign(tVariant *pDst, const tVariant *pSrc) { } if (pDst->nType != TSDB_DATA_TYPE_ARRAY) { - pDst->nLen = tDataTypeDesc[pDst->nType].nSize; + pDst->nLen = tDataTypes[pDst->nType].bytes; } } @@ -399,6 +399,7 @@ static int32_t toNchar(tVariant *pVariant, char **pDest, int32_t *pDestSize) { pVariant->wpz = (wchar_t *)tmp; } else { int32_t output = 0; + bool ret = taosMbsToUcs4(pDst, nLen, *pDest, (nLen + 1) * TSDB_NCHAR_SIZE, &output); if (!ret) { return -1; @@ -424,7 +425,7 @@ static FORCE_INLINE int32_t convertToDouble(char *pStr, int32_t len, double *val static FORCE_INLINE int32_t convertToInteger(tVariant *pVariant, int64_t *result, int32_t type, bool issigned, bool releaseVariantPtr) { if (pVariant->nType == TSDB_DATA_TYPE_NULL) { - setNull((char *)result, type, tDataTypeDesc[type].nSize); + setNull((char *)result, type, tDataTypes[type].bytes); return 0; } @@ -445,7 +446,7 @@ static FORCE_INLINE int32_t convertToInteger(tVariant *pVariant, int64_t *result pVariant->nLen = 0; } - setNull((char *)result, type, tDataTypeDesc[type].nSize); + setNull((char *)result, type, tDataTypes[type].bytes); return 0; } @@ -495,7 +496,7 @@ static FORCE_INLINE int32_t convertToInteger(tVariant *pVariant, int64_t *result free(pVariant->pz); pVariant->nLen = 0; } - setNull((char *)result, type, tDataTypeDesc[type].nSize); + setNull((char *)result, type, tDataTypes[type].bytes); return 0; } else { int64_t val = wcstoll(pVariant->wpz, &endPtr, 10); diff --git a/src/connector/jdbc/.classpath b/src/connector/jdbc/.classpath deleted file mode 100644 index a5d95095cc..0000000000 --- a/src/connector/jdbc/.classpath +++ /dev/null @@ -1,32 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/connector/jdbc/.project b/src/connector/jdbc/.project deleted file mode 100644 index 656ab58d20..0000000000 --- a/src/connector/jdbc/.project +++ /dev/null @@ -1,23 +0,0 @@ - - - taos-jdbcdriver - - - - - - org.eclipse.jdt.core.javabuilder - - - - - org.eclipse.m2e.core.maven2Builder - - - - - - org.eclipse.jdt.core.javanature - org.eclipse.m2e.core.maven2Nature - - diff --git a/src/connector/jdbc/CMakeLists.txt b/src/connector/jdbc/CMakeLists.txt index e289f1ae1b..7097e9bc5a 100644 --- a/src/connector/jdbc/CMakeLists.txt +++ b/src/connector/jdbc/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) @@ -8,7 +8,7 @@ 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.15-dist.jar ${LIBRARY_OUTPUT_PATH} + COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/target/taos-jdbcdriver-2.0.16-dist.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}) diff --git a/src/connector/jdbc/deploy-pom.xml b/src/connector/jdbc/deploy-pom.xml index 1a86bc57dc..5aa60c0df9 100755 --- a/src/connector/jdbc/deploy-pom.xml +++ b/src/connector/jdbc/deploy-pom.xml @@ -5,7 +5,7 @@ com.taosdata.jdbc taos-jdbcdriver - 2.0.15 + 2.0.16 jar JDBCDriver diff --git a/src/connector/jdbc/pom.xml b/src/connector/jdbc/pom.xml index 9865fc7127..d18d86258a 100755 --- a/src/connector/jdbc/pom.xml +++ b/src/connector/jdbc/pom.xml @@ -3,7 +3,7 @@ 4.0.0 com.taosdata.jdbc taos-jdbcdriver - 2.0.15 + 2.0.16 jar JDBCDriver https://github.com/taosdata/TDengine/tree/master/src/connector/jdbc @@ -49,6 +49,7 @@ + junit junit @@ -56,12 +57,6 @@ test - - mysql - mysql-connector-java - 5.1.47 - - org.apache.httpcomponents @@ -79,12 +74,6 @@ 1.2.58 - - mysql - mysql-connector-java - 5.1.49 - - diff --git a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/AbstractDatabaseMetaData.java b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/AbstractDatabaseMetaData.java index 1445be1865..8ab0e4429a 100644 --- a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/AbstractDatabaseMetaData.java +++ b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/AbstractDatabaseMetaData.java @@ -497,12 +497,12 @@ public abstract class AbstractDatabaseMetaData implements DatabaseMetaData { public ResultSet getProcedures(String catalog, String schemaPattern, String procedureNamePattern) throws SQLException { - throw new SQLException(TSDBConstants.UNSUPPORT_METHOD_EXCEPTIONZ_MSG); + return null; } public ResultSet getProcedureColumns(String catalog, String schemaPattern, String procedureNamePattern, String columnNamePattern) throws SQLException { - throw new SQLException(TSDBConstants.UNSUPPORT_METHOD_EXCEPTIONZ_MSG); + return null; } public abstract ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) diff --git a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDatabaseMetaData.java b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDatabaseMetaData.java index f4dee67adf..4ea0fc7950 100644 --- a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDatabaseMetaData.java +++ b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDatabaseMetaData.java @@ -20,13 +20,11 @@ import java.util.List; public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { - private String dbProductName = null; - private String url = null; - private String userName = null; - private Connection conn = null; + private String url; + private String userName; + private Connection conn; - public TSDBDatabaseMetaData(String dbProductName, String url, String userName) { - this.dbProductName = dbProductName; + public TSDBDatabaseMetaData(String url, String userName) { this.url = url; this.userName = userName; } @@ -35,12 +33,17 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { this.conn = conn; } + @Override public T unwrap(Class iface) throws SQLException { - return null; + try { + return iface.cast(this); + } catch (ClassCastException cce) { + throw new SQLException("Unable to unwrap to " + iface.toString()); + } } public boolean isWrapperFor(Class iface) throws SQLException { - return false; + return iface.isInstance(this); } public boolean allProceduresAreCallable() throws SQLException { @@ -80,11 +83,11 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public String getDatabaseProductName() throws SQLException { - return this.dbProductName; + return "TDengine"; } public String getDatabaseProductVersion() throws SQLException { - return "1.5.1"; + return "2.0.x.x"; } public String getDriverName() throws SQLException { @@ -92,7 +95,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public String getDriverVersion() throws SQLException { - return "1.0.0"; + return "2.0.x"; } public int getDriverMajorVersion() { @@ -111,7 +114,9 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { return false; } + public boolean supportsMixedCaseIdentifiers() throws SQLException { + //像database、table这些对象的标识符,在存储时是否采用大小写混合的模式 return false; } @@ -120,7 +125,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public boolean storesLowerCaseIdentifiers() throws SQLException { - return false; + return true; } public boolean storesMixedCaseIdentifiers() throws SQLException { @@ -128,6 +133,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public boolean supportsMixedCaseQuotedIdentifiers() throws SQLException { + //像database、table这些对象的标识符,在存储时是否采用大小写混合、并带引号的模式 return false; } @@ -188,10 +194,12 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public boolean nullPlusNonNullIsNull() throws SQLException { + // null + non-null != null return false; } public boolean supportsConvert() throws SQLException { + // 是否支持转换函数convert return false; } @@ -216,7 +224,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public boolean supportsGroupBy() throws SQLException { - return false; + return true; } public boolean supportsGroupByUnrelated() throws SQLException { @@ -488,7 +496,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public int getDefaultTransactionIsolation() throws SQLException { - return 0; + return Connection.TRANSACTION_NONE; } public boolean supportsTransactions() throws SQLException { @@ -496,6 +504,8 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public boolean supportsTransactionIsolationLevel(int level) throws SQLException { + if (level == Connection.TRANSACTION_NONE) + return true; return false; } @@ -517,28 +527,27 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { public ResultSet getProcedures(String catalog, String schemaPattern, String procedureNamePattern) throws SQLException { - throw new SQLException(TSDBConstants.UNSUPPORT_METHOD_EXCEPTIONZ_MSG); + return null; } public ResultSet getProcedureColumns(String catalog, String schemaPattern, String procedureNamePattern, String columnNamePattern) throws SQLException { - throw new SQLException(TSDBConstants.UNSUPPORT_METHOD_EXCEPTIONZ_MSG); + return null; } - public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) - throws SQLException { - Statement stmt = null; - if (null != conn && !conn.isClosed()) { - stmt = conn.createStatement(); - if (catalog == null || catalog.length() < 1) { - catalog = conn.getCatalog(); - } + public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) throws SQLException { + if (conn == null || conn.isClosed()) { + throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL)); + } + + try (Statement stmt = conn.createStatement()) { + if (catalog == null || catalog.isEmpty()) + return null; + stmt.executeUpdate("use " + catalog); ResultSet resultSet0 = stmt.executeQuery("show tables"); GetTablesResultSet getTablesResultSet = new GetTablesResultSet(resultSet0, catalog, schemaPattern, tableNamePattern, types); return getTablesResultSet; - } else { - throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL)); } } @@ -547,14 +556,12 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public ResultSet getCatalogs() throws SQLException { + if (conn == null || conn.isClosed()) + throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL)); - if (conn != null && !conn.isClosed()) { - Statement stmt = conn.createStatement(); - ResultSet resultSet0 = stmt.executeQuery("show databases"); - CatalogResultSet resultSet = new CatalogResultSet(resultSet0); - return resultSet; - } else { - return getEmptyResultSet(); + try (Statement stmt = conn.createStatement()) { + ResultSet rs = stmt.executeQuery("show databases"); + return new CatalogResultSet(rs); } } @@ -562,7 +569,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { DatabaseMetaDataResultSet resultSet = new DatabaseMetaDataResultSet(); // set up ColumnMetaDataList - List columnMetaDataList = new ArrayList(1); + List columnMetaDataList = new ArrayList<>(1); ColumnMetaData colMetaData = new ColumnMetaData(); colMetaData.setColIndex(0); colMetaData.setColName("TABLE_TYPE"); @@ -571,7 +578,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { columnMetaDataList.add(colMetaData); // set up rowDataList - List rowDataList = new ArrayList(2); + List rowDataList = new ArrayList<>(2); TSDBResultSetRowData rowData = new TSDBResultSetRowData(); rowData.setString(0, "TABLE"); rowDataList.add(rowData); @@ -591,11 +598,10 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { Statement stmt = null; if (null != conn && !conn.isClosed()) { stmt = conn.createStatement(); - if (catalog == null || catalog.length() < 1) { - catalog = conn.getCatalog(); - } - stmt.executeUpdate("use " + catalog); + if (catalog == null || catalog.isEmpty()) + return null; + stmt.executeUpdate("use " + catalog); DatabaseMetaDataResultSet resultSet = new DatabaseMetaDataResultSet(); // set up ColumnMetaDataList List columnMetaDataList = new ArrayList<>(24); @@ -851,7 +857,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public Connection getConnection() throws SQLException { - return null; + return this.conn; } public boolean supportsSavepoints() throws SQLException { @@ -884,15 +890,17 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public boolean supportsResultSetHoldability(int holdability) throws SQLException { + if (holdability == ResultSet.HOLD_CURSORS_OVER_COMMIT) + return true; return false; } public int getResultSetHoldability() throws SQLException { - return 0; + return ResultSet.HOLD_CURSORS_OVER_COMMIT; } public int getDatabaseMajorVersion() throws SQLException { - return 0; + return 2; } public int getDatabaseMinorVersion() throws SQLException { @@ -900,7 +908,7 @@ public class TSDBDatabaseMetaData implements java.sql.DatabaseMetaData { } public int getJDBCMajorVersion() throws SQLException { - return 0; + return 2; } public int getJDBCMinorVersion() throws SQLException { diff --git a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDriver.java b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDriver.java index 06f88cebfa..c171ca2a36 100755 --- a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDriver.java +++ b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBDriver.java @@ -214,7 +214,7 @@ public class TSDBDriver extends AbstractTaosDriver { urlProps.setProperty(TSDBDriver.PROPERTY_KEY_HOST, url); } - this.dbMetaData = new TSDBDatabaseMetaData(dbProductName, urlForMeta, urlProps.getProperty(TSDBDriver.PROPERTY_KEY_USER)); + this.dbMetaData = new TSDBDatabaseMetaData(urlForMeta, urlProps.getProperty(TSDBDriver.PROPERTY_KEY_USER)); return urlProps; } diff --git a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBResultSet.java b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBResultSet.java index 84a3f58f46..a8a8b3ca87 100644 --- a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBResultSet.java +++ b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBResultSet.java @@ -39,7 +39,6 @@ import java.util.Iterator; import java.util.List; import java.util.Map; -@SuppressWarnings("unused") public class TSDBResultSet implements ResultSet { private TSDBJNIConnector jniConnector = null; @@ -104,6 +103,7 @@ public class TSDBResultSet implements ResultSet { } public TSDBResultSet() { + } public TSDBResultSet(TSDBJNIConnector connector, long resultSetPointer) throws SQLException { diff --git a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBStatement.java b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBStatement.java index cd2a768a38..381f1d3622 100644 --- a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBStatement.java +++ b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/TSDBStatement.java @@ -17,6 +17,7 @@ package com.taosdata.jdbc; import java.sql.*; import java.util.ArrayList; import java.util.List; +import java.util.concurrent.TimeUnit; public class TSDBStatement implements Statement { private TSDBJNIConnector connector = null; @@ -68,7 +69,6 @@ public class TSDBStatement implements Statement { pSql = this.connector.executeQuery(sql); long resultSetPointer = this.connector.getResultSet(); - if (resultSetPointer == TSDBConstants.JNI_CONNECTION_NULL) { this.connector.freeResultSet(pSql); throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL)); diff --git a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/rs/RestfulDatabaseMetaData.java b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/rs/RestfulDatabaseMetaData.java index 21d2c6402f..3c372cc503 100644 --- a/src/connector/jdbc/src/main/java/com/taosdata/jdbc/rs/RestfulDatabaseMetaData.java +++ b/src/connector/jdbc/src/main/java/com/taosdata/jdbc/rs/RestfulDatabaseMetaData.java @@ -8,7 +8,6 @@ import java.util.List; public class RestfulDatabaseMetaData extends AbstractDatabaseMetaData { - private final String url; private final String userName; private final Connection connection; diff --git a/src/connector/jdbc/src/test/java/com/taosdata/jdbc/DatabaseMetaDataTest.java b/src/connector/jdbc/src/test/java/com/taosdata/jdbc/DatabaseMetaDataTest.java deleted file mode 100644 index 19dabe0746..0000000000 --- a/src/connector/jdbc/src/test/java/com/taosdata/jdbc/DatabaseMetaDataTest.java +++ /dev/null @@ -1,245 +0,0 @@ -package com.taosdata.jdbc; - -import org.junit.AfterClass; -import org.junit.BeforeClass; -import org.junit.Test; - -import java.sql.*; -import java.util.Properties; - -public class DatabaseMetaDataTest { - static Connection connection = null; - static PreparedStatement statement = null; - static String dbName = "test"; - static String tName = "t0"; - static String host = "localhost"; - - @BeforeClass - public static void createConnection() throws SQLException { - try { - Class.forName("com.taosdata.jdbc.TSDBDriver"); - } catch (ClassNotFoundException e) { - return; - } - Properties properties = new Properties(); - properties.setProperty(TSDBDriver.PROPERTY_KEY_HOST, host); - properties.setProperty(TSDBDriver.PROPERTY_KEY_USER, "root"); - properties.setProperty(TSDBDriver.PROPERTY_KEY_PASSWORD, "taosdata"); - 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 + ":0/", properties); - - String sql = "drop database if exists " + dbName; - statement = connection.prepareStatement(sql); - statement.executeUpdate("create database if not exists " + dbName); - statement.executeUpdate("create table if not exists " + dbName + "." + tName + " (ts timestamp, k int, v int)"); - } - - @Test - public void testMetaDataTest() throws SQLException { - DatabaseMetaData databaseMetaData = connection.getMetaData(); - ResultSet resultSet = databaseMetaData.getTables(dbName, "t*", "t*", new String[]{"t"}); - while (resultSet.next()) { - for (int i = 1; i <= resultSet.getMetaData().getColumnCount(); i++) { - System.out.printf("%d: %s\n", i, resultSet.getString(i)); - } - } - resultSet.close(); - databaseMetaData.isWrapperFor(null); - databaseMetaData.allProceduresAreCallable(); - databaseMetaData.allTablesAreSelectable(); - databaseMetaData.getURL(); - databaseMetaData.getUserName(); - databaseMetaData.isReadOnly(); - databaseMetaData.nullsAreSortedHigh(); - databaseMetaData.nullsAreSortedLow(); - databaseMetaData.nullsAreSortedAtStart(); - databaseMetaData.nullsAreSortedAtEnd(); - databaseMetaData.getDatabaseProductName(); - databaseMetaData.getDatabaseProductVersion(); - databaseMetaData.getDriverName(); - databaseMetaData.getDriverVersion(); - databaseMetaData.getDriverMajorVersion(); - databaseMetaData.getDriverMinorVersion(); - databaseMetaData.usesLocalFiles(); - databaseMetaData.usesLocalFilePerTable(); - databaseMetaData.supportsMixedCaseIdentifiers(); - databaseMetaData.storesUpperCaseIdentifiers(); - databaseMetaData.storesLowerCaseIdentifiers(); - databaseMetaData.storesMixedCaseIdentifiers(); - databaseMetaData.supportsMixedCaseQuotedIdentifiers(); - databaseMetaData.storesUpperCaseQuotedIdentifiers(); - databaseMetaData.storesLowerCaseQuotedIdentifiers(); - databaseMetaData.storesMixedCaseQuotedIdentifiers(); - databaseMetaData.getIdentifierQuoteString(); - databaseMetaData.getSQLKeywords(); - databaseMetaData.getNumericFunctions(); - databaseMetaData.getStringFunctions(); - databaseMetaData.getSystemFunctions(); - databaseMetaData.getTimeDateFunctions(); - databaseMetaData.getSearchStringEscape(); - databaseMetaData.getExtraNameCharacters(); - databaseMetaData.supportsAlterTableWithAddColumn(); - databaseMetaData.supportsAlterTableWithDropColumn(); - databaseMetaData.supportsColumnAliasing(); - databaseMetaData.nullPlusNonNullIsNull(); - databaseMetaData.supportsConvert(); - databaseMetaData.supportsConvert(0, 0); - databaseMetaData.supportsTableCorrelationNames(); - databaseMetaData.supportsDifferentTableCorrelationNames(); - databaseMetaData.supportsExpressionsInOrderBy(); - databaseMetaData.supportsOrderByUnrelated(); - databaseMetaData.supportsGroupBy(); - databaseMetaData.supportsGroupByUnrelated(); - databaseMetaData.supportsGroupByBeyondSelect(); - databaseMetaData.supportsLikeEscapeClause(); - databaseMetaData.supportsMultipleResultSets(); - databaseMetaData.supportsMultipleTransactions(); - databaseMetaData.supportsNonNullableColumns(); - databaseMetaData.supportsMinimumSQLGrammar(); - databaseMetaData.supportsCoreSQLGrammar(); - databaseMetaData.supportsExtendedSQLGrammar(); - databaseMetaData.supportsANSI92EntryLevelSQL(); - databaseMetaData.supportsANSI92IntermediateSQL(); - databaseMetaData.supportsANSI92FullSQL(); - databaseMetaData.supportsIntegrityEnhancementFacility(); - databaseMetaData.supportsOuterJoins(); - databaseMetaData.supportsFullOuterJoins(); - databaseMetaData.supportsLimitedOuterJoins(); - databaseMetaData.getSchemaTerm(); - databaseMetaData.getProcedureTerm(); - databaseMetaData.getCatalogTerm(); - databaseMetaData.isCatalogAtStart(); - databaseMetaData.getCatalogSeparator(); - databaseMetaData.supportsSchemasInDataManipulation(); - databaseMetaData.supportsSchemasInProcedureCalls(); - databaseMetaData.supportsSchemasInTableDefinitions(); - databaseMetaData.supportsSchemasInIndexDefinitions(); - databaseMetaData.supportsSchemasInPrivilegeDefinitions(); - databaseMetaData.supportsCatalogsInDataManipulation(); - databaseMetaData.supportsCatalogsInProcedureCalls(); - databaseMetaData.supportsCatalogsInTableDefinitions(); - databaseMetaData.supportsCatalogsInIndexDefinitions(); - databaseMetaData.supportsCatalogsInPrivilegeDefinitions(); - databaseMetaData.supportsPositionedDelete(); - databaseMetaData.supportsPositionedUpdate(); - databaseMetaData.supportsSelectForUpdate(); - databaseMetaData.supportsStoredProcedures(); - databaseMetaData.supportsSubqueriesInComparisons(); - databaseMetaData.supportsSubqueriesInExists(); - databaseMetaData.supportsSubqueriesInIns(); - databaseMetaData.supportsSubqueriesInQuantifieds(); - databaseMetaData.supportsCorrelatedSubqueries(); - databaseMetaData.supportsUnion(); - databaseMetaData.supportsUnionAll(); - databaseMetaData.supportsOpenCursorsAcrossCommit(); - databaseMetaData.supportsOpenCursorsAcrossRollback(); - databaseMetaData.supportsOpenStatementsAcrossCommit(); - databaseMetaData.supportsOpenStatementsAcrossRollback(); - databaseMetaData.getMaxBinaryLiteralLength(); - databaseMetaData.getMaxCharLiteralLength(); - databaseMetaData.getMaxColumnNameLength(); - databaseMetaData.getMaxColumnsInGroupBy(); - databaseMetaData.getMaxColumnsInIndex(); - databaseMetaData.getMaxColumnsInOrderBy(); - databaseMetaData.getMaxColumnsInSelect(); - databaseMetaData.getMaxColumnsInTable(); - databaseMetaData.getMaxConnections(); - databaseMetaData.getMaxCursorNameLength(); - databaseMetaData.getMaxIndexLength(); - databaseMetaData.getMaxSchemaNameLength(); - databaseMetaData.getMaxProcedureNameLength(); - databaseMetaData.getMaxCatalogNameLength(); - databaseMetaData.getMaxRowSize(); - databaseMetaData.doesMaxRowSizeIncludeBlobs(); - databaseMetaData.getMaxStatementLength(); - databaseMetaData.getMaxStatements(); - databaseMetaData.getMaxTableNameLength(); - databaseMetaData.getMaxTablesInSelect(); - databaseMetaData.getMaxUserNameLength(); - databaseMetaData.getDefaultTransactionIsolation(); - databaseMetaData.supportsTransactions(); - databaseMetaData.supportsTransactionIsolationLevel(0); - databaseMetaData.supportsDataDefinitionAndDataManipulationTransactions(); - databaseMetaData.supportsDataManipulationTransactionsOnly(); - databaseMetaData.dataDefinitionCausesTransactionCommit(); - databaseMetaData.dataDefinitionIgnoredInTransactions(); - try { - databaseMetaData.getProcedures("", "", ""); - } catch (Exception e) { - } - try { - databaseMetaData.getProcedureColumns("", "", "", ""); - } catch (Exception e) { - } - try { - databaseMetaData.getTables("", "", "", new String[]{""}); - } catch (Exception e) { - } - databaseMetaData.getSchemas(); - databaseMetaData.getCatalogs(); -// databaseMetaData.getTableTypes(); - - databaseMetaData.getColumns(dbName, "", tName, ""); - databaseMetaData.getColumnPrivileges("", "", "", ""); - databaseMetaData.getTablePrivileges("", "", ""); - databaseMetaData.getBestRowIdentifier("", "", "", 0, false); - databaseMetaData.getVersionColumns("", "", ""); - databaseMetaData.getPrimaryKeys("", "", ""); - databaseMetaData.getImportedKeys("", "", ""); - databaseMetaData.getExportedKeys("", "", ""); - databaseMetaData.getCrossReference("", "", "", "", "", ""); - databaseMetaData.getTypeInfo(); - databaseMetaData.getIndexInfo("", "", "", false, false); - databaseMetaData.supportsResultSetType(0); - databaseMetaData.supportsResultSetConcurrency(0, 0); - databaseMetaData.ownUpdatesAreVisible(0); - databaseMetaData.ownDeletesAreVisible(0); - databaseMetaData.ownInsertsAreVisible(0); - databaseMetaData.othersUpdatesAreVisible(0); - databaseMetaData.othersDeletesAreVisible(0); - databaseMetaData.othersInsertsAreVisible(0); - databaseMetaData.updatesAreDetected(0); - databaseMetaData.deletesAreDetected(0); - databaseMetaData.insertsAreDetected(0); - databaseMetaData.supportsBatchUpdates(); - databaseMetaData.getUDTs("", "", "", new int[]{0}); - databaseMetaData.getConnection(); - databaseMetaData.supportsSavepoints(); - databaseMetaData.supportsNamedParameters(); - databaseMetaData.supportsMultipleOpenResults(); - databaseMetaData.supportsGetGeneratedKeys(); - databaseMetaData.getSuperTypes("", "", ""); - databaseMetaData.getSuperTables("", "", ""); - databaseMetaData.getAttributes("", "", "", ""); - databaseMetaData.supportsResultSetHoldability(0); - databaseMetaData.getResultSetHoldability(); - databaseMetaData.getDatabaseMajorVersion(); - databaseMetaData.getDatabaseMinorVersion(); - databaseMetaData.getJDBCMajorVersion(); - databaseMetaData.getJDBCMinorVersion(); - databaseMetaData.getSQLStateType(); - databaseMetaData.locatorsUpdateCopy(); - databaseMetaData.supportsStatementPooling(); - databaseMetaData.getRowIdLifetime(); - databaseMetaData.getSchemas("", ""); - databaseMetaData.supportsStoredFunctionsUsingCallSyntax(); - databaseMetaData.autoCommitFailureClosesAllResultSets(); - databaseMetaData.getClientInfoProperties(); - databaseMetaData.getFunctions("", "", ""); - databaseMetaData.getFunctionColumns("", "", "", ""); - databaseMetaData.getPseudoColumns("", "", "", ""); - databaseMetaData.generatedKeyAlwaysReturned(); - - } - - @AfterClass - public static void close() throws Exception { - statement.executeUpdate("drop database " + dbName); - statement.close(); - connection.close(); - Thread.sleep(10); - - } -} diff --git a/src/connector/jdbc/src/test/java/com/taosdata/jdbc/TSDBDatabaseMetaDataTest.java b/src/connector/jdbc/src/test/java/com/taosdata/jdbc/TSDBDatabaseMetaDataTest.java new file mode 100644 index 0000000000..448b513d0e --- /dev/null +++ b/src/connector/jdbc/src/test/java/com/taosdata/jdbc/TSDBDatabaseMetaDataTest.java @@ -0,0 +1,913 @@ +package com.taosdata.jdbc; + +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import java.sql.Connection; +import java.sql.DriverManager; +import java.sql.ResultSet; +import java.sql.SQLException; +import java.util.Properties; + +public class TSDBDatabaseMetaDataTest { + private TSDBDatabaseMetaData metaData; + private static final String host = "localhost"; + + @Before + public void before() throws ClassNotFoundException, SQLException { + Class.forName("com.taosdata.jdbc.TSDBDriver"); + Properties properties = new Properties(); + properties.setProperty(TSDBDriver.PROPERTY_KEY_HOST, host); + 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"); + metaData = (TSDBDatabaseMetaData) DriverManager.getConnection("jdbc:TAOS://" + host + ":6030/?user=root&password=taosdata", properties).getMetaData(); + } + + @Test + public void unwrap() throws SQLException { + TSDBDatabaseMetaData unwrap = metaData.unwrap(TSDBDatabaseMetaData.class); + Assert.assertNotNull(unwrap); + } + + @Test + public void isWrapperFor() throws SQLException { + Assert.assertTrue(metaData.isWrapperFor(TSDBDatabaseMetaData.class)); + } + + @Test + public void allProceduresAreCallable() throws SQLException { + Assert.assertFalse(metaData.allProceduresAreCallable()); + } + + @Test + public void allTablesAreSelectable() throws SQLException { + Assert.assertFalse(metaData.allTablesAreSelectable()); + } + + @Test + public void getURL() throws SQLException { + Assert.assertEquals("jdbc:TAOS://localhost:6030/?user=root&password=taosdata", metaData.getURL()); + } + + @Test + public void getUserName() throws SQLException { + Assert.assertEquals("root", metaData.getUserName()); + } + + @Test + public void isReadOnly() throws SQLException { + Assert.assertFalse(metaData.isReadOnly()); + } + + @Test + public void nullsAreSortedHigh() throws SQLException { + Assert.assertFalse(metaData.nullsAreSortedHigh()); + } + + @Test + public void nullsAreSortedLow() throws SQLException { + Assert.assertTrue(metaData.nullsAreSortedLow()); + } + + @Test + public void nullsAreSortedAtStart() throws SQLException { + Assert.assertTrue(metaData.nullsAreSortedAtStart()); + } + + @Test + public void nullsAreSortedAtEnd() throws SQLException { + Assert.assertFalse(metaData.nullsAreSortedAtEnd()); + } + + @Test + public void getDatabaseProductName() throws SQLException { + Assert.assertEquals("TDengine", metaData.getDatabaseProductName()); + } + + @Test + public void getDatabaseProductVersion() throws SQLException { + Assert.assertEquals("2.0.x.x", metaData.getDatabaseProductVersion()); + } + + @Test + public void getDriverName() throws SQLException { + Assert.assertEquals("com.taosdata.jdbc.TSDBDriver", metaData.getDriverName()); + } + + @Test + public void getDriverVersion() throws SQLException { + Assert.assertEquals("2.0.x", metaData.getDriverVersion()); + } + + @Test + public void getDriverMajorVersion() { + Assert.assertEquals(2, metaData.getDriverMajorVersion()); + } + + @Test + public void getDriverMinorVersion() { + Assert.assertEquals(0, metaData.getDriverMinorVersion()); + } + + @Test + public void usesLocalFiles() throws SQLException { + Assert.assertFalse(metaData.usesLocalFiles()); + } + + @Test + public void usesLocalFilePerTable() throws SQLException { + Assert.assertFalse(metaData.usesLocalFilePerTable()); + } + + @Test + public void supportsMixedCaseIdentifiers() throws SQLException { + Assert.assertFalse(metaData.supportsMixedCaseIdentifiers()); + } + + @Test + public void storesUpperCaseIdentifiers() throws SQLException { + Assert.assertFalse(metaData.storesUpperCaseIdentifiers()); + } + + @Test + public void storesLowerCaseIdentifiers() throws SQLException { + Assert.assertTrue(metaData.storesLowerCaseIdentifiers()); + } + + @Test + public void storesMixedCaseIdentifiers() throws SQLException { + Assert.assertFalse(metaData.storesMixedCaseIdentifiers()); + } + + @Test + public void supportsMixedCaseQuotedIdentifiers() throws SQLException { + Assert.assertFalse(metaData.supportsMixedCaseQuotedIdentifiers()); + } + + @Test + public void storesUpperCaseQuotedIdentifiers() throws SQLException { + Assert.assertFalse(metaData.storesUpperCaseQuotedIdentifiers()); + } + + @Test + public void storesLowerCaseQuotedIdentifiers() throws SQLException { + Assert.assertFalse(metaData.storesLowerCaseQuotedIdentifiers()); + } + + @Test + public void storesMixedCaseQuotedIdentifiers() throws SQLException { + Assert.assertFalse(metaData.storesMixedCaseQuotedIdentifiers()); + } + + @Test + public void getIdentifierQuoteString() throws SQLException { + Assert.assertEquals(" ", metaData.getIdentifierQuoteString()); + } + + @Test + public void getSQLKeywords() throws SQLException { + Assert.assertEquals(null, metaData.getSQLKeywords()); + } + + @Test + public void getNumericFunctions() throws SQLException { + Assert.assertEquals(null, metaData.getNumericFunctions()); + } + + @Test + public void getStringFunctions() throws SQLException { + Assert.assertEquals(null, metaData.getStringFunctions()); + } + + @Test + public void getSystemFunctions() throws SQLException { + Assert.assertEquals(null, metaData.getSystemFunctions()); + } + + @Test + public void getTimeDateFunctions() throws SQLException { + Assert.assertEquals(null, metaData.getTimeDateFunctions()); + } + + @Test + public void getSearchStringEscape() throws SQLException { + Assert.assertEquals(null, metaData.getSearchStringEscape()); + } + + @Test + public void getExtraNameCharacters() throws SQLException { + Assert.assertEquals(null, metaData.getExtraNameCharacters()); + } + + @Test + public void supportsAlterTableWithAddColumn() throws SQLException { + Assert.assertTrue(metaData.supportsAlterTableWithAddColumn()); + } + + @Test + public void supportsAlterTableWithDropColumn() throws SQLException { + Assert.assertTrue(metaData.supportsAlterTableWithDropColumn()); + } + + @Test + public void supportsColumnAliasing() throws SQLException { + Assert.assertTrue(metaData.supportsColumnAliasing()); + } + + @Test + public void nullPlusNonNullIsNull() throws SQLException { + Assert.assertFalse(metaData.nullPlusNonNullIsNull()); + } + + @Test + public void supportsConvert() throws SQLException { + Assert.assertFalse(metaData.supportsConvert()); + } + + @Test + public void testSupportsConvert() throws SQLException { + Assert.assertFalse(metaData.supportsConvert(1, 1)); + } + + @Test + public void supportsTableCorrelationNames() throws SQLException { + Assert.assertFalse(metaData.supportsTableCorrelationNames()); + } + + @Test + public void supportsDifferentTableCorrelationNames() throws SQLException { + Assert.assertFalse(metaData.supportsDifferentTableCorrelationNames()); + } + + @Test + public void supportsExpressionsInOrderBy() throws SQLException { + Assert.assertFalse(metaData.supportsExpressionsInOrderBy()); + } + + @Test + public void supportsOrderByUnrelated() throws SQLException { + Assert.assertFalse(metaData.supportsOrderByUnrelated()); + } + + @Test + public void supportsGroupBy() throws SQLException { + Assert.assertTrue(metaData.supportsGroupBy()); + } + + @Test + public void supportsGroupByUnrelated() throws SQLException { + Assert.assertFalse(metaData.supportsGroupByUnrelated()); + } + + @Test + public void supportsGroupByBeyondSelect() throws SQLException { + Assert.assertFalse(metaData.supportsGroupByBeyondSelect()); + } + + @Test + public void supportsLikeEscapeClause() throws SQLException { + Assert.assertFalse(metaData.supportsLikeEscapeClause()); + } + + @Test + public void supportsMultipleResultSets() throws SQLException { + Assert.assertFalse(metaData.supportsMultipleResultSets()); + } + + @Test + public void supportsMultipleTransactions() throws SQLException { + Assert.assertFalse(metaData.supportsMultipleTransactions()); + } + + @Test + public void supportsNonNullableColumns() throws SQLException { + Assert.assertFalse(metaData.supportsNonNullableColumns()); + } + + @Test + public void supportsMinimumSQLGrammar() throws SQLException { + Assert.assertFalse(metaData.supportsMinimumSQLGrammar()); + } + + @Test + public void supportsCoreSQLGrammar() throws SQLException { + Assert.assertFalse(metaData.supportsCoreSQLGrammar()); + } + + @Test + public void supportsExtendedSQLGrammar() throws SQLException { + Assert.assertFalse(metaData.supportsExtendedSQLGrammar()); + } + + @Test + public void supportsANSI92EntryLevelSQL() throws SQLException { + Assert.assertFalse(metaData.supportsANSI92EntryLevelSQL()); + } + + @Test + public void supportsANSI92IntermediateSQL() throws SQLException { + Assert.assertFalse(metaData.supportsANSI92IntermediateSQL()); + } + + @Test + public void supportsANSI92FullSQL() throws SQLException { + Assert.assertFalse(metaData.supportsANSI92FullSQL()); + } + + @Test + public void supportsIntegrityEnhancementFacility() throws SQLException { + Assert.assertFalse(metaData.supportsIntegrityEnhancementFacility()); + } + + @Test + public void supportsOuterJoins() throws SQLException { + Assert.assertFalse(metaData.supportsOuterJoins()); + } + + @Test + public void supportsFullOuterJoins() throws SQLException { + Assert.assertFalse(metaData.supportsFullOuterJoins()); + } + + @Test + public void supportsLimitedOuterJoins() throws SQLException { + Assert.assertFalse(metaData.supportsLimitedOuterJoins()); + } + + @Test + public void getSchemaTerm() throws SQLException { + Assert.assertNull(metaData.getSchemaTerm()); + } + + @Test + public void getProcedureTerm() throws SQLException { + Assert.assertNull(metaData.getProcedureTerm()); + } + + @Test + public void getCatalogTerm() throws SQLException { + Assert.assertEquals("database", metaData.getCatalogTerm()); + } + + @Test + public void isCatalogAtStart() throws SQLException { + Assert.assertTrue(metaData.isCatalogAtStart()); + } + + @Test + public void getCatalogSeparator() throws SQLException { + Assert.assertEquals(".", metaData.getCatalogSeparator()); + } + + @Test + public void supportsSchemasInDataManipulation() throws SQLException { + Assert.assertFalse(metaData.supportsSchemasInDataManipulation()); + } + + @Test + public void supportsSchemasInProcedureCalls() throws SQLException { + Assert.assertFalse(metaData.supportsSchemasInProcedureCalls()); + } + + @Test + public void supportsSchemasInTableDefinitions() throws SQLException { + Assert.assertFalse(metaData.supportsSchemasInTableDefinitions()); + } + + @Test + public void supportsSchemasInIndexDefinitions() throws SQLException { + Assert.assertFalse(metaData.supportsSchemasInIndexDefinitions()); + } + + @Test + public void supportsSchemasInPrivilegeDefinitions() throws SQLException { + Assert.assertFalse(metaData.supportsSchemasInPrivilegeDefinitions()); + } + + @Test + public void supportsCatalogsInDataManipulation() throws SQLException { + Assert.assertTrue(metaData.supportsCatalogsInDataManipulation()); + } + + @Test + public void supportsCatalogsInProcedureCalls() throws SQLException { + Assert.assertFalse(metaData.supportsCatalogsInProcedureCalls()); + } + + @Test + public void supportsCatalogsInTableDefinitions() throws SQLException { + Assert.assertFalse(metaData.supportsCatalogsInTableDefinitions()); + } + + @Test + public void supportsCatalogsInIndexDefinitions() throws SQLException { + Assert.assertFalse(metaData.supportsCatalogsInIndexDefinitions()); + } + + @Test + public void supportsCatalogsInPrivilegeDefinitions() throws SQLException { + Assert.assertFalse(metaData.supportsCatalogsInPrivilegeDefinitions()); + } + + @Test + public void supportsPositionedDelete() throws SQLException { + Assert.assertFalse(metaData.supportsPositionedDelete()); + } + + @Test + public void supportsPositionedUpdate() throws SQLException { + Assert.assertFalse(metaData.supportsPositionedUpdate()); + } + + @Test + public void supportsSelectForUpdate() throws SQLException { + Assert.assertFalse(metaData.supportsSelectForUpdate()); + } + + @Test + public void supportsStoredProcedures() throws SQLException { + Assert.assertFalse(metaData.supportsStoredProcedures()); + } + + @Test + public void supportsSubqueriesInComparisons() throws SQLException { + Assert.assertFalse(metaData.supportsSubqueriesInComparisons()); + } + + @Test + public void supportsSubqueriesInExists() throws SQLException { + Assert.assertFalse(metaData.supportsSubqueriesInExists()); + } + + @Test + public void supportsSubqueriesInIns() throws SQLException { + Assert.assertFalse(metaData.supportsSubqueriesInIns()); + } + + @Test + public void supportsSubqueriesInQuantifieds() throws SQLException { + Assert.assertFalse(metaData.supportsSubqueriesInQuantifieds()); + } + + @Test + public void supportsCorrelatedSubqueries() throws SQLException { + Assert.assertFalse(metaData.supportsCorrelatedSubqueries()); + } + + @Test + public void supportsUnion() throws SQLException { + Assert.assertFalse(metaData.supportsUnion()); + } + + @Test + public void supportsUnionAll() throws SQLException { + Assert.assertFalse(metaData.supportsUnionAll()); + } + + @Test + public void supportsOpenCursorsAcrossCommit() throws SQLException { + Assert.assertFalse(metaData.supportsOpenCursorsAcrossCommit()); + } + + @Test + public void supportsOpenCursorsAcrossRollback() throws SQLException { + Assert.assertFalse(metaData.supportsOpenCursorsAcrossRollback()); + } + + @Test + public void supportsOpenStatementsAcrossCommit() throws SQLException { + Assert.assertFalse(metaData.supportsOpenStatementsAcrossCommit()); + } + + @Test + public void supportsOpenStatementsAcrossRollback() throws SQLException { + Assert.assertFalse(metaData.supportsOpenStatementsAcrossRollback()); + } + + @Test + public void getMaxBinaryLiteralLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxBinaryLiteralLength()); + } + + @Test + public void getMaxCharLiteralLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxCharLiteralLength()); + } + + @Test + public void getMaxColumnNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxColumnNameLength()); + } + + @Test + public void getMaxColumnsInGroupBy() throws SQLException { + Assert.assertEquals(0, metaData.getMaxColumnsInGroupBy()); + } + + @Test + public void getMaxColumnsInIndex() throws SQLException { + Assert.assertEquals(0, metaData.getMaxColumnsInIndex()); + } + + @Test + public void getMaxColumnsInOrderBy() throws SQLException { + Assert.assertEquals(0, metaData.getMaxColumnsInOrderBy()); + } + + @Test + public void getMaxColumnsInSelect() throws SQLException { + Assert.assertEquals(0, metaData.getMaxColumnsInSelect()); + } + + @Test + public void getMaxColumnsInTable() throws SQLException { + Assert.assertEquals(0, metaData.getMaxColumnsInTable()); + } + + @Test + public void getMaxConnections() throws SQLException { + Assert.assertEquals(0, metaData.getMaxConnections()); + } + + @Test + public void getMaxCursorNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxCursorNameLength()); + } + + @Test + public void getMaxIndexLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxIndexLength()); + } + + @Test + public void getMaxSchemaNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxSchemaNameLength()); + } + + @Test + public void getMaxProcedureNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxProcedureNameLength()); + } + + @Test + public void getMaxCatalogNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxCatalogNameLength()); + } + + @Test + public void getMaxRowSize() throws SQLException { + Assert.assertEquals(0, metaData.getMaxRowSize()); + } + + @Test + public void doesMaxRowSizeIncludeBlobs() throws SQLException { + Assert.assertFalse(metaData.doesMaxRowSizeIncludeBlobs()); + } + + @Test + public void getMaxStatementLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxStatementLength()); + } + + @Test + public void getMaxStatements() throws SQLException { + Assert.assertEquals(0, metaData.getMaxStatements()); + } + + @Test + public void getMaxTableNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxTableNameLength()); + } + + @Test + public void getMaxTablesInSelect() throws SQLException { + Assert.assertEquals(0, metaData.getMaxTablesInSelect()); + } + + @Test + public void getMaxUserNameLength() throws SQLException { + Assert.assertEquals(0, metaData.getMaxUserNameLength()); + } + + @Test + public void getDefaultTransactionIsolation() throws SQLException { + Assert.assertEquals(Connection.TRANSACTION_NONE, metaData.getDefaultTransactionIsolation()); + } + + @Test + public void supportsTransactions() throws SQLException { + Assert.assertFalse(metaData.supportsTransactions()); + } + + @Test + public void supportsTransactionIsolationLevel() throws SQLException { + Assert.assertTrue(metaData.supportsTransactionIsolationLevel(Connection.TRANSACTION_NONE)); + Assert.assertFalse(metaData.supportsTransactionIsolationLevel(Connection.TRANSACTION_READ_COMMITTED)); + Assert.assertFalse(metaData.supportsTransactionIsolationLevel(Connection.TRANSACTION_READ_UNCOMMITTED)); + Assert.assertFalse(metaData.supportsTransactionIsolationLevel(Connection.TRANSACTION_REPEATABLE_READ)); + Assert.assertFalse(metaData.supportsTransactionIsolationLevel(Connection.TRANSACTION_SERIALIZABLE)); + } + + @Test + public void supportsDataDefinitionAndDataManipulationTransactions() throws SQLException { + Assert.assertFalse(metaData.supportsDataDefinitionAndDataManipulationTransactions()); + } + + @Test + public void supportsDataManipulationTransactionsOnly() throws SQLException { + Assert.assertFalse(metaData.supportsDataManipulationTransactionsOnly()); + } + + @Test + public void dataDefinitionCausesTransactionCommit() throws SQLException { + Assert.assertFalse(metaData.dataDefinitionCausesTransactionCommit()); + } + + @Test + public void dataDefinitionIgnoredInTransactions() throws SQLException { + Assert.assertFalse(metaData.dataDefinitionIgnoredInTransactions()); + } + + @Test + public void getProcedures() throws SQLException { + Assert.assertNull(metaData.getProcedures("*", "*", "*")); + } + + @Test + public void getProcedureColumns() throws SQLException { + Assert.assertNull(metaData.getProcedureColumns("*", "*", "*", "*")); + } + + @Test + public void getTables() throws SQLException { + Assert.assertNull(metaData.getTables("", "", "*", null)); + } + + @Test + public void getSchemas() throws SQLException { + Assert.assertNotNull(metaData.getSchemas()); + } + + @Test + public void getCatalogs() throws SQLException { + Assert.assertNotNull(metaData.getCatalogs()); + } + + @Test + public void getTableTypes() throws SQLException { + Assert.assertNotNull(metaData.getTableTypes()); + } + + @Test + public void getColumns() throws SQLException { + Assert.assertNotNull(metaData.getColumns("", "", "", "")); + } + + @Test + public void getColumnPrivileges() throws SQLException { + Assert.assertNotNull(metaData.getColumnPrivileges("", "", "", "")); + } + + @Test + public void getTablePrivileges() throws SQLException { + Assert.assertNotNull(metaData.getTablePrivileges("", "", "")); + } + + @Test + public void getBestRowIdentifier() throws SQLException { + Assert.assertNotNull(metaData.getBestRowIdentifier("", "", "", 0, false)); + } + + @Test + public void getVersionColumns() throws SQLException { + Assert.assertNotNull(metaData.getVersionColumns("", "", "")); + } + + @Test + public void getPrimaryKeys() throws SQLException { + Assert.assertNotNull(metaData.getPrimaryKeys("", "", "")); + } + + @Test + public void getImportedKeys() throws SQLException { + Assert.assertNotNull(metaData.getImportedKeys("", "", "")); + } + + @Test + public void getExportedKeys() throws SQLException { + Assert.assertNotNull(metaData.getExportedKeys("", "", "")); + } + + @Test + public void getCrossReference() throws SQLException { + Assert.assertNotNull(metaData.getCrossReference("", "", "", "", "", "")); + } + + @Test + public void getTypeInfo() throws SQLException { + Assert.assertNotNull(metaData.getTypeInfo()); + } + + @Test + public void getIndexInfo() throws SQLException { + Assert.assertNotNull(metaData.getIndexInfo("", "", "", false, false)); + } + + @Test + public void supportsResultSetType() throws SQLException { + Assert.assertFalse(metaData.supportsResultSetType(0)); + } + + @Test + public void supportsResultSetConcurrency() throws SQLException { + Assert.assertFalse(metaData.supportsResultSetConcurrency(0, 0)); + } + + @Test + public void ownUpdatesAreVisible() throws SQLException { + Assert.assertFalse(metaData.ownUpdatesAreVisible(0)); + } + + @Test + public void ownDeletesAreVisible() throws SQLException { + Assert.assertFalse(metaData.ownDeletesAreVisible(0)); + } + + @Test + public void ownInsertsAreVisible() throws SQLException { + Assert.assertFalse(metaData.ownInsertsAreVisible(0)); + } + + @Test + public void othersUpdatesAreVisible() throws SQLException { + Assert.assertFalse(metaData.othersUpdatesAreVisible(0)); + } + + @Test + public void othersDeletesAreVisible() throws SQLException { + Assert.assertFalse(metaData.othersDeletesAreVisible(0)); + } + + @Test + public void othersInsertsAreVisible() throws SQLException { + Assert.assertFalse(metaData.othersInsertsAreVisible(0)); + } + + @Test + public void updatesAreDetected() throws SQLException { + Assert.assertFalse(metaData.updatesAreDetected(0)); + } + + @Test + public void deletesAreDetected() throws SQLException { + Assert.assertFalse(metaData.deletesAreDetected(0)); + } + + @Test + public void insertsAreDetected() throws SQLException { + Assert.assertFalse(metaData.insertsAreDetected(0)); + } + + @Test + public void supportsBatchUpdates() throws SQLException { + Assert.assertFalse(metaData.supportsBatchUpdates()); + } + + @Test + public void getUDTs() throws SQLException { + Assert.assertNotNull(metaData.getUDTs("", "", "", null)); + } + + @Test + public void getConnection() throws SQLException { + Assert.assertNotNull(metaData.getConnection()); + } + + @Test + public void supportsSavepoints() throws SQLException { + Assert.assertFalse(metaData.supportsSavepoints()); + } + + @Test + public void supportsNamedParameters() throws SQLException { + Assert.assertFalse(metaData.supportsNamedParameters()); + } + + @Test + public void supportsMultipleOpenResults() throws SQLException { + Assert.assertFalse(metaData.supportsMultipleOpenResults()); + } + + @Test + public void supportsGetGeneratedKeys() throws SQLException { + Assert.assertFalse(metaData.supportsGetGeneratedKeys()); + } + + @Test + public void getSuperTypes() throws SQLException { + Assert.assertNotNull(metaData.getSuperTypes("", "", "")); + } + + @Test + public void getSuperTables() throws SQLException { + Assert.assertNotNull(metaData.getSuperTables("", "", "")); + } + + @Test + public void getAttributes() throws SQLException { + Assert.assertNotNull(metaData.getAttributes("", "", "", "")); + } + + @Test + public void supportsResultSetHoldability() throws SQLException { + Assert.assertTrue(metaData.supportsResultSetHoldability(ResultSet.HOLD_CURSORS_OVER_COMMIT)); + Assert.assertFalse(metaData.supportsResultSetHoldability(ResultSet.CLOSE_CURSORS_AT_COMMIT)); + } + + @Test + public void getResultSetHoldability() throws SQLException { + Assert.assertEquals(1, metaData.getResultSetHoldability()); + } + + @Test + public void getDatabaseMajorVersion() throws SQLException { + Assert.assertEquals(2, metaData.getDatabaseMajorVersion()); + } + + @Test + public void getDatabaseMinorVersion() throws SQLException { + Assert.assertEquals(0, metaData.getDatabaseMinorVersion()); + } + + @Test + public void getJDBCMajorVersion() throws SQLException { + Assert.assertEquals(2, metaData.getJDBCMajorVersion()); + } + + @Test + public void getJDBCMinorVersion() throws SQLException { + Assert.assertEquals(0, metaData.getJDBCMinorVersion()); + } + + @Test + public void getSQLStateType() throws SQLException { + Assert.assertEquals(0, metaData.getSQLStateType()); + } + + @Test + public void locatorsUpdateCopy() throws SQLException { + Assert.assertFalse(metaData.locatorsUpdateCopy()); + } + + @Test + public void supportsStatementPooling() throws SQLException { + Assert.assertFalse(metaData.supportsStatementPooling()); + } + + @Test + public void getRowIdLifetime() throws SQLException { + Assert.assertNull(metaData.getRowIdLifetime()); + } + + @Test + public void testGetSchemas() throws SQLException { + Assert.assertNull(metaData.getSchemas()); + } + + @Test + public void supportsStoredFunctionsUsingCallSyntax() throws SQLException { + Assert.assertFalse(metaData.supportsStoredFunctionsUsingCallSyntax()); + } + + @Test + public void autoCommitFailureClosesAllResultSets() throws SQLException { + Assert.assertFalse(metaData.autoCommitFailureClosesAllResultSets()); + } + + @Test + public void getClientInfoProperties() throws SQLException { + Assert.assertNotNull(metaData.getClientInfoProperties()); + } + + @Test + public void getFunctions() throws SQLException { + Assert.assertNotNull(metaData.getFunctions("", "", "")); + } + + @Test + public void getFunctionColumns() throws SQLException { + Assert.assertNotNull(metaData.getFunctionColumns("", "", "", "")); + } + + @Test + public void getPseudoColumns() throws SQLException { + Assert.assertNotNull(metaData.getPseudoColumns("", "", "", "")); + } + + @Test + public void generatedKeyAlwaysReturned() throws SQLException { + Assert.assertFalse(metaData.generatedKeyAlwaysReturned()); + } +} \ No newline at end of file diff --git a/src/connector/jdbc/src/test/java/com/taosdata/jdbc/cases/MultiThreadsWithSameStatmentTest.java b/src/connector/jdbc/src/test/java/com/taosdata/jdbc/cases/MultiThreadsWithSameStatmentTest.java new file mode 100644 index 0000000000..5cb76cc0cb --- /dev/null +++ b/src/connector/jdbc/src/test/java/com/taosdata/jdbc/cases/MultiThreadsWithSameStatmentTest.java @@ -0,0 +1,91 @@ +package com.taosdata.jdbc.cases; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import java.sql.*; +import java.util.concurrent.TimeUnit; + +public class MultiThreadsWithSameStatmentTest { + + + private class Service { + public Connection conn; + public Statement stmt; + + public Service() { + try { + Class.forName("com.taosdata.jdbc.TSDBDriver"); + conn = DriverManager.getConnection("jdbc:TAOS://localhost:6030/?user=root&password=taosdata"); + stmt = conn.createStatement(); + stmt.execute("create database if not exists jdbctest"); + stmt.executeUpdate("create table if not exists jdbctest.weather (ts timestamp, f1 int)"); + } catch (ClassNotFoundException | SQLException e) { + e.printStackTrace(); + } + } + + public void release() { + try { + stmt.close(); + conn.close(); + } catch (SQLException e) { + e.printStackTrace(); + } + } + } + + @Before + public void before() { + } + + @Test + public void test() { + Thread t1 = new Thread(() -> { + try { + Service service = new Service(); + ResultSet resultSet = service.stmt.executeQuery("select * from jdbctest.weather"); + while (resultSet.next()) { + ResultSetMetaData metaData = resultSet.getMetaData(); + for (int i = 1; i <= metaData.getColumnCount(); i++) { + System.out.print(metaData.getColumnLabel(i) + ": " + resultSet.getString(i)); + } + System.out.println(); + } + resultSet.close(); + service.release(); + } catch (SQLException e) { + e.printStackTrace(); + } + }); + + Thread t2 = new Thread(() -> { + while (true) { + try { + Service service = new Service(); + service.stmt.executeUpdate("insert into jdbctest.weather values(now,1)"); + service.release(); + } catch (SQLException e) { + e.printStackTrace(); + } + } + + }); + t1.start(); + sleep(1000); + t2.start(); + } + + private void sleep(long mills) { + try { + TimeUnit.MILLISECONDS.sleep(mills); + } catch (InterruptedException e) { + e.printStackTrace(); + } + } + + @After + public void after() { + } +} diff --git a/src/connector/odbc/CMakeLists.txt b/src/connector/odbc/CMakeLists.txt index 0d8c07041a..2e1e39ef12 100644 --- a/src/connector/odbc/CMakeLists.txt +++ b/src/connector/odbc/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX_64) diff --git a/src/connector/odbc/src/CMakeLists.txt b/src/connector/odbc/src/CMakeLists.txt index 2699e1bc90..67357cb469 100644 --- a/src/connector/odbc/src/CMakeLists.txt +++ b/src/connector/odbc/src/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX_64) diff --git a/src/connector/python/linux/python2/setup.py b/src/connector/python/linux/python2/setup.py index 92a931b504..2cad664307 100644 --- a/src/connector/python/linux/python2/setup.py +++ b/src/connector/python/linux/python2/setup.py @@ -5,7 +5,7 @@ with open("README.md", "r") as fh: setuptools.setup( name="taos", - version="2.0.3", + version="2.0.4", author="Taosdata Inc.", author_email="support@taosdata.com", description="TDengine python client package", diff --git a/src/connector/python/linux/python2/taos/cursor.py b/src/connector/python/linux/python2/taos/cursor.py index 82a01be671..ada83d72c5 100644 --- a/src/connector/python/linux/python2/taos/cursor.py +++ b/src/connector/python/linux/python2/taos/cursor.py @@ -184,7 +184,7 @@ class TDengineCursor(object): return False - def fetchall(self): + def fetchall_row(self): """Fetch all (remaining) rows of a query result, returning them as a sequence of sequences (e.g. a list of tuples). Note that the cursor's arraysize attribute can affect the performance of this operation. """ if self._result is None or self._fields is None: @@ -203,7 +203,7 @@ class TDengineCursor(object): for i in range(len(self._fields)): buffer[i].extend(block[i]) return list(map(tuple, zip(*buffer))) - def fetchall_block(self): + def fetchall(self): if self._result is None or self._fields is None: raise OperationalError("Invalid use of fetchall") diff --git a/src/connector/python/linux/python3/setup.py b/src/connector/python/linux/python3/setup.py index 655a12ad13..e238372cd3 100644 --- a/src/connector/python/linux/python3/setup.py +++ b/src/connector/python/linux/python3/setup.py @@ -5,7 +5,7 @@ with open("README.md", "r") as fh: setuptools.setup( name="taos", - version="2.0.3", + version="2.0.4", author="Taosdata Inc.", author_email="support@taosdata.com", description="TDengine python client package", diff --git a/src/connector/python/linux/python3/taos/cursor.py b/src/connector/python/linux/python3/taos/cursor.py index 0ce20f0eda..f972d2ff07 100644 --- a/src/connector/python/linux/python3/taos/cursor.py +++ b/src/connector/python/linux/python3/taos/cursor.py @@ -192,7 +192,7 @@ class TDengineCursor(object): return False - def fetchall(self): + def fetchall_row(self): """Fetch all (remaining) rows of a query result, returning them as a sequence of sequences (e.g. a list of tuples). Note that the cursor's arraysize attribute can affect the performance of this operation. """ if self._result is None or self._fields is None: @@ -212,7 +212,7 @@ class TDengineCursor(object): buffer[i].extend(block[i]) return list(map(tuple, zip(*buffer))) - def fetchall_block(self): + def fetchall(self): if self._result is None or self._fields is None: raise OperationalError("Invalid use of fetchall") diff --git a/src/connector/python/windows/python2/setup.py b/src/connector/python/windows/python2/setup.py index 5ddbe83011..333f5bedad 100644 --- a/src/connector/python/windows/python2/setup.py +++ b/src/connector/python/windows/python2/setup.py @@ -5,7 +5,7 @@ with open("README.md", "r") as fh: setuptools.setup( name="taos", - version="2.0.3", + version="2.0.4", author="Taosdata Inc.", author_email="support@taosdata.com", description="TDengine python client package", diff --git a/src/connector/python/windows/python2/taos/cursor.py b/src/connector/python/windows/python2/taos/cursor.py index f6fde2619b..958466985e 100644 --- a/src/connector/python/windows/python2/taos/cursor.py +++ b/src/connector/python/windows/python2/taos/cursor.py @@ -138,7 +138,7 @@ class TDengineCursor(object): def fetchmany(self): pass - def fetchall(self): + def fetchall_row(self): """Fetch all (remaining) rows of a query result, returning them as a sequence of sequences (e.g. a list of tuples). Note that the cursor's arraysize attribute can affect the performance of this operation. """ if self._result is None or self._fields is None: @@ -158,7 +158,7 @@ class TDengineCursor(object): buffer[i].extend(block[i]) return list(map(tuple, zip(*buffer))) - def fetchall_block(self): + def fetchall(self): if self._result is None or self._fields is None: raise OperationalError("Invalid use of fetchall") diff --git a/src/connector/python/windows/python3/setup.py b/src/connector/python/windows/python3/setup.py index ffed304c85..f29fec121b 100644 --- a/src/connector/python/windows/python3/setup.py +++ b/src/connector/python/windows/python3/setup.py @@ -5,7 +5,7 @@ with open("README.md", "r") as fh: setuptools.setup( name="taos", - version="2.0.3", + version="2.0.4", author="Taosdata Inc.", author_email="support@taosdata.com", description="TDengine python client package", diff --git a/src/connector/python/windows/python3/taos/cursor.py b/src/connector/python/windows/python3/taos/cursor.py index db66b99d3b..bbac1b1dd5 100644 --- a/src/connector/python/windows/python3/taos/cursor.py +++ b/src/connector/python/windows/python3/taos/cursor.py @@ -139,7 +139,7 @@ class TDengineCursor(object): def fetchmany(self): pass - def fetchall(self): + def fetchall_row(self): """Fetch all (remaining) rows of a query result, returning them as a sequence of sequences (e.g. a list of tuples). Note that the cursor's arraysize attribute can affect the performance of this operation. """ if self._result is None or self._fields is None: @@ -159,7 +159,7 @@ class TDengineCursor(object): buffer[i].extend(block[i]) return list(map(tuple, zip(*buffer))) - def fetchall_block(self): + def fetchall(self): if self._result is None or self._fields is None: raise OperationalError("Invalid use of fetchall") diff --git a/src/cq/CMakeLists.txt b/src/cq/CMakeLists.txt index e631397348..9da831c9c1 100644 --- a/src/cq/CMakeLists.txt +++ b/src/cq/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/cq/src/cqMain.c b/src/cq/src/cqMain.c index a0df8247b7..0fe5ea78d4 100644 --- a/src/cq/src/cqMain.c +++ b/src/cq/src/cqMain.c @@ -43,7 +43,7 @@ typedef struct { int32_t master; int32_t num; // number of continuous streams char user[TSDB_USER_LEN]; - char pass[TSDB_PASSWORD_LEN]; + char pass[TSDB_KEY_LEN]; char db[TSDB_DB_NAME_LEN]; FCqWrite cqWrite; struct SCqObj *pHead; diff --git a/src/cq/test/CMakeLists.txt b/src/cq/test/CMakeLists.txt index 59c0ac79cf..87a8705fcd 100644 --- a/src/cq/test/CMakeLists.txt +++ b/src/cq/test/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) LIST(APPEND CQTEST_SRC ./cqtest.c) diff --git a/src/dnode/CMakeLists.txt b/src/dnode/CMakeLists.txt index ebb25bf858..699ca00a25 100644 --- a/src/dnode/CMakeLists.txt +++ b/src/dnode/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/query/inc) diff --git a/src/dnode/src/dnodeShell.c b/src/dnode/src/dnodeShell.c index 79cc70005b..fbdf7f7b40 100644 --- a/src/dnode/src/dnodeShell.c +++ b/src/dnode/src/dnodeShell.c @@ -216,7 +216,7 @@ void *dnodeSendCfgTableToRecv(int32_t vgId, int32_t tid) { int16_t numOfTags = htons(pTable->numOfTags); int32_t tableId = htonl(pTable->tid); uint64_t uid = htobe64(pTable->uid); - dInfo("table:%s, numOfColumns:%d numOfTags:%d tid:%d uid:%" PRIu64, pTable->tableId, numOfColumns, numOfTags, tableId, uid); + dInfo("table:%s, numOfColumns:%d numOfTags:%d tid:%d uid:%" PRIu64, pTable->tableFname, numOfColumns, numOfTags, tableId, uid); return rpcRsp.pCont; } diff --git a/src/dnode/src/dnodeVWrite.c b/src/dnode/src/dnodeVWrite.c index 588e577cd8..ab5a4ccaad 100644 --- a/src/dnode/src/dnodeVWrite.c +++ b/src/dnode/src/dnodeVWrite.c @@ -202,12 +202,12 @@ static void *dnodeProcessVWriteQueue(void *wparam) { for (int32_t i = 0; i < numOfMsgs; ++i) { taosGetQitem(pWorker->qall, &qtype, (void **)&pWrite); dTrace("msg:%p, app:%p type:%s will be processed in vwrite queue, qtype:%s hver:%" PRIu64, pWrite, - pWrite->rpcMsg.ahandle, taosMsg[pWrite->pHead->msgType], qtypeStr[qtype], pWrite->pHead->version); + pWrite->rpcMsg.ahandle, taosMsg[pWrite->pHead.msgType], qtypeStr[qtype], pWrite->pHead.version); - pWrite->code = vnodeProcessWrite(pVnode, pWrite->pHead, qtype, pWrite); + pWrite->code = vnodeProcessWrite(pVnode, &pWrite->pHead, qtype, pWrite); if (pWrite->code <= 0) pWrite->processedCount = 1; if (pWrite->code > 0) pWrite->code = 0; - if (pWrite->code == 0 && pWrite->pHead->msgType != TSDB_MSG_TYPE_SUBMIT) forceFsync = true; + if (pWrite->code == 0 && pWrite->pHead.msgType != TSDB_MSG_TYPE_SUBMIT) forceFsync = true; dTrace("msg:%p is processed in vwrite queue, code:0x%x", pWrite, pWrite->code); } @@ -222,7 +222,7 @@ static void *dnodeProcessVWriteQueue(void *wparam) { dnodeSendRpcVWriteRsp(pVnode, pWrite, pWrite->code); } else { if (qtype == TAOS_QTYPE_FWD) { - vnodeConfirmForward(pVnode, pWrite->pHead->version, 0); + vnodeConfirmForward(pVnode, pWrite->pHead.version, 0); } if (pWrite->rspRet.rsp) { rpcFreeCont(pWrite->rspRet.rsp); diff --git a/src/inc/taos.h b/src/inc/taos.h index 5e4f50e31d..05d390ffd0 100644 --- a/src/inc/taos.h +++ b/src/inc/taos.h @@ -140,7 +140,7 @@ DLL_EXPORT int taos_errno(TAOS_RES *tres); DLL_EXPORT void taos_query_a(TAOS *taos, const char *sql, void (*fp)(void *param, TAOS_RES *, int code), void *param); DLL_EXPORT void taos_fetch_rows_a(TAOS_RES *res, void (*fp)(void *param, TAOS_RES *, int numOfRows), void *param); -DLL_EXPORT void taos_fetch_row_a(TAOS_RES *res, void (*fp)(void *param, TAOS_RES *, TAOS_ROW row), void *param); +//DLL_EXPORT void taos_fetch_row_a(TAOS_RES *res, void (*fp)(void *param, TAOS_RES *, TAOS_ROW row), void *param); typedef void (*TAOS_SUBSCRIBE_CALLBACK)(TAOS_SUB* tsub, TAOS_RES *res, void* param, int code); DLL_EXPORT TAOS_SUB *taos_subscribe(TAOS* taos, int restart, const char* topic, const char *sql, TAOS_SUBSCRIBE_CALLBACK fp, void *param, int interval); diff --git a/src/inc/taosdef.h b/src/inc/taosdef.h index 3599cf86d8..d751dbb969 100644 --- a/src/inc/taosdef.h +++ b/src/inc/taosdef.h @@ -36,29 +36,6 @@ extern "C" { #define TSWINDOW_INITIALIZER ((STimeWindow) {INT64_MIN, INT64_MAX}) #define TSKEY_INITIAL_VAL INT64_MIN -// ----------------- For variable data types such as TSDB_DATA_TYPE_BINARY and TSDB_DATA_TYPE_NCHAR -typedef int32_t VarDataOffsetT; -typedef int16_t VarDataLenT; - -typedef struct tstr { - VarDataLenT len; - char data[]; -} tstr; - -#define VARSTR_HEADER_SIZE sizeof(VarDataLenT) - -#define varDataLen(v) ((VarDataLenT *)(v))[0] -#define varDataTLen(v) (sizeof(VarDataLenT) + varDataLen(v)) -#define varDataVal(v) ((void *)((char *)v + VARSTR_HEADER_SIZE)) -#define varDataCopy(dst, v) memcpy((dst), (void*) (v), varDataTLen(v)) -#define varDataLenByData(v) (*(VarDataLenT *)(((char*)(v)) - VARSTR_HEADER_SIZE)) -#define varDataSetLen(v, _len) (((VarDataLenT *)(v))[0] = (VarDataLenT) (_len)) -#define IS_VAR_DATA_TYPE(t) (((t) == TSDB_DATA_TYPE_BINARY) || ((t) == TSDB_DATA_TYPE_NCHAR)) - -// this data type is internally used only in 'in' query to hold the values -#define TSDB_DATA_TYPE_ARRAY (TSDB_DATA_TYPE_NCHAR + 1) - - // Bytes for each type. extern const int32_t TYPE_BYTES[15]; @@ -164,70 +141,6 @@ do { \ #define SET_DOUBLE_PTR(x, y) { (*(double *)(x)) = (*(double *)(y)); } #endif -typedef struct tDataTypeDescriptor { - int16_t nType; - int16_t nameLen; - int32_t nSize; - char * aName; - int (*compFunc)(const char *const input, int inputSize, const int nelements, char *const output, int outputSize, - char algorithm, char *const buffer, int bufferSize); - int (*decompFunc)(const char *const input, int compressedSize, const int nelements, char *const output, - int outputSize, char algorithm, char *const buffer, int bufferSize); - void (*getStatisFunc)(const void *pData, int32_t numofrow, int64_t *min, int64_t *max, int64_t *sum, - int16_t *minindex, int16_t *maxindex, int16_t *numofnull); -} tDataTypeDescriptor; - -extern tDataTypeDescriptor tDataTypeDesc[15]; - -bool isValidDataType(int32_t type); - -static FORCE_INLINE bool isNull(const char *val, int32_t type) { - switch (type) { - case TSDB_DATA_TYPE_BOOL: - return *(uint8_t *)val == TSDB_DATA_BOOL_NULL; - case TSDB_DATA_TYPE_TINYINT: - return *(uint8_t *)val == TSDB_DATA_TINYINT_NULL; - case TSDB_DATA_TYPE_SMALLINT: - return *(uint16_t *)val == TSDB_DATA_SMALLINT_NULL; - case TSDB_DATA_TYPE_INT: - return *(uint32_t *)val == TSDB_DATA_INT_NULL; - case TSDB_DATA_TYPE_BIGINT: - case TSDB_DATA_TYPE_TIMESTAMP: - return *(uint64_t *)val == TSDB_DATA_BIGINT_NULL; - case TSDB_DATA_TYPE_FLOAT: - return *(uint32_t *)val == TSDB_DATA_FLOAT_NULL; - case TSDB_DATA_TYPE_DOUBLE: - return *(uint64_t *)val == TSDB_DATA_DOUBLE_NULL; - case TSDB_DATA_TYPE_NCHAR: - return varDataLen(val) == sizeof(int32_t) && *(uint32_t*) varDataVal(val) == TSDB_DATA_NCHAR_NULL; - case TSDB_DATA_TYPE_BINARY: - return varDataLen(val) == sizeof(int8_t) && *(uint8_t *) varDataVal(val) == TSDB_DATA_BINARY_NULL; - case TSDB_DATA_TYPE_UTINYINT: - return *(uint8_t*) val == TSDB_DATA_UTINYINT_NULL; - case TSDB_DATA_TYPE_USMALLINT: - return *(uint16_t*) val == TSDB_DATA_USMALLINT_NULL; - case TSDB_DATA_TYPE_UINT: - return *(uint32_t*) val == TSDB_DATA_UINT_NULL; - case TSDB_DATA_TYPE_UBIGINT: - return *(uint64_t*) val == TSDB_DATA_UBIGINT_NULL; - - default: - return false; - }; -} - -void setVardataNull(char* val, int32_t type); -void setNull(char *val, int32_t type, int32_t bytes); -void setNullN(char *val, int32_t type, int32_t bytes, int32_t numOfElems); -void* getNullValue(int32_t type); - -void assignVal(char *val, const char *src, int32_t len, int32_t type); -void tsDataSwap(void *pLeft, void *pRight, int32_t type, int32_t size, void* buf); - -int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bool issigned); - -#define SET_DOUBLE_NULL(v) (*(uint64_t *)(v) = TSDB_DATA_DOUBLE_NULL) - // TODO: check if below is necessary #define TSDB_RELATION_INVALID 0 #define TSDB_RELATION_LESS 1 @@ -256,10 +169,8 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_USER_LEN TSDB_UNI_LEN // ACCOUNT is a 32 bit positive integer -// this is the length of its string representation -// including the terminator zero -#define TSDB_ACCT_LEN 11 -#define TSDB_PASSWORD_LEN TSDB_UNI_LEN +// this is the length of its string representation, including the terminator zero +#define TSDB_ACCT_ID_LEN 11 #define TSDB_MAX_COLUMNS 1024 #define TSDB_MIN_COLUMNS 2 //PRIMARY COLUMN(timestamp) + other columns @@ -267,12 +178,12 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_NODE_NAME_LEN 64 #define TSDB_TABLE_NAME_LEN 193 // it is a null-terminated string #define TSDB_DB_NAME_LEN 33 -#define TSDB_TABLE_FNAME_LEN (TSDB_ACCT_LEN + TSDB_DB_NAME_LEN + TSDB_TABLE_NAME_LEN) +#define TSDB_TABLE_FNAME_LEN (TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN + TSDB_TABLE_NAME_LEN) #define TSDB_COL_NAME_LEN 65 #define TSDB_MAX_SAVED_SQL_LEN TSDB_MAX_COLUMNS * 64 #define TSDB_MAX_SQL_LEN TSDB_PAYLOAD_SIZE #define TSDB_MAX_SQL_SHOW_LEN 512 -#define TSDB_MAX_ALLOWED_SQL_LEN (1*1024*1024U) // sql length should be less than 1mb +#define TSDB_MAX_ALLOWED_SQL_LEN (1*1024*1024u) // sql length should be less than 1mb #define TSDB_APPNAME_LEN TSDB_UNI_LEN @@ -293,11 +204,6 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_EP_LEN (TSDB_FQDN_LEN+6) #define TSDB_IPv4ADDR_LEN 16 #define TSDB_FILENAME_LEN 128 -#define TSDB_METER_VNODE_BITS 20 -#define TSDB_METER_SID_MASK 0xFFFFF -#define TSDB_SHELL_VNODE_BITS 24 -#define TSDB_SHELL_SID_MASK 0xFF -#define TSDB_HTTP_TOKEN_LEN 20 #define TSDB_SHOW_SQL_LEN 512 #define TSDB_SLOW_QUERY_SQL_LEN 512 @@ -311,9 +217,6 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_MQTT_TOPIC_LEN 64 #define TSDB_MQTT_CLIENT_ID_LEN 32 -#define TSDB_METER_STATE_OFFLINE 0 -#define TSDB_METER_STATE_ONLLINE 1 - #define TSDB_DEFAULT_PKT_SIZE 65480 //same as RPC_MAX_UDP_SIZE #define TSDB_PAYLOAD_SIZE TSDB_DEFAULT_PKT_SIZE @@ -333,7 +236,7 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_TBNAME_COLUMN_INDEX (-1) #define TSDB_UD_COLUMN_INDEX (-100) -#define TSDB_MULTI_METERMETA_MAX_NUM 100000 // maximum batch size allowed to load metermeta +#define TSDB_MULTI_TABLEMETA_MAX_NUM 100000 // maximum batch size allowed to load table meta #define TSDB_MIN_CACHE_BLOCK_SIZE 1 #define TSDB_MAX_CACHE_BLOCK_SIZE 128 // 128MB for each vnode @@ -409,8 +312,8 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_MAX_RPC_THREADS 5 -#define TSDB_QUERY_TYPE_NON_TYPE 0x00u // none type -#define TSDB_QUERY_TYPE_FREE_RESOURCE 0x01u // free qhandle at vnode +#define TSDB_QUERY_TYPE_NON_TYPE 0x00u // none type +#define TSDB_QUERY_TYPE_FREE_RESOURCE 0x01u // free qhandle at vnode /* * 1. ordinary sub query for select * from super_table @@ -430,31 +333,31 @@ int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bo #define TSDB_QUERY_TYPE_MULTITABLE_QUERY 0x200u #define TSDB_QUERY_TYPE_STMT_INSERT 0x800u // stmt insert type -#define TSDB_QUERY_HAS_TYPE(x, _type) (((x) & (_type)) != 0) -#define TSDB_QUERY_SET_TYPE(x, _type) ((x) |= (_type)) -#define TSDB_QUERY_CLEAR_TYPE(x, _type) ((x) &= (~_type)) -#define TSDB_QUERY_RESET_TYPE(x) ((x) = TSDB_QUERY_TYPE_NON_TYPE) +#define TSDB_QUERY_HAS_TYPE(x, _type) (((x) & (_type)) != 0) +#define TSDB_QUERY_SET_TYPE(x, _type) ((x) |= (_type)) +#define TSDB_QUERY_CLEAR_TYPE(x, _type) ((x) &= (~_type)) +#define TSDB_QUERY_RESET_TYPE(x) ((x) = TSDB_QUERY_TYPE_NON_TYPE) -#define TSDB_ORDER_ASC 1 -#define TSDB_ORDER_DESC 2 +#define TSDB_ORDER_ASC 1 +#define TSDB_ORDER_DESC 2 + +#define TSDB_DEFAULT_CLUSTER_HASH_SIZE 1 +#define TSDB_DEFAULT_MNODES_HASH_SIZE 5 +#define TSDB_DEFAULT_DNODES_HASH_SIZE 10 +#define TSDB_DEFAULT_ACCOUNTS_HASH_SIZE 10 +#define TSDB_DEFAULT_USERS_HASH_SIZE 20 +#define TSDB_DEFAULT_DBS_HASH_SIZE 100 +#define TSDB_DEFAULT_VGROUPS_HASH_SIZE 100 +#define TSDB_DEFAULT_STABLES_HASH_SIZE 100 +#define TSDB_DEFAULT_CTABLES_HASH_SIZE 20000 -#define TSDB_DEFAULT_CLUSTER_HASH_SIZE 1 -#define TSDB_DEFAULT_MNODES_HASH_SIZE 5 -#define TSDB_DEFAULT_DNODES_HASH_SIZE 10 -#define TSDB_DEFAULT_ACCOUNTS_HASH_SIZE 10 -#define TSDB_DEFAULT_USERS_HASH_SIZE 20 -#define TSDB_DEFAULT_DBS_HASH_SIZE 100 -#define TSDB_DEFAULT_VGROUPS_HASH_SIZE 100 -#define TSDB_DEFAULT_STABLES_HASH_SIZE 100 -#define TSDB_DEFAULT_CTABLES_HASH_SIZE 20000 +#define TSDB_PORT_DNODESHELL 0 +#define TSDB_PORT_DNODEDNODE 5 +#define TSDB_PORT_SYNC 10 +#define TSDB_PORT_HTTP 11 +#define TSDB_PORT_ARBITRATOR 12 -#define TSDB_PORT_DNODESHELL 0 -#define TSDB_PORT_DNODEDNODE 5 -#define TSDB_PORT_SYNC 10 -#define TSDB_PORT_HTTP 11 -#define TSDB_PORT_ARBITRATOR 12 - -#define TSDB_MAX_WAL_SIZE (1024*1024*2) +#define TSDB_MAX_WAL_SIZE (1024*1024*3) typedef enum { TAOS_QTYPE_RPC = 0, diff --git a/src/inc/taosmsg.h b/src/inc/taosmsg.h index 2dee6dc3bb..4582efbc40 100644 --- a/src/inc/taosmsg.h +++ b/src/inc/taosmsg.h @@ -153,30 +153,31 @@ enum _mgmt_table { #define TSDB_ALTER_TABLE_DROP_COLUMN 6 #define TSDB_ALTER_TABLE_CHANGE_COLUMN 7 -#define TSDB_FILL_NONE 0 -#define TSDB_FILL_NULL 1 -#define TSDB_FILL_SET_VALUE 2 -#define TSDB_FILL_LINEAR 3 -#define TSDB_FILL_PREV 4 +#define TSDB_FILL_NONE 0 +#define TSDB_FILL_NULL 1 +#define TSDB_FILL_SET_VALUE 2 +#define TSDB_FILL_LINEAR 3 +#define TSDB_FILL_PREV 4 +#define TSDB_FILL_NEXT 5 -#define TSDB_ALTER_USER_PASSWD 0x1 +#define TSDB_ALTER_USER_PASSWD 0x1 #define TSDB_ALTER_USER_PRIVILEGES 0x2 -#define TSDB_KILL_MSG_LEN 30 +#define TSDB_KILL_MSG_LEN 30 -#define TSDB_VN_READ_ACCCESS ((char)0x1) -#define TSDB_VN_WRITE_ACCCESS ((char)0x2) +#define TSDB_VN_READ_ACCCESS ((char)0x1) +#define TSDB_VN_WRITE_ACCCESS ((char)0x2) #define TSDB_VN_ALL_ACCCESS (TSDB_VN_READ_ACCCESS | TSDB_VN_WRITE_ACCCESS) -#define TSDB_COL_NORMAL 0x0u // the normal column of the table -#define TSDB_COL_TAG 0x1u // the tag column type -#define TSDB_COL_UDC 0x2u // the user specified normal string column, it is a dummy column -#define TSDB_COL_NULL 0x4u // the column filter NULL or not +#define TSDB_COL_NORMAL 0x0u // the normal column of the table +#define TSDB_COL_TAG 0x1u // the tag column type +#define TSDB_COL_UDC 0x2u // the user specified normal string column, it is a dummy column +#define TSDB_COL_NULL 0x4u // the column filter NULL or not -#define TSDB_COL_IS_TAG(f) (((f&(~(TSDB_COL_NULL)))&TSDB_COL_TAG) != 0) -#define TSDB_COL_IS_NORMAL_COL(f) ((f&(~(TSDB_COL_NULL))) == TSDB_COL_NORMAL) -#define TSDB_COL_IS_UD_COL(f) ((f&(~(TSDB_COL_NULL))) == TSDB_COL_UDC) -#define TSDB_COL_REQ_NULL(f) (((f)&TSDB_COL_NULL) != 0) +#define TSDB_COL_IS_TAG(f) (((f&(~(TSDB_COL_NULL)))&TSDB_COL_TAG) != 0) +#define TSDB_COL_IS_NORMAL_COL(f) ((f&(~(TSDB_COL_NULL))) == TSDB_COL_NORMAL) +#define TSDB_COL_IS_UD_COL(f) ((f&(~(TSDB_COL_NULL))) == TSDB_COL_UDC) +#define TSDB_COL_REQ_NULL(f) (((f)&TSDB_COL_NULL) != 0) extern char *taosMsg[]; @@ -260,15 +261,15 @@ typedef struct { uint64_t uid; uint64_t superTableUid; uint64_t createdTime; - char tableId[TSDB_TABLE_FNAME_LEN]; - char superTableId[TSDB_TABLE_FNAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; + char stableFname[TSDB_TABLE_FNAME_LEN]; char data[]; } SMDCreateTableMsg; typedef struct { int32_t len; // one create table message - char tableId[TSDB_TABLE_FNAME_LEN]; - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; int8_t igExists; int8_t getMeta; int16_t numOfTags; @@ -284,13 +285,13 @@ typedef struct { } SCMCreateTableMsg; typedef struct { - char tableId[TSDB_TABLE_FNAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; int8_t igNotExists; } SCMDropTableMsg; typedef struct { - char tableId[TSDB_TABLE_FNAME_LEN]; - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; int16_t type; /* operation type */ int16_t numOfCols; /* number of schema */ int32_t tagValLen; @@ -322,7 +323,7 @@ typedef struct { } SConnectMsg; typedef struct { - char acctId[TSDB_ACCT_LEN]; + char acctId[TSDB_ACCT_ID_LEN]; char serverVersion[TSDB_VERSION_LEN]; char clusterId[TSDB_CLUSTER_ID_LEN]; int8_t writeAuth; @@ -369,14 +370,14 @@ typedef struct { int32_t vgId; int32_t tid; uint64_t uid; - char tableId[TSDB_TABLE_FNAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; } SMDDropTableMsg; typedef struct { int32_t contLen; int32_t vgId; uint64_t uid; - char tableId[TSDB_TABLE_FNAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; } SDropSTableMsg; typedef struct { @@ -534,7 +535,7 @@ typedef struct { } SVnodeLoad; typedef struct { - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; int32_t cacheBlockSize; //MB int32_t totalBlocks; int32_t maxTables; @@ -682,13 +683,13 @@ typedef struct { } SVnodeDesc; typedef struct { - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; SVnodeCfg cfg; SVnodeDesc nodes[TSDB_MAX_REPLICA]; } SCreateVnodeMsg, SAlterVnodeMsg; typedef struct { - char tableId[TSDB_TABLE_FNAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; int16_t createFlag; char tags[]; } STableInfoMsg; @@ -726,7 +727,7 @@ typedef struct { typedef struct STableMetaMsg { int32_t contLen; - char tableId[TSDB_TABLE_FNAME_LEN]; // table id + char tableFname[TSDB_TABLE_FNAME_LEN]; // table id uint8_t numOfTags; uint8_t precision; uint8_t tableType; @@ -761,7 +762,7 @@ typedef struct { */ typedef struct { int8_t type; - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; uint16_t payloadLen; char payload[]; } SShowMsg; @@ -847,7 +848,7 @@ typedef struct { uint64_t uid; uint64_t stime; // stream starting time int32_t status; - char tableId[TSDB_TABLE_FNAME_LEN]; + char tableFname[TSDB_TABLE_FNAME_LEN]; } SAlterStreamMsg; typedef struct { diff --git a/src/inc/tcq.h b/src/inc/tcq.h index ad123d4080..1941649d0a 100644 --- a/src/inc/tcq.h +++ b/src/inc/tcq.h @@ -26,7 +26,7 @@ typedef int32_t (*FCqWrite)(int32_t vgId, void *pHead, int32_t qtype, void *pMsg typedef struct { int32_t vgId; char user[TSDB_USER_LEN]; - char pass[TSDB_PASSWORD_LEN]; + char pass[TSDB_KEY_LEN]; char db[TSDB_DB_NAME_LEN]; FCqWrite cqWrite; } SCqCfg; diff --git a/src/inc/ttype.h b/src/inc/ttype.h index 1849139df1..686c986f5b 100644 --- a/src/inc/ttype.h +++ b/src/inc/ttype.h @@ -7,6 +7,28 @@ extern "C" { #include "taosdef.h" +// ----------------- For variable data types such as TSDB_DATA_TYPE_BINARY and TSDB_DATA_TYPE_NCHAR +typedef int32_t VarDataOffsetT; +typedef int16_t VarDataLenT; + +typedef struct tstr { + VarDataLenT len; + char data[]; +} tstr; + +#define VARSTR_HEADER_SIZE sizeof(VarDataLenT) + +#define varDataLen(v) ((VarDataLenT *)(v))[0] +#define varDataTLen(v) (sizeof(VarDataLenT) + varDataLen(v)) +#define varDataVal(v) ((void *)((char *)v + VARSTR_HEADER_SIZE)) +#define varDataCopy(dst, v) memcpy((dst), (void*) (v), varDataTLen(v)) +#define varDataLenByData(v) (*(VarDataLenT *)(((char*)(v)) - VARSTR_HEADER_SIZE)) +#define varDataSetLen(v, _len) (((VarDataLenT *)(v))[0] = (VarDataLenT) (_len)) +#define IS_VAR_DATA_TYPE(t) (((t) == TSDB_DATA_TYPE_BINARY) || ((t) == TSDB_DATA_TYPE_NCHAR)) + +// this data type is internally used only in 'in' query to hold the values +#define TSDB_DATA_TYPE_ARRAY (TSDB_DATA_TYPE_NCHAR + 1) + #define GET_TYPED_DATA(_v, _finalType, _type, _data) \ do { \ switch (_type) { \ @@ -59,6 +81,70 @@ extern "C" { #define IS_VALID_UINT(_t) ((_t) >= 0 && (_t) < UINT32_MAX) #define IS_VALID_UBIGINT(_t) ((_t) >= 0 && (_t) < UINT64_MAX) +static FORCE_INLINE bool isNull(const char *val, int32_t type) { + switch (type) { + case TSDB_DATA_TYPE_BOOL: + return *(uint8_t *)val == TSDB_DATA_BOOL_NULL; + case TSDB_DATA_TYPE_TINYINT: + return *(uint8_t *)val == TSDB_DATA_TINYINT_NULL; + case TSDB_DATA_TYPE_SMALLINT: + return *(uint16_t *)val == TSDB_DATA_SMALLINT_NULL; + case TSDB_DATA_TYPE_INT: + return *(uint32_t *)val == TSDB_DATA_INT_NULL; + case TSDB_DATA_TYPE_BIGINT: + case TSDB_DATA_TYPE_TIMESTAMP: + return *(uint64_t *)val == TSDB_DATA_BIGINT_NULL; + case TSDB_DATA_TYPE_FLOAT: + return *(uint32_t *)val == TSDB_DATA_FLOAT_NULL; + case TSDB_DATA_TYPE_DOUBLE: + return *(uint64_t *)val == TSDB_DATA_DOUBLE_NULL; + case TSDB_DATA_TYPE_NCHAR: + return varDataLen(val) == sizeof(int32_t) && *(uint32_t*) varDataVal(val) == TSDB_DATA_NCHAR_NULL; + case TSDB_DATA_TYPE_BINARY: + return varDataLen(val) == sizeof(int8_t) && *(uint8_t *) varDataVal(val) == TSDB_DATA_BINARY_NULL; + case TSDB_DATA_TYPE_UTINYINT: + return *(uint8_t*) val == TSDB_DATA_UTINYINT_NULL; + case TSDB_DATA_TYPE_USMALLINT: + return *(uint16_t*) val == TSDB_DATA_USMALLINT_NULL; + case TSDB_DATA_TYPE_UINT: + return *(uint32_t*) val == TSDB_DATA_UINT_NULL; + case TSDB_DATA_TYPE_UBIGINT: + return *(uint64_t*) val == TSDB_DATA_UBIGINT_NULL; + + default: + return false; + }; +} + +typedef struct tDataTypeDescriptor { + int16_t type; + int16_t nameLen; + int32_t bytes; + char * name; + int (*compFunc)(const char *const input, int inputSize, const int nelements, char *const output, int outputSize, + char algorithm, char *const buffer, int bufferSize); + int (*decompFunc)(const char *const input, int compressedSize, const int nelements, char *const output, + int outputSize, char algorithm, char *const buffer, int bufferSize); + void (*statisFunc)(const void *pData, int32_t numofrow, int64_t *min, int64_t *max, int64_t *sum, + int16_t *minindex, int16_t *maxindex, int16_t *numofnull); +} tDataTypeDescriptor; + +extern tDataTypeDescriptor tDataTypes[15]; + +bool isValidDataType(int32_t type); + +void setVardataNull(char* val, int32_t type); +void setNull(char *val, int32_t type, int32_t bytes); +void setNullN(char *val, int32_t type, int32_t bytes, int32_t numOfElems); +void* getNullValue(int32_t type); + +void assignVal(char *val, const char *src, int32_t len, int32_t type); +void tsDataSwap(void *pLeft, void *pRight, int32_t type, int32_t size, void* buf); + +int32_t tStrToInteger(const char* z, int16_t type, int32_t n, int64_t* value, bool issigned); + +#define SET_DOUBLE_NULL(v) (*(uint64_t *)(v) = TSDB_DATA_DOUBLE_NULL) + #ifdef __cplusplus } #endif diff --git a/src/inc/vnode.h b/src/inc/vnode.h index cbe64484b1..7c9ebd8a0b 100644 --- a/src/inc/vnode.h +++ b/src/inc/vnode.h @@ -49,7 +49,7 @@ typedef struct { SRpcMsg rpcMsg; SRspRet rspRet; char reserveForSync[24]; - SWalHead pHead[]; + SWalHead pHead; } SVWriteMsg; // vnodeStatus diff --git a/src/kit/CMakeLists.txt b/src/kit/CMakeLists.txt index bf52784300..bf77d856f9 100644 --- a/src/kit/CMakeLists.txt +++ b/src/kit/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) ADD_SUBDIRECTORY(shell) diff --git a/src/kit/shell/CMakeLists.txt b/src/kit/shell/CMakeLists.txt index c86cac281c..45da99e572 100644 --- a/src/kit/shell/CMakeLists.txt +++ b/src/kit/shell/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/client/inc) diff --git a/src/kit/taosdemo/CMakeLists.txt b/src/kit/taosdemo/CMakeLists.txt index ab02bdb64d..91c743939c 100644 --- a/src/kit/taosdemo/CMakeLists.txt +++ b/src/kit/taosdemo/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/client/inc) diff --git a/src/kit/taosdemox/CMakeLists.txt b/src/kit/taosdemox/CMakeLists.txt index 3f5e725aea..7db6c04b28 100644 --- a/src/kit/taosdemox/CMakeLists.txt +++ b/src/kit/taosdemox/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/client/inc) diff --git a/src/kit/taosdemox/taosdemox.c b/src/kit/taosdemox/taosdemox.c index 5c187030c5..2968d65331 100644 --- a/src/kit/taosdemox/taosdemox.c +++ b/src/kit/taosdemox/taosdemox.c @@ -1085,8 +1085,8 @@ static void printfQueryMeta() { printf("database name: \033[33m%s\033[0m\n", g_queryInfo.dbName); printf("\n"); - printf("super table query info: \n"); - printf("rate: \033[33m%d\033[0m\n", g_queryInfo.superQueryInfo.rate); + printf("specified table query info: \n"); + printf("query interval: \033[33m%d\033[0m\n", g_queryInfo.superQueryInfo.rate); printf("concurrent: \033[33m%d\033[0m\n", g_queryInfo.superQueryInfo.concurrent); printf("sqlCount: \033[33m%d\033[0m\n", g_queryInfo.superQueryInfo.sqlCount); @@ -1102,11 +1102,11 @@ static void printfQueryMeta() { printf(" sql[%d]: \033[33m%s\033[0m\n", i, g_queryInfo.superQueryInfo.sql[i]); } printf("\n"); - printf("sub table query info: \n"); - printf("rate: \033[33m%d\033[0m\n", g_queryInfo.subQueryInfo.rate); + printf("super table query info: \n"); + printf("query interval: \033[33m%d\033[0m\n", g_queryInfo.subQueryInfo.rate); printf("threadCnt: \033[33m%d\033[0m\n", g_queryInfo.subQueryInfo.threadCnt); printf("childTblCount: \033[33m%d\033[0m\n", g_queryInfo.subQueryInfo.childTblCount); - printf("childTblPrefix: \033[33m%s\033[0m\n", g_queryInfo.subQueryInfo.childTblPrefix); + printf("stable name: \033[33m%s\033[0m\n", g_queryInfo.subQueryInfo.sTblName); if (SUBSCRIBE_MODE == g_jsonType) { printf("mod: \033[33m%d\033[0m\n", g_queryInfo.subQueryInfo.subscribeMode); @@ -4020,23 +4020,23 @@ void *superQueryProcess(void *sarg) { } selectAndGetResult(winfo->taos, g_queryInfo.superQueryInfo.sql[i], tmpFile); int64_t t2 = taosGetTimestampUs(); - printf("taosc select sql return, Spent %f s\n", (t2 - t1)/1000000.0); + printf("=[taosc] thread[%"PRIu64"] complete one sql, Spent %f s\n", (uint64_t)pthread_self(), (t2 - t1)/1000000.0); } else { #ifdef TD_LOWA_CURL int64_t t1 = taosGetTimestampUs(); int retCode = curlProceSql(g_queryInfo.host, g_queryInfo.port, g_queryInfo.superQueryInfo.sql[i], winfo->curl_handle); int64_t t2 = taosGetTimestampUs(); - printf("http select sql return, Spent %f s \n", (t2 - t1)/1000000.0); + printf("=[restful] thread[%"PRIu64"] complete one sql, Spent %f s\n", (uint64_t)pthread_self(), (t2 - t1)/1000000.0); if (0 != retCode) { - printf("========curl return fail, threadID[%d]\n", winfo->threadID); + printf("====curl return fail, threadID[%d]\n", winfo->threadID); return NULL; } #endif } } et = taosGetTimestampMs(); - printf("========thread[%"PRIu64"] complete all sqls to super table once queries duration:%.6fs\n\n", (uint64_t)pthread_self(), (double)(et - st)/1000.0); + printf("==thread[%"PRIu64"] complete all sqls to specify tables once queries duration:%.6fs\n\n", (uint64_t)pthread_self(), (double)(et - st)/1000.0); } return NULL; } @@ -4065,7 +4065,7 @@ void *subQueryProcess(void *sarg) { char sqlstr[1024]; threadInfo *winfo = (threadInfo *)sarg; int64_t st = 0; - int64_t et = 0; + int64_t et = g_queryInfo.subQueryInfo.rate*1000; while (1) { if (g_queryInfo.subQueryInfo.rate && (et - st) < g_queryInfo.subQueryInfo.rate*1000) { taosMsleep(g_queryInfo.subQueryInfo.rate*1000 - (et - st)); // ms @@ -4085,17 +4085,12 @@ void *subQueryProcess(void *sarg) { } } et = taosGetTimestampMs(); - printf("========thread[%"PRIu64"] complete all sqls to allocate all sub-tables once queries duration:%.4fs\n\n", (uint64_t)pthread_self(), (double)(et - st)/1000.0); + printf("####thread[%"PRIu64"] complete all sqls to allocate all sub-tables[%d - %d] once queries duration:%.4fs\n\n", (uint64_t)pthread_self(), winfo->start_table_id, winfo->end_table_id, (double)(et - st)/1000.0); } return NULL; } int queryTestProcess() { - printfQueryMeta(); - - printf("Press enter key to continue\n\n"); - (void)getchar(); - TAOS * taos = NULL; taos_init(); taos = taos_connect(g_queryInfo.host, g_queryInfo.user, g_queryInfo.password, g_queryInfo.dbName, g_queryInfo.port); @@ -4108,9 +4103,13 @@ int queryTestProcess() { (void)getAllChildNameOfSuperTable(taos, g_queryInfo.dbName, g_queryInfo.subQueryInfo.sTblName, &g_queryInfo.subQueryInfo.childTblName, &g_queryInfo.subQueryInfo.childTblCount); } + printfQueryMeta(); + printf("Press enter key to continue\n\n"); + (void)getchar(); + pthread_t *pids = NULL; threadInfo *infos = NULL; - //==== create sub threads for query from super table + //==== create sub threads for query from specify table if (g_queryInfo.superQueryInfo.sqlCount > 0 && g_queryInfo.superQueryInfo.concurrent > 0) { pids = malloc(g_queryInfo.superQueryInfo.concurrent * sizeof(pthread_t)); @@ -4146,7 +4145,7 @@ int queryTestProcess() { pthread_t *pidsOfSub = NULL; threadInfo *infosOfSub = NULL; - //==== create sub threads for query from sub table + //==== create sub threads for query from all sub table of the super table if ((g_queryInfo.subQueryInfo.sqlCount > 0) && (g_queryInfo.subQueryInfo.threadCnt > 0)) { pidsOfSub = malloc(g_queryInfo.subQueryInfo.threadCnt * sizeof(pthread_t)); infosOfSub = malloc(g_queryInfo.subQueryInfo.threadCnt * sizeof(threadInfo)); @@ -4177,6 +4176,7 @@ int queryTestProcess() { t_info->start_table_id = last; t_info->end_table_id = i < b ? last + a : last + a - 1; + last = t_info->end_table_id + 1; t_info->taos = taos; pthread_create(pidsOfSub + i, NULL, subQueryProcess, t_info); } diff --git a/src/kit/taosdump/CMakeLists.txt b/src/kit/taosdump/CMakeLists.txt index dcdbd48615..dc9ac6d4a7 100644 --- a/src/kit/taosdump/CMakeLists.txt +++ b/src/kit/taosdump/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/client/inc) diff --git a/src/mnode/CMakeLists.txt b/src/mnode/CMakeLists.txt index ff5c9335b6..4123098694 100644 --- a/src/mnode/CMakeLists.txt +++ b/src/mnode/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX) diff --git a/src/mnode/inc/mnodeDef.h b/src/mnode/inc/mnodeDef.h index d29a738a10..5eeac97209 100644 --- a/src/mnode/inc/mnodeDef.h +++ b/src/mnode/inc/mnodeDef.h @@ -138,7 +138,7 @@ typedef struct SVgObj { int64_t createdTime; int32_t lbDnodeId; int32_t lbTime; - char dbName[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char dbName[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; int8_t inUse; int8_t accessState; int8_t status; @@ -179,7 +179,7 @@ typedef struct { } SDbCfg; typedef struct SDbObj { - char name[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char name[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; int8_t reserved0[4]; char acct[TSDB_USER_LEN]; int64_t createdTime; diff --git a/src/mnode/src/mnodeCluster.c b/src/mnode/src/mnodeCluster.c index a35e304810..7892918a39 100644 --- a/src/mnode/src/mnodeCluster.c +++ b/src/mnode/src/mnodeCluster.c @@ -195,7 +195,7 @@ static int32_t mnodeGetClusterMeta(STableMetaMsg *pMeta, SShowObj *pShow, void * cols++; pMeta->numOfColumns = htons(cols); - strcpy(pMeta->tableId, "show cluster"); + strcpy(pMeta->tableFname, "show cluster"); pShow->numOfColumns = cols; pShow->offset[0] = 0; diff --git a/src/mnode/src/mnodeTable.c b/src/mnode/src/mnodeTable.c index de37b09345..bdf5a7fb8b 100644 --- a/src/mnode/src/mnodeTable.c +++ b/src/mnode/src/mnodeTable.c @@ -68,7 +68,7 @@ static int32_t mnodeGetShowSuperTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, static int32_t mnodeRetrieveShowSuperTables(SShowObj *pShow, char *data, int32_t rows, void *pConn); static int32_t mnodeGetStreamTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, void *pConn); static int32_t mnodeRetrieveStreamTables(SShowObj *pShow, char *data, int32_t rows, void *pConn); - + static int32_t mnodeProcessCreateTableMsg(SMnodeMsg *pMsg); static int32_t mnodeProcessCreateSuperTableMsg(SMnodeMsg *pMsg); static int32_t mnodeProcessCreateChildTableMsg(SMnodeMsg *pMsg); @@ -164,7 +164,7 @@ static int32_t mnodeChildTableActionDelete(SSdbRow *pRow) { SVgObj *pVgroup = NULL; SDbObj *pDb = NULL; SAcctObj *pAcct = NULL; - + pVgroup = mnodeGetVgroup(pTable->vgId); if (pVgroup != NULL) pDb = mnodeGetDb(pVgroup->dbName); if (pDb != NULL) pAcct = mnodeGetAcct(pDb->acct); @@ -180,14 +180,14 @@ static int32_t mnodeChildTableActionDelete(SSdbRow *pRow) { grantRestore(TSDB_GRANT_TIMESERIES, pTable->numOfColumns - 1); if (pAcct != NULL) pAcct->acctInfo.numOfTimeSeries -= (pTable->numOfColumns - 1); } - + if (pDb != NULL) mnodeRemoveTableFromDb(pDb); if (pVgroup != NULL) mnodeRemoveTableFromVgroup(pVgroup, pTable); mnodeDecVgroupRef(pVgroup); mnodeDecDbRef(pDb); mnodeDecAcctRef(pAcct); - + return TSDB_CODE_SUCCESS; } @@ -195,19 +195,19 @@ static int32_t mnodeChildTableActionUpdate(SSdbRow *pRow) { SCTableObj *pNew = pRow->pObj; SCTableObj *pTable = mnodeGetChildTable(pNew->info.tableId); if (pTable != pNew) { - void *oldTableId = pTable->info.tableId; + void *oldTableId = pTable->info.tableId; void *oldSql = pTable->sql; void *oldSchema = pTable->schema; void *oldSTable = pTable->superTable; int32_t oldRefCount = pTable->refCount; - + memcpy(pTable, pNew, sizeof(SCTableObj)); - + pTable->refCount = oldRefCount; pTable->sql = pNew->sql; pTable->schema = pNew->schema; pTable->superTable = oldSTable; - + free(pNew); free(oldSql); free(oldSchema); @@ -544,7 +544,7 @@ static int32_t mnodeSuperTableActionDecode(SSdbRow *pRow) { } memcpy(pStable->schema, pRow->rowData + len, schemaSize); - + pRow->pObj = pStable; return TSDB_CODE_SUCCESS; @@ -611,7 +611,7 @@ int32_t mnodeInitTables() { mnodeAddWriteMsgHandle(TSDB_MSG_TYPE_CM_ALTER_TABLE, mnodeProcessAlterTableMsg); mnodeAddReadMsgHandle(TSDB_MSG_TYPE_CM_TABLE_META, mnodeProcessTableMetaMsg); mnodeAddReadMsgHandle(TSDB_MSG_TYPE_CM_STABLE_VGROUP, mnodeProcessSuperTableVgroupMsg); - + mnodeAddPeerRspHandle(TSDB_MSG_TYPE_MD_CREATE_TABLE_RSP, mnodeProcessCreateChildTableRsp); mnodeAddPeerRspHandle(TSDB_MSG_TYPE_MD_DROP_TABLE_RSP, mnodeProcessDropChildTableRsp); mnodeAddPeerRspHandle(TSDB_MSG_TYPE_MD_DROP_STABLE_RSP, mnodeProcessDropSuperTableRsp); @@ -750,7 +750,7 @@ void mnodeDestroySubMsg(SMnodeMsg *pSubMsg) { static int32_t mnodeValidateCreateTableMsg(SCreateTableMsg *pCreateTable, SMnodeMsg *pMsg) { if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDb(pCreateTable->db); if (pMsg->pDb == NULL) { - mError("msg:%p, app:%p table:%s, failed to create, db not selected", pMsg, pMsg->rpcMsg.ahandle, pCreateTable->tableId); + mError("msg:%p, app:%p table:%s, failed to create, db not selected", pMsg, pMsg->rpcMsg.ahandle, pCreateTable->tableFname); return TSDB_CODE_MND_DB_NOT_SELECTED; } @@ -759,28 +759,28 @@ static int32_t mnodeValidateCreateTableMsg(SCreateTableMsg *pCreateTable, SMnode return TSDB_CODE_MND_DB_IN_DROPPING; } - if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pCreateTable->tableId); + if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pCreateTable->tableFname); if (pMsg->pTable != NULL && pMsg->retry == 0) { if (pCreateTable->getMeta) { - mDebug("msg:%p, app:%p table:%s, continue to get meta", pMsg, pMsg->rpcMsg.ahandle, pCreateTable->tableId); + mDebug("msg:%p, app:%p table:%s, continue to get meta", pMsg, pMsg->rpcMsg.ahandle, pCreateTable->tableFname); return mnodeGetChildTableMeta(pMsg); } else if (pCreateTable->igExists) { - mDebug("msg:%p, app:%p table:%s, is already exist", pMsg, pMsg->rpcMsg.ahandle, pCreateTable->tableId); + mDebug("msg:%p, app:%p table:%s, is already exist", pMsg, pMsg->rpcMsg.ahandle, pCreateTable->tableFname); return TSDB_CODE_SUCCESS; } else { mError("msg:%p, app:%p table:%s, failed to create, table already exist", pMsg, pMsg->rpcMsg.ahandle, - pCreateTable->tableId); + pCreateTable->tableFname); return TSDB_CODE_MND_TABLE_ALREADY_EXIST; } } if (pCreateTable->numOfTags != 0) { mDebug("msg:%p, app:%p table:%s, create stable msg is received from thandle:%p", pMsg, pMsg->rpcMsg.ahandle, - pCreateTable->tableId, pMsg->rpcMsg.handle); + pCreateTable->tableFname, pMsg->rpcMsg.handle); return mnodeProcessCreateSuperTableMsg(pMsg); } else { mDebug("msg:%p, app:%p table:%s, create ctable msg is received from thandle:%p", pMsg, pMsg->rpcMsg.ahandle, - pCreateTable->tableId, pMsg->rpcMsg.handle); + pCreateTable->tableFname, pMsg->rpcMsg.handle); return mnodeProcessCreateChildTableMsg(pMsg); } } @@ -862,47 +862,46 @@ static int32_t mnodeProcessCreateTableMsg(SMnodeMsg *pMsg) { SCreateTableMsg *p = (SCreateTableMsg*)((char*) pCreate + sizeof(SCMCreateTableMsg)); if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDb(p->db); if (pMsg->pDb == NULL) { - mError("msg:%p, app:%p table:%s, failed to create, db not selected", pMsg, pMsg->rpcMsg.ahandle, p->tableId); + mError("msg:%p, app:%p table:%s, failed to create, db not selected", pMsg, pMsg->rpcMsg.ahandle, p->tableFname); return TSDB_CODE_MND_DB_NOT_SELECTED; } - + if (pMsg->pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pMsg->pDb->name, pMsg->pDb->status); return TSDB_CODE_MND_DB_IN_DROPPING; } - if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(p->tableId); + if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(p->tableFname); if (pMsg->pTable != NULL && pMsg->retry == 0) { if (p->getMeta) { - mDebug("msg:%p, app:%p table:%s, continue to get meta", pMsg, pMsg->rpcMsg.ahandle, p->tableId); + mDebug("msg:%p, app:%p table:%s, continue to get meta", pMsg, pMsg->rpcMsg.ahandle, p->tableFname); return mnodeGetChildTableMeta(pMsg); } else if (p->igExists) { - mDebug("msg:%p, app:%p table:%s, is already exist", pMsg, pMsg->rpcMsg.ahandle, p->tableId); + mDebug("msg:%p, app:%p table:%s, is already exist", pMsg, pMsg->rpcMsg.ahandle, p->tableFname); return TSDB_CODE_SUCCESS; } else { - mError("msg:%p, app:%p table:%s, failed to create, table already exist", pMsg, pMsg->rpcMsg.ahandle, - p->tableId); + mError("msg:%p, app:%p table:%s, failed to create, table already exist", pMsg, pMsg->rpcMsg.ahandle, p->tableFname); return TSDB_CODE_MND_TABLE_ALREADY_EXIST; } } if (p->numOfTags != 0) { mDebug("msg:%p, app:%p table:%s, create stable msg is received from thandle:%p", pMsg, pMsg->rpcMsg.ahandle, - p->tableId, pMsg->rpcMsg.handle); + p->tableFname, pMsg->rpcMsg.handle); return mnodeProcessCreateSuperTableMsg(pMsg); } else { mDebug("msg:%p, app:%p table:%s, create ctable msg is received from thandle:%p", pMsg, pMsg->rpcMsg.ahandle, - p->tableId, pMsg->rpcMsg.handle); + p->tableFname, pMsg->rpcMsg.handle); return mnodeProcessCreateChildTableMsg(pMsg); } } static int32_t mnodeProcessDropTableMsg(SMnodeMsg *pMsg) { SCMDropTableMsg *pDrop = pMsg->rpcMsg.pCont; - if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDbByTableId(pDrop->tableId); + if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDbByTableId(pDrop->tableFname); if (pMsg->pDb == NULL) { mError("msg:%p, app:%p table:%s, failed to drop table, db not selected or db in dropping", pMsg, - pMsg->rpcMsg.ahandle, pDrop->tableId); + pMsg->rpcMsg.ahandle, pDrop->tableFname); return TSDB_CODE_MND_DB_NOT_SELECTED; } @@ -913,17 +912,17 @@ static int32_t mnodeProcessDropTableMsg(SMnodeMsg *pMsg) { if (mnodeCheckIsMonitorDB(pMsg->pDb->name, tsMonitorDbName)) { mError("msg:%p, app:%p table:%s, failed to drop table, in monitor database", pMsg, pMsg->rpcMsg.ahandle, - pDrop->tableId); + pDrop->tableFname); return TSDB_CODE_MND_MONITOR_DB_FORBIDDEN; } - if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pDrop->tableId); + if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pDrop->tableFname); if (pMsg->pTable == NULL) { if (pDrop->igNotExists) { - mDebug("msg:%p, app:%p table:%s is not exist, treat as success", pMsg, pMsg->rpcMsg.ahandle, pDrop->tableId); + mDebug("msg:%p, app:%p table:%s is not exist, treat as success", pMsg, pMsg->rpcMsg.ahandle, pDrop->tableFname); return TSDB_CODE_SUCCESS; } else { - mError("msg:%p, app:%p table:%s, failed to drop, table not exist", pMsg, pMsg->rpcMsg.ahandle, pDrop->tableId); + mError("msg:%p, app:%p table:%s, failed to drop, table not exist", pMsg, pMsg->rpcMsg.ahandle, pDrop->tableFname); return TSDB_CODE_MND_INVALID_TABLE_NAME; } } @@ -931,12 +930,12 @@ static int32_t mnodeProcessDropTableMsg(SMnodeMsg *pMsg) { if (pMsg->pTable->type == TSDB_SUPER_TABLE) { SSTableObj *pSTable = (SSTableObj *)pMsg->pTable; mInfo("msg:%p, app:%p table:%s, start to drop stable, uid:%" PRIu64 ", numOfChildTables:%d, sizeOfVgList:%d", pMsg, - pMsg->rpcMsg.ahandle, pDrop->tableId, pSTable->uid, pSTable->numOfTables, taosHashGetSize(pSTable->vgHash)); + pMsg->rpcMsg.ahandle, pDrop->tableFname, pSTable->uid, pSTable->numOfTables, taosHashGetSize(pSTable->vgHash)); return mnodeProcessDropSuperTableMsg(pMsg); } else { SCTableObj *pCTable = (SCTableObj *)pMsg->pTable; mInfo("msg:%p, app:%p table:%s, start to drop ctable, vgId:%d tid:%d uid:%" PRIu64, pMsg, pMsg->rpcMsg.ahandle, - pDrop->tableId, pCTable->vgId, pCTable->tid, pCTable->uid); + pDrop->tableFname, pCTable->vgId, pCTable->tid, pCTable->uid); return mnodeProcessDropChildTableMsg(pMsg); } } @@ -945,29 +944,29 @@ static int32_t mnodeProcessTableMetaMsg(SMnodeMsg *pMsg) { STableInfoMsg *pInfo = pMsg->rpcMsg.pCont; pInfo->createFlag = htons(pInfo->createFlag); mDebug("msg:%p, app:%p table:%s, table meta msg is received from thandle:%p, createFlag:%d", pMsg, pMsg->rpcMsg.ahandle, - pInfo->tableId, pMsg->rpcMsg.handle, pInfo->createFlag); + pInfo->tableFname, pMsg->rpcMsg.handle, pInfo->createFlag); - if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDbByTableId(pInfo->tableId); + if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDbByTableId(pInfo->tableFname); if (pMsg->pDb == NULL) { mError("msg:%p, app:%p table:%s, failed to get table meta, db not selected", pMsg, pMsg->rpcMsg.ahandle, - pInfo->tableId); + pInfo->tableFname); return TSDB_CODE_MND_DB_NOT_SELECTED; } - + if (pMsg->pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pMsg->pDb->name, pMsg->pDb->status); return TSDB_CODE_MND_DB_IN_DROPPING; } - if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pInfo->tableId); + if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pInfo->tableFname); if (pMsg->pTable == NULL) { if (!pInfo->createFlag) { mError("msg:%p, app:%p table:%s, failed to get table meta, table not exist", pMsg, pMsg->rpcMsg.ahandle, - pInfo->tableId); + pInfo->tableFname); return TSDB_CODE_MND_INVALID_TABLE_NAME; } else { mDebug("msg:%p, app:%p table:%s, failed to get table meta, start auto create table ", pMsg, pMsg->rpcMsg.ahandle, - pInfo->tableId); + pInfo->tableFname); return mnodeAutoCreateChildTable(pMsg); } } else { @@ -1007,12 +1006,12 @@ static int32_t mnodeProcessCreateSuperTableMsg(SMnodeMsg *pMsg) { SSTableObj * pStable = calloc(1, sizeof(SSTableObj)); if (pStable == NULL) { - mError("msg:%p, app:%p table:%s, failed to create, no enough memory", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + mError("msg:%p, app:%p table:%s, failed to create, no enough memory", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); return TSDB_CODE_MND_OUT_OF_MEMORY; } int64_t us = taosGetTimestampUs(); - pStable->info.tableId = strdup(pCreate->tableId); + pStable->info.tableId = strdup(pCreate->tableFname); pStable->info.type = TSDB_SUPER_TABLE; pStable->createdTime = taosGetTimestampMs(); pStable->uid = (us << 24) + ((sdbGetVersion() & ((1ul << 16) - 1ul)) << 8) + (taosRand() & ((1ul << 8) - 1ul)); @@ -1026,41 +1025,27 @@ static int32_t mnodeProcessCreateSuperTableMsg(SMnodeMsg *pMsg) { pStable->schema = (SSchema *)calloc(1, schemaSize); if (pStable->schema == NULL) { free(pStable); - mError("msg:%p, app:%p table:%s, failed to create, no schema input", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + mError("msg:%p, app:%p table:%s, failed to create, no schema input", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); return TSDB_CODE_MND_INVALID_TABLE_NAME; } memcpy(pStable->schema, pCreate->schema, numOfCols * sizeof(SSchema)); if (pStable->numOfColumns > TSDB_MAX_COLUMNS || pStable->numOfTags > TSDB_MAX_TAGS) { - mError("msg:%p, app:%p table:%s, failed to create, too many columns", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + mError("msg:%p, app:%p table:%s, failed to create, too many columns", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); return TSDB_CODE_MND_INVALID_TABLE_NAME; } pStable->nextColId = 0; - // TODO extract method to valid the schema - int32_t schemaLen = 0; - int32_t tagLen = 0; for (int32_t col = 0; col < numOfCols; col++) { SSchema *tschema = pStable->schema; tschema[col].colId = pStable->nextColId++; tschema[col].bytes = htons(tschema[col].bytes); - - if (col < pStable->numOfTables) { - schemaLen += tschema[col].bytes; - } else { - tagLen += tschema[col].bytes; - } - - if (!isValidDataType(tschema[col].type)) { - mError("msg:%p, app:%p table:%s, failed to create, invalid data type in schema", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); - return TSDB_CODE_MND_INVALID_CREATE_TABLE_MSG; - } } - if (schemaLen > (TSDB_MAX_BYTES_PER_ROW || tagLen > TSDB_MAX_TAGS_LEN)) { - mError("msg:%p, app:%p table:%s, failed to create, schema is too long", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + if (!isValidSchema(pStable->schema, pStable->numOfColumns, pStable->numOfTags)) { + mError("msg:%p, app:%p table:%s, failed to create table, invalid schema", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); return TSDB_CODE_MND_INVALID_CREATE_TABLE_MSG; } @@ -1080,7 +1065,7 @@ static int32_t mnodeProcessCreateSuperTableMsg(SMnodeMsg *pMsg) { if (code != TSDB_CODE_SUCCESS && code != TSDB_CODE_MND_ACTION_IN_PROGRESS) { mnodeDestroySuperTable(pStable); pMsg->pTable = NULL; - mError("msg:%p, app:%p table:%s, failed to create, sdb error", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + mError("msg:%p, app:%p table:%s, failed to create, sdb error", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); } return code; @@ -1115,7 +1100,7 @@ static int32_t mnodeProcessDropSuperTableMsg(SMnodeMsg *pMsg) { pDrop->contLen = htonl(sizeof(SDropSTableMsg)); pDrop->vgId = htonl(pVgroup->vgId); pDrop->uid = htobe64(pStable->uid); - mnodeExtractTableName(pStable->info.tableId, pDrop->tableId); + mnodeExtractTableName(pStable->info.tableId, pDrop->tableFname); mInfo("msg:%p, app:%p stable:%s, send drop stable msg to vgId:%d, hash:%p sizeOfVgList:%d", pMsg, pMsg->rpcMsg.ahandle, pStable->info.tableId, pVgroup->vgId, pStable->vgHash, @@ -1129,8 +1114,8 @@ static int32_t mnodeProcessDropSuperTableMsg(SMnodeMsg *pMsg) { taosHashCancelIterate(pStable->vgHash, pVgId); mnodeDropAllChildTablesInStable(pStable); - } - + } + SSdbRow row = { .type = SDB_OPER_GLOBAL, .pTable = tsSuperTableSdb, @@ -1274,7 +1259,7 @@ static int32_t mnodeModifySuperTableTagName(SMnodeMsg *pMsg, char *oldTagName, c if (mnodeFindSuperTableTagIndex(pStable, newTagName) >= 0) { return TSDB_CODE_MND_TAG_ALREAY_EXIST; } - + // update SSchema *schema = (SSchema *) (pStable->schema + pStable->numOfColumns + col); tstrncpy(schema->name, newTagName, sizeof(schema->name)); @@ -1437,7 +1422,7 @@ static int32_t mnodeChangeSuperTableColumn(SMnodeMsg *pMsg, char *oldName, char if (mnodeFindSuperTableColumnIndex(pStable, newName) >= 0) { return TSDB_CODE_MND_FIELD_ALREAY_EXIST; } - + // update SSchema *schema = (SSchema *) (pStable->schema + col); tstrncpy(schema->name, newName, sizeof(schema->name)); @@ -1460,7 +1445,7 @@ static int32_t mnodeChangeSuperTableColumn(SMnodeMsg *pMsg, char *oldName, char static int32_t mnodeGetShowSuperTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, void *pConn) { SDbObj *pDb = mnodeGetDb(pShow->db); if (pDb == NULL) return TSDB_CODE_MND_DB_NOT_SELECTED; - + if (pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pDb->name, pDb->status); mnodeDecDbRef(pDb); @@ -1525,7 +1510,7 @@ int32_t mnodeRetrieveShowSuperTables(SShowObj *pShow, char *data, int32_t rows, SDbObj *pDb = mnodeGetDb(pShow->db); if (pDb == NULL) return 0; - + if (pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pDb->name, pDb->status); mnodeDecDbRef(pDb); @@ -1539,7 +1524,7 @@ int32_t mnodeRetrieveShowSuperTables(SShowObj *pShow, char *data, int32_t rows, SPatternCompareInfo info = PATTERN_COMPARE_INFO_INITIALIZER; char stableName[TSDB_TABLE_NAME_LEN] = {0}; - while (numOfRows < rows) { + while (numOfRows < rows) { pShow->pIter = mnodeGetNextSuperTable(pShow->pIter, &pTable); if (pTable == NULL) break; if (strncmp(pTable->info.tableId, prefix, prefixLen)) { @@ -1558,11 +1543,11 @@ int32_t mnodeRetrieveShowSuperTables(SShowObj *pShow, char *data, int32_t rows, cols = 0; pWrite = data + pShow->offset[cols] * rows + pShow->bytes[cols] * numOfRows; - + int16_t len = strnlen(stableName, TSDB_TABLE_NAME_LEN - 1); *(int16_t*) pWrite = len; pWrite += sizeof(int16_t); // todo refactor - + strncpy(pWrite, stableName, len); cols++; @@ -1629,7 +1614,7 @@ void mnodeDropAllSuperTables(SDbObj *pDropDb) { static int32_t mnodeSetSchemaFromSuperTable(SSchema *pSchema, SSTableObj *pTable) { int32_t numOfCols = pTable->numOfColumns + pTable->numOfTags; assert(numOfCols <= TSDB_MAX_COLUMNS); - + for (int32_t i = 0; i < numOfCols; ++i) { tstrncpy(pSchema->name, pTable->schema[i].name, sizeof(pSchema->name)); pSchema->type = pTable->schema[i].type; @@ -1655,7 +1640,7 @@ static int32_t mnodeGetSuperTableMeta(SMnodeMsg *pMsg) { pMeta->numOfColumns = htons((int16_t)pTable->numOfColumns); pMeta->tableType = pTable->info.type; pMeta->contLen = sizeof(STableMetaMsg) + mnodeSetSchemaFromSuperTable(pMeta->schema, pTable); - tstrncpy(pMeta->tableId, pTable->info.tableId, sizeof(pMeta->tableId)); + tstrncpy(pMeta->tableFname, pTable->info.tableId, sizeof(pMeta->tableFname)); pMsg->rpcRsp.len = pMeta->contLen; pMeta->contLen = htons(pMeta->contLen); @@ -1709,7 +1694,7 @@ static int32_t mnodeProcessSuperTableVgroupMsg(SMnodeMsg *pMsg) { SVgroupsMsg *pVgroupMsg = (SVgroupsMsg *)msg; pVgroupMsg->numOfVgroups = 0; - + msg += sizeof(SVgroupsMsg); } else { SVgroupsMsg *pVgroupMsg = (SVgroupsMsg *)msg; @@ -1798,7 +1783,7 @@ static void *mnodeBuildCreateChildTableMsg(SCMCreateTableMsg *pCreateMsg, SCTabl return NULL; } - mnodeExtractTableName(pTable->info.tableId, pCreate->tableId); + mnodeExtractTableName(pTable->info.tableId, pCreate->tableFname); pCreate->contLen = htonl(contLen); pCreate->vgId = htonl(pTable->vgId); pCreate->tableType = pTable->info.type; @@ -1806,9 +1791,9 @@ static void *mnodeBuildCreateChildTableMsg(SCMCreateTableMsg *pCreateMsg, SCTabl pCreate->tid = htonl(pTable->tid); pCreate->sqlDataLen = htonl(pTable->sqlLen); pCreate->uid = htobe64(pTable->uid); - + if (pTable->info.type == TSDB_CHILD_TABLE) { - mnodeExtractTableName(pTable->superTable->info.tableId, pCreate->superTableId); + mnodeExtractTableName(pTable->superTable->info.tableId, pCreate->stableFname); pCreate->numOfColumns = htons(pTable->superTable->numOfColumns); pCreate->numOfTags = htons(pTable->superTable->numOfTags); pCreate->sversion = htonl(pTable->superTable->sversion); @@ -1823,7 +1808,7 @@ static void *mnodeBuildCreateChildTableMsg(SCMCreateTableMsg *pCreateMsg, SCTabl pCreate->tagDataLen = 0; pCreate->superTableUid = 0; } - + SSchema *pSchema = (SSchema *) pCreate->data; if (pTable->info.type == TSDB_CHILD_TABLE) { memcpy(pSchema, pTable->superTable->schema, totalCols * sizeof(SSchema)); @@ -1922,12 +1907,12 @@ static int32_t mnodeDoCreateChildTable(SMnodeMsg *pMsg, int32_t tid) { SCTableObj *pTable = calloc(1, sizeof(SCTableObj)); if (pTable == NULL) { - mError("msg:%p, app:%p table:%s, failed to alloc memory", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + mError("msg:%p, app:%p table:%s, failed to alloc memory", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); return TSDB_CODE_MND_OUT_OF_MEMORY; } pTable->info.type = (pCreate->numOfColumns == 0)? TSDB_CHILD_TABLE:TSDB_NORMAL_TABLE; - pTable->info.tableId = strdup(pCreate->tableId); + pTable->info.tableId = strdup(pCreate->tableFname); pTable->createdTime = taosGetTimestampMs(); pTable->tid = tid; pTable->vgId = pVgroup->vgId; @@ -1943,7 +1928,7 @@ static int32_t mnodeDoCreateChildTable(SMnodeMsg *pMsg, int32_t tid) { size_t prefixLen = tableIdPrefix(pMsg->pDb->name, prefix, 64); if (0 != strncasecmp(prefix, stableName, prefixLen)) { mError("msg:%p, app:%p table:%s, corresponding super table:%s not in this db", pMsg, pMsg->rpcMsg.ahandle, - pCreate->tableId, stableName); + pCreate->tableFname, stableName); mnodeDestroyChildTable(pTable); return TSDB_CODE_TDB_INVALID_CREATE_TB_MSG; } @@ -1951,7 +1936,7 @@ static int32_t mnodeDoCreateChildTable(SMnodeMsg *pMsg, int32_t tid) { if (pMsg->pSTable == NULL) pMsg->pSTable = mnodeGetSuperTable(stableName); if (pMsg->pSTable == NULL) { mError("msg:%p, app:%p table:%s, corresponding super table:%s does not exist", pMsg, pMsg->rpcMsg.ahandle, - pCreate->tableId, stableName); + pCreate->tableFname, stableName); mnodeDestroyChildTable(pTable); return TSDB_CODE_MND_INVALID_TABLE_NAME; } @@ -2013,12 +1998,12 @@ static int32_t mnodeDoCreateChildTable(SMnodeMsg *pMsg, int32_t tid) { .pMsg = pMsg, .fpReq = mnodeDoCreateChildTableFp }; - + int32_t code = sdbInsertRow(&desc); if (code != TSDB_CODE_SUCCESS && code != TSDB_CODE_MND_ACTION_IN_PROGRESS) { mnodeDestroyChildTable(pTable); pMsg->pTable = NULL; - mError("msg:%p, app:%p table:%s, failed to create, reason:%s", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId, + mError("msg:%p, app:%p table:%s, failed to create, reason:%s", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname, tstrerror(code)); } else { mDebug("msg:%p, app:%p table:%s, allocated in vgroup, vgId:%d sid:%d uid:%" PRIu64, pMsg, pMsg->rpcMsg.ahandle, @@ -2035,7 +2020,7 @@ static int32_t mnodeProcessCreateChildTableMsg(SMnodeMsg *pMsg) { int32_t code = grantCheck(TSDB_GRANT_TIMESERIES); if (code != TSDB_CODE_SUCCESS) { mError("msg:%p, app:%p table:%s, failed to create, grant timeseries failed", pMsg, pMsg->rpcMsg.ahandle, - pCreate->tableId); + pCreate->tableFname); return code; } @@ -2046,7 +2031,7 @@ static int32_t mnodeProcessCreateChildTableMsg(SMnodeMsg *pMsg) { code = mnodeGetAvailableVgroup(pMsg, &pVgroup, &tid); if (code != TSDB_CODE_SUCCESS) { mDebug("msg:%p, app:%p table:%s, failed to get available vgroup, reason:%s", pMsg, pMsg->rpcMsg.ahandle, - pCreate->tableId, tstrerror(code)); + pCreate->tableFname, tstrerror(code)); return code; } @@ -2060,15 +2045,15 @@ static int32_t mnodeProcessCreateChildTableMsg(SMnodeMsg *pMsg) { return mnodeDoCreateChildTable(pMsg, tid); } } else { - if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pCreate->tableId); + if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pCreate->tableFname); } if (pMsg->pTable == NULL) { - mError("msg:%p, app:%p table:%s, object not found, retry:%d reason:%s", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId, pMsg->retry, + mError("msg:%p, app:%p table:%s, object not found, retry:%d reason:%s", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname, pMsg->retry, tstrerror(terrno)); return terrno; } else { - mDebug("msg:%p, app:%p table:%s, send create msg to vnode again", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableId); + mDebug("msg:%p, app:%p table:%s, send create msg to vnode again", pMsg, pMsg->rpcMsg.ahandle, pCreate->tableFname); return mnodeDoCreateChildTableFp(pMsg); } } @@ -2084,7 +2069,7 @@ static int32_t mnodeSendDropChildTableMsg(SMnodeMsg *pMsg, bool needReturn) { return TSDB_CODE_MND_OUT_OF_MEMORY; } - tstrncpy(pDrop->tableId, pTable->info.tableId, TSDB_TABLE_FNAME_LEN); + tstrncpy(pDrop->tableFname, pTable->info.tableId, TSDB_TABLE_FNAME_LEN); pDrop->vgId = htonl(pTable->vgId); pDrop->contLen = htonl(sizeof(SMDDropTableMsg)); pDrop->tid = htonl(pTable->tid); @@ -2093,7 +2078,7 @@ static int32_t mnodeSendDropChildTableMsg(SMnodeMsg *pMsg, bool needReturn) { SRpcEpSet epSet = mnodeGetEpSetFromVgroup(pMsg->pVgroup); mInfo("msg:%p, app:%p ctable:%s, send drop ctable msg, vgId:%d sid:%d uid:%" PRIu64, pMsg, pMsg->rpcMsg.ahandle, - pDrop->tableId, pTable->vgId, pTable->tid, pTable->uid); + pDrop->tableFname, pTable->vgId, pTable->tid, pTable->uid); SRpcMsg rpcMsg = { .ahandle = pMsg, @@ -2115,7 +2100,7 @@ static int32_t mnodeDropChildTableCb(SMnodeMsg *pMsg, int32_t code) { SCTableObj *pTable = (SCTableObj *)pMsg->pTable; mError("msg:%p, app:%p ctable:%s, failed to drop, sdb error", pMsg, pMsg->rpcMsg.ahandle, pTable->info.tableId); return code; - } + } return mnodeSendDropChildTableMsg(pMsg, true); } @@ -2224,7 +2209,7 @@ static int32_t mnodeAddNormalTableColumn(SMnodeMsg *pMsg, SSchema schema[], int3 pTable->numOfColumns += ncols; pTable->sversion++; - + SAcctObj *pAcct = mnodeGetAcct(pDb->acct); if (pAcct != NULL) { pAcct->acctInfo.numOfTimeSeries += ncols; @@ -2295,7 +2280,7 @@ static int32_t mnodeChangeNormalTableColumn(SMnodeMsg *pMsg, char *oldName, char if (mnodeFindNormalTableColumnIndex(pTable, newName) >= 0) { return TSDB_CODE_MND_FIELD_ALREAY_EXIST; } - + // update SSchema *schema = (SSchema *) (pTable->schema + col); tstrncpy(schema->name, newName, sizeof(schema->name)); @@ -2335,7 +2320,7 @@ static int32_t mnodeDoGetChildTableMeta(SMnodeMsg *pMsg, STableMetaMsg *pMeta) { pMeta->tid = htonl(pTable->tid); pMeta->precision = pDb->cfg.precision; pMeta->tableType = pTable->info.type; - tstrncpy(pMeta->tableId, pTable->info.tableId, TSDB_TABLE_FNAME_LEN); + tstrncpy(pMeta->tableFname, pTable->info.tableId, TSDB_TABLE_FNAME_LEN); if (pTable->info.type == TSDB_CHILD_TABLE) { assert(pTable->superTable != NULL); @@ -2352,7 +2337,7 @@ static int32_t mnodeDoGetChildTableMeta(SMnodeMsg *pMsg, STableMetaMsg *pMeta) { pMeta->tversion = 0; pMeta->numOfTags = 0; pMeta->numOfColumns = htons((int16_t)pTable->numOfColumns); - pMeta->contLen = sizeof(STableMetaMsg) + mnodeSetSchemaFromNormalTable(pMeta->schema, pTable); + pMeta->contLen = sizeof(STableMetaMsg) + mnodeSetSchemaFromNormalTable(pMeta->schema, pTable); } if (pMsg->pVgroup == NULL) pMsg->pVgroup = mnodeGetVgroup(pTable->vgId); @@ -2383,7 +2368,7 @@ static int32_t mnodeAutoCreateChildTable(SMnodeMsg *pMsg) { if (pMsg->rpcMsg.contLen <= sizeof(*pInfo)) { mError("msg:%p, app:%p table:%s, failed to auto create child table, tags not exist", pMsg, pMsg->rpcMsg.ahandle, - pInfo->tableId); + pInfo->tableFname); return TSDB_CODE_MND_TAG_NOT_EXIST; } @@ -2398,7 +2383,7 @@ static int32_t mnodeAutoCreateChildTable(SMnodeMsg *pMsg) { int32_t totalLen = nameLen + tagLen + sizeof(int32_t)*2; if (tagLen == 0 || nameLen == 0) { mError("msg:%p, app:%p table:%s, failed to create table on demand for super table is empty, tagLen:%d", pMsg, - pMsg->rpcMsg.ahandle, pInfo->tableId, tagLen); + pMsg->rpcMsg.ahandle, pInfo->tableFname, tagLen); return TSDB_CODE_MND_INVALID_STABLE_NAME; } @@ -2406,14 +2391,14 @@ static int32_t mnodeAutoCreateChildTable(SMnodeMsg *pMsg) { SCMCreateTableMsg *pCreateMsg = calloc(1, contLen); if (pCreateMsg == NULL) { mError("msg:%p, app:%p table:%s, failed to create table while get meta info, no enough memory", pMsg, - pMsg->rpcMsg.ahandle, pInfo->tableId); + pMsg->rpcMsg.ahandle, pInfo->tableFname); return TSDB_CODE_MND_OUT_OF_MEMORY; } SCreateTableMsg* pCreate = (SCreateTableMsg*) ((char*) pCreateMsg + sizeof(SCMCreateTableMsg)); - size_t size = tListLen(pInfo->tableId); - tstrncpy(pCreate->tableId, pInfo->tableId, size); + size_t size = tListLen(pInfo->tableFname); + tstrncpy(pCreate->tableFname, pInfo->tableFname, size); tstrncpy(pCreate->db, pMsg->pDb->name, sizeof(pCreate->db)); pCreate->igExists = 1; pCreate->getMeta = 1; @@ -2427,7 +2412,7 @@ static int32_t mnodeAutoCreateChildTable(SMnodeMsg *pMsg) { memcpy(name, pInfo->tags + sizeof(int32_t), nameLen); mDebug("msg:%p, app:%p table:%s, start to create on demand, tagLen:%d stable:%s", pMsg, pMsg->rpcMsg.ahandle, - pInfo->tableId, tagLen, name); + pInfo->tableFname, tagLen, name); if (pMsg->rpcMsg.pCont != pMsg->pCont) { tfree(pMsg->rpcMsg.pCont); @@ -2557,7 +2542,7 @@ static SCTableObj* mnodeGetTableByPos(int32_t vnode, int32_t tid) { static int32_t mnodeProcessTableCfgMsg(SMnodeMsg *pMsg) { return TSDB_CODE_COM_OPS_NOT_SUPPORT; -#if 0 +#if 0 SConfigTableMsg *pCfg = pMsg->rpcMsg.pCont; pCfg->dnodeId = htonl(pCfg->dnodeId); pCfg->vgId = htonl(pCfg->vgId); @@ -2575,13 +2560,13 @@ static int32_t mnodeProcessTableCfgMsg(SMnodeMsg *pMsg) { SMDCreateTableMsg *pCreate = NULL; pCreate = mnodeBuildCreateChildTableMsg(NULL, (SCTableObj *)pTable); mnodeDecTableRef(pTable); - + if (pCreate == NULL) return terrno; - + pMsg->rpcRsp.rsp = pCreate; pMsg->rpcRsp.len = htonl(pCreate->contLen); return TSDB_CODE_SUCCESS; -#endif +#endif } // handle drop child response @@ -2674,7 +2659,7 @@ static void mnodeProcessCreateChildTableRsp(SRpcMsg *rpcMsg) { .pMsg = pMsg, .fpRsp = mnodeDoCreateChildTableCb }; - + int32_t code = sdbInsertRowToQueue(&desc); if (code != TSDB_CODE_SUCCESS && code != TSDB_CODE_MND_ACTION_IN_PROGRESS) { pMsg->pTable = NULL; @@ -2821,7 +2806,7 @@ static int32_t mnodeProcessMultiTableMetaMsg(SMnodeMsg *pMsg) { static int32_t mnodeGetShowTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, void *pConn) { SDbObj *pDb = mnodeGetDb(pShow->db); if (pDb == NULL) return TSDB_CODE_MND_DB_NOT_SELECTED; - + if (pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pDb->name, pDb->status); mnodeDecDbRef(pDb); @@ -2894,7 +2879,7 @@ static int32_t mnodeGetShowTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, void static int32_t mnodeRetrieveShowTables(SShowObj *pShow, char *data, int32_t rows, void *pConn) { SDbObj *pDb = mnodeGetDb(pShow->db); if (pDb == NULL) return 0; - + if (pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pDb->name, pDb->status); mnodeDecDbRef(pDb); @@ -2931,7 +2916,7 @@ static int32_t mnodeRetrieveShowTables(SShowObj *pShow, char *data, int32_t rows } char tableName[TSDB_TABLE_NAME_LEN] = {0}; - + // pattern compare for table name mnodeExtractTableName(pTable->info.tableId, tableName); @@ -2960,13 +2945,13 @@ static int32_t mnodeRetrieveShowTables(SShowObj *pShow, char *data, int32_t rows cols++; pWrite = data + pShow->offset[cols] * rows + pShow->bytes[cols] * numOfRows; - + memset(tableName, 0, sizeof(tableName)); if (pTable->info.type == TSDB_CHILD_TABLE) { mnodeExtractTableName(pTable->superTable->info.tableId, tableName); STR_WITH_MAXSIZE_TO_VARSTR(pWrite, tableName, pShow->bytes[cols]); } - + cols++; // uid @@ -3001,27 +2986,27 @@ static int32_t mnodeRetrieveShowTables(SShowObj *pShow, char *data, int32_t rows static int32_t mnodeProcessAlterTableMsg(SMnodeMsg *pMsg) { SAlterTableMsg *pAlter = pMsg->rpcMsg.pCont; mDebug("msg:%p, app:%p table:%s, alter table msg is received from thandle:%p", pMsg, pMsg->rpcMsg.ahandle, - pAlter->tableId, pMsg->rpcMsg.handle); + pAlter->tableFname, pMsg->rpcMsg.handle); - if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDbByTableId(pAlter->tableId); + if (pMsg->pDb == NULL) pMsg->pDb = mnodeGetDbByTableId(pAlter->tableFname); if (pMsg->pDb == NULL) { - mError("msg:%p, app:%p table:%s, failed to alter table, db not selected", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableId); + mError("msg:%p, app:%p table:%s, failed to alter table, db not selected", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableFname); return TSDB_CODE_MND_DB_NOT_SELECTED; } - + if (pMsg->pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pMsg->pDb->name, pMsg->pDb->status); return TSDB_CODE_MND_DB_IN_DROPPING; } if (mnodeCheckIsMonitorDB(pMsg->pDb->name, tsMonitorDbName)) { - mError("msg:%p, app:%p table:%s, failed to alter table, its log db", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableId); + mError("msg:%p, app:%p table:%s, failed to alter table, its log db", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableFname); return TSDB_CODE_MND_MONITOR_DB_FORBIDDEN; } - if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pAlter->tableId); + if (pMsg->pTable == NULL) pMsg->pTable = mnodeGetTable(pAlter->tableFname); if (pMsg->pTable == NULL) { - mError("msg:%p, app:%p table:%s, failed to alter table, table not exist", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableId); + mError("msg:%p, app:%p table:%s, failed to alter table, table not exist", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableFname); return TSDB_CODE_MND_INVALID_TABLE_NAME; } @@ -3030,7 +3015,7 @@ static int32_t mnodeProcessAlterTableMsg(SMnodeMsg *pMsg) { pAlter->tagValLen = htonl(pAlter->tagValLen); if (pAlter->numOfCols > 2) { - mError("msg:%p, app:%p table:%s, error numOfCols:%d in alter table", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableId, + mError("msg:%p, app:%p table:%s, error numOfCols:%d in alter table", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableFname, pAlter->numOfCols); return TSDB_CODE_MND_APP_ERROR; } @@ -3041,7 +3026,7 @@ static int32_t mnodeProcessAlterTableMsg(SMnodeMsg *pMsg) { int32_t code = TSDB_CODE_COM_OPS_NOT_SUPPORT; if (pMsg->pTable->type == TSDB_SUPER_TABLE) { - mDebug("msg:%p, app:%p table:%s, start to alter stable", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableId); + mDebug("msg:%p, app:%p table:%s, start to alter stable", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableFname); if (pAlter->type == TSDB_ALTER_TABLE_ADD_TAG_COLUMN) { code = mnodeAddSuperTableTag(pMsg, pAlter->schema, 1); } else if (pAlter->type == TSDB_ALTER_TABLE_DROP_TAG_COLUMN) { @@ -3057,7 +3042,7 @@ static int32_t mnodeProcessAlterTableMsg(SMnodeMsg *pMsg) { } else { } } else { - mDebug("msg:%p, app:%p table:%s, start to alter ctable", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableId); + mDebug("msg:%p, app:%p table:%s, start to alter ctable", pMsg, pMsg->rpcMsg.ahandle, pAlter->tableFname); if (pAlter->type == TSDB_ALTER_TABLE_UPDATE_TAG_VAL) { return TSDB_CODE_COM_OPS_NOT_SUPPORT; } else if (pAlter->type == TSDB_ALTER_TABLE_ADD_COLUMN) { @@ -3076,7 +3061,7 @@ static int32_t mnodeProcessAlterTableMsg(SMnodeMsg *pMsg) { static int32_t mnodeGetStreamTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, void *pConn) { SDbObj *pDb = mnodeGetDb(pShow->db); if (pDb == NULL) return TSDB_CODE_MND_DB_NOT_SELECTED; - + if (pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pDb->name, pDb->status); mnodeDecDbRef(pDb); @@ -3129,13 +3114,13 @@ static int32_t mnodeGetStreamTableMeta(STableMetaMsg *pMeta, SShowObj *pShow, vo static int32_t mnodeRetrieveStreamTables(SShowObj *pShow, char *data, int32_t rows, void *pConn) { SDbObj *pDb = mnodeGetDb(pShow->db); if (pDb == NULL) return 0; - + if (pDb->status != TSDB_DB_STATUS_READY) { mError("db:%s, status:%d, in dropping", pDb->name, pDb->status); mnodeDecDbRef(pDb); return 0; } - + int32_t numOfRows = 0; SCTableObj *pTable = NULL; SPatternCompareInfo info = PATTERN_COMPARE_INFO_INITIALIZER; @@ -3148,7 +3133,7 @@ static int32_t mnodeRetrieveStreamTables(SShowObj *pShow, char *data, int32_t ro while (numOfRows < rows) { pShow->pIter = mnodeGetNextChildTable(pShow->pIter, &pTable); if (pTable == NULL) break; - + // not belong to current db if (strncmp(pTable->info.tableId, prefix, prefixLen) || pTable->info.type != TSDB_STREAM_TABLE) { mnodeDecTableRef(pTable); @@ -3156,7 +3141,7 @@ static int32_t mnodeRetrieveStreamTables(SShowObj *pShow, char *data, int32_t ro } char tableName[TSDB_TABLE_NAME_LEN] = {0}; - + // pattern compare for table name mnodeExtractTableName(pTable->info.tableId, tableName); diff --git a/src/mnode/src/mnodeUser.c b/src/mnode/src/mnodeUser.c index fb26086d04..fbee8a42b8 100644 --- a/src/mnode/src/mnodeUser.c +++ b/src/mnode/src/mnodeUser.c @@ -337,7 +337,7 @@ static int32_t mnodeGetUserMeta(STableMetaMsg *pMeta, SShowObj *pShow, void *pCo cols++; pMeta->numOfColumns = htons(cols); - strcpy(pMeta->tableId, "show users"); + strcpy(pMeta->tableFname, "show users"); pShow->numOfColumns = cols; pShow->offset[0] = 0; diff --git a/src/mnode/src/mnodeVgroup.c b/src/mnode/src/mnodeVgroup.c index 827be0687d..881ef95fca 100644 --- a/src/mnode/src/mnodeVgroup.c +++ b/src/mnode/src/mnodeVgroup.c @@ -565,7 +565,7 @@ int32_t mnodeCreateVgroup(SMnodeMsg *pMsg) { SDbObj *pDb = pMsg->pDb; SVgObj *pVgroup = (SVgObj *)calloc(1, sizeof(SVgObj)); - tstrncpy(pVgroup->dbName, pDb->name, TSDB_ACCT_LEN + TSDB_DB_NAME_LEN); + tstrncpy(pVgroup->dbName, pDb->name, TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN); pVgroup->numOfVnodes = pDb->cfg.replications; pVgroup->createdTime = taosGetTimestampMs(); pVgroup->accessState = TSDB_VN_ALL_ACCCESS; diff --git a/src/os/CMakeLists.txt b/src/os/CMakeLists.txt index 4e44d29a02..f41719f240 100644 --- a/src/os/CMakeLists.txt +++ b/src/os/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX) @@ -10,3 +10,5 @@ ELSEIF (TD_WINDOWS) ENDIF () ADD_SUBDIRECTORY(src/detail) +ADD_SUBDIRECTORY(tests) + diff --git a/src/os/src/alpine/CMakeLists.txt b/src/os/src/alpine/CMakeLists.txt index b5e739c24c..daa0b3cf43 100644 --- a/src/os/src/alpine/CMakeLists.txt +++ b/src/os/src/alpine/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) AUX_SOURCE_DIRECTORY(. SRC) diff --git a/src/os/src/darwin/CMakeLists.txt b/src/os/src/darwin/CMakeLists.txt index c4cb28aa05..7f05ddd64b 100644 --- a/src/os/src/darwin/CMakeLists.txt +++ b/src/os/src/darwin/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) AUX_SOURCE_DIRECTORY(. SRC) diff --git a/src/os/src/detail/CMakeLists.txt b/src/os/src/detail/CMakeLists.txt index 0d5c130d6e..e4052a4fb3 100644 --- a/src/os/src/detail/CMakeLists.txt +++ b/src/os/src/detail/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(.) diff --git a/src/os/src/detail/osTime.c b/src/os/src/detail/osTime.c index b78627f46f..1710c469fb 100644 --- a/src/os/src/detail/osTime.c +++ b/src/os/src/detail/osTime.c @@ -486,7 +486,7 @@ int64_t taosTimeTruncate(int64_t t, const SInterval* pInterval, int32_t precisio start = (delta / pInterval->sliding + factor) * pInterval->sliding; if (pInterval->intervalUnit == 'd' || pInterval->intervalUnit == 'w') { - /* + /* * here we revised the start time of day according to the local time zone, * but in case of DST, the start time of one day need to be dynamically decided. */ @@ -501,9 +501,24 @@ int64_t taosTimeTruncate(int64_t t, const SInterval* pInterval, int32_t precisio start += (int64_t)(timezone * TSDB_TICK_PER_SECOND(precision)); } - int64_t end = start + pInterval->interval - 1; - if (end < t) { - start += pInterval->sliding; + int64_t end = 0; + + // not enough time range + if (INT64_MAX - start > pInterval->interval - 1) { + end = start + pInterval->interval - 1; + + while(end < t && ((start + pInterval->sliding) <= INT64_MAX)) { // move forward to the correct time window + start += pInterval->sliding; + + if (INT64_MAX - start > pInterval->interval - 1) { + end = start + pInterval->interval - 1; + } else { + end = INT64_MAX; + break; + } + } + } else { + end = INT64_MAX; } } diff --git a/src/os/src/linux/CMakeLists.txt b/src/os/src/linux/CMakeLists.txt index b1a7ebf54e..8ab8f55467 100644 --- a/src/os/src/linux/CMakeLists.txt +++ b/src/os/src/linux/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) AUX_SOURCE_DIRECTORY(. SRC) diff --git a/src/os/src/windows/CMakeLists.txt b/src/os/src/windows/CMakeLists.txt index 9dcc9e7e6d..a430dd3b3f 100644 --- a/src/os/src/windows/CMakeLists.txt +++ b/src/os/src/windows/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) AUX_SOURCE_DIRECTORY(. SRC) diff --git a/src/os/tests/CMakeLists.txt b/src/os/tests/CMakeLists.txt new file mode 100644 index 0000000000..1a18a72b40 --- /dev/null +++ b/src/os/tests/CMakeLists.txt @@ -0,0 +1,15 @@ +CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +PROJECT(TDengine) + +FIND_PATH(HEADER_GTEST_INCLUDE_DIR gtest.h /usr/include/gtest /usr/local/include/gtest) +FIND_LIBRARY(LIB_GTEST_STATIC_DIR libgtest.a /usr/lib/ /usr/local/lib) + +IF (HEADER_GTEST_INCLUDE_DIR AND LIB_GTEST_STATIC_DIR) + MESSAGE(STATUS "gTest library found, build unit test") + + INCLUDE_DIRECTORIES(${HEADER_GTEST_INCLUDE_DIR}) + AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR} SOURCE_LIST) + + ADD_EXECUTABLE(osTest ${SOURCE_LIST}) + TARGET_LINK_LIBRARIES(osTest taos osdetail tutil common gtest pthread) +ENDIF() \ No newline at end of file diff --git a/src/os/tests/test.cpp b/src/os/tests/test.cpp new file mode 100644 index 0000000000..600e5d71a7 --- /dev/null +++ b/src/os/tests/test.cpp @@ -0,0 +1,34 @@ +#include "os.h" +#include +#include +#include + +#include "taos.h" +#include "tstoken.h" +#include "tutil.h" + +int main(int argc, char** argv) { + testing::InitGoogleTest(&argc, argv); + return RUN_ALL_TESTS(); +} + +// test function in os module +TEST(testCase, parse_time) { + taos_options(TSDB_OPTION_TIMEZONE, "GMT-8"); + deltaToUtcInitOnce(); + + // window: 1500000001000, 1500002000000 + // pQuery->interval: interval: 86400000, sliding:3600000 + int64_t key = 1500000001000; + SInterval interval = {0}; + interval.interval = 86400000; + interval.intervalUnit = 'd'; + interval.sliding = 3600000; + interval.slidingUnit = 'h'; + + int64_t s = taosTimeTruncate(key, &interval, TSDB_TIME_PRECISION_MILLI); + ASSERT_TRUE(s + interval.interval >= key); +} + + + diff --git a/src/plugins/CMakeLists.txt b/src/plugins/CMakeLists.txt index 742235894a..d03717b6e1 100644 --- a/src/plugins/CMakeLists.txt +++ b/src/plugins/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) ADD_SUBDIRECTORY(monitor) diff --git a/src/plugins/http/CMakeLists.txt b/src/plugins/http/CMakeLists.txt index 5d8b52986a..56c3c25d7c 100644 --- a/src/plugins/http/CMakeLists.txt +++ b/src/plugins/http/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/deps/zlib-1.2.11/inc) diff --git a/src/plugins/http/inc/httpInt.h b/src/plugins/http/inc/httpInt.h index ebdfabf310..ac182b707b 100644 --- a/src/plugins/http/inc/httpInt.h +++ b/src/plugins/http/inc/httpInt.h @@ -39,7 +39,7 @@ #define HTTP_GC_TARGET_SIZE 512 #define HTTP_WRITE_RETRY_TIMES 500 #define HTTP_WRITE_WAIT_TIME_MS 5 -#define HTTP_SESSION_ID_LEN (TSDB_USER_LEN + TSDB_PASSWORD_LEN) +#define HTTP_SESSION_ID_LEN (TSDB_USER_LEN + TSDB_KEY_LEN) typedef enum HttpReqType { HTTP_REQTYPE_OTHERS = 0, @@ -147,7 +147,7 @@ typedef struct HttpContext { uint8_t parsed; char ipstr[22]; char user[TSDB_USER_LEN]; // parsed from auth token or login message - char pass[TSDB_PASSWORD_LEN]; + char pass[TSDB_KEY_LEN]; TAOS * taos; void * ppContext; HttpSession *session; diff --git a/src/plugins/http/src/httpAuth.c b/src/plugins/http/src/httpAuth.c index 8beef7c042..56da8a7089 100644 --- a/src/plugins/http/src/httpAuth.c +++ b/src/plugins/http/src/httpAuth.c @@ -51,7 +51,7 @@ int32_t httpParseBasicAuthToken(HttpContext *pContext, char *token, int32_t len) char *password = user + 1; int32_t pass_len = (int32_t)((base64 + outlen) - password); - if (pass_len < 1 || pass_len >= TSDB_PASSWORD_LEN) { + if (pass_len < 1 || pass_len >= TSDB_KEY_LEN) { httpError("context:%p, fd:%d, basic token:%s parse password error", pContext, pContext->fd, token); free(base64); return -1; @@ -73,7 +73,7 @@ int32_t httpParseTaosdAuthToken(HttpContext *pContext, char *token, int32_t len) if (base64) free(base64); return 01; } - if (outlen != (TSDB_USER_LEN + TSDB_PASSWORD_LEN)) { + if (outlen != (TSDB_USER_LEN + TSDB_KEY_LEN)) { httpError("context:%p, fd:%d, taosd token:%s length error", pContext, pContext->fd, token); free(base64); return -1; @@ -103,8 +103,8 @@ int32_t httpGenTaosdAuthToken(HttpContext *pContext, char *token, int32_t maxLen size = sizeof(pContext->pass); tstrncpy(buffer + sizeof(pContext->user), pContext->pass, size); - char *encrypt = taosDesEncode(KEY_DES_4, buffer, TSDB_USER_LEN + TSDB_PASSWORD_LEN); - char *base64 = base64_encode((const unsigned char *)encrypt, TSDB_USER_LEN + TSDB_PASSWORD_LEN); + char *encrypt = taosDesEncode(KEY_DES_4, buffer, TSDB_USER_LEN + TSDB_KEY_LEN); + char *base64 = base64_encode((const unsigned char *)encrypt, TSDB_USER_LEN + TSDB_KEY_LEN); size_t len = strlen(base64); tstrncpy(token, base64, len + 1); diff --git a/src/plugins/http/src/httpGcHandle.c b/src/plugins/http/src/httpGcHandle.c index 5d4cb0c680..c21799e736 100644 --- a/src/plugins/http/src/httpGcHandle.c +++ b/src/plugins/http/src/httpGcHandle.c @@ -59,11 +59,11 @@ bool gcGetUserFromUrl(HttpContext* pContext) { bool gcGetPassFromUrl(HttpContext* pContext) { HttpParser* pParser = pContext->parser; - if (pParser->path[GC_PASS_URL_POS].pos >= TSDB_PASSWORD_LEN || pParser->path[GC_PASS_URL_POS].pos <= 0) { + if (pParser->path[GC_PASS_URL_POS].pos >= TSDB_KEY_LEN || pParser->path[GC_PASS_URL_POS].pos <= 0) { return false; } - tstrncpy(pContext->pass, pParser->path[GC_PASS_URL_POS].str, TSDB_PASSWORD_LEN); + tstrncpy(pContext->pass, pParser->path[GC_PASS_URL_POS].str, TSDB_KEY_LEN); return true; } diff --git a/src/plugins/http/src/httpRestHandle.c b/src/plugins/http/src/httpRestHandle.c index 0a28c431ef..66f1db1a54 100644 --- a/src/plugins/http/src/httpRestHandle.c +++ b/src/plugins/http/src/httpRestHandle.c @@ -72,11 +72,11 @@ bool restGetUserFromUrl(HttpContext* pContext) { bool restGetPassFromUrl(HttpContext* pContext) { HttpParser* pParser = pContext->parser; - if (pParser->path[REST_PASS_URL_POS].pos >= TSDB_PASSWORD_LEN || pParser->path[REST_PASS_URL_POS].pos <= 0) { + if (pParser->path[REST_PASS_URL_POS].pos >= TSDB_KEY_LEN || pParser->path[REST_PASS_URL_POS].pos <= 0) { return false; } - tstrncpy(pContext->pass, pParser->path[REST_PASS_URL_POS].str, TSDB_PASSWORD_LEN); + tstrncpy(pContext->pass, pParser->path[REST_PASS_URL_POS].str, TSDB_KEY_LEN); return true; } diff --git a/src/plugins/http/src/httpTgHandle.c b/src/plugins/http/src/httpTgHandle.c index e2b57b87bb..0a3ef539e3 100644 --- a/src/plugins/http/src/httpTgHandle.c +++ b/src/plugins/http/src/httpTgHandle.c @@ -324,7 +324,7 @@ bool tgGetUserFromUrl(HttpContext *pContext) { bool tgGetPassFromUrl(HttpContext *pContext) { HttpParser *pParser = pContext->parser; - if (pParser->path[TG_PASS_URL_POS].pos >= TSDB_PASSWORD_LEN || pParser->path[TG_PASS_URL_POS].pos <= 0) { + if (pParser->path[TG_PASS_URL_POS].pos >= TSDB_KEY_LEN || pParser->path[TG_PASS_URL_POS].pos <= 0) { return false; } diff --git a/src/plugins/monitor/CMakeLists.txt b/src/plugins/monitor/CMakeLists.txt index edea2187ea..90189c9d75 100644 --- a/src/plugins/monitor/CMakeLists.txt +++ b/src/plugins/monitor/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/plugins/mqtt/CMakeLists.txt b/src/plugins/mqtt/CMakeLists.txt index cf5729d608..3761f70134 100644 --- a/src/plugins/mqtt/CMakeLists.txt +++ b/src/plugins/mqtt/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/query/CMakeLists.txt b/src/query/CMakeLists.txt index c1024f0080..e403251858 100644 --- a/src/query/CMakeLists.txt +++ b/src/query/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/tsdb/inc) diff --git a/src/query/inc/qFill.h b/src/query/inc/qFill.h index 385ae88543..93537ec3da 100644 --- a/src/query/inc/qFill.h +++ b/src/query/inc/qFill.h @@ -82,9 +82,9 @@ void taosFillCopyInputDataFromFilePage(SFillInfo* pFillInfo, const tFilePage** p void taosFillCopyInputDataFromOneFilePage(SFillInfo* pFillInfo, const tFilePage* pInput); -int64_t getNumOfResWithFill(SFillInfo* pFillInfo, int64_t ekey, int32_t maxNumOfRows); +bool taosFillHasMoreResults(SFillInfo* pFillInfo); -int32_t taosNumOfRemainRows(SFillInfo *pFillInfo); +int64_t getNumOfResultsAfterFillGap(SFillInfo* pFillInfo, int64_t ekey, int32_t maxNumOfRows); int32_t taosGetLinearInterpolationVal(int32_t type, SPoint *point1, SPoint *point2, SPoint *point); diff --git a/src/query/inc/qPercentile.h b/src/query/inc/qPercentile.h index c34c24c5b2..f5b770593c 100644 --- a/src/query/inc/qPercentile.h +++ b/src/query/inc/qPercentile.h @@ -16,32 +16,36 @@ #ifndef TDENGINE_QPERCENTILE_H #define TDENGINE_QPERCENTILE_H +#ifdef __cplusplus +extern "C" { +#endif + #include "qExtbuffer.h" #include "qResultbuf.h" #include "qTsbuf.h" typedef struct MinMaxEntry { union { - double dMinVal; - int32_t iMinVal; - int64_t i64MinVal; + double dMinVal; + int64_t i64MinVal; + uint64_t u64MinVal; }; union { double dMaxVal; - int32_t iMaxVal; int64_t i64MaxVal; + int64_t u64MaxVal; }; } MinMaxEntry; typedef struct { - int32_t size; - int32_t pageId; + int32_t size; + int32_t pageId; tFilePage *data; } SSlotInfo; typedef struct tMemBucketSlot { - SSlotInfo info; - MinMaxEntry range; + SSlotInfo info; + MinMaxEntry range; } tMemBucketSlot; struct tMemBucket; @@ -52,16 +56,16 @@ typedef struct tMemBucket { int16_t type; int16_t bytes; int32_t total; - int32_t elemPerPage; // number of elements for each object - int32_t maxCapacity; // maximum allowed number of elements that can be sort directly to get the result - int32_t bufPageSize; // disk page size - MinMaxEntry range; // value range - int32_t times; // count that has been checked for deciding the correct data value buckets. + int32_t elemPerPage; // number of elements for each object + int32_t maxCapacity; // maximum allowed number of elements that can be sort directly to get the result + int32_t bufPageSize; // disk page size + MinMaxEntry range; // value range + int32_t times; // count that has been checked for deciding the correct data value buckets. __compar_fn_t comparFn; - tMemBucketSlot *pSlots; + tMemBucketSlot * pSlots; SDiskbasedResultBuf *pBuffer; - __perc_hash_func_t hashFunc; + __perc_hash_func_t hashFunc; } tMemBucket; tMemBucket *tMemBucketCreate(int16_t nElemSize, int16_t dataType, double minval, double maxval); @@ -73,3 +77,7 @@ int32_t tMemBucketPut(tMemBucket *pBucket, const void *data, size_t size); double getPercentile(tMemBucket *pMemBucket, double percent); #endif // TDENGINE_QPERCENTILE_H + +#ifdef __cplusplus +} +#endif \ No newline at end of file diff --git a/src/query/src/qAggMain.c b/src/query/src/qAggMain.c index 0427d65561..543b205112 100644 --- a/src/query/src/qAggMain.c +++ b/src/query/src/qAggMain.c @@ -1901,7 +1901,7 @@ static void valuePairAssign(tValuePair *dst, int16_t type, const char *val, int6 static void do_top_function_add(STopBotInfo *pInfo, int32_t maxLen, void *pData, int64_t ts, uint16_t type, SExtTagsInfo *pTagInfo, char *pTags, int16_t stage) { tVariant val = {0}; - tVariantCreateFromBinary(&val, pData, tDataTypeDesc[type].nSize, type); + tVariantCreateFromBinary(&val, pData, tDataTypes[type].bytes, type); tValuePair **pList = pInfo->res; assert(pList != NULL); @@ -1958,7 +1958,7 @@ static void do_top_function_add(STopBotInfo *pInfo, int32_t maxLen, void *pData, static void do_bottom_function_add(STopBotInfo *pInfo, int32_t maxLen, void *pData, int64_t ts, uint16_t type, SExtTagsInfo *pTagInfo, char *pTags, int16_t stage) { tVariant val = {0}; - tVariantCreateFromBinary(&val, pData, tDataTypeDesc[type].nSize, type); + tVariantCreateFromBinary(&val, pData, tDataTypes[type].bytes, type); tValuePair **pList = pInfo->res; assert(pList != NULL); @@ -2545,7 +2545,7 @@ static void percentile_next_step(SQLFunctionCtx *pCtx) { if (pInfo->numOfElems == 0) { pResInfo->complete = true; } else { - pInfo->pMemBucket = tMemBucketCreate(pCtx->inputBytes, pCtx->inputType, GET_DOUBLE_VAL(&pInfo->minval), GET_DOUBLE_VAL(&pInfo->maxval)); + pInfo->pMemBucket = tMemBucketCreate(pCtx->inputBytes, pCtx->inputType, pInfo->minval, pInfo->maxval); } pInfo->stage += 1; diff --git a/src/query/src/qArithmeticOperator.c b/src/query/src/qArithmeticOperator.c index 27bdd4372b..677951bd07 100644 --- a/src/query/src/qArithmeticOperator.c +++ b/src/query/src/qArithmeticOperator.c @@ -16,7 +16,7 @@ #include "os.h" #include "qArithmeticOperator.h" -#include "taosdef.h" +#include "ttype.h" #include "tutil.h" #define ARRAY_LIST_OP(left, right, _left_type, _right_type, len1, len2, out, op, _res_type, _ord) \ @@ -145,7 +145,7 @@ void calc_i32_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight if (numLeft == numRight) { for (; i >= 0 && i < numRight; i += step, pOutput += 1) { if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); + SET_DOUBLE_NULL(pOutput); continue; } @@ -154,7 +154,7 @@ void calc_i32_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight } else if (numLeft == 1) { for (; i >= 0 && i < numRight; i += step, pOutput += 1) { if (isNull((char *)(pLeft), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); + SET_DOUBLE_NULL(pOutput); continue; } @@ -163,7 +163,7 @@ void calc_i32_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight } else if (numRight == 1) { for (; i >= 0 && i < numLeft; i += step, pOutput += 1) { if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)(pRight), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); + SET_DOUBLE_NULL(pOutput); continue; } *pOutput = (double)pLeft[i] + pRight[0]; @@ -2556,1123 +2556,6 @@ void vectorRemainder(void *left, int32_t numLeft, int32_t leftType, void *right, } } -/* -void calc_i32_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int8_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i16_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int16_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i64_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int64_t); - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_f_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, float) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i32_d_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, double) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i8_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int8_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_u8_u8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, uint8_t, uint8_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_UTINYINT, TSDB_DATA_TYPE_UTINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_u8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, uint8_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_UTINYINT, numLeft, numRight, pOutput, order); -} - -void calc_u8_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_u8_add(right, left, numRight, numLeft, output, order); -} - -void calc_i8_i16_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int16_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_i8_add(right, left, numRight, numLeft, output, order); -} - -void calc_i8_i64_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int64_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_f_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, float) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i8_d_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, double) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i16_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_i16_add(right, left, numRight, numLeft, output, order); -} - -void calc_i16_i16_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int16_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_i16_add(right, left, numRight, numLeft, output, order); -} - -void calc_i16_i64_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int64_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_f_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, float) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i16_d_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, double) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i64_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_i64_add(right, left, numRight, numLeft, output, order); -} - -void calc_i64_i16_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i16_i64_add(right, left, numRight, numLeft, output, order); -} - -void calc_i64_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_i64_add(right, left, numRight, numLeft, output, order); -} - -void calc_i64_i64_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int64_t) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_f_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, float) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i64_d_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, double) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_f_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_f_add(right, left, numRight, numLeft, output, order); -} - -void calc_f_i16_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i16_f_add(right, left, numRight, numLeft, output, order); -} - -void calc_f_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_f_add(right, left, numRight, numLeft, output, order); -} - -void calc_f_i64_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i64_f_add(right, left, numRight, numLeft, output, order); -} - -void calc_f_f_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, float) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_f_d_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, double) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_d_i8_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_d_add(right, left, numRight, numLeft, output, order); -} - -void calc_d_i16_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i16_d_add(right, left, numRight, numLeft, output, order); -} - -void calc_d_i32_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_d_add(right, left, numRight, numLeft, output, order); -} - -void calc_d_i64_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i64_d_add(right, left, numRight, numLeft, output, order); -} - -void calc_d_f_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_f_d_add(right, left, numRight, numLeft, output, order); -} - -void calc_d_d_add(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, double) - ARRAY_LIST_ADD(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -///////////////////////////////////////////////////////////////////////////////////////////////////////// -void calc_i32_i32_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - int32_t *pLeft = (int32_t *)left; - int32_t *pRight = (int32_t *)right; - double * pOutput = (double *)output; - - int32_t i = (order == TSDB_ORDER_ASC) ? 0 : MAX(numLeft, numRight) - 1; - int32_t step = (order == TSDB_ORDER_ASC) ? 1 : -1; - - if (numLeft == numRight) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - *pOutput = (double)pLeft[i] - pRight[i]; - } - } else if (numLeft == 1) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)(pLeft), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - *pOutput = (double)pLeft[0] - pRight[i]; - } - } else if (numRight == 1) { - for (; i >= 0 && i < numLeft; i += step, pOutput += 1) { - if (isNull((char *)&pLeft[i], TSDB_DATA_TYPE_INT) || isNull((char *)(pRight), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - *pOutput = (double)pLeft[i] - pRight[0]; - } - } -} - -void calc_i32_i8_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int8_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i16_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int16_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i64_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int64_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_f_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, float) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i32_d_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, double) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i8_i8_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int8_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i16_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int16_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i32_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int32_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i64_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int64_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_f_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, float) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i8_d_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, double) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i16_i8_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int8_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i16_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int16_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i32_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int32_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i64_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int64_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_f_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, float) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i16_d_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, double) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i64_i8_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int8_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i16_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int16_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i32_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int32_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i64_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int64_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_f_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, float) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i64_d_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, double) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_f_i8_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int8_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_f_i16_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int16_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_f_i32_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int32_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_f_i64_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int64_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_f_f_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, float) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_f_d_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, double) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_d_i8_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int8_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_d_i16_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int16_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_d_i32_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int32_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_d_i64_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int64_t) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_d_f_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, float) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_d_d_sub(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, double) - ARRAY_LIST_SUB(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -///////////////////////////////////////////////////////////////////////////////////////////////////////// -void calc_i32_i32_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - int32_t *pLeft = (int32_t *)left; - int32_t *pRight = (int32_t *)right; - double * pOutput = (double *)output; - - int32_t i = (order == TSDB_ORDER_ASC) ? 0 : MAX(numLeft, numRight) - 1; - int32_t step = (order == TSDB_ORDER_ASC) ? 1 : -1; - - if (numLeft == numRight) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[i] * pRight[i]; - } - } else if (numLeft == 1) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)(pLeft), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[0] * pRight[i]; - } - } else if (numRight == 1) { - for (; i >= 0 && i < numLeft; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)(pRight), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - *pOutput = (double)pLeft[i] * pRight[0]; - } - } -} - -void calc_i32_i8_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int8_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i16_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int16_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i64_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int64_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_f_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, float) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i32_d_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, double) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i8_i8_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int8_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i16_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int16_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i32_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_i8_multi(right, left, numRight, numLeft, output, order); -} - -void calc_i8_i64_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int64_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_f_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, float) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i8_d_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, double) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i16_i8_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_i16_multi(right, left, numRight, numLeft, output, order); -} - -void calc_i16_i16_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int16_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i32_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_i16_multi(right, left, numRight, numLeft, output, order); -} - -void calc_i16_i64_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int64_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_f_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, float) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i16_d_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, double) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i64_i8_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_i64_multi(right, left, numRight, numLeft, output, order); -} - -void calc_i64_i16_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i16_i64_multi(right, left, numRight, numLeft, output, order); -} - -void calc_i64_i32_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_i64_multi(right, left, numRight, numLeft, output, order); -} - -void calc_i64_i64_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int64_t) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_f_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, float) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i64_d_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, double) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_f_i8_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_f_multi(right, left, numRight, numLeft, output, order); -} - -void calc_f_i16_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i16_f_multi(right, left, numRight, numLeft, output, order); -} - -void calc_f_i32_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_f_multi(right, left, numRight, numLeft, output, order); -} - -void calc_f_i64_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i64_f_multi(right, left, numRight, numLeft, output, order); -} - -void calc_f_f_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, float) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_f_d_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, double) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_d_i8_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i8_d_multi(right, left, numRight, numLeft, output, order); -} - -void calc_d_i16_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i16_d_multi(right, left, numRight, numLeft, output, order); -} - -void calc_d_i32_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i32_d_multi(right, left, numRight, numLeft, output, order); -} - -void calc_d_i64_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_i64_d_multi(right, left, numRight, numLeft, output, order); -} - -void calc_d_f_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - calc_f_d_multi(right, left, numRight, numLeft, output, order); -} - -void calc_d_d_multi(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, double) - ARRAY_LIST_MULTI(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -//////////////////////////////////////////////////////////////////////////////////////////////////////////// -void calc_i32_i32_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - int32_t *pLeft = (int32_t *)left; - int32_t *pRight = (int32_t *)right; - double * pOutput = (double *)output; - - int32_t i = (order == TSDB_ORDER_ASC) ? 0 : MAX(numLeft, numRight) - 1; - int32_t step = (order == TSDB_ORDER_ASC) ? 1 : -1; - - if (numLeft == numRight) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[i] / pRight[i]; - } - } else if (numLeft == 1) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)(pLeft), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[0] / pRight[i]; - } - } else if (numRight == 1) { - for (; i >= 0 && i < numLeft; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)(pRight), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - *pOutput = (double)pLeft[i] / pRight[0]; - } - } -} - -void calc_i32_i8_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int8_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i16_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int16_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i64_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int64_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_f_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, float) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i32_d_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, double) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i8_i8_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int8_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i16_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int16_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i32_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int32_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i64_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int64_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_f_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, float) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i8_d_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, double) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i16_i8_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int8_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i16_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int16_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i32_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int32_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i64_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int64_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_f_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, float) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i16_d_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, double) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i64_i8_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int8_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i16_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int16_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i32_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int32_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i64_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int64_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_f_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, float) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i64_d_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, double) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_f_i8_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int8_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_f_i16_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int16_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_f_i32_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int32_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_f_i64_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int64_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_f_f_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, float) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_f_d_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, double) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_d_i8_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int8_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_d_i16_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int16_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_d_i32_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int32_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_d_i64_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int64_t) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_d_f_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, float) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_d_d_div(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, double) - ARRAY_LIST_DIV(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -//////////////////////////////////////////////////////////////////////////////////////////////////////////// - -void calc_i32_i32_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - int32_t *pLeft = (int32_t *)left; - int32_t *pRight = (int32_t *)right; - double * pOutput = (double *)output; - - int32_t i = (order == TSDB_ORDER_ASC) ? 0 : MAX(numLeft, numRight) - 1; - int32_t step = (order == TSDB_ORDER_ASC) ? 1 : -1; - - if (numLeft == numRight) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[i] - ((int64_t)(((double)pLeft[i]) / pRight[i])) * pRight[i]; - } - } else if (numLeft == 1) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)(pLeft), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[0] - ((int64_t)(((double)pLeft[0]) / pRight[i])) * pRight[i]; - } - } else if (numRight == 1) { - for (; i >= 0 && i < numLeft; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)(pRight), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[i] - ((int64_t)(((double)pLeft[i]) / pRight[0])) * pRight[0]; - } - } -} - -void calc_i32_i8_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int8_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i16_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int16_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_i64_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, int64_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i32_f_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int32_t, float) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_INT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i32_d_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - int32_t *pLeft = (int32_t *)left; - double * pRight = (double *)right; - double * pOutput = (double *)output; - - int32_t i = (order == TSDB_ORDER_ASC) ? 0 : MAX(numLeft, numRight) - 1; - int32_t step = (order == TSDB_ORDER_ASC) ? 1 : -1; - - if (numLeft == numRight) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)(pOutput), TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[i] - ((int64_t)(((double)pLeft[i]) / pRight[i])) * pRight[i]; - } - } else if (numLeft == 1) { - for (; i >= 0 && i < numRight; i += step, pOutput += 1) { - if (isNull((char *)(pLeft), TSDB_DATA_TYPE_INT) || isNull((char *)&(pRight[i]), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[0] - ((int64_t)(((double)pLeft[0]) / pRight[i])) * pRight[i]; - } - } else if (numRight == 1) { - for (; i >= 0 && i < numLeft; i += step, pOutput += 1) { - if (isNull((char *)&(pLeft[i]), TSDB_DATA_TYPE_INT) || isNull((char *)(pRight), TSDB_DATA_TYPE_INT)) { - setNull((char *)pOutput, TSDB_DATA_TYPE_DOUBLE, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); - continue; - } - - *pOutput = (double)pLeft[i] - ((int64_t)(((double)pLeft[i]) / pRight[0])) * pRight[0]; - } - } -} - -void calc_i8_i8_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int8_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i16_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int16_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i32_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int32_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i8_i64_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, int64_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i8_f_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, float) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i8_d_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int8_t, double) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_TINYINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i16_i8_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int8_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i16_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int16_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i32_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int32_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i16_i64_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, int64_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i16_f_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, float) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i16_d_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int16_t, double) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_SMALLINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_i64_i8_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int8_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i16_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int16_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i32_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int32_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_i64_i64_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, int64_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_i64_f_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, float) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_i64_d_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, int64_t, double) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_BIGINT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_f_i8_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int8_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_f_i16_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int16_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_f_i32_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int32_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_f_i64_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, int64_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_f_f_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, float) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_f_d_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, float, double) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_FLOAT, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -void calc_d_i8_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int8_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_TINYINT, numLeft, numRight, pOutput, order); -} - -void calc_d_i16_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int16_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_SMALLINT, numLeft, numRight, pOutput, order); -} - -void calc_d_i32_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int32_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_INT, numLeft, numRight, pOutput, order); -} - -void calc_d_i64_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, int64_t) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_BIGINT, numLeft, numRight, pOutput, order); -} - -void calc_d_f_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, float) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_FLOAT, numLeft, numRight, pOutput, order); -} - -void calc_d_d_rem(void *left, void *right, int32_t numLeft, int32_t numRight, void *output, int32_t order) { - TYPE_CONVERT(left, right, output, double, double) - ARRAY_LIST_REM(pLeft, pRight, TSDB_DATA_TYPE_DOUBLE, TSDB_DATA_TYPE_DOUBLE, numLeft, numRight, pOutput, order); -} - -* - * the following are two-dimensional array list of callback function . - */ -//_arithmetic_operator_fn_t add_function_arraylist[15][15] = { -// /*NULL, bool, tinyint, smallint, int, bigint, float, double, timestamp, binary*/ -// {0}, // EMPTY, -// {0}, // TSDB_DATA_TYPE_BOOL, -// {NULL, NULL, calc_i8_i8_add, calc_i8_i16_add, calc_i8_i32_add, calc_i8_i64_add, calc_i8_f_add, calc_i8_d_add, NULL, NULL}, // TSDB_DATA_TYPE_TINYINT -// {NULL, NULL, calc_i16_i8_add, calc_i16_i16_add, calc_i16_i32_add, calc_i16_i64_add, calc_i16_f_add, calc_i16_d_add, NULL, NULL}, // TSDB_DATA_TYPE_SMALLINT -// {NULL, NULL, calc_i32_i8_add, calc_i32_i16_add, calc_i32_i32_add, calc_i32_i64_add, calc_i32_f_add, calc_i32_d_add, NULL, NULL}, // TSDB_DATA_TYPE_INT -// {NULL, NULL, calc_i64_i8_add, calc_i64_i16_add, calc_i64_i32_add, calc_i64_i64_add, calc_i64_f_add, calc_i64_d_add, NULL, NULL}, // TSDB_DATA_TYPE_BIGINT -// {NULL, NULL, calc_f_i8_add, calc_f_i16_add, calc_f_i32_add, calc_f_i64_add, calc_f_f_add, calc_f_d_add, NULL, NULL}, // TSDB_DATA_TYPE_FLOAT -// {NULL, NULL, calc_d_i8_add, calc_d_i16_add, calc_d_i32_add, calc_d_i64_add, calc_d_f_add, calc_d_d_add, NULL, NULL}, // TSDB_DATA_TYPE_DOUBLE -// {0}, // TSDB_DATA_TYPE_BINARY, -// {0}, // TSDB_DATA_TYPE_NCHAR, -// {NULL, NULL, calc_u8_i8_add, calc_u8_i16_add, calc_u8_i32_add, calc_u8_i64_add, calc_u8_f_add, calc_u8_d_add, NULL, NULL, calc_u8_u8_add, calc_u8_u16_add, calc_u8_u32_add, calc_u8_u64_add, NULL}, // TSDB_DATA_TYPE_UTINYINT, -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // TSDB_DATA_TYPE_USMALLINT, -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // TSDB_DATA_TYPE_UINT, -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // TSDB_DATA_TYPE_UBIGINT, -// -//}; -// -//_arithmetic_operator_fn_t sub_function_arraylist[8][15] = { -// /*NULL, bool, tinyint, smallint, int, bigint, float, double, timestamp, binary*/ -// {0}, // EMPTY, -// {0}, // TSDB_DATA_TYPE_BOOL, -// {NULL, NULL, calc_i8_i8_sub, calc_i8_i16_sub, calc_i8_i32_sub, calc_i8_i64_sub, calc_i8_f_sub, calc_i8_d_sub, NULL, NULL}, // TSDB_DATA_TYPE_TINYINT -// {NULL, NULL, calc_i16_i8_sub, calc_i16_i16_sub, calc_i16_i32_sub, calc_i16_i64_sub, calc_i16_f_sub, calc_i16_d_sub, NULL, NULL}, // TSDB_DATA_TYPE_SMALLINT -// {NULL, NULL, calc_i32_i8_sub, calc_i32_i16_sub, calc_i32_i32_sub, calc_i32_i64_sub, calc_i32_f_sub, calc_i32_d_sub, NULL, NULL}, // TSDB_DATA_TYPE_INT -// {NULL, NULL, calc_i64_i8_sub, calc_i64_i16_sub, calc_i64_i32_sub, calc_i64_i64_sub, calc_i64_f_sub, calc_i64_d_sub, NULL, NULL}, // TSDB_DATA_TYPE_BIGINT -// {NULL, NULL, calc_f_i8_sub, calc_f_i16_sub, calc_f_i32_sub, calc_f_i64_sub, calc_f_f_sub, calc_f_d_sub, NULL, NULL}, // TSDB_DATA_TYPE_FLOAT -// {NULL, NULL, calc_d_i8_sub, calc_d_i16_sub, calc_d_i32_sub, calc_d_i64_sub, calc_d_f_sub, calc_d_d_sub, NULL, NULL}, // TSDB_DATA_TYPE_DOUBLE -//}; -// -//_arithmetic_operator_fn_t multi_function_arraylist[][15] = { -// /*NULL, bool, tinyint, smallint, int, bigint, float, double, timestamp, binary*/ -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // EMPTY, -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // TSDB_DATA_TYPE_BOOL, -// {NULL, NULL, calc_i8_i8_multi, calc_i8_i16_multi, calc_i8_i32_multi, calc_i8_i64_multi, calc_i8_f_multi, calc_i8_d_multi, NULL, NULL}, // TSDB_DATA_TYPE_TINYINT -// {NULL, NULL, calc_i16_i8_multi, calc_i16_i16_multi, calc_i16_i32_multi, calc_i16_i64_multi, calc_i16_f_multi, calc_i16_d_multi, NULL, NULL}, // TSDB_DATA_TYPE_SMALLINT -// {NULL, NULL, calc_i32_i8_multi, calc_i32_i16_multi, calc_i32_i32_multi, calc_i32_i64_multi, calc_i32_f_multi, calc_i32_d_multi, NULL, NULL}, // TSDB_DATA_TYPE_INT -// {NULL, NULL, calc_i64_i8_multi, calc_i64_i16_multi, calc_i64_i32_multi, calc_i64_i64_multi, calc_i64_f_multi, calc_i64_d_multi, NULL, NULL}, // TSDB_DATA_TYPE_BIGINT -// {NULL, NULL, calc_f_i8_multi, calc_f_i16_multi, calc_f_i32_multi, calc_f_i64_multi, calc_f_f_multi, calc_f_d_multi, NULL, NULL}, // TSDB_DATA_TYPE_FLOAT -// {NULL, NULL, calc_d_i8_multi, calc_d_i16_multi, calc_d_i32_multi, calc_d_i64_multi, calc_d_f_multi, calc_d_d_multi, NULL, NULL}, // TSDB_DATA_TYPE_DOUBLE -//}; -// -//_arithmetic_operator_fn_t div_function_arraylist[8][15] = { -// /*NULL, bool, tinyint, smallint, int, bigint, float, double, timestamp, binary*/ -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // EMPTY, -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // TSDB_DATA_TYPE_BOOL, -// {NULL, NULL, calc_i8_i8_div, calc_i8_i16_div, calc_i8_i32_div, calc_i8_i64_div, calc_i8_f_div, calc_i8_d_div, NULL, NULL}, // TSDB_DATA_TYPE_TINYINT -// {NULL, NULL, calc_i16_i8_div, calc_i16_i16_div, calc_i16_i32_div, calc_i16_i64_div, calc_i16_f_div, calc_i16_d_div, NULL, NULL}, // TSDB_DATA_TYPE_SMALLINT -// {NULL, NULL, calc_i32_i8_div, calc_i32_i16_div, calc_i32_i32_div, calc_i32_i64_div, calc_i32_f_div, calc_i32_d_div, NULL, NULL}, // TSDB_DATA_TYPE_INT -// {NULL, NULL, calc_i64_i8_div, calc_i64_i16_div, calc_i64_i32_div, calc_i64_i64_div, calc_i64_f_div, calc_i64_d_div, NULL, NULL}, // TSDB_DATA_TYPE_BIGINT -// {NULL, NULL, calc_f_i8_div, calc_f_i16_div, calc_f_i32_div, calc_f_i64_div, calc_f_f_div, calc_f_d_div, NULL, NULL}, // TSDB_DATA_TYPE_FLOAT -// {NULL, NULL, calc_d_i8_div, calc_d_i16_div, calc_d_i32_div, calc_d_i64_div, calc_d_f_div, calc_d_d_div, NULL, NULL}, // TSDB_DATA_TYPE_DOUBLE -//}; -// -//_arithmetic_operator_fn_t rem_function_arraylist[8][15] = { -// /*NULL, bool, tinyint, smallint, int, bigint, float, double, timestamp, binary, nchar, unsigned tinyint, unsigned smallint, unsigned int, unsigned bigint*/ -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // EMPTY, -// {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}, // TSDB_DATA_TYPE_BOOL, -// {NULL, NULL, calc_i8_i8_rem, calc_i8_i16_rem, calc_i8_i32_rem, calc_i8_i64_rem, calc_i8_f_rem, calc_i8_d_rem, NULL, NULL}, // TSDB_DATA_TYPE_TINYINT -// {NULL, NULL, calc_i16_i8_rem, calc_i16_i16_rem, calc_i16_i32_rem, calc_i16_i64_rem, calc_i16_f_rem, calc_i16_d_rem, NULL, NULL}, // TSDB_DATA_TYPE_SMALLINT -// {NULL, NULL, calc_i32_i8_rem, calc_i32_i16_rem, calc_i32_i32_rem, calc_i32_i64_rem, calc_i32_f_rem, calc_i32_d_rem, NULL, NULL}, // TSDB_DATA_TYPE_INT -// {NULL, NULL, calc_i64_i8_rem, calc_i64_i16_rem, calc_i64_i32_rem, calc_i64_i64_rem, calc_i64_f_rem, calc_i64_d_rem, NULL, NULL}, // TSDB_DATA_TYPE_BIGINT -// {NULL, NULL, calc_f_i8_rem, calc_f_i16_rem, calc_f_i32_rem, calc_f_i64_rem, calc_f_f_rem, calc_f_d_rem, NULL, NULL}, // TSDB_DATA_TYPE_FLOAT -// {NULL, NULL, calc_d_i8_rem, calc_d_i16_rem, calc_d_i32_rem, calc_d_i64_rem, calc_d_f_rem, calc_d_d_rem, NULL, NULL}, // TSDB_DATA_TYPE_DOUBLE -//}; - -//////////////////////////////////////////////////////////////////////////////////////////////////////////// - _arithmetic_operator_fn_t getArithmeticOperatorFn(int32_t arithmeticOptr) { switch (arithmeticOptr) { case TSDB_BINARY_OP_ADD: diff --git a/src/query/src/qExecutor.c b/src/query/src/qExecutor.c index 261ba86bda..110b0d198c 100644 --- a/src/query/src/qExecutor.c +++ b/src/query/src/qExecutor.c @@ -3168,6 +3168,10 @@ void copyResToQueryResultBuf(SQInfo *pQInfo, SQuery *pQuery) { // all results in current group have been returned to client, try next group if (pGroupResInfo->index >= taosArrayGetSize(pGroupResInfo->pRows)) { // current results of group has been sent to client, try next group + pGroupResInfo->index = 0; + pGroupResInfo->rowId = 0; + taosArrayClear(pGroupResInfo->pRows); + if (mergeGroupResult(pQInfo) != TSDB_CODE_SUCCESS) { return; // failed to save data in the disk } @@ -4176,7 +4180,7 @@ static void stableApplyFunctionsOnBlock(SQueryRuntimeEnv *pRuntimeEnv, SDataBloc } } -bool queryHasRemainResForTableQuery(SQueryRuntimeEnv* pRuntimeEnv) { +bool hasNotReturnedResults(SQueryRuntimeEnv* pRuntimeEnv) { SQuery *pQuery = pRuntimeEnv->pQuery; SFillInfo *pFillInfo = pRuntimeEnv->pFillInfo; @@ -4186,8 +4190,7 @@ bool queryHasRemainResForTableQuery(SQueryRuntimeEnv* pRuntimeEnv) { if (pQuery->fillType != TSDB_FILL_NONE && !isPointInterpoQuery(pQuery)) { // There are results not returned to client yet, so filling applied to the remain result is required firstly. - int32_t remain = taosNumOfRemainRows(pFillInfo); - if (remain > 0) { + if (taosFillHasMoreResults(pFillInfo)) { return true; } @@ -4201,7 +4204,7 @@ bool queryHasRemainResForTableQuery(SQueryRuntimeEnv* pRuntimeEnv) { * first result row in the actual result set will fill nothing. */ if (Q_STATUS_EQUAL(pQuery->status, QUERY_COMPLETED)) { - int32_t numOfTotal = (int32_t)getNumOfResWithFill(pFillInfo, pQuery->window.ekey, (int32_t)pQuery->rec.capacity); + int32_t numOfTotal = (int32_t)getNumOfResultsAfterFillGap(pFillInfo, pQuery->window.ekey, (int32_t)pQuery->rec.capacity); return numOfTotal > 0; } @@ -4269,7 +4272,7 @@ static void doCopyQueryResultToMsg(SQInfo *pQInfo, int32_t numOfRows, char *data setQueryStatus(pQuery, QUERY_OVER); } } else { - if (!queryHasRemainResForTableQuery(&pQInfo->runtimeEnv)) { + if (!hasNotReturnedResults(&pQInfo->runtimeEnv)) { setQueryStatus(pQuery, QUERY_OVER); } } @@ -4296,7 +4299,6 @@ int32_t doFillGapsInResults(SQueryRuntimeEnv* pRuntimeEnv, tFilePage **pDst, int pQInfo, pFillInfo->numOfRows, ret, pQuery->limit.offset, ret - pQuery->limit.offset, 0); ret -= (int32_t)pQuery->limit.offset; - // todo !!!!there exactly number of interpo is not valid. for (int32_t i = 0; i < pQuery->numOfOutput; ++i) { memmove(pDst[i]->data, pDst[i]->data + pQuery->pExpr1[i].bytes * pQuery->limit.offset, ret * pQuery->pExpr1[i].bytes); @@ -4314,7 +4316,7 @@ int32_t doFillGapsInResults(SQueryRuntimeEnv* pRuntimeEnv, tFilePage **pDst, int ret = 0; } - if (!queryHasRemainResForTableQuery(pRuntimeEnv)) { + if (!hasNotReturnedResults(pRuntimeEnv)) { return ret; } } @@ -5774,7 +5776,7 @@ static void tableQueryImpl(SQInfo *pQInfo) { SQueryRuntimeEnv *pRuntimeEnv = &pQInfo->runtimeEnv; SQuery * pQuery = pRuntimeEnv->pQuery; - if (queryHasRemainResForTableQuery(pRuntimeEnv)) { + if (hasNotReturnedResults(pRuntimeEnv)) { if (pQuery->fillType != TSDB_FILL_NONE) { /* * There are remain results that are not returned due to result interpolation @@ -6314,7 +6316,7 @@ static int32_t createQueryFuncExprFromMsg(SQueryTableMsg *pQueryMsg, int32_t num } type = TSDB_DATA_TYPE_DOUBLE; - bytes = tDataTypeDesc[type].nSize; + bytes = tDataTypes[type].bytes; } else if (pExprs[i].base.colInfo.colId == TSDB_TBNAME_COLUMN_INDEX && pExprs[i].base.functionId == TSDB_FUNC_TAGPRJ) { // parse the normal column SSchema s = tGetTableNameColumnSchema(); type = s.type; @@ -6928,11 +6930,12 @@ static size_t getResultSize(SQInfo *pQInfo, int64_t *numOfRows) { */ if (isTSCompQuery(pQuery) && (*numOfRows) > 0) { struct stat fStat; - if (fstat(fileno(*(FILE **)pQuery->sdata[0]->data), &fStat) == 0) { + FILE *f = *(FILE **)pQuery->sdata[0]->data; + if ((f != NULL) && (fstat(fileno(f), &fStat) == 0)) { *numOfRows = fStat.st_size; return fStat.st_size; } else { - qError("QInfo:%p failed to get file info, path:%s, reason:%s", pQInfo, pQuery->sdata[0]->data, strerror(errno)); + qError("QInfo:%p failed to get file info, file:%p, reason:%s", pQInfo, f, strerror(errno)); return 0; } } else { @@ -6947,7 +6950,7 @@ static int32_t doDumpQueryResult(SQInfo *pQInfo, char *data) { // load data from file to msg buffer if (isTSCompQuery(pQuery)) { - FILE *f = *(FILE **)pQuery->sdata[0]->data; + FILE *f = *(FILE **)pQuery->sdata[0]->data; // TODO refactor // make sure file exist if (f) { diff --git a/src/query/src/qFill.c b/src/query/src/qFill.c index ca1203cb17..65b58467b7 100644 --- a/src/query/src/qFill.c +++ b/src/query/src/qFill.c @@ -25,6 +25,251 @@ #include "queryLog.h" #define FILL_IS_ASC_FILL(_f) ((_f)->order == TSDB_ORDER_ASC) +#define DO_INTERPOLATION(_v1, _v2, _k1, _k2, _k) ((_v1) + ((_v2) - (_v1)) * (((double)(_k)) - ((double)(_k1))) / (((double)(_k2)) - ((double)(_k1)))) + +static void setTagsValue(SFillInfo* pFillInfo, tFilePage** data, int32_t genRows) { + for(int32_t j = 0; j < pFillInfo->numOfCols; ++j) { + SFillColInfo* pCol = &pFillInfo->pFillCol[j]; + if (TSDB_COL_IS_NORMAL_COL(pCol->flag)) { + continue; + } + + char* val1 = elePtrAt(data[j]->data, pCol->col.bytes, genRows); + + assert(pCol->tagIndex >= 0 && pCol->tagIndex < pFillInfo->numOfTags); + SFillTagColInfo* pTag = &pFillInfo->pTags[pCol->tagIndex]; + + assert (pTag->col.colId == pCol->col.colId); + assignVal(val1, pTag->tagVal, pCol->col.bytes, pCol->col.type); + } +} + +static void setNullValueForRow(SFillInfo* pFillInfo, tFilePage** data, int32_t numOfCol, int32_t rowIndex) { + // the first are always the timestamp column, so start from the second column. + for (int32_t i = 1; i < numOfCol; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + + char* output = elePtrAt(data[i]->data, pCol->col.bytes, rowIndex); + setNull(output, pCol->col.type, pCol->col.bytes); + } +} + +static void doFillOneRowResult(SFillInfo* pFillInfo, tFilePage** data, char** srcData, int64_t ts, bool outOfBound) { + char* prev = pFillInfo->prevValues; + char* next = pFillInfo->nextValues; + + SPoint point1, point2, point; + int32_t step = GET_FORWARD_DIRECTION_FACTOR(pFillInfo->order); + + // set the primary timestamp column value + int32_t index = pFillInfo->numOfCurrent; + char* val = elePtrAt(data[0]->data, TSDB_KEYSIZE, index); + *(TSKEY*) val = pFillInfo->currentKey; + + // set the other values + if (pFillInfo->type == TSDB_FILL_PREV) { + char* p = FILL_IS_ASC_FILL(pFillInfo) ? prev : next; + + if (p != NULL) { + for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + if (TSDB_COL_IS_TAG(pCol->flag)) { + continue; + } + + char* output = elePtrAt(data[i]->data, pCol->col.bytes, index); + assignVal(output, p + pCol->col.offset, pCol->col.bytes, pCol->col.type); + } + } else { // no prev value yet, set the value for NULL + setNullValueForRow(pFillInfo, data, pFillInfo->numOfCols, index); + } + } else if (pFillInfo->type == TSDB_FILL_NEXT) { + char* p = FILL_IS_ASC_FILL(pFillInfo)? next : prev; + + if (p != NULL) { + for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + if (TSDB_COL_IS_TAG(pCol->flag)) { + continue; + } + + char* output = elePtrAt(data[i]->data, pCol->col.bytes, index); + assignVal(output, p + pCol->col.offset, pCol->col.bytes, pCol->col.type); + } + } else { // no prev value yet, set the value for NULL + setNullValueForRow(pFillInfo, data, pFillInfo->numOfCols, index); + } + } else if (pFillInfo->type == TSDB_FILL_LINEAR) { + // TODO : linear interpolation supports NULL value + if (prev != NULL && !outOfBound) { + for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + if (TSDB_COL_IS_TAG(pCol->flag)) { + continue; + } + + int16_t type = pCol->col.type; + int16_t bytes = pCol->col.bytes; + + char *val1 = elePtrAt(data[i]->data, pCol->col.bytes, index); + if (type == TSDB_DATA_TYPE_BINARY|| type == TSDB_DATA_TYPE_NCHAR || type == TSDB_DATA_TYPE_BOOL) { + setNull(val1, pCol->col.type, bytes); + continue; + } + + point1 = (SPoint){.key = *(TSKEY*)(prev), .val = prev + pCol->col.offset}; + point2 = (SPoint){.key = ts, .val = srcData[i] + pFillInfo->index * bytes}; + point = (SPoint){.key = pFillInfo->currentKey, .val = val1}; + taosGetLinearInterpolationVal(type, &point1, &point2, &point); + } + } else { + setNullValueForRow(pFillInfo, data, pFillInfo->numOfCols, index); + } + } else { /* fill the default value */ + for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + if (TSDB_COL_IS_TAG(pCol->flag)) { + continue; + } + + char* val1 = elePtrAt(data[i]->data, pCol->col.bytes, index); + assignVal(val1, (char*)&pCol->fillVal.i, pCol->col.bytes, pCol->col.type); + } + } + + setTagsValue(pFillInfo, data, index); + pFillInfo->currentKey = taosTimeAdd(pFillInfo->currentKey, pFillInfo->interval.sliding * step, pFillInfo->interval.slidingUnit, pFillInfo->precision); + pFillInfo->numOfCurrent++; +} + +static void initBeforeAfterDataBuf(SFillInfo* pFillInfo, char** next) { + if (*next != NULL) { + return; + } + + *next = calloc(1, pFillInfo->rowSize); + for (int i = 1; i < pFillInfo->numOfCols; i++) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + setNull(*next + pCol->col.offset, pCol->col.type, pCol->col.bytes); + } +} + +static void copyCurrentRowIntoBuf(SFillInfo* pFillInfo, char** srcData, char* buf) { + int32_t rowIndex = pFillInfo->index; + for (int32_t i = 0; i < pFillInfo->numOfCols; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + memcpy(buf + pCol->col.offset, srcData[i] + rowIndex * pCol->col.bytes, pCol->col.bytes); + } +} + +static int32_t fillResultImpl(SFillInfo* pFillInfo, tFilePage** data, int32_t outputRows) { + pFillInfo->numOfCurrent = 0; + + char** srcData = pFillInfo->pData; + char** prev = &pFillInfo->prevValues; + char** next = &pFillInfo->nextValues; + + int32_t step = GET_FORWARD_DIRECTION_FACTOR(pFillInfo->order); + + if (FILL_IS_ASC_FILL(pFillInfo)) { + assert(pFillInfo->currentKey >= pFillInfo->start); + } else { + assert(pFillInfo->currentKey <= pFillInfo->start); + } + + while (pFillInfo->numOfCurrent < outputRows) { + int64_t ts = ((int64_t*)pFillInfo->pData[0])[pFillInfo->index]; + + // set the next value for interpolation + if ((pFillInfo->currentKey < ts && FILL_IS_ASC_FILL(pFillInfo)) || + (pFillInfo->currentKey > ts && !FILL_IS_ASC_FILL(pFillInfo))) { + initBeforeAfterDataBuf(pFillInfo, next); + copyCurrentRowIntoBuf(pFillInfo, srcData, *next); + } + + if (((pFillInfo->currentKey < ts && FILL_IS_ASC_FILL(pFillInfo)) || (pFillInfo->currentKey > ts && !FILL_IS_ASC_FILL(pFillInfo))) && + pFillInfo->numOfCurrent < outputRows) { + + // fill the gap between two actual input rows + while (((pFillInfo->currentKey < ts && FILL_IS_ASC_FILL(pFillInfo)) || + (pFillInfo->currentKey > ts && !FILL_IS_ASC_FILL(pFillInfo))) && + pFillInfo->numOfCurrent < outputRows) { + doFillOneRowResult(pFillInfo, data, srcData, ts, false); + } + + // output buffer is full, abort + if (pFillInfo->numOfCurrent == outputRows) { + pFillInfo->numOfTotal += pFillInfo->numOfCurrent; + return outputRows; + } + } else { + assert(pFillInfo->currentKey == ts); + initBeforeAfterDataBuf(pFillInfo, prev); + + // assign rows to dst buffer + for (int32_t i = 0; i < pFillInfo->numOfCols; ++i) { + SFillColInfo* pCol = &pFillInfo->pFillCol[i]; + if (TSDB_COL_IS_TAG(pCol->flag)) { + continue; + } + + char* output = elePtrAt(data[i]->data, pCol->col.bytes, pFillInfo->numOfCurrent); + char* src = elePtrAt(srcData[i], pCol->col.bytes, pFillInfo->index); + + if (i == 0 || (pCol->functionId != TSDB_FUNC_COUNT && !isNull(src, pCol->col.type)) || + (pCol->functionId == TSDB_FUNC_COUNT && GET_INT64_VAL(src) != 0)) { + assignVal(output, src, pCol->col.bytes, pCol->col.type); + memcpy(*prev + pCol->col.offset, src, pCol->col.bytes); + } else { // i > 0 and data is null , do interpolation + if (pFillInfo->type == TSDB_FILL_PREV) { + assignVal(output, *prev + pCol->col.offset, pCol->col.bytes, pCol->col.type); + } else if (pFillInfo->type == TSDB_FILL_LINEAR) { + assignVal(output, src, pCol->col.bytes, pCol->col.type); + memcpy(*prev + pCol->col.offset, src, pCol->col.bytes); + } else { + assignVal(output, (char*)&pCol->fillVal.i, pCol->col.bytes, pCol->col.type); + } + } + } + + // set the tag value for final result + setTagsValue(pFillInfo, data, pFillInfo->numOfCurrent); + + pFillInfo->currentKey = taosTimeAdd(pFillInfo->currentKey, pFillInfo->interval.sliding * step, + pFillInfo->interval.slidingUnit, pFillInfo->precision); + pFillInfo->index += 1; + pFillInfo->numOfCurrent += 1; + } + + if (pFillInfo->index >= pFillInfo->numOfRows || pFillInfo->numOfCurrent >= outputRows) { + /* the raw data block is exhausted, next value does not exists */ + if (pFillInfo->index >= pFillInfo->numOfRows) { + tfree(*next); + } + + pFillInfo->numOfTotal += pFillInfo->numOfCurrent; + return pFillInfo->numOfCurrent; + } + } + + return pFillInfo->numOfCurrent; +} + +static int64_t appendFilledResult(SFillInfo* pFillInfo, tFilePage** output, int64_t resultCapacity) { + /* + * These data are generated according to fill strategy, since the current timestamp is out of the time window of + * real result set. Note that we need to keep the direct previous result rows, to generated the filled data. + */ + pFillInfo->numOfCurrent = 0; + while (pFillInfo->numOfCurrent < resultCapacity) { + doFillOneRowResult(pFillInfo, output, pFillInfo->pData, pFillInfo->start, true); + } + + pFillInfo->numOfTotal += pFillInfo->numOfCurrent; + + assert(pFillInfo->numOfCurrent == resultCapacity); + return resultCapacity; +} // there are no duplicated tags in the SFillTagColInfo list static int32_t setTagColumnInfo(SFillInfo* pFillInfo, int32_t numOfCols, int32_t capacity) { @@ -68,6 +313,14 @@ static int32_t setTagColumnInfo(SFillInfo* pFillInfo, int32_t numOfCols, int32_t return rowsize; } +static int32_t taosNumOfRemainRows(SFillInfo* pFillInfo) { + if (pFillInfo->numOfRows == 0 || (pFillInfo->numOfRows > 0 && pFillInfo->index >= pFillInfo->numOfRows)) { + return 0; + } + + return pFillInfo->numOfRows - pFillInfo->index; +} + SFillInfo* taosInitFillInfo(int32_t order, TSKEY skey, int32_t numOfTags, int32_t capacity, int32_t numOfCols, int64_t slidingTime, int8_t slidingUnit, int8_t precision, int32_t fillType, SFillColInfo* pCol, void* handle) { @@ -76,22 +329,21 @@ SFillInfo* taosInitFillInfo(int32_t order, TSKEY skey, int32_t numOfTags, int32_ } SFillInfo* pFillInfo = calloc(1, sizeof(SFillInfo)); - taosResetFillInfo(pFillInfo, skey); - pFillInfo->order = order; - pFillInfo->type = fillType; - pFillInfo->pFillCol = pCol; + pFillInfo->order = order; + pFillInfo->type = fillType; + pFillInfo->pFillCol = pCol; pFillInfo->numOfTags = numOfTags; pFillInfo->numOfCols = numOfCols; pFillInfo->precision = precision; pFillInfo->alloc = capacity; pFillInfo->handle = handle; - pFillInfo->interval.interval = slidingTime; + pFillInfo->interval.interval = slidingTime; pFillInfo->interval.intervalUnit = slidingUnit; - pFillInfo->interval.sliding = slidingTime; - pFillInfo->interval.slidingUnit = slidingUnit; + pFillInfo->interval.sliding = slidingTime; + pFillInfo->interval.slidingUnit = slidingUnit; pFillInfo->pData = malloc(POINTER_BYTES * numOfCols); if (numOfTags > 0) { @@ -185,7 +437,11 @@ void taosFillCopyInputDataFromOneFilePage(SFillInfo* pFillInfo, const tFilePage* } } -int64_t getNumOfResWithFill(SFillInfo* pFillInfo, TSKEY ekey, int32_t maxNumOfRows) { +bool taosFillHasMoreResults(SFillInfo* pFillInfo) { + return taosNumOfRemainRows(pFillInfo) > 0; +} + +int64_t getNumOfResultsAfterFillGap(SFillInfo* pFillInfo, TSKEY ekey, int32_t maxNumOfRows) { int64_t* tsList = (int64_t*) pFillInfo->pData[0]; int32_t numOfRows = taosNumOfRemainRows(pFillInfo); @@ -223,16 +479,6 @@ int64_t getNumOfResWithFill(SFillInfo* pFillInfo, TSKEY ekey, int32_t maxNumOfRo return (numOfRes > maxNumOfRows) ? maxNumOfRows : numOfRes; } -int32_t taosNumOfRemainRows(SFillInfo* pFillInfo) { - if (pFillInfo->numOfRows == 0 || (pFillInfo->numOfRows > 0 && pFillInfo->index >= pFillInfo->numOfRows)) { - return 0; - } - - return pFillInfo->numOfRows - pFillInfo->index; -} - -#define DO_INTERPOLATION(_v1, _v2, _k1, _k2, _k) ((_v1) + ((_v2) - (_v1)) * (((double)(_k)) - ((double)(_k1))) / (((double)(_k2)) - ((double)(_k1)))) - int32_t taosGetLinearInterpolationVal(int32_t type, SPoint* point1, SPoint* point2, SPoint* point) { double v1 = -1; double v2 = -1; @@ -256,243 +502,15 @@ int32_t taosGetLinearInterpolationVal(int32_t type, SPoint* point1, SPoint* poin return TSDB_CODE_SUCCESS; } -static void setTagsValue(SFillInfo* pFillInfo, tFilePage** data, int32_t genRows) { - for(int32_t j = 0; j < pFillInfo->numOfCols; ++j) { - SFillColInfo* pCol = &pFillInfo->pFillCol[j]; - if (TSDB_COL_IS_NORMAL_COL(pCol->flag)) { - continue; - } - - char* val1 = elePtrAt(data[j]->data, pCol->col.bytes, genRows); - - assert(pCol->tagIndex >= 0 && pCol->tagIndex < pFillInfo->numOfTags); - SFillTagColInfo* pTag = &pFillInfo->pTags[pCol->tagIndex]; - - assert (pTag->col.colId == pCol->col.colId); - assignVal(val1, pTag->tagVal, pCol->col.bytes, pCol->col.type); - } -} - -static void setNullValueForRow(SFillInfo* pFillInfo, tFilePage** data, int32_t numOfCol, int32_t rowIndex) { - // the first are always the timestamp column, so start from the second column. - for (int32_t i = 1; i < numOfCol; ++i) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - - char* output = elePtrAt(data[i]->data, pCol->col.bytes, rowIndex); - setNull(output, pCol->col.type, pCol->col.bytes); - } -} - -static void doFillOneRowResult(SFillInfo* pFillInfo, tFilePage** data, char** srcData, int64_t ts, bool outOfBound) { - char* prev = pFillInfo->prevValues; - char* next = pFillInfo->nextValues; - - SPoint point1, point2, point; - int32_t step = GET_FORWARD_DIRECTION_FACTOR(pFillInfo->order); - - // set the primary timestamp column value - int32_t index = pFillInfo->numOfCurrent; - char* val = elePtrAt(data[0]->data, TSDB_KEYSIZE, index); - *(TSKEY*) val = pFillInfo->currentKey; - - // set the other values - if (pFillInfo->type == TSDB_FILL_PREV) { - char* p = FILL_IS_ASC_FILL(pFillInfo) ? prev : next; - - if (p != NULL) { - for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - if (TSDB_COL_IS_TAG(pCol->flag)) { - continue; - } - - char* output = elePtrAt(data[i]->data, pCol->col.bytes, index); - assignVal(output, p + pCol->col.offset, pCol->col.bytes, pCol->col.type); - } - } else { // no prev value yet, set the value for NULL - setNullValueForRow(pFillInfo, data, pFillInfo->numOfCols, index); - } - } else if (pFillInfo->type == TSDB_FILL_LINEAR) { - // TODO : linear interpolation supports NULL value - if (prev != NULL && !outOfBound) { - for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - if (TSDB_COL_IS_TAG(pCol->flag)) { - continue; - } - - int16_t type = pCol->col.type; - int16_t bytes = pCol->col.bytes; - - char *val1 = elePtrAt(data[i]->data, pCol->col.bytes, index); - if (type == TSDB_DATA_TYPE_BINARY|| type == TSDB_DATA_TYPE_NCHAR || type == TSDB_DATA_TYPE_BOOL) { - setNull(val1, pCol->col.type, bytes); - continue; - } - - point1 = (SPoint){.key = *(TSKEY*)(prev), .val = prev + pCol->col.offset}; - point2 = (SPoint){.key = ts, .val = srcData[i] + pFillInfo->index * bytes}; - point = (SPoint){.key = pFillInfo->currentKey, .val = val1}; - taosGetLinearInterpolationVal(type, &point1, &point2, &point); - } - } else { - setNullValueForRow(pFillInfo, data, pFillInfo->numOfCols, index); - } - } else { /* fill the default value */ - for (int32_t i = 1; i < pFillInfo->numOfCols; ++i) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - if (TSDB_COL_IS_TAG(pCol->flag)) { - continue; - } - - char* val1 = elePtrAt(data[i]->data, pCol->col.bytes, index); - assignVal(val1, (char*)&pCol->fillVal.i, pCol->col.bytes, pCol->col.type); - } - } - - setTagsValue(pFillInfo, data, index); - pFillInfo->currentKey = taosTimeAdd(pFillInfo->currentKey, pFillInfo->interval.sliding * step, pFillInfo->interval.slidingUnit, pFillInfo->precision); - pFillInfo->numOfCurrent++; -} - -static void initBeforeAfterDataBuf(SFillInfo* pFillInfo, char** next) { - if (*next != NULL) { - return; - } - - *next = calloc(1, pFillInfo->rowSize); - for (int i = 1; i < pFillInfo->numOfCols; i++) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - setNull(*next + pCol->col.offset, pCol->col.type, pCol->col.bytes); - } -} - -static void copyCurrentRowIntoBuf(SFillInfo* pFillInfo, char** srcData, char* buf) { - int32_t rowIndex = pFillInfo->index; - for (int32_t i = 0; i < pFillInfo->numOfCols; ++i) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - memcpy(buf + pCol->col.offset, srcData[i] + rowIndex * pCol->col.bytes, pCol->col.bytes); - } -} - -static int32_t fillResultImpl(SFillInfo* pFillInfo, tFilePage** data, int32_t outputRows) { - pFillInfo->numOfCurrent = 0; - - char** srcData = pFillInfo->pData; - char** prev = &pFillInfo->prevValues; - char** next = &pFillInfo->nextValues; - - int32_t step = GET_FORWARD_DIRECTION_FACTOR(pFillInfo->order); - - if (FILL_IS_ASC_FILL(pFillInfo)) { - assert(pFillInfo->currentKey >= pFillInfo->start); - } else { - assert(pFillInfo->currentKey <= pFillInfo->start); - } - - while (pFillInfo->numOfCurrent < outputRows) { - int64_t ts = ((int64_t*)pFillInfo->pData[0])[pFillInfo->index]; - - if ((pFillInfo->currentKey < ts && FILL_IS_ASC_FILL(pFillInfo)) || - (pFillInfo->currentKey > ts && !FILL_IS_ASC_FILL(pFillInfo))) { - /* set the next value for interpolation */ - initBeforeAfterDataBuf(pFillInfo, next); - copyCurrentRowIntoBuf(pFillInfo, srcData, *next); - } - - if (((pFillInfo->currentKey < ts && FILL_IS_ASC_FILL(pFillInfo)) || (pFillInfo->currentKey > ts && !FILL_IS_ASC_FILL(pFillInfo))) && - pFillInfo->numOfCurrent < outputRows) { - - // fill the gap between two actual input rows - while (((pFillInfo->currentKey < ts && FILL_IS_ASC_FILL(pFillInfo)) || - (pFillInfo->currentKey > ts && !FILL_IS_ASC_FILL(pFillInfo))) && - pFillInfo->numOfCurrent < outputRows) { - doFillOneRowResult(pFillInfo, data, srcData, ts, false); - } - - // output buffer is full, abort - if (pFillInfo->numOfCurrent == outputRows) { - pFillInfo->numOfTotal += pFillInfo->numOfCurrent; - return outputRows; - } - } else { - assert(pFillInfo->currentKey == ts); - initBeforeAfterDataBuf(pFillInfo, prev); - - // assign rows to dst buffer - for (int32_t i = 0; i < pFillInfo->numOfCols; ++i) { - SFillColInfo* pCol = &pFillInfo->pFillCol[i]; - if (TSDB_COL_IS_TAG(pCol->flag)) { - continue; - } - - char* output = elePtrAt(data[i]->data, pCol->col.bytes, pFillInfo->numOfCurrent); - char* src = elePtrAt(srcData[i], pCol->col.bytes, pFillInfo->index); - - if (i == 0 || (pCol->functionId != TSDB_FUNC_COUNT && !isNull(src, pCol->col.type)) || - (pCol->functionId == TSDB_FUNC_COUNT && GET_INT64_VAL(src) != 0)) { - assignVal(output, src, pCol->col.bytes, pCol->col.type); - memcpy(*prev + pCol->col.offset, src, pCol->col.bytes); - } else { // i > 0 and data is null , do interpolation - if (pFillInfo->type == TSDB_FILL_PREV) { - assignVal(output, *prev + pCol->col.offset, pCol->col.bytes, pCol->col.type); - } else if (pFillInfo->type == TSDB_FILL_LINEAR) { - assignVal(output, src, pCol->col.bytes, pCol->col.type); - memcpy(*prev + pCol->col.offset, src, pCol->col.bytes); - } else { - assignVal(output, (char*)&pCol->fillVal.i, pCol->col.bytes, pCol->col.type); - } - } - } - - // set the tag value for final result - setTagsValue(pFillInfo, data, pFillInfo->numOfCurrent); - - pFillInfo->currentKey = taosTimeAdd(pFillInfo->currentKey, pFillInfo->interval.sliding * step, - pFillInfo->interval.slidingUnit, pFillInfo->precision); - pFillInfo->index += 1; - pFillInfo->numOfCurrent += 1; - } - - if (pFillInfo->index >= pFillInfo->numOfRows || pFillInfo->numOfCurrent >= outputRows) { - /* the raw data block is exhausted, next value does not exists */ - if (pFillInfo->index >= pFillInfo->numOfRows) { - tfree(*next); - } - - pFillInfo->numOfTotal += pFillInfo->numOfCurrent; - return pFillInfo->numOfCurrent; - } - } - - return pFillInfo->numOfCurrent; -} - -static int64_t fillExternalResults(SFillInfo* pFillInfo, tFilePage** output, int64_t resultCapacity) { - /* - * These data are generated according to fill strategy, since the current timestamp is out of the time window of - * real result set. Note that we need to keep the direct previous result rows, to generated the filled data. - */ - pFillInfo->numOfCurrent = 0; - while (pFillInfo->numOfCurrent < resultCapacity) { - doFillOneRowResult(pFillInfo, output, pFillInfo->pData, pFillInfo->start, true); - } - - pFillInfo->numOfTotal += pFillInfo->numOfCurrent; - - assert(pFillInfo->numOfCurrent == resultCapacity); - return resultCapacity; -} - int64_t taosFillResultDataBlock(SFillInfo* pFillInfo, tFilePage** output, int32_t capacity) { int32_t remain = taosNumOfRemainRows(pFillInfo); - int64_t numOfRes = getNumOfResWithFill(pFillInfo, pFillInfo->end, capacity); + int64_t numOfRes = getNumOfResultsAfterFillGap(pFillInfo, pFillInfo->end, capacity); assert(numOfRes <= capacity); // no data existed for fill operation now, append result according to the fill strategy if (remain == 0) { - fillExternalResults(pFillInfo, output, numOfRes); + appendFilledResult(pFillInfo, output, numOfRes); } else { fillResultImpl(pFillInfo, output, (int32_t) numOfRes); assert(numOfRes == pFillInfo->numOfCurrent); diff --git a/src/query/src/qHistogram.c b/src/query/src/qHistogram.c index bdc071060c..ae25a75234 100644 --- a/src/query/src/qHistogram.c +++ b/src/query/src/qHistogram.c @@ -184,7 +184,7 @@ int32_t tHistogramAdd(SHistogramInfo** pHisto, double val) { histogramCreateBin(*pHisto, idx, val); } #else - tSkipListKey key = tSkipListCreateKey(TSDB_DATA_TYPE_DOUBLE, &val, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); + tSkipListKey key = tSkipListCreateKey(TSDB_DATA_TYPE_DOUBLE, &val, tDataTypes[TSDB_DATA_TYPE_DOUBLE].nSize); SHistBin* entry = calloc(1, sizeof(SHistBin)); entry->val = val; @@ -217,7 +217,7 @@ int32_t tHistogramAdd(SHistogramInfo** pHisto, double val) { } tSkipListKey kx = - tSkipListCreateKey(TSDB_DATA_TYPE_DOUBLE, &(*pHisto)->max, tDataTypeDesc[TSDB_DATA_TYPE_DOUBLE].nSize); + tSkipListCreateKey(TSDB_DATA_TYPE_DOUBLE, &(*pHisto)->max, tDataTypes[TSDB_DATA_TYPE_DOUBLE].nSize); pLast = tSkipListGetOne((*pHisto)->pList, &kx); } } else { diff --git a/src/query/src/qParserImpl.c b/src/query/src/qParserImpl.c index d311cb3557..a5a3d7e323 100644 --- a/src/query/src/qParserImpl.c +++ b/src/query/src/qParserImpl.c @@ -398,21 +398,21 @@ void tSqlSetColumnType(TAOS_FIELD *pField, SStrToken *type) { pField->name[0] = 0; int32_t i = 0; - while (i < tListLen(tDataTypeDesc)) { - if ((type->n == tDataTypeDesc[i].nameLen) && - (strncasecmp(type->z, tDataTypeDesc[i].aName, tDataTypeDesc[i].nameLen) == 0)) { + while (i < tListLen(tDataTypes)) { + if ((type->n == tDataTypes[i].nameLen) && + (strncasecmp(type->z, tDataTypes[i].name, tDataTypes[i].nameLen) == 0)) { break; } i += 1; } - if (i == tListLen(tDataTypeDesc)) { + if (i == tListLen(tDataTypes)) { return; } pField->type = i; - pField->bytes = tDataTypeDesc[i].nSize; + pField->bytes = tDataTypes[i].bytes; if (i == TSDB_DATA_TYPE_NCHAR) { /* diff --git a/src/query/src/qPercentile.c b/src/query/src/qPercentile.c index 51125d62b9..3e4891092a 100644 --- a/src/query/src/qPercentile.c +++ b/src/query/src/qPercentile.c @@ -12,14 +12,14 @@ * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see . */ +#include "os.h" #include "qPercentile.h" #include "qResultbuf.h" -#include "os.h" #include "queryLog.h" #include "taosdef.h" -#include "tulog.h" #include "tcompare.h" +#include "ttype.h" #define DEFAULT_NUM_OF_SLOT 1024 @@ -48,25 +48,15 @@ static tFilePage *loadDataFromFilePage(tMemBucket *pMemBucket, int32_t slotIdx) } static void resetBoundingBox(MinMaxEntry* range, int32_t type) { - switch (type) { - case TSDB_DATA_TYPE_BIGINT: { - range->i64MaxVal = INT64_MIN; - range->i64MinVal = INT64_MAX; - break; - }; - case TSDB_DATA_TYPE_INT: - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_TINYINT: { - range->iMaxVal = INT32_MIN; - range->iMinVal = INT32_MAX; - break; - }; - case TSDB_DATA_TYPE_DOUBLE: - case TSDB_DATA_TYPE_FLOAT: { - range->dMaxVal = -DBL_MAX; - range->dMinVal = DBL_MAX; - break; - } + if (IS_SIGNED_NUMERIC_TYPE(type)) { + range->i64MaxVal = INT64_MIN; + range->i64MinVal = INT64_MAX; + } else if (IS_UNSIGNED_NUMERIC_TYPE(type)) { + range->u64MaxVal = 0; + range->u64MinVal = UINT64_MAX; + } else { + range->dMaxVal = -DBL_MAX; + range->dMinVal = DBL_MAX; } } @@ -75,23 +65,15 @@ static int32_t setBoundingBox(MinMaxEntry* range, int16_t type, double minval, d return -1; } - switch(type) { - case TSDB_DATA_TYPE_TINYINT: - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_INT: - range->iMinVal = (int32_t) minval; - range->iMaxVal = (int32_t) maxval; - break; - - case TSDB_DATA_TYPE_BIGINT: - range->i64MinVal = (int64_t) minval; - range->i64MaxVal = (int64_t) maxval; - break; - case TSDB_DATA_TYPE_FLOAT: - case TSDB_DATA_TYPE_DOUBLE: - range->dMinVal = minval; - range->dMaxVal = maxval; - break; + if (IS_SIGNED_NUMERIC_TYPE(type)) { + range->i64MinVal = (int64_t) minval; + range->i64MaxVal = (int64_t) maxval; + } else if (IS_UNSIGNED_NUMERIC_TYPE(type)){ + range->u64MinVal = (uint64_t) minval; + range->u64MaxVal = (uint64_t) maxval; + } else { + range->dMinVal = minval; + range->dMaxVal = maxval; } return 0; @@ -120,117 +102,56 @@ double findOnlyResult(tMemBucket *pMemBucket) { tFilePage* pPage = getResBufPage(pMemBucket->pBuffer, pgInfo->pageId); assert(pPage->num == 1); - switch (pMemBucket->type) { - case TSDB_DATA_TYPE_INT: - return *(int32_t *)pPage->data; - case TSDB_DATA_TYPE_SMALLINT: - return *(int16_t *)pPage->data; - case TSDB_DATA_TYPE_TINYINT: - return *(int8_t *)pPage->data; - case TSDB_DATA_TYPE_BIGINT: - return (double)(*(int64_t *)pPage->data); - case TSDB_DATA_TYPE_DOUBLE: { - double dv = GET_DOUBLE_VAL(pPage->data); - return dv; - } - case TSDB_DATA_TYPE_FLOAT: { - float fv = GET_FLOAT_VAL(pPage->data); - return fv; - } - default: - return 0; - } + double v = 0; + GET_TYPED_DATA(v, double, pMemBucket->type, pPage->data); + return v; } return 0; } -int32_t tBucketBigIntHash(tMemBucket *pBucket, const void *value) { - int64_t v = *(int64_t *)value; +int32_t tBucketIntHash(tMemBucket *pBucket, const void *value) { + int64_t v = 0; + GET_TYPED_DATA(v, int64_t, pBucket->type, value); + int32_t index = -1; - - int32_t halfSlot = pBucket->numOfSlots >> 1; -// int32_t bits = 32;//bitsOfNumber(pBucket->numOfSlots) - 1; - - if (pBucket->range.i64MaxVal == INT64_MIN) { - if (v >= 0) { - index = (v >> (64 - 9)) + halfSlot; - } else { // v<0 - index = ((-v) >> (64 - 9)); - index = -index + (halfSlot - 1); - } - - return index; + // divide the value range into 1024 buckets + uint64_t span = pBucket->range.i64MaxVal - pBucket->range.i64MinVal; + if (span < pBucket->numOfSlots) { + int64_t delta = v - pBucket->range.i64MinVal; + index = (delta % pBucket->numOfSlots); } else { - // out of range - if (v < pBucket->range.i64MinVal || v > pBucket->range.i64MaxVal) { - return -1; + double slotSpan = (double)span / pBucket->numOfSlots; + index = (int32_t)((v - pBucket->range.i64MinVal) / slotSpan); + if (v == pBucket->range.i64MaxVal) { + index -= 1; } - - // todo hash for bigint and float and double - int64_t span = pBucket->range.i64MaxVal - pBucket->range.i64MinVal; - if (span < pBucket->numOfSlots) { - int32_t delta = (int32_t)(v - pBucket->range.i64MinVal); - index = delta % pBucket->numOfSlots; - } else { - double slotSpan = (double)span / pBucket->numOfSlots; - index = (int32_t)((v - pBucket->range.i64MinVal) / slotSpan); - if (v == pBucket->range.i64MaxVal) { - index -= 1; - } - } - - return index; } + + assert(v >= pBucket->range.i64MinVal && v <= pBucket->range.i64MaxVal && index >= 0 && index < pBucket->numOfSlots); + return index; } -// todo refactor to more generic -int32_t tBucketIntHash(tMemBucket *pBucket, const void *value) { - int32_t v = 0; - switch(pBucket->type) { - case TSDB_DATA_TYPE_SMALLINT: v = *(int16_t*) value; break; - case TSDB_DATA_TYPE_TINYINT: v = *(int8_t*) value; break; - default: v = *(int32_t*) value;break; - } +int32_t tBucketUintHash(tMemBucket *pBucket, const void *value) { + int64_t v = 0; + GET_TYPED_DATA(v, uint64_t, pBucket->type, value); int32_t index = -1; - if (pBucket->range.iMaxVal == INT32_MIN) { - /* - * taking negative integer into consideration, - * there is only half of pBucket->segs available for non-negative integer - */ - int32_t halfSlot = pBucket->numOfSlots >> 1; - int32_t bits = 32;//bitsOfNumber(pBucket->numOfSlots) - 1; - - if (v >= 0) { - index = (v >> (bits - 9)) + halfSlot; - } else { // v < 0 - index = ((-v) >> (32 - 9)); - index = -index + (halfSlot - 1); - } - - return index; + // divide the value range into 1024 buckets + uint64_t span = pBucket->range.u64MaxVal - pBucket->range.u64MinVal; + if (span < pBucket->numOfSlots) { + int64_t delta = v - pBucket->range.u64MinVal; + index = (int32_t) (delta % pBucket->numOfSlots); } else { - // out of range - if (v < pBucket->range.iMinVal || v > pBucket->range.iMaxVal) { - return -1; + double slotSpan = (double)span / pBucket->numOfSlots; + index = (int32_t)((v - pBucket->range.u64MinVal) / slotSpan); + if (v == pBucket->range.u64MaxVal) { + index -= 1; } - - // divide a range of [iMinVal, iMaxVal] into 1024 buckets - int32_t span = pBucket->range.iMaxVal - pBucket->range.iMinVal; - if (span < pBucket->numOfSlots) { - int32_t delta = v - pBucket->range.iMinVal; - index = (delta % pBucket->numOfSlots); - } else { - double slotSpan = (double)span / pBucket->numOfSlots; - index = (int32_t)((v - pBucket->range.iMinVal) / slotSpan); - if (v == pBucket->range.iMaxVal) { - index -= 1; - } - } - - return index; } + + assert(v >= pBucket->range.u64MinVal && v <= pBucket->range.i64MaxVal && index >= 0 && index < pBucket->numOfSlots); + return index; } int32_t tBucketDoubleHash(tMemBucket *pBucket, const void *value) { @@ -243,62 +164,30 @@ int32_t tBucketDoubleHash(tMemBucket *pBucket, const void *value) { int32_t index = -1; - if (pBucket->range.dMinVal == DBL_MAX) { - /* - * taking negative integer into consideration, - * there is only half of pBucket->segs available for non-negative integer - */ - double x = DBL_MAX / (pBucket->numOfSlots >> 1); - double posx = (v + DBL_MAX) / x; - return ((int32_t)posx) % pBucket->numOfSlots; + // divide a range of [dMinVal, dMaxVal] into 1024 buckets + double span = pBucket->range.dMaxVal - pBucket->range.dMinVal; + if (span < pBucket->numOfSlots) { + int32_t delta = (int32_t)(v - pBucket->range.dMinVal); + index = (delta % pBucket->numOfSlots); } else { - - // out of range - if (v < pBucket->range.dMinVal || v > pBucket->range.dMaxVal) { - return -1; + double slotSpan = span / pBucket->numOfSlots; + index = (int32_t)((v - pBucket->range.dMinVal) / slotSpan); + if (v == pBucket->range.dMaxVal) { + index -= 1; } - - // divide a range of [dMinVal, dMaxVal] into 1024 buckets - double span = pBucket->range.dMaxVal - pBucket->range.dMinVal; - if (span < pBucket->numOfSlots) { - int32_t delta = (int32_t)(v - pBucket->range.dMinVal); - index = (delta % pBucket->numOfSlots); - } else { - double slotSpan = span / pBucket->numOfSlots; - index = (int32_t)((v - pBucket->range.dMinVal) / slotSpan); - if (v == pBucket->range.dMaxVal) { - index -= 1; - } - } - - if (index < 0 || index > pBucket->numOfSlots) { - uError("error in hash process. slot id: %d", index); - } - - return index; } + + assert(v >= pBucket->range.dMinVal && v <= pBucket->range.dMaxVal && index >= 0 && index < pBucket->numOfSlots); + return index; } static __perc_hash_func_t getHashFunc(int32_t type) { - switch (type) { - case TSDB_DATA_TYPE_INT: - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_TINYINT: { - return tBucketIntHash; - }; - - case TSDB_DATA_TYPE_DOUBLE: - case TSDB_DATA_TYPE_FLOAT: { - return tBucketDoubleHash; - }; - - case TSDB_DATA_TYPE_BIGINT: { - return tBucketBigIntHash; - }; - - default: { - return NULL; - } + if (IS_SIGNED_NUMERIC_TYPE(type)) { + return tBucketIntHash; + } else if (IS_UNSIGNED_NUMERIC_TYPE(type)) { + return tBucketUintHash; + } else { + return tBucketDoubleHash; } } @@ -328,7 +217,7 @@ tMemBucket *tMemBucketCreate(int16_t nElemSize, int16_t dataType, double minval, pBucket->maxCapacity = 200000; if (setBoundingBox(&pBucket->range, pBucket->type, minval, maxval) != 0) { - uError("MemBucket:%p, invalid value range: %f-%f", pBucket, minval, maxval); + qError("MemBucket:%p, invalid value range: %f-%f", pBucket, minval, maxval); free(pBucket); return NULL; } @@ -338,7 +227,7 @@ tMemBucket *tMemBucketCreate(int16_t nElemSize, int16_t dataType, double minval, pBucket->hashFunc = getHashFunc(pBucket->type); if (pBucket->hashFunc == NULL) { - uError("MemBucket:%p, not support data type %d, failed", pBucket, pBucket->type); + qError("MemBucket:%p, not support data type %d, failed", pBucket, pBucket->type); free(pBucket); return NULL; } @@ -357,7 +246,7 @@ tMemBucket *tMemBucketCreate(int16_t nElemSize, int16_t dataType, double minval, return NULL; } - uDebug("MemBucket:%p, elem size:%d", pBucket, pBucket->bytes); + qDebug("MemBucket:%p, elem size:%d", pBucket, pBucket->bytes); return pBucket; } @@ -372,77 +261,41 @@ void tMemBucketDestroy(tMemBucket *pBucket) { } void tMemBucketUpdateBoundingBox(MinMaxEntry *r, const char *data, int32_t dataType) { - switch (dataType) { - case TSDB_DATA_TYPE_INT: { - int32_t val = *(int32_t *)data; - if (r->iMinVal > val) { - r->iMinVal = val; - } + if (IS_SIGNED_NUMERIC_TYPE(dataType)) { + int64_t v = 0; + GET_TYPED_DATA(v, int64_t, dataType, data); - if (r->iMaxVal < val) { - r->iMaxVal = val; - } - break; - }; - case TSDB_DATA_TYPE_BIGINT: { - int64_t val = *(int64_t *)data; - if (r->i64MinVal > val) { - r->i64MinVal = val; - } + if (r->i64MinVal > v) { + r->i64MinVal = v; + } - if (r->i64MaxVal < val) { - r->i64MaxVal = val; - } - break; - }; - case TSDB_DATA_TYPE_SMALLINT: { - int32_t val = *(int16_t *)data; - if (r->iMinVal > val) { - r->iMinVal = val; - } + if (r->i64MaxVal < v) { + r->i64MaxVal = v; + } + } else if (IS_UNSIGNED_NUMERIC_TYPE(dataType)) { + uint64_t v = 0; + GET_TYPED_DATA(v, uint64_t, dataType, data); - if (r->iMaxVal < val) { - r->iMaxVal = val; - } - break; - }; - case TSDB_DATA_TYPE_TINYINT: { - int32_t val = *(int8_t *)data; - if (r->iMinVal > val) { - r->iMinVal = val; - } + if (r->i64MinVal > v) { + r->i64MinVal = v; + } - if (r->iMaxVal < val) { - r->iMaxVal = val; - } + if (r->i64MaxVal < v) { + r->i64MaxVal = v; + } + } else if (IS_FLOAT_TYPE(dataType)) { + double v = 0; + GET_TYPED_DATA(v, double, dataType, data); - break; - }; - case TSDB_DATA_TYPE_DOUBLE: { - // double val = *(double *)data; - double val = GET_DOUBLE_VAL(data); - if (r->dMinVal > val) { - r->dMinVal = val; - } + if (r->dMinVal > v) { + r->dMinVal = v; + } - if (r->dMaxVal < val) { - r->dMaxVal = val; - } - break; - }; - case TSDB_DATA_TYPE_FLOAT: { - double val = GET_FLOAT_VAL(data); - - if (r->dMinVal > val) { - r->dMinVal = val; - } - - if (r->dMaxVal < val) { - r->dMaxVal = val; - } - break; - }; - default: { assert(false); } + if (r->dMaxVal < v) { + r->dMaxVal = v; + } + } else { + assert(0); } } @@ -452,16 +305,13 @@ void tMemBucketUpdateBoundingBox(MinMaxEntry *r, const char *data, int32_t dataT int32_t tMemBucketPut(tMemBucket *pBucket, const void *data, size_t size) { assert(pBucket != NULL && data != NULL && size > 0); - pBucket->total += (int32_t)size; - + int32_t count = 0; int32_t bytes = pBucket->bytes; for (int32_t i = 0; i < size; ++i) { char *d = (char *) data + i * bytes; + count += 1; int32_t index = (pBucket->hashFunc)(pBucket, d); - if (index == -1) { // the value is out of range, do not add it into bucket - return -1; - } tMemBucketSlot *pSlot = &pBucket->pSlots[index]; tMemBucketUpdateBoundingBox(&pSlot->range, d, pBucket->type); @@ -489,64 +339,11 @@ int32_t tMemBucketPut(tMemBucket *pBucket, const void *data, size_t size) { pSlot->info.size += 1; } + pBucket->total += count; return 0; } //////////////////////////////////////////////////////////////////////////////////////////// -static UNUSED_FUNC void findMaxMinValue(tMemBucket *pMemBucket, double *maxVal, double *minVal) { - *minVal = DBL_MAX; - *maxVal = -DBL_MAX; - - for (int32_t i = 0; i < pMemBucket->numOfSlots; ++i) { - tMemBucketSlot *pSlot = &pMemBucket->pSlots[i]; - if (pSlot->info.size == 0) { - continue; - } - - switch (pMemBucket->type) { - case TSDB_DATA_TYPE_INT: - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_TINYINT: { - double minv = pSlot->range.iMinVal; - double maxv = pSlot->range.iMaxVal; - - if (*minVal > minv) { - *minVal = minv; - } - if (*maxVal < maxv) { - *maxVal = maxv; - } - break; - } - case TSDB_DATA_TYPE_DOUBLE: - case TSDB_DATA_TYPE_FLOAT: { - double minv = pSlot->range.dMinVal; - double maxv = pSlot->range.dMaxVal; - - if (*minVal > minv) { - *minVal = minv; - } - if (*maxVal < maxv) { - *maxVal = maxv; - } - break; - } - case TSDB_DATA_TYPE_BIGINT: { - double minv = (double)pSlot->range.i64MinVal; - double maxv = (double)pSlot->range.i64MaxVal; - - if (*minVal > minv) { - *minVal = minv; - } - if (*maxVal < maxv) { - *maxVal = maxv; - } - break; - } - } - } -} - /* * * now, we need to find the minimum value of the next slot for @@ -565,7 +362,6 @@ static MinMaxEntry getMinMaxEntryOfNextSlotWithData(tMemBucket *pMemBucket, int3 } static bool isIdenticalData(tMemBucket *pMemBucket, int32_t index); -char *getFirstElemOfMemBuffer(tMemBucketSlot *pSeg, int32_t slotIdx, tFilePage *pPage); static double getIdenticalDataVal(tMemBucket* pMemBucket, int32_t slotIndex) { assert(isIdenticalData(pMemBucket, slotIndex)); @@ -573,24 +369,12 @@ static double getIdenticalDataVal(tMemBucket* pMemBucket, int32_t slotIndex) { tMemBucketSlot *pSlot = &pMemBucket->pSlots[slotIndex]; double finalResult = 0.0; - switch (pMemBucket->type) { - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_TINYINT: - case TSDB_DATA_TYPE_INT: { - finalResult = pSlot->range.iMinVal; - break; - } - - case TSDB_DATA_TYPE_FLOAT: - case TSDB_DATA_TYPE_DOUBLE: { - finalResult = pSlot->range.dMinVal; - break; - }; - - case TSDB_DATA_TYPE_BIGINT: { - finalResult = (double)pSlot->range.i64MinVal; - break; - } + if (IS_SIGNED_NUMERIC_TYPE(pMemBucket->type)) { + finalResult = (double) pSlot->range.i64MinVal; + } else if (IS_UNSIGNED_NUMERIC_TYPE(pMemBucket->type)) { + finalResult = (double) pSlot->range.u64MinVal; + } else { + finalResult = (double) pSlot->range.dMinVal; } return finalResult; @@ -616,26 +400,16 @@ double getPercentileImpl(tMemBucket *pMemBucket, int32_t count, double fraction) double maxOfThisSlot = 0; double minOfNextSlot = 0; - switch (pMemBucket->type) { - case TSDB_DATA_TYPE_INT: - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_TINYINT: { - maxOfThisSlot = pSlot->range.iMaxVal; - minOfNextSlot = next.iMinVal; - break; - }; - case TSDB_DATA_TYPE_FLOAT: - case TSDB_DATA_TYPE_DOUBLE: { - maxOfThisSlot = pSlot->range.dMaxVal; - minOfNextSlot = next.dMinVal; - break; - }; - case TSDB_DATA_TYPE_BIGINT: { - maxOfThisSlot = (double)pSlot->range.i64MaxVal; - minOfNextSlot = (double)next.i64MinVal; - break; - } - }; + if (IS_SIGNED_NUMERIC_TYPE(pMemBucket->type)) { + maxOfThisSlot = (double) pSlot->range.i64MaxVal; + minOfNextSlot = (double) next.i64MinVal; + } else if (IS_UNSIGNED_NUMERIC_TYPE(pMemBucket->type)) { + maxOfThisSlot = (double) pSlot->range.u64MaxVal; + minOfNextSlot = (double) next.u64MinVal; + } else { + maxOfThisSlot = (double) pSlot->range.dMaxVal; + minOfNextSlot = (double) next.dMinVal; + } assert(minOfNextSlot > maxOfThisSlot); @@ -652,38 +426,8 @@ double getPercentileImpl(tMemBucket *pMemBucket, int32_t count, double fraction) char *nextVal = thisVal + pMemBucket->bytes; double td = 1.0, nd = 1.0; - switch (pMemBucket->type) { - case TSDB_DATA_TYPE_SMALLINT: { - td = *(int16_t *)thisVal; - nd = *(int16_t *)nextVal; - break; - } - case TSDB_DATA_TYPE_TINYINT: { - td = *(int8_t *)thisVal; - nd = *(int8_t *)nextVal; - break; - } - case TSDB_DATA_TYPE_INT: { - td = *(int32_t *)thisVal; - nd = *(int32_t *)nextVal; - break; - }; - case TSDB_DATA_TYPE_FLOAT: { - td = GET_FLOAT_VAL(thisVal); - nd = GET_FLOAT_VAL(nextVal); - break; - } - case TSDB_DATA_TYPE_DOUBLE: { - td = GET_DOUBLE_VAL(thisVal); - nd = GET_DOUBLE_VAL(nextVal); - break; - } - case TSDB_DATA_TYPE_BIGINT: { - td = (double)*(int64_t *)thisVal; - nd = (double)*(int64_t *)nextVal; - break; - } - } + GET_TYPED_DATA(td, double, pMemBucket->type, thisVal); + GET_TYPED_DATA(nd, double, pMemBucket->type, nextVal); double val = (1 - fraction) * td + fraction * nd; tfree(buffer); @@ -696,7 +440,7 @@ double getPercentileImpl(tMemBucket *pMemBucket, int32_t count, double fraction) // try next round pMemBucket->times += 1; - uDebug("MemBucket:%p, start next round data bucketing, time:%d", pMemBucket, pMemBucket->times); + qDebug("MemBucket:%p, start next round data bucketing, time:%d", pMemBucket, pMemBucket->times); pMemBucket->range = pSlot->range; pMemBucket->total = 0; @@ -741,20 +485,14 @@ double getPercentile(tMemBucket *pMemBucket, double percent) { if (fabs(percent - 100.0) < DBL_EPSILON || (percent < DBL_EPSILON)) { MinMaxEntry* pRange = &pMemBucket->range; - switch(pMemBucket->type) { - case TSDB_DATA_TYPE_TINYINT: - case TSDB_DATA_TYPE_SMALLINT: - case TSDB_DATA_TYPE_INT: - return fabs(percent - 100) < DBL_EPSILON? pRange->iMaxVal:pRange->iMinVal; - case TSDB_DATA_TYPE_BIGINT: { - double v = (double)(fabs(percent - 100) < DBL_EPSILON ? pRange->i64MaxVal : pRange->i64MinVal); - return v; - } - case TSDB_DATA_TYPE_FLOAT: - case TSDB_DATA_TYPE_DOUBLE: - return fabs(percent - 100) < DBL_EPSILON? pRange->dMaxVal:pRange->dMinVal; - default: - return -1; + if (IS_SIGNED_NUMERIC_TYPE(pMemBucket->type)) { + double v = (double)(fabs(percent - 100) < DBL_EPSILON ? pRange->i64MaxVal : pRange->i64MinVal); + return v; + } else if (IS_UNSIGNED_NUMERIC_TYPE(pMemBucket->type)) { + double v = (double)(fabs(percent - 100) < DBL_EPSILON ? pRange->u64MaxVal : pRange->u64MinVal); + return v; + } else { + return fabs(percent - 100) < DBL_EPSILON? pRange->dMaxVal:pRange->dMinVal; } } @@ -771,40 +509,9 @@ double getPercentile(tMemBucket *pMemBucket, double percent) { bool isIdenticalData(tMemBucket *pMemBucket, int32_t index) { tMemBucketSlot *pSeg = &pMemBucket->pSlots[index]; - if (pMemBucket->type == TSDB_DATA_TYPE_INT || pMemBucket->type == TSDB_DATA_TYPE_BIGINT || - pMemBucket->type == TSDB_DATA_TYPE_SMALLINT || pMemBucket->type == TSDB_DATA_TYPE_TINYINT) { + if (IS_FLOAT_TYPE(pMemBucket->type)) { + return fabs(pSeg->range.dMaxVal - pSeg->range.dMinVal) < DBL_EPSILON; + } else { return pSeg->range.i64MinVal == pSeg->range.i64MaxVal; } - - if (pMemBucket->type == TSDB_DATA_TYPE_FLOAT || pMemBucket->type == TSDB_DATA_TYPE_DOUBLE) { - return fabs(pSeg->range.dMaxVal - pSeg->range.dMinVal) < DBL_EPSILON; - } - - return false; -} - -/* - * get the first element of one slot into memory. - * if no data of current slot in memory, load it from disk - */ -char *getFirstElemOfMemBuffer(tMemBucketSlot *pSeg, int32_t slotIdx, tFilePage *pPage) { -// STSBuf *pMemBuffer = pSeg->pBuffer[slotIdx]; - char *thisVal = NULL; - -// if (pSeg->pBuffer[slotIdx]->numOfTotal != 0) { -//// thisVal = pSeg->pBuffer[slotIdx]->pHead->item.data; -// } else { -// /* -// * no data in memory, load one page into memory -// */ -// tFlushoutInfo *pFlushInfo = &pMemBuffer->fileMeta.flushoutData.pFlushoutInfo[0]; -// assert(pFlushInfo->numOfPages == pMemBuffer->fileMeta.nFileSize); -// int32_t ret; -// ret = fseek(pMemBuffer->file, pFlushInfo->startPageId * pMemBuffer->pageSize, SEEK_SET); -// UNUSED(ret); -// size_t sz = fread(pPage, pMemBuffer->pageSize, 1, pMemBuffer->file); -// UNUSED(sz); -// thisVal = pPage->data; -// } - return thisVal; } diff --git a/src/query/tests/CMakeLists.txt b/src/query/tests/CMakeLists.txt index 1856223391..c3798b869e 100644 --- a/src/query/tests/CMakeLists.txt +++ b/src/query/tests/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) FIND_PATH(HEADER_GTEST_INCLUDE_DIR gtest.h /usr/include/gtest /usr/local/include/gtest) diff --git a/src/query/tests/percentileTest.cpp b/src/query/tests/percentileTest.cpp new file mode 100644 index 0000000000..f2b457e7dd --- /dev/null +++ b/src/query/tests/percentileTest.cpp @@ -0,0 +1,254 @@ +#include +#include + +#include "qResultbuf.h" +#include "taos.h" +#include "taosdef.h" + +#include "qPercentile.h" + +namespace { +tMemBucket *createBigIntDataBucket(int32_t start, int32_t end) { + tMemBucket *pBucket = tMemBucketCreate(sizeof(int64_t), TSDB_DATA_TYPE_BIGINT, start, end); + for (int32_t i = start; i <= end; ++i) { + int64_t val = i; + tMemBucketPut(pBucket, &val, 1); + } + + return pBucket; +} + +tMemBucket *createIntDataBucket(int32_t start, int32_t end) { + tMemBucket *pBucket = tMemBucketCreate(sizeof(int32_t), TSDB_DATA_TYPE_INT, start, end); + + for (int32_t i = start; i <= end; ++i) { + int32_t val = i; + tMemBucketPut(pBucket, &val, 1); + } + + return pBucket; +} + +tMemBucket *createDoubleDataBucket(int32_t start, int32_t end) { + tMemBucket *pBucket = tMemBucketCreate(sizeof(double), TSDB_DATA_TYPE_DOUBLE, start, end); + for (int32_t i = start; i <= end; ++i) { + double val = i; + int32_t ret = tMemBucketPut(pBucket, &val, 1); + if (ret != 0) { + printf("value out of range:%f", val); + } + } + + return pBucket; +} + +tMemBucket *createUnsignedDataBucket(int32_t start, int32_t end, int32_t type) { + tMemBucket *pBucket = tMemBucketCreate(tDataTypes[type].bytes, type, start, end); + for (int32_t i = start; i <= end; ++i) { + uint64_t k = i; + int32_t ret = tMemBucketPut(pBucket, &k, 1); + if (ret != 0) { + printf("value out of range:%f", k); + } + } + + return pBucket; +} + +void intDataTest() { + printf("running %s\n", __FUNCTION__); + + tMemBucket *pBucket = NULL; + double result = 0.; + + pBucket = createIntDataBucket(0, 0); + result = getPercentile(pBucket, 0); + ASSERT_DOUBLE_EQ(result, 0); + tMemBucketDestroy(pBucket); + + pBucket = createIntDataBucket(0, 1); + result = getPercentile(pBucket, 100); + ASSERT_DOUBLE_EQ(result, 1); + + result = getPercentile(pBucket, 0); + ASSERT_DOUBLE_EQ(result, 0); + tMemBucketDestroy(pBucket); + + pBucket = createIntDataBucket(-1, 1); + + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 0); + + result = getPercentile(pBucket, 0); + ASSERT_DOUBLE_EQ(result, -1); + + result = getPercentile(pBucket, 75); + ASSERT_DOUBLE_EQ(result, 0.5); + + result = getPercentile(pBucket, 100); + ASSERT_DOUBLE_EQ(result, 1); + tMemBucketDestroy(pBucket); + + pBucket = createIntDataBucket(0, 99999); + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 49999.5); + + tMemBucketDestroy(pBucket); +} + +void bigintDataTest() { + printf("running %s\n", __FUNCTION__); + + tMemBucket *pBucket = NULL; + double result = 0.0; + + pBucket = createBigIntDataBucket(-1000, 1000); + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 0.); + tMemBucketDestroy(pBucket); + + pBucket = createBigIntDataBucket(-10000, 10000); + result = getPercentile(pBucket, 100); + ASSERT_DOUBLE_EQ(result, 10000.0); + tMemBucketDestroy(pBucket); + + pBucket = createBigIntDataBucket(-10000, 10000); + result = getPercentile(pBucket, 75); + ASSERT_DOUBLE_EQ(result, 5000.0); + + tMemBucketDestroy(pBucket); +} + +void doubleDataTest() { + printf("running %s\n", __FUNCTION__); + + tMemBucket *pBucket = NULL; + double result = 0; + + pBucket = createDoubleDataBucket(-10, 10); + result = getPercentile(pBucket, 0); + ASSERT_DOUBLE_EQ(result, -10.0); + + printf("result is: %lf\n", result); + tMemBucketDestroy(pBucket); + + pBucket = createDoubleDataBucket(-100000, 100000); + result = getPercentile(pBucket, 25); + ASSERT_DOUBLE_EQ(result, -50000); + + printf("result is: %lf\n", result); + + tMemBucketDestroy(pBucket); + + pBucket = createDoubleDataBucket(-100000, 100000); + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 0); + + tMemBucketDestroy(pBucket); + + pBucket = createDoubleDataBucket(-100000, 100000); + result = getPercentile(pBucket, 75); + ASSERT_DOUBLE_EQ(result, 50000); + tMemBucketDestroy(pBucket); + + pBucket = createDoubleDataBucket(-100000, 100000); + + result = getPercentile(pBucket, 100); + ASSERT_DOUBLE_EQ(result, 100000.0); + + printf("result is: %lf\n", result); + tMemBucketDestroy(pBucket); +} + +/* + * large data test, we employ 0.1billion double data to calculated the percentile + * which is 800MB data + */ +void largeDataTest() { + printf("running : %s\n", __FUNCTION__); + + tMemBucket *pBucket = NULL; + double result = 0; + + struct timeval tv; + gettimeofday(&tv, NULL); + + int64_t start = tv.tv_sec; + printf("start time: %" PRId64 "\n", tv.tv_sec); + pBucket = createDoubleDataBucket(0, 100000000); + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 50000000); + + gettimeofday(&tv, NULL); + + printf("total elapsed time: %" PRId64 " sec.", -start + tv.tv_sec); + printf("the result of %d is: %lf\n", 50, result); + tMemBucketDestroy(pBucket); +} + +void qsortTest() { + printf("running : %s\n", __FUNCTION__); + + SSchema field[1] = { + {TSDB_DATA_TYPE_INT, "k", sizeof(int32_t)}, + }; + + const int32_t num = 2000; + + int32_t *d = (int32_t *)malloc(sizeof(int32_t) * num); + for (int32_t i = 0; i < num; ++i) { + d[i] = i % 4; + } + + const int32_t numOfOrderCols = 1; + int32_t orderColIdx = 0; + SColumnModel * pModel = createColumnModel(field, 1, 1000); + tOrderDescriptor *pDesc = tOrderDesCreate(&orderColIdx, numOfOrderCols, pModel, 1); + + tColDataQSort(pDesc, num, 0, num - 1, (char *)d, 1); + + for (int32_t i = 0; i < num; ++i) { + printf("%d\t", d[i]); + } + printf("\n"); + + destroyColumnModel(pModel); +} + +void unsignedDataTest() { + printf("running %s\n", __FUNCTION__); + + tMemBucket *pBucket = NULL; + double result = 0.0; + + pBucket = createUnsignedDataBucket(0, 1000, TSDB_DATA_TYPE_UINT); + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 500.0); + tMemBucketDestroy(pBucket); + + pBucket = createUnsignedDataBucket(0, 10000, TSDB_DATA_TYPE_UBIGINT); + result = getPercentile(pBucket, 100); + ASSERT_DOUBLE_EQ(result, 10000.0); + + result = getPercentile(pBucket, 0); + ASSERT_DOUBLE_EQ(result, 0.0); + + result = getPercentile(pBucket, 50); + ASSERT_DOUBLE_EQ(result, 5000); + + result = getPercentile(pBucket, 75); + ASSERT_DOUBLE_EQ(result, 7500); + tMemBucketDestroy(pBucket); + +} + +} // namespace + +TEST(testCase, percentileTest) { + // qsortTest(); + intDataTest(); + bigintDataTest(); + doubleDataTest(); + unsignedDataTest(); + largeDataTest(); +} diff --git a/src/rpc/CMakeLists.txt b/src/rpc/CMakeLists.txt index f94b4aeb6d..02a1e7c2d8 100644 --- a/src/rpc/CMakeLists.txt +++ b/src/rpc/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/rpc/src/rpcTcp.c b/src/rpc/src/rpcTcp.c index 178b96c423..daf3bd86c1 100644 --- a/src/rpc/src/rpcTcp.c +++ b/src/rpc/src/rpcTcp.c @@ -241,7 +241,7 @@ static void *taosAcceptTcpConnection(void *arg) { } taosKeepTcpAlive(connFd); - struct timeval to={1, 0}; + struct timeval to={5, 0}; int32_t ret = taosSetSockOpt(connFd, SOL_SOCKET, SO_RCVTIMEO, &to, sizeof(to)); if (ret != 0) { taosCloseSocket(connFd); diff --git a/src/rpc/test/CMakeLists.txt b/src/rpc/test/CMakeLists.txt index 383ce1b0f6..9a4bcc353d 100644 --- a/src/rpc/test/CMakeLists.txt +++ b/src/rpc/test/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/rpc/inc) diff --git a/src/sync/CMakeLists.txt b/src/sync/CMakeLists.txt index aa38a56f38..6a53380841 100644 --- a/src/sync/CMakeLists.txt +++ b/src/sync/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/sync/src/syncRetrieve.c b/src/sync/src/syncRetrieve.c index 153886102e..cb2379583f 100644 --- a/src/sync/src/syncRetrieve.c +++ b/src/sync/src/syncRetrieve.c @@ -475,7 +475,8 @@ void *syncRetrieveData(void *param) { SSyncNode *pNode = pPeer->pSyncNode; taosBlockSIGPIPE(); - sInfo("%s, start to retrieve data, sstatus:%s", pPeer->id, syncStatus[pPeer->sstatus]); + sInfo("%s, start to retrieve data, sstatus:%s, numOfRetrieves:%d", pPeer->id, syncStatus[pPeer->sstatus], + pPeer->numOfRetrieves); if (pNode->notifyFlowCtrl) (*pNode->notifyFlowCtrl)(pNode->vgId, pPeer->numOfRetrieves); @@ -497,9 +498,11 @@ void *syncRetrieveData(void *param) { pPeer->numOfRetrieves++; } else { pPeer->numOfRetrieves = 0; - if (pNode->notifyFlowCtrl) (*pNode->notifyFlowCtrl)(pNode->vgId, 0); + // if (pNode->notifyFlowCtrl) (*pNode->notifyFlowCtrl)(pNode->vgId, 0); } + if (pNode->notifyFlowCtrl) (*pNode->notifyFlowCtrl)(pNode->vgId, 0); + pPeer->fileChanged = 0; taosClose(pPeer->syncFd); diff --git a/src/sync/test/CMakeLists.txt b/src/sync/test/CMakeLists.txt index 27614454f9..256e87580d 100644 --- a/src/sync/test/CMakeLists.txt +++ b/src/sync/test/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX) diff --git a/src/tsdb/CMakeLists.txt b/src/tsdb/CMakeLists.txt index d86b104f23..d8bc20ca99 100644 --- a/src/tsdb/CMakeLists.txt +++ b/src/tsdb/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/tsdb/src/tsdbMeta.c b/src/tsdb/src/tsdbMeta.c index 7b08178f49..2bc387c3cd 100644 --- a/src/tsdb/src/tsdbMeta.c +++ b/src/tsdb/src/tsdbMeta.c @@ -253,7 +253,7 @@ STableCfg *tsdbCreateTableCfgFromMsg(SMDCreateTableMsg *pMsg) { } } if (tsdbTableSetSchema(pCfg, tdGetSchemaFromBuilder(&schemaBuilder), false) < 0) goto _err; - if (tsdbTableSetName(pCfg, pMsg->tableId, true) < 0) goto _err; + if (tsdbTableSetName(pCfg, pMsg->tableFname, true) < 0) goto _err; if (numOfTags > 0) { // Decode tag schema @@ -265,7 +265,7 @@ STableCfg *tsdbCreateTableCfgFromMsg(SMDCreateTableMsg *pMsg) { } } if (tsdbTableSetTagSchema(pCfg, tdGetSchemaFromBuilder(&schemaBuilder), false) < 0) goto _err; - if (tsdbTableSetSName(pCfg, pMsg->superTableId, true) < 0) goto _err; + if (tsdbTableSetSName(pCfg, pMsg->stableFname, true) < 0) goto _err; if (tsdbTableSetSuperUid(pCfg, htobe64(pMsg->superTableUid)) < 0) goto _err; int32_t tagDataLen = htonl(pMsg->tagDataLen); diff --git a/src/tsdb/src/tsdbRWHelper.c b/src/tsdb/src/tsdbRWHelper.c index b53b8ed5b4..4a44784cc2 100644 --- a/src/tsdb/src/tsdbRWHelper.c +++ b/src/tsdb/src/tsdbRWHelper.c @@ -751,8 +751,8 @@ static int tsdbWriteBlockToFile(SRWHelper *pHelper, SFile *pFile, SDataCols *pDa pCompCol->colId = pDataCol->colId; pCompCol->type = pDataCol->type; - if (tDataTypeDesc[pDataCol->type].getStatisFunc) { - (*tDataTypeDesc[pDataCol->type].getStatisFunc)( + if (tDataTypes[pDataCol->type].statisFunc) { + (*tDataTypes[pDataCol->type].statisFunc)( pDataCol->pData, rowsToWrite, &(pCompCol->min), &(pCompCol->max), &(pCompCol->sum), &(pCompCol->minIndex), &(pCompCol->maxIndex), &(pCompCol->numOfNull)); } @@ -788,7 +788,7 @@ static int tsdbWriteBlockToFile(SRWHelper *pHelper, SFile *pFile, SDataCols *pDa } } - flen = (*(tDataTypeDesc[pDataCol->type].compFunc))((char *)pDataCol->pData, tlen, rowsToWrite, tptr, + flen = (*(tDataTypes[pDataCol->type].compFunc))((char *)pDataCol->pData, tlen, rowsToWrite, tptr, (int32_t)taosTSizeof(pHelper->pBuffer) - lsize, pCfg->compression, pHelper->compBuffer, (int32_t)taosTSizeof(pHelper->compBuffer)); } else { @@ -1208,7 +1208,7 @@ static int tsdbCheckAndDecodeColumnData(SDataCol *pDataCol, char *content, int32 // Decode the data if (comp) { // // Need to decompress - int tlen = (*(tDataTypeDesc[pDataCol->type].decompFunc))(content, len - sizeof(TSCKSUM), numOfRows, pDataCol->pData, + int tlen = (*(tDataTypes[pDataCol->type].decompFunc))(content, len - sizeof(TSCKSUM), numOfRows, pDataCol->pData, pDataCol->spaceSize, comp, buffer, bufferSize); if (tlen <= 0) { tsdbError("Failed to decompress column, file corrupted, len:%d comp:%d numOfRows:%d maxPoints:%d bufferSize:%d", diff --git a/src/util/CMakeLists.txt b/src/util/CMakeLists.txt index 78b9c90979..48b4d76561 100644 --- a/src/util/CMakeLists.txt +++ b/src/util/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/rpc/inc) diff --git a/src/util/src/tcompare.c b/src/util/src/tcompare.c index de6fbe7302..01e61987c6 100644 --- a/src/util/src/tcompare.c +++ b/src/util/src/tcompare.c @@ -1,4 +1,4 @@ -#include "taosdef.h" +#include "ttype.h" #include "tcompare.h" #include "tarray.h" @@ -30,24 +30,32 @@ int32_t compareInt8Val(const void *pLeft, const void *pRight) { return 0; } -int32_t compareIntDoubleVal(const void *pLeft, const void *pRight) { - int64_t lhs = GET_INT64_VAL(pLeft); - double rhs = GET_DOUBLE_VAL(pRight); - if (fabs(lhs - rhs) < FLT_EPSILON) { - return 0; - } else { - return (lhs > rhs) ? 1 : -1; - } +int32_t compareUint32Val(const void *pLeft, const void *pRight) { + int32_t left = GET_UINT32_VAL(pLeft), right = GET_UINT32_VAL(pRight); + if (left > right) return 1; + if (left < right) return -1; + return 0; } -int32_t compareDoubleIntVal(const void *pLeft, const void *pRight) { - double lhs = GET_DOUBLE_VAL(pLeft); - int64_t rhs = GET_INT64_VAL(pRight); - if (fabs(lhs - rhs) < FLT_EPSILON) { - return 0; - } else { - return (lhs > rhs) ? 1 : -1; - } +int32_t compareUint64Val(const void *pLeft, const void *pRight) { + int64_t left = GET_UINT64_VAL(pLeft), right = GET_UINT64_VAL(pRight); + if (left > right) return 1; + if (left < right) return -1; + return 0; +} + +int32_t compareUint16Val(const void *pLeft, const void *pRight) { + int16_t left = GET_UINT16_VAL(pLeft), right = GET_UINT16_VAL(pRight); + if (left > right) return 1; + if (left < right) return -1; + return 0; +} + +int32_t compareUint8Val(const void* pLeft, const void* pRight) { + uint8_t left = GET_UINT8_VAL(pLeft), right = GET_UINT8_VAL(pRight); + if (left > right) return 1; + if (left < right) return -1; + return 0; } int32_t compareFloatVal(const void *pLeft, const void *pRight) { @@ -369,15 +377,24 @@ __compar_fn_t getKeyComparFunc(int32_t keyType) { case TSDB_DATA_TYPE_DOUBLE: comparFn = compareDoubleVal; break; - + case TSDB_DATA_TYPE_UTINYINT: + comparFn = compareUint8Val; + break; + case TSDB_DATA_TYPE_USMALLINT: + comparFn = compareUint16Val; + break; + case TSDB_DATA_TYPE_UINT: + comparFn = compareUint32Val; + break; + case TSDB_DATA_TYPE_UBIGINT: + comparFn = compareUint64Val; + break; case TSDB_DATA_TYPE_BINARY: comparFn = compareLenPrefixedStr; break; - case TSDB_DATA_TYPE_NCHAR: comparFn = compareLenPrefixedWStr; break; - default: comparFn = compareInt32Val; break; diff --git a/src/util/src/tsocket.c b/src/util/src/tsocket.c index 1a5c3bd64d..49b69ea0a1 100644 --- a/src/util/src/tsocket.c +++ b/src/util/src/tsocket.c @@ -283,6 +283,7 @@ SOCKET taosOpenTcpClientSocket(uint32_t destIp, uint16_t destPort, uint32_t clie SOCKET sockFd = 0; int32_t ret; struct sockaddr_in serverAddr, clientAddr; + int32_t bufSize = 1024 * 1024; sockFd = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); @@ -300,6 +301,18 @@ SOCKET taosOpenTcpClientSocket(uint32_t destIp, uint16_t destPort, uint32_t clie return -1; } + if (taosSetSockOpt(sockFd, SOL_SOCKET, SO_SNDBUF, (void *)&bufSize, sizeof(bufSize)) != 0) { + uError("failed to set the send buffer size for TCP socket\n"); + taosCloseSocket(sockFd); + return -1; + } + + if (taosSetSockOpt(sockFd, SOL_SOCKET, SO_RCVBUF, (void *)&bufSize, sizeof(bufSize)) != 0) { + uError("failed to set the receive buffer size for TCP socket\n"); + taosCloseSocket(sockFd); + return -1; + } + if (clientIp != 0) { memset((char *)&clientAddr, 0, sizeof(clientAddr)); clientAddr.sin_family = AF_INET; diff --git a/src/util/tests/CMakeLists.txt b/src/util/tests/CMakeLists.txt index 0c96ed2a2f..6066d58416 100644 --- a/src/util/tests/CMakeLists.txt +++ b/src/util/tests/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) FIND_PATH(HEADER_GTEST_INCLUDE_DIR gtest.h /usr/include/gtest /usr/local/include/gtest) diff --git a/src/vnode/CMakeLists.txt b/src/vnode/CMakeLists.txt index de0cdb028b..c953883361 100644 --- a/src/vnode/CMakeLists.txt +++ b/src/vnode/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/query/inc) diff --git a/src/vnode/inc/vnodeInt.h b/src/vnode/inc/vnodeInt.h index 7adeda590a..3ec77bbc12 100644 --- a/src/vnode/inc/vnodeInt.h +++ b/src/vnode/inc/vnodeInt.h @@ -67,7 +67,7 @@ typedef struct { void * qMgmt; char * rootDir; tsem_t sem; - char db[TSDB_ACCT_LEN + TSDB_DB_NAME_LEN]; + char db[TSDB_ACCT_ID_LEN + TSDB_DB_NAME_LEN]; pthread_mutex_t statusMutex; } SVnodeObj; diff --git a/src/vnode/src/vnodeWrite.c b/src/vnode/src/vnodeWrite.c index 12261b838a..b1df7bc19f 100644 --- a/src/vnode/src/vnodeWrite.c +++ b/src/vnode/src/vnodeWrite.c @@ -174,7 +174,7 @@ static int32_t vnodeProcessDropTableMsg(SVnodeObj *pVnode, void *pCont, SRspRet SMDDropTableMsg *pTable = pCont; int32_t code = TSDB_CODE_SUCCESS; - vDebug("vgId:%d, table:%s, start to drop", pVnode->vgId, pTable->tableId); + vDebug("vgId:%d, table:%s, start to drop", pVnode->vgId, pTable->tableFname); STableId tableId = {.uid = htobe64(pTable->uid), .tid = htonl(pTable->tid)}; if (tsdbDropTable(pVnode->tsdb, tableId) < 0) code = terrno; @@ -197,13 +197,13 @@ static int32_t vnodeProcessDropStableMsg(SVnodeObj *pVnode, void *pCont, SRspRet SDropSTableMsg *pTable = pCont; int32_t code = TSDB_CODE_SUCCESS; - vDebug("vgId:%d, stable:%s, start to drop", pVnode->vgId, pTable->tableId); + vDebug("vgId:%d, stable:%s, start to drop", pVnode->vgId, pTable->tableFname); STableId stableId = {.uid = htobe64(pTable->uid), .tid = -1}; if (tsdbDropTable(pVnode->tsdb, stableId) < 0) code = terrno; - vDebug("vgId:%d, stable:%s, drop stable result:%s", pVnode->vgId, pTable->tableId, tstrerror(code)); + vDebug("vgId:%d, stable:%s, drop stable result:%s", pVnode->vgId, pTable->tableFname, tstrerror(code)); return code; } @@ -233,7 +233,7 @@ static SVWriteMsg *vnodeBuildVWriteMsg(SVnodeObj *pVnode, SWalHead *pHead, int32 pWrite->rpcMsg = *pRpcMsg; } - memcpy(pWrite->pHead, pHead, sizeof(SWalHead) + pHead->len); + memcpy(&pWrite->pHead, pHead, sizeof(SWalHead) + pHead->len); pWrite->pVnode = pVnode; pWrite->qtype = qtype; @@ -308,7 +308,7 @@ static void vnodeFlowCtrlMsgToWQueue(void *param, void *tmrId) { if (pVnode->flowctrlLevel <= 0) code = TSDB_CODE_VND_IS_FLOWCTRL; pWrite->processedCount++; - if (pWrite->processedCount > 100) { + if (pWrite->processedCount >= 100) { vError("vgId:%d, msg:%p, failed to process since %s, retry:%d", pVnode->vgId, pWrite, tstrerror(code), pWrite->processedCount); pWrite->processedCount = 1; diff --git a/src/wal/CMakeLists.txt b/src/wal/CMakeLists.txt index 359e09287a..681bed5425 100644 --- a/src/wal/CMakeLists.txt +++ b/src/wal/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(inc) diff --git a/src/wal/test/CMakeLists.txt b/src/wal/test/CMakeLists.txt index 6c232ce4b9..b8338b1738 100644 --- a/src/wal/test/CMakeLists.txt +++ b/src/wal/test/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX) diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index 4e7e9a87ea..57fc8b1953 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -3,7 +3,7 @@ # generate release version: # mkdir release; cd release; cmake -DCMAKE_BUILD_TYPE=Release .. -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) SET(CMAKE_C_STANDARD 11) diff --git a/tests/comparisonTest/tdengine/CMakeLists.txt b/tests/comparisonTest/tdengine/CMakeLists.txt index 990612b8c3..aaa18592ed 100644 --- a/tests/comparisonTest/tdengine/CMakeLists.txt +++ b/tests/comparisonTest/tdengine/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) IF (TD_LINUX) diff --git a/tests/examples/C#/taosdemo/README.md b/tests/examples/C#/taosdemo/README.md index 82a8dc674a..2d125fb140 100644 --- a/tests/examples/C#/taosdemo/README.md +++ b/tests/examples/C#/taosdemo/README.md @@ -10,30 +10,27 @@ run C# version taosdemo === Usage: mono taosdemo.exe [OPTION...] - --help Show usage. + --help Show usage. - -h host, The host to connect to TDengine. Default is localhost. - -p port, The TCP/IP port number to use for the connection. Default is 0. - -u user, The user name to use when connecting to the server. Default is 'root'. - -P password, The password to use when connecting to the server. Default is 'taosdata'. - -d database, Destination database. Default is 'test'. - -a replica, Set the replica parameters of the database, Default 1, min: 1, max: 5. - -m table_prefix, Table prefix name. Default is 't'. - -s sql file, The select sql file. - -M stable, Use super table. - -o outputfile, Direct output to the named file. Default is './output.txt'. - -q query_mode, Query mode--0: SYNC, 1: ASYNC. Default is SYNC. - -b type_of_cols, data_type of columns: 'INT', 'TINYINT', 'SMALLINT', 'BIGINT', 'FLOAT', 'DOUBLE', 'BINARY'. Default is 'INT'. - -w length_of_binary, The length of data_type 'BINARY'. Only applicable when type of cols is 'BINARY'. Default is 8 - -l num_of_cols_per_record, The number of columns per record. Default is 3. - -T num_of_threads, The number of threads. Default is 10. - -r num_of_records_per_req, The number of records per request. Default is 1000. - -t num_of_tables, The number of tables. Default is 1. - -n num_of_records_per_table, The number of records per table. Default is 1. - -c config_directory, Configuration directory. Default is '/etc/taos/'. - -x flag, Insert only flag. - -O order, Insert mode--0: In order, 1: Out of order. Default is in order. - -R rate, Out of order data's rate--if order=1 Default 10, min: 0, max: 50. - -D Delete data methods 0: don't delete, 1: delete by table, 2: delete by stable, 3: delete by database. - -v Print verbose output - -y Skip read key for continous test, default is not skip + -h host, The host to connect to TDengine. Default is localhost. + -p port, The TCP/IP port number to use for the connection. Default is 0. + -u user, The user name to use when connecting to the server. Default is 'root'. + -P password, The password to use when connecting to the server. Default is 'taosdata'. + -d database, Destination database. Default is 'test'. + -a replica, Set the replica parameters of the database, Default 1, min: 1, max: 5. + -m table_prefix, Table prefix name. Default is 't'. + -M stable, Use super table. + -s stable_prefix, STable prefix name. Default is 'st' + -Q query, Execute query command. set 'DEFAULT' means select * from each table + -T num_of_threads, The number of threads. Default is 10. + -r num_of_records_per_req, The number of records per request. Default is 1000. + -t num_of_tables, The number of tables. Default is 1. + -n num_of_records_per_table, The number of records per table. Default is 1. + -c config_directory, Configuration directory. Default is '/etc/taos/'. + -x flag, Insert only flag. + -O order, Insert mode--0: In order, 1: Out of order. Default is in order. + -R rate, Out of order data's rate--if order=1 Default 10, min: 0, max: 50. + -D Delete data methods 0: don't delete, 1: delete by table, 2: delete by stable, 3: delete by database. + -v Print verbose output + -g Print debug output + -y Skip read key for continous test, default is not skip diff --git a/tests/examples/C#/taosdemo/taosdemo.cs b/tests/examples/C#/taosdemo/taosdemo.cs index 7e7c18db26..df52acc99d 100644 --- a/tests/examples/C#/taosdemo/taosdemo.cs +++ b/tests/examples/C#/taosdemo/taosdemo.cs @@ -34,11 +34,12 @@ namespace TDengineDriver //sql parameters private string dbName = "db"; - private string stableName = "st"; + private string stablePrefix = "st"; private string tablePrefix = "t"; private bool isInsertOnly = false; - private int queryMode = 1; + private string query = "NONE"; + private short queryMode = 1; private long recordsPerTable = 1; private int recordsPerRequest = 1; @@ -52,12 +53,19 @@ namespace TDengineDriver private bool useStable = false; private short methodOfDelete = 0; private long numOfThreads = 1; - private long rateOfOutorder = 0; + private short rateOfOutorder = 10; private bool order = true; private bool skipReadKey = false; private bool verbose = false; + private bool debug = false; + static void HelpPrint(string arg, string desc) + { + string indent = " "; + Console.WriteLine("{0}{1}", indent, arg.PadRight(25)+desc); + } + static void PrintHelp(String[] argv) { for (int i = 0; i < argv.Length; ++i) @@ -66,59 +74,38 @@ namespace TDengineDriver { Console.WriteLine("Usage: mono taosdemo.exe [OPTION...]"); Console.WriteLine(""); - string indent = " "; - Console.WriteLine("{0}{1}", indent, "--help Show usage."); + HelpPrint("--help", "Show usage."); Console.WriteLine(""); - Console.Write("{0}{1}", indent, "-h"); - Console.Write("{0}{1}{2}\n", indent, indent, "host, The host to connect to TDengine. Default is localhost."); - Console.Write("{0}{1}", indent, "-p"); - Console.Write("{0}{1}{2}\n", indent, indent, "port, The TCP/IP port number to use for the connection. Default is 0."); - Console.Write("{0}{1}", indent, "-u"); - Console.Write("{0}{1}{2}\n", indent, indent, "user, The user name to use when connecting to the server. Default is 'root'."); - Console.Write("{0}{1}", indent, "-P"); - Console.Write("{0}{1}{2}\n", indent, indent, "password, The password to use when connecting to the server. Default is 'taosdata'."); - Console.Write("{0}{1}", indent, "-d"); - Console.Write("{0}{1}{2}\n", indent, indent, "database, Destination database. Default is 'test'."); - Console.Write("{0}{1}", indent, "-a"); - Console.Write("{0}{1}{2}\n", indent, indent, "replica, Set the replica parameters of the database, Default 1, min: 1, max: 5."); - Console.Write("{0}{1}", indent, "-m"); - Console.Write("{0}{1}{2}\n", indent, indent, "table_prefix, Table prefix name. Default is 't'."); - Console.Write("{0}{1}", indent, "-s"); - Console.Write("{0}{1}{2}\n", indent, indent, "sql file, The select sql file."); - Console.Write("{0}{1}", indent, "-M"); - Console.Write("{0}{1}{2}\n", indent, indent, "stable, Use super table."); - Console.Write("{0}{1}", indent, "-o"); - Console.Write("{0}{1}{2}\n", indent, indent, "outputfile, Direct output to the named file. Default is './output.txt'."); - Console.Write("{0}{1}", indent, "-q"); - Console.Write("{0}{1}{2}\n", indent, indent, "query_mode, Query mode--0: SYNC, 1: ASYNC. Default is SYNC."); - Console.Write("{0}{1}", indent, "-b"); - Console.Write("{0}{1}{2}\n", indent, indent, "type_of_cols, data_type of columns: 'INT', 'TINYINT', 'SMALLINT', 'BIGINT', 'FLOAT', 'DOUBLE', 'BINARY'. Default is 'INT'."); - Console.Write("{0}{1}", indent, "-w"); - Console.Write("{0}{1}{2}\n", indent, indent, "length_of_binary, The length of data_type 'BINARY'. Only applicable when type of cols is 'BINARY'. Default is 8"); - Console.Write("{0}{1}", indent, "-l"); - Console.Write("{0}{1}{2}\n", indent, indent, "num_of_cols_per_record, The number of columns per record. Default is 3."); - Console.Write("{0}{1}", indent, "-T"); - Console.Write("{0}{1}{2}\n", indent, indent, "num_of_threads, The number of threads. Default is 10."); - Console.Write("{0}{1}", indent, "-r"); - Console.Write("{0}{1}{2}\n", indent, indent, "num_of_records_per_req, The number of records per request. Default is 1000."); - Console.Write("{0}{1}", indent, "-t"); - Console.Write("{0}{1}{2}\n", indent, indent, "num_of_tables, The number of tables. Default is 1."); - Console.Write("{0}{1}", indent, "-n"); - Console.Write("{0}{1}{2}\n", indent, indent, "num_of_records_per_table, The number of records per table. Default is 1."); - Console.Write("{0}{1}", indent, "-c"); - Console.Write("{0}{1}{2}\n", indent, indent, "config_directory, Configuration directory. Default is '/etc/taos/'."); - Console.Write("{0}{1}", indent, "-x"); - Console.Write("{0}{1}{2}\n", indent, indent, "flag, Insert only flag."); - Console.Write("{0}{1}", indent, "-O"); - Console.Write("{0}{1}{2}\n", indent, indent, "order, Insert mode--0: In order, 1: Out of order. Default is in order."); - Console.Write("{0}{1}", indent, "-R"); - Console.Write("{0}{1}{2}\n", indent, indent, "rate, Out of order data's rate--if order=1 Default 10, min: 0, max: 50."); - Console.Write("{0}{1}", indent, "-D"); - Console.Write("{0}{1}{2}\n", indent, indent, "Delete data methods 0: don't delete, 1: delete by table, 2: delete by stable, 3: delete by database."); - Console.Write("{0}{1}", indent, "-v"); - Console.Write("{0}{1}{2}\n", indent, indent, "Print verbose output"); - Console.Write("{0}{1}", indent, "-y"); - Console.Write("{0}{1}{2}\n", indent, indent, "Skip read key for continous test, default is not skip"); + + HelpPrint("-h ", "host, The host to connect to TDengine. Default is localhost."); + HelpPrint("-p ", "port, The TCP/IP port number to use for the connection. Default is 0."); + HelpPrint("-u ", "user, The user name to use when connecting to the server. Default is 'root'."); + HelpPrint("-P ", "password, The password to use when connecting to the server. Default is 'taosdata'."); + HelpPrint("-d ", "database, Destination database. Default is 'test'."); + HelpPrint("-a ", "replica, Set the replica parameters of the database, Default 1, min: 1, max: 5."); + HelpPrint("-m
", "table_prefix, Table prefix name. Default is 't'."); + HelpPrint("-M", "stable, Use super table."); + HelpPrint("-s ", "stable_prefix, STable prefix name. Default is 'st'"); + HelpPrint("-Q ", "query, Execute query command. set 'DEFAULT' means select * from each table"); + /* NOT SUPPORT SO FAR + HelpPrint("-o", "outputfile, Direct output to the named file. Default is './output.txt'."); + HelpPrint("-q", "query_mode, Query mode--0: SYNC, 1: ASYNC. Default is SYNC."); + HelpPrint("-b", "type_of_cols, data_type of columns: 'INT', 'TINYINT', 'SMALLINT', 'BIGINT', 'FLOAT', 'DOUBLE', 'BINARY'. Default is 'INT'."); + HelpPrint("-w", "length_of_binary, The length of data_type 'BINARY'. Only applicable when type of cols is 'BINARY'. Default is 8"); + HelpPrint("-l", "num_of_cols_per_record, The number of columns per record. Default is 3."); + */ + HelpPrint("-T ", "num_of_threads, The number of threads. Default is 10."); + HelpPrint("-r ", "num_of_records_per_req, The number of records per request. Default is 1000."); + HelpPrint("-t ", "num_of_tables, The number of tables. Default is 1."); + HelpPrint("-n ", "num_of_records_per_table, The number of records per table. Default is 1."); + HelpPrint("-c ", "config_directory, Configuration directory. Default is '/etc/taos/'."); + HelpPrint("-x", "flag, Insert only flag."); + HelpPrint("-O", "order, Insert mode--0: In order, 1: Out of order. Default is in order."); + HelpPrint("-R ", "rate, Out of order data's rate--if order=1 Default 10, min: 0, max: 50."); + HelpPrint("-D ", "Delete data methods 0: don't delete, 1: delete by table, 2: delete by stable, 3: delete by database."); + HelpPrint("-v", "Print verbose output"); + HelpPrint("-g", "Print debug output"); + HelpPrint("-y", "Skip read key for continous test, default is not skip"); System.Environment.Exit(0); } @@ -132,49 +119,56 @@ namespace TDengineDriver user = this.GetArgumentAsString(argv, "-u", "root"); password = this.GetArgumentAsString(argv, "-P", "taosdata"); dbName = this.GetArgumentAsString(argv, "-d", "db"); - stableName = this.GetArgumentAsString(argv, "-s", "st"); + stablePrefix = this.GetArgumentAsString(argv, "-s", "st"); tablePrefix = this.GetArgumentAsString(argv, "-m", "t"); - isInsertOnly = this.GetArgumentAsFlag(argv, "-x"); - queryMode = (int)this.GetArgumentAsLong(argv, "-q", 0, 1, 0); + isInsertOnly = this.GetArgumentAsFlag(argv, "-x", true); + query = this.GetArgumentAsString(argv, "-Q", "NONE"); + queryMode = (short)this.GetArgumentAsLong(argv, "-q", 0, 1, 0); numOfTables = this.GetArgumentAsLong(argv, "-t", 1, 1000000000, 1); batchRows = this.GetArgumentAsLong(argv, "-r", 1, 10000, 1000); recordsPerTable = this.GetArgumentAsLong(argv, "-n", 1, 100000000000, 1); recordsPerRequest = (int)this.GetArgumentAsLong(argv, "-r", 1, 10000, 1); colsPerRecord = (int)this.GetArgumentAsLong(argv, "-l", 1, 1024, 3); configDir = this.GetArgumentAsString(argv, "-c", "C:/TDengine/cfg"); - useStable = this.GetArgumentAsFlag(argv, "-M"); + useStable = this.GetArgumentAsFlag(argv, "-M", true); replica = (short)this.GetArgumentAsLong(argv, "-a", 1, 5, 1); methodOfDelete = (short)this.GetArgumentAsLong(argv, "-D", 0, 3, 0); numOfThreads = (short)this.GetArgumentAsLong(argv, "-T", 1, 10000, 1); - order = this.GetArgumentAsFlag(argv, "-O"); - rateOfOutorder = this.GetArgumentAsLong(argv, "-R", 0, 100, 0); + order = this.GetArgumentAsFlag(argv, "-O", false); + rateOfOutorder = (short)this.GetArgumentAsLong(argv, "-R", 0, 50, 10); - skipReadKey = this.GetArgumentAsFlag(argv, "-y"); - verbose = this.GetArgumentAsFlag(argv, "-v"); + skipReadKey = this.GetArgumentAsFlag(argv, "-y", true); + verbose = this.GetArgumentAsFlag(argv, "-v", true); + debug = this.GetArgumentAsFlag(argv, "-g", true); - Console.Write("###################################################################\n"); - Console.Write("# Server IP: {0}\n", host); - Console.Write("# User: {0}\n", user); - Console.Write("# Password: {0}\n", password); - Console.Write("# Number of Columns per record: {0}\n", colsPerRecord); - Console.Write("# Number of Threads: {0}\n", numOfThreads); - Console.Write("# Number of Tables: {0}\n", numOfTables); - Console.Write("# Number of Data per Table: {0}\n", recordsPerTable); - Console.Write("# Records/Request: {0}\n", recordsPerRequest); - Console.Write("# Database name: {0}\n", dbName); - Console.Write("# Replica: {0}\n", replica); - Console.Write("# Use STable: {0}\n", useStable); - Console.Write("# Table prefix: {0}\n", tablePrefix); - Console.Write("# Data order: {0}\n", order); - Console.Write("# Data out of order rate: {0}\n", rateOfOutorder); - Console.Write("# Delete method: {0}\n", methodOfDelete); - Console.Write("# Query Mode: {0}\n", queryMode); - Console.Write("# Insert Only: {0}\n", isInsertOnly); - Console.Write("# Verbose output {0}\n", verbose); - Console.Write("# Test time: {0}\n", DateTime.Now.ToString("h:mm:ss tt")); + VerbosePrint ("###################################################################\n"); + VerbosePrintFormat ("# Server IP: {0}\n", host); + VerbosePrintFormat ("# User: {0}\n", user); + VerbosePrintFormat ("# Password: {0}\n", password); + VerbosePrintFormat ("# Number of Columns per record: {0}\n", colsPerRecord); + VerbosePrintFormat ("# Number of Threads: {0}\n", numOfThreads); + VerbosePrintFormat ("# Number of Tables: {0}\n", numOfTables); + VerbosePrintFormat ("# Number of records per Table: {0}\n", recordsPerTable); + VerbosePrintFormat ("# Records/Request: {0}\n", recordsPerRequest); + VerbosePrintFormat ("# Database name: {0}\n", dbName); + VerbosePrintFormat ("# Replica: {0}\n", replica); + VerbosePrintFormat ("# Use STable: {0}\n", useStable); + VerbosePrintFormat ("# Table prefix: {0}\n", tablePrefix); + if (useStable == true) + { + VerbosePrintFormat("# STable prefix: {0}\n", stablePrefix); + } + VerbosePrintFormat ("# Data order: {0}\n", order); + VerbosePrintFormat ("# Data out of order rate: {0}\n", rateOfOutorder); + VerbosePrintFormat ("# Delete method: {0}\n", methodOfDelete); + VerbosePrintFormat ("# Query command: {0}\n", query); + VerbosePrintFormat ("# Query Mode: {0}\n", queryMode); + VerbosePrintFormat ("# Insert Only: {0}\n", isInsertOnly); + VerbosePrintFormat ("# Verbose output {0}\n", verbose); + VerbosePrintFormat ("# Test time: {0}\n", DateTime.Now.ToString("h:mm:ss tt")); - Console.Write("###################################################################\n"); + VerbosePrint ("###################################################################\n"); if (skipReadKey == false) { @@ -183,17 +177,17 @@ namespace TDengineDriver } } - public bool GetArgumentAsFlag(String[] argv, String argName) + public bool GetArgumentAsFlag(String[] argv, String argName, bool defaultValue) { int argc = argv.Length; for (int i = 0; i < argc; ++i) { if (argName == argv[i]) { - return true; + return defaultValue; } } - return false; + return !defaultValue; } public long GetArgumentAsLong(String[] argv, String argName, int minVal, long maxVal, int defaultValue) @@ -210,15 +204,15 @@ namespace TDengineDriver String tmp = argv[i + 1]; if (tmp[0] == '-') { - Console.WriteLine("option {0:G} requires an argument", tmp); - ExitProgram(); + Console.WriteLine("option {0:G} requires an argument", argName); + ExitProgram(1); } long tmpVal = Convert.ToInt64(tmp); if (tmpVal < minVal || tmpVal > maxVal) { - Console.WriteLine("option {0:G} should in range [{1:G}, {2:G}]", argName, minVal, maxVal); - ExitProgram(); + Console.WriteLine("option {0:G} value should in range [{1:G}, {2:G}]", argName, minVal, maxVal); + ExitProgram(1); } return tmpVal; @@ -242,8 +236,8 @@ namespace TDengineDriver String tmp = argv[i + 1]; if (tmp[0] == '-') { - Console.WriteLine("option {0:G} requires an argument", tmp); - ExitProgram(); + Console.WriteLine("option {0:G} requires an argument", argName); + ExitProgram(1); } return tmp; } @@ -252,13 +246,18 @@ namespace TDengineDriver return defaultValue; } - static void ExitProgram() + static void CleanAndExitProgram(int ret) { TDengine.Cleanup(); - System.Environment.Exit(0); + System.Environment.Exit(ret); } - private void DebugPrintFormat(string format, params object[] parameters) + static void ExitProgram(int ret) + { + System.Environment.Exit(ret); + } + + private void VerbosePrintFormat(string format, params object[] parameters) { if (verbose == true) { @@ -266,7 +265,7 @@ namespace TDengineDriver } } - private void DebugPrint(string str) + private void VerbosePrint(string str) { if (verbose == true) { @@ -274,28 +273,44 @@ namespace TDengineDriver } } + private void DebugPrintFormat(string format, params object[] parameters) + { + if (debug == true) + { + Console.Write(format, parameters); + } + } + + private void DebugPrint(string str) + { + if (debug == true) + { + Console.Write(str); + } + } + public void InitTDengine() { TDengine.Options((int)TDengineInitOption.TDDB_OPTION_CONFIGDIR, this.configDir); TDengine.Options((int)TDengineInitOption.TDDB_OPTION_SHELL_ACTIVITY_TIMER, "60"); TDengine.Init(); - DebugPrint("TDengine Initialization finished\n"); + VerbosePrint("TDengine Initialization finished\n"); } public void ConnectTDengine() { string db = ""; - DebugPrintFormat("host:{0} user:{1}, pass:{2}; db:{3}, port:{4}\n", + VerbosePrintFormat("host:{0} user:{1}, pass:{2}; db:{3}, port:{4}\n", this.host, this.user, this.password, db, this.port); this.conn = TDengine.Connect(this.host, this.user, this.password, db, this.port); if (this.conn == IntPtr.Zero) { Console.WriteLine("Connect to TDengine failed"); - ExitProgram(); + CleanAndExitProgram(1); } else { - DebugPrint("Connect to TDengine success\n"); + VerbosePrint("Connect to TDengine success\n"); } } @@ -323,12 +338,13 @@ namespace TDengineDriver CreateTableThread createTableThread = new CreateTableThread(); createTableThread.id = i; createTableThread.verbose = verbose; + createTableThread.debug = debug; createTableThread.dbName = this.dbName; createTableThread.tablePrefix = this.tablePrefix; createTableThread.useStable = useStable; if (useStable) { - createTableThread.stableName = stableName; + createTableThread.stablePrefix = stablePrefix; } createTableThread.conn = conn; @@ -356,12 +372,12 @@ namespace TDengineDriver IntPtr res = TDengine.Query(this.conn, sql.ToString()); if (res != IntPtr.Zero) { - DebugPrint(sql.ToString() + " success\n"); + VerbosePrint(sql.ToString() + " success\n"); } else { Console.WriteLine(sql.ToString() + " failure, reason: " + TDengine.Error(res)); - ExitProgram(); + CleanAndExitProgram(1); } } @@ -373,12 +389,12 @@ namespace TDengineDriver IntPtr res = TDengine.Query(this.conn, sql.ToString()); if (res != IntPtr.Zero) { - DebugPrint(sql.ToString() + " success\n"); + VerbosePrint(sql.ToString() + " success\n"); } else { Console.WriteLine(sql.ToString() + " failure, reason: " + TDengine.Error(res)); - ExitProgram(); + CleanAndExitProgram(1); } TDengine.FreeResult(res); } @@ -389,17 +405,17 @@ namespace TDengineDriver sql.Clear(); sql.Append("CREATE TABLE IF NOT EXISTS "). - Append(this.dbName).Append(".").Append(this.stableName). + Append(this.dbName).Append(".").Append(this.stablePrefix). Append("(ts timestamp, v1 bool, v2 tinyint, v3 smallint, v4 int, v5 bigint, v6 float, v7 double, v8 binary(10), v9 nchar(10)) tags(t1 int)"); IntPtr res = TDengine.Query(this.conn, sql.ToString()); if (res != IntPtr.Zero) { - DebugPrint(sql.ToString() + " success\n"); + VerbosePrint(sql.ToString() + " success\n"); } else { Console.WriteLine(sql.ToString() + " failure, reason: " + TDengine.Error(res)); - ExitProgram(); + CleanAndExitProgram(1); } TDengine.FreeResult(res); } @@ -431,11 +447,14 @@ namespace TDengineDriver insertThread.batchRows = batchRows; insertThread.numOfTables = numOfTables; insertThread.verbose = verbose; + insertThread.debug = debug; insertThread.dbName = this.dbName; insertThread.tablePrefix = this.tablePrefix; + insertThread.order = this.order; + insertThread.rateOfOutorder = this.rateOfOutorder; if (useStable) { - // insertThread.stableName = stableName; + insertThread.stablePrefix = stablePrefix; } insertThread.conn = conn; @@ -458,33 +477,43 @@ namespace TDengineDriver public void ExecuteQuery() { - // System.DateTime start = new System.DateTime(); long queryRows = 0; - for (int i = 0; i < 1/*this.numOfTables*/; ++i) + for (int i = 0; i < this.numOfTables; ++i) { - String sql = "select * from " + this.dbName + "." + tablePrefix + i; - // Console.WriteLine(sql); + string sql; + + if (query == "DEFAULT") + { + sql = "select * from " + this.dbName + "." + tablePrefix + i; + } + else + { + sql = query; + } + DebugPrintFormat("query: {0}, sql:{1}\n", query, sql); IntPtr res = TDengine.Query(conn, sql); + DebugPrintFormat("res: {0}\n", res); if (res == IntPtr.Zero) { Console.WriteLine(sql + " failure, reason: " + TDengine.Error(res)); - ExitProgram(); + CleanAndExitProgram(1); } int fieldCount = TDengine.FieldCount(res); - // Console.WriteLine("field count: " + fieldCount); + DebugPrint("field count: " + fieldCount + "\n"); List metas = TDengine.FetchFields(res); for (int j = 0; j < metas.Count; j++) { TDengineMeta meta = (TDengineMeta)metas[j]; - // Console.WriteLine("index:" + j + ", type:" + meta.type + ", typename:" + meta.TypeName() + ", name:" + meta.name + ", size:" + meta.size); + DebugPrint("index:" + j + ", type:" + meta.type + ", typename:" + meta.TypeName() + ", name:" + meta.name + ", size:" + meta.size + "\n"); } IntPtr rowdata; StringBuilder builder = new StringBuilder(); + while ((rowdata = TDengine.FetchRows(res)) != IntPtr.Zero) { queryRows++; @@ -548,10 +577,7 @@ namespace TDengineDriver } builder.Append("---"); - if (queryRows <= 10) - { - Console.WriteLine(builder.ToString()); - } + VerbosePrint(builder.ToString() + "\n"); builder.Clear(); } @@ -563,13 +589,6 @@ namespace TDengineDriver TDengine.FreeResult(res); } - /* - System.DateTime end = new System.DateTime(); - TimeSpan ts = end - start; - - Console.Write("Total {0:G} rows inserted, {1:G} rows query, time spend {2:G} seconds.\n" - , this.rowsInserted, queryRows, ts.TotalSeconds); - */ } public void CloseConnection() @@ -610,13 +629,24 @@ namespace TDengineDriver watch.Stop(); double elapsedMs = watch.Elapsed.TotalMilliseconds; - Console.WriteLine("Spent {0} seconds to insert {1} records with {2} record(s) per request: {3} records/second", + Console.WriteLine("C# taosdemo: Spent {0} seconds to insert {1} records with {2} record(s) per request: {3} records/second", elapsedMs / 1000, tester.recordsPerTable * tester.numOfTables, tester.batchRows, (tester.recordsPerTable * tester.numOfTables * 1000) / elapsedMs); - tester.ExecuteQuery(); + tester.DebugPrintFormat("query command:{0}\n", tester.query); + if (tester.query != "NONE") + { + watch = Stopwatch.StartNew(); + tester.ExecuteQuery(); + watch.Stop(); + elapsedMs = watch.Elapsed.TotalMilliseconds; + Console.WriteLine("C# taosdemo: Spent {0} seconds to query {1} records.\n", + elapsedMs/1000, + tester.recordsPerTable * tester.numOfTables + ); + } tester.CloseConnection(); Console.WriteLine("End."); @@ -630,13 +660,16 @@ namespace TDengineDriver public string dbName { set; get; } public IntPtr conn { set; get; } public string tablePrefix { set; get; } - // public string stableName { set; get; } + public string stablePrefix { set; get; } public long recordsPerTable { set; get; } public long batchRows { set; get; } public long numOfTables { set; get; } public bool verbose { set; get; } + public bool debug { set; get; } + public bool order { set; get; } + public short rateOfOutorder { set; get; } - private void DebugPrintFormat(string format, params object[] parameters) + private void VerbosePrintFormat(string format, params object[] parameters) { if (verbose == true) { @@ -644,7 +677,7 @@ namespace TDengineDriver } } - private void DebugPrint(string str) + private void VerbosePrint(string str) { if (verbose == true) { @@ -652,9 +685,25 @@ namespace TDengineDriver } } + private void DebugPrintFormat(string format, params object[] parameters) + { + if (debug == true) + { + Console.Write(format, parameters); + } + } + + private void DebugPrint(string str) + { + if (debug == true) + { + Console.Write(str); + } + } + public void ThreadMain() { - DebugPrintFormat("InsertDataThread {0} from {1} to {2}\n", id, start, end); + VerbosePrintFormat("InsertDataThread {0} from {1} to {2}\n", id, start, end); StringBuilder sql = new StringBuilder(); DateTime now = DateTime.Now; @@ -663,12 +712,12 @@ namespace TDengineDriver int s = now.Second; long baseTimestamp = 1609430400000; // 2021/01/01 0:0:0 - DebugPrintFormat("beginTime is {0} + {1}h:{2}m:{3}s\n", baseTimestamp, h, m, s); + VerbosePrintFormat("beginTime is {0} + {1}h:{2}m:{3}s\n", baseTimestamp, h, m, s); long beginTimestamp = baseTimestamp + ((h*60 + m) * 60 + s) * 1000; + Random random = new Random(); long rowsInserted = 0; - // System.DateTime startTime = new System.DateTime(); long i = 0; while (i < recordsPerTable) { @@ -686,8 +735,25 @@ namespace TDengineDriver } for (int batch = 0; batch < batchRows; ++batch) { + long writeTimeStamp = beginTimestamp + i + batch; + int rnd = 100; + if (this.order == false) + { + rnd = random.Next(1, 100); + if (rnd <= this.rateOfOutorder) + { + writeTimeStamp = writeTimeStamp + rnd * 10000; + DebugPrint("### "); + } + DebugPrintFormat("order:{0} rnd:{1} timestamp:{2}\n", this.order, rnd, writeTimeStamp); + } + else + { + DebugPrintFormat("order:{0} timestamp:{1}\n", this.order, writeTimeStamp); + } + sql.Append("(") - .Append(beginTimestamp + i + batch) + .Append(writeTimeStamp) .Append(", 1, 2, 3,") .Append(i + batch) .Append(", 5, 6, 7, 'abc', 'def')"); @@ -696,7 +762,7 @@ namespace TDengineDriver IntPtr res = TDengine.Query(this.conn, sql.ToString()); if (res == IntPtr.Zero) { - DebugPrint(sql.ToString() + " failure, reason: " + TDengine.Error(res) + "\n"); + VerbosePrint(sql.ToString() + " failure, reason: " + TDengine.Error(res) + "\n"); } inserted += this.batchRows; @@ -723,11 +789,12 @@ namespace TDengineDriver public string dbName { set; get; } public IntPtr conn { set; get; } public string tablePrefix { set; get; } - public string stableName { set; get; } + public string stablePrefix { set; get; } public bool verbose { set; get; } + public bool debug { set; get; } public bool useStable { set; get; } - private void DebugPrintFormat(string format, params object[] parameters) + private void VerbosePrintFormat(string format, params object[] parameters) { if (verbose == true) { @@ -735,7 +802,7 @@ namespace TDengineDriver } } - private void DebugPrint(string str) + private void VerbosePrint(string str) { if (verbose == true) { @@ -743,9 +810,17 @@ namespace TDengineDriver } } + private void DebugPrintFormat(string format, params object[] parameters) + { + if (debug == true) + { + Console.Write(format, parameters); + } + } + public void ThreadMain() { - DebugPrintFormat("CreateTable {0} from {1} to {2}\n", id, start, end); + VerbosePrintFormat("CreateTable {0} from {1} to {2}\n", id, start, end); StringBuilder sql = new StringBuilder(); @@ -756,7 +831,7 @@ namespace TDengineDriver Append(this.dbName).Append(".").Append(this.tablePrefix).Append(tableId); if (useStable == true) { - sql = sql.Append(" USING ").Append(this.dbName).Append(".").Append(this.stableName). + sql = sql.Append(" USING ").Append(this.dbName).Append(".").Append(this.stablePrefix). Append(" TAGS(").Append(tableId).Append(")"); } else @@ -766,12 +841,12 @@ namespace TDengineDriver IntPtr res = TDengine.Query(this.conn, sql.ToString()); if (res != IntPtr.Zero) { - DebugPrint(sql.ToString() + " success\n"); + VerbosePrint(sql.ToString() + " success\n"); } else { - DebugPrint(sql.ToString() + " failure, reason: " + TDengine.Error(res) + "\n"); - ExitProgram(); + VerbosePrint(sql.ToString() + " failure, reason: " + TDengine.Error(res) + "\n"); + CleanAndExitProgram(1); } TDengine.FreeResult(res); } diff --git a/tests/examples/JDBC/taosdemo/readme.md b/tests/examples/JDBC/taosdemo/readme.md index a4b6e29769..123affc71a 100644 --- a/tests/examples/JDBC/taosdemo/readme.md +++ b/tests/examples/JDBC/taosdemo/readme.md @@ -1,3 +1,6 @@ + + 需求: 1. 可以读lowa的配置文件 -2. 支持对JNI方式和Restful方式的taos-driver \ No newline at end of file +2. 支持JDBC-JNI和JDBC-restful +3. 读取配置文件,持续执行查询 \ No newline at end of file diff --git a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/TaosDemoApplication.java b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/TaosDemoApplication.java index b9a22a1ef7..4dc49fd37b 100644 --- a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/TaosDemoApplication.java +++ b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/TaosDemoApplication.java @@ -19,14 +19,13 @@ import java.util.Map; public class TaosDemoApplication { - private static Logger logger = Logger.getLogger(TaosDemoApplication.class); + private static final Logger logger = Logger.getLogger(TaosDemoApplication.class); public static void main(String[] args) throws IOException { // 读配置参数 JdbcTaosdemoConfig config = new JdbcTaosdemoConfig(args); boolean isHelp = Arrays.asList(args).contains("--help"); if (isHelp || config.host == null || config.host.isEmpty()) { -// if (isHelp) { JdbcTaosdemoConfig.printHelp(); System.exit(0); } @@ -75,7 +74,7 @@ public class TaosDemoApplication { } } end = System.currentTimeMillis(); - logger.error(">>> create table time cost : " + (end - start) + " ms."); + logger.info(">>> create table time cost : " + (end - start) + " ms."); /**********************************************************************************/ // 插入 long tableSize = config.numOfTables; @@ -90,7 +89,7 @@ public class TaosDemoApplication { // multi threads to insert int affectedRows = subTableService.insertMultiThreads(superTableMeta, threadSize, tableSize, startTime, gap, config); end = System.currentTimeMillis(); - logger.error("insert " + affectedRows + " rows, time cost: " + (end - start) + " ms"); + logger.info("insert " + affectedRows + " rows, time cost: " + (end - start) + " ms"); /**********************************************************************************/ // 删除表 if (config.dropTable) { @@ -108,5 +107,4 @@ public class TaosDemoApplication { return startTime; } - } diff --git a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/DatabaseMapperImpl.java b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/DatabaseMapperImpl.java index 69bae160f6..421a2dea1f 100644 --- a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/DatabaseMapperImpl.java +++ b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/DatabaseMapperImpl.java @@ -21,27 +21,27 @@ public class DatabaseMapperImpl implements DatabaseMapper { public void createDatabase(String dbname) { String sql = "create database if not exists " + dbname; jdbcTemplate.execute(sql); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); } @Override public void dropDatabase(String dbname) { String sql = "drop database if exists " + dbname; jdbcTemplate.update(sql); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); } @Override public void createDatabaseWithParameters(Map map) { String sql = SqlSpeller.createDatabase(map); jdbcTemplate.execute(sql); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); } @Override public void useDatabase(String dbname) { String sql = "use " + dbname; jdbcTemplate.execute(sql); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); } } diff --git a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SubTableMapperImpl.java b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SubTableMapperImpl.java index e3a6691430..90b0990a2b 100644 --- a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SubTableMapperImpl.java +++ b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SubTableMapperImpl.java @@ -21,14 +21,14 @@ public class SubTableMapperImpl implements SubTableMapper { @Override public void createUsingSuperTable(SubTableMeta subTableMeta) { String sql = SqlSpeller.createTableUsingSuperTable(subTableMeta); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); jdbcTemplate.execute(sql); } @Override public int insertOneTableMultiValues(SubTableValue subTableValue) { String sql = SqlSpeller.insertOneTableMultiValues(subTableValue); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); int affectRows = 0; try { @@ -42,7 +42,7 @@ public class SubTableMapperImpl implements SubTableMapper { @Override public int insertOneTableMultiValuesUsingSuperTable(SubTableValue subTableValue) { String sql = SqlSpeller.insertOneTableMultiValuesUsingSuperTable(subTableValue); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); int affectRows = 0; try { @@ -56,7 +56,7 @@ public class SubTableMapperImpl implements SubTableMapper { @Override public int insertMultiTableMultiValues(List tables) { String sql = SqlSpeller.insertMultiSubTableMultiValues(tables); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); int affectRows = 0; try { affectRows = jdbcTemplate.update(sql); @@ -69,7 +69,7 @@ public class SubTableMapperImpl implements SubTableMapper { @Override public int insertMultiTableMultiValuesUsingSuperTable(List tables) { String sql = SqlSpeller.insertMultiTableMultiValuesUsingSuperTable(tables); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); int affectRows = 0; try { affectRows = jdbcTemplate.update(sql); diff --git a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SuperTableMapperImpl.java b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SuperTableMapperImpl.java index a293de5100..efa9a1f39e 100644 --- a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SuperTableMapperImpl.java +++ b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/SuperTableMapperImpl.java @@ -18,14 +18,14 @@ public class SuperTableMapperImpl implements SuperTableMapper { @Override public void createSuperTable(SuperTableMeta tableMetadata) { String sql = SqlSpeller.createSuperTable(tableMetadata); - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); jdbcTemplate.execute(sql); } @Override public void dropSuperTable(String database, String name) { String sql = "drop table if exists " + database + "." + name; - logger.info("SQL >>> " + sql); + logger.debug("SQL >>> " + sql); jdbcTemplate.execute(sql); } } diff --git a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/TableMapperImpl.java b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/TableMapperImpl.java index 77415619f0..b049fbe197 100644 --- a/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/TableMapperImpl.java +++ b/tests/examples/JDBC/taosdemo/src/main/java/com/taosdata/taosdemo/dao/TableMapperImpl.java @@ -1,43 +1,49 @@ package com.taosdata.taosdemo.dao; -import com.taosdata.taosdemo.dao.TableMapper; import com.taosdata.taosdemo.domain.TableMeta; import com.taosdata.taosdemo.domain.TableValue; import com.taosdata.taosdemo.utils.SqlSpeller; +import org.apache.log4j.Logger; import org.springframework.jdbc.core.JdbcTemplate; import java.util.List; public class TableMapperImpl implements TableMapper { + private static final Logger logger = Logger.getLogger(TableMapperImpl.class); private JdbcTemplate template; @Override public void create(TableMeta tableMeta) { String sql = SqlSpeller.createTable(tableMeta); + logger.debug("SQL >>> " + sql); template.execute(sql); } @Override public int insertOneTableMultiValues(TableValue values) { String sql = SqlSpeller.insertOneTableMultiValues(values); + logger.debug("SQL >>> " + sql); return template.update(sql); } @Override public int insertOneTableMultiValuesWithColumns(TableValue values) { String sql = SqlSpeller.insertOneTableMultiValuesWithColumns(values); + logger.debug("SQL >>> " + sql); return template.update(sql); } @Override public int insertMultiTableMultiValues(List tables) { String sql = SqlSpeller.insertMultiTableMultiValues(tables); + logger.debug("SQL >>> " + sql); return template.update(sql); } @Override public int insertMultiTableMultiValuesWithColumns(List tables) { String sql = SqlSpeller.insertMultiTableMultiValuesWithColumns(tables); + logger.debug("SQL >>> " + sql); return template.update(sql); } } diff --git a/tests/examples/JDBC/taosdemo/src/main/resources/log4j.properties b/tests/examples/JDBC/taosdemo/src/main/resources/log4j.properties index b2a9586ea7..352545854d 100644 --- a/tests/examples/JDBC/taosdemo/src/main/resources/log4j.properties +++ b/tests/examples/JDBC/taosdemo/src/main/resources/log4j.properties @@ -1,5 +1,5 @@ ### 设置### -log4j.rootLogger=error,stdout +log4j.rootLogger=info,stdout ### 输出信息到控制抬 ### log4j.appender.stdout=org.apache.log4j.ConsoleAppender log4j.appender.stdout.Target=System.out diff --git a/tests/examples/c/asyncdemo.c b/tests/examples/c/asyncdemo.c index c6cc89b31d..be3a908f11 100644 --- a/tests/examples/c/asyncdemo.c +++ b/tests/examples/c/asyncdemo.c @@ -261,9 +261,6 @@ void taos_select_call_back(void *param, TAOS_RES *tres, int code) if (code == 0 && tres) { // asynchronous API to fetch a batch of records taos_fetch_rows_a(tres, taos_retrieve_call_back, pTable); - - // taos_fetch_row_a is a less efficient way to retrieve records since it call back app for every row - // taos_fetch_row_a(tres, taos_fetch_row_call_back, pTable); } else { printf("%s select failed, code:%d\n", pTable->name, code); diff --git a/tests/examples/c/demo.c b/tests/examples/c/demo.c index 54e81d33b9..9cbcee45a2 100644 --- a/tests/examples/c/demo.c +++ b/tests/examples/c/demo.c @@ -93,15 +93,15 @@ void Test(TAOS *taos, char *qstr, int index) { // if (taos_query(taos, qstr)) { // printf("insert row: %i, reason:%s\n", i, taos_errstr(taos)); // } - TAOS_RES *result = taos_query(taos, qstr); - if (result) { + TAOS_RES *result1 = taos_query(taos, qstr); + if (result1) { printf("insert row: %i\n", i); } else { printf("failed to insert row: %i, reason:%s\n", i, "null result"/*taos_errstr(result)*/); - taos_free_result(result); + taos_free_result(result1); exit(1); } - taos_free_result(result); + taos_free_result(result1); } printf("success to insert rows, total %d rows\n", i); diff --git a/tests/perftest-scripts/perftest-taosdemo.sh b/tests/perftest-scripts/perftest-taosdemo.sh index ae9e8dd737..dffa251ef7 100755 --- a/tests/perftest-scripts/perftest-taosdemo.sh +++ b/tests/perftest-scripts/perftest-taosdemo.sh @@ -16,6 +16,9 @@ fi logDir=`grep "^logDir" /etc/taos/taos.cfg | awk '{print $2}'` dataDir=`grep "^dataDir" /etc/taos/taos.cfg | awk '{print $2}'` +[ -z "$logDir" ] && logDir="/var/log/taos" +[ -z "$dataDir" ] && dataDir="/var/lib/taos" + # Coloured Echoes function red_echo { echo -e "\033[31m$@\033[0m"; } function green_echo { echo -e "\033[32m$@\033[0m"; } diff --git a/tests/perftest-scripts/perftest-tsdb-compare-13d.sh b/tests/perftest-scripts/perftest-tsdb-compare-13d.sh index 110ab9e5fa..3f56a048e9 100755 --- a/tests/perftest-scripts/perftest-tsdb-compare-13d.sh +++ b/tests/perftest-scripts/perftest-tsdb-compare-13d.sh @@ -16,6 +16,9 @@ fi logDir=`grep "^logDir" /etc/taos/taos.cfg | awk '{print $2}'` dataDir=`grep "^dataDir" /etc/taos/taos.cfg | awk '{print $2}'` +[ -z "$logDir" ] && logDir="/var/log/taos" +[ -z "$dataDir" ] && dataDir="/var/lib/taos" + # Coloured Echoes # function red_echo { echo -e "\033[31m$@\033[0m"; } # function green_echo { echo -e "\033[32m$@\033[0m"; } # diff --git a/tests/perftest-scripts/perftest-tsdb-compare-1d.sh b/tests/perftest-scripts/perftest-tsdb-compare-1d.sh index 9e8bc697bc..29e72d7b3f 100755 --- a/tests/perftest-scripts/perftest-tsdb-compare-1d.sh +++ b/tests/perftest-scripts/perftest-tsdb-compare-1d.sh @@ -16,6 +16,9 @@ fi logDir=`grep "^logDir" /etc/taos/taos.cfg | awk '{print $2}'` dataDir=`grep "^dataDir" /etc/taos/taos.cfg | awk '{print $2}'` +[ -z "$logDir" ] && logDir="/var/log/taos" +[ -z "$dataDir" ] && dataDir="/var/lib/taos" + # Coloured Echoes # function red_echo { echo -e "\033[31m$@\033[0m"; } # function green_echo { echo -e "\033[32m$@\033[0m"; } # diff --git a/tests/perftest-scripts/perftest-tsdb-compare-var10k-int100s.sh b/tests/perftest-scripts/perftest-tsdb-compare-var10k-int100s.sh index 5fc5b9d03a..3bc63b831b 100755 --- a/tests/perftest-scripts/perftest-tsdb-compare-var10k-int100s.sh +++ b/tests/perftest-scripts/perftest-tsdb-compare-var10k-int100s.sh @@ -16,6 +16,9 @@ fi logDir=`grep "^logDir" /etc/taos/taos.cfg | awk '{print $2}'` dataDir=`grep "^dataDir" /etc/taos/taos.cfg | awk '{print $2}'` +[ -z "$logDir" ] && logDir="/var/log/taos" +[ -z "$dataDir" ] && dataDir="/var/lib/taos" + # Coloured Echoes # function red_echo { echo -e "\033[31m$@\033[0m"; } # function green_echo { echo -e "\033[32m$@\033[0m"; } # diff --git a/tests/perftest-scripts/perftest-tsdb-compare-var10k-int10s.sh b/tests/perftest-scripts/perftest-tsdb-compare-var10k-int10s.sh index bafa04f174..566479c967 100755 --- a/tests/perftest-scripts/perftest-tsdb-compare-var10k-int10s.sh +++ b/tests/perftest-scripts/perftest-tsdb-compare-var10k-int10s.sh @@ -16,6 +16,9 @@ fi logDir=`grep "^logDir" /etc/taos/taos.cfg | awk '{print $2}'` dataDir=`grep "^dataDir" /etc/taos/taos.cfg | awk '{print $2}'` +[ -z "$logDir" ] && logDir="/var/log/taos" +[ -z "$dataDir" ] && dataDir="/var/lib/taos" + # Coloured Echoes # function red_echo { echo -e "\033[31m$@\033[0m"; } # function green_echo { echo -e "\033[32m$@\033[0m"; } # diff --git a/tests/pytest/alter/alter_table.py b/tests/pytest/alter/alter_table.py index f1d1da2990..2982492f65 100644 --- a/tests/pytest/alter/alter_table.py +++ b/tests/pytest/alter/alter_table.py @@ -131,7 +131,7 @@ class TDTestCase: tdSql.execute("alter table t0 set tag t1=2.1") tdSql.query("show tables") - tdSql.checkRows(1) + tdSql.checkRows(2) def stop(self): tdSql.close() diff --git a/tests/pytest/cluster/clusterEnvSetup/Dockerfile b/tests/pytest/cluster/clusterEnvSetup/Dockerfile new file mode 100644 index 0000000000..b699e8a23f --- /dev/null +++ b/tests/pytest/cluster/clusterEnvSetup/Dockerfile @@ -0,0 +1,36 @@ +FROM ubuntu:latest AS builder + +ARG PACKAGE=TDengine-server-1.6.5.10-Linux-x64.tar.gz +ARG EXTRACTDIR=TDengine-enterprise-server +ARG CONTENT=taos.tar.gz + +WORKDIR /root + +COPY ${PACKAGE} . + +RUN tar -zxf ${PACKAGE} +RUN mv ${EXTRACTDIR}/driver ./lib +RUN tar -zxf ${EXTRACTDIR}/${CONTENT} + +FROM ubuntu:latest + +WORKDIR /root + +RUN apt-get update +RUN apt-get install -y vim tmux net-tools +RUN echo 'alias ll="ls -l --color=auto"' >> /root/.bashrc + +COPY --from=builder /root/bin/taosd /usr/bin +COPY --from=builder /root/bin/taos /usr/bin +COPY --from=builder /root/cfg/taos.cfg /etc/taos/ +COPY --from=builder /root/lib/libtaos.so.* /usr/lib/libtaos.so.1 + +ENV LD_LIBRARY_PATH="$LD_LIBRARY_PATH:/usr/lib" +ENV LC_CTYPE=en_US.UTF-8 +ENV LANG=en_US.UTF-8 + +EXPOSE 6030-6041/tcp 6060/tcp 6030-6039/udp + +# VOLUME [ "/var/lib/taos", "/var/log/taos", "/etc/taos" ] + +CMD [ "bash" ] diff --git a/tests/pytest/cluster/clusterEnvSetup/buildClusterEnv.sh b/tests/pytest/cluster/clusterEnvSetup/buildClusterEnv.sh new file mode 100755 index 0000000000..e0788ef329 --- /dev/null +++ b/tests/pytest/cluster/clusterEnvSetup/buildClusterEnv.sh @@ -0,0 +1,102 @@ +#!/bin/bash +echo "Executing buildClusterEnv.sh" +DOCKER_DIR=/data +CURR_DIR=`pwd` + +if [ $# != 4 ]; then + echo "argument list need input : " + echo " -n numOfNodes" + echo " -v version" + exit 1 +fi + +NUM_OF_NODES= +VERSION= +while getopts "n:v:" arg +do + case $arg in + n) + NUM_OF_NODES=$OPTARG + ;; + v) + VERSION=$OPTARG + ;; + ?) + echo "unkonwn argument" + ;; + esac +done + + +function createDIR { + for i in {1.. $2} + do + mkdir -p /data/node$i/data + mkdir -p /data/node$i/log + mkdir -p /data/node$i/cfg + done +} + +function cleanEnv { + for i in {1..3} + do + echo /data/node$i/data/* + rm -rf /data/node$i/data/* + echo /data/node$i/log/* + rm -rf /data/node$i/log/* + done +} + +function prepareBuild { + + if [ -d $CURR_DIR/../../../../release ]; then + echo release exists + rm -rf $CURR_DIR/../../../../release/* + fi + + cd $CURR_DIR/../../../../packaging + ./release.sh -v edge -n $VERSION >> /dev/null + + if [ ! -f $CURR_DIR/../../../../release/TDengine-server-$VERSION-Linux-x64.tar.gz ]; then + echo "no TDengine install package found" + exit 1 + fi + + cd $CURR_DIR/../../../../release + mv TDengine-server-$VERSION-Linux-x64.tar.gz $DOCKER_DIR + + rm -rf $DOCKER_DIR/*.yml + cd $CURR_DIR + + cp docker-compose.yml $DOCKER_DIR + cp Dockerfile $DOCKER_DIR + + if [ $NUM_OF_NODES -eq 4 ]; then + cp ../node4.yml $DOCKER_DIR + fi + + if [ $NUM_OF_NODES -eq 5 ]; then + cp ../node5.yml $DOCKER_DIR + fi +} + +function clusterUp { + + cd $DOCKER_DIR + + if [ $NUM_OF_NODES -eq 3 ]; then + PACKAGE=TDengine-server-$VERSION-Linux-x64.tar.gz DIR=TDengine-server-$VERSION docker-compose up -d + fi + + if [ $NUM_OF_NODES -eq 4 ]; then + PACKAGE=TDengine-server-$VERSION-Linux-x64.tar.gz DIR=TDengine-server-$VERSION docker-compose -f docker-compose.yml -f node4.yml up -d + fi + + if [ $NUM_OF_NODES -eq 5 ]; then + PACKAGE=TDengine-server-$VERSION-Linux-x64.tar.gz DIR=TDengine-server-$VERSION docker-compose -f docker-compose.yml -f node4.yml -f node5.yml up -d + fi +} + +cleanEnv +# prepareBuild +# clusterUp \ No newline at end of file diff --git a/tests/pytest/cluster/clusterEnvSetup/docker-compose.yml b/tests/pytest/cluster/clusterEnvSetup/docker-compose.yml new file mode 100644 index 0000000000..c8498b36d4 --- /dev/null +++ b/tests/pytest/cluster/clusterEnvSetup/docker-compose.yml @@ -0,0 +1,127 @@ +version: '3.7' + +services: + td2.0-node1: + build: + context: . + args: + - PACKAGE=${PACKAGE} + - EXTRACTDIR=${DIR} + image: 'tdengine:2.0.13.1' + container_name: 'td2.0-node1' + cap_add: + - ALL + stdin_open: true + tty: true + environment: + TZ: "Asia/Shanghai" + command: > + sh -c "ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && + echo $TZ > /etc/timezone && + exec my-main-application" + volumes: + # bind data directory + - type: bind + source: /data/node1/data + target: /var/lib/taos + # bind log directory + - type: bind + source: /data/node1/log + target: /var/log/taos + # bind configuration + - type: bind + source: /data/node1/cfg + target: /etc/taos + - type: bind + source: /data + target: /root + networks: + taos_update_net: + ipv4_address: 172.27.0.7 + command: taosd + + td2.0-node2: + build: + context: . + args: + - PACKAGE=${PACKAGE} + - EXTRACTDIR=${DIR} + image: 'tdengine:2.0.13.1' + container_name: 'td2.0-node2' + cap_add: + - ALL + stdin_open: true + tty: true + environment: + TZ: "Asia/Shanghai" + command: > + sh -c "ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && + echo $TZ > /etc/timezone && + exec my-main-application" + volumes: + # bind data directory + - type: bind + source: /data/node2/data + target: /var/lib/taos + # bind log directory + - type: bind + source: /data/node2/log + target: /var/log/taos + # bind configuration + - type: bind + source: /data/node2/cfg + target: /etc/taos + - type: bind + source: /data + target: /root + networks: + taos_update_net: + ipv4_address: 172.27.0.8 + command: taosd + + td2.0-node3: + build: + context: . + args: + - PACKAGE=${PACKAGE} + - EXTRACTDIR=${DIR} + image: 'tdengine:2.0.13.1' + container_name: 'td2.0-node3' + cap_add: + - ALL + stdin_open: true + tty: true + environment: + TZ: "Asia/Shanghai" + command: > + sh -c "ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && + echo $TZ > /etc/timezone && + exec my-main-application" + volumes: + # bind data directory + - type: bind + source: /data/node3/data + target: /var/lib/taos + # bind log directory + - type: bind + source: /data/node3/log + target: /var/log/taos + # bind configuration + - type: bind + source: /data/node3/cfg + target: /etc/taos + - type: bind + source: /data + target: /root + networks: + taos_update_net: + ipv4_address: 172.27.0.9 + command: taosd + +networks: + taos_update_net: +# external: true + ipam: + driver: default + config: + - subnet: "172.27.0.0/24" diff --git a/tests/pytest/cluster/clusterEnvSetup/node4.yml b/tests/pytest/cluster/clusterEnvSetup/node4.yml new file mode 100644 index 0000000000..542dc4cac1 --- /dev/null +++ b/tests/pytest/cluster/clusterEnvSetup/node4.yml @@ -0,0 +1,41 @@ +version: '3.7' + +services: + td2.0-node4: + build: + context: . + args: + - PACKAGE=${PACKAGE} + - EXTRACTDIR=${DIR} + image: 'tdengine:2.0.13.1' + container_name: 'td2.0-node4' + cap_add: + - ALL + stdin_open: true + tty: true + environment: + TZ: "Asia/Shanghai" + command: > + sh -c "ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && + echo $TZ > /etc/timezone && + exec my-main-application" + volumes: + # bind data directory + - type: bind + source: /data/node4/data + target: /var/lib/taos + # bind log directory + - type: bind + source: /data/node4/log + target: /var/log/taos + # bind configuration + - type: bind + source: /data/node4/cfg + target: /etc/taos + - type: bind + source: /data + target: /root + networks: + taos_update_net: + ipv4_address: 172.27.0.10 + command: taosd \ No newline at end of file diff --git a/tests/pytest/cluster/clusterEnvSetup/node5.yml b/tests/pytest/cluster/clusterEnvSetup/node5.yml new file mode 100644 index 0000000000..832cc65e08 --- /dev/null +++ b/tests/pytest/cluster/clusterEnvSetup/node5.yml @@ -0,0 +1,41 @@ +version: '3.7' + +services: + td2.0-node5: + build: + context: . + args: + - PACKAGE=${PACKAGE} + - EXTRACTDIR=${DIR} + image: 'tdengine:2.0.13.1' + container_name: 'td2.0-node5' + cap_add: + - ALL + stdin_open: true + tty: true + environment: + TZ: "Asia/Shanghai" + command: > + sh -c "ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && + echo $TZ > /etc/timezone && + exec my-main-application" + volumes: + # bind data directory + - type: bind + source: /data/node5/data + target: /var/lib/taos + # bind log directory + - type: bind + source: /data/node5/log + target: /var/log/taos + # bind configuration + - type: bind + source: /data/node5/cfg + target: /etc/taos + - type: bind + source: /data + target: /root + networks: + taos_update_net: + ipv4_address: 172.27.0.11 + command: taosd \ No newline at end of file diff --git a/tests/pytest/fulltest.sh b/tests/pytest/fulltest.sh index cb233f85b8..d9bc185b6c 100755 --- a/tests/pytest/fulltest.sh +++ b/tests/pytest/fulltest.sh @@ -190,6 +190,7 @@ python3 ./test.py -f stream/table_n.py #alter table python3 ./test.py -f alter/alter_table_crash.py +python3 ./test.py -f alter/alter_table.py # client python3 ./test.py -f client/client.py diff --git a/tests/pytest/query/query.py b/tests/pytest/query/query.py index d0750ac4a5..756aa0eda9 100644 --- a/tests/pytest/query/query.py +++ b/tests/pytest/query/query.py @@ -23,6 +23,8 @@ class TDTestCase: tdLog.debug("start to execute %s" % __file__) tdSql.init(conn.cursor(), logSql) + self.ts = 1538548685000 + def run(self): tdSql.prepare() @@ -77,7 +79,37 @@ class TDTestCase: tdSql.checkRows(1) tdSql.checkData(0, 0, 1) + ## 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) def stop(self): tdSql.close() diff --git a/tests/pytest/stream/new.py b/tests/pytest/stream/new.py index 12ec6d4507..70f300e937 100644 --- a/tests/pytest/stream/new.py +++ b/tests/pytest/stream/new.py @@ -43,7 +43,7 @@ class TDTestCase: tdLog.info("=============== step3") start = time.time() tdSql.waitedQuery("select * from st", 1, 120) - delay = int(time.time() - start) + 20 + delay = int(time.time() - start) + 80 v = tdSql.getData(0, 3) if v >= 51: tdLog.exit("value is %d, which is larger than 51" % v) diff --git a/tests/pytest/table/create.py b/tests/pytest/table/create.py index a0991d674a..ecd4d01141 100644 --- a/tests/pytest/table/create.py +++ b/tests/pytest/table/create.py @@ -56,6 +56,12 @@ class TDTestCase: tdSql.query("show stables like 'st%' ") tdSql.checkRows(3) + # case for defect: https://jira.taosdata.com:18080/browse/TD-2693 + tdSql.execute("create database db2") + tdSql.execute("use db2") + tdSql.execute("create table stb(ts timestamp, c int) tags(t int)") + tdSql.error("insert into db2.tb6 using db2.stb tags(1) values(now 1) tb2 using db2. tags( )values(now 2)") + def stop(self): tdSql.close() tdLog.success("%s successfully executed" % __file__) diff --git a/tests/script/general/cache/new_metrics.sim b/tests/script/general/cache/new_metrics.sim index 0e304d9acb..84f9e40de3 100644 --- a/tests/script/general/cache/new_metrics.sim +++ b/tests/script/general/cache/new_metrics.sim @@ -3,7 +3,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 10 system sh/exec.sh -n dnode1 -s start sleep 3000 diff --git a/tests/script/general/cache/restart_metrics.sim b/tests/script/general/cache/restart_metrics.sim index 18c514acbf..f24768859f 100644 --- a/tests/script/general/cache/restart_metrics.sim +++ b/tests/script/general/cache/restart_metrics.sim @@ -3,7 +3,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 10 system sh/exec.sh -n dnode1 -s start sleep 3000 @@ -53,7 +52,6 @@ system sh/exec.sh -n dnode1 -s stop sleep 5000 system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 10 system sh/exec.sh -n dnode1 -s start print =============== step3 diff --git a/tests/script/general/cache/restart_table.sim b/tests/script/general/cache/restart_table.sim index c4e6c6f2ac..8697c26bc3 100644 --- a/tests/script/general/cache/restart_table.sim +++ b/tests/script/general/cache/restart_table.sim @@ -3,7 +3,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 10 system sh/exec.sh -n dnode1 -s start sleep 3000 @@ -37,7 +36,6 @@ system sh/exec.sh -n dnode1 -s stop sleep 5000 system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 10 system sh/exec.sh -n dnode1 -s start print =============== step3 diff --git a/tests/script/general/parser/alter.sim b/tests/script/general/parser/alter.sim index aec519085c..eae9b88be9 100644 --- a/tests/script/general/parser/alter.sim +++ b/tests/script/general/parser/alter.sim @@ -2,7 +2,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 3 system sh/exec.sh -n dnode1 -s start sleep 100 sql connect diff --git a/tests/script/general/parser/alter_stable.sim b/tests/script/general/parser/alter_stable.sim index 52916ebada..17fc8d984a 100644 --- a/tests/script/general/parser/alter_stable.sim +++ b/tests/script/general/parser/alter_stable.sim @@ -2,7 +2,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 3 system sh/exec.sh -n dnode1 -s start sleep 100 sql connect diff --git a/tests/script/general/parser/binary_escapeCharacter.sim b/tests/script/general/parser/binary_escapeCharacter.sim index 7c5a8f9319..dc54add763 100644 --- a/tests/script/general/parser/binary_escapeCharacter.sim +++ b/tests/script/general/parser/binary_escapeCharacter.sim @@ -2,7 +2,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 3 system sh/exec.sh -n dnode1 -s start sleep 100 sql connect diff --git a/tests/script/general/parser/columnValue.sim b/tests/script/general/parser/columnValue.sim index 5f8152b3f0..4e6c664004 100644 --- a/tests/script/general/parser/columnValue.sim +++ b/tests/script/general/parser/columnValue.sim @@ -3,7 +3,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 3 system sh/exec.sh -n dnode1 -s start sleep 100 sql connect diff --git a/tests/script/general/parser/columnValue_unsign.sim b/tests/script/general/parser/columnValue_unsign.sim index 22ef5c42a3..6e9a37fdb6 100644 --- a/tests/script/general/parser/columnValue_unsign.sim +++ b/tests/script/general/parser/columnValue_unsign.sim @@ -106,4 +106,71 @@ if $data01 != 1 then return -1 endi -sql select a+b+c from mt_unsigned_1 where a is null; \ No newline at end of file +sql select a+b+c from mt_unsigned_1 where a is null; +if $rows != 1 then + return -1 +endi + +if $data00 != NULL then + print expect NULL, actual:$data00 + return -1 +endi + +sql select count(*), a from mt_unsigned_1 group by a; +if $rows != 1 then + return -1 +endi + +if $data00 != 1 then + return -1 +endi + +if $data01 != 1 then + return -1 +endi + +sql select count(*), b from mt_unsigned_1 group by b; +if $rows != 1 then + return -1 +endi + +if $data00 != 1 then + return -1 +endi + +if $data01 != 2 then + return -1 +endi + +sql select count(*), c from mt_unsigned_1 group by c; +if $rows != 1 then + return -1 +endi + +if $data00 != 1 then + return -1 +endi + +if $data01 != 3 then + return -1 +endi + +sql select count(*), d from mt_unsigned_1 group by d; +if $rows != 1 then + return -1 +endi + +if $data00 != 1 then + return -1 +endi + +if $data01 != 4 then + return -1 +endi + +## todo insert more rows and chec it +sql select first(a),count(b),last(c),sum(b),spread(d),avg(c),min(b),max(a),stddev(a) from mt_unsigned_1; +if $rows != 1 then + return -1 +endi + diff --git a/tests/script/general/parser/function.sim b/tests/script/general/parser/function.sim index 1c255b92a2..7d702e989e 100644 --- a/tests/script/general/parser/function.sim +++ b/tests/script/general/parser/function.sim @@ -2,7 +2,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 3 system sh/exec.sh -n dnode1 -s start sleep 100 sql connect @@ -228,7 +227,7 @@ sql select twa(k),avg(k),count(1) from t1 where ts>='2015-8-18 00:00:00' and ts< sql select twa(k),avg(k),count(1) from t1 where ts>='2015-8-18 00:00:00' and ts<='2015-8-18 00:30:00' interval(10m) order by ts desc -#todo add test case while column filter exists. +#todo add test case while column filter exists for twa query #sql select count(*),TWA(k) from tm0 where ts>='1970-1-1 13:43:00' and ts<='1970-1-1 13:44:10' interval(9s) @@ -373,3 +372,14 @@ sql select twa(k) from tm2 where ts='2020-12-29 18:46:19.109' if $rows != 0 then return -1 endi + +print ========================> TD-1787 +sql create table cars(ts timestamp, c int) tags(id int); +sql create table car1 using cars tags(1); +sql create table car2 using cars tags(2); +sql insert into car1 (ts, c) values (now,1) car2(ts, c) values(now, 2); +sql drop table cars; +sql create table cars(ts timestamp, c int) tags(id int); +sql create table car1 using cars tags(1); +sql create table car2 using cars tags(2); +sql insert into car1 (ts, c) values (now,1) car2(ts, c) values(now, 2); \ No newline at end of file diff --git a/tests/script/general/parser/null_char.sim b/tests/script/general/parser/null_char.sim index b3200da88e..4e7c8ab354 100644 --- a/tests/script/general/parser/null_char.sim +++ b/tests/script/general/parser/null_char.sim @@ -3,7 +3,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 3 system sh/exec.sh -n dnode1 -s start sleep 100 diff --git a/tests/script/general/parser/testSuite.sim b/tests/script/general/parser/testSuite.sim index 2d77cb15d2..90cccb80e5 100644 --- a/tests/script/general/parser/testSuite.sim +++ b/tests/script/general/parser/testSuite.sim @@ -1,64 +1,64 @@ -#run general/parser/alter.sim -#sleep 100 -#run general/parser/alter1.sim -#sleep 100 -#run general/parser/alter_stable.sim -#sleep 100 -#run general/parser/auto_create_tb.sim -#sleep 100 -#run general/parser/auto_create_tb_drop_tb.sim -#sleep 100 -#run general/parser/col_arithmetic_operation.sim -#sleep 100 -#run general/parser/columnValue.sim -#sleep 100 -#run general/parser/commit.sim -#sleep 100 -#run general/parser/create_db.sim -#sleep 100 -#run general/parser/create_mt.sim -#sleep 100 -#run general/parser/create_tb.sim -#sleep 100 -#run general/parser/dbtbnameValidate.sim -#sleep 100 -#run general/parser/fill.sim -#sleep 100 -#run general/parser/fill_stb.sim -#sleep 100 -##run general/parser/fill_us.sim # -#sleep 100 -#run general/parser/first_last.sim -#sleep 100 -#run general/parser/import_commit1.sim -#sleep 100 -#run general/parser/import_commit2.sim -#sleep 100 -#run general/parser/import_commit3.sim -#sleep 100 -##run general/parser/import_file.sim -#sleep 100 -#run general/parser/insert_tb.sim -#sleep 100 -#run general/parser/tags_dynamically_specifiy.sim -#sleep 100 -#run general/parser/interp.sim -#sleep 100 -#run general/parser/lastrow.sim -#sleep 100 -#run general/parser/limit.sim -#sleep 100 -#run general/parser/limit1.sim -#sleep 100 -#run general/parser/limit1_tblocks100.sim -#sleep 100 -#run general/parser/limit2.sim -#sleep 100 -#run general/parser/mixed_blocks.sim -#sleep 100 -#run general/parser/nchar.sim -#sleep 100 -#run general/parser/null_char.sim +run general/parser/alter.sim +sleep 100 +run general/parser/alter1.sim +sleep 100 +run general/parser/alter_stable.sim +sleep 100 +run general/parser/auto_create_tb.sim +sleep 100 +run general/parser/auto_create_tb_drop_tb.sim +sleep 100 +run general/parser/col_arithmetic_operation.sim +sleep 100 +run general/parser/columnValue.sim +sleep 100 +run general/parser/commit.sim +sleep 100 +run general/parser/create_db.sim +sleep 100 +run general/parser/create_mt.sim +sleep 100 +run general/parser/create_tb.sim +sleep 100 +run general/parser/dbtbnameValidate.sim +sleep 100 +run general/parser/fill.sim +sleep 100 +run general/parser/fill_stb.sim +sleep 100 +#run general/parser/fill_us.sim # +sleep 100 +run general/parser/first_last.sim +sleep 100 +run general/parser/import_commit1.sim +sleep 100 +run general/parser/import_commit2.sim +sleep 100 +run general/parser/import_commit3.sim +sleep 100 +#run general/parser/import_file.sim +sleep 100 +run general/parser/insert_tb.sim +sleep 100 +run general/parser/tags_dynamically_specifiy.sim +sleep 100 +run general/parser/interp.sim +sleep 100 +run general/parser/lastrow.sim +sleep 100 +run general/parser/limit.sim +sleep 100 +run general/parser/limit1.sim +sleep 100 +run general/parser/limit1_tblocks100.sim +sleep 100 +run general/parser/limit2.sim +sleep 100 +run general/parser/mixed_blocks.sim +sleep 100 +run general/parser/nchar.sim +sleep 100 +run general/parser/null_char.sim sleep 100 run general/parser/selectResNum.sim sleep 100 diff --git a/tests/script/general/stream/restart_stream.sim b/tests/script/general/stream/restart_stream.sim index 138e2a6e2e..b5a2038d9b 100644 --- a/tests/script/general/stream/restart_stream.sim +++ b/tests/script/general/stream/restart_stream.sim @@ -3,7 +3,6 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 1 system sh/exec.sh -n dnode1 -s start sleep 3000 @@ -98,7 +97,6 @@ print =============== step4 system sh/exec.sh -n dnode1 -s stop system sh/deploy.sh -n dnode1 -i 1 system sh/cfg.sh -n dnode1 -c walLevel -v 0 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 1 system sh/exec.sh -n dnode1 -s start print =============== step5 diff --git a/tests/script/test.sh b/tests/script/test.sh index a68ac4736d..1c7a7527ab 100755 --- a/tests/script/test.sh +++ b/tests/script/test.sh @@ -113,7 +113,6 @@ echo "rpcDebugFlag 143" >> $TAOS_CFG echo "tmrDebugFlag 131" >> $TAOS_CFG echo "cDebugFlag 143" >> $TAOS_CFG echo "udebugFlag 143" >> $TAOS_CFG -echo "tablemetakeeptimer 5" >> $TAOS_CFG echo "wal 0" >> $TAOS_CFG echo "asyncLog 0" >> $TAOS_CFG echo "locale en_US.UTF-8" >> $TAOS_CFG diff --git a/tests/script/unique/stream/metrics_balance.sim b/tests/script/unique/stream/metrics_balance.sim index 36086fe4b8..3cb0d73ab8 100644 --- a/tests/script/unique/stream/metrics_balance.sim +++ b/tests/script/unique/stream/metrics_balance.sim @@ -14,8 +14,6 @@ system sh/cfg.sh -n dnode1 -c mnodeEqualVnodeNum -v 0 system sh/cfg.sh -n dnode2 -c mnodeEqualVnodeNum -v 0 system sh/cfg.sh -n dnode1 -c maxTablesPerVnode -v 4 system sh/cfg.sh -n dnode2 -c maxTablesPerVnode -v 4 -system sh/cfg.sh -n dnode1 -c tableMetaKeepTimer -v 5 -system sh/cfg.sh -n dnode2 -c tableMetaKeepTimer -v 5 system sh/cfg.sh -n dnode1 -c numOfMnodes -v 2 system sh/cfg.sh -n dnode2 -c numOfMnodes -v 2 diff --git a/tests/test/c/CMakeLists.txt b/tests/test/c/CMakeLists.txt index 2eb8ee1614..33e1528b70 100644 --- a/tests/test/c/CMakeLists.txt +++ b/tests/test/c/CMakeLists.txt @@ -1,4 +1,4 @@ -CMAKE_MINIMUM_REQUIRED(VERSION 2.8) +CMAKE_MINIMUM_REQUIRED(VERSION 3.5) PROJECT(TDengine) INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/inc)