Merge branch 'develop' into feature/TD-2502-v3
This commit is contained in:
commit
9256daccf5
|
@ -128,5 +128,18 @@ TDengine是一个高效的存储、查询、分析时序大数据的平台,专
|
|||
|
||||
## [培训和FAQ](https://www.taosdata.com/cn/faq)
|
||||
|
||||
- [FAQ](https://www.taosdata.com/cn/documentation20/faq):常见问题与答案
|
||||
- [应用案列](https://www.taosdata.com/cn/blog/?categories=4):一些使用实例来解释如何使用TDengine
|
||||
<ul>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/12/25/2126.html">技术公开课:开源、高效的物联网大数据平台,TDengine内核技术剖析</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1941.html">TDengine视频教程-快速上手</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1945.html">TDengine视频教程-数据建模</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1961.html">TDengine视频教程-集群搭建</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1951.html">TDengine视频教程-Go Connector</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1955.html">TDengine视频教程-JDBC Connector</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1957.html">TDengine视频教程-NodeJS Connector</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1963.html">TDengine视频教程-Python Connector</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1965.html">TDengine视频教程-RESTful Connector</a></li>
|
||||
<li><a l href="https://www.taosdata.com/blog/2020/11/11/1959.html">TDengine视频教程-“零”代码运维监控</a></li>
|
||||
<li><a l href="https://www.taosdata.com/cn/documentation20/faq">FAQ:常见问题与答案</a></li>
|
||||
<li><a l href="https://www.taosdata.com/cn/blog/?categories=4"> 应用案例:一些使用实例来解释如何使用TDengine</a></li>
|
||||
</ul>
|
||||
|
||||
|
|
|
@ -20,7 +20,7 @@ TDengine的安装非常简单,从下载到安装成功仅仅只要几秒钟。
|
|||
- TDengine-server-2.0.10.0-Linux-x64.deb (2.7M)
|
||||
- TDengine-server-2.0.10.0-Linux-x64.tar.gz (4.5M)
|
||||
|
||||
具体的安装过程,请参见<a href="https://www.taosdata.com/blog/2019/08/09/566.html">TDengine多种安装包的安装和卸载</a>。
|
||||
具体的安装过程,请参见<a href="https://www.taosdata.com/blog/2019/08/09/566.html">TDengine多种安装包的安装和卸载</a>以及<a href="https://www.taosdata.com/blog/2020/11/11/1941.html">视频教程</a>。
|
||||
|
||||
## 轻松启动
|
||||
|
||||
|
|
|
@ -59,3 +59,5 @@ INSERT INTO d1001 USING METERS TAGS ("Beijng.Chaoyang", 2) VALUES (now, 10.2, 21
|
|||
TDengine支持多列模型,只要物理量是一个数据采集点同时采集的(时间戳一致),这些量就可以作为不同列放在一张超级表里。但还有一种极限的设计,单列模型,每个采集的物理量都单独建表,因此每种类型的物理量都单独建立一超级表。比如电流、电压、相位,就建三张超级表。
|
||||
|
||||
TDengine建议尽可能采用多列模型,因为插入效率以及存储效率更高。但对于有些场景,一个采集点的采集量的种类经常变化,这个时候,如果采用多列模型,就需要频繁修改超级表的结构定义,让应用变的复杂,这个时候,采用单列模型会显得简单。
|
||||
|
||||
关于数据建模请参考<a href="https://www.taosdata.com/blog/2020/11/11/1945.html">视频教程</a>。
|
||||
|
|
|
@ -226,3 +226,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, 系统也不会去建立连接。
|
||||
|
||||
关于集群搭建请参考<a href="https://www.taosdata.com/blog/2020/11/11/1961.html">视频教程</a>。
|
||||
|
|
|
@ -394,6 +394,8 @@ TDengine提供时间驱动的实时流式计算API。可以每隔一指定的时
|
|||
|
||||
## Python Connector
|
||||
|
||||
Python连接器的使用参见<a href="https://www.taosdata.com/blog/2020/11/11/1963.html">视频教程</a>
|
||||
|
||||
### 安装准备
|
||||
* 应用驱动安装请参考<a href="https://www.taosdata.com/cn/documentation/connector/#安装连接器驱动步骤">安装连接器驱动步骤</a>。
|
||||
* 已安装python 2.7 or >= 3.4
|
||||
|
@ -534,7 +536,7 @@ conn.close()
|
|||
|
||||
## RESTful Connector
|
||||
|
||||
为支持各种不同类型平台的开发,TDengine提供符合REST设计标准的API,即RESTful API。为最大程度降低学习成本,不同于其他数据库RESTful API的设计方法,TDengine直接通过HTTP POST 请求BODY中包含的SQL语句来操作数据库,仅需要一个URL。
|
||||
为支持各种不同类型平台的开发,TDengine提供符合REST设计标准的API,即RESTful API。为最大程度降低学习成本,不同于其他数据库RESTful API的设计方法,TDengine直接通过HTTP POST 请求BODY中包含的SQL语句来操作数据库,仅需要一个URL。RESTful连接器的使用参见<a href=https://www.taosdata.com/blog/2020/11/11/1965.html>视频教程</a>。
|
||||
|
||||
### HTTP请求格式
|
||||
|
||||
|
@ -779,7 +781,7 @@ https://www.taosdata.com/blog/2020/11/02/1901.html
|
|||
|
||||
TDengine提供了GO驱动程序`taosSql`。 `taosSql`实现了GO语言的内置接口`database/sql/driver`。用户只需按如下方式引入包就可以在应用程序中访问TDengine, 详见`https://github.com/taosdata/driver-go/blob/develop/taosSql/driver_test.go`。
|
||||
|
||||
使用 Go 连接器的示例代码请参考 https://github.com/taosdata/TDengine/tree/develop/tests/examples/go。
|
||||
使用 Go 连接器的示例代码请参考 https://github.com/taosdata/TDengine/tree/develop/tests/examples/go 以及<a href="https://www.taosdata.com/blog/2020/11/11/1951.html">视频教程</a>。
|
||||
|
||||
```Go
|
||||
import (
|
||||
|
@ -796,7 +798,7 @@ go env -w GOPROXY=https://goproxy.io,direct
|
|||
|
||||
### 常用API
|
||||
|
||||
- sql.Open(DRIVER_NAME string, dataSourceName string) *DB`
|
||||
- `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
|
||||
|
||||
|
@ -835,6 +837,8 @@ Node.js连接器支持的系统有:
|
|||
| **OS类型** | Linux | Win64 | Win32 | Linux | Linux |
|
||||
| **支持与否** | **支持** | **支持** | **支持** | **支持** | **支持** |
|
||||
|
||||
Node.js连接器的使用参见<a href="https://www.taosdata.com/blog/2020/11/11/1957.html">视频教程</a>
|
||||
|
||||
### 安装准备
|
||||
|
||||
* 应用驱动安装请参考<a href="https://www.taosdata.com/cn/documentation/connector/#安装连接器驱动步骤">安装连接器驱动步骤</a>。
|
||||
|
@ -909,7 +913,7 @@ node nodejsChecker.js host=localhost
|
|||
|
||||
#### 建立连接
|
||||
|
||||
使用node.js连接器时,必须先<em>require</em> ```td2.0-connector```,然后使用 ```taos.connect``` 函数。```taos.connect``` 函数必须提供的参数是```host```,其它参数在没有提供的情况下会使用如下的默认值。最后需要初始化```cursor``` 来和TDengine服务端通信
|
||||
使用node.js连接器时,必须先<em>require</em> `td2.0-connector`,然后使用 `taos.connect` 函数。`taos.connect` 函数必须提供的参数是`host`,其它参数在没有提供的情况下会使用如下的默认值。最后需要初始化`cursor` 来和TDengine服务端通信
|
||||
|
||||
```javascript
|
||||
const taos = require('td2.0-connector');
|
||||
|
@ -945,13 +949,13 @@ TDengine目前还不支持update和delete语句。
|
|||
|
||||
#### 查询
|
||||
|
||||
可通过 ```cursor.query``` 函数来查询数据库。
|
||||
可通过 `cursor.query` 函数来查询数据库。
|
||||
|
||||
```javascript
|
||||
var query = cursor.query('show databases;')
|
||||
```
|
||||
|
||||
查询的结果可以通过 ```query.execute()``` 函数获取并打印出来
|
||||
查询的结果可以通过 `query.execute()` 函数获取并打印出来
|
||||
|
||||
```javascript
|
||||
var promise = query.execute();
|
||||
|
@ -959,7 +963,7 @@ promise.then(function(result) {
|
|||
result.pretty();
|
||||
});
|
||||
```
|
||||
格式化查询语句还可以使用```query```的```bind```方法。如下面的示例:```query```会自动将提供的数值填入查询语句的```?```里。
|
||||
格式化查询语句还可以使用`query`的`bind`方法。如下面的示例:`query`会自动将提供的数值填入查询语句的`?`里。
|
||||
|
||||
```javascript
|
||||
var query = cursor.query('select * from meterinfo.meters where ts <= ? and areaid = ?;').bind(new Date(), 5);
|
||||
|
@ -967,7 +971,7 @@ query.execute().then(function(result) {
|
|||
result.pretty();
|
||||
})
|
||||
```
|
||||
如果在```query```语句里提供第二个参数并设为```true```也可以立即获取查询结果。如下:
|
||||
如果在`query`语句里提供第二个参数并设为`true`也可以立即获取查询结果。如下:
|
||||
|
||||
```javascript
|
||||
var promise = cursor.query('select * from meterinfo.meters where v1 = 30;', true)
|
||||
|
|
|
@ -6,6 +6,8 @@ Java连接器支持的系统有:
|
|||
| **OS类型** | Linux | Win64 | Win32 | Linux | Linux |
|
||||
| **支持与否** | **支持** | **支持** | **支持** | **支持** | **支持** |
|
||||
|
||||
Java连接器的使用请参见<a href=https://www.taosdata.com/blog/2020/11/11/1955.html>视频教程</a>。
|
||||
|
||||
TDengine 为了方便 Java 应用使用,提供了遵循 JDBC 标准(3.0)API 规范的 `taos-jdbcdriver` 实现。目前可以通过 [Sonatype Repository][1] 搜索并下载。
|
||||
|
||||
由于 TDengine 是使用 c 语言开发的,使用 taos-jdbcdriver 驱动包时需要依赖系统对应的本地函数库。
|
||||
|
|
|
@ -419,7 +419,7 @@ void tscCloseTscObj(void *pObj);
|
|||
// todo move to taos? or create a new file: taos_internal.h
|
||||
TAOS *taos_connect_a(char *ip, char *user, char *pass, char *db, uint16_t port, void (*fp)(void *, TAOS_RES *, int),
|
||||
void *param, TAOS **taos);
|
||||
TAOS_RES* taos_query_h(TAOS* taos, const char *sqlstr, TAOS_RES** res);
|
||||
TAOS_RES* taos_query_h(TAOS* taos, const char *sqlstr, int64_t* res);
|
||||
void waitForQueryRsp(void *param, TAOS_RES *tres, int code);
|
||||
|
||||
void doAsyncQuery(STscObj *pObj, SSqlObj *pSql, __async_cb_func_t fp, void *param, const char *sqlstr, size_t sqlLen);
|
||||
|
|
|
@ -5442,6 +5442,7 @@ static void setCreateDBOption(SCreateDbMsg* pMsg, SCreateDBInfo* pCreateDb) {
|
|||
pMsg->quorum = pCreateDb->quorum;
|
||||
pMsg->ignoreExist = pCreateDb->ignoreExists;
|
||||
pMsg->update = pCreateDb->update;
|
||||
pMsg->cacheLastRow = pCreateDb->cachelast;
|
||||
}
|
||||
|
||||
int32_t parseCreateDBOptions(SSqlCmd* pCmd, SCreateDBInfo* pCreateDbSql) {
|
||||
|
|
|
@ -1247,7 +1247,7 @@ int32_t tscBuildShowMsg(SSqlObj *pSql, SSqlInfo *pInfo) {
|
|||
pShowMsg->payloadLen = htons(pEpAddr->n);
|
||||
}
|
||||
|
||||
pCmd->payloadLen = sizeof(SShowMsg) + pShowMsg->payloadLen;
|
||||
pCmd->payloadLen = sizeof(SShowMsg) + htons(pShowMsg->payloadLen);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
|
|
|
@ -314,7 +314,7 @@ static void waitForRetrieveRsp(void *param, TAOS_RES *tres, int numOfRows) {
|
|||
tsem_post(&pSql->rspSem);
|
||||
}
|
||||
|
||||
TAOS_RES* taos_query_c(TAOS *taos, const char *sqlstr, uint32_t sqlLen, TAOS_RES** res) {
|
||||
TAOS_RES* taos_query_c(TAOS *taos, const char *sqlstr, uint32_t sqlLen, int64_t* res) {
|
||||
STscObj *pObj = (STscObj *)taos;
|
||||
if (pObj == NULL || pObj->signature != pObj) {
|
||||
terrno = TSDB_CODE_TSC_DISCONNECTED;
|
||||
|
@ -340,7 +340,7 @@ TAOS_RES* taos_query_c(TAOS *taos, const char *sqlstr, uint32_t sqlLen, TAOS_RES
|
|||
doAsyncQuery(pObj, pSql, waitForQueryRsp, taos, sqlstr, sqlLen);
|
||||
|
||||
if (res != NULL) {
|
||||
*res = pSql;
|
||||
atomic_store_64(res, pSql->self);
|
||||
}
|
||||
|
||||
tsem_wait(&pSql->rspSem);
|
||||
|
@ -351,7 +351,7 @@ TAOS_RES* taos_query(TAOS *taos, const char *sqlstr) {
|
|||
return taos_query_c(taos, sqlstr, (uint32_t)strlen(sqlstr), NULL);
|
||||
}
|
||||
|
||||
TAOS_RES* taos_query_h(TAOS* taos, const char *sqlstr, TAOS_RES** res) {
|
||||
TAOS_RES* taos_query_h(TAOS* taos, const char *sqlstr, int64_t* res) {
|
||||
return taos_query_c(taos, sqlstr, (uint32_t) strlen(sqlstr), res);
|
||||
}
|
||||
|
||||
|
|
|
@ -94,6 +94,7 @@ extern int32_t tsFsyncPeriod;
|
|||
extern int32_t tsReplications;
|
||||
extern int32_t tsQuorum;
|
||||
extern int32_t tsUpdate;
|
||||
extern int32_t tsCacheLastRow;
|
||||
|
||||
// balance
|
||||
extern int32_t tsEnableBalance;
|
||||
|
|
|
@ -127,6 +127,7 @@ int32_t tsFsyncPeriod = TSDB_DEFAULT_FSYNC_PERIOD;
|
|||
int32_t tsReplications = TSDB_DEFAULT_DB_REPLICA_OPTION;
|
||||
int32_t tsQuorum = TSDB_DEFAULT_DB_QUORUM_OPTION;
|
||||
int32_t tsUpdate = TSDB_DEFAULT_DB_UPDATE_OPTION;
|
||||
int32_t tsCacheLastRow = TSDB_DEFAULT_CACHE_BLOCK_SIZE;
|
||||
int32_t tsMaxVgroupsPerDb = 0;
|
||||
int32_t tsMinTablePerVnode = TSDB_TABLES_STEP;
|
||||
int32_t tsMaxTablePerVnode = TSDB_DEFAULT_TABLES;
|
||||
|
|
|
@ -369,6 +369,10 @@ void tsDataSwap(void *pLeft, void *pRight, int32_t type, int32_t size, void* buf
|
|||
#define TSDB_MAX_DB_UPDATE 1
|
||||
#define TSDB_DEFAULT_DB_UPDATE_OPTION 0
|
||||
|
||||
#define TSDB_MIN_DB_CACHE_LAST_ROW 0
|
||||
#define TSDB_MAX_DB_CACHE_LAST_ROW 1
|
||||
#define TSDB_DEFAULT_CACHE_LAST_ROW 0
|
||||
|
||||
#define TSDB_MIN_FSYNC_PERIOD 0
|
||||
#define TSDB_MAX_FSYNC_PERIOD 180000 // millisecond
|
||||
#define TSDB_DEFAULT_FSYNC_PERIOD 3000 // three second
|
||||
|
|
|
@ -549,7 +549,8 @@ typedef struct {
|
|||
int8_t quorum;
|
||||
int8_t ignoreExist;
|
||||
int8_t update;
|
||||
int8_t reserve[9];
|
||||
int8_t cacheLastRow;
|
||||
int8_t reserve[8];
|
||||
} SCreateDbMsg, SAlterDbMsg;
|
||||
|
||||
typedef struct {
|
||||
|
@ -661,8 +662,9 @@ typedef struct {
|
|||
int8_t wals;
|
||||
int8_t quorum;
|
||||
int8_t update;
|
||||
int8_t reserved[11];
|
||||
int8_t cacheLastRow;
|
||||
int32_t vgCfgVersion;
|
||||
int8_t reserved[10];
|
||||
} SVnodeCfg;
|
||||
|
||||
typedef struct {
|
||||
|
|
|
@ -66,6 +66,7 @@ typedef struct {
|
|||
int8_t precision;
|
||||
int8_t compression;
|
||||
int8_t update;
|
||||
int8_t cacheLastRow;
|
||||
} STsdbCfg;
|
||||
|
||||
// --------- TSDB REPOSITORY USAGE STATISTICS
|
||||
|
@ -119,7 +120,7 @@ STableCfg *tsdbCreateTableCfgFromMsg(SMDCreateTableMsg *pMsg);
|
|||
int tsdbCreateTable(TSDB_REPO_T *repo, STableCfg *pCfg);
|
||||
int tsdbDropTable(TSDB_REPO_T *pRepo, STableId tableId);
|
||||
int tsdbUpdateTableTagValue(TSDB_REPO_T *repo, SUpdateTableTagValMsg *pMsg);
|
||||
TSKEY tsdbGetTableLastKey(TSDB_REPO_T *repo, uint64_t uid);
|
||||
// TSKEY tsdbGetTableLastKey(TSDB_REPO_T *repo, uint64_t uid);
|
||||
|
||||
uint32_t tsdbGetFileInfo(TSDB_REPO_T *repo, char *name, uint32_t *index, uint32_t eindex, int64_t *size);
|
||||
|
||||
|
|
|
@ -114,114 +114,115 @@
|
|||
#define TK_COMP 96
|
||||
#define TK_PRECISION 97
|
||||
#define TK_UPDATE 98
|
||||
#define TK_LP 99
|
||||
#define TK_RP 100
|
||||
#define TK_TAGS 101
|
||||
#define TK_USING 102
|
||||
#define TK_AS 103
|
||||
#define TK_COMMA 104
|
||||
#define TK_NULL 105
|
||||
#define TK_SELECT 106
|
||||
#define TK_UNION 107
|
||||
#define TK_ALL 108
|
||||
#define TK_FROM 109
|
||||
#define TK_VARIABLE 110
|
||||
#define TK_INTERVAL 111
|
||||
#define TK_FILL 112
|
||||
#define TK_SLIDING 113
|
||||
#define TK_ORDER 114
|
||||
#define TK_BY 115
|
||||
#define TK_ASC 116
|
||||
#define TK_DESC 117
|
||||
#define TK_GROUP 118
|
||||
#define TK_HAVING 119
|
||||
#define TK_LIMIT 120
|
||||
#define TK_OFFSET 121
|
||||
#define TK_SLIMIT 122
|
||||
#define TK_SOFFSET 123
|
||||
#define TK_WHERE 124
|
||||
#define TK_NOW 125
|
||||
#define TK_RESET 126
|
||||
#define TK_QUERY 127
|
||||
#define TK_ADD 128
|
||||
#define TK_COLUMN 129
|
||||
#define TK_TAG 130
|
||||
#define TK_CHANGE 131
|
||||
#define TK_SET 132
|
||||
#define TK_KILL 133
|
||||
#define TK_CONNECTION 134
|
||||
#define TK_STREAM 135
|
||||
#define TK_COLON 136
|
||||
#define TK_ABORT 137
|
||||
#define TK_AFTER 138
|
||||
#define TK_ATTACH 139
|
||||
#define TK_BEFORE 140
|
||||
#define TK_BEGIN 141
|
||||
#define TK_CASCADE 142
|
||||
#define TK_CLUSTER 143
|
||||
#define TK_CONFLICT 144
|
||||
#define TK_COPY 145
|
||||
#define TK_DEFERRED 146
|
||||
#define TK_DELIMITERS 147
|
||||
#define TK_DETACH 148
|
||||
#define TK_EACH 149
|
||||
#define TK_END 150
|
||||
#define TK_EXPLAIN 151
|
||||
#define TK_FAIL 152
|
||||
#define TK_FOR 153
|
||||
#define TK_IGNORE 154
|
||||
#define TK_IMMEDIATE 155
|
||||
#define TK_INITIALLY 156
|
||||
#define TK_INSTEAD 157
|
||||
#define TK_MATCH 158
|
||||
#define TK_KEY 159
|
||||
#define TK_OF 160
|
||||
#define TK_RAISE 161
|
||||
#define TK_REPLACE 162
|
||||
#define TK_RESTRICT 163
|
||||
#define TK_ROW 164
|
||||
#define TK_STATEMENT 165
|
||||
#define TK_TRIGGER 166
|
||||
#define TK_VIEW 167
|
||||
#define TK_COUNT 168
|
||||
#define TK_SUM 169
|
||||
#define TK_AVG 170
|
||||
#define TK_MIN 171
|
||||
#define TK_MAX 172
|
||||
#define TK_FIRST 173
|
||||
#define TK_LAST 174
|
||||
#define TK_TOP 175
|
||||
#define TK_BOTTOM 176
|
||||
#define TK_STDDEV 177
|
||||
#define TK_PERCENTILE 178
|
||||
#define TK_APERCENTILE 179
|
||||
#define TK_LEASTSQUARES 180
|
||||
#define TK_HISTOGRAM 181
|
||||
#define TK_DIFF 182
|
||||
#define TK_SPREAD 183
|
||||
#define TK_TWA 184
|
||||
#define TK_INTERP 185
|
||||
#define TK_LAST_ROW 186
|
||||
#define TK_RATE 187
|
||||
#define TK_IRATE 188
|
||||
#define TK_SUM_RATE 189
|
||||
#define TK_SUM_IRATE 190
|
||||
#define TK_AVG_RATE 191
|
||||
#define TK_AVG_IRATE 192
|
||||
#define TK_TBID 193
|
||||
#define TK_SEMI 194
|
||||
#define TK_NONE 195
|
||||
#define TK_PREV 196
|
||||
#define TK_LINEAR 197
|
||||
#define TK_IMPORT 198
|
||||
#define TK_METRIC 199
|
||||
#define TK_TBNAME 200
|
||||
#define TK_JOIN 201
|
||||
#define TK_METRICS 202
|
||||
#define TK_STABLE 203
|
||||
#define TK_INSERT 204
|
||||
#define TK_INTO 205
|
||||
#define TK_VALUES 206
|
||||
#define TK_CACHELAST 99
|
||||
#define TK_LP 100
|
||||
#define TK_RP 101
|
||||
#define TK_TAGS 102
|
||||
#define TK_USING 103
|
||||
#define TK_AS 104
|
||||
#define TK_COMMA 105
|
||||
#define TK_NULL 106
|
||||
#define TK_SELECT 107
|
||||
#define TK_UNION 108
|
||||
#define TK_ALL 109
|
||||
#define TK_FROM 110
|
||||
#define TK_VARIABLE 111
|
||||
#define TK_INTERVAL 112
|
||||
#define TK_FILL 113
|
||||
#define TK_SLIDING 114
|
||||
#define TK_ORDER 115
|
||||
#define TK_BY 116
|
||||
#define TK_ASC 117
|
||||
#define TK_DESC 118
|
||||
#define TK_GROUP 119
|
||||
#define TK_HAVING 120
|
||||
#define TK_LIMIT 121
|
||||
#define TK_OFFSET 122
|
||||
#define TK_SLIMIT 123
|
||||
#define TK_SOFFSET 124
|
||||
#define TK_WHERE 125
|
||||
#define TK_NOW 126
|
||||
#define TK_RESET 127
|
||||
#define TK_QUERY 128
|
||||
#define TK_ADD 129
|
||||
#define TK_COLUMN 130
|
||||
#define TK_TAG 131
|
||||
#define TK_CHANGE 132
|
||||
#define TK_SET 133
|
||||
#define TK_KILL 134
|
||||
#define TK_CONNECTION 135
|
||||
#define TK_STREAM 136
|
||||
#define TK_COLON 137
|
||||
#define TK_ABORT 138
|
||||
#define TK_AFTER 139
|
||||
#define TK_ATTACH 140
|
||||
#define TK_BEFORE 141
|
||||
#define TK_BEGIN 142
|
||||
#define TK_CASCADE 143
|
||||
#define TK_CLUSTER 144
|
||||
#define TK_CONFLICT 145
|
||||
#define TK_COPY 146
|
||||
#define TK_DEFERRED 147
|
||||
#define TK_DELIMITERS 148
|
||||
#define TK_DETACH 149
|
||||
#define TK_EACH 150
|
||||
#define TK_END 151
|
||||
#define TK_EXPLAIN 152
|
||||
#define TK_FAIL 153
|
||||
#define TK_FOR 154
|
||||
#define TK_IGNORE 155
|
||||
#define TK_IMMEDIATE 156
|
||||
#define TK_INITIALLY 157
|
||||
#define TK_INSTEAD 158
|
||||
#define TK_MATCH 159
|
||||
#define TK_KEY 160
|
||||
#define TK_OF 161
|
||||
#define TK_RAISE 162
|
||||
#define TK_REPLACE 163
|
||||
#define TK_RESTRICT 164
|
||||
#define TK_ROW 165
|
||||
#define TK_STATEMENT 166
|
||||
#define TK_TRIGGER 167
|
||||
#define TK_VIEW 168
|
||||
#define TK_COUNT 169
|
||||
#define TK_SUM 170
|
||||
#define TK_AVG 171
|
||||
#define TK_MIN 172
|
||||
#define TK_MAX 173
|
||||
#define TK_FIRST 174
|
||||
#define TK_LAST 175
|
||||
#define TK_TOP 176
|
||||
#define TK_BOTTOM 177
|
||||
#define TK_STDDEV 178
|
||||
#define TK_PERCENTILE 179
|
||||
#define TK_APERCENTILE 180
|
||||
#define TK_LEASTSQUARES 181
|
||||
#define TK_HISTOGRAM 182
|
||||
#define TK_DIFF 183
|
||||
#define TK_SPREAD 184
|
||||
#define TK_TWA 185
|
||||
#define TK_INTERP 186
|
||||
#define TK_LAST_ROW 187
|
||||
#define TK_RATE 188
|
||||
#define TK_IRATE 189
|
||||
#define TK_SUM_RATE 190
|
||||
#define TK_SUM_IRATE 191
|
||||
#define TK_AVG_RATE 192
|
||||
#define TK_AVG_IRATE 193
|
||||
#define TK_TBID 194
|
||||
#define TK_SEMI 195
|
||||
#define TK_NONE 196
|
||||
#define TK_PREV 197
|
||||
#define TK_LINEAR 198
|
||||
#define TK_IMPORT 199
|
||||
#define TK_METRIC 200
|
||||
#define TK_TBNAME 201
|
||||
#define TK_JOIN 202
|
||||
#define TK_METRICS 203
|
||||
#define TK_STABLE 204
|
||||
#define TK_INSERT 205
|
||||
#define TK_INTO 206
|
||||
#define TK_VALUES 207
|
||||
|
||||
|
||||
#define TK_SPACE 300
|
||||
|
|
|
@ -302,14 +302,12 @@ void shellRunCommandOnServer(TAOS *con, char command[]) {
|
|||
|
||||
st = taosGetTimestampUs();
|
||||
|
||||
TAOS_RES* tmpSql = NULL;
|
||||
TAOS_RES* pSql = taos_query_h(con, command, &tmpSql);
|
||||
TAOS_RES* pSql = taos_query_h(con, command, &result);
|
||||
if (taos_errno(pSql)) {
|
||||
taos_error(pSql, st);
|
||||
return;
|
||||
}
|
||||
|
||||
atomic_store_64(&result, ((SSqlObj*)tmpSql)->self);
|
||||
int64_t oresult = atomic_load_64(&result);
|
||||
|
||||
if (regex_match(command, "^\\s*use\\s+[a-zA-Z0-9_]+\\s*;\\s*$", REG_EXTENDED | REG_ICASE)) {
|
||||
|
|
|
@ -174,7 +174,8 @@ typedef struct {
|
|||
int8_t replications;
|
||||
int8_t quorum;
|
||||
int8_t update;
|
||||
int8_t reserved[11];
|
||||
int8_t cacheLastRow;
|
||||
int8_t reserved[10];
|
||||
} SDbCfg;
|
||||
|
||||
typedef struct SDbObj {
|
||||
|
|
|
@ -322,6 +322,11 @@ static int32_t mnodeCheckDbCfg(SDbCfg *pCfg) {
|
|||
return TSDB_CODE_MND_INVALID_DB_OPTION;
|
||||
}
|
||||
|
||||
if (pCfg->cacheLastRow < TSDB_MIN_DB_CACHE_LAST_ROW || pCfg->cacheLastRow > TSDB_MAX_DB_CACHE_LAST_ROW) {
|
||||
mError("invalid db option cacheLastRow:%d valid range: [%d, %d]", pCfg->cacheLastRow, TSDB_MIN_DB_CACHE_LAST_ROW, TSDB_MAX_DB_CACHE_LAST_ROW);
|
||||
return TSDB_CODE_MND_INVALID_DB_OPTION;
|
||||
}
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
|
@ -343,6 +348,7 @@ static void mnodeSetDefaultDbCfg(SDbCfg *pCfg) {
|
|||
if (pCfg->replications < 0) pCfg->replications = tsReplications;
|
||||
if (pCfg->quorum < 0) pCfg->quorum = tsQuorum;
|
||||
if (pCfg->update < 0) pCfg->update = tsUpdate;
|
||||
if (pCfg->cacheLastRow < 0) pCfg->cacheLastRow = tsCacheLastRow;
|
||||
}
|
||||
|
||||
static int32_t mnodeCreateDbCb(SMnodeMsg *pMsg, int32_t code) {
|
||||
|
@ -396,7 +402,8 @@ static int32_t mnodeCreateDb(SAcctObj *pAcct, SCreateDbMsg *pCreate, SMnodeMsg *
|
|||
.walLevel = pCreate->walLevel,
|
||||
.replications = pCreate->replications,
|
||||
.quorum = pCreate->quorum,
|
||||
.update = pCreate->update
|
||||
.update = pCreate->update,
|
||||
.cacheLastRow = pCreate->cacheLastRow
|
||||
};
|
||||
|
||||
mnodeSetDefaultDbCfg(&pDb->cfg);
|
||||
|
@ -605,6 +612,12 @@ static int32_t mnodeGetDbMeta(STableMetaMsg *pMeta, SShowObj *pShow, void *pConn
|
|||
strcpy(pSchema[cols].name, "comp");
|
||||
pSchema[cols].bytes = htons(pShow->bytes[cols]);
|
||||
cols++;
|
||||
|
||||
pShow->bytes[cols] = 1;
|
||||
pSchema[cols].type = TSDB_DATA_TYPE_TINYINT;
|
||||
strcpy(pSchema[cols].name, "cachelast");
|
||||
pSchema[cols].bytes = htons(pShow->bytes[cols]);
|
||||
cols++;
|
||||
#ifndef __CLOUD_VERSION__
|
||||
}
|
||||
#endif
|
||||
|
@ -750,6 +763,10 @@ static int32_t mnodeRetrieveDbs(SShowObj *pShow, char *data, int32_t rows, void
|
|||
pWrite = data + pShow->offset[cols] * rows + pShow->bytes[cols] * numOfRows;
|
||||
*(int8_t *)pWrite = pDb->cfg.compression;
|
||||
cols++;
|
||||
|
||||
pWrite = data + pShow->offset[cols] * rows + pShow->bytes[cols] * numOfRows;
|
||||
*(int8_t *)pWrite = pDb->cfg.cacheLastRow;
|
||||
cols++;
|
||||
#ifndef __CLOUD_VERSION__
|
||||
}
|
||||
#endif
|
||||
|
@ -864,6 +881,7 @@ static SDbCfg mnodeGetAlterDbOption(SDbObj *pDb, SAlterDbMsg *pAlter) {
|
|||
int8_t quorum = pAlter->quorum;
|
||||
int8_t precision = pAlter->precision;
|
||||
int8_t update = pAlter->update;
|
||||
int8_t cacheLastRow = pAlter->cacheLastRow;
|
||||
|
||||
terrno = TSDB_CODE_SUCCESS;
|
||||
|
||||
|
@ -976,6 +994,11 @@ static SDbCfg mnodeGetAlterDbOption(SDbObj *pDb, SAlterDbMsg *pAlter) {
|
|||
#endif
|
||||
}
|
||||
|
||||
if (cacheLastRow >= 0 && cacheLastRow != pDb->cfg.cacheLastRow) {
|
||||
mDebug("db:%s, cacheLastRow:%d change to %d", pDb->name, pDb->cfg.cacheLastRow, cacheLastRow);
|
||||
newCfg.cacheLastRow = cacheLastRow;
|
||||
}
|
||||
|
||||
return newCfg;
|
||||
}
|
||||
|
||||
|
|
|
@ -863,6 +863,7 @@ static SCreateVnodeMsg *mnodeBuildVnodeMsg(SVgObj *pVgroup) {
|
|||
pCfg->wals = 3;
|
||||
pCfg->quorum = pDb->cfg.quorum;
|
||||
pCfg->update = pDb->cfg.update;
|
||||
pCfg->cacheLastRow = pDb->cfg.cacheLastRow;
|
||||
|
||||
SVnodeDesc *pNodes = pVnode->nodes;
|
||||
for (int32_t j = 0; j < pVgroup->numOfVnodes; ++j) {
|
||||
|
|
|
@ -121,6 +121,7 @@ typedef struct SCreateDBInfo {
|
|||
SStrToken precision;
|
||||
bool ignoreExists;
|
||||
int8_t update;
|
||||
int8_t cachelast;
|
||||
|
||||
SArray *keep;
|
||||
} SCreateDBInfo;
|
||||
|
|
|
@ -112,29 +112,29 @@ cmd ::= SHOW dbPrefix(X) STABLES. {
|
|||
|
||||
cmd ::= SHOW dbPrefix(X) STABLES LIKE ids(Y). {
|
||||
SStrToken token;
|
||||
setDBName(&token, &X);
|
||||
setDbName(&token, &X);
|
||||
setShowOptions(pInfo, TSDB_MGMT_TABLE_METRIC, &token, &Y);
|
||||
}
|
||||
|
||||
cmd ::= SHOW dbPrefix(X) VGROUPS. {
|
||||
SStrToken token;
|
||||
setDBName(&token, &X);
|
||||
setDbName(&token, &X);
|
||||
setShowOptions(pInfo, TSDB_MGMT_TABLE_VGROUP, &token, 0);
|
||||
}
|
||||
|
||||
cmd ::= SHOW dbPrefix(X) VGROUPS ids(Y). {
|
||||
SStrToken token;
|
||||
setDBName(&token, &X);
|
||||
setDbName(&token, &X);
|
||||
setShowOptions(pInfo, TSDB_MGMT_TABLE_VGROUP, &token, &Y);
|
||||
}
|
||||
|
||||
//drop configure for tables
|
||||
cmd ::= DROP TABLE ifexists(Y) ids(X) cpxName(Z). {
|
||||
X.n += Z.n;
|
||||
setDropDBTableInfo(pInfo, TSDB_SQL_DROP_TABLE, &X, &Y);
|
||||
setDropDbTableInfo(pInfo, TSDB_SQL_DROP_TABLE, &X, &Y);
|
||||
}
|
||||
|
||||
cmd ::= DROP DATABASE ifexists(Y) ids(X). { setDropDBTableInfo(pInfo, TSDB_SQL_DROP_DB, &X, &Y); }
|
||||
cmd ::= DROP DATABASE ifexists(Y) ids(X). { setDropDbTableInfo(pInfo, TSDB_SQL_DROP_DB, &X, &Y); }
|
||||
cmd ::= DROP DNODE ids(X). { setDCLSQLElems(pInfo, TSDB_SQL_DROP_DNODE, 1, &X); }
|
||||
cmd ::= DROP USER ids(X). { setDCLSQLElems(pInfo, TSDB_SQL_DROP_USER, 1, &X); }
|
||||
cmd ::= DROP ACCOUNT ids(X). { setDCLSQLElems(pInfo, TSDB_SQL_DROP_ACCT, 1, &X); }
|
||||
|
@ -149,16 +149,16 @@ cmd ::= DESCRIBE ids(X) cpxName(Y). {
|
|||
}
|
||||
|
||||
/////////////////////////////////THE ALTER STATEMENT////////////////////////////////////////
|
||||
cmd ::= ALTER USER ids(X) PASS ids(Y). { setAlterUserSQL(pInfo, TSDB_ALTER_USER_PASSWD, &X, &Y, NULL); }
|
||||
cmd ::= ALTER USER ids(X) PRIVILEGE ids(Y). { setAlterUserSQL(pInfo, TSDB_ALTER_USER_PRIVILEGES, &X, NULL, &Y);}
|
||||
cmd ::= ALTER USER ids(X) PASS ids(Y). { setAlterUserSql(pInfo, TSDB_ALTER_USER_PASSWD, &X, &Y, NULL); }
|
||||
cmd ::= ALTER USER ids(X) PRIVILEGE ids(Y). { setAlterUserSql(pInfo, TSDB_ALTER_USER_PRIVILEGES, &X, NULL, &Y);}
|
||||
cmd ::= ALTER DNODE ids(X) ids(Y). { setDCLSQLElems(pInfo, TSDB_SQL_CFG_DNODE, 2, &X, &Y); }
|
||||
cmd ::= ALTER DNODE ids(X) ids(Y) ids(Z). { setDCLSQLElems(pInfo, TSDB_SQL_CFG_DNODE, 3, &X, &Y, &Z); }
|
||||
cmd ::= ALTER LOCAL ids(X). { setDCLSQLElems(pInfo, TSDB_SQL_CFG_LOCAL, 1, &X); }
|
||||
cmd ::= ALTER LOCAL ids(X) ids(Y). { setDCLSQLElems(pInfo, TSDB_SQL_CFG_LOCAL, 2, &X, &Y); }
|
||||
cmd ::= ALTER DATABASE ids(X) alter_db_optr(Y). { SStrToken t = {0}; setCreateDBSQL(pInfo, TSDB_SQL_ALTER_DB, &X, &Y, &t);}
|
||||
|
||||
cmd ::= ALTER ACCOUNT ids(X) acct_optr(Z). { setCreateAcctSQL(pInfo, TSDB_SQL_ALTER_ACCT, &X, NULL, &Z);}
|
||||
cmd ::= ALTER ACCOUNT ids(X) PASS ids(Y) acct_optr(Z). { setCreateAcctSQL(pInfo, TSDB_SQL_ALTER_ACCT, &X, &Y, &Z);}
|
||||
cmd ::= ALTER ACCOUNT ids(X) acct_optr(Z). { setCreateAcctSql(pInfo, TSDB_SQL_ALTER_ACCT, &X, NULL, &Z);}
|
||||
cmd ::= ALTER ACCOUNT ids(X) PASS ids(Y) acct_optr(Z). { setCreateAcctSql(pInfo, TSDB_SQL_ALTER_ACCT, &X, &Y, &Z);}
|
||||
|
||||
// An IDENTIFIER can be a generic identifier, or one of several keywords.
|
||||
// Any non-standard keyword can also be an identifier.
|
||||
|
@ -179,9 +179,9 @@ ifnotexists(X) ::= . { X.n = 0;}
|
|||
//create option for dnode/db/user/account
|
||||
cmd ::= CREATE DNODE ids(X). { setDCLSQLElems(pInfo, TSDB_SQL_CREATE_DNODE, 1, &X);}
|
||||
cmd ::= CREATE ACCOUNT ids(X) PASS ids(Y) acct_optr(Z).
|
||||
{ setCreateAcctSQL(pInfo, TSDB_SQL_CREATE_ACCT, &X, &Y, &Z);}
|
||||
{ setCreateAcctSql(pInfo, TSDB_SQL_CREATE_ACCT, &X, &Y, &Z);}
|
||||
cmd ::= CREATE DATABASE ifnotexists(Z) ids(X) db_optr(Y). { setCreateDBSQL(pInfo, TSDB_SQL_CREATE_DB, &X, &Y, &Z);}
|
||||
cmd ::= CREATE USER ids(X) PASS ids(Y). { setCreateUserSQL(pInfo, &X, &Y);}
|
||||
cmd ::= CREATE USER ids(X) PASS ids(Y). { setCreateUserSql(pInfo, &X, &Y);}
|
||||
|
||||
pps(Y) ::= . { Y.n = 0; }
|
||||
pps(Y) ::= PPS INTEGER(X). { Y = X; }
|
||||
|
@ -240,6 +240,7 @@ fsync(Y) ::= FSYNC INTEGER(X). { Y = X; }
|
|||
comp(Y) ::= COMP INTEGER(X). { Y = X; }
|
||||
prec(Y) ::= PRECISION STRING(X). { Y = X; }
|
||||
update(Y) ::= UPDATE INTEGER(X). { Y = X; }
|
||||
cachelast(Y) ::= CACHELAST INTEGER(X). { Y = X; }
|
||||
|
||||
%type db_optr {SCreateDBInfo}
|
||||
db_optr(Y) ::= . {setDefaultCreateDbOption(&Y);}
|
||||
|
@ -258,6 +259,7 @@ db_optr(Y) ::= db_optr(Z) comp(X). { Y = Z; Y.compressionLevel = strto
|
|||
db_optr(Y) ::= db_optr(Z) prec(X). { Y = Z; Y.precision = X; }
|
||||
db_optr(Y) ::= db_optr(Z) keep(X). { Y = Z; Y.keep = X; }
|
||||
db_optr(Y) ::= db_optr(Z) update(X). { Y = Z; Y.update = strtol(X.z, NULL, 10); }
|
||||
db_optr(Y) ::= db_optr(Z) cachelast(X). { Y = Z; Y.cachelast = strtol(X.z, NULL, 10); }
|
||||
|
||||
%type alter_db_optr {SCreateDBInfo}
|
||||
alter_db_optr(Y) ::= . { setDefaultCreateDbOption(&Y);}
|
||||
|
@ -270,21 +272,22 @@ alter_db_optr(Y) ::= alter_db_optr(Z) comp(X). { Y = Z; Y.compressionLeve
|
|||
alter_db_optr(Y) ::= alter_db_optr(Z) wal(X). { Y = Z; Y.walLevel = strtol(X.z, NULL, 10); }
|
||||
alter_db_optr(Y) ::= alter_db_optr(Z) fsync(X). { Y = Z; Y.fsyncPeriod = strtol(X.z, NULL, 10); }
|
||||
alter_db_optr(Y) ::= alter_db_optr(Z) update(X). { Y = Z; Y.update = strtol(X.z, NULL, 10); }
|
||||
alter_db_optr(Y) ::= alter_db_optr(Z) cachelast(X). { Y = Z; Y.cachelast = strtol(X.z, NULL, 10); }
|
||||
|
||||
%type typename {TAOS_FIELD}
|
||||
typename(A) ::= ids(X). {
|
||||
X.type = 0;
|
||||
tSQLSetColumnType (&A, &X);
|
||||
tSqlSetColumnType (&A, &X);
|
||||
}
|
||||
|
||||
//define binary type, e.g., binary(10), nchar(10)
|
||||
typename(A) ::= ids(X) LP signed(Y) RP. {
|
||||
if (Y <= 0) {
|
||||
X.type = 0;
|
||||
tSQLSetColumnType(&A, &X);
|
||||
tSqlSetColumnType(&A, &X);
|
||||
} else {
|
||||
X.type = -Y; // negative value of name length
|
||||
tSQLSetColumnType(&A, &X);
|
||||
tSqlSetColumnType(&A, &X);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -315,8 +318,8 @@ create_table_list(A) ::= create_table_list(X) create_from_stable(Z). {
|
|||
|
||||
%type create_table_args{SCreateTableSQL*}
|
||||
create_table_args(A) ::= ifnotexists(U) ids(V) cpxName(Z) LP columnlist(X) RP. {
|
||||
A = tSetCreateSQLElems(X, NULL, NULL, TSQL_CREATE_TABLE);
|
||||
setSQLInfo(pInfo, A, NULL, TSDB_SQL_CREATE_TABLE);
|
||||
A = tSetCreateSqlElems(X, NULL, NULL, TSQL_CREATE_TABLE);
|
||||
setSqlInfo(pInfo, A, NULL, TSDB_SQL_CREATE_TABLE);
|
||||
|
||||
V.n += Z.n;
|
||||
setCreatedTableName(pInfo, &V, &U);
|
||||
|
@ -324,8 +327,8 @@ create_table_args(A) ::= ifnotexists(U) ids(V) cpxName(Z) LP columnlist(X) RP. {
|
|||
|
||||
// create super table
|
||||
create_table_args(A) ::= ifnotexists(U) ids(V) cpxName(Z) LP columnlist(X) RP TAGS LP columnlist(Y) RP. {
|
||||
A = tSetCreateSQLElems(X, Y, NULL, TSQL_CREATE_STABLE);
|
||||
setSQLInfo(pInfo, A, NULL, TSDB_SQL_CREATE_TABLE);
|
||||
A = tSetCreateSqlElems(X, Y, NULL, TSQL_CREATE_STABLE);
|
||||
setSqlInfo(pInfo, A, NULL, TSDB_SQL_CREATE_TABLE);
|
||||
|
||||
V.n += Z.n;
|
||||
setCreatedTableName(pInfo, &V, &U);
|
||||
|
@ -343,8 +346,8 @@ create_from_stable(A) ::= ifnotexists(U) ids(V) cpxName(Z) USING ids(X) cpxName(
|
|||
// create stream
|
||||
// create table table_name as select count(*) from super_table_name interval(time)
|
||||
create_table_args(A) ::= ifnotexists(U) ids(V) cpxName(Z) AS select(S). {
|
||||
A = tSetCreateSQLElems(NULL, NULL, S, TSQL_CREATE_STREAM);
|
||||
setSQLInfo(pInfo, A, NULL, TSDB_SQL_CREATE_TABLE);
|
||||
A = tSetCreateSqlElems(NULL, NULL, S, TSQL_CREATE_STREAM);
|
||||
setSqlInfo(pInfo, A, NULL, TSDB_SQL_CREATE_TABLE);
|
||||
|
||||
V.n += Z.n;
|
||||
setCreatedTableName(pInfo, &V, &U);
|
||||
|
@ -359,7 +362,7 @@ columnlist(A) ::= column(X). {A = taosArrayInit(4, sizeof(T
|
|||
// The information used for a column is the name and type of column:
|
||||
// tinyint smallint int bigint float double bool timestamp binary(x) nchar(x)
|
||||
column(A) ::= ids(X) typename(Y). {
|
||||
tSQLSetColumnInfo(&A, &X, &Y);
|
||||
tSqlSetColumnInfo(&A, &X, &Y);
|
||||
}
|
||||
|
||||
%type tagitemlist {SArray*}
|
||||
|
@ -407,7 +410,7 @@ tagitem(A) ::= PLUS(X) FLOAT(Y). {
|
|||
%type select {SQuerySQL*}
|
||||
%destructor select {doDestroyQuerySql($$);}
|
||||
select(A) ::= SELECT(T) selcollist(W) from(X) where_opt(Y) interval_opt(K) fill_opt(F) sliding_opt(S) groupby_opt(P) orderby_opt(Z) having_opt(N) slimit_opt(G) limit_opt(L). {
|
||||
A = tSetQuerySQLElems(&T, W, X, Y, P, Z, &K, &S, F, &L, &G);
|
||||
A = tSetQuerySqlElems(&T, W, X, Y, P, Z, &K, &S, F, &L, &G);
|
||||
}
|
||||
|
||||
%type union {SSubclauseInfo*}
|
||||
|
@ -418,33 +421,33 @@ union(Y) ::= LP union(X) RP. { Y = X; }
|
|||
union(Y) ::= union(Z) UNION ALL select(X). { Y = appendSelectClause(Z, X); }
|
||||
union(Y) ::= union(Z) UNION ALL LP select(X) RP. { Y = appendSelectClause(Z, X); }
|
||||
|
||||
cmd ::= union(X). { setSQLInfo(pInfo, X, NULL, TSDB_SQL_SELECT); }
|
||||
cmd ::= union(X). { setSqlInfo(pInfo, X, NULL, TSDB_SQL_SELECT); }
|
||||
|
||||
// Support for the SQL exprssion without from & where subclauses, e.g.,
|
||||
// select current_database(),
|
||||
// select server_version(), select client_version(),
|
||||
// select server_state();
|
||||
select(A) ::= SELECT(T) selcollist(W). {
|
||||
A = tSetQuerySQLElems(&T, W, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
|
||||
A = tSetQuerySqlElems(&T, W, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
|
||||
}
|
||||
|
||||
// selcollist is a list of expressions that are to become the return
|
||||
// values of the SELECT statement. The "*" in statements like
|
||||
// "SELECT * FROM ..." is encoded as a special expression with an opcode of TK_ALL.
|
||||
%type selcollist {tSQLExprList*}
|
||||
%destructor selcollist {tSQLExprListDestroy($$);}
|
||||
%destructor selcollist {tSqlExprListDestroy($$);}
|
||||
|
||||
%type sclp {tSQLExprList*}
|
||||
%destructor sclp {tSQLExprListDestroy($$);}
|
||||
%destructor sclp {tSqlExprListDestroy($$);}
|
||||
sclp(A) ::= selcollist(X) COMMA. {A = X;}
|
||||
sclp(A) ::= . {A = 0;}
|
||||
selcollist(A) ::= sclp(P) expr(X) as(Y). {
|
||||
A = tSQLExprListAppend(P, X, Y.n?&Y:0);
|
||||
A = tSqlExprListAppend(P, X, Y.n?&Y:0);
|
||||
}
|
||||
|
||||
selcollist(A) ::= sclp(P) STAR. {
|
||||
tSQLExpr *pNode = tSQLExprIdValueCreate(NULL, TK_ALL);
|
||||
A = tSQLExprListAppend(P, pNode, 0);
|
||||
tSQLExpr *pNode = tSqlExprIdValueCreate(NULL, TK_ALL);
|
||||
A = tSqlExprListAppend(P, pNode, 0);
|
||||
}
|
||||
|
||||
// An option "AS <id>" phrase that can follow one of the expressions that
|
||||
|
@ -573,7 +576,7 @@ grouplist(A) ::= item(X). {
|
|||
|
||||
//having clause, ignore the input condition in having
|
||||
%type having_opt {tSQLExpr*}
|
||||
%destructor having_opt {tSQLExprDestroy($$);}
|
||||
%destructor having_opt {tSqlExprDestroy($$);}
|
||||
having_opt(A) ::=. {A = 0;}
|
||||
having_opt(A) ::= HAVING expr(X). {A = X;}
|
||||
|
||||
|
@ -595,7 +598,7 @@ slimit_opt(A) ::= SLIMIT signed(X) COMMA signed(Y).
|
|||
{A.limit = Y; A.offset = X;}
|
||||
|
||||
%type where_opt {tSQLExpr*}
|
||||
%destructor where_opt {tSQLExprDestroy($$);}
|
||||
%destructor where_opt {tSqlExprDestroy($$);}
|
||||
|
||||
where_opt(A) ::= . {A = 0;}
|
||||
where_opt(A) ::= WHERE expr(X). {A = X;}
|
||||
|
@ -603,67 +606,67 @@ where_opt(A) ::= WHERE expr(X). {A = X;}
|
|||
/////////////////////////// Expression Processing /////////////////////////////
|
||||
//
|
||||
%type expr {tSQLExpr*}
|
||||
%destructor expr {tSQLExprDestroy($$);}
|
||||
%destructor expr {tSqlExprDestroy($$);}
|
||||
|
||||
expr(A) ::= LP(X) expr(Y) RP(Z). {A = Y; A->token.z = X.z; A->token.n = (Z.z - X.z + 1);}
|
||||
|
||||
expr(A) ::= ID(X). { A = tSQLExprIdValueCreate(&X, TK_ID);}
|
||||
expr(A) ::= ID(X) DOT ID(Y). { X.n += (1+Y.n); A = tSQLExprIdValueCreate(&X, TK_ID);}
|
||||
expr(A) ::= ID(X) DOT STAR(Y). { X.n += (1+Y.n); A = tSQLExprIdValueCreate(&X, TK_ALL);}
|
||||
expr(A) ::= ID(X). { A = tSqlExprIdValueCreate(&X, TK_ID);}
|
||||
expr(A) ::= ID(X) DOT ID(Y). { X.n += (1+Y.n); A = tSqlExprIdValueCreate(&X, TK_ID);}
|
||||
expr(A) ::= ID(X) DOT STAR(Y). { X.n += (1+Y.n); A = tSqlExprIdValueCreate(&X, TK_ALL);}
|
||||
|
||||
expr(A) ::= INTEGER(X). { A = tSQLExprIdValueCreate(&X, TK_INTEGER);}
|
||||
expr(A) ::= MINUS(X) INTEGER(Y). { X.n += Y.n; X.type = TK_INTEGER; A = tSQLExprIdValueCreate(&X, TK_INTEGER);}
|
||||
expr(A) ::= PLUS(X) INTEGER(Y). { X.n += Y.n; X.type = TK_INTEGER; A = tSQLExprIdValueCreate(&X, TK_INTEGER);}
|
||||
expr(A) ::= FLOAT(X). { A = tSQLExprIdValueCreate(&X, TK_FLOAT);}
|
||||
expr(A) ::= MINUS(X) FLOAT(Y). { X.n += Y.n; X.type = TK_FLOAT; A = tSQLExprIdValueCreate(&X, TK_FLOAT);}
|
||||
expr(A) ::= PLUS(X) FLOAT(Y). { X.n += Y.n; X.type = TK_FLOAT; A = tSQLExprIdValueCreate(&X, TK_FLOAT);}
|
||||
expr(A) ::= STRING(X). { A = tSQLExprIdValueCreate(&X, TK_STRING);}
|
||||
expr(A) ::= NOW(X). { A = tSQLExprIdValueCreate(&X, TK_NOW); }
|
||||
expr(A) ::= VARIABLE(X). { A = tSQLExprIdValueCreate(&X, TK_VARIABLE);}
|
||||
expr(A) ::= BOOL(X). { A = tSQLExprIdValueCreate(&X, TK_BOOL);}
|
||||
expr(A) ::= INTEGER(X). { A = tSqlExprIdValueCreate(&X, TK_INTEGER);}
|
||||
expr(A) ::= MINUS(X) INTEGER(Y). { X.n += Y.n; X.type = TK_INTEGER; A = tSqlExprIdValueCreate(&X, TK_INTEGER);}
|
||||
expr(A) ::= PLUS(X) INTEGER(Y). { X.n += Y.n; X.type = TK_INTEGER; A = tSqlExprIdValueCreate(&X, TK_INTEGER);}
|
||||
expr(A) ::= FLOAT(X). { A = tSqlExprIdValueCreate(&X, TK_FLOAT);}
|
||||
expr(A) ::= MINUS(X) FLOAT(Y). { X.n += Y.n; X.type = TK_FLOAT; A = tSqlExprIdValueCreate(&X, TK_FLOAT);}
|
||||
expr(A) ::= PLUS(X) FLOAT(Y). { X.n += Y.n; X.type = TK_FLOAT; A = tSqlExprIdValueCreate(&X, TK_FLOAT);}
|
||||
expr(A) ::= STRING(X). { A = tSqlExprIdValueCreate(&X, TK_STRING);}
|
||||
expr(A) ::= NOW(X). { A = tSqlExprIdValueCreate(&X, TK_NOW); }
|
||||
expr(A) ::= VARIABLE(X). { A = tSqlExprIdValueCreate(&X, TK_VARIABLE);}
|
||||
expr(A) ::= BOOL(X). { A = tSqlExprIdValueCreate(&X, TK_BOOL);}
|
||||
|
||||
// ordinary functions: min(x), max(x), top(k, 20)
|
||||
expr(A) ::= ID(X) LP exprlist(Y) RP(E). { A = tSQLExprCreateFunction(Y, &X, &E, X.type); }
|
||||
expr(A) ::= ID(X) LP exprlist(Y) RP(E). { A = tSqlExprCreateFunction(Y, &X, &E, X.type); }
|
||||
|
||||
// for parsing sql functions with wildcard for parameters. e.g., count(*)/first(*)/last(*) operation
|
||||
expr(A) ::= ID(X) LP STAR RP(Y). { A = tSQLExprCreateFunction(NULL, &X, &Y, X.type); }
|
||||
expr(A) ::= ID(X) LP STAR RP(Y). { A = tSqlExprCreateFunction(NULL, &X, &Y, X.type); }
|
||||
|
||||
// is (not) null expression
|
||||
expr(A) ::= expr(X) IS NULL. {A = tSQLExprCreate(X, NULL, TK_ISNULL);}
|
||||
expr(A) ::= expr(X) IS NOT NULL. {A = tSQLExprCreate(X, NULL, TK_NOTNULL);}
|
||||
expr(A) ::= expr(X) IS NULL. {A = tSqlExprCreate(X, NULL, TK_ISNULL);}
|
||||
expr(A) ::= expr(X) IS NOT NULL. {A = tSqlExprCreate(X, NULL, TK_NOTNULL);}
|
||||
|
||||
// relational expression
|
||||
expr(A) ::= expr(X) LT expr(Y). {A = tSQLExprCreate(X, Y, TK_LT);}
|
||||
expr(A) ::= expr(X) GT expr(Y). {A = tSQLExprCreate(X, Y, TK_GT);}
|
||||
expr(A) ::= expr(X) LE expr(Y). {A = tSQLExprCreate(X, Y, TK_LE);}
|
||||
expr(A) ::= expr(X) GE expr(Y). {A = tSQLExprCreate(X, Y, TK_GE);}
|
||||
expr(A) ::= expr(X) NE expr(Y). {A = tSQLExprCreate(X, Y, TK_NE);}
|
||||
expr(A) ::= expr(X) EQ expr(Y). {A = tSQLExprCreate(X, Y, TK_EQ);}
|
||||
expr(A) ::= expr(X) LT expr(Y). {A = tSqlExprCreate(X, Y, TK_LT);}
|
||||
expr(A) ::= expr(X) GT expr(Y). {A = tSqlExprCreate(X, Y, TK_GT);}
|
||||
expr(A) ::= expr(X) LE expr(Y). {A = tSqlExprCreate(X, Y, TK_LE);}
|
||||
expr(A) ::= expr(X) GE expr(Y). {A = tSqlExprCreate(X, Y, TK_GE);}
|
||||
expr(A) ::= expr(X) NE expr(Y). {A = tSqlExprCreate(X, Y, TK_NE);}
|
||||
expr(A) ::= expr(X) EQ expr(Y). {A = tSqlExprCreate(X, Y, TK_EQ);}
|
||||
|
||||
expr(A) ::= expr(X) AND expr(Y). {A = tSQLExprCreate(X, Y, TK_AND);}
|
||||
expr(A) ::= expr(X) OR expr(Y). {A = tSQLExprCreate(X, Y, TK_OR); }
|
||||
expr(A) ::= expr(X) AND expr(Y). {A = tSqlExprCreate(X, Y, TK_AND);}
|
||||
expr(A) ::= expr(X) OR expr(Y). {A = tSqlExprCreate(X, Y, TK_OR); }
|
||||
|
||||
// binary arithmetic expression
|
||||
expr(A) ::= expr(X) PLUS expr(Y). {A = tSQLExprCreate(X, Y, TK_PLUS); }
|
||||
expr(A) ::= expr(X) MINUS expr(Y). {A = tSQLExprCreate(X, Y, TK_MINUS); }
|
||||
expr(A) ::= expr(X) STAR expr(Y). {A = tSQLExprCreate(X, Y, TK_STAR); }
|
||||
expr(A) ::= expr(X) SLASH expr(Y). {A = tSQLExprCreate(X, Y, TK_DIVIDE);}
|
||||
expr(A) ::= expr(X) REM expr(Y). {A = tSQLExprCreate(X, Y, TK_REM); }
|
||||
expr(A) ::= expr(X) PLUS expr(Y). {A = tSqlExprCreate(X, Y, TK_PLUS); }
|
||||
expr(A) ::= expr(X) MINUS expr(Y). {A = tSqlExprCreate(X, Y, TK_MINUS); }
|
||||
expr(A) ::= expr(X) STAR expr(Y). {A = tSqlExprCreate(X, Y, TK_STAR); }
|
||||
expr(A) ::= expr(X) SLASH expr(Y). {A = tSqlExprCreate(X, Y, TK_DIVIDE);}
|
||||
expr(A) ::= expr(X) REM expr(Y). {A = tSqlExprCreate(X, Y, TK_REM); }
|
||||
|
||||
// like expression
|
||||
expr(A) ::= expr(X) LIKE expr(Y). {A = tSQLExprCreate(X, Y, TK_LIKE); }
|
||||
expr(A) ::= expr(X) LIKE expr(Y). {A = tSqlExprCreate(X, Y, TK_LIKE); }
|
||||
|
||||
//in expression
|
||||
expr(A) ::= expr(X) IN LP exprlist(Y) RP. {A = tSQLExprCreate(X, (tSQLExpr*)Y, TK_IN); }
|
||||
expr(A) ::= expr(X) IN LP exprlist(Y) RP. {A = tSqlExprCreate(X, (tSQLExpr*)Y, TK_IN); }
|
||||
|
||||
%type exprlist {tSQLExprList*}
|
||||
%destructor exprlist {tSQLExprListDestroy($$);}
|
||||
%destructor exprlist {tSqlExprListDestroy($$);}
|
||||
|
||||
%type expritem {tSQLExpr*}
|
||||
%destructor expritem {tSQLExprDestroy($$);}
|
||||
%destructor expritem {tSqlExprDestroy($$);}
|
||||
|
||||
exprlist(A) ::= exprlist(X) COMMA expritem(Y). {A = tSQLExprListAppend(X,Y,0);}
|
||||
exprlist(A) ::= expritem(X). {A = tSQLExprListAppend(0,X,0);}
|
||||
exprlist(A) ::= exprlist(X) COMMA expritem(Y). {A = tSqlExprListAppend(X,Y,0);}
|
||||
exprlist(A) ::= expritem(X). {A = tSqlExprListAppend(0,X,0);}
|
||||
expritem(A) ::= expr(X). {A = X;}
|
||||
expritem(A) ::= . {A = 0;}
|
||||
|
||||
|
@ -673,8 +676,8 @@ cmd ::= RESET QUERY CACHE. { setDCLSQLElems(pInfo, TSDB_SQL_RESET_CACHE, 0);}
|
|||
///////////////////////////////////ALTER TABLE statement//////////////////////////////////
|
||||
cmd ::= ALTER TABLE ids(X) cpxName(F) ADD COLUMN columnlist(A). {
|
||||
X.n += F.n;
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSQLElems(&X, A, NULL, TSDB_ALTER_TABLE_ADD_COLUMN);
|
||||
setSQLInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSqlElems(&X, A, NULL, TSDB_ALTER_TABLE_ADD_COLUMN);
|
||||
setSqlInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
}
|
||||
|
||||
cmd ::= ALTER TABLE ids(X) cpxName(F) DROP COLUMN ids(A). {
|
||||
|
@ -683,15 +686,15 @@ cmd ::= ALTER TABLE ids(X) cpxName(F) DROP COLUMN ids(A). {
|
|||
toTSDBType(A.type);
|
||||
SArray* K = tVariantListAppendToken(NULL, &A, -1);
|
||||
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSQLElems(&X, NULL, K, TSDB_ALTER_TABLE_DROP_COLUMN);
|
||||
setSQLInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSqlElems(&X, NULL, K, TSDB_ALTER_TABLE_DROP_COLUMN);
|
||||
setSqlInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
}
|
||||
|
||||
//////////////////////////////////ALTER TAGS statement/////////////////////////////////////
|
||||
cmd ::= ALTER TABLE ids(X) cpxName(Y) ADD TAG columnlist(A). {
|
||||
X.n += Y.n;
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSQLElems(&X, A, NULL, TSDB_ALTER_TABLE_ADD_TAG_COLUMN);
|
||||
setSQLInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSqlElems(&X, A, NULL, TSDB_ALTER_TABLE_ADD_TAG_COLUMN);
|
||||
setSqlInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
}
|
||||
cmd ::= ALTER TABLE ids(X) cpxName(Z) DROP TAG ids(Y). {
|
||||
X.n += Z.n;
|
||||
|
@ -699,8 +702,8 @@ cmd ::= ALTER TABLE ids(X) cpxName(Z) DROP TAG ids(Y). {
|
|||
toTSDBType(Y.type);
|
||||
SArray* A = tVariantListAppendToken(NULL, &Y, -1);
|
||||
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSQLElems(&X, NULL, A, TSDB_ALTER_TABLE_DROP_TAG_COLUMN);
|
||||
setSQLInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSqlElems(&X, NULL, A, TSDB_ALTER_TABLE_DROP_TAG_COLUMN);
|
||||
setSqlInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
}
|
||||
|
||||
cmd ::= ALTER TABLE ids(X) cpxName(F) CHANGE TAG ids(Y) ids(Z). {
|
||||
|
@ -712,8 +715,8 @@ cmd ::= ALTER TABLE ids(X) cpxName(F) CHANGE TAG ids(Y) ids(Z). {
|
|||
toTSDBType(Z.type);
|
||||
A = tVariantListAppendToken(A, &Z, -1);
|
||||
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSQLElems(&X, NULL, A, TSDB_ALTER_TABLE_CHANGE_TAG_COLUMN);
|
||||
setSQLInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSqlElems(&X, NULL, A, TSDB_ALTER_TABLE_CHANGE_TAG_COLUMN);
|
||||
setSqlInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
}
|
||||
|
||||
cmd ::= ALTER TABLE ids(X) cpxName(F) SET TAG ids(Y) EQ tagitem(Z). {
|
||||
|
@ -723,14 +726,14 @@ cmd ::= ALTER TABLE ids(X) cpxName(F) SET TAG ids(Y) EQ tagitem(Z). {
|
|||
SArray* A = tVariantListAppendToken(NULL, &Y, -1);
|
||||
A = tVariantListAppend(A, &Z, -1);
|
||||
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSQLElems(&X, NULL, A, TSDB_ALTER_TABLE_UPDATE_TAG_VAL);
|
||||
setSQLInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
SAlterTableSQL* pAlterTable = tAlterTableSqlElems(&X, NULL, A, TSDB_ALTER_TABLE_UPDATE_TAG_VAL);
|
||||
setSqlInfo(pInfo, pAlterTable, NULL, TSDB_SQL_ALTER_TABLE);
|
||||
}
|
||||
|
||||
////////////////////////////////////////kill statement///////////////////////////////////////
|
||||
cmd ::= KILL CONNECTION INTEGER(Y). {setKillSQL(pInfo, TSDB_SQL_KILL_CONNECTION, &Y);}
|
||||
cmd ::= KILL STREAM INTEGER(X) COLON(Z) INTEGER(Y). {X.n += (Z.n + Y.n); setKillSQL(pInfo, TSDB_SQL_KILL_STREAM, &X);}
|
||||
cmd ::= KILL QUERY INTEGER(X) COLON(Z) INTEGER(Y). {X.n += (Z.n + Y.n); setKillSQL(pInfo, TSDB_SQL_KILL_QUERY, &X);}
|
||||
cmd ::= KILL CONNECTION INTEGER(Y). {setKillSql(pInfo, TSDB_SQL_KILL_CONNECTION, &Y);}
|
||||
cmd ::= KILL STREAM INTEGER(X) COLON(Z) INTEGER(Y). {X.n += (Z.n + Y.n); setKillSql(pInfo, TSDB_SQL_KILL_STREAM, &X);}
|
||||
cmd ::= KILL QUERY INTEGER(X) COLON(Z) INTEGER(Y). {X.n += (Z.n + Y.n); setKillSql(pInfo, TSDB_SQL_KILL_QUERY, &X);}
|
||||
|
||||
%fallback ID ABORT AFTER ASC ATTACH BEFORE BEGIN CASCADE CLUSTER CONFLICT COPY DATABASE DEFERRED
|
||||
DELIMITERS DESC DETACH EACH END EXPLAIN FAIL FOR GLOB IGNORE IMMEDIATE INITIALLY INSTEAD
|
||||
|
|
|
@ -4662,7 +4662,6 @@ static int32_t setupQueryHandle(void* tsdb, SQInfo* pQInfo, bool isSTableQuery)
|
|||
|
||||
// update the query time window
|
||||
pQuery->window = cond.twindow;
|
||||
|
||||
if (pQInfo->tableGroupInfo.numOfTables == 0) {
|
||||
pQInfo->tableqinfoGroupInfo.numOfTables = 0;
|
||||
} else {
|
||||
|
|
|
@ -846,5 +846,6 @@ void setDefaultCreateDbOption(SCreateDBInfo *pDBInfo) {
|
|||
pDBInfo->keep = NULL;
|
||||
|
||||
pDBInfo->update = -1;
|
||||
pDBInfo->cachelast = 0;
|
||||
memset(&pDBInfo->precision, 0, sizeof(SStrToken));
|
||||
}
|
||||
|
|
|
@ -238,6 +238,7 @@ static SKeyword keywordTable[] = {
|
|||
{"SUM_IRATE", TK_SUM_IRATE},
|
||||
{"AVG_RATE", TK_AVG_RATE},
|
||||
{"AVG_IRATE", TK_AVG_IRATE},
|
||||
{"CACHELAST", TK_CACHELAST},
|
||||
};
|
||||
|
||||
static const char isIdChar[] = {
|
||||
|
|
2455
src/query/src/sql.c
2455
src/query/src/sql.c
File diff suppressed because it is too large
Load Diff
|
@ -66,7 +66,8 @@ typedef struct STable {
|
|||
SSkipList* pIndex; // For TSDB_SUPER_TABLE, it is the skiplist index
|
||||
void* eventHandler; // TODO
|
||||
void* streamHandler; // TODO
|
||||
TSKEY lastKey; // lastkey inserted in this table, initialized as 0, TODO: make a structure
|
||||
TSKEY lastKey;
|
||||
SDataRow lastRow;
|
||||
char* sql;
|
||||
void* cqhandle;
|
||||
SRWLatch latch; // TODO: implementa latch functions
|
||||
|
@ -360,8 +361,11 @@ typedef struct {
|
|||
#define TABLE_UID(t) (t)->tableId.uid
|
||||
#define TABLE_TID(t) (t)->tableId.tid
|
||||
#define TABLE_SUID(t) (t)->suid
|
||||
#define TABLE_LASTKEY(t) (t)->lastKey
|
||||
#define TSDB_META_FILE_MAGIC(m) KVSTORE_MAGIC((m)->pStore)
|
||||
#define TSDB_RLOCK_TABLE(t) taosRLockLatch(&((t)->latch))
|
||||
#define TSDB_RUNLOCK_TABLE(t) taosRUnLockLatch(&((t)->latch))
|
||||
#define TSDB_WLOCK_TABLE(t) taosWLockLatch(&((t)->latch))
|
||||
#define TSDB_WUNLOCK_TABLE(t) taosWUnLockLatch(&((t)->latch))
|
||||
|
||||
STsdbMeta* tsdbNewMeta(STsdbCfg* pCfg);
|
||||
void tsdbFreeMeta(STsdbMeta* pMeta);
|
||||
|
@ -391,7 +395,7 @@ static FORCE_INLINE STSchema* tsdbGetTableSchemaImpl(STable* pTable, bool lock,
|
|||
STSchema* pSchema = NULL;
|
||||
STSchema* pTSchema = NULL;
|
||||
|
||||
if (lock) taosRLockLatch(&(pDTable->latch));
|
||||
if (lock) TSDB_RLOCK_TABLE(pDTable);
|
||||
if (version < 0) { // get the latest version of schema
|
||||
pTSchema = pDTable->schema[pDTable->numOfSchemas - 1];
|
||||
} else { // get the schema with version
|
||||
|
@ -413,7 +417,7 @@ static FORCE_INLINE STSchema* tsdbGetTableSchemaImpl(STable* pTable, bool lock,
|
|||
}
|
||||
|
||||
_exit:
|
||||
if (lock) taosRUnLockLatch(&(pDTable->latch));
|
||||
if (lock) TSDB_RUNLOCK_TABLE(pDTable);
|
||||
return pSchema;
|
||||
}
|
||||
|
||||
|
@ -433,6 +437,11 @@ static FORCE_INLINE STSchema *tsdbGetTableTagSchema(STable *pTable) {
|
|||
}
|
||||
}
|
||||
|
||||
static FORCE_INLINE TSKEY tsdbGetTableLastKeyImpl(STable* pTable) {
|
||||
ASSERT(pTable->lastRow == NULL || pTable->lastKey == dataRowKey(pTable->lastRow));
|
||||
return pTable->lastKey;
|
||||
}
|
||||
|
||||
// ------------------ tsdbBuffer.c
|
||||
#define TSDB_BUFFER_RESERVE 1024 // Reseve 1K as commit threshold
|
||||
|
||||
|
|
|
@ -225,7 +225,7 @@ static int tsdbCommitToFile(STsdbRepo *pRepo, int fid, SCommitIter *iters, SRWHe
|
|||
SCommitIter *pIter = iters + tid;
|
||||
if (pIter->pTable == NULL) continue;
|
||||
|
||||
taosRLockLatch(&(pIter->pTable->latch));
|
||||
TSDB_RLOCK_TABLE(pIter->pTable);
|
||||
|
||||
if (tsdbSetHelperTable(pHelper, pIter->pTable, pRepo) < 0) goto _err;
|
||||
|
||||
|
@ -236,7 +236,7 @@ static int tsdbCommitToFile(STsdbRepo *pRepo, int fid, SCommitIter *iters, SRWHe
|
|||
}
|
||||
|
||||
if (tsdbCommitTableData(pHelper, pIter, pDataCols, maxKey) < 0) {
|
||||
taosRUnLockLatch(&(pIter->pTable->latch));
|
||||
TSDB_RUNLOCK_TABLE(pIter->pTable);
|
||||
tsdbError("vgId:%d failed to write data of table %s tid %d uid %" PRIu64 " since %s", REPO_ID(pRepo),
|
||||
TABLE_CHAR_NAME(pIter->pTable), TABLE_TID(pIter->pTable), TABLE_UID(pIter->pTable),
|
||||
tstrerror(terrno));
|
||||
|
@ -244,7 +244,7 @@ static int tsdbCommitToFile(STsdbRepo *pRepo, int fid, SCommitIter *iters, SRWHe
|
|||
}
|
||||
}
|
||||
|
||||
taosRUnLockLatch(&(pIter->pTable->latch));
|
||||
TSDB_RUNLOCK_TABLE(pIter->pTable);
|
||||
|
||||
// Move the last block to the new .l file if neccessary
|
||||
if (tsdbMoveLastBlockIfNeccessary(pHelper) < 0) {
|
||||
|
|
|
@ -77,9 +77,9 @@ int32_t tsdbCreateRepo(char *rootDir, STsdbCfg *pCfg) {
|
|||
|
||||
tsdbDebug(
|
||||
"vgId:%d tsdb env create succeed! cacheBlockSize %d totalBlocks %d daysPerFile %d keep "
|
||||
"%d minRowsPerFileBlock %d maxRowsPerFileBlock %d precision %d compression %d",
|
||||
"%d minRowsPerFileBlock %d maxRowsPerFileBlock %d precision %d compression %d update %d cacheLastRow %d",
|
||||
pCfg->tsdbId, pCfg->cacheBlockSize, pCfg->totalBlocks, pCfg->daysPerFile, pCfg->keep, pCfg->minRowsPerFileBlock,
|
||||
pCfg->maxRowsPerFileBlock, pCfg->precision, pCfg->compression);
|
||||
pCfg->maxRowsPerFileBlock, pCfg->precision, pCfg->compression, pCfg->update, pCfg->cacheLastRow);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -281,6 +281,10 @@ int32_t tsdbConfigRepo(TSDB_REPO_T *repo, STsdbCfg *pCfg) {
|
|||
config.totalBlocks = pCfg->totalBlocks;
|
||||
configChanged = true;
|
||||
}
|
||||
if (pRCfg->cacheLastRow != pCfg->cacheLastRow) {
|
||||
config.cacheLastRow = pCfg->cacheLastRow;
|
||||
configChanged = true;
|
||||
}
|
||||
|
||||
if (configChanged) {
|
||||
if (tsdbSaveConfig(pRepo->rootDir, &config) < 0) {
|
||||
|
@ -475,6 +479,9 @@ static int32_t tsdbCheckAndSetDefaultCfg(STsdbCfg *pCfg) {
|
|||
// update check
|
||||
if (pCfg->update != 0) pCfg->update = 1;
|
||||
|
||||
// update cacheLastRow
|
||||
if (pCfg->cacheLastRow != 0) pCfg->cacheLastRow = 1;
|
||||
|
||||
return 0;
|
||||
|
||||
_err:
|
||||
|
@ -692,10 +699,12 @@ static void tsdbFreeRepo(STsdbRepo *pRepo) {
|
|||
}
|
||||
}
|
||||
|
||||
static int tsdbRestoreInfo(STsdbRepo *pRepo) {
|
||||
static int tsdbRestoreInfo(STsdbRepo *pRepo) { // TODO
|
||||
STsdbMeta * pMeta = pRepo->tsdbMeta;
|
||||
STsdbFileH *pFileH = pRepo->tsdbFileH;
|
||||
SFileGroup *pFGroup = NULL;
|
||||
STsdbCfg * pCfg = &(pRepo->config);
|
||||
SCompBlock *pBlock = NULL;
|
||||
|
||||
SFileGroupIter iter;
|
||||
SRWHelper rhelper = {0};
|
||||
|
@ -713,7 +722,32 @@ static int tsdbRestoreInfo(STsdbRepo *pRepo) {
|
|||
if (tsdbSetHelperTable(&rhelper, pTable, pRepo) < 0) goto _err;
|
||||
SCompIdx *pIdx = &(rhelper.curCompIdx);
|
||||
|
||||
if (pIdx->offset > 0 && pTable->lastKey < pIdx->maxKey) pTable->lastKey = pIdx->maxKey;
|
||||
TSKEY lastKey = tsdbGetTableLastKeyImpl(pTable);
|
||||
if (pIdx->offset > 0 && lastKey < pIdx->maxKey) {
|
||||
pTable->lastKey = pIdx->maxKey;
|
||||
if (pCfg->cacheLastRow) { // load the block of data
|
||||
if (tsdbLoadCompInfo(&rhelper, NULL) < 0) goto _err;
|
||||
|
||||
pBlock = rhelper.pCompInfo->blocks + pIdx->numOfBlocks - 1;
|
||||
if (tsdbLoadBlockData(&rhelper, pBlock, NULL) < 0) goto _err;
|
||||
|
||||
// construct the data row
|
||||
ASSERT(pTable->lastRow == NULL);
|
||||
STSchema *pSchema = tsdbGetTableSchema(pTable);
|
||||
pTable->lastRow = taosTMalloc(schemaTLen(pSchema));
|
||||
if (pTable->lastRow == NULL) {
|
||||
goto _err;
|
||||
}
|
||||
|
||||
tdInitDataRow(pTable->lastRow, pSchema);
|
||||
for (int icol = 0; icol < schemaNCols(pSchema); icol++) {
|
||||
STColumn *pCol = schemaColAt(pSchema, icol);
|
||||
SDataCol *pDataCol = rhelper.pDataCols[0]->cols + icol;
|
||||
tdAppendColVal(pTable->lastRow, tdGetColDataOfRow(pDataCol, pBlock->numOfRows - 1), pCol->type, pCol->bytes,
|
||||
pCol->offset);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -800,6 +834,7 @@ static int tsdbEncodeCfg(void **buf, STsdbCfg *pCfg) {
|
|||
tlen += taosEncodeFixedI8(buf, pCfg->precision);
|
||||
tlen += taosEncodeFixedI8(buf, pCfg->compression);
|
||||
tlen += taosEncodeFixedI8(buf, pCfg->update);
|
||||
tlen += taosEncodeFixedI8(buf, pCfg->cacheLastRow);
|
||||
|
||||
return tlen;
|
||||
}
|
||||
|
@ -817,6 +852,7 @@ static void *tsdbDecodeCfg(void *buf, STsdbCfg *pCfg) {
|
|||
buf = taosDecodeFixedI8(buf, &(pCfg->precision));
|
||||
buf = taosDecodeFixedI8(buf, &(pCfg->compression));
|
||||
buf = taosDecodeFixedI8(buf, &(pCfg->update));
|
||||
buf = taosDecodeFixedI8(buf, &(pCfg->cacheLastRow));
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
|
|
@ -36,6 +36,7 @@ static int tsdbGetSubmitMsgNext(SSubmitMsgIter *pIter, SSubmitBlk **pPB
|
|||
static int tsdbCheckTableSchema(STsdbRepo *pRepo, SSubmitBlk *pBlock, STable *pTable);
|
||||
static int tsdbInsertDataToTableImpl(STsdbRepo *pRepo, STable *pTable, void **rows, int rowCounter);
|
||||
static void tsdbFreeRows(STsdbRepo *pRepo, void **rows, int rowCounter);
|
||||
static int tsdbUpdateTableLatestInfo(STsdbRepo *pRepo, STable *pTable, SDataRow row);
|
||||
|
||||
static FORCE_INLINE int tsdbCheckRowRange(STsdbRepo *pRepo, STable *pTable, SDataRow row, TSKEY minKey, TSKEY maxKey,
|
||||
TSKEY now);
|
||||
|
@ -663,9 +664,10 @@ static int tsdbCopyRowToMem(STsdbRepo *pRepo, SDataRow row, STable *pTable, void
|
|||
return -1;
|
||||
}
|
||||
|
||||
if (key > TABLE_LASTKEY(pTable)) {
|
||||
TSKEY lastKey = tsdbGetTableLastKeyImpl(pTable);
|
||||
if (key > lastKey) {
|
||||
tsdbTrace("vgId:%d skip to delete row key %" PRId64 " which is larger than table lastKey %" PRId64,
|
||||
REPO_ID(pRepo), key, TABLE_LASTKEY(pTable));
|
||||
REPO_ID(pRepo), key, lastKey);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
@ -846,8 +848,10 @@ static int tsdbInsertDataToTableImpl(STsdbRepo *pRepo, STable *pTable, void **ro
|
|||
if (pTableData->keyLast < dataRowKey(rows[rowCounter - 1])) pTableData->keyLast = dataRowKey(rows[rowCounter - 1]);
|
||||
pTableData->numOfRows += dsize;
|
||||
|
||||
// TODO: impl delete row thing
|
||||
if (TABLE_LASTKEY(pTable) < dataRowKey(rows[rowCounter-1])) TABLE_LASTKEY(pTable) = dataRowKey(rows[rowCounter-1]);
|
||||
// update table latest info
|
||||
if (tsdbUpdateTableLatestInfo(pRepo, pTable, rows[rowCounter - 1]) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -890,3 +894,37 @@ static void tsdbFreeRows(STsdbRepo *pRepo, void **rows, int rowCounter) {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int tsdbUpdateTableLatestInfo(STsdbRepo *pRepo, STable *pTable, SDataRow row) {
|
||||
STsdbCfg *pCfg = &pRepo->config;
|
||||
|
||||
if (tsdbGetTableLastKeyImpl(pTable) < dataRowKey(row)) {
|
||||
if (pCfg->cacheLastRow || pTable->lastRow != NULL) {
|
||||
SDataRow nrow = pTable->lastRow;
|
||||
if (taosTSizeof(nrow) < dataRowLen(row)) {
|
||||
SDataRow orow = nrow;
|
||||
nrow = taosTMalloc(dataRowLen(row));
|
||||
if (nrow == NULL) {
|
||||
terrno = TSDB_CODE_TDB_OUT_OF_MEMORY;
|
||||
return -1;
|
||||
}
|
||||
|
||||
dataRowCpy(nrow, row);
|
||||
TSDB_WLOCK_TABLE(pTable);
|
||||
pTable->lastKey = dataRowKey(row);
|
||||
pTable->lastRow = nrow;
|
||||
TSDB_WUNLOCK_TABLE(pTable);
|
||||
taosTZfree(orow);
|
||||
} else {
|
||||
TSDB_WLOCK_TABLE(pTable);
|
||||
pTable->lastKey = dataRowKey(row);
|
||||
dataRowCpy(nrow, row);
|
||||
TSDB_WUNLOCK_TABLE(pTable);
|
||||
}
|
||||
} else {
|
||||
pTable->lastKey = dataRowKey(row);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -377,11 +377,11 @@ int tsdbUpdateTableTagValue(TSDB_REPO_T *repo, SUpdateTableTagValMsg *pMsg) {
|
|||
|
||||
// Chage in memory
|
||||
if (pNewSchema != NULL) { // change super table tag schema
|
||||
taosWLockLatch(&(pTable->pSuper->latch));
|
||||
TSDB_WLOCK_TABLE(pTable->pSuper);
|
||||
STSchema *pOldSchema = pTable->pSuper->tagSchema;
|
||||
pTable->pSuper->tagSchema = pNewSchema;
|
||||
tdFreeSchema(pOldSchema);
|
||||
taosWUnLockLatch(&(pTable->pSuper->latch));
|
||||
TSDB_WUNLOCK_TABLE(pTable->pSuper);
|
||||
}
|
||||
|
||||
bool isChangeIndexCol = (pMsg->colId == colColId(schemaColAt(pTable->pSuper->tagSchema, 0)));
|
||||
|
@ -392,9 +392,9 @@ int tsdbUpdateTableTagValue(TSDB_REPO_T *repo, SUpdateTableTagValMsg *pMsg) {
|
|||
tsdbWLockRepoMeta(pRepo);
|
||||
tsdbRemoveTableFromIndex(pMeta, pTable);
|
||||
}
|
||||
taosWLockLatch(&(pTable->latch));
|
||||
TSDB_WLOCK_TABLE(pTable);
|
||||
tdSetKVRowDataOfCol(&(pTable->tagVal), pMsg->colId, pMsg->type, POINTER_SHIFT(pMsg->data, pMsg->schemaLen));
|
||||
taosWUnLockLatch(&(pTable->latch));
|
||||
TSDB_WUNLOCK_TABLE(pTable);
|
||||
if (isChangeIndexCol) {
|
||||
tsdbAddTableIntoIndex(pMeta, pTable, false);
|
||||
tsdbUnlockRepoMeta(pRepo);
|
||||
|
@ -587,7 +587,7 @@ void tsdbUpdateTableSchema(STsdbRepo *pRepo, STable *pTable, STSchema *pSchema,
|
|||
STable *pCTable = (TABLE_TYPE(pTable) == TSDB_CHILD_TABLE) ? pTable->pSuper : pTable;
|
||||
ASSERT(schemaVersion(pSchema) > schemaVersion(pCTable->schema[pCTable->numOfSchemas - 1]));
|
||||
|
||||
taosWLockLatch(&(pCTable->latch));
|
||||
TSDB_WLOCK_TABLE(pCTable);
|
||||
if (pCTable->numOfSchemas < TSDB_MAX_TABLE_SCHEMAS) {
|
||||
pCTable->schema[pCTable->numOfSchemas++] = pSchema;
|
||||
} else {
|
||||
|
@ -599,7 +599,7 @@ void tsdbUpdateTableSchema(STsdbRepo *pRepo, STable *pTable, STSchema *pSchema,
|
|||
|
||||
if (schemaNCols(pSchema) > pMeta->maxCols) pMeta->maxCols = schemaNCols(pSchema);
|
||||
if (schemaTLen(pSchema) > pMeta->maxRowBytes) pMeta->maxRowBytes = schemaTLen(pSchema);
|
||||
taosWUnLockLatch(&(pCTable->latch));
|
||||
TSDB_WUNLOCK_TABLE(pCTable);
|
||||
|
||||
if (insertAct) {
|
||||
int tlen = tsdbGetTableEncodeSize(TSDB_UPDATE_META, pCTable);
|
||||
|
@ -775,6 +775,7 @@ static void tsdbFreeTable(STable *pTable) {
|
|||
kvRowFree(pTable->tagVal);
|
||||
|
||||
tSkipListDestroy(pTable->pIndex);
|
||||
taosTZfree(pTable->lastRow);
|
||||
tfree(pTable->sql);
|
||||
free(pTable);
|
||||
}
|
||||
|
|
|
@ -110,6 +110,7 @@ typedef struct STsdbQueryHandle {
|
|||
SArray* pTableCheckInfo; // SArray<STableCheckInfo>
|
||||
int32_t activeIndex;
|
||||
bool checkFiles; // check file stage
|
||||
bool cachelastrow; // check if last row cached
|
||||
void* qinfo; // query info handle, for debug purpose
|
||||
int32_t type; // query type: retrieve all data blocks, 2. retrieve only last row, 3. retrieve direct prev|next rows
|
||||
SFileGroup* pFileGroup;
|
||||
|
@ -133,7 +134,9 @@ typedef struct STableGroupSupporter {
|
|||
STSchema* pTagSchema;
|
||||
} STableGroupSupporter;
|
||||
|
||||
static STimeWindow changeTableGroupByLastrow(STableGroupInfo *groupList);
|
||||
static STimeWindow updateLastrowForEachGroup(STableGroupInfo *groupList);
|
||||
static int32_t checkForCachedLastRow(STsdbQueryHandle* pQueryHandle, STableGroupInfo *groupList);
|
||||
static int32_t tsdbGetCachedLastRow(STable* pTable, SDataRow* pRes, TSKEY* lastKey);
|
||||
|
||||
static void changeQueryHandleForInterpQuery(TsdbQueryHandleT pHandle);
|
||||
static void doMergeTwoLevelData(STsdbQueryHandle* pQueryHandle, STableCheckInfo* pCheckInfo, SCompBlock* pBlock);
|
||||
|
@ -370,7 +373,7 @@ TsdbQueryHandleT* tsdbQueryTables(TSDB_REPO_T* tsdb, STsdbQueryCond* pCond, STab
|
|||
}
|
||||
|
||||
TsdbQueryHandleT tsdbQueryLastRow(TSDB_REPO_T *tsdb, STsdbQueryCond *pCond, STableGroupInfo *groupList, void* qinfo, SMemRef* pMemRef) {
|
||||
pCond->twindow = changeTableGroupByLastrow(groupList);
|
||||
pCond->twindow = updateLastrowForEachGroup(groupList);
|
||||
|
||||
// no qualified table
|
||||
if (groupList->numOfTables == 0) {
|
||||
|
@ -378,8 +381,14 @@ TsdbQueryHandleT tsdbQueryLastRow(TSDB_REPO_T *tsdb, STsdbQueryCond *pCond, STab
|
|||
}
|
||||
|
||||
STsdbQueryHandle *pQueryHandle = (STsdbQueryHandle*) tsdbQueryTables(tsdb, pCond, groupList, qinfo, pMemRef);
|
||||
int32_t code = checkForCachedLastRow(pQueryHandle, groupList);
|
||||
if (code != TSDB_CODE_SUCCESS) { // set the numOfTables to be 0
|
||||
terrno = code;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
assert(pCond->order == TSDB_ORDER_ASC && pCond->twindow.skey <= pCond->twindow.ekey);
|
||||
pQueryHandle->type = TSDB_QUERY_TYPE_LAST;
|
||||
return pQueryHandle;
|
||||
}
|
||||
|
||||
|
@ -2144,6 +2153,39 @@ bool tsdbNextDataBlock(TsdbQueryHandleT* pHandle) {
|
|||
// restore the pMemRef
|
||||
pQueryHandle->pMemRef = pMemRef;
|
||||
return ret;
|
||||
} else if (pQueryHandle->type == TSDB_QUERY_TYPE_LAST && pQueryHandle->cachelastrow) {
|
||||
// the last row is cached in buffer, return it directly.
|
||||
// here note that the pQueryHandle->window must be the TS_INITIALIZER
|
||||
int32_t numOfCols = (int32_t)(QH_GET_NUM_OF_COLS(pQueryHandle));
|
||||
SQueryFilePos* cur = &pQueryHandle->cur;
|
||||
|
||||
SDataRow pRow = NULL;
|
||||
TSKEY key = TSKEY_INITIAL_VAL;
|
||||
int32_t step = ASCENDING_TRAVERSE(pQueryHandle->order)? 1:-1;
|
||||
|
||||
if (++pQueryHandle->activeIndex < numOfTables) {
|
||||
STableCheckInfo* pCheckInfo = taosArrayGet(pQueryHandle->pTableCheckInfo, pQueryHandle->activeIndex);
|
||||
int32_t ret = tsdbGetCachedLastRow(pCheckInfo->pTableObj, &pRow, &key);
|
||||
if (ret != TSDB_CODE_SUCCESS) {
|
||||
return false;
|
||||
}
|
||||
|
||||
copyOneRowFromMem(pQueryHandle, pQueryHandle->outputCapacity, 0, pRow, numOfCols, pCheckInfo->pTableObj);
|
||||
tfree(pRow);
|
||||
|
||||
// update the last key value
|
||||
pCheckInfo->lastKey = key + step;
|
||||
|
||||
cur->rows = 1; // only one row
|
||||
cur->lastKey = key + step;
|
||||
cur->mixBlock = true;
|
||||
cur->win.skey = key;
|
||||
cur->win.ekey = key;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
if (pQueryHandle->checkFiles) {
|
||||
|
@ -2176,7 +2218,57 @@ bool tsdbNextDataBlock(TsdbQueryHandleT* pHandle) {
|
|||
return ret;
|
||||
}
|
||||
|
||||
STimeWindow changeTableGroupByLastrow(STableGroupInfo *groupList) {
|
||||
/*
|
||||
* 1. no data at all (pTable->lastKey = TSKEY_INITIAL_VAL), just return TSKEY_INITIAL_VAL
|
||||
* 2. has data but not loaded, just return lastKey but not set pRes
|
||||
* 3. has data and loaded, return lastKey and set pRes
|
||||
*/
|
||||
int32_t tsdbGetCachedLastRow(STable* pTable, SDataRow* pRes, TSKEY* lastKey) {
|
||||
TSDB_RLOCK_TABLE(pTable);
|
||||
*lastKey = pTable->lastKey;
|
||||
|
||||
if ((*lastKey) != TSKEY_INITIAL_VAL && pTable->lastRow) {
|
||||
*pRes = tdDataRowDup(pTable->lastRow);
|
||||
if (*pRes == NULL) {
|
||||
TSDB_RUNLOCK_TABLE(pTable);
|
||||
return TSDB_CODE_TDB_OUT_OF_MEMORY;
|
||||
}
|
||||
}
|
||||
|
||||
TSDB_RUNLOCK_TABLE(pTable);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
int32_t checkForCachedLastRow(STsdbQueryHandle* pQueryHandle, STableGroupInfo *groupList) {
|
||||
assert(pQueryHandle != NULL && groupList != NULL);
|
||||
|
||||
SDataRow pRow = NULL;
|
||||
TSKEY key = TSKEY_INITIAL_VAL;
|
||||
|
||||
SArray* group = taosArrayGetP(groupList->pGroupList, 0);
|
||||
assert(group != NULL);
|
||||
|
||||
STableKeyInfo* pInfo = (STableKeyInfo*)taosArrayGet(group, 0);
|
||||
|
||||
int32_t code = tsdbGetCachedLastRow(pInfo->pTable, &pRow, &key);
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
pQueryHandle->cachelastrow = false;
|
||||
} else {
|
||||
pQueryHandle->cachelastrow = (pRow != NULL);
|
||||
}
|
||||
|
||||
// update the tsdb query time range
|
||||
if (pQueryHandle->cachelastrow) {
|
||||
pQueryHandle->window = TSWINDOW_INITIALIZER;
|
||||
pQueryHandle->checkFiles = false;
|
||||
pQueryHandle->activeIndex = -1; // start from -1
|
||||
}
|
||||
|
||||
tfree(pRow);
|
||||
return code;
|
||||
}
|
||||
|
||||
STimeWindow updateLastrowForEachGroup(STableGroupInfo *groupList) {
|
||||
STimeWindow window = {INT64_MAX, INT64_MIN};
|
||||
|
||||
int32_t totalNumOfTable = 0;
|
||||
|
@ -2191,16 +2283,16 @@ STimeWindow changeTableGroupByLastrow(STableGroupInfo *groupList) {
|
|||
|
||||
size_t numOfTables = taosArrayGetSize(pGroup);
|
||||
for(int32_t i = 0; i < numOfTables; ++i) {
|
||||
STableKeyInfo* pKeyInfo = (STableKeyInfo*) taosArrayGet(pGroup, i);
|
||||
STableKeyInfo* pInfo = (STableKeyInfo*) taosArrayGet(pGroup, i);
|
||||
|
||||
// if the lastKey equals to INT64_MIN, there is no data in this table
|
||||
TSKEY lastKey = ((STable*)(pKeyInfo->pTable))->lastKey;
|
||||
TSKEY lastKey = ((STable*)(pInfo->pTable))->lastKey;
|
||||
if (key < lastKey) {
|
||||
key = lastKey;
|
||||
|
||||
keyInfo.pTable = pKeyInfo->pTable;
|
||||
keyInfo.pTable = pInfo->pTable;
|
||||
keyInfo.lastKey = key;
|
||||
pKeyInfo->lastKey = key;
|
||||
pInfo->lastKey = key;
|
||||
|
||||
if (key < window.skey) {
|
||||
window.skey = key;
|
||||
|
@ -2214,11 +2306,11 @@ STimeWindow changeTableGroupByLastrow(STableGroupInfo *groupList) {
|
|||
|
||||
// clear current group, unref unused table
|
||||
for (int32_t i = 0; i < numOfTables; ++i) {
|
||||
STableKeyInfo* pKeyInfo = (STableKeyInfo*)taosArrayGet(pGroup, i);
|
||||
STableKeyInfo* pInfo = (STableKeyInfo*)taosArrayGet(pGroup, i);
|
||||
|
||||
// keyInfo.pTable may be NULL here.
|
||||
if (pKeyInfo->pTable != keyInfo.pTable) {
|
||||
tsdbUnRefTable(pKeyInfo->pTable);
|
||||
if (pInfo->pTable != keyInfo.pTable) {
|
||||
tsdbUnRefTable(pInfo->pTable);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -34,6 +34,7 @@ static void vnodeLoadCfg(SVnodeObj *pVnode, SCreateVnodeMsg* vnodeMsg) {
|
|||
pVnode->tsdbCfg.maxRowsPerFileBlock = vnodeMsg->cfg.maxRowsPerFileBlock;
|
||||
pVnode->tsdbCfg.precision = vnodeMsg->cfg.precision;
|
||||
pVnode->tsdbCfg.compression = vnodeMsg->cfg.compression;
|
||||
pVnode->tsdbCfg.cacheLastRow = vnodeMsg->cfg.cacheLastRow;
|
||||
pVnode->walCfg.walLevel = vnodeMsg->cfg.walLevel;
|
||||
pVnode->walCfg.fsyncPeriod = vnodeMsg->cfg.fsyncPeriod;
|
||||
pVnode->walCfg.keep = TAOS_WAL_NOT_KEEP;
|
||||
|
@ -216,6 +217,15 @@ int32_t vnodeReadCfg(SVnodeObj *pVnode) {
|
|||
}
|
||||
vnodeMsg.cfg.quorum = (int8_t)quorum->valueint;
|
||||
|
||||
cJSON *cacheLastRow = cJSON_GetObjectItem(root, "cacheLastRow");
|
||||
if (!cacheLastRow || cacheLastRow->type != cJSON_Number) {
|
||||
vError("vgId: %d, failed to read %s, cacheLastRow not found", pVnode->vgId, file);
|
||||
//goto PARSE_VCFG_ERROR;
|
||||
vnodeMsg.cfg.cacheLastRow = 0;
|
||||
} else {
|
||||
vnodeMsg.cfg.cacheLastRow = (int8_t)cacheLastRow->valueint;
|
||||
}
|
||||
|
||||
cJSON *nodeInfos = cJSON_GetObjectItem(root, "nodeInfos");
|
||||
if (!nodeInfos || nodeInfos->type != cJSON_Array) {
|
||||
vError("vgId:%d, failed to read %s, nodeInfos not found", pVnode->vgId, file);
|
||||
|
@ -304,6 +314,7 @@ int32_t vnodeWriteCfg(SCreateVnodeMsg *pMsg) {
|
|||
len += snprintf(content + len, maxLen - len, " \"replica\": %d,\n", pMsg->cfg.replications);
|
||||
len += snprintf(content + len, maxLen - len, " \"wals\": %d,\n", pMsg->cfg.wals);
|
||||
len += snprintf(content + len, maxLen - len, " \"quorum\": %d,\n", pMsg->cfg.quorum);
|
||||
len += snprintf(content + len, maxLen - len, " \"cacheLastRow\": %d,\n", pMsg->cfg.cacheLastRow);
|
||||
len += snprintf(content + len, maxLen - len, " \"nodeInfos\": [{\n");
|
||||
for (int32_t i = 0; i < pMsg->cfg.replications; i++) {
|
||||
SVnodeDesc *node = &pMsg->nodes[i];
|
||||
|
|
|
@ -86,6 +86,7 @@ int32_t vnodeCreate(SCreateVnodeMsg *pVnodeCfg) {
|
|||
tsdbCfg.precision = pVnodeCfg->cfg.precision;
|
||||
tsdbCfg.compression = pVnodeCfg->cfg.compression;
|
||||
tsdbCfg.update = pVnodeCfg->cfg.update;
|
||||
tsdbCfg.cacheLastRow = pVnodeCfg->cfg.cacheLastRow;
|
||||
|
||||
char tsdbDir[TSDB_FILENAME_LEN] = {0};
|
||||
sprintf(tsdbDir, "%s/vnode%d/tsdb", tsVnodeDir, pVnodeCfg->cfg.vgId);
|
||||
|
|
|
@ -81,7 +81,7 @@ print =============== step2 - no db
|
|||
#11
|
||||
system_content curl -H 'Authorization: Taosd /KfeAzX/f9na8qdtNZmtONryp201ma04bEl8LcvLUd7a8qdtNZmtONryp201ma04' -d 'show databases' 127.0.0.1:7111/rest/sql
|
||||
print 11-> $system_content
|
||||
if $system_content != @{"status":"succ","head":["name","created_time","ntables","vgroups","replica","quorum","days","keep1,keep2,keep(D)","cache(MB)","blocks","minrows","maxrows","wallevel","fsync","comp","precision","update","status"],"data":[],"rows":0}@ then
|
||||
if $system_content != @{"status":"succ","head":["name","created_time","ntables","vgroups","replica","quorum","days","keep1,keep2,keep(D)","cache(MB)","blocks","minrows","maxrows","wallevel","fsync","comp","cachelast","precision","update","status"],"data":[],"rows":0}@ then
|
||||
return -1
|
||||
endi
|
||||
|
||||
|
|
Loading…
Reference in New Issue