Merge branch 'develop' into test/jenkins
This commit is contained in:
commit
3b4f730faa
|
@ -43,7 +43,7 @@ CREATE STABLE meters (ts timestamp, current float, voltage int, phase float) TAG
|
||||||
## <a class="anchor" id="create-table"></a>创建表
|
## <a class="anchor" id="create-table"></a>创建表
|
||||||
|
|
||||||
TDengine对每个数据采集点需要独立建表。与标准的关系型数据一样,一张表有表名,Schema,但除此之外,还可以带有一到多个标签。创建时,需要使用超级表做模板,同时指定标签的具体值。以表一中的智能电表为例,可以使用如下的SQL命令建表:
|
TDengine对每个数据采集点需要独立建表。与标准的关系型数据一样,一张表有表名,Schema,但除此之外,还可以带有一到多个标签。创建时,需要使用超级表做模板,同时指定标签的具体值。以表一中的智能电表为例,可以使用如下的SQL命令建表:
|
||||||
```cmd
|
```mysql
|
||||||
CREATE TABLE d1001 USING meters TAGS ("Beijing.Chaoyang", 2);
|
CREATE TABLE d1001 USING meters TAGS ("Beijing.Chaoyang", 2);
|
||||||
```
|
```
|
||||||
其中d1001是表名,meters是超级表的表名,后面紧跟标签Location的具体标签值”Beijing.Chaoyang",标签groupId的具体标签值2。虽然在创建表时,需要指定标签值,但可以事后修改。详细细则请见 [TAOS SQL 的表管理](https://www.taosdata.com/cn/documentation/taos-sql#table) 章节。
|
其中d1001是表名,meters是超级表的表名,后面紧跟标签Location的具体标签值”Beijing.Chaoyang",标签groupId的具体标签值2。虽然在创建表时,需要指定标签值,但可以事后修改。详细细则请见 [TAOS SQL 的表管理](https://www.taosdata.com/cn/documentation/taos-sql#table) 章节。
|
||||||
|
@ -54,10 +54,12 @@ TDengine建议将数据采集点的全局唯一ID作为表名(比如设备序列
|
||||||
|
|
||||||
**自动建表**:在某些特殊场景中,用户在写数据时并不确定某个数据采集点的表是否存在,此时可在写入数据时使用自动建表语法来创建不存在的表,若该表已存在则不会建立新表。比如:
|
**自动建表**:在某些特殊场景中,用户在写数据时并不确定某个数据采集点的表是否存在,此时可在写入数据时使用自动建表语法来创建不存在的表,若该表已存在则不会建立新表。比如:
|
||||||
|
|
||||||
```cmd
|
```mysql
|
||||||
INSERT INTO d1001 USING METERS TAGS ("Beijng.Chaoyang", 2) VALUES (now, 10.2, 219, 0.32);
|
INSERT INTO d1001 USING METERS TAGS ("Beijng.Chaoyang", 2) VALUES (now, 10.2, 219, 0.32);
|
||||||
```
|
```
|
||||||
上述SQL语句将记录(now, 10.2, 219, 0.32) 插入进表d1001。如果表d1001还未创建,则使用超级表meters做模板自动创建,同时打上标签值“Beijing.Chaoyang", 2。
|
上述SQL语句将记录 (now, 10.2, 219, 0.32) 插入表d1001。如果表d1001还未创建,则使用超级表meters做模板自动创建,同时打上标签值“Beijing.Chaoyang", 2。
|
||||||
|
|
||||||
|
关于自动建表的详细语法请参见 [插入记录时自动建表](https://www.taosdata.com/cn/documentation/taos-sql#auto_create_table) 章节。
|
||||||
|
|
||||||
## 多列模型 vs 单列模型
|
## 多列模型 vs 单列模型
|
||||||
|
|
||||||
|
|
|
@ -152,6 +152,14 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic
|
||||||
```
|
```
|
||||||
以指定的超级表为模板,指定 tags 的值来创建数据表。
|
以指定的超级表为模板,指定 tags 的值来创建数据表。
|
||||||
|
|
||||||
|
- **以超级表为模板创建数据表,并指定具体的 tags 列**
|
||||||
|
|
||||||
|
```mysql
|
||||||
|
CREATE TABLE [IF NOT EXISTS] tb_name USING stb_name (tag_name1, ...) TAGS (tag_value1, ...);
|
||||||
|
```
|
||||||
|
以指定的超级表为模板,指定一部分 tags 列的值来创建数据表。(没被指定的 tags 列会设为空值。)
|
||||||
|
说明:从 2.0.17 版本开始支持这种方式。在之前的版本中,不允许指定 tags 列,而必须显式给出所有 tags 列的取值。
|
||||||
|
|
||||||
- **批量创建数据表**
|
- **批量创建数据表**
|
||||||
|
|
||||||
```mysql
|
```mysql
|
||||||
|
@ -306,7 +314,7 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic
|
||||||
|
|
||||||
- **插入一条记录,数据对应到指定的列**
|
- **插入一条记录,数据对应到指定的列**
|
||||||
```mysql
|
```mysql
|
||||||
INSERT INTO tb_name (field1_name, ...) VALUES (field1_value, ...)
|
INSERT INTO tb_name (field1_name, ...) VALUES (field1_value1, ...);
|
||||||
```
|
```
|
||||||
向表tb_name中插入一条记录,数据对应到指定的列。SQL语句中没有出现的列,数据库将自动填充为NULL。主键(时间戳)不能为NULL。
|
向表tb_name中插入一条记录,数据对应到指定的列。SQL语句中没有出现的列,数据库将自动填充为NULL。主键(时间戳)不能为NULL。
|
||||||
|
|
||||||
|
@ -340,6 +348,18 @@ TDengine缺省的时间戳是毫秒精度,但通过修改配置参数enableMic
|
||||||
1) 如果时间戳为0,系统将自动使用服务器当前时间作为该记录的时间戳;
|
1) 如果时间戳为0,系统将自动使用服务器当前时间作为该记录的时间戳;
|
||||||
2) 允许插入的最老记录的时间戳,是相对于当前服务器时间,减去配置的keep值(数据保留的天数),允许插入的最新记录的时间戳,是相对于当前服务器时间,加上配置的days值(数据文件存储数据的时间跨度,单位为天)。keep和days都是可以在创建数据库时指定的,缺省值分别是3650天和10天。
|
2) 允许插入的最老记录的时间戳,是相对于当前服务器时间,减去配置的keep值(数据保留的天数),允许插入的最新记录的时间戳,是相对于当前服务器时间,加上配置的days值(数据文件存储数据的时间跨度,单位为天)。keep和days都是可以在创建数据库时指定的,缺省值分别是3650天和10天。
|
||||||
|
|
||||||
|
- <a class="anchor" id="auto_create_table"></a>**插入记录时自动建表**
|
||||||
|
```mysql
|
||||||
|
INSERT INTO tb_name USING stb_name TAGS (tag_value1, ...) VALUES (field_value1, ...);
|
||||||
|
```
|
||||||
|
如果用户在写数据时并不确定某个表是否存在,此时可以在写入数据时使用自动建表语法来创建不存在的表,若该表已存在则不会建立新表。自动建表时,要求必须以超级表为模板,并写明数据表的 tags 取值。
|
||||||
|
|
||||||
|
- **插入记录时自动建表,并指定具体的 tags 列**
|
||||||
|
```mysql
|
||||||
|
INSERT INTO tb_name USING stb_name (tag_name1, ...) TAGS (tag_value1, ...) VALUES (field_value1, ...);
|
||||||
|
```
|
||||||
|
在自动建表时,可以只是指定部分 tags 列的取值,未被指定的 tags 列将取为空值。
|
||||||
|
|
||||||
**历史记录写入**:可使用IMPORT或者INSERT命令,IMPORT的语法,功能与INSERT完全一样。
|
**历史记录写入**:可使用IMPORT或者INSERT命令,IMPORT的语法,功能与INSERT完全一样。
|
||||||
|
|
||||||
说明:针对 insert 类型的 SQL 语句,我们采用的流式解析策略,在发现后面的错误之前,前面正确的部分SQL仍会执行。下面的sql中,insert语句是无效的,但是d1001仍会被创建。
|
说明:针对 insert 类型的 SQL 语句,我们采用的流式解析策略,在发现后面的错误之前,前面正确的部分SQL仍会执行。下面的sql中,insert语句是无效的,但是d1001仍会被创建。
|
||||||
|
@ -383,7 +403,7 @@ SELECT select_expr [, select_expr ...]
|
||||||
[ORDER BY col_list { DESC | ASC }]
|
[ORDER BY col_list { DESC | ASC }]
|
||||||
[SLIMIT limit_val [, SOFFSET offset_val]]
|
[SLIMIT limit_val [, SOFFSET offset_val]]
|
||||||
[LIMIT limit_val [, OFFSET offset_val]]
|
[LIMIT limit_val [, OFFSET offset_val]]
|
||||||
[>> export_file]
|
[>> export_file];
|
||||||
```
|
```
|
||||||
|
|
||||||
#### SELECT子句
|
#### SELECT子句
|
||||||
|
|
|
@ -128,6 +128,7 @@
|
||||||
</includes>
|
</includes>
|
||||||
<excludes>
|
<excludes>
|
||||||
<exclude>**/AppMemoryLeakTest.java</exclude>
|
<exclude>**/AppMemoryLeakTest.java</exclude>
|
||||||
|
<exclude>**/AuthenticationTest.java</exclude>
|
||||||
<exclude>**/TaosInfoMonitorTest.java</exclude>
|
<exclude>**/TaosInfoMonitorTest.java</exclude>
|
||||||
<exclude>**/FailOverTest.java</exclude>
|
<exclude>**/FailOverTest.java</exclude>
|
||||||
<exclude>**/InvalidResultSetPointerTest.java</exclude>
|
<exclude>**/InvalidResultSetPointerTest.java</exclude>
|
||||||
|
|
|
@ -0,0 +1,529 @@
|
||||||
|
package com.taosdata.jdbc;
|
||||||
|
|
||||||
|
import java.sql.*;
|
||||||
|
import java.util.Enumeration;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Properties;
|
||||||
|
import java.util.concurrent.*;
|
||||||
|
|
||||||
|
public abstract class AbstractConnection extends WrapperImpl implements Connection {
|
||||||
|
|
||||||
|
protected volatile boolean isClosed;
|
||||||
|
protected volatile String catalog;
|
||||||
|
protected volatile Properties clientInfoProps = new Properties();
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public abstract Statement createStatement() throws SQLException;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public abstract PreparedStatement prepareStatement(String sql) throws SQLException;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public CallableStatement prepareCall(String sql) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String nativeSQL(String sql) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
// do nothing
|
||||||
|
return sql;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setAutoCommit(boolean autoCommit) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
//do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean getAutoCommit() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void commit() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
// do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void rollback() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
// do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public abstract void close() throws SQLException;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public abstract boolean isClosed() throws SQLException;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public abstract DatabaseMetaData getMetaData() throws SQLException;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setReadOnly(boolean readOnly) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
//do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isReadOnly() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setCatalog(String catalog) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
/*
|
||||||
|
try (Statement stmt = createStatement()) {
|
||||||
|
boolean execute = stmt.execute("use " + catalog);
|
||||||
|
if (execute)
|
||||||
|
this.catalog = catalog;
|
||||||
|
} catch (SQLException e) {
|
||||||
|
// do nothing
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
this.catalog = catalog;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getCatalog() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return this.catalog;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setTransactionIsolation(int level) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (level) {
|
||||||
|
case Connection.TRANSACTION_NONE:
|
||||||
|
break;
|
||||||
|
case Connection.TRANSACTION_READ_UNCOMMITTED:
|
||||||
|
case Connection.TRANSACTION_READ_COMMITTED:
|
||||||
|
case Connection.TRANSACTION_REPEATABLE_READ:
|
||||||
|
case Connection.TRANSACTION_SERIALIZABLE:
|
||||||
|
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
||||||
|
default:
|
||||||
|
throw new SQLException(TSDBConstants.INVALID_VARIABLES);
|
||||||
|
}
|
||||||
|
//do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getTransactionIsolation() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return Connection.TRANSACTION_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public SQLWarning getWarnings() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void clearWarnings() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
// do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Statement createStatement(int resultSetType, int resultSetConcurrency) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (resultSetType) {
|
||||||
|
case ResultSet.TYPE_FORWARD_ONLY:
|
||||||
|
break;
|
||||||
|
case ResultSet.TYPE_SCROLL_INSENSITIVE:
|
||||||
|
case ResultSet.TYPE_SCROLL_SENSITIVE:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (resultSetConcurrency) {
|
||||||
|
case ResultSet.CONCUR_READ_ONLY:
|
||||||
|
break;
|
||||||
|
case ResultSet.CONCUR_UPDATABLE:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
|
||||||
|
return createStatement();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (resultSetType) {
|
||||||
|
case ResultSet.TYPE_FORWARD_ONLY:
|
||||||
|
break;
|
||||||
|
case ResultSet.TYPE_SCROLL_INSENSITIVE:
|
||||||
|
case ResultSet.TYPE_SCROLL_SENSITIVE:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (resultSetConcurrency) {
|
||||||
|
case ResultSet.CONCUR_READ_ONLY:
|
||||||
|
break;
|
||||||
|
case ResultSet.CONCUR_UPDATABLE:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
return prepareStatement(sql);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Map<String, Class<?>> getTypeMap() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setTypeMap(Map<String, Class<?>> map) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setHoldability(int holdability) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (holdability) {
|
||||||
|
case ResultSet.HOLD_CURSORS_OVER_COMMIT:
|
||||||
|
break;
|
||||||
|
case ResultSet.CLOSE_CURSORS_AT_COMMIT:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
//do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getHoldability() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return ResultSet.HOLD_CURSORS_OVER_COMMIT;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Savepoint setSavepoint() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Savepoint setSavepoint(String name) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void rollback(Savepoint savepoint) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void releaseSavepoint(Savepoint savepoint) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Statement createStatement(int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (resultSetHoldability) {
|
||||||
|
case ResultSet.HOLD_CURSORS_OVER_COMMIT:
|
||||||
|
break;
|
||||||
|
case ResultSet.CLOSE_CURSORS_AT_COMMIT:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
|
||||||
|
return createStatement(resultSetType, resultSetConcurrency);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability)
|
||||||
|
throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (resultSetHoldability) {
|
||||||
|
case ResultSet.HOLD_CURSORS_OVER_COMMIT:
|
||||||
|
break;
|
||||||
|
case ResultSet.CLOSE_CURSORS_AT_COMMIT:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
default:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
}
|
||||||
|
return prepareStatement(sql, resultSetType, resultSetConcurrency);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PreparedStatement prepareStatement(String sql, int autoGeneratedKeys) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
switch (autoGeneratedKeys) {
|
||||||
|
case Statement.RETURN_GENERATED_KEYS:
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
case Statement.NO_GENERATED_KEYS:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return prepareStatement(sql, ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PreparedStatement prepareStatement(String sql, int[] columnIndexes) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public PreparedStatement prepareStatement(String sql, String[] columnNames) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Clob createClob() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Blob createBlob() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public NClob createNClob() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public SQLXML createSQLXML() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isValid(int timeout) throws SQLException {
|
||||||
|
//true if the connection is valid, false otherwise
|
||||||
|
if (isClosed())
|
||||||
|
return false;
|
||||||
|
if (timeout < 0) //SQLException - if the value supplied for timeout is less then 0
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
|
||||||
|
ExecutorService executor = Executors.newCachedThreadPool();
|
||||||
|
Future<Boolean> future = executor.submit(() -> {
|
||||||
|
int status;
|
||||||
|
try (Statement stmt = createStatement()) {
|
||||||
|
ResultSet resultSet = stmt.executeQuery("select server_status()");
|
||||||
|
resultSet.next();
|
||||||
|
status = resultSet.getInt("server_status()");
|
||||||
|
resultSet.close();
|
||||||
|
}
|
||||||
|
return status == 1 ? true : false;
|
||||||
|
});
|
||||||
|
|
||||||
|
boolean status = false;
|
||||||
|
try {
|
||||||
|
if (timeout == 0)
|
||||||
|
status = future.get();
|
||||||
|
else
|
||||||
|
status = future.get(timeout, TimeUnit.SECONDS);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
} catch (ExecutionException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
} catch (TimeoutException e) {
|
||||||
|
future.cancel(true);
|
||||||
|
status = false;
|
||||||
|
} finally {
|
||||||
|
executor.shutdownNow();
|
||||||
|
}
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setClientInfo(String name, String value) throws SQLClientInfoException {
|
||||||
|
if (isClosed)
|
||||||
|
throw TSDBError.createSQLClientInfoException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
if (clientInfoProps == null)
|
||||||
|
clientInfoProps = new Properties();
|
||||||
|
clientInfoProps.setProperty(name, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setClientInfo(Properties properties) throws SQLClientInfoException {
|
||||||
|
if (isClosed)
|
||||||
|
throw TSDBError.createSQLClientInfoException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
for (Enumeration<Object> enumer = properties.keys(); enumer.hasMoreElements(); ) {
|
||||||
|
String name = (String) enumer.nextElement();
|
||||||
|
clientInfoProps.put(name, properties.getProperty(name));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getClientInfo(String name) throws SQLException {
|
||||||
|
if (isClosed)
|
||||||
|
throw TSDBError.createSQLClientInfoException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return clientInfoProps.getProperty(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Properties getClientInfo() throws SQLException {
|
||||||
|
if (isClosed)
|
||||||
|
throw TSDBError.createSQLClientInfoException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return clientInfoProps;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Array createArrayOf(String typeName, Object[] elements) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Struct createStruct(String typeName, Object[] attributes) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setSchema(String schema) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
//do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getSchema() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void abort(Executor executor) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
// do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setNetworkTimeout(Executor executor, int milliseconds) throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
if (milliseconds < 0)
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getNetworkTimeout() throws SQLException {
|
||||||
|
if (isClosed())
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
|
|
||||||
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
|
}
|
||||||
|
}
|
|
@ -4,7 +4,7 @@ import java.sql.*;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
public abstract class AbstractDatabaseMetaData implements DatabaseMetaData, Wrapper {
|
public abstract class AbstractDatabaseMetaData extends WrapperImpl implements DatabaseMetaData {
|
||||||
|
|
||||||
private final static String PRODUCT_NAME = "TDengine";
|
private final static String PRODUCT_NAME = "TDengine";
|
||||||
private final static String PRODUCT_VESION = "2.0.x.x";
|
private final static String PRODUCT_VESION = "2.0.x.x";
|
||||||
|
@ -981,9 +981,7 @@ public abstract class AbstractDatabaseMetaData implements DatabaseMetaData, Wrap
|
||||||
return getEmptyResultSet();
|
return getEmptyResultSet();
|
||||||
}
|
}
|
||||||
|
|
||||||
public Connection getConnection() throws SQLException {
|
public abstract Connection getConnection() throws SQLException;
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean supportsSavepoints() throws SQLException {
|
public boolean supportsSavepoints() throws SQLException {
|
||||||
return false;
|
return false;
|
||||||
|
@ -1067,6 +1065,7 @@ public abstract class AbstractDatabaseMetaData implements DatabaseMetaData, Wrap
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResultSet getClientInfoProperties() throws SQLException {
|
public ResultSet getClientInfoProperties() throws SQLException {
|
||||||
|
//TODO: see https://docs.oracle.com/javase/8/docs/api/java/sql/Connection.html#setClientInfo-java.lang.String-java.lang.String-
|
||||||
return getEmptyResultSet();
|
return getEmptyResultSet();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1093,20 +1092,6 @@ public abstract class AbstractDatabaseMetaData implements DatabaseMetaData, Wrap
|
||||||
return new EmptyResultSet();
|
return new EmptyResultSet();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <T> T unwrap(Class<T> iface) throws SQLException {
|
|
||||||
try {
|
|
||||||
return iface.cast(this);
|
|
||||||
} catch (ClassCastException cce) {
|
|
||||||
throw new SQLException("Unable to unwrap to " + iface.toString());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean isWrapperFor(Class<?> iface) throws SQLException {
|
|
||||||
return iface.isInstance(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
protected ResultSet getCatalogs(Connection conn) throws SQLException {
|
protected ResultSet getCatalogs(Connection conn) throws SQLException {
|
||||||
try (Statement stmt = conn.createStatement()) {
|
try (Statement stmt = conn.createStatement()) {
|
||||||
DatabaseMetaDataResultSet resultSet = new DatabaseMetaDataResultSet();
|
DatabaseMetaDataResultSet resultSet = new DatabaseMetaDataResultSet();
|
||||||
|
|
|
@ -14,41 +14,25 @@
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
package com.taosdata.jdbc;
|
package com.taosdata.jdbc;
|
||||||
|
|
||||||
import java.sql.Array;
|
import java.sql.*;
|
||||||
import java.sql.Blob;
|
import java.util.Properties;
|
||||||
import java.sql.CallableStatement;
|
|
||||||
import java.sql.Clob;
|
|
||||||
import java.sql.Connection;
|
|
||||||
import java.sql.DatabaseMetaData;
|
|
||||||
import java.sql.NClob;
|
|
||||||
import java.sql.PreparedStatement;
|
|
||||||
import java.sql.ResultSet;
|
|
||||||
import java.sql.SQLClientInfoException;
|
|
||||||
import java.sql.SQLException;
|
|
||||||
import java.sql.SQLWarning;
|
|
||||||
import java.sql.SQLXML;
|
|
||||||
import java.sql.Savepoint;
|
|
||||||
import java.sql.Statement;
|
|
||||||
import java.sql.Struct;
|
|
||||||
import java.util.*;
|
|
||||||
import java.util.concurrent.Executor;
|
|
||||||
|
|
||||||
public class TSDBConnection implements Connection {
|
public class TSDBConnection extends AbstractConnection {
|
||||||
|
|
||||||
private TSDBJNIConnector connector = null;
|
private TSDBJNIConnector connector;
|
||||||
|
private TSDBDatabaseMetaData databaseMetaData;
|
||||||
|
private boolean batchFetch;
|
||||||
|
|
||||||
private String catalog = null;
|
public Boolean getBatchFetch() {
|
||||||
|
return this.batchFetch;
|
||||||
|
}
|
||||||
|
|
||||||
private TSDBDatabaseMetaData dbMetaData;
|
public void setBatchFetch(Boolean batchFetch) {
|
||||||
|
this.batchFetch = batchFetch;
|
||||||
private Properties clientInfoProps = new Properties();
|
}
|
||||||
|
|
||||||
private int timeoutMilliseconds = 0;
|
|
||||||
|
|
||||||
private boolean batchFetch = false;
|
|
||||||
|
|
||||||
public TSDBConnection(Properties info, TSDBDatabaseMetaData meta) throws SQLException {
|
public TSDBConnection(Properties info, TSDBDatabaseMetaData meta) throws SQLException {
|
||||||
this.dbMetaData = meta;
|
this.databaseMetaData = meta;
|
||||||
connect(info.getProperty(TSDBDriver.PROPERTY_KEY_HOST),
|
connect(info.getProperty(TSDBDriver.PROPERTY_KEY_HOST),
|
||||||
Integer.parseInt(info.getProperty(TSDBDriver.PROPERTY_KEY_PORT, "0")),
|
Integer.parseInt(info.getProperty(TSDBDriver.PROPERTY_KEY_PORT, "0")),
|
||||||
info.getProperty(TSDBDriver.PROPERTY_KEY_DBNAME),
|
info.getProperty(TSDBDriver.PROPERTY_KEY_DBNAME),
|
||||||
|
@ -64,8 +48,8 @@ public class TSDBConnection implements Connection {
|
||||||
private void connect(String host, int port, String dbName, String user, String password) throws SQLException {
|
private void connect(String host, int port, String dbName, String user, String password) throws SQLException {
|
||||||
this.connector = new TSDBJNIConnector();
|
this.connector = new TSDBJNIConnector();
|
||||||
this.connector.connect(host, port, dbName, user, password);
|
this.connector.connect(host, port, dbName, user, password);
|
||||||
this.setCatalog(dbName);
|
this.catalog = dbName;
|
||||||
this.dbMetaData.setConnection(this);
|
this.databaseMetaData.setConnection(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public TSDBJNIConnector getConnection() {
|
public TSDBJNIConnector getConnection() {
|
||||||
|
@ -102,52 +86,11 @@ public class TSDBConnection implements Connection {
|
||||||
return new TSDBPreparedStatement(this, this.connector, sql);
|
return new TSDBPreparedStatement(this, this.connector, sql);
|
||||||
}
|
}
|
||||||
|
|
||||||
public CallableStatement prepareCall(String sql) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public String nativeSQL(String sql) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setAutoCommit(boolean autoCommit) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean getAutoCommit() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void commit() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void rollback() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() throws SQLException {
|
public void close() throws SQLException {
|
||||||
if (isClosed()) {
|
if (isClosed()) {
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
}
|
}
|
||||||
|
this.isClosed = true;
|
||||||
this.connector.closeConnection();
|
this.connector.closeConnection();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -155,105 +98,11 @@ public class TSDBConnection implements Connection {
|
||||||
return this.connector != null && this.connector.isClosed();
|
return this.connector != null && this.connector.isClosed();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* A connection's database is able to provide information describing its tables,
|
|
||||||
* its supported SQL grammar, its stored procedures, the capabilities of this
|
|
||||||
* connection, etc. This information is made available through a
|
|
||||||
* DatabaseMetaData object.
|
|
||||||
*
|
|
||||||
* @return a DatabaseMetaData object for this connection
|
|
||||||
* @throws SQLException if a database access error occurs
|
|
||||||
*/
|
|
||||||
public DatabaseMetaData getMetaData() throws SQLException {
|
public DatabaseMetaData getMetaData() throws SQLException {
|
||||||
if (isClosed()) {
|
if (isClosed()) {
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
}
|
}
|
||||||
return this.dbMetaData;
|
return this.databaseMetaData;
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This readOnly option is not supported by TDengine. However, the method is intentionally left blank here to
|
|
||||||
* support HikariCP connection.
|
|
||||||
*
|
|
||||||
* @param readOnly
|
|
||||||
* @throws SQLException
|
|
||||||
*/
|
|
||||||
public void setReadOnly(boolean readOnly) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isReadOnly() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setCatalog(String catalog) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
this.catalog = catalog;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getCatalog() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return this.catalog;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The transaction isolation level option is not supported by TDengine.
|
|
||||||
* This method is intentionally left empty to support HikariCP connection.
|
|
||||||
*
|
|
||||||
* @param level
|
|
||||||
* @throws SQLException
|
|
||||||
*/
|
|
||||||
public void setTransactionIsolation(int level) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
switch (level) {
|
|
||||||
case Connection.TRANSACTION_NONE:
|
|
||||||
case Connection.TRANSACTION_READ_COMMITTED:
|
|
||||||
case Connection.TRANSACTION_READ_UNCOMMITTED:
|
|
||||||
case Connection.TRANSACTION_REPEATABLE_READ:
|
|
||||||
case Connection.TRANSACTION_SERIALIZABLE:
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The transaction isolation level option is not supported by TDengine.
|
|
||||||
*
|
|
||||||
* @return
|
|
||||||
* @throws SQLException
|
|
||||||
*/
|
|
||||||
public int getTransactionIsolation() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return Connection.TRANSACTION_NONE;
|
|
||||||
}
|
|
||||||
|
|
||||||
public SQLWarning getWarnings() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
//todo: implement getWarnings according to the warning messages returned from TDengine
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void clearWarnings() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
//todo: implement clearWarnings according to the warning messages returned from TDengine
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public Statement createStatement(int resultSetType, int resultSetConcurrency) throws SQLException {
|
public Statement createStatement(int resultSetType, int resultSetConcurrency) throws SQLException {
|
||||||
|
@ -263,253 +112,4 @@ public class TSDBConnection implements Connection {
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
||||||
}
|
}
|
||||||
|
|
||||||
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency)
|
|
||||||
throws SQLException {
|
|
||||||
// This method is implemented in the current way to support Spark
|
|
||||||
if (resultSetType != ResultSet.TYPE_FORWARD_ONLY) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (resultSetConcurrency != ResultSet.CONCUR_READ_ONLY) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_VARIABLE);
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.prepareStatement(sql);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Boolean getBatchFetch() {
|
|
||||||
return this.batchFetch;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setBatchFetch(Boolean batchFetch) {
|
|
||||||
this.batchFetch = batchFetch;
|
|
||||||
}
|
|
||||||
|
|
||||||
public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Map<String, Class<?>> getTypeMap() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setTypeMap(Map<String, Class<?>> map) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setHoldability(int holdability) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* the transaction is not supported by TDengine, so the opened ResultSet Objects will remain open
|
|
||||||
*
|
|
||||||
* @return
|
|
||||||
* @throws SQLException
|
|
||||||
*/
|
|
||||||
public int getHoldability() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return ResultSet.HOLD_CURSORS_OVER_COMMIT;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Savepoint setSavepoint() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Savepoint setSavepoint(String name) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void rollback(Savepoint savepoint) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void releaseSavepoint(Savepoint savepoint) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Statement createStatement(int resultSetType, int resultSetConcurrency, int resultSetHoldability)
|
|
||||||
throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency,
|
|
||||||
int resultSetHoldability) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency,
|
|
||||||
int resultSetHoldability) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public PreparedStatement prepareStatement(String sql, int autoGeneratedKeys) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public PreparedStatement prepareStatement(String sql, int[] columnIndexes) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public PreparedStatement prepareStatement(String sql, String[] columnNames) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Clob createClob() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Blob createBlob() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public NClob createNClob() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public SQLXML createSQLXML() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isValid(int timeout) throws SQLException {
|
|
||||||
return !this.isClosed();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setClientInfo(String name, String value) throws SQLClientInfoException {
|
|
||||||
clientInfoProps.setProperty(name, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setClientInfo(Properties properties) throws SQLClientInfoException {
|
|
||||||
for (Enumeration<Object> enumer = properties.keys(); enumer.hasMoreElements(); ) {
|
|
||||||
String name = (String) enumer.nextElement();
|
|
||||||
clientInfoProps.put(name, properties.getProperty(name));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getClientInfo(String name) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return clientInfoProps.getProperty(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Properties getClientInfo() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return clientInfoProps;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Array createArrayOf(String typeName, Object[] elements) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Struct createStruct(String typeName, Object[] attributes) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setSchema(String schema) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getSchema() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void abort(Executor executor) throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_UNSUPPORTED_METHOD);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setNetworkTimeout(Executor executor, int milliseconds) throws SQLException {
|
|
||||||
this.timeoutMilliseconds = milliseconds;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getNetworkTimeout() throws SQLException {
|
|
||||||
if (isClosed()) {
|
|
||||||
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
|
||||||
}
|
|
||||||
return this.timeoutMilliseconds;
|
|
||||||
}
|
|
||||||
|
|
||||||
public <T> T unwrap(Class<T> iface) throws SQLException {
|
|
||||||
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 iface.isInstance(this);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -57,39 +57,38 @@ public class TSDBDatabaseMetaData extends AbstractDatabaseMetaData {
|
||||||
*/
|
*/
|
||||||
public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) throws SQLException {
|
public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) throws SQLException {
|
||||||
if (conn == null || conn.isClosed()) {
|
if (conn == null || conn.isClosed()) {
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
}
|
}
|
||||||
return super.getTables(catalog, schemaPattern, tableNamePattern, types, conn);
|
return super.getTables(catalog, schemaPattern, tableNamePattern, types, conn);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public ResultSet getCatalogs() throws SQLException {
|
public ResultSet getCatalogs() throws SQLException {
|
||||||
if (conn == null || conn.isClosed())
|
if (conn == null || conn.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getCatalogs(conn);
|
return super.getCatalogs(conn);
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResultSet getTableTypes() throws SQLException {
|
public ResultSet getTableTypes() throws SQLException {
|
||||||
if (conn == null || conn.isClosed())
|
if (conn == null || conn.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getTableTypes();
|
return super.getTableTypes();
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResultSet getColumns(String catalog, String schemaPattern, String tableNamePattern, String columnNamePattern) throws SQLException {
|
public ResultSet getColumns(String catalog, String schemaPattern, String tableNamePattern, String columnNamePattern) throws SQLException {
|
||||||
if (conn == null || conn.isClosed())
|
if (conn == null || conn.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getColumns(catalog, schemaPattern, tableNamePattern, columnNamePattern, conn);
|
return super.getColumns(catalog, schemaPattern, tableNamePattern, columnNamePattern, conn);
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResultSet getPrimaryKeys(String catalog, String schema, String table) throws SQLException {
|
public ResultSet getPrimaryKeys(String catalog, String schema, String table) throws SQLException {
|
||||||
if (conn == null || conn.isClosed())
|
if (conn == null || conn.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getPrimaryKeys(catalog, schema, table, conn);
|
return super.getPrimaryKeys(catalog, schema, table, conn);
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResultSet getSuperTables(String catalog, String schemaPattern, String tableNamePattern) throws SQLException {
|
public ResultSet getSuperTables(String catalog, String schemaPattern, String tableNamePattern) throws SQLException {
|
||||||
if (conn == null || conn.isClosed())
|
if (conn == null || conn.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getSuperTables(catalog, schemaPattern, tableNamePattern, conn);
|
return super.getSuperTables(catalog, schemaPattern, tableNamePattern, conn);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -90,7 +90,7 @@ public class TSDBDriver extends AbstractDriver {
|
||||||
* fetch data from native function in a batch model
|
* fetch data from native function in a batch model
|
||||||
*/
|
*/
|
||||||
public static final String PROPERTY_KEY_BATCH_LOAD = "batchfetch";
|
public static final String PROPERTY_KEY_BATCH_LOAD = "batchfetch";
|
||||||
|
|
||||||
private TSDBDatabaseMetaData dbMetaData = null;
|
private TSDBDatabaseMetaData dbMetaData = null;
|
||||||
|
|
||||||
static {
|
static {
|
||||||
|
@ -179,18 +179,18 @@ public class TSDBDriver extends AbstractDriver {
|
||||||
while (queryParams.hasMoreElements()) {
|
while (queryParams.hasMoreElements()) {
|
||||||
String oneToken = queryParams.nextToken();
|
String oneToken = queryParams.nextToken();
|
||||||
String[] pair = oneToken.split("=");
|
String[] pair = oneToken.split("=");
|
||||||
|
|
||||||
if ((pair[0] != null && pair[0].trim().length() > 0) && (pair[1] != null && pair[1].trim().length() > 0)) {
|
if ((pair[0] != null && pair[0].trim().length() > 0) && (pair[1] != null && pair[1].trim().length() > 0)) {
|
||||||
urlProps.setProperty(pair[0].trim(), pair[1].trim());
|
urlProps.setProperty(pair[0].trim(), pair[1].trim());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// parse Product Name
|
// parse Product Name
|
||||||
String dbProductName = url.substring(0, beginningOfSlashes);
|
String dbProductName = url.substring(0, beginningOfSlashes);
|
||||||
dbProductName = dbProductName.substring(dbProductName.indexOf(":") + 1);
|
dbProductName = dbProductName.substring(dbProductName.indexOf(":") + 1);
|
||||||
dbProductName = dbProductName.substring(0, dbProductName.indexOf(":"));
|
dbProductName = dbProductName.substring(0, dbProductName.indexOf(":"));
|
||||||
|
|
||||||
// parse database name
|
// parse database name
|
||||||
url = url.substring(beginningOfSlashes + 2);
|
url = url.substring(beginningOfSlashes + 2);
|
||||||
int indexOfSlash = url.indexOf("/");
|
int indexOfSlash = url.indexOf("/");
|
||||||
|
@ -200,7 +200,7 @@ public class TSDBDriver extends AbstractDriver {
|
||||||
}
|
}
|
||||||
url = url.substring(0, indexOfSlash);
|
url = url.substring(0, indexOfSlash);
|
||||||
}
|
}
|
||||||
|
|
||||||
// parse port
|
// parse port
|
||||||
int indexOfColon = url.indexOf(":");
|
int indexOfColon = url.indexOf(":");
|
||||||
if (indexOfColon != -1) {
|
if (indexOfColon != -1) {
|
||||||
|
@ -209,11 +209,11 @@ public class TSDBDriver extends AbstractDriver {
|
||||||
}
|
}
|
||||||
url = url.substring(0, indexOfColon);
|
url = url.substring(0, indexOfColon);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (url != null && url.length() > 0 && url.trim().length() > 0) {
|
if (url != null && url.length() > 0 && url.trim().length() > 0) {
|
||||||
urlProps.setProperty(TSDBDriver.PROPERTY_KEY_HOST, url);
|
urlProps.setProperty(TSDBDriver.PROPERTY_KEY_HOST, url);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.dbMetaData = new TSDBDatabaseMetaData(urlForMeta, urlProps.getProperty(TSDBDriver.PROPERTY_KEY_USER));
|
this.dbMetaData = new TSDBDatabaseMetaData(urlForMeta, urlProps.getProperty(TSDBDriver.PROPERTY_KEY_USER));
|
||||||
return urlProps;
|
return urlProps;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package com.taosdata.jdbc;
|
package com.taosdata.jdbc;
|
||||||
|
|
||||||
|
import java.sql.SQLClientInfoException;
|
||||||
import java.sql.SQLException;
|
import java.sql.SQLException;
|
||||||
import java.sql.SQLFeatureNotSupportedException;
|
import java.sql.SQLFeatureNotSupportedException;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
@ -17,6 +18,10 @@ public class TSDBError {
|
||||||
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_BATCH_IS_EMPTY, "Batch is empty!");
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_BATCH_IS_EMPTY, "Batch is empty!");
|
||||||
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_WITH_EXECUTEQUERY, "Can not issue data manipulation statements with executeQuery()");
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_WITH_EXECUTEQUERY, "Can not issue data manipulation statements with executeQuery()");
|
||||||
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_WITH_EXECUTEUPDATE, "Can not issue SELECT via executeUpdate()");
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_WITH_EXECUTEUPDATE, "Can not issue SELECT via executeUpdate()");
|
||||||
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE_QUERY, "not a valid sql for executeQuery: (?)");
|
||||||
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_DATABASE_NOT_SPECIFIED_OR_AVAILABLE, "Database not specified or available");
|
||||||
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE_UPDATE, "not a valid sql for executeUpdate: (?)");
|
||||||
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE, "not a valid sql for execute: (?)");
|
||||||
|
|
||||||
/**************************************************/
|
/**************************************************/
|
||||||
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_UNKNOWN, "unknown error");
|
TSDBErrorMap.put(TSDBErrorNumbers.ERROR_UNKNOWN, "unknown error");
|
||||||
|
@ -58,4 +63,8 @@ public class TSDBError {
|
||||||
// JNI exception's error number is large than 0x2350
|
// JNI exception's error number is large than 0x2350
|
||||||
return new SQLException("TDengine ERROR (" + Integer.toHexString(errorNumber) + "): " + message);
|
return new SQLException("TDengine ERROR (" + Integer.toHexString(errorNumber) + "): " + message);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static SQLClientInfoException createSQLClientInfoException(int errorNumber) {
|
||||||
|
return new SQLClientInfoException();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -12,6 +12,10 @@ public class TSDBErrorNumbers {
|
||||||
public static final int ERROR_BATCH_IS_EMPTY = 0x2306; //Batch is empty!
|
public static final int ERROR_BATCH_IS_EMPTY = 0x2306; //Batch is empty!
|
||||||
public static final int ERROR_INVALID_WITH_EXECUTEQUERY = 0x2307; //Can not issue data manipulation statements with executeQuery()
|
public static final int ERROR_INVALID_WITH_EXECUTEQUERY = 0x2307; //Can not issue data manipulation statements with executeQuery()
|
||||||
public static final int ERROR_INVALID_WITH_EXECUTEUPDATE = 0x2308; //Can not issue SELECT via executeUpdate()
|
public static final int ERROR_INVALID_WITH_EXECUTEUPDATE = 0x2308; //Can not issue SELECT via executeUpdate()
|
||||||
|
public static final int ERROR_INVALID_FOR_EXECUTE_QUERY = 0x2309; //not a valid sql for executeQuery: (SQL)
|
||||||
|
public static final int ERROR_DATABASE_NOT_SPECIFIED_OR_AVAILABLE = 0x2310; //Database not specified or available
|
||||||
|
public static final int ERROR_INVALID_FOR_EXECUTE_UPDATE = 0x2311; //not a valid sql for executeUpdate: (SQL)
|
||||||
|
public static final int ERROR_INVALID_FOR_EXECUTE = 0x2312; //not a valid sql for execute: (SQL)
|
||||||
|
|
||||||
public static final int ERROR_UNKNOWN = 0x2350; //unknown error
|
public static final int ERROR_UNKNOWN = 0x2350; //unknown error
|
||||||
|
|
||||||
|
@ -37,6 +41,11 @@ public class TSDBErrorNumbers {
|
||||||
errorNumbers.add(ERROR_RESULTSET_CLOSED);
|
errorNumbers.add(ERROR_RESULTSET_CLOSED);
|
||||||
errorNumbers.add(ERROR_INVALID_WITH_EXECUTEQUERY);
|
errorNumbers.add(ERROR_INVALID_WITH_EXECUTEQUERY);
|
||||||
errorNumbers.add(ERROR_INVALID_WITH_EXECUTEUPDATE);
|
errorNumbers.add(ERROR_INVALID_WITH_EXECUTEUPDATE);
|
||||||
|
errorNumbers.add(ERROR_INVALID_FOR_EXECUTE_QUERY);
|
||||||
|
errorNumbers.add(ERROR_DATABASE_NOT_SPECIFIED_OR_AVAILABLE);
|
||||||
|
errorNumbers.add(ERROR_INVALID_FOR_EXECUTE_UPDATE);
|
||||||
|
errorNumbers.add(ERROR_INVALID_FOR_EXECUTE);
|
||||||
|
|
||||||
/*****************************************************/
|
/*****************************************************/
|
||||||
errorNumbers.add(ERROR_SUBSCRIBE_FAILED);
|
errorNumbers.add(ERROR_SUBSCRIBE_FAILED);
|
||||||
errorNumbers.add(ERROR_UNSUPPORTED_ENCODING);
|
errorNumbers.add(ERROR_UNSUPPORTED_ENCODING);
|
||||||
|
|
|
@ -16,9 +16,6 @@ package com.taosdata.jdbc;
|
||||||
|
|
||||||
import javax.management.OperationsException;
|
import javax.management.OperationsException;
|
||||||
import java.sql.SQLException;
|
import java.sql.SQLException;
|
||||||
import java.util.Map;
|
|
||||||
import java.util.TimerTask;
|
|
||||||
import java.util.concurrent.*;
|
|
||||||
|
|
||||||
public class TSDBSubscribe {
|
public class TSDBSubscribe {
|
||||||
private TSDBJNIConnector connecter = null;
|
private TSDBJNIConnector connecter = null;
|
||||||
|
@ -36,9 +33,8 @@ public class TSDBSubscribe {
|
||||||
/**
|
/**
|
||||||
* consume
|
* consume
|
||||||
*
|
*
|
||||||
* @throws OperationsException, SQLException
|
|
||||||
*/
|
*/
|
||||||
public TSDBResultSet consume() throws OperationsException, SQLException {
|
public TSDBResultSet consume() throws SQLException {
|
||||||
if (this.connecter.isClosed()) {
|
if (this.connecter.isClosed()) {
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,34 +1,23 @@
|
||||||
package com.taosdata.jdbc.rs;
|
package com.taosdata.jdbc.rs;
|
||||||
|
|
||||||
import com.taosdata.jdbc.TSDBConstants;
|
import com.taosdata.jdbc.*;
|
||||||
import com.taosdata.jdbc.TSDBDriver;
|
|
||||||
|
|
||||||
import java.sql.*;
|
import java.sql.*;
|
||||||
import java.util.Enumeration;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
import java.util.concurrent.Executor;
|
|
||||||
|
|
||||||
public class RestfulConnection implements Connection {
|
public class RestfulConnection extends AbstractConnection {
|
||||||
|
|
||||||
private static final String CONNECTION_IS_CLOSED = "connection is closed.";
|
|
||||||
private static final String AUTO_COMMIT_IS_TRUE = "auto commit is true";
|
|
||||||
private final String host;
|
private final String host;
|
||||||
private final int port;
|
private final int port;
|
||||||
private final Properties props;
|
|
||||||
private volatile String database;
|
|
||||||
private final String url;
|
private final String url;
|
||||||
|
private volatile String database;
|
||||||
/******************************************************/
|
/******************************************************/
|
||||||
private boolean isClosed;
|
private boolean isClosed;
|
||||||
private DatabaseMetaData metadata;
|
private final DatabaseMetaData metadata;
|
||||||
private Map<String, Class<?>> typeMap;
|
|
||||||
private Properties clientInfoProps = new Properties();
|
|
||||||
|
|
||||||
public RestfulConnection(String host, String port, Properties props, String database, String url) {
|
public RestfulConnection(String host, String port, Properties props, String database, String url) {
|
||||||
this.host = host;
|
this.host = host;
|
||||||
this.port = Integer.parseInt(port);
|
this.port = Integer.parseInt(port);
|
||||||
this.props = props;
|
|
||||||
this.database = database;
|
this.database = database;
|
||||||
this.url = url;
|
this.url = url;
|
||||||
this.metadata = new RestfulDatabaseMetaData(url, props.getProperty(TSDBDriver.PROPERTY_KEY_USER), this);
|
this.metadata = new RestfulDatabaseMetaData(url, props.getProperty(TSDBDriver.PROPERTY_KEY_USER), this);
|
||||||
|
@ -37,7 +26,7 @@ public class RestfulConnection implements Connection {
|
||||||
@Override
|
@Override
|
||||||
public Statement createStatement() throws SQLException {
|
public Statement createStatement() throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);;
|
||||||
|
|
||||||
return new RestfulStatement(this, database);
|
return new RestfulStatement(this, database);
|
||||||
}
|
}
|
||||||
|
@ -45,61 +34,11 @@ public class RestfulConnection implements Connection {
|
||||||
@Override
|
@Override
|
||||||
public PreparedStatement prepareStatement(String sql) throws SQLException {
|
public PreparedStatement prepareStatement(String sql) throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);;
|
||||||
//TODO: prepareStatement
|
//TODO: prepareStatement
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public CallableStatement prepareCall(String sql) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String nativeSQL(String sql) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
|
|
||||||
//nothing did
|
|
||||||
return sql;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setAutoCommit(boolean autoCommit) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (!autoCommit)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean getAutoCommit() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void commit() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (getAutoCommit())
|
|
||||||
throw new SQLException(AUTO_COMMIT_IS_TRUE);
|
|
||||||
//nothing to do
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void rollback() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (getAutoCommit())
|
|
||||||
throw new SQLException(AUTO_COMMIT_IS_TRUE);
|
|
||||||
//nothing to do
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void close() throws SQLException {
|
public void close() throws SQLException {
|
||||||
if (isClosed)
|
if (isClosed)
|
||||||
|
@ -116,356 +55,11 @@ public class RestfulConnection implements Connection {
|
||||||
@Override
|
@Override
|
||||||
public DatabaseMetaData getMetaData() throws SQLException {
|
public DatabaseMetaData getMetaData() throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);;
|
||||||
|
|
||||||
return this.metadata;
|
return this.metadata;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setReadOnly(boolean readOnly) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
// nothing to do
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean isReadOnly() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setCatalog(String catalog) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
synchronized (RestfulConnection.class) {
|
|
||||||
this.database = catalog;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getCatalog() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
return this.database;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setTransactionIsolation(int level) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
switch (level) {
|
|
||||||
case Connection.TRANSACTION_NONE:
|
|
||||||
break;
|
|
||||||
case Connection.TRANSACTION_READ_UNCOMMITTED:
|
|
||||||
case Connection.TRANSACTION_READ_COMMITTED:
|
|
||||||
case Connection.TRANSACTION_REPEATABLE_READ:
|
|
||||||
case Connection.TRANSACTION_SERIALIZABLE:
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
default:
|
|
||||||
throw new SQLException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getTransactionIsolation() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
//Connection.TRANSACTION_NONE specifies that transactions are not supported.
|
|
||||||
return Connection.TRANSACTION_NONE;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public SQLWarning getWarnings() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void clearWarnings() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
//nothing to do
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Statement createStatement(int resultSetType, int resultSetConcurrency) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
|
|
||||||
if (resultSetType != ResultSet.TYPE_FORWARD_ONLY) {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
if (resultSetConcurrency != ResultSet.CONCUR_READ_ONLY)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
return createStatement();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (resultSetType != ResultSet.TYPE_FORWARD_ONLY || resultSetConcurrency != ResultSet.CONCUR_READ_ONLY)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
|
|
||||||
return this.prepareStatement(sql);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (resultSetType != ResultSet.TYPE_FORWARD_ONLY || resultSetConcurrency != ResultSet.CONCUR_READ_ONLY)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Map<String, Class<?>> getTypeMap() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
|
|
||||||
synchronized (RestfulConnection.class) {
|
|
||||||
if (this.typeMap == null) {
|
|
||||||
this.typeMap = new HashMap<>();
|
|
||||||
}
|
|
||||||
return this.typeMap;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setTypeMap(Map<String, Class<?>> map) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
|
|
||||||
synchronized (RestfulConnection.class) {
|
|
||||||
this.typeMap = map;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setHoldability(int holdability) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (holdability != ResultSet.HOLD_CURSORS_OVER_COMMIT)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getHoldability() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
return ResultSet.HOLD_CURSORS_OVER_COMMIT;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Savepoint setSavepoint() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (getAutoCommit())
|
|
||||||
throw new SQLException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
//nothing to do
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Savepoint setSavepoint(String name) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (getAutoCommit())
|
|
||||||
throw new SQLException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
//nothing to do
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void rollback(Savepoint savepoint) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
if (getAutoCommit())
|
|
||||||
throw new SQLException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
//nothing to do
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void releaseSavepoint(Savepoint savepoint) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Statement createStatement(int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
|
|
||||||
if (resultSetHoldability != ResultSet.HOLD_CURSORS_OVER_COMMIT)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
return createStatement(resultSetType, resultSetConcurrency);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
|
|
||||||
if (resultSetHoldability != ResultSet.HOLD_CURSORS_OVER_COMMIT)
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
return prepareStatement(sql, resultSetType, resultSetConcurrency);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public PreparedStatement prepareStatement(String sql, int autoGeneratedKeys) throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public PreparedStatement prepareStatement(String sql, int[] columnIndexes) throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public PreparedStatement prepareStatement(String sql, String[] columnNames) throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Clob createClob() throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Blob createBlob() throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public NClob createNClob() throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public SQLXML createSQLXML() throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean isValid(int timeout) throws SQLException {
|
|
||||||
if (timeout < 0)
|
|
||||||
throw new SQLException(TSDBConstants.INVALID_VARIABLES);
|
|
||||||
// TODO:
|
|
||||||
/* The driver shall submit a query on the connection or use some other mechanism that positively verifies
|
|
||||||
the connection is still valid when this method is called.*/
|
|
||||||
return !isClosed();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setClientInfo(String name, String value) throws SQLClientInfoException {
|
|
||||||
if (isClosed)
|
|
||||||
throw new SQLClientInfoException();
|
|
||||||
clientInfoProps.setProperty(name, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setClientInfo(Properties properties) throws SQLClientInfoException {
|
|
||||||
if (isClosed)
|
|
||||||
throw new SQLClientInfoException();
|
|
||||||
|
|
||||||
for (Enumeration<Object> enumer = properties.keys(); enumer.hasMoreElements(); ) {
|
|
||||||
String name = (String) enumer.nextElement();
|
|
||||||
clientInfoProps.put(name, properties.getProperty(name));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getClientInfo(String name) throws SQLException {
|
|
||||||
if (isClosed)
|
|
||||||
throw new SQLClientInfoException();
|
|
||||||
|
|
||||||
return clientInfoProps.getProperty(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Properties getClientInfo() throws SQLException {
|
|
||||||
if (isClosed)
|
|
||||||
throw new SQLClientInfoException();
|
|
||||||
|
|
||||||
return clientInfoProps;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Array createArrayOf(String typeName, Object[] elements) throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public Struct createStruct(String typeName, Object[] attributes) throws SQLException {
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setSchema(String schema) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
synchronized (RestfulConnection.class) {
|
|
||||||
this.database = schema;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getSchema() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
return this.database;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void abort(Executor executor) throws SQLException {
|
|
||||||
if (executor == null) {
|
|
||||||
throw new SQLException("Executor can not be null");
|
|
||||||
}
|
|
||||||
|
|
||||||
executor.execute(() -> {
|
|
||||||
try {
|
|
||||||
close();
|
|
||||||
} catch (SQLException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setNetworkTimeout(Executor executor, int milliseconds) throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
throw new SQLFeatureNotSupportedException(TSDBConstants.UNSUPPORTED_METHOD_EXCEPTION_MSG);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getNetworkTimeout() throws SQLException {
|
|
||||||
if (isClosed())
|
|
||||||
throw new SQLException(CONNECTION_IS_CLOSED);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public <T> T unwrap(Class<T> iface) throws SQLException {
|
|
||||||
try {
|
|
||||||
return iface.cast(this);
|
|
||||||
} catch (ClassCastException cce) {
|
|
||||||
throw new SQLException("Unable to unwrap to " + iface.toString());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean isWrapperFor(Class<?> iface) throws SQLException {
|
|
||||||
return iface.isInstance(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getHost() {
|
public String getHost() {
|
||||||
return host;
|
return host;
|
||||||
}
|
}
|
||||||
|
@ -474,10 +68,6 @@ public class RestfulConnection implements Connection {
|
||||||
return port;
|
return port;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Properties getProps() {
|
|
||||||
return props;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getDatabase() {
|
public String getDatabase() {
|
||||||
return database;
|
return database;
|
||||||
}
|
}
|
||||||
|
@ -485,4 +75,4 @@ public class RestfulConnection implements Connection {
|
||||||
public String getUrl() {
|
public String getUrl() {
|
||||||
return url;
|
return url;
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -1,10 +1,12 @@
|
||||||
package com.taosdata.jdbc.rs;
|
package com.taosdata.jdbc.rs;
|
||||||
|
|
||||||
import com.taosdata.jdbc.*;
|
import com.taosdata.jdbc.AbstractDatabaseMetaData;
|
||||||
|
import com.taosdata.jdbc.TSDBError;
|
||||||
|
import com.taosdata.jdbc.TSDBErrorNumbers;
|
||||||
|
|
||||||
import java.sql.*;
|
import java.sql.Connection;
|
||||||
import java.util.ArrayList;
|
import java.sql.ResultSet;
|
||||||
import java.util.List;
|
import java.sql.SQLException;
|
||||||
|
|
||||||
public class RestfulDatabaseMetaData extends AbstractDatabaseMetaData {
|
public class RestfulDatabaseMetaData extends AbstractDatabaseMetaData {
|
||||||
|
|
||||||
|
@ -33,11 +35,10 @@ public class RestfulDatabaseMetaData extends AbstractDatabaseMetaData {
|
||||||
return RestfulDriver.class.getName();
|
return RestfulDriver.class.getName();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) throws SQLException {
|
public ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern, String[] types) throws SQLException {
|
||||||
if (connection == null || connection.isClosed()) {
|
if (connection == null || connection.isClosed()) {
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
}
|
}
|
||||||
return super.getTables(catalog, schemaPattern, tableNamePattern, types, connection);
|
return super.getTables(catalog, schemaPattern, tableNamePattern, types, connection);
|
||||||
}
|
}
|
||||||
|
@ -45,14 +46,14 @@ public class RestfulDatabaseMetaData extends AbstractDatabaseMetaData {
|
||||||
@Override
|
@Override
|
||||||
public ResultSet getCatalogs() throws SQLException {
|
public ResultSet getCatalogs() throws SQLException {
|
||||||
if (connection == null || connection.isClosed())
|
if (connection == null || connection.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getCatalogs(connection);
|
return super.getCatalogs(connection);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ResultSet getTableTypes() throws SQLException {
|
public ResultSet getTableTypes() throws SQLException {
|
||||||
if (connection == null || connection.isClosed()) {
|
if (connection == null || connection.isClosed()) {
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
}
|
}
|
||||||
return super.getTableTypes();
|
return super.getTableTypes();
|
||||||
}
|
}
|
||||||
|
@ -60,21 +61,26 @@ public class RestfulDatabaseMetaData extends AbstractDatabaseMetaData {
|
||||||
@Override
|
@Override
|
||||||
public ResultSet getColumns(String catalog, String schemaPattern, String tableNamePattern, String columnNamePattern) throws SQLException {
|
public ResultSet getColumns(String catalog, String schemaPattern, String tableNamePattern, String columnNamePattern) throws SQLException {
|
||||||
if (connection == null || connection.isClosed())
|
if (connection == null || connection.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getColumns(catalog, schemaPattern, tableNamePattern, columnNamePattern, connection);
|
return super.getColumns(catalog, schemaPattern, tableNamePattern, columnNamePattern, connection);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ResultSet getPrimaryKeys(String catalog, String schema, String table) throws SQLException {
|
public ResultSet getPrimaryKeys(String catalog, String schema, String table) throws SQLException {
|
||||||
if (connection == null || connection.isClosed())
|
if (connection == null || connection.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getPrimaryKeys(catalog, schema, table, connection);
|
return super.getPrimaryKeys(catalog, schema, table, connection);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Connection getConnection() throws SQLException {
|
||||||
|
return this.connection;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ResultSet getSuperTables(String catalog, String schemaPattern, String tableNamePattern) throws SQLException {
|
public ResultSet getSuperTables(String catalog, String schemaPattern, String tableNamePattern) throws SQLException {
|
||||||
if (connection == null || connection.isClosed())
|
if (connection == null || connection.isClosed())
|
||||||
throw new SQLException(TSDBConstants.FixErrMsg(TSDBConstants.JNI_CONNECTION_NULL));
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_CONNECTION_CLOSED);
|
||||||
return super.getSuperTables(catalog, schemaPattern, tableNamePattern, connection);
|
return super.getSuperTables(catalog, schemaPattern, tableNamePattern, connection);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -4,6 +4,8 @@ import com.alibaba.fastjson.JSON;
|
||||||
import com.alibaba.fastjson.JSONObject;
|
import com.alibaba.fastjson.JSONObject;
|
||||||
import com.taosdata.jdbc.AbstractStatement;
|
import com.taosdata.jdbc.AbstractStatement;
|
||||||
import com.taosdata.jdbc.TSDBConstants;
|
import com.taosdata.jdbc.TSDBConstants;
|
||||||
|
import com.taosdata.jdbc.TSDBError;
|
||||||
|
import com.taosdata.jdbc.TSDBErrorNumbers;
|
||||||
import com.taosdata.jdbc.rs.util.HttpClientPoolUtil;
|
import com.taosdata.jdbc.rs.util.HttpClientPoolUtil;
|
||||||
import com.taosdata.jdbc.utils.SqlSyntaxValidator;
|
import com.taosdata.jdbc.utils.SqlSyntaxValidator;
|
||||||
|
|
||||||
|
@ -63,9 +65,9 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
@Override
|
@Override
|
||||||
public ResultSet executeQuery(String sql) throws SQLException {
|
public ResultSet executeQuery(String sql) throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException("statement already closed");
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||||
if (!SqlSyntaxValidator.isValidForExecuteQuery(sql))
|
if (!SqlSyntaxValidator.isValidForExecuteQuery(sql))
|
||||||
throw new SQLException("not a valid sql for executeQuery: " + sql);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE_QUERY, "not a valid sql for executeQuery: " + sql);
|
||||||
|
|
||||||
final String url = "http://" + conn.getHost() + ":" + conn.getPort() + "/rest/sql";
|
final String url = "http://" + conn.getHost() + ":" + conn.getPort() + "/rest/sql";
|
||||||
if (SqlSyntaxValidator.isDatabaseUnspecifiedQuery(sql)) {
|
if (SqlSyntaxValidator.isDatabaseUnspecifiedQuery(sql)) {
|
||||||
|
@ -73,7 +75,7 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.database == null || this.database.isEmpty())
|
if (this.database == null || this.database.isEmpty())
|
||||||
throw new SQLException("Database not specified or available");
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_DATABASE_NOT_SPECIFIED_OR_AVAILABLE);
|
||||||
HttpClientPoolUtil.execute(url, "use " + this.database);
|
HttpClientPoolUtil.execute(url, "use " + this.database);
|
||||||
return executeOneQuery(url, sql);
|
return executeOneQuery(url, sql);
|
||||||
}
|
}
|
||||||
|
@ -81,9 +83,9 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
@Override
|
@Override
|
||||||
public int executeUpdate(String sql) throws SQLException {
|
public int executeUpdate(String sql) throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException("statement already closed");
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||||
if (!SqlSyntaxValidator.isValidForExecuteUpdate(sql))
|
if (!SqlSyntaxValidator.isValidForExecuteUpdate(sql))
|
||||||
throw new SQLException("not a valid sql for executeUpdate: " + sql);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE_UPDATE, "not a valid sql for executeUpdate: " + sql);
|
||||||
|
|
||||||
final String url = "http://" + conn.getHost() + ":" + conn.getPort() + "/rest/sql";
|
final String url = "http://" + conn.getHost() + ":" + conn.getPort() + "/rest/sql";
|
||||||
if (SqlSyntaxValidator.isDatabaseUnspecifiedUpdate(sql)) {
|
if (SqlSyntaxValidator.isDatabaseUnspecifiedUpdate(sql)) {
|
||||||
|
@ -91,7 +93,8 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.database == null || this.database.isEmpty())
|
if (this.database == null || this.database.isEmpty())
|
||||||
throw new SQLException("Database not specified or available");
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_DATABASE_NOT_SPECIFIED_OR_AVAILABLE);
|
||||||
|
|
||||||
HttpClientPoolUtil.execute(url, "use " + this.database);
|
HttpClientPoolUtil.execute(url, "use " + this.database);
|
||||||
return executeOneUpdate(url, sql);
|
return executeOneUpdate(url, sql);
|
||||||
}
|
}
|
||||||
|
@ -107,9 +110,9 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
@Override
|
@Override
|
||||||
public boolean execute(String sql) throws SQLException {
|
public boolean execute(String sql) throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException("Invalid method call on a closed statement.");
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||||
if (!SqlSyntaxValidator.isValidForExecute(sql))
|
if (!SqlSyntaxValidator.isValidForExecute(sql))
|
||||||
throw new SQLException("not a valid sql for execute: " + sql);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE, "not a valid sql for execute: " + sql);
|
||||||
|
|
||||||
//如果执行了use操作应该将当前Statement的catalog设置为新的database
|
//如果执行了use操作应该将当前Statement的catalog设置为新的database
|
||||||
final String url = "http://" + conn.getHost() + ":" + conn.getPort() + "/rest/sql";
|
final String url = "http://" + conn.getHost() + ":" + conn.getPort() + "/rest/sql";
|
||||||
|
@ -134,7 +137,7 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
|
|
||||||
private ResultSet executeOneQuery(String url, String sql) throws SQLException {
|
private ResultSet executeOneQuery(String url, String sql) throws SQLException {
|
||||||
if (!SqlSyntaxValidator.isValidForExecuteQuery(sql))
|
if (!SqlSyntaxValidator.isValidForExecuteQuery(sql))
|
||||||
throw new SQLException("not a select sql for executeQuery: " + sql);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE_QUERY, "not a valid sql for executeQuery: " + sql);
|
||||||
|
|
||||||
// row data
|
// row data
|
||||||
String result = HttpClientPoolUtil.execute(url, sql);
|
String result = HttpClientPoolUtil.execute(url, sql);
|
||||||
|
@ -165,7 +168,7 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
|
|
||||||
private int executeOneUpdate(String url, String sql) throws SQLException {
|
private int executeOneUpdate(String url, String sql) throws SQLException {
|
||||||
if (!SqlSyntaxValidator.isValidForExecuteUpdate(sql))
|
if (!SqlSyntaxValidator.isValidForExecuteUpdate(sql))
|
||||||
throw new SQLException("not a valid sql for executeUpdate: " + sql);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_INVALID_FOR_EXECUTE_UPDATE, "not a valid sql for executeUpdate: " + sql);
|
||||||
|
|
||||||
String result = HttpClientPoolUtil.execute(url, sql);
|
String result = HttpClientPoolUtil.execute(url, sql);
|
||||||
JSONObject jsonObject = JSON.parseObject(result);
|
JSONObject jsonObject = JSON.parseObject(result);
|
||||||
|
@ -186,16 +189,16 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getUpdateCount() throws SQLException {
|
public int getUpdateCount() throws SQLException {
|
||||||
if (isClosed()) {
|
if (isClosed())
|
||||||
throw new SQLException("Invalid method call on a closed statement.");
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||||
}
|
|
||||||
return this.affectedRows;
|
return this.affectedRows;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void addBatch(String sql) throws SQLException {
|
public void addBatch(String sql) throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException(TSDBConstants.STATEMENT_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||||
//TODO:
|
//TODO:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -213,7 +216,7 @@ public class RestfulStatement extends AbstractStatement {
|
||||||
@Override
|
@Override
|
||||||
public Connection getConnection() throws SQLException {
|
public Connection getConnection() throws SQLException {
|
||||||
if (isClosed())
|
if (isClosed())
|
||||||
throw new SQLException(TSDBConstants.STATEMENT_CLOSED);
|
throw TSDBError.createSQLException(TSDBErrorNumbers.ERROR_STATEMENT_CLOSED);
|
||||||
return this.conn;
|
return this.conn;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,39 +0,0 @@
|
||||||
package com.taosdata.jdbc;
|
|
||||||
|
|
||||||
import org.junit.Assert;
|
|
||||||
import org.junit.Test;
|
|
||||||
|
|
||||||
import java.sql.Connection;
|
|
||||||
import java.sql.DriverManager;
|
|
||||||
import java.sql.SQLException;
|
|
||||||
import java.sql.Statement;
|
|
||||||
import java.util.Properties;
|
|
||||||
|
|
||||||
|
|
||||||
public class ConnectionTest {
|
|
||||||
private Connection connection;
|
|
||||||
private Statement statement;
|
|
||||||
private static String host = "127.0.0.1";
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void testConnection() {
|
|
||||||
Properties properties = new Properties();
|
|
||||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
|
||||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
|
||||||
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
|
||||||
|
|
||||||
try {
|
|
||||||
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
|
||||||
connection = DriverManager.getConnection("jdbc:TAOS://" + host + ":0/", properties);
|
|
||||||
Assert.assertTrue(null != connection);
|
|
||||||
statement = connection.createStatement();
|
|
||||||
Assert.assertTrue(null != statement);
|
|
||||||
statement.close();
|
|
||||||
connection.close();
|
|
||||||
} catch (ClassNotFoundException e) {
|
|
||||||
return;
|
|
||||||
} catch (SQLException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -0,0 +1,423 @@
|
||||||
|
package com.taosdata.jdbc;
|
||||||
|
|
||||||
|
import org.junit.AfterClass;
|
||||||
|
import org.junit.Assert;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import javax.management.OperationsException;
|
||||||
|
import java.sql.*;
|
||||||
|
import java.util.Properties;
|
||||||
|
|
||||||
|
public class TSDBConnectionTest {
|
||||||
|
|
||||||
|
private static final String host = "127.0.0.1";
|
||||||
|
private static Connection conn;
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getConnection() {
|
||||||
|
// already test in beforeClass method
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createStatement() {
|
||||||
|
try (Statement stmt = conn.createStatement()) {
|
||||||
|
ResultSet rs = stmt.executeQuery("select server_status()");
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void subscribe() {
|
||||||
|
try {
|
||||||
|
TSDBConnection unwrap = conn.unwrap(TSDBConnection.class);
|
||||||
|
TSDBSubscribe subscribe = unwrap.subscribe("topic1", "select * from log.log", false);
|
||||||
|
TSDBResultSet rs = subscribe.consume();
|
||||||
|
ResultSetMetaData metaData = rs.getMetaData();
|
||||||
|
for (int count = 0; count < 10 && rs.next(); count++) {
|
||||||
|
for (int i = 1; i <= metaData.getColumnCount(); i++) {
|
||||||
|
String value = rs.getString(i);
|
||||||
|
System.out.print(metaData.getColumnLabel(i) + ":" + value + "\t");
|
||||||
|
}
|
||||||
|
System.out.println();
|
||||||
|
}
|
||||||
|
Assert.assertNotNull(rs);
|
||||||
|
subscribe.close(false);
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void prepareStatement() throws SQLException {
|
||||||
|
PreparedStatement pstmt = conn.prepareStatement("select server_status()");
|
||||||
|
ResultSet rs = pstmt.executeQuery();
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void prepareCall() throws SQLException {
|
||||||
|
conn.prepareCall("select server_status()");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void nativeSQL() throws SQLException {
|
||||||
|
String nativeSQL = conn.nativeSQL("select * from log.log");
|
||||||
|
Assert.assertEquals("select * from log.log", nativeSQL);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setAutoCommit() throws SQLException {
|
||||||
|
conn.setAutoCommit(true);
|
||||||
|
conn.setAutoCommit(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getAutoCommit() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.getAutoCommit());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void commit() throws SQLException {
|
||||||
|
conn.commit();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void rollback() throws SQLException {
|
||||||
|
conn.rollback();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void close() {
|
||||||
|
// connection will close in afterClass method
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isClosed() throws SQLException {
|
||||||
|
Assert.assertFalse(conn.isClosed());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getMetaData() throws SQLException {
|
||||||
|
DatabaseMetaData meta = conn.getMetaData();
|
||||||
|
Assert.assertNotNull(meta);
|
||||||
|
Assert.assertEquals("com.taosdata.jdbc.TSDBDriver", meta.getDriverName());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setReadOnly() throws SQLException {
|
||||||
|
conn.setReadOnly(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isReadOnly() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.isReadOnly());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setCatalog() throws SQLException {
|
||||||
|
conn.setCatalog("test");
|
||||||
|
Assert.assertEquals("test", conn.getCatalog());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getCatalog() throws SQLException {
|
||||||
|
conn.setCatalog("log");
|
||||||
|
Assert.assertEquals("log", conn.getCatalog());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setTransactionIsolation() throws SQLException {
|
||||||
|
conn.setTransactionIsolation(Connection.TRANSACTION_NONE);
|
||||||
|
Assert.assertEquals(Connection.TRANSACTION_NONE, conn.getTransactionIsolation());
|
||||||
|
conn.setTransactionIsolation(Connection.TRANSACTION_READ_UNCOMMITTED);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getTransactionIsolation() throws SQLException {
|
||||||
|
Assert.assertEquals(Connection.TRANSACTION_NONE, conn.getTransactionIsolation());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getWarnings() throws SQLException {
|
||||||
|
Assert.assertNull(conn.getWarnings());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void clearWarnings() throws SQLException {
|
||||||
|
conn.clearWarnings();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testCreateStatement() throws SQLException {
|
||||||
|
Statement stmt = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
ResultSet rs = stmt.executeQuery("select server_status()");
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement() throws SQLException {
|
||||||
|
PreparedStatement pstmt = conn.prepareStatement("select server_status()",
|
||||||
|
ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
ResultSet rs = pstmt.executeQuery();
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.prepareStatement("select server_status", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareCall() throws SQLException {
|
||||||
|
conn.prepareCall("", ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void getTypeMap() throws SQLException {
|
||||||
|
conn.getTypeMap();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setTypeMap() throws SQLException {
|
||||||
|
conn.setTypeMap(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setHoldability() throws SQLException {
|
||||||
|
conn.setHoldability(ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
Assert.assertEquals(ResultSet.HOLD_CURSORS_OVER_COMMIT, conn.getHoldability());
|
||||||
|
conn.setHoldability(ResultSet.CLOSE_CURSORS_AT_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getHoldability() throws SQLException {
|
||||||
|
Assert.assertEquals(ResultSet.HOLD_CURSORS_OVER_COMMIT, conn.getHoldability());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setSavepoint() throws SQLException {
|
||||||
|
conn.setSavepoint();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testSetSavepoint() throws SQLException {
|
||||||
|
conn.setSavepoint(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testRollback() throws SQLException {
|
||||||
|
conn.rollback(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void releaseSavepoint() throws SQLException {
|
||||||
|
conn.releaseSavepoint(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testCreateStatement1() throws SQLException {
|
||||||
|
Statement stmt = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
ResultSet rs = stmt.executeQuery("select server_status()");
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement1() throws SQLException {
|
||||||
|
PreparedStatement pstmt = conn.prepareStatement("select server_status()",
|
||||||
|
ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
ResultSet rs = pstmt.executeQuery();
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.prepareStatement("select server_status", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareCall1() throws SQLException {
|
||||||
|
conn.prepareCall("", ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement2() throws SQLException {
|
||||||
|
Assert.assertNotNull("", Statement.NO_GENERATED_KEYS);
|
||||||
|
conn.prepareStatement("", Statement.RETURN_GENERATED_KEYS);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement3() throws SQLException {
|
||||||
|
conn.prepareStatement("", new int[]{});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement4() throws SQLException {
|
||||||
|
conn.prepareStatement("", new String[]{});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createClob() throws SQLException {
|
||||||
|
conn.createClob();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createBlob() throws SQLException {
|
||||||
|
conn.createBlob();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createNClob() throws SQLException {
|
||||||
|
conn.createNClob();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createSQLXML() throws SQLException {
|
||||||
|
conn.createSQLXML();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLException.class)
|
||||||
|
public void isValid() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.isValid(10));
|
||||||
|
Assert.assertTrue(conn.isValid(0));
|
||||||
|
conn.isValid(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setClientInfo() throws SQLClientInfoException {
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "en_US.UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTC-8");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testSetClientInfo() throws SQLClientInfoException {
|
||||||
|
Properties properties = new Properties();
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
conn.setClientInfo(properties);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getClientInfo() throws SQLException {
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
|
||||||
|
Properties info = conn.getClientInfo();
|
||||||
|
String charset = info.getProperty(TSDBDriver.PROPERTY_KEY_CHARSET);
|
||||||
|
Assert.assertEquals("UTF-8", charset);
|
||||||
|
String locale = info.getProperty(TSDBDriver.PROPERTY_KEY_LOCALE);
|
||||||
|
Assert.assertEquals("en_US.UTF-8", locale);
|
||||||
|
String timezone = info.getProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE);
|
||||||
|
Assert.assertEquals("UTC-8", timezone);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testGetClientInfo() throws SQLException {
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
|
||||||
|
String charset = conn.getClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET);
|
||||||
|
Assert.assertEquals("UTF-8", charset);
|
||||||
|
String locale = conn.getClientInfo(TSDBDriver.PROPERTY_KEY_LOCALE);
|
||||||
|
Assert.assertEquals("en_US.UTF-8", locale);
|
||||||
|
String timezone = conn.getClientInfo(TSDBDriver.PROPERTY_KEY_TIME_ZONE);
|
||||||
|
Assert.assertEquals("UTC-8", timezone);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createArrayOf() throws SQLException {
|
||||||
|
conn.createArrayOf("", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createStruct() throws SQLException {
|
||||||
|
conn.createStruct("", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setSchema() throws SQLException {
|
||||||
|
conn.setSchema("test");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSchema() throws SQLException {
|
||||||
|
Assert.assertNull(conn.getSchema());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void abort() throws SQLException {
|
||||||
|
conn.abort(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setNetworkTimeout() throws SQLException {
|
||||||
|
conn.setNetworkTimeout(null, 1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void getNetworkTimeout() throws SQLException {
|
||||||
|
conn.getNetworkTimeout();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void unwrap() {
|
||||||
|
try {
|
||||||
|
TSDBConnection tsdbConnection = conn.unwrap(TSDBConnection.class);
|
||||||
|
Assert.assertNotNull(tsdbConnection);
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isWrapperFor() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.isWrapperFor(TSDBConnection.class));
|
||||||
|
}
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void beforeClass() {
|
||||||
|
try {
|
||||||
|
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
||||||
|
Properties properties = new Properties();
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
conn = DriverManager.getConnection("jdbc:TAOS://" + host + ":6030/log?user=root&password=taosdata", properties);
|
||||||
|
// create test database for test cases
|
||||||
|
try (Statement stmt = conn.createStatement()) {
|
||||||
|
stmt.execute("create database if not exists test");
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (ClassNotFoundException | SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@AfterClass
|
||||||
|
public static void afterClass() {
|
||||||
|
try {
|
||||||
|
if (conn != null)
|
||||||
|
conn.close();
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -24,11 +24,10 @@ public class TSDBDriverTest {
|
||||||
"jdbc:TAOS://:/test",
|
"jdbc:TAOS://:/test",
|
||||||
"jdbc:TAOS://localhost:0/?user=root&password=taosdata"
|
"jdbc:TAOS://localhost:0/?user=root&password=taosdata"
|
||||||
};
|
};
|
||||||
|
|
||||||
private Connection conn;
|
private Connection conn;
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testConnectWithJdbcURL() {
|
public void connectWithJdbcURL() {
|
||||||
final String url = "jdbc:TAOS://localhost:6030/log?user=root&password=taosdata";
|
final String url = "jdbc:TAOS://localhost:6030/log?user=root&password=taosdata";
|
||||||
try {
|
try {
|
||||||
conn = DriverManager.getConnection(url);
|
conn = DriverManager.getConnection(url);
|
||||||
|
@ -40,7 +39,7 @@ public class TSDBDriverTest {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testConnectWithProperties() {
|
public void connectWithProperties() {
|
||||||
final String jdbcUrl = "jdbc:TAOS://localhost:6030/log?user=root&password=taosdata";
|
final String jdbcUrl = "jdbc:TAOS://localhost:6030/log?user=root&password=taosdata";
|
||||||
Properties connProps = new Properties();
|
Properties connProps = new Properties();
|
||||||
connProps.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
connProps.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
@ -56,7 +55,7 @@ public class TSDBDriverTest {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testConnectWithConfigFile() {
|
public void connectWithConfigFile() {
|
||||||
String jdbcUrl = "jdbc:TAOS://:/log?user=root&password=taosdata";
|
String jdbcUrl = "jdbc:TAOS://:/log?user=root&password=taosdata";
|
||||||
Properties connProps = new Properties();
|
Properties connProps = new Properties();
|
||||||
connProps.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
connProps.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
@ -71,16 +70,6 @@ public class TSDBDriverTest {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test(expected = SQLException.class)
|
|
||||||
public void testAcceptsURL() throws SQLException {
|
|
||||||
Driver driver = new TSDBDriver();
|
|
||||||
for (String url : validURLs) {
|
|
||||||
assertTrue("failure - acceptsURL(\" " + url + " \") should be true", driver.acceptsURL(url));
|
|
||||||
}
|
|
||||||
driver.acceptsURL(null);
|
|
||||||
fail("acceptsURL throws exception when parameter is null");
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testParseURL() {
|
public void testParseURL() {
|
||||||
TSDBDriver driver = new TSDBDriver();
|
TSDBDriver driver = new TSDBDriver();
|
||||||
|
@ -121,8 +110,19 @@ public class TSDBDriverTest {
|
||||||
assertNull("failure - dbname should be null", actual.getProperty("dbname"));
|
assertNull("failure - dbname should be null", actual.getProperty("dbname"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Test(expected = SQLException.class)
|
||||||
|
public void acceptsURL() throws SQLException {
|
||||||
|
Driver driver = new TSDBDriver();
|
||||||
|
for (String url : validURLs) {
|
||||||
|
assertTrue("failure - acceptsURL(\" " + url + " \") should be true", driver.acceptsURL(url));
|
||||||
|
}
|
||||||
|
driver.acceptsURL(null);
|
||||||
|
fail("acceptsURL throws exception when parameter is null");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testGetPropertyInfo() throws SQLException {
|
public void getPropertyInfo() throws SQLException {
|
||||||
Driver driver = new TSDBDriver();
|
Driver driver = new TSDBDriver();
|
||||||
final String url = "jdbc:TAOS://localhost:6030/log?user=root&password=taosdata";
|
final String url = "jdbc:TAOS://localhost:6030/log?user=root&password=taosdata";
|
||||||
Properties connProps = new Properties();
|
Properties connProps = new Properties();
|
||||||
|
@ -142,23 +142,23 @@ public class TSDBDriverTest {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testGetMajorVersion() {
|
public void getMajorVersion() {
|
||||||
assertEquals("failure - getMajorVersion should be 2", 2, new TSDBDriver().getMajorVersion());
|
assertEquals(2, new TSDBDriver().getMajorVersion());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testGetMinorVersion() {
|
public void getMinorVersion() {
|
||||||
assertEquals("failure - getMinorVersion should be 0", 0, new TSDBDriver().getMinorVersion());
|
assertEquals(0, new TSDBDriver().getMinorVersion());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testJdbcCompliant() {
|
public void jdbcCompliant() {
|
||||||
assertFalse("failure - jdbcCompliant should be false", new TSDBDriver().jdbcCompliant());
|
assertFalse(new TSDBDriver().jdbcCompliant());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testGetParentLogger() throws SQLFeatureNotSupportedException {
|
public void getParentLogger() throws SQLFeatureNotSupportedException {
|
||||||
assertNull("failure - getParentLogger should be be null", new TSDBDriver().getParentLogger());
|
assertNull(new TSDBDriver().getParentLogger());
|
||||||
}
|
}
|
||||||
|
|
||||||
@BeforeClass
|
@BeforeClass
|
||||||
|
@ -169,6 +169,4 @@ public class TSDBDriverTest {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
|
@ -1,5 +1,6 @@
|
||||||
package com.taosdata.jdbc;
|
package com.taosdata.jdbc.cases;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.TSDBDriver;
|
||||||
import org.junit.*;
|
import org.junit.*;
|
||||||
import org.junit.runners.MethodSorters;
|
import org.junit.runners.MethodSorters;
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package com.taosdata.jdbc;
|
package com.taosdata.jdbc.cases;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.TSDBDriver;
|
||||||
import org.junit.After;
|
import org.junit.After;
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
|
@ -1,5 +1,6 @@
|
||||||
package com.taosdata.jdbc;
|
package com.taosdata.jdbc.cases;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.TSDBDriver;
|
||||||
import org.junit.After;
|
import org.junit.After;
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
|
@ -1,5 +1,6 @@
|
||||||
package com.taosdata.jdbc;
|
package com.taosdata.jdbc.cases;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.TSDBDriver;
|
||||||
import org.junit.AfterClass;
|
import org.junit.AfterClass;
|
||||||
import org.junit.BeforeClass;
|
import org.junit.BeforeClass;
|
||||||
import org.junit.FixMethodOrder;
|
import org.junit.FixMethodOrder;
|
|
@ -0,0 +1,406 @@
|
||||||
|
package com.taosdata.jdbc.rs;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.TSDBConnection;
|
||||||
|
import com.taosdata.jdbc.TSDBDriver;
|
||||||
|
import com.taosdata.jdbc.TSDBResultSet;
|
||||||
|
import com.taosdata.jdbc.TSDBSubscribe;
|
||||||
|
import org.junit.AfterClass;
|
||||||
|
import org.junit.Assert;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import javax.management.OperationsException;
|
||||||
|
import java.sql.*;
|
||||||
|
import java.util.Properties;
|
||||||
|
|
||||||
|
public class RestfulConnectionTest {
|
||||||
|
|
||||||
|
// private static final String host = "127.0.0.1";
|
||||||
|
private static final String host = "master";
|
||||||
|
private static Connection conn;
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getConnection() {
|
||||||
|
// already test in beforeClass method
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createStatement() {
|
||||||
|
try (Statement stmt = conn.createStatement()) {
|
||||||
|
ResultSet rs = stmt.executeQuery("select server_status()");
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void prepareStatement() throws SQLException {
|
||||||
|
PreparedStatement pstmt = conn.prepareStatement("select server_status()");
|
||||||
|
ResultSet rs = pstmt.executeQuery();
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void prepareCall() throws SQLException {
|
||||||
|
conn.prepareCall("select server_status()");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void nativeSQL() throws SQLException {
|
||||||
|
String nativeSQL = conn.nativeSQL("select * from log.log");
|
||||||
|
Assert.assertEquals("select * from log.log", nativeSQL);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setAutoCommit() throws SQLException {
|
||||||
|
conn.setAutoCommit(true);
|
||||||
|
conn.setAutoCommit(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getAutoCommit() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.getAutoCommit());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void commit() throws SQLException {
|
||||||
|
conn.commit();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void rollback() throws SQLException {
|
||||||
|
conn.rollback();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void close() {
|
||||||
|
// connection will close in afterClass method
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isClosed() throws SQLException {
|
||||||
|
Assert.assertFalse(conn.isClosed());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getMetaData() throws SQLException {
|
||||||
|
DatabaseMetaData meta = conn.getMetaData();
|
||||||
|
Assert.assertNotNull(meta);
|
||||||
|
Assert.assertEquals("com.taosdata.jdbc.rs.RestfulDriver", meta.getDriverName());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setReadOnly() throws SQLException {
|
||||||
|
conn.setReadOnly(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isReadOnly() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.isReadOnly());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setCatalog() throws SQLException {
|
||||||
|
conn.setCatalog("test");
|
||||||
|
Assert.assertEquals("test", conn.getCatalog());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getCatalog() throws SQLException {
|
||||||
|
conn.setCatalog("log");
|
||||||
|
Assert.assertEquals("log", conn.getCatalog());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setTransactionIsolation() throws SQLException {
|
||||||
|
conn.setTransactionIsolation(Connection.TRANSACTION_NONE);
|
||||||
|
Assert.assertEquals(Connection.TRANSACTION_NONE, conn.getTransactionIsolation());
|
||||||
|
conn.setTransactionIsolation(Connection.TRANSACTION_READ_UNCOMMITTED);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getTransactionIsolation() throws SQLException {
|
||||||
|
Assert.assertEquals(Connection.TRANSACTION_NONE, conn.getTransactionIsolation());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getWarnings() throws SQLException {
|
||||||
|
Assert.assertNull(conn.getWarnings());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void clearWarnings() throws SQLException {
|
||||||
|
conn.clearWarnings();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testCreateStatement() throws SQLException {
|
||||||
|
Statement stmt = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
ResultSet rs = stmt.executeQuery("select server_status()");
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement() throws SQLException {
|
||||||
|
PreparedStatement pstmt = conn.prepareStatement("select server_status()",
|
||||||
|
ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
ResultSet rs = pstmt.executeQuery();
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.prepareStatement("select server_status", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareCall() throws SQLException {
|
||||||
|
conn.prepareCall("", ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void getTypeMap() throws SQLException {
|
||||||
|
conn.getTypeMap();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setTypeMap() throws SQLException {
|
||||||
|
conn.setTypeMap(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setHoldability() throws SQLException {
|
||||||
|
conn.setHoldability(ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
Assert.assertEquals(ResultSet.HOLD_CURSORS_OVER_COMMIT, conn.getHoldability());
|
||||||
|
conn.setHoldability(ResultSet.CLOSE_CURSORS_AT_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getHoldability() throws SQLException {
|
||||||
|
Assert.assertEquals(ResultSet.HOLD_CURSORS_OVER_COMMIT, conn.getHoldability());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setSavepoint() throws SQLException {
|
||||||
|
conn.setSavepoint();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testSetSavepoint() throws SQLException {
|
||||||
|
conn.setSavepoint(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testRollback() throws SQLException {
|
||||||
|
conn.rollback(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void releaseSavepoint() throws SQLException {
|
||||||
|
conn.releaseSavepoint(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testCreateStatement1() throws SQLException {
|
||||||
|
Statement stmt = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
ResultSet rs = stmt.executeQuery("select server_status()");
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement1() throws SQLException {
|
||||||
|
PreparedStatement pstmt = conn.prepareStatement("select server_status()",
|
||||||
|
ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
ResultSet rs = pstmt.executeQuery();
|
||||||
|
rs.next();
|
||||||
|
int status = rs.getInt("server_status()");
|
||||||
|
Assert.assertEquals(1, status);
|
||||||
|
|
||||||
|
conn.prepareStatement("select server_status", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareCall1() throws SQLException {
|
||||||
|
conn.prepareCall("", ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement2() throws SQLException {
|
||||||
|
Assert.assertNotNull("", Statement.NO_GENERATED_KEYS);
|
||||||
|
conn.prepareStatement("", Statement.RETURN_GENERATED_KEYS);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement3() throws SQLException {
|
||||||
|
conn.prepareStatement("", new int[]{});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void testPrepareStatement4() throws SQLException {
|
||||||
|
conn.prepareStatement("", new String[]{});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createClob() throws SQLException {
|
||||||
|
conn.createClob();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createBlob() throws SQLException {
|
||||||
|
conn.createBlob();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createNClob() throws SQLException {
|
||||||
|
conn.createNClob();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createSQLXML() throws SQLException {
|
||||||
|
conn.createSQLXML();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLException.class)
|
||||||
|
public void isValid() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.isValid(10));
|
||||||
|
Assert.assertTrue(conn.isValid(0));
|
||||||
|
conn.isValid(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setClientInfo() throws SQLClientInfoException {
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "en_US.UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTC-8");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testSetClientInfo() throws SQLClientInfoException {
|
||||||
|
Properties properties = new Properties();
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
conn.setClientInfo(properties);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getClientInfo() throws SQLException {
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
|
||||||
|
Properties info = conn.getClientInfo();
|
||||||
|
String charset = info.getProperty(TSDBDriver.PROPERTY_KEY_CHARSET);
|
||||||
|
Assert.assertEquals("UTF-8", charset);
|
||||||
|
String locale = info.getProperty(TSDBDriver.PROPERTY_KEY_LOCALE);
|
||||||
|
Assert.assertEquals("en_US.UTF-8", locale);
|
||||||
|
String timezone = info.getProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE);
|
||||||
|
Assert.assertEquals("UTC-8", timezone);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testGetClientInfo() throws SQLException {
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
conn.setClientInfo(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
|
||||||
|
String charset = conn.getClientInfo(TSDBDriver.PROPERTY_KEY_CHARSET);
|
||||||
|
Assert.assertEquals("UTF-8", charset);
|
||||||
|
String locale = conn.getClientInfo(TSDBDriver.PROPERTY_KEY_LOCALE);
|
||||||
|
Assert.assertEquals("en_US.UTF-8", locale);
|
||||||
|
String timezone = conn.getClientInfo(TSDBDriver.PROPERTY_KEY_TIME_ZONE);
|
||||||
|
Assert.assertEquals("UTC-8", timezone);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createArrayOf() throws SQLException {
|
||||||
|
conn.createArrayOf("", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void createStruct() throws SQLException {
|
||||||
|
conn.createStruct("", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void setSchema() throws SQLException {
|
||||||
|
conn.setSchema("test");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSchema() throws SQLException {
|
||||||
|
Assert.assertNull(conn.getSchema());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void abort() throws SQLException {
|
||||||
|
conn.abort(null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void setNetworkTimeout() throws SQLException {
|
||||||
|
conn.setNetworkTimeout(null, 1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test(expected = SQLFeatureNotSupportedException.class)
|
||||||
|
public void getNetworkTimeout() throws SQLException {
|
||||||
|
conn.getNetworkTimeout();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void unwrap() {
|
||||||
|
try {
|
||||||
|
RestfulConnection restfulConnection = conn.unwrap(RestfulConnection.class);
|
||||||
|
Assert.assertNotNull(restfulConnection);
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isWrapperFor() throws SQLException {
|
||||||
|
Assert.assertTrue(conn.isWrapperFor(RestfulConnection.class));
|
||||||
|
}
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void beforeClass() {
|
||||||
|
try {
|
||||||
|
Class.forName("com.taosdata.jdbc.rs.RestfulDriver");
|
||||||
|
Properties properties = new Properties();
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
conn = DriverManager.getConnection("jdbc:TAOS-RS://" + host + ":6041/log?user=root&password=taosdata", properties);
|
||||||
|
// create test database for test cases
|
||||||
|
try (Statement stmt = conn.createStatement()) {
|
||||||
|
stmt.execute("create database if not exists test");
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (ClassNotFoundException | SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@AfterClass
|
||||||
|
public static void afterClass() {
|
||||||
|
try {
|
||||||
|
if (conn != null)
|
||||||
|
conn.close();
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,984 @@
|
||||||
|
package com.taosdata.jdbc.rs;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.TSDBDriver;
|
||||||
|
import org.junit.AfterClass;
|
||||||
|
import org.junit.Assert;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import java.sql.*;
|
||||||
|
import java.util.Properties;
|
||||||
|
|
||||||
|
public class RestfulDatabaseMetaDataTest {
|
||||||
|
// private static final String host = "master";
|
||||||
|
private static final String host = "127.0.0.1";
|
||||||
|
private static final String url = "jdbc:TAOS-RS://" + host + ":6041/?user=root&password=taosdata";
|
||||||
|
private static Connection connection;
|
||||||
|
private static RestfulDatabaseMetaData metaData;
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void unwrap() throws SQLException {
|
||||||
|
RestfulDatabaseMetaData unwrap = metaData.unwrap(RestfulDatabaseMetaData.class);
|
||||||
|
Assert.assertNotNull(unwrap);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void isWrapperFor() throws SQLException {
|
||||||
|
Assert.assertTrue(metaData.isWrapperFor(RestfulDatabaseMetaData.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(url, 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.rs.RestfulDriver", 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 {
|
||||||
|
System.out.println("****************************************************");
|
||||||
|
ResultSet tables = metaData.getTables("log", "", null, null);
|
||||||
|
ResultSetMetaData metaData = tables.getMetaData();
|
||||||
|
while (tables.next()) {
|
||||||
|
System.out.print(metaData.getColumnLabel(1) + ":" + tables.getString(1) + "\t");
|
||||||
|
System.out.print(metaData.getColumnLabel(3) + ":" + tables.getString(3) + "\t");
|
||||||
|
System.out.print(metaData.getColumnLabel(4) + ":" + tables.getString(4) + "\t");
|
||||||
|
System.out.print(metaData.getColumnLabel(5) + ":" + tables.getString(5) + "\n");
|
||||||
|
}
|
||||||
|
System.out.println();
|
||||||
|
Assert.assertNotNull(tables);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSchemas() throws SQLException {
|
||||||
|
Assert.assertNotNull(metaData.getSchemas());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getCatalogs() throws SQLException {
|
||||||
|
System.out.println("****************************************************");
|
||||||
|
|
||||||
|
ResultSet catalogs = metaData.getCatalogs();
|
||||||
|
ResultSetMetaData meta = catalogs.getMetaData();
|
||||||
|
while (catalogs.next()) {
|
||||||
|
for (int i = 1; i <= meta.getColumnCount(); i++) {
|
||||||
|
System.out.print(meta.getColumnLabel(i) + ": " + catalogs.getString(i));
|
||||||
|
}
|
||||||
|
System.out.println();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getTableTypes() throws SQLException {
|
||||||
|
System.out.println("****************************************************");
|
||||||
|
|
||||||
|
ResultSet tableTypes = metaData.getTableTypes();
|
||||||
|
while (tableTypes.next()) {
|
||||||
|
System.out.println(tableTypes.getString("TABLE_TYPE"));
|
||||||
|
}
|
||||||
|
Assert.assertNotNull(metaData.getTableTypes());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getColumns() throws SQLException {
|
||||||
|
System.out.println("****************************************************");
|
||||||
|
|
||||||
|
ResultSet columns = metaData.getColumns("log", "", "dn", "");
|
||||||
|
ResultSetMetaData meta = columns.getMetaData();
|
||||||
|
while (columns.next()) {
|
||||||
|
System.out.print(meta.getColumnLabel(1) + ": " + columns.getString(1) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(3) + ": " + columns.getString(3) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(4) + ": " + columns.getString(4) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(5) + ": " + columns.getString(5) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(6) + ": " + columns.getString(6) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(7) + ": " + columns.getString(7) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(9) + ": " + columns.getString(9) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(10) + ": " + columns.getString(10) + "\t");
|
||||||
|
System.out.print(meta.getColumnLabel(11) + ": " + columns.getString(11) + "\n");
|
||||||
|
System.out.print(meta.getColumnLabel(12) + ": " + columns.getString(12) + "\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@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 {
|
||||||
|
System.out.println("****************************************************");
|
||||||
|
|
||||||
|
ResultSet rs = metaData.getPrimaryKeys("log", "", "dn1");
|
||||||
|
while (rs.next()) {
|
||||||
|
System.out.println("TABLE_NAME: " + rs.getString("TABLE_NAME"));
|
||||||
|
System.out.println("COLUMN_NAME: " + rs.getString("COLUMN_NAME"));
|
||||||
|
System.out.println("KEY_SEQ: " + rs.getString("KEY_SEQ"));
|
||||||
|
System.out.println("PK_NAME: " + rs.getString("PK_NAME"));
|
||||||
|
}
|
||||||
|
|
||||||
|
Assert.assertNotNull(rs);
|
||||||
|
}
|
||||||
|
|
||||||
|
@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 {
|
||||||
|
System.out.println("****************************************************");
|
||||||
|
|
||||||
|
ResultSet rs = metaData.getSuperTables("log", "", "dn1");
|
||||||
|
while (rs.next()) {
|
||||||
|
System.out.println("TABLE_NAME: " + rs.getString("TABLE_NAME"));
|
||||||
|
System.out.println("SUPERTABLE_NAME: " + rs.getString("SUPERTABLE_NAME"));
|
||||||
|
}
|
||||||
|
Assert.assertNotNull(rs);
|
||||||
|
}
|
||||||
|
|
||||||
|
@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 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());
|
||||||
|
}
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void beforeClass() {
|
||||||
|
try {
|
||||||
|
Class.forName("com.taosdata.jdbc.rs.RestfulDriver");
|
||||||
|
Properties properties = new Properties();
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_CHARSET, "UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_LOCALE, "en_US.UTF-8");
|
||||||
|
properties.setProperty(TSDBDriver.PROPERTY_KEY_TIME_ZONE, "UTC-8");
|
||||||
|
connection = DriverManager.getConnection(url, properties);
|
||||||
|
metaData = connection.getMetaData().unwrap(RestfulDatabaseMetaData.class);
|
||||||
|
} catch (ClassNotFoundException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@AfterClass
|
||||||
|
public static void afterClass() {
|
||||||
|
try {
|
||||||
|
if (connection != null)
|
||||||
|
connection.close();
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -67,13 +67,13 @@ def _crow_tinyint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_byte))[
|
ctypes.c_ubyte))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_byte))[
|
ctypes.c_ubyte))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -102,13 +102,13 @@ def _crow_smallint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_short))[
|
ctypes.c_ushort))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_short))[
|
ctypes.c_ushort))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -130,13 +130,13 @@ def _crow_int_unsigned_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_int))[
|
ctypes.c_uint))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_int))[
|
ctypes.c_uint))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -162,13 +162,13 @@ def _crow_bigint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_long))[
|
ctypes.c_ulong))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_long))[
|
ctypes.c_ulong))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -19,10 +19,10 @@ class FieldType(object):
|
||||||
C_BINARY = 8
|
C_BINARY = 8
|
||||||
C_TIMESTAMP = 9
|
C_TIMESTAMP = 9
|
||||||
C_NCHAR = 10
|
C_NCHAR = 10
|
||||||
C_TINYINT_UNSIGNED = 12
|
C_TINYINT_UNSIGNED = 11
|
||||||
C_SMALLINT_UNSIGNED = 13
|
C_SMALLINT_UNSIGNED = 12
|
||||||
C_INT_UNSIGNED = 14
|
C_INT_UNSIGNED = 13
|
||||||
C_BIGINT_UNSIGNED = 15
|
C_BIGINT_UNSIGNED = 14
|
||||||
# NULL value definition
|
# NULL value definition
|
||||||
# NOTE: These values should change according to C definition in tsdb.h
|
# NOTE: These values should change according to C definition in tsdb.h
|
||||||
C_BOOL_NULL = 0x02
|
C_BOOL_NULL = 0x02
|
||||||
|
|
|
@ -67,13 +67,13 @@ def _crow_tinyint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_byte))[
|
ctypes.c_ubyte))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_byte))[
|
ctypes.c_ubyte))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -102,13 +102,13 @@ def _crow_smallint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_short))[
|
ctypes.c_ushort))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_short))[
|
ctypes.c_ushort))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -130,13 +130,13 @@ def _crow_int_unsigned_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_int))[
|
ctypes.c_uint))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_int))[
|
ctypes.c_uint))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -162,13 +162,13 @@ def _crow_bigint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_long))[
|
ctypes.c_ulong))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_long))[
|
ctypes.c_ulong))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -19,10 +19,10 @@ class FieldType(object):
|
||||||
C_BINARY = 8
|
C_BINARY = 8
|
||||||
C_TIMESTAMP = 9
|
C_TIMESTAMP = 9
|
||||||
C_NCHAR = 10
|
C_NCHAR = 10
|
||||||
C_TINYINT_UNSIGNED = 12
|
C_TINYINT_UNSIGNED = 11
|
||||||
C_SMALLINT_UNSIGNED = 13
|
C_SMALLINT_UNSIGNED = 12
|
||||||
C_INT_UNSIGNED = 14
|
C_INT_UNSIGNED = 13
|
||||||
C_BIGINT_UNSIGNED = 15
|
C_BIGINT_UNSIGNED = 14
|
||||||
# NULL value definition
|
# NULL value definition
|
||||||
# NOTE: These values should change according to C definition in tsdb.h
|
# NOTE: These values should change according to C definition in tsdb.h
|
||||||
C_BOOL_NULL = 0x02
|
C_BOOL_NULL = 0x02
|
||||||
|
|
|
@ -67,13 +67,13 @@ def _crow_tinyint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_byte))[
|
ctypes.c_ubyte))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_byte))[
|
ctypes.c_ubyte))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -102,13 +102,13 @@ def _crow_smallint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_short))[
|
ctypes.c_ushort))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_short))[
|
ctypes.c_ushort))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -130,13 +130,13 @@ def _crow_int_unsigned_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_int))[
|
ctypes.c_uint))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_int))[
|
ctypes.c_uint))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
@ -162,13 +162,13 @@ def _crow_bigint_unsigned_to_python(
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_long))[
|
ctypes.c_ulong))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [
|
return [
|
||||||
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
data, ctypes.POINTER(
|
data, ctypes.POINTER(
|
||||||
ctypes.c_long))[
|
ctypes.c_ulong))[
|
||||||
:abs(num_of_rows)]]
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -19,10 +19,10 @@ class FieldType(object):
|
||||||
C_BINARY = 8
|
C_BINARY = 8
|
||||||
C_TIMESTAMP = 9
|
C_TIMESTAMP = 9
|
||||||
C_NCHAR = 10
|
C_NCHAR = 10
|
||||||
C_TINYINT_UNSIGNED = 12
|
C_TINYINT_UNSIGNED = 11
|
||||||
C_SMALLINT_UNSIGNED = 13
|
C_SMALLINT_UNSIGNED = 12
|
||||||
C_INT_UNSIGNED = 14
|
C_INT_UNSIGNED = 13
|
||||||
C_BIGINT_UNSIGNED = 15
|
C_BIGINT_UNSIGNED = 14
|
||||||
# NULL value definition
|
# NULL value definition
|
||||||
# NOTE: These values should change according to C definition in tsdb.h
|
# NOTE: These values should change according to C definition in tsdb.h
|
||||||
C_BOOL_NULL = 0x02
|
C_BOOL_NULL = 0x02
|
||||||
|
|
|
@ -8,6 +8,7 @@ paramstyle = 'pyformat'
|
||||||
|
|
||||||
__all__ = ['connection', 'cursor']
|
__all__ = ['connection', 'cursor']
|
||||||
|
|
||||||
|
|
||||||
def connect(*args, **kwargs):
|
def connect(*args, **kwargs):
|
||||||
""" Function to return a TDengine connector object
|
""" Function to return a TDengine connector object
|
||||||
|
|
||||||
|
|
|
@ -4,11 +4,14 @@ from .error import *
|
||||||
import math
|
import math
|
||||||
import datetime
|
import datetime
|
||||||
|
|
||||||
|
|
||||||
def _convert_millisecond_to_datetime(milli):
|
def _convert_millisecond_to_datetime(milli):
|
||||||
return datetime.datetime.fromtimestamp(milli/1000.0)
|
return datetime.datetime.fromtimestamp(milli / 1000.0)
|
||||||
|
|
||||||
|
|
||||||
def _convert_microsecond_to_datetime(micro):
|
def _convert_microsecond_to_datetime(micro):
|
||||||
return datetime.datetime.fromtimestamp(micro/1000000.0)
|
return datetime.datetime.fromtimestamp(micro / 1000000.0)
|
||||||
|
|
||||||
|
|
||||||
def _crow_timestamp_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_timestamp_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C bool row to python row
|
"""Function to convert C bool row to python row
|
||||||
|
@ -18,168 +21,309 @@ def _crow_timestamp_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
_timestamp_converter = _convert_microsecond_to_datetime
|
_timestamp_converter = _convert_microsecond_to_datetime
|
||||||
|
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return list(map(_timestamp_converter, ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)]))
|
return list(map(_timestamp_converter, ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]))
|
||||||
else:
|
else:
|
||||||
return list(map(_timestamp_converter, ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)]))
|
return list(map(_timestamp_converter, ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]))
|
||||||
|
|
||||||
|
|
||||||
def _crow_bool_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_bool_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C bool row to python row
|
"""Function to convert C bool row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)] ]
|
return [
|
||||||
|
None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_byte))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_bool))[:abs(num_of_rows)] ]
|
return [
|
||||||
|
None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_bool))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_tinyint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_tinyint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C tinyint row to python row
|
"""Function to convert C tinyint row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_tinyint_unsigned_to_python(
|
||||||
|
data,
|
||||||
|
num_of_rows,
|
||||||
|
nbytes=None,
|
||||||
|
micro=False):
|
||||||
|
"""Function to convert C tinyint row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ubyte))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ubyte))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_smallint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_smallint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C smallint row to python row
|
"""Function to convert C smallint row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_short))[:abs(num_of_rows)]]
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_short))[:abs(num_of_rows)] ]
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_smallint_unsigned_to_python(
|
||||||
|
data, num_of_rows, nbytes=None, micro=False):
|
||||||
|
"""Function to convert C smallint row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ushort))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ushort))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_int_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_int_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C int row to python row
|
"""Function to convert C int row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_int_unsigned_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
|
"""Function to convert C int row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_uint))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_uint))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_bigint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_bigint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C bigint row to python row
|
"""Function to convert C bigint row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_bigint_unsigned_to_python(
|
||||||
|
data,
|
||||||
|
num_of_rows,
|
||||||
|
nbytes=None,
|
||||||
|
micro=False):
|
||||||
|
"""Function to convert C bigint row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ulong))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ulong))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_float_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_float_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C float row to python row
|
"""Function to convert C float row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_double_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_double_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C double row to python row
|
"""Function to convert C double row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_binary_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_binary_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C binary row to python row
|
"""Function to convert C binary row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode('utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
return [None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode(
|
||||||
|
'utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode('utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
return [None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode(
|
||||||
|
'utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_nchar_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_nchar_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C nchar row to python row
|
"""Function to convert C nchar row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
res=[]
|
res = []
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
if num_of_rows >= 0:
|
if num_of_rows >= 0:
|
||||||
tmpstr = ctypes.c_char_p(data)
|
tmpstr = ctypes.c_char_p(data)
|
||||||
res.append( tmpstr.value.decode() )
|
res.append(tmpstr.value.decode())
|
||||||
else:
|
else:
|
||||||
res.append( (ctypes.cast(data+nbytes*i, ctypes.POINTER(ctypes.c_wchar * (nbytes//4))))[0].value )
|
res.append((ctypes.cast(data + nbytes * i,
|
||||||
|
ctypes.POINTER(ctypes.c_wchar * (nbytes // 4))))[0].value)
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
|
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
def _crow_binary_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_binary_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C binary row to python row
|
"""Function to convert C binary row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
res=[]
|
res = []
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
rbyte=ctypes.cast(data+nbytes*i,ctypes.POINTER(ctypes.c_short))[:1].pop()
|
rbyte = ctypes.cast(
|
||||||
tmpstr = ctypes.c_char_p(data+nbytes*i+2)
|
data + nbytes * i,
|
||||||
res.append( tmpstr.value.decode()[0:rbyte] )
|
ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:1].pop()
|
||||||
|
tmpstr = ctypes.c_char_p(data + nbytes * i + 2)
|
||||||
|
res.append(tmpstr.value.decode()[0:rbyte])
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
else:
|
else:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
rbyte=ctypes.cast(data+nbytes*i,ctypes.POINTER(ctypes.c_short))[:1].pop()
|
rbyte = ctypes.cast(
|
||||||
tmpstr = ctypes.c_char_p(data+nbytes*i+2)
|
data + nbytes * i,
|
||||||
res.append( tmpstr.value.decode()[0:rbyte] )
|
ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:1].pop()
|
||||||
|
tmpstr = ctypes.c_char_p(data + nbytes * i + 2)
|
||||||
|
res.append(tmpstr.value.decode()[0:rbyte])
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
def _crow_nchar_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_nchar_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C nchar row to python row
|
"""Function to convert C nchar row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
res=[]
|
res = []
|
||||||
if num_of_rows >= 0:
|
if num_of_rows >= 0:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
tmpstr = ctypes.c_char_p(data+nbytes*i+2)
|
tmpstr = ctypes.c_char_p(data + nbytes * i + 2)
|
||||||
res.append( tmpstr.value.decode() )
|
res.append(tmpstr.value.decode())
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
else:
|
else:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
res.append( (ctypes.cast(data+nbytes*i+2, ctypes.POINTER(ctypes.c_wchar * (nbytes//4))))[0].value )
|
res.append((ctypes.cast(data + nbytes * i + 2,
|
||||||
|
ctypes.POINTER(ctypes.c_wchar * (nbytes // 4))))[0].value)
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
_CONVERT_FUNC = {
|
_CONVERT_FUNC = {
|
||||||
FieldType.C_BOOL: _crow_bool_to_python,
|
FieldType.C_BOOL: _crow_bool_to_python,
|
||||||
FieldType.C_TINYINT : _crow_tinyint_to_python,
|
FieldType.C_TINYINT: _crow_tinyint_to_python,
|
||||||
FieldType.C_SMALLINT : _crow_smallint_to_python,
|
FieldType.C_SMALLINT: _crow_smallint_to_python,
|
||||||
FieldType.C_INT : _crow_int_to_python,
|
FieldType.C_INT: _crow_int_to_python,
|
||||||
FieldType.C_BIGINT : _crow_bigint_to_python,
|
FieldType.C_BIGINT: _crow_bigint_to_python,
|
||||||
FieldType.C_FLOAT : _crow_float_to_python,
|
FieldType.C_FLOAT: _crow_float_to_python,
|
||||||
FieldType.C_DOUBLE : _crow_double_to_python,
|
FieldType.C_DOUBLE: _crow_double_to_python,
|
||||||
FieldType.C_BINARY: _crow_binary_to_python,
|
FieldType.C_BINARY: _crow_binary_to_python,
|
||||||
FieldType.C_TIMESTAMP : _crow_timestamp_to_python,
|
FieldType.C_TIMESTAMP: _crow_timestamp_to_python,
|
||||||
FieldType.C_NCHAR : _crow_nchar_to_python
|
FieldType.C_NCHAR: _crow_nchar_to_python,
|
||||||
|
FieldType.C_TINYINT_UNSIGNED: _crow_tinyint_unsigned_to_python,
|
||||||
|
FieldType.C_SMALLINT_UNSIGNED: _crow_smallint_unsigned_to_python,
|
||||||
|
FieldType.C_INT_UNSIGNED: _crow_int_unsigned_to_python,
|
||||||
|
FieldType.C_BIGINT_UNSIGNED: _crow_bigint_unsigned_to_python
|
||||||
}
|
}
|
||||||
|
|
||||||
_CONVERT_FUNC_BLOCK = {
|
_CONVERT_FUNC_BLOCK = {
|
||||||
FieldType.C_BOOL: _crow_bool_to_python,
|
FieldType.C_BOOL: _crow_bool_to_python,
|
||||||
FieldType.C_TINYINT : _crow_tinyint_to_python,
|
FieldType.C_TINYINT: _crow_tinyint_to_python,
|
||||||
FieldType.C_SMALLINT : _crow_smallint_to_python,
|
FieldType.C_SMALLINT: _crow_smallint_to_python,
|
||||||
FieldType.C_INT : _crow_int_to_python,
|
FieldType.C_INT: _crow_int_to_python,
|
||||||
FieldType.C_BIGINT : _crow_bigint_to_python,
|
FieldType.C_BIGINT: _crow_bigint_to_python,
|
||||||
FieldType.C_FLOAT : _crow_float_to_python,
|
FieldType.C_FLOAT: _crow_float_to_python,
|
||||||
FieldType.C_DOUBLE : _crow_double_to_python,
|
FieldType.C_DOUBLE: _crow_double_to_python,
|
||||||
FieldType.C_BINARY: _crow_binary_to_python_block,
|
FieldType.C_BINARY: _crow_binary_to_python_block,
|
||||||
FieldType.C_TIMESTAMP : _crow_timestamp_to_python,
|
FieldType.C_TIMESTAMP: _crow_timestamp_to_python,
|
||||||
FieldType.C_NCHAR : _crow_nchar_to_python_block
|
FieldType.C_NCHAR: _crow_nchar_to_python_block,
|
||||||
|
FieldType.C_TINYINT_UNSIGNED: _crow_tinyint_unsigned_to_python,
|
||||||
|
FieldType.C_SMALLINT_UNSIGNED: _crow_smallint_unsigned_to_python,
|
||||||
|
FieldType.C_INT_UNSIGNED: _crow_int_unsigned_to_python,
|
||||||
|
FieldType.C_BIGINT_UNSIGNED: _crow_bigint_unsigned_to_python
|
||||||
}
|
}
|
||||||
|
|
||||||
# Corresponding TAOS_FIELD structure in C
|
# Corresponding TAOS_FIELD structure in C
|
||||||
|
|
||||||
|
|
||||||
class TaosField(ctypes.Structure):
|
class TaosField(ctypes.Structure):
|
||||||
_fields_ = [('name', ctypes.c_char * 65),
|
_fields_ = [('name', ctypes.c_char * 65),
|
||||||
('type', ctypes.c_char),
|
('type', ctypes.c_char),
|
||||||
('bytes', ctypes.c_short)]
|
('bytes', ctypes.c_short)]
|
||||||
|
|
||||||
# C interface class
|
# C interface class
|
||||||
|
|
||||||
|
|
||||||
class CTaosInterface(object):
|
class CTaosInterface(object):
|
||||||
|
|
||||||
libtaos = ctypes.windll.LoadLibrary('taos')
|
libtaos = ctypes.windll.LoadLibrary('taos')
|
||||||
|
@ -216,7 +360,7 @@ class CTaosInterface(object):
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("config is expected as a str")
|
raise AttributeError("config is expected as a str")
|
||||||
|
|
||||||
if config != None:
|
if config is not None:
|
||||||
CTaosInterface.libtaos.taos_options(3, self._config)
|
CTaosInterface.libtaos.taos_options(3, self._config)
|
||||||
|
|
||||||
CTaosInterface.libtaos.taos_init()
|
CTaosInterface.libtaos.taos_init()
|
||||||
|
@ -227,7 +371,13 @@ class CTaosInterface(object):
|
||||||
"""
|
"""
|
||||||
return self._config
|
return self._config
|
||||||
|
|
||||||
def connect(self, host=None, user="root", password="taosdata", db=None, port=0):
|
def connect(
|
||||||
|
self,
|
||||||
|
host=None,
|
||||||
|
user="root",
|
||||||
|
password="taosdata",
|
||||||
|
db=None,
|
||||||
|
port=0):
|
||||||
'''
|
'''
|
||||||
Function to connect to server
|
Function to connect to server
|
||||||
|
|
||||||
|
@ -236,7 +386,7 @@ class CTaosInterface(object):
|
||||||
# host
|
# host
|
||||||
try:
|
try:
|
||||||
_host = ctypes.c_char_p(host.encode(
|
_host = ctypes.c_char_p(host.encode(
|
||||||
"utf-8")) if host != None else ctypes.c_char_p(None)
|
"utf-8")) if host is not None else ctypes.c_char_p(None)
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("host is expected as a str")
|
raise AttributeError("host is expected as a str")
|
||||||
|
|
||||||
|
@ -255,7 +405,7 @@ class CTaosInterface(object):
|
||||||
# db
|
# db
|
||||||
try:
|
try:
|
||||||
_db = ctypes.c_char_p(
|
_db = ctypes.c_char_p(
|
||||||
db.encode("utf-8")) if db != None else ctypes.c_char_p(None)
|
db.encode("utf-8")) if db is not None else ctypes.c_char_p(None)
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("db is expected as a str")
|
raise AttributeError("db is expected as a str")
|
||||||
|
|
||||||
|
@ -268,11 +418,11 @@ class CTaosInterface(object):
|
||||||
connection = ctypes.c_void_p(CTaosInterface.libtaos.taos_connect(
|
connection = ctypes.c_void_p(CTaosInterface.libtaos.taos_connect(
|
||||||
_host, _user, _password, _db, _port))
|
_host, _user, _password, _db, _port))
|
||||||
|
|
||||||
if connection.value == None:
|
if connection.value is None:
|
||||||
print('connect to TDengine failed')
|
print('connect to TDengine failed')
|
||||||
raise ConnectionError("connect to TDengine failed")
|
raise ConnectionError("connect to TDengine failed")
|
||||||
# sys.exit(1)
|
# sys.exit(1)
|
||||||
#else:
|
# else:
|
||||||
# print('connect to TDengine success')
|
# print('connect to TDengine success')
|
||||||
|
|
||||||
return connection
|
return connection
|
||||||
|
@ -293,12 +443,13 @@ class CTaosInterface(object):
|
||||||
@rtype: 0 on success and -1 on failure
|
@rtype: 0 on success and -1 on failure
|
||||||
'''
|
'''
|
||||||
try:
|
try:
|
||||||
return CTaosInterface.libtaos.taos_query(connection, ctypes.c_char_p(sql.encode('utf-8')))
|
return CTaosInterface.libtaos.taos_query(
|
||||||
|
connection, ctypes.c_char_p(sql.encode('utf-8')))
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("sql is expected as a string")
|
raise AttributeError("sql is expected as a string")
|
||||||
# finally:
|
# finally:
|
||||||
# CTaosInterface.libtaos.close(connection)
|
# CTaosInterface.libtaos.close(connection)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def affectedRows(result):
|
def affectedRows(result):
|
||||||
"""The affected rows after runing query
|
"""The affected rows after runing query
|
||||||
|
@ -308,7 +459,7 @@ class CTaosInterface(object):
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def subscribe(connection, restart, topic, sql, interval):
|
def subscribe(connection, restart, topic, sql, interval):
|
||||||
"""Create a subscription
|
"""Create a subscription
|
||||||
@restart boolean,
|
@restart boolean,
|
||||||
@sql string, sql statement for data query, must be a 'select' statement.
|
@sql string, sql statement for data query, must be a 'select' statement.
|
||||||
@topic string, name of this subscription
|
@topic string, name of this subscription
|
||||||
"""
|
"""
|
||||||
|
@ -360,35 +511,49 @@ class CTaosInterface(object):
|
||||||
result, ctypes.byref(pblock))
|
result, ctypes.byref(pblock))
|
||||||
if num_of_rows == 0:
|
if num_of_rows == 0:
|
||||||
return None, 0
|
return None, 0
|
||||||
isMicro = (CTaosInterface.libtaos.taos_result_precision(result) == FieldType.C_TIMESTAMP_MICRO)
|
isMicro = (CTaosInterface.libtaos.taos_result_precision(
|
||||||
|
result) == FieldType.C_TIMESTAMP_MICRO)
|
||||||
blocks = [None] * len(fields)
|
blocks = [None] * len(fields)
|
||||||
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
||||||
fieldLen = [ele for ele in ctypes.cast(fieldL, ctypes.POINTER(ctypes.c_int))[:len(fields)]]
|
fieldLen = [
|
||||||
|
ele for ele in ctypes.cast(
|
||||||
|
fieldL, ctypes.POINTER(
|
||||||
|
ctypes.c_int))[
|
||||||
|
:len(fields)]]
|
||||||
for i in range(len(fields)):
|
for i in range(len(fields)):
|
||||||
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
||||||
if fields[i]['type'] not in _CONVERT_FUNC_BLOCK:
|
if fields[i]['type'] not in _CONVERT_FUNC_BLOCK:
|
||||||
raise DatabaseError("Invalid data type returned from database")
|
raise DatabaseError("Invalid data type returned from database")
|
||||||
blocks[i] = _CONVERT_FUNC_BLOCK[fields[i]['type']](data, num_of_rows, fieldLen[i], isMicro)
|
blocks[i] = _CONVERT_FUNC_BLOCK[fields[i]['type']](
|
||||||
|
data, num_of_rows, fieldLen[i], isMicro)
|
||||||
|
|
||||||
return blocks, abs(num_of_rows)
|
return blocks, abs(num_of_rows)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def fetchRow(result, fields):
|
def fetchRow(result, fields):
|
||||||
pblock = ctypes.c_void_p(0)
|
pblock = ctypes.c_void_p(0)
|
||||||
pblock = CTaosInterface.libtaos.taos_fetch_row(result)
|
pblock = CTaosInterface.libtaos.taos_fetch_row(result)
|
||||||
if pblock :
|
if pblock:
|
||||||
num_of_rows = 1
|
num_of_rows = 1
|
||||||
isMicro = (CTaosInterface.libtaos.taos_result_precision(result) == FieldType.C_TIMESTAMP_MICRO)
|
isMicro = (CTaosInterface.libtaos.taos_result_precision(
|
||||||
|
result) == FieldType.C_TIMESTAMP_MICRO)
|
||||||
blocks = [None] * len(fields)
|
blocks = [None] * len(fields)
|
||||||
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
||||||
fieldLen = [ele for ele in ctypes.cast(fieldL, ctypes.POINTER(ctypes.c_int))[:len(fields)]]
|
fieldLen = [
|
||||||
|
ele for ele in ctypes.cast(
|
||||||
|
fieldL, ctypes.POINTER(
|
||||||
|
ctypes.c_int))[
|
||||||
|
:len(fields)]]
|
||||||
for i in range(len(fields)):
|
for i in range(len(fields)):
|
||||||
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
||||||
if fields[i]['type'] not in _CONVERT_FUNC:
|
if fields[i]['type'] not in _CONVERT_FUNC:
|
||||||
raise DatabaseError("Invalid data type returned from database")
|
raise DatabaseError(
|
||||||
|
"Invalid data type returned from database")
|
||||||
if data is None:
|
if data is None:
|
||||||
blocks[i] = [None]
|
blocks[i] = [None]
|
||||||
else:
|
else:
|
||||||
blocks[i] = _CONVERT_FUNC[fields[i]['type']](data, num_of_rows, fieldLen[i], isMicro)
|
blocks[i] = _CONVERT_FUNC[fields[i]['type']](
|
||||||
|
data, num_of_rows, fieldLen[i], isMicro)
|
||||||
else:
|
else:
|
||||||
return None, 0
|
return None, 0
|
||||||
return blocks, abs(num_of_rows)
|
return blocks, abs(num_of_rows)
|
||||||
|
|
|
@ -2,9 +2,11 @@ from .cursor import TDengineCursor
|
||||||
from .subscription import TDengineSubscription
|
from .subscription import TDengineSubscription
|
||||||
from .cinterface import CTaosInterface
|
from .cinterface import CTaosInterface
|
||||||
|
|
||||||
|
|
||||||
class TDengineConnection(object):
|
class TDengineConnection(object):
|
||||||
""" TDengine connection object
|
""" TDengine connection object
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
self._conn = None
|
self._conn = None
|
||||||
self._host = None
|
self._host = None
|
||||||
|
@ -30,7 +32,7 @@ class TDengineConnection(object):
|
||||||
# password
|
# password
|
||||||
if 'password' in kwargs:
|
if 'password' in kwargs:
|
||||||
self._password = kwargs['password']
|
self._password = kwargs['password']
|
||||||
|
|
||||||
# database
|
# database
|
||||||
if 'database' in kwargs:
|
if 'database' in kwargs:
|
||||||
self._database = kwargs['database']
|
self._database = kwargs['database']
|
||||||
|
@ -44,7 +46,12 @@ class TDengineConnection(object):
|
||||||
self._config = kwargs['config']
|
self._config = kwargs['config']
|
||||||
|
|
||||||
self._chandle = CTaosInterface(self._config)
|
self._chandle = CTaosInterface(self._config)
|
||||||
self._conn = self._chandle.connect(self._host, self._user, self._password, self._database, self._port)
|
self._conn = self._chandle.connect(
|
||||||
|
self._host,
|
||||||
|
self._user,
|
||||||
|
self._password,
|
||||||
|
self._database,
|
||||||
|
self._port)
|
||||||
|
|
||||||
def close(self):
|
def close(self):
|
||||||
"""Close current connection.
|
"""Close current connection.
|
||||||
|
@ -56,7 +63,8 @@ class TDengineConnection(object):
|
||||||
"""
|
"""
|
||||||
if self._conn is None:
|
if self._conn is None:
|
||||||
return None
|
return None
|
||||||
sub = CTaosInterface.subscribe(self._conn, restart, topic, sql, interval)
|
sub = CTaosInterface.subscribe(
|
||||||
|
self._conn, restart, topic, sql, interval)
|
||||||
return TDengineSubscription(sub)
|
return TDengineSubscription(sub)
|
||||||
|
|
||||||
def cursor(self):
|
def cursor(self):
|
||||||
|
@ -81,7 +89,8 @@ class TDengineConnection(object):
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
conn = TDengineConnection(host='192.168.1.107')
|
conn = TDengineConnection(host='192.168.1.107')
|
||||||
conn.close()
|
conn.close()
|
||||||
print("Hello world")
|
print("Hello world")
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
|
|
||||||
from .dbapi import *
|
from .dbapi import *
|
||||||
|
|
||||||
|
|
||||||
class FieldType(object):
|
class FieldType(object):
|
||||||
"""TDengine Field Types
|
"""TDengine Field Types
|
||||||
"""
|
"""
|
||||||
|
@ -18,13 +19,21 @@ class FieldType(object):
|
||||||
C_BINARY = 8
|
C_BINARY = 8
|
||||||
C_TIMESTAMP = 9
|
C_TIMESTAMP = 9
|
||||||
C_NCHAR = 10
|
C_NCHAR = 10
|
||||||
|
C_TINYINT_UNSIGNED = 11
|
||||||
|
C_SMALLINT_UNSIGNED = 12
|
||||||
|
C_INT_UNSIGNED = 13
|
||||||
|
C_BIGINT_UNSIGNED = 14
|
||||||
# NULL value definition
|
# NULL value definition
|
||||||
# NOTE: These values should change according to C definition in tsdb.h
|
# NOTE: These values should change according to C definition in tsdb.h
|
||||||
C_BOOL_NULL = 0x02
|
C_BOOL_NULL = 0x02
|
||||||
C_TINYINT_NULL = -128
|
C_TINYINT_NULL = -128
|
||||||
|
C_TINYINT_UNSIGNED_NULL = 255
|
||||||
C_SMALLINT_NULL = -32768
|
C_SMALLINT_NULL = -32768
|
||||||
|
C_SMALLINT_UNSIGNED_NULL = 65535
|
||||||
C_INT_NULL = -2147483648
|
C_INT_NULL = -2147483648
|
||||||
|
C_INT_UNSIGNED_NULL = 4294967295
|
||||||
C_BIGINT_NULL = -9223372036854775808
|
C_BIGINT_NULL = -9223372036854775808
|
||||||
|
C_BIGINT_UNSIGNED_NULL = 18446744073709551615
|
||||||
C_FLOAT_NULL = float('nan')
|
C_FLOAT_NULL = float('nan')
|
||||||
C_DOUBLE_NULL = float('nan')
|
C_DOUBLE_NULL = float('nan')
|
||||||
C_BINARY_NULL = bytearray([int('0xff', 16)])
|
C_BINARY_NULL = bytearray([int('0xff', 16)])
|
||||||
|
|
|
@ -5,6 +5,7 @@ import threading
|
||||||
|
|
||||||
# querySeqNum = 0
|
# querySeqNum = 0
|
||||||
|
|
||||||
|
|
||||||
class TDengineCursor(object):
|
class TDengineCursor(object):
|
||||||
"""Database cursor which is used to manage the context of a fetch operation.
|
"""Database cursor which is used to manage the context of a fetch operation.
|
||||||
|
|
||||||
|
@ -23,7 +24,7 @@ class TDengineCursor(object):
|
||||||
if the cursor has not had an operation invoked via the .execute*() method yet.
|
if the cursor has not had an operation invoked via the .execute*() method yet.
|
||||||
|
|
||||||
.rowcount:This read-only attribute specifies the number of rows that the last
|
.rowcount:This read-only attribute specifies the number of rows that the last
|
||||||
.execute*() produced (for DQL statements like SELECT) or affected
|
.execute*() produced (for DQL statements like SELECT) or affected
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, connection=None):
|
def __init__(self, connection=None):
|
||||||
|
@ -50,13 +51,14 @@ class TDengineCursor(object):
|
||||||
raise OperationalError("Invalid use of fetch iterator")
|
raise OperationalError("Invalid use of fetch iterator")
|
||||||
|
|
||||||
if self._block_rows <= self._block_iter:
|
if self._block_rows <= self._block_iter:
|
||||||
block, self._block_rows = CTaosInterface.fetchRow(self._result, self._fields)
|
block, self._block_rows = CTaosInterface.fetchRow(
|
||||||
|
self._result, self._fields)
|
||||||
if self._block_rows == 0:
|
if self._block_rows == 0:
|
||||||
raise StopIteration
|
raise StopIteration
|
||||||
self._block = list(map(tuple, zip(*block)))
|
self._block = list(map(tuple, zip(*block)))
|
||||||
self._block_iter = 0
|
self._block_iter = 0
|
||||||
|
|
||||||
data = self._block[self._block_iter]
|
data = self._block[self._block_iter]
|
||||||
self._block_iter += 1
|
self._block_iter += 1
|
||||||
|
|
||||||
return data
|
return data
|
||||||
|
@ -91,7 +93,7 @@ class TDengineCursor(object):
|
||||||
"""
|
"""
|
||||||
if self._connection is None:
|
if self._connection is None:
|
||||||
return False
|
return False
|
||||||
|
|
||||||
self._reset_result()
|
self._reset_result()
|
||||||
self._connection = None
|
self._connection = None
|
||||||
|
|
||||||
|
@ -106,19 +108,20 @@ class TDengineCursor(object):
|
||||||
if not self._connection:
|
if not self._connection:
|
||||||
# TODO : change the exception raised here
|
# TODO : change the exception raised here
|
||||||
raise ProgrammingError("Cursor is not connected")
|
raise ProgrammingError("Cursor is not connected")
|
||||||
|
|
||||||
self._reset_result()
|
self._reset_result()
|
||||||
|
|
||||||
stmt = operation
|
stmt = operation
|
||||||
if params is not None:
|
if params is not None:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
self._result = CTaosInterface.query(self._connection._conn, stmt)
|
self._result = CTaosInterface.query(self._connection._conn, stmt)
|
||||||
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
||||||
if errno == 0:
|
if errno == 0:
|
||||||
if CTaosInterface.fieldsCount(self._result) == 0:
|
if CTaosInterface.fieldsCount(self._result) == 0:
|
||||||
self._affected_rows += CTaosInterface.affectedRows(self._result)
|
self._affected_rows += CTaosInterface.affectedRows(
|
||||||
return CTaosInterface.affectedRows(self._result )
|
self._result)
|
||||||
|
return CTaosInterface.affectedRows(self._result)
|
||||||
else:
|
else:
|
||||||
self._fields = CTaosInterface.useResult(self._result)
|
self._fields = CTaosInterface.useResult(self._result)
|
||||||
return self._handle_result()
|
return self._handle_result()
|
||||||
|
@ -147,17 +150,20 @@ class TDengineCursor(object):
|
||||||
buffer = [[] for i in range(len(self._fields))]
|
buffer = [[] for i in range(len(self._fields))]
|
||||||
self._rowcount = 0
|
self._rowcount = 0
|
||||||
while True:
|
while True:
|
||||||
block, num_of_fields = CTaosInterface.fetchRow(self._result, self._fields)
|
block, num_of_fields = CTaosInterface.fetchRow(
|
||||||
|
self._result, self._fields)
|
||||||
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
||||||
if errno != 0:
|
if errno != 0:
|
||||||
raise ProgrammingError(CTaosInterface.errStr(self._result), errno)
|
raise ProgrammingError(
|
||||||
|
CTaosInterface.errStr(
|
||||||
|
self._result), errno)
|
||||||
if num_of_fields == 0:
|
if num_of_fields == 0:
|
||||||
break
|
break
|
||||||
self._rowcount += num_of_fields
|
self._rowcount += num_of_fields
|
||||||
for i in range(len(self._fields)):
|
for i in range(len(self._fields)):
|
||||||
buffer[i].extend(block[i])
|
buffer[i].extend(block[i])
|
||||||
return list(map(tuple, zip(*buffer)))
|
return list(map(tuple, zip(*buffer)))
|
||||||
|
|
||||||
def fetchall(self):
|
def fetchall(self):
|
||||||
if self._result is None or self._fields is None:
|
if self._result is None or self._fields is None:
|
||||||
raise OperationalError("Invalid use of fetchall")
|
raise OperationalError("Invalid use of fetchall")
|
||||||
|
@ -165,20 +171,21 @@ class TDengineCursor(object):
|
||||||
buffer = [[] for i in range(len(self._fields))]
|
buffer = [[] for i in range(len(self._fields))]
|
||||||
self._rowcount = 0
|
self._rowcount = 0
|
||||||
while True:
|
while True:
|
||||||
block, num_of_fields = CTaosInterface.fetchBlock(self._result, self._fields)
|
block, num_of_fields = CTaosInterface.fetchBlock(
|
||||||
|
self._result, self._fields)
|
||||||
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
||||||
if errno != 0:
|
if errno != 0:
|
||||||
raise ProgrammingError(CTaosInterface.errStr(self._result), errno)
|
raise ProgrammingError(
|
||||||
if num_of_fields == 0: break
|
CTaosInterface.errStr(
|
||||||
|
self._result), errno)
|
||||||
|
if num_of_fields == 0:
|
||||||
|
break
|
||||||
self._rowcount += num_of_fields
|
self._rowcount += num_of_fields
|
||||||
for i in range(len(self._fields)):
|
for i in range(len(self._fields)):
|
||||||
buffer[i].extend(block[i])
|
buffer[i].extend(block[i])
|
||||||
|
|
||||||
|
|
||||||
return list(map(tuple, zip(*buffer)))
|
return list(map(tuple, zip(*buffer)))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def nextset(self):
|
def nextset(self):
|
||||||
"""
|
"""
|
||||||
"""
|
"""
|
||||||
|
@ -209,6 +216,7 @@ class TDengineCursor(object):
|
||||||
"""
|
"""
|
||||||
self._description = []
|
self._description = []
|
||||||
for ele in self._fields:
|
for ele in self._fields:
|
||||||
self._description.append((ele['name'], ele['type'], None, None, None, None, False))
|
self._description.append(
|
||||||
|
(ele['name'], ele['type'], None, None, None, None, False))
|
||||||
|
|
||||||
return self._result
|
return self._result
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
import time
|
import time
|
||||||
import datetime
|
import datetime
|
||||||
|
|
||||||
|
|
||||||
class DBAPITypeObject(object):
|
class DBAPITypeObject(object):
|
||||||
def __init__(self, *values):
|
def __init__(self, *values):
|
||||||
self.values = values
|
self.values = values
|
||||||
|
@ -16,23 +17,28 @@ class DBAPITypeObject(object):
|
||||||
else:
|
else:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
|
|
||||||
Date = datetime.date
|
Date = datetime.date
|
||||||
Time = datetime.time
|
Time = datetime.time
|
||||||
Timestamp = datetime.datetime
|
Timestamp = datetime.datetime
|
||||||
|
|
||||||
|
|
||||||
def DataFromTicks(ticks):
|
def DataFromTicks(ticks):
|
||||||
return Date(*time.localtime(ticks)[:3])
|
return Date(*time.localtime(ticks)[:3])
|
||||||
|
|
||||||
|
|
||||||
def TimeFromTicks(ticks):
|
def TimeFromTicks(ticks):
|
||||||
return Time(*time.localtime(ticks)[3:6])
|
return Time(*time.localtime(ticks)[3:6])
|
||||||
|
|
||||||
|
|
||||||
def TimestampFromTicks(ticks):
|
def TimestampFromTicks(ticks):
|
||||||
return Timestamp(*time.localtime(ticks)[:6])
|
return Timestamp(*time.localtime(ticks)[:6])
|
||||||
|
|
||||||
|
|
||||||
Binary = bytes
|
Binary = bytes
|
||||||
|
|
||||||
# STRING = DBAPITypeObject(*constants.FieldType.get_string_types())
|
# STRING = DBAPITypeObject(*constants.FieldType.get_string_types())
|
||||||
# BINARY = DBAPITypeObject(*constants.FieldType.get_binary_types())
|
# BINARY = DBAPITypeObject(*constants.FieldType.get_binary_types())
|
||||||
# NUMBER = BAPITypeObject(*constants.FieldType.get_number_types())
|
# NUMBER = BAPITypeObject(*constants.FieldType.get_number_types())
|
||||||
# DATETIME = DBAPITypeObject(*constants.FieldType.get_timestamp_types())
|
# DATETIME = DBAPITypeObject(*constants.FieldType.get_timestamp_types())
|
||||||
# ROWID = DBAPITypeObject()
|
# ROWID = DBAPITypeObject()
|
||||||
|
|
|
@ -1,35 +1,41 @@
|
||||||
"""Python exceptions
|
"""Python exceptions
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
||||||
class Error(Exception):
|
class Error(Exception):
|
||||||
def __init__(self, msg=None, errno=None):
|
def __init__(self, msg=None, errno=None):
|
||||||
self.msg = msg
|
self.msg = msg
|
||||||
self._full_msg = self.msg
|
self._full_msg = self.msg
|
||||||
self.errno = errno
|
self.errno = errno
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return self._full_msg
|
return self._full_msg
|
||||||
|
|
||||||
|
|
||||||
class Warning(Exception):
|
class Warning(Exception):
|
||||||
"""Exception raised for important warnings like data truncations while inserting.
|
"""Exception raised for important warnings like data truncations while inserting.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class InterfaceError(Error):
|
class InterfaceError(Error):
|
||||||
"""Exception raised for errors that are related to the database interface rather than the database itself.
|
"""Exception raised for errors that are related to the database interface rather than the database itself.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class DatabaseError(Error):
|
class DatabaseError(Error):
|
||||||
"""Exception raised for errors that are related to the database.
|
"""Exception raised for errors that are related to the database.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class DataError(DatabaseError):
|
class DataError(DatabaseError):
|
||||||
"""Exception raised for errors that are due to problems with the processed data like division by zero, numeric value out of range.
|
"""Exception raised for errors that are due to problems with the processed data like division by zero, numeric value out of range.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class OperationalError(DatabaseError):
|
class OperationalError(DatabaseError):
|
||||||
"""Exception raised for errors that are related to the database's operation and not necessarily under the control of the programmer
|
"""Exception raised for errors that are related to the database's operation and not necessarily under the control of the programmer
|
||||||
"""
|
"""
|
||||||
|
@ -41,17 +47,20 @@ class IntegrityError(DatabaseError):
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class InternalError(DatabaseError):
|
class InternalError(DatabaseError):
|
||||||
"""Exception raised when the database encounters an internal error.
|
"""Exception raised when the database encounters an internal error.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class ProgrammingError(DatabaseError):
|
class ProgrammingError(DatabaseError):
|
||||||
"""Exception raised for programming errors.
|
"""Exception raised for programming errors.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class NotSupportedError(DatabaseError):
|
class NotSupportedError(DatabaseError):
|
||||||
"""Exception raised in case a method or database API was used which is not supported by the database,.
|
"""Exception raised in case a method or database API was used which is not supported by the database,.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
|
@ -1,32 +1,33 @@
|
||||||
from .cinterface import CTaosInterface
|
from .cinterface import CTaosInterface
|
||||||
from .error import *
|
from .error import *
|
||||||
|
|
||||||
|
|
||||||
class TDengineSubscription(object):
|
class TDengineSubscription(object):
|
||||||
"""TDengine subscription object
|
"""TDengine subscription object
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, sub):
|
def __init__(self, sub):
|
||||||
self._sub = sub
|
self._sub = sub
|
||||||
|
|
||||||
|
|
||||||
def consume(self):
|
def consume(self):
|
||||||
"""Consume rows of a subscription
|
"""Consume rows of a subscription
|
||||||
"""
|
"""
|
||||||
if self._sub is None:
|
if self._sub is None:
|
||||||
raise OperationalError("Invalid use of consume")
|
raise OperationalError("Invalid use of consume")
|
||||||
|
|
||||||
result, fields = CTaosInterface.consume(self._sub)
|
result, fields = CTaosInterface.consume(self._sub)
|
||||||
buffer = [[] for i in range(len(fields))]
|
buffer = [[] for i in range(len(fields))]
|
||||||
while True:
|
while True:
|
||||||
block, num_of_fields = CTaosInterface.fetchBlock(result, fields)
|
block, num_of_fields = CTaosInterface.fetchBlock(result, fields)
|
||||||
if num_of_fields == 0: break
|
if num_of_fields == 0:
|
||||||
|
break
|
||||||
for i in range(len(fields)):
|
for i in range(len(fields)):
|
||||||
buffer[i].extend(block[i])
|
buffer[i].extend(block[i])
|
||||||
|
|
||||||
self.fields = fields
|
self.fields = fields
|
||||||
return list(map(tuple, zip(*buffer)))
|
return list(map(tuple, zip(*buffer)))
|
||||||
|
|
||||||
|
def close(self, keepProgress=True):
|
||||||
def close(self, keepProgress = True):
|
|
||||||
"""Close the Subscription.
|
"""Close the Subscription.
|
||||||
"""
|
"""
|
||||||
if self._sub is None:
|
if self._sub is None:
|
||||||
|
@ -38,15 +39,19 @@ class TDengineSubscription(object):
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
from .connection import TDengineConnection
|
from .connection import TDengineConnection
|
||||||
conn = TDengineConnection(host="127.0.0.1", user="root", password="taosdata", database="test")
|
conn = TDengineConnection(
|
||||||
|
host="127.0.0.1",
|
||||||
|
user="root",
|
||||||
|
password="taosdata",
|
||||||
|
database="test")
|
||||||
|
|
||||||
# Generate a cursor object to run SQL commands
|
# Generate a cursor object to run SQL commands
|
||||||
sub = conn.subscribe(True, "test", "select * from meters;", 1000)
|
sub = conn.subscribe(True, "test", "select * from meters;", 1000)
|
||||||
|
|
||||||
for i in range(0,10):
|
for i in range(0, 10):
|
||||||
data = sub.consume()
|
data = sub.consume()
|
||||||
for d in data:
|
for d in data:
|
||||||
print(d)
|
print(d)
|
||||||
|
|
||||||
sub.close()
|
sub.close()
|
||||||
conn.close()
|
conn.close()
|
||||||
|
|
|
@ -8,6 +8,7 @@ paramstyle = 'pyformat'
|
||||||
|
|
||||||
__all__ = ['connection', 'cursor']
|
__all__ = ['connection', 'cursor']
|
||||||
|
|
||||||
|
|
||||||
def connect(*args, **kwargs):
|
def connect(*args, **kwargs):
|
||||||
""" Function to return a TDengine connector object
|
""" Function to return a TDengine connector object
|
||||||
|
|
||||||
|
|
|
@ -4,11 +4,14 @@ from .error import *
|
||||||
import math
|
import math
|
||||||
import datetime
|
import datetime
|
||||||
|
|
||||||
|
|
||||||
def _convert_millisecond_to_datetime(milli):
|
def _convert_millisecond_to_datetime(milli):
|
||||||
return datetime.datetime.fromtimestamp(milli/1000.0)
|
return datetime.datetime.fromtimestamp(milli / 1000.0)
|
||||||
|
|
||||||
|
|
||||||
def _convert_microsecond_to_datetime(micro):
|
def _convert_microsecond_to_datetime(micro):
|
||||||
return datetime.datetime.fromtimestamp(micro/1000000.0)
|
return datetime.datetime.fromtimestamp(micro / 1000000.0)
|
||||||
|
|
||||||
|
|
||||||
def _crow_timestamp_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_timestamp_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C bool row to python row
|
"""Function to convert C bool row to python row
|
||||||
|
@ -18,170 +21,309 @@ def _crow_timestamp_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
_timestamp_converter = _convert_microsecond_to_datetime
|
_timestamp_converter = _convert_microsecond_to_datetime
|
||||||
|
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return list(map(_timestamp_converter, ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)]))
|
return list(map(_timestamp_converter, ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]))
|
||||||
else:
|
else:
|
||||||
return list(map(_timestamp_converter, ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)]))
|
return list(map(_timestamp_converter, ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]))
|
||||||
|
|
||||||
|
|
||||||
def _crow_bool_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_bool_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C bool row to python row
|
"""Function to convert C bool row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)] ]
|
return [
|
||||||
|
None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_byte))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_bool))[:abs(num_of_rows)] ]
|
return [
|
||||||
|
None if ele == FieldType.C_BOOL_NULL else bool(ele) for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_bool))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_tinyint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_tinyint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C tinyint row to python row
|
"""Function to convert C tinyint row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_TINYINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_byte))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_tinyint_unsigned_to_python(
|
||||||
|
data,
|
||||||
|
num_of_rows,
|
||||||
|
nbytes=None,
|
||||||
|
micro=False):
|
||||||
|
"""Function to convert C tinyint row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ubyte))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_TINYINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ubyte))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_smallint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_smallint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C smallint row to python row
|
"""Function to convert C smallint row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_short))[:abs(num_of_rows)]]
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_short))[:abs(num_of_rows)] ]
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_smallint_unsigned_to_python(
|
||||||
|
data, num_of_rows, nbytes=None, micro=False):
|
||||||
|
"""Function to convert C smallint row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ushort))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_SMALLINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ushort))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_int_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_int_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C int row to python row
|
"""Function to convert C int row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_INT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_int))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_int_unsigned_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
|
"""Function to convert C int row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_uint))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_INT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_uint))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_bigint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_bigint_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C bigint row to python row
|
"""Function to convert C bigint row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_longlong))[:abs(num_of_rows)] ]
|
return [None if ele == FieldType.C_BIGINT_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_long))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
|
def _crow_bigint_unsigned_to_python(
|
||||||
|
data,
|
||||||
|
num_of_rows,
|
||||||
|
nbytes=None,
|
||||||
|
micro=False):
|
||||||
|
"""Function to convert C bigint row to python row
|
||||||
|
"""
|
||||||
|
if num_of_rows > 0:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ulong))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
else:
|
||||||
|
return [
|
||||||
|
None if ele == FieldType.C_BIGINT_UNSIGNED_NULL else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(
|
||||||
|
ctypes.c_ulong))[
|
||||||
|
:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_float_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_float_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C float row to python row
|
"""Function to convert C float row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_float))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_double_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_double_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C double row to python row
|
"""Function to convert C double row to python row
|
||||||
"""
|
"""
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if math.isnan(ele) else ele for ele in ctypes.cast(data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)] ]
|
return [None if math.isnan(ele) else ele for ele in ctypes.cast(
|
||||||
|
data, ctypes.POINTER(ctypes.c_double))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_binary_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_binary_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C binary row to python row
|
"""Function to convert C binary row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
return [ None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode('utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
return [None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode(
|
||||||
|
'utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
||||||
else:
|
else:
|
||||||
return [ None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode('utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
return [None if ele.value[0:1] == FieldType.C_BINARY_NULL else ele.value.decode(
|
||||||
|
'utf-8') for ele in (ctypes.cast(data, ctypes.POINTER(ctypes.c_char * nbytes)))[:abs(num_of_rows)]]
|
||||||
|
|
||||||
|
|
||||||
def _crow_nchar_to_python(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_nchar_to_python(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C nchar row to python row
|
"""Function to convert C nchar row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
|
|
||||||
res = []
|
res = []
|
||||||
|
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
if num_of_rows >= 0:
|
if num_of_rows >= 0:
|
||||||
tmpstr = ctypes.c_char_p(data)
|
tmpstr = ctypes.c_char_p(data)
|
||||||
res.append( tmpstr.value.decode() )
|
res.append(tmpstr.value.decode())
|
||||||
else:
|
else:
|
||||||
res.append( (ctypes.cast(data+nbytes*i, ctypes.POINTER(ctypes.c_wchar * (nbytes//4))))[0].value )
|
res.append((ctypes.cast(data + nbytes * i,
|
||||||
|
ctypes.POINTER(ctypes.c_wchar * (nbytes // 4))))[0].value)
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
|
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
def _crow_binary_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_binary_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C binary row to python row
|
"""Function to convert C binary row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
res=[]
|
res = []
|
||||||
if num_of_rows > 0:
|
if num_of_rows > 0:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
rbyte=ctypes.cast(data+nbytes*i,ctypes.POINTER(ctypes.c_short))[:1].pop()
|
rbyte = ctypes.cast(
|
||||||
tmpstr = ctypes.c_char_p(data+nbytes*i+2)
|
data + nbytes * i,
|
||||||
res.append( tmpstr.value.decode()[0:rbyte] )
|
ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:1].pop()
|
||||||
|
tmpstr = ctypes.c_char_p(data + nbytes * i + 2)
|
||||||
|
res.append(tmpstr.value.decode()[0:rbyte])
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
else:
|
else:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
rbyte=ctypes.cast(data+nbytes*i,ctypes.POINTER(ctypes.c_short))[:1].pop()
|
rbyte = ctypes.cast(
|
||||||
tmpstr = ctypes.c_char_p(data+nbytes*i+2)
|
data + nbytes * i,
|
||||||
res.append( tmpstr.value.decode()[0:rbyte] )
|
ctypes.POINTER(
|
||||||
|
ctypes.c_short))[
|
||||||
|
:1].pop()
|
||||||
|
tmpstr = ctypes.c_char_p(data + nbytes * i + 2)
|
||||||
|
res.append(tmpstr.value.decode()[0:rbyte])
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
def _crow_nchar_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
def _crow_nchar_to_python_block(data, num_of_rows, nbytes=None, micro=False):
|
||||||
"""Function to convert C nchar row to python row
|
"""Function to convert C nchar row to python row
|
||||||
"""
|
"""
|
||||||
assert(nbytes is not None)
|
assert(nbytes is not None)
|
||||||
res=[]
|
res = []
|
||||||
if num_of_rows >= 0:
|
if num_of_rows >= 0:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
tmpstr = ctypes.c_char_p(data+nbytes*i+2)
|
tmpstr = ctypes.c_char_p(data + nbytes * i + 2)
|
||||||
res.append( tmpstr.value.decode() )
|
res.append(tmpstr.value.decode())
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
else:
|
else:
|
||||||
for i in range(abs(num_of_rows)):
|
for i in range(abs(num_of_rows)):
|
||||||
try:
|
try:
|
||||||
res.append( (ctypes.cast(data+nbytes*i+2, ctypes.POINTER(ctypes.c_wchar * (nbytes//4))))[0].value )
|
res.append((ctypes.cast(data + nbytes * i + 2,
|
||||||
|
ctypes.POINTER(ctypes.c_wchar * (nbytes // 4))))[0].value)
|
||||||
except ValueError:
|
except ValueError:
|
||||||
res.append(None)
|
res.append(None)
|
||||||
return res
|
return res
|
||||||
|
|
||||||
|
|
||||||
_CONVERT_FUNC = {
|
_CONVERT_FUNC = {
|
||||||
FieldType.C_BOOL: _crow_bool_to_python,
|
FieldType.C_BOOL: _crow_bool_to_python,
|
||||||
FieldType.C_TINYINT : _crow_tinyint_to_python,
|
FieldType.C_TINYINT: _crow_tinyint_to_python,
|
||||||
FieldType.C_SMALLINT : _crow_smallint_to_python,
|
FieldType.C_SMALLINT: _crow_smallint_to_python,
|
||||||
FieldType.C_INT : _crow_int_to_python,
|
FieldType.C_INT: _crow_int_to_python,
|
||||||
FieldType.C_BIGINT : _crow_bigint_to_python,
|
FieldType.C_BIGINT: _crow_bigint_to_python,
|
||||||
FieldType.C_FLOAT : _crow_float_to_python,
|
FieldType.C_FLOAT: _crow_float_to_python,
|
||||||
FieldType.C_DOUBLE : _crow_double_to_python,
|
FieldType.C_DOUBLE: _crow_double_to_python,
|
||||||
FieldType.C_BINARY: _crow_binary_to_python,
|
FieldType.C_BINARY: _crow_binary_to_python,
|
||||||
FieldType.C_TIMESTAMP : _crow_timestamp_to_python,
|
FieldType.C_TIMESTAMP: _crow_timestamp_to_python,
|
||||||
FieldType.C_NCHAR : _crow_nchar_to_python
|
FieldType.C_NCHAR: _crow_nchar_to_python,
|
||||||
|
FieldType.C_TINYINT_UNSIGNED: _crow_tinyint_unsigned_to_python,
|
||||||
|
FieldType.C_SMALLINT_UNSIGNED: _crow_smallint_unsigned_to_python,
|
||||||
|
FieldType.C_INT_UNSIGNED: _crow_int_unsigned_to_python,
|
||||||
|
FieldType.C_BIGINT_UNSIGNED: _crow_bigint_unsigned_to_python
|
||||||
}
|
}
|
||||||
|
|
||||||
_CONVERT_FUNC_BLOCK = {
|
_CONVERT_FUNC_BLOCK = {
|
||||||
FieldType.C_BOOL: _crow_bool_to_python,
|
FieldType.C_BOOL: _crow_bool_to_python,
|
||||||
FieldType.C_TINYINT : _crow_tinyint_to_python,
|
FieldType.C_TINYINT: _crow_tinyint_to_python,
|
||||||
FieldType.C_SMALLINT : _crow_smallint_to_python,
|
FieldType.C_SMALLINT: _crow_smallint_to_python,
|
||||||
FieldType.C_INT : _crow_int_to_python,
|
FieldType.C_INT: _crow_int_to_python,
|
||||||
FieldType.C_BIGINT : _crow_bigint_to_python,
|
FieldType.C_BIGINT: _crow_bigint_to_python,
|
||||||
FieldType.C_FLOAT : _crow_float_to_python,
|
FieldType.C_FLOAT: _crow_float_to_python,
|
||||||
FieldType.C_DOUBLE : _crow_double_to_python,
|
FieldType.C_DOUBLE: _crow_double_to_python,
|
||||||
FieldType.C_BINARY: _crow_binary_to_python_block,
|
FieldType.C_BINARY: _crow_binary_to_python_block,
|
||||||
FieldType.C_TIMESTAMP : _crow_timestamp_to_python,
|
FieldType.C_TIMESTAMP: _crow_timestamp_to_python,
|
||||||
FieldType.C_NCHAR : _crow_nchar_to_python_block
|
FieldType.C_NCHAR: _crow_nchar_to_python_block,
|
||||||
|
FieldType.C_TINYINT_UNSIGNED: _crow_tinyint_unsigned_to_python,
|
||||||
|
FieldType.C_SMALLINT_UNSIGNED: _crow_smallint_unsigned_to_python,
|
||||||
|
FieldType.C_INT_UNSIGNED: _crow_int_unsigned_to_python,
|
||||||
|
FieldType.C_BIGINT_UNSIGNED: _crow_bigint_unsigned_to_python
|
||||||
}
|
}
|
||||||
|
|
||||||
# Corresponding TAOS_FIELD structure in C
|
# Corresponding TAOS_FIELD structure in C
|
||||||
|
|
||||||
|
|
||||||
class TaosField(ctypes.Structure):
|
class TaosField(ctypes.Structure):
|
||||||
_fields_ = [('name', ctypes.c_char * 65),
|
_fields_ = [('name', ctypes.c_char * 65),
|
||||||
('type', ctypes.c_char),
|
('type', ctypes.c_char),
|
||||||
('bytes', ctypes.c_short)]
|
('bytes', ctypes.c_short)]
|
||||||
|
|
||||||
# C interface class
|
# C interface class
|
||||||
|
|
||||||
|
|
||||||
class CTaosInterface(object):
|
class CTaosInterface(object):
|
||||||
|
|
||||||
libtaos = ctypes.windll.LoadLibrary('taos')
|
libtaos = ctypes.windll.LoadLibrary('taos')
|
||||||
|
@ -218,7 +360,7 @@ class CTaosInterface(object):
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("config is expected as a str")
|
raise AttributeError("config is expected as a str")
|
||||||
|
|
||||||
if config != None:
|
if config is not None:
|
||||||
CTaosInterface.libtaos.taos_options(3, self._config)
|
CTaosInterface.libtaos.taos_options(3, self._config)
|
||||||
|
|
||||||
CTaosInterface.libtaos.taos_init()
|
CTaosInterface.libtaos.taos_init()
|
||||||
|
@ -229,7 +371,13 @@ class CTaosInterface(object):
|
||||||
"""
|
"""
|
||||||
return self._config
|
return self._config
|
||||||
|
|
||||||
def connect(self, host=None, user="root", password="taosdata", db=None, port=0):
|
def connect(
|
||||||
|
self,
|
||||||
|
host=None,
|
||||||
|
user="root",
|
||||||
|
password="taosdata",
|
||||||
|
db=None,
|
||||||
|
port=0):
|
||||||
'''
|
'''
|
||||||
Function to connect to server
|
Function to connect to server
|
||||||
|
|
||||||
|
@ -238,7 +386,7 @@ class CTaosInterface(object):
|
||||||
# host
|
# host
|
||||||
try:
|
try:
|
||||||
_host = ctypes.c_char_p(host.encode(
|
_host = ctypes.c_char_p(host.encode(
|
||||||
"utf-8")) if host != None else ctypes.c_char_p(None)
|
"utf-8")) if host is not None else ctypes.c_char_p(None)
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("host is expected as a str")
|
raise AttributeError("host is expected as a str")
|
||||||
|
|
||||||
|
@ -257,7 +405,7 @@ class CTaosInterface(object):
|
||||||
# db
|
# db
|
||||||
try:
|
try:
|
||||||
_db = ctypes.c_char_p(
|
_db = ctypes.c_char_p(
|
||||||
db.encode("utf-8")) if db != None else ctypes.c_char_p(None)
|
db.encode("utf-8")) if db is not None else ctypes.c_char_p(None)
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("db is expected as a str")
|
raise AttributeError("db is expected as a str")
|
||||||
|
|
||||||
|
@ -270,11 +418,11 @@ class CTaosInterface(object):
|
||||||
connection = ctypes.c_void_p(CTaosInterface.libtaos.taos_connect(
|
connection = ctypes.c_void_p(CTaosInterface.libtaos.taos_connect(
|
||||||
_host, _user, _password, _db, _port))
|
_host, _user, _password, _db, _port))
|
||||||
|
|
||||||
if connection.value == None:
|
if connection.value is None:
|
||||||
print('connect to TDengine failed')
|
print('connect to TDengine failed')
|
||||||
raise ConnectionError("connect to TDengine failed")
|
raise ConnectionError("connect to TDengine failed")
|
||||||
# sys.exit(1)
|
# sys.exit(1)
|
||||||
#else:
|
# else:
|
||||||
# print('connect to TDengine success')
|
# print('connect to TDengine success')
|
||||||
|
|
||||||
return connection
|
return connection
|
||||||
|
@ -295,7 +443,8 @@ class CTaosInterface(object):
|
||||||
@rtype: 0 on success and -1 on failure
|
@rtype: 0 on success and -1 on failure
|
||||||
'''
|
'''
|
||||||
try:
|
try:
|
||||||
return CTaosInterface.libtaos.taos_query(connection, ctypes.c_char_p(sql.encode('utf-8')))
|
return CTaosInterface.libtaos.taos_query(
|
||||||
|
connection, ctypes.c_char_p(sql.encode('utf-8')))
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
raise AttributeError("sql is expected as a string")
|
raise AttributeError("sql is expected as a string")
|
||||||
# finally:
|
# finally:
|
||||||
|
@ -310,7 +459,7 @@ class CTaosInterface(object):
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def subscribe(connection, restart, topic, sql, interval):
|
def subscribe(connection, restart, topic, sql, interval):
|
||||||
"""Create a subscription
|
"""Create a subscription
|
||||||
@restart boolean,
|
@restart boolean,
|
||||||
@sql string, sql statement for data query, must be a 'select' statement.
|
@sql string, sql statement for data query, must be a 'select' statement.
|
||||||
@topic string, name of this subscription
|
@topic string, name of this subscription
|
||||||
"""
|
"""
|
||||||
|
@ -362,35 +511,49 @@ class CTaosInterface(object):
|
||||||
result, ctypes.byref(pblock))
|
result, ctypes.byref(pblock))
|
||||||
if num_of_rows == 0:
|
if num_of_rows == 0:
|
||||||
return None, 0
|
return None, 0
|
||||||
isMicro = (CTaosInterface.libtaos.taos_result_precision(result) == FieldType.C_TIMESTAMP_MICRO)
|
isMicro = (CTaosInterface.libtaos.taos_result_precision(
|
||||||
|
result) == FieldType.C_TIMESTAMP_MICRO)
|
||||||
blocks = [None] * len(fields)
|
blocks = [None] * len(fields)
|
||||||
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
||||||
fieldLen = [ele for ele in ctypes.cast(fieldL, ctypes.POINTER(ctypes.c_int))[:len(fields)]]
|
fieldLen = [
|
||||||
|
ele for ele in ctypes.cast(
|
||||||
|
fieldL, ctypes.POINTER(
|
||||||
|
ctypes.c_int))[
|
||||||
|
:len(fields)]]
|
||||||
for i in range(len(fields)):
|
for i in range(len(fields)):
|
||||||
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
||||||
if fields[i]['type'] not in _CONVERT_FUNC_BLOCK:
|
if fields[i]['type'] not in _CONVERT_FUNC_BLOCK:
|
||||||
raise DatabaseError("Invalid data type returned from database")
|
raise DatabaseError("Invalid data type returned from database")
|
||||||
blocks[i] = _CONVERT_FUNC_BLOCK[fields[i]['type']](data, num_of_rows, fieldLen[i], isMicro)
|
blocks[i] = _CONVERT_FUNC_BLOCK[fields[i]['type']](
|
||||||
|
data, num_of_rows, fieldLen[i], isMicro)
|
||||||
|
|
||||||
return blocks, abs(num_of_rows)
|
return blocks, abs(num_of_rows)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def fetchRow(result, fields):
|
def fetchRow(result, fields):
|
||||||
pblock = ctypes.c_void_p(0)
|
pblock = ctypes.c_void_p(0)
|
||||||
pblock = CTaosInterface.libtaos.taos_fetch_row(result)
|
pblock = CTaosInterface.libtaos.taos_fetch_row(result)
|
||||||
if pblock :
|
if pblock:
|
||||||
num_of_rows = 1
|
num_of_rows = 1
|
||||||
isMicro = (CTaosInterface.libtaos.taos_result_precision(result) == FieldType.C_TIMESTAMP_MICRO)
|
isMicro = (CTaosInterface.libtaos.taos_result_precision(
|
||||||
|
result) == FieldType.C_TIMESTAMP_MICRO)
|
||||||
blocks = [None] * len(fields)
|
blocks = [None] * len(fields)
|
||||||
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
fieldL = CTaosInterface.libtaos.taos_fetch_lengths(result)
|
||||||
fieldLen = [ele for ele in ctypes.cast(fieldL, ctypes.POINTER(ctypes.c_int))[:len(fields)]]
|
fieldLen = [
|
||||||
|
ele for ele in ctypes.cast(
|
||||||
|
fieldL, ctypes.POINTER(
|
||||||
|
ctypes.c_int))[
|
||||||
|
:len(fields)]]
|
||||||
for i in range(len(fields)):
|
for i in range(len(fields)):
|
||||||
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
data = ctypes.cast(pblock, ctypes.POINTER(ctypes.c_void_p))[i]
|
||||||
if fields[i]['type'] not in _CONVERT_FUNC:
|
if fields[i]['type'] not in _CONVERT_FUNC:
|
||||||
raise DatabaseError("Invalid data type returned from database")
|
raise DatabaseError(
|
||||||
|
"Invalid data type returned from database")
|
||||||
if data is None:
|
if data is None:
|
||||||
blocks[i] = [None]
|
blocks[i] = [None]
|
||||||
else:
|
else:
|
||||||
blocks[i] = _CONVERT_FUNC[fields[i]['type']](data, num_of_rows, fieldLen[i], isMicro)
|
blocks[i] = _CONVERT_FUNC[fields[i]['type']](
|
||||||
|
data, num_of_rows, fieldLen[i], isMicro)
|
||||||
else:
|
else:
|
||||||
return None, 0
|
return None, 0
|
||||||
return blocks, abs(num_of_rows)
|
return blocks, abs(num_of_rows)
|
||||||
|
@ -476,4 +639,4 @@ if __name__ == '__main__':
|
||||||
print(data)
|
print(data)
|
||||||
|
|
||||||
cinter.freeResult(result)
|
cinter.freeResult(result)
|
||||||
cinter.close(conn)
|
cinter.close(conn)
|
||||||
|
|
|
@ -2,9 +2,11 @@ from .cursor import TDengineCursor
|
||||||
from .subscription import TDengineSubscription
|
from .subscription import TDengineSubscription
|
||||||
from .cinterface import CTaosInterface
|
from .cinterface import CTaosInterface
|
||||||
|
|
||||||
|
|
||||||
class TDengineConnection(object):
|
class TDengineConnection(object):
|
||||||
""" TDengine connection object
|
""" TDengine connection object
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
self._conn = None
|
self._conn = None
|
||||||
self._host = None
|
self._host = None
|
||||||
|
@ -30,7 +32,7 @@ class TDengineConnection(object):
|
||||||
# password
|
# password
|
||||||
if 'password' in kwargs:
|
if 'password' in kwargs:
|
||||||
self._password = kwargs['password']
|
self._password = kwargs['password']
|
||||||
|
|
||||||
# database
|
# database
|
||||||
if 'database' in kwargs:
|
if 'database' in kwargs:
|
||||||
self._database = kwargs['database']
|
self._database = kwargs['database']
|
||||||
|
@ -44,7 +46,12 @@ class TDengineConnection(object):
|
||||||
self._config = kwargs['config']
|
self._config = kwargs['config']
|
||||||
|
|
||||||
self._chandle = CTaosInterface(self._config)
|
self._chandle = CTaosInterface(self._config)
|
||||||
self._conn = self._chandle.connect(self._host, self._user, self._password, self._database, self._port)
|
self._conn = self._chandle.connect(
|
||||||
|
self._host,
|
||||||
|
self._user,
|
||||||
|
self._password,
|
||||||
|
self._database,
|
||||||
|
self._port)
|
||||||
|
|
||||||
def close(self):
|
def close(self):
|
||||||
"""Close current connection.
|
"""Close current connection.
|
||||||
|
@ -56,7 +63,8 @@ class TDengineConnection(object):
|
||||||
"""
|
"""
|
||||||
if self._conn is None:
|
if self._conn is None:
|
||||||
return None
|
return None
|
||||||
sub = CTaosInterface.subscribe(self._conn, restart, topic, sql, interval)
|
sub = CTaosInterface.subscribe(
|
||||||
|
self._conn, restart, topic, sql, interval)
|
||||||
return TDengineSubscription(sub)
|
return TDengineSubscription(sub)
|
||||||
|
|
||||||
def cursor(self):
|
def cursor(self):
|
||||||
|
@ -81,7 +89,8 @@ class TDengineConnection(object):
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
conn = TDengineConnection(host='192.168.1.107')
|
conn = TDengineConnection(host='192.168.1.107')
|
||||||
conn.close()
|
conn.close()
|
||||||
print("Hello world")
|
print("Hello world")
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
|
|
||||||
from .dbapi import *
|
from .dbapi import *
|
||||||
|
|
||||||
|
|
||||||
class FieldType(object):
|
class FieldType(object):
|
||||||
"""TDengine Field Types
|
"""TDengine Field Types
|
||||||
"""
|
"""
|
||||||
|
@ -18,13 +19,21 @@ class FieldType(object):
|
||||||
C_BINARY = 8
|
C_BINARY = 8
|
||||||
C_TIMESTAMP = 9
|
C_TIMESTAMP = 9
|
||||||
C_NCHAR = 10
|
C_NCHAR = 10
|
||||||
|
C_TINYINT_UNSIGNED = 11
|
||||||
|
C_SMALLINT_UNSIGNED = 12
|
||||||
|
C_INT_UNSIGNED = 13
|
||||||
|
C_BIGINT_UNSIGNED = 14
|
||||||
# NULL value definition
|
# NULL value definition
|
||||||
# NOTE: These values should change according to C definition in tsdb.h
|
# NOTE: These values should change according to C definition in tsdb.h
|
||||||
C_BOOL_NULL = 0x02
|
C_BOOL_NULL = 0x02
|
||||||
C_TINYINT_NULL = -128
|
C_TINYINT_NULL = -128
|
||||||
|
C_TINYINT_UNSIGNED_NULL = 255
|
||||||
C_SMALLINT_NULL = -32768
|
C_SMALLINT_NULL = -32768
|
||||||
|
C_SMALLINT_UNSIGNED_NULL = 65535
|
||||||
C_INT_NULL = -2147483648
|
C_INT_NULL = -2147483648
|
||||||
|
C_INT_UNSIGNED_NULL = 4294967295
|
||||||
C_BIGINT_NULL = -9223372036854775808
|
C_BIGINT_NULL = -9223372036854775808
|
||||||
|
C_BIGINT_UNSIGNED_NULL = 18446744073709551615
|
||||||
C_FLOAT_NULL = float('nan')
|
C_FLOAT_NULL = float('nan')
|
||||||
C_DOUBLE_NULL = float('nan')
|
C_DOUBLE_NULL = float('nan')
|
||||||
C_BINARY_NULL = bytearray([int('0xff', 16)])
|
C_BINARY_NULL = bytearray([int('0xff', 16)])
|
||||||
|
|
|
@ -24,7 +24,7 @@ class TDengineCursor(object):
|
||||||
if the cursor has not had an operation invoked via the .execute*() method yet.
|
if the cursor has not had an operation invoked via the .execute*() method yet.
|
||||||
|
|
||||||
.rowcount:This read-only attribute specifies the number of rows that the last
|
.rowcount:This read-only attribute specifies the number of rows that the last
|
||||||
.execute*() produced (for DQL statements like SELECT) or affected
|
.execute*() produced (for DQL statements like SELECT) or affected
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, connection=None):
|
def __init__(self, connection=None):
|
||||||
|
@ -51,13 +51,14 @@ class TDengineCursor(object):
|
||||||
raise OperationalError("Invalid use of fetch iterator")
|
raise OperationalError("Invalid use of fetch iterator")
|
||||||
|
|
||||||
if self._block_rows <= self._block_iter:
|
if self._block_rows <= self._block_iter:
|
||||||
block, self._block_rows = CTaosInterface.fetchRow(self._result, self._fields)
|
block, self._block_rows = CTaosInterface.fetchRow(
|
||||||
|
self._result, self._fields)
|
||||||
if self._block_rows == 0:
|
if self._block_rows == 0:
|
||||||
raise StopIteration
|
raise StopIteration
|
||||||
self._block = list(map(tuple, zip(*block)))
|
self._block = list(map(tuple, zip(*block)))
|
||||||
self._block_iter = 0
|
self._block_iter = 0
|
||||||
|
|
||||||
data = self._block[self._block_iter]
|
data = self._block[self._block_iter]
|
||||||
self._block_iter += 1
|
self._block_iter += 1
|
||||||
|
|
||||||
return data
|
return data
|
||||||
|
@ -92,7 +93,7 @@ class TDengineCursor(object):
|
||||||
"""
|
"""
|
||||||
if self._connection is None:
|
if self._connection is None:
|
||||||
return False
|
return False
|
||||||
|
|
||||||
self._reset_result()
|
self._reset_result()
|
||||||
self._connection = None
|
self._connection = None
|
||||||
|
|
||||||
|
@ -107,24 +108,25 @@ class TDengineCursor(object):
|
||||||
if not self._connection:
|
if not self._connection:
|
||||||
# TODO : change the exception raised here
|
# TODO : change the exception raised here
|
||||||
raise ProgrammingError("Cursor is not connected")
|
raise ProgrammingError("Cursor is not connected")
|
||||||
|
|
||||||
self._reset_result()
|
self._reset_result()
|
||||||
|
|
||||||
stmt = operation
|
stmt = operation
|
||||||
if params is not None:
|
if params is not None:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
self._result = CTaosInterface.query(self._connection._conn, stmt)
|
self._result = CTaosInterface.query(self._connection._conn, stmt)
|
||||||
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
||||||
if errno == 0:
|
if errno == 0:
|
||||||
if CTaosInterface.fieldsCount(self._result) == 0:
|
if CTaosInterface.fieldsCount(self._result) == 0:
|
||||||
self._affected_rows += CTaosInterface.affectedRows(self._result )
|
self._affected_rows += CTaosInterface.affectedRows(
|
||||||
return CTaosInterface.affectedRows(self._result )
|
self._result)
|
||||||
|
return CTaosInterface.affectedRows(self._result)
|
||||||
else:
|
else:
|
||||||
self._fields = CTaosInterface.useResult(self._result )
|
self._fields = CTaosInterface.useResult(self._result)
|
||||||
return self._handle_result()
|
return self._handle_result()
|
||||||
else:
|
else:
|
||||||
raise ProgrammingError(CTaosInterface.errStr(self._result ), errno)
|
raise ProgrammingError(CTaosInterface.errStr(self._result), errno)
|
||||||
|
|
||||||
def executemany(self, operation, seq_of_parameters):
|
def executemany(self, operation, seq_of_parameters):
|
||||||
"""Prepare a database operation (query or command) and then execute it against all parameter sequences or mappings found in the sequence seq_of_parameters.
|
"""Prepare a database operation (query or command) and then execute it against all parameter sequences or mappings found in the sequence seq_of_parameters.
|
||||||
|
@ -148,10 +150,13 @@ class TDengineCursor(object):
|
||||||
buffer = [[] for i in range(len(self._fields))]
|
buffer = [[] for i in range(len(self._fields))]
|
||||||
self._rowcount = 0
|
self._rowcount = 0
|
||||||
while True:
|
while True:
|
||||||
block, num_of_fields = CTaosInterface.fetchRow(self._result, self._fields)
|
block, num_of_fields = CTaosInterface.fetchRow(
|
||||||
|
self._result, self._fields)
|
||||||
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
||||||
if errno != 0:
|
if errno != 0:
|
||||||
raise ProgrammingError(CTaosInterface.errStr(self._result), errno)
|
raise ProgrammingError(
|
||||||
|
CTaosInterface.errStr(
|
||||||
|
self._result), errno)
|
||||||
if num_of_fields == 0:
|
if num_of_fields == 0:
|
||||||
break
|
break
|
||||||
self._rowcount += num_of_fields
|
self._rowcount += num_of_fields
|
||||||
|
@ -166,20 +171,21 @@ class TDengineCursor(object):
|
||||||
buffer = [[] for i in range(len(self._fields))]
|
buffer = [[] for i in range(len(self._fields))]
|
||||||
self._rowcount = 0
|
self._rowcount = 0
|
||||||
while True:
|
while True:
|
||||||
block, num_of_fields = CTaosInterface.fetchBlock(self._result, self._fields)
|
block, num_of_fields = CTaosInterface.fetchBlock(
|
||||||
|
self._result, self._fields)
|
||||||
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
errno = CTaosInterface.libtaos.taos_errno(self._result)
|
||||||
if errno != 0:
|
if errno != 0:
|
||||||
raise ProgrammingError(CTaosInterface.errStr(self._result), errno)
|
raise ProgrammingError(
|
||||||
if num_of_fields == 0: break
|
CTaosInterface.errStr(
|
||||||
|
self._result), errno)
|
||||||
|
if num_of_fields == 0:
|
||||||
|
break
|
||||||
self._rowcount += num_of_fields
|
self._rowcount += num_of_fields
|
||||||
for i in range(len(self._fields)):
|
for i in range(len(self._fields)):
|
||||||
buffer[i].extend(block[i])
|
buffer[i].extend(block[i])
|
||||||
|
|
||||||
|
|
||||||
return list(map(tuple, zip(*buffer)))
|
return list(map(tuple, zip(*buffer)))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def nextset(self):
|
def nextset(self):
|
||||||
"""
|
"""
|
||||||
"""
|
"""
|
||||||
|
@ -204,12 +210,13 @@ class TDengineCursor(object):
|
||||||
self._block_rows = -1
|
self._block_rows = -1
|
||||||
self._block_iter = 0
|
self._block_iter = 0
|
||||||
self._affected_rows = 0
|
self._affected_rows = 0
|
||||||
|
|
||||||
def _handle_result(self):
|
def _handle_result(self):
|
||||||
"""Handle the return result from query.
|
"""Handle the return result from query.
|
||||||
"""
|
"""
|
||||||
self._description = []
|
self._description = []
|
||||||
for ele in self._fields:
|
for ele in self._fields:
|
||||||
self._description.append((ele['name'], ele['type'], None, None, None, None, False))
|
self._description.append(
|
||||||
|
(ele['name'], ele['type'], None, None, None, None, False))
|
||||||
|
|
||||||
return self._result
|
return self._result
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
import time
|
import time
|
||||||
import datetime
|
import datetime
|
||||||
|
|
||||||
|
|
||||||
class DBAPITypeObject(object):
|
class DBAPITypeObject(object):
|
||||||
def __init__(self, *values):
|
def __init__(self, *values):
|
||||||
self.values = values
|
self.values = values
|
||||||
|
@ -16,23 +17,28 @@ class DBAPITypeObject(object):
|
||||||
else:
|
else:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
|
|
||||||
Date = datetime.date
|
Date = datetime.date
|
||||||
Time = datetime.time
|
Time = datetime.time
|
||||||
Timestamp = datetime.datetime
|
Timestamp = datetime.datetime
|
||||||
|
|
||||||
|
|
||||||
def DataFromTicks(ticks):
|
def DataFromTicks(ticks):
|
||||||
return Date(*time.localtime(ticks)[:3])
|
return Date(*time.localtime(ticks)[:3])
|
||||||
|
|
||||||
|
|
||||||
def TimeFromTicks(ticks):
|
def TimeFromTicks(ticks):
|
||||||
return Time(*time.localtime(ticks)[3:6])
|
return Time(*time.localtime(ticks)[3:6])
|
||||||
|
|
||||||
|
|
||||||
def TimestampFromTicks(ticks):
|
def TimestampFromTicks(ticks):
|
||||||
return Timestamp(*time.localtime(ticks)[:6])
|
return Timestamp(*time.localtime(ticks)[:6])
|
||||||
|
|
||||||
|
|
||||||
Binary = bytes
|
Binary = bytes
|
||||||
|
|
||||||
# STRING = DBAPITypeObject(*constants.FieldType.get_string_types())
|
# STRING = DBAPITypeObject(*constants.FieldType.get_string_types())
|
||||||
# BINARY = DBAPITypeObject(*constants.FieldType.get_binary_types())
|
# BINARY = DBAPITypeObject(*constants.FieldType.get_binary_types())
|
||||||
# NUMBER = BAPITypeObject(*constants.FieldType.get_number_types())
|
# NUMBER = BAPITypeObject(*constants.FieldType.get_number_types())
|
||||||
# DATETIME = DBAPITypeObject(*constants.FieldType.get_timestamp_types())
|
# DATETIME = DBAPITypeObject(*constants.FieldType.get_timestamp_types())
|
||||||
# ROWID = DBAPITypeObject()
|
# ROWID = DBAPITypeObject()
|
||||||
|
|
|
@ -1,35 +1,41 @@
|
||||||
"""Python exceptions
|
"""Python exceptions
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
||||||
class Error(Exception):
|
class Error(Exception):
|
||||||
def __init__(self, msg=None, errno=None):
|
def __init__(self, msg=None, errno=None):
|
||||||
self.msg = msg
|
self.msg = msg
|
||||||
self._full_msg = self.msg
|
self._full_msg = self.msg
|
||||||
self.errno = errno
|
self.errno = errno
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return self._full_msg
|
return self._full_msg
|
||||||
|
|
||||||
|
|
||||||
class Warning(Exception):
|
class Warning(Exception):
|
||||||
"""Exception raised for important warnings like data truncations while inserting.
|
"""Exception raised for important warnings like data truncations while inserting.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class InterfaceError(Error):
|
class InterfaceError(Error):
|
||||||
"""Exception raised for errors that are related to the database interface rather than the database itself.
|
"""Exception raised for errors that are related to the database interface rather than the database itself.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class DatabaseError(Error):
|
class DatabaseError(Error):
|
||||||
"""Exception raised for errors that are related to the database.
|
"""Exception raised for errors that are related to the database.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class DataError(DatabaseError):
|
class DataError(DatabaseError):
|
||||||
"""Exception raised for errors that are due to problems with the processed data like division by zero, numeric value out of range.
|
"""Exception raised for errors that are due to problems with the processed data like division by zero, numeric value out of range.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class OperationalError(DatabaseError):
|
class OperationalError(DatabaseError):
|
||||||
"""Exception raised for errors that are related to the database's operation and not necessarily under the control of the programmer
|
"""Exception raised for errors that are related to the database's operation and not necessarily under the control of the programmer
|
||||||
"""
|
"""
|
||||||
|
@ -41,17 +47,20 @@ class IntegrityError(DatabaseError):
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class InternalError(DatabaseError):
|
class InternalError(DatabaseError):
|
||||||
"""Exception raised when the database encounters an internal error.
|
"""Exception raised when the database encounters an internal error.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class ProgrammingError(DatabaseError):
|
class ProgrammingError(DatabaseError):
|
||||||
"""Exception raised for programming errors.
|
"""Exception raised for programming errors.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class NotSupportedError(DatabaseError):
|
class NotSupportedError(DatabaseError):
|
||||||
"""Exception raised in case a method or database API was used which is not supported by the database,.
|
"""Exception raised in case a method or database API was used which is not supported by the database,.
|
||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
|
@ -1,32 +1,33 @@
|
||||||
from .cinterface import CTaosInterface
|
from .cinterface import CTaosInterface
|
||||||
from .error import *
|
from .error import *
|
||||||
|
|
||||||
|
|
||||||
class TDengineSubscription(object):
|
class TDengineSubscription(object):
|
||||||
"""TDengine subscription object
|
"""TDengine subscription object
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, sub):
|
def __init__(self, sub):
|
||||||
self._sub = sub
|
self._sub = sub
|
||||||
|
|
||||||
|
|
||||||
def consume(self):
|
def consume(self):
|
||||||
"""Consume rows of a subscription
|
"""Consume rows of a subscription
|
||||||
"""
|
"""
|
||||||
if self._sub is None:
|
if self._sub is None:
|
||||||
raise OperationalError("Invalid use of consume")
|
raise OperationalError("Invalid use of consume")
|
||||||
|
|
||||||
result, fields = CTaosInterface.consume(self._sub)
|
result, fields = CTaosInterface.consume(self._sub)
|
||||||
buffer = [[] for i in range(len(fields))]
|
buffer = [[] for i in range(len(fields))]
|
||||||
while True:
|
while True:
|
||||||
block, num_of_fields = CTaosInterface.fetchBlock(result, fields)
|
block, num_of_fields = CTaosInterface.fetchBlock(result, fields)
|
||||||
if num_of_fields == 0: break
|
if num_of_fields == 0:
|
||||||
|
break
|
||||||
for i in range(len(fields)):
|
for i in range(len(fields)):
|
||||||
buffer[i].extend(block[i])
|
buffer[i].extend(block[i])
|
||||||
|
|
||||||
self.fields = fields
|
self.fields = fields
|
||||||
return list(map(tuple, zip(*buffer)))
|
return list(map(tuple, zip(*buffer)))
|
||||||
|
|
||||||
|
def close(self, keepProgress=True):
|
||||||
def close(self, keepProgress = True):
|
|
||||||
"""Close the Subscription.
|
"""Close the Subscription.
|
||||||
"""
|
"""
|
||||||
if self._sub is None:
|
if self._sub is None:
|
||||||
|
@ -38,15 +39,19 @@ class TDengineSubscription(object):
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
from .connection import TDengineConnection
|
from .connection import TDengineConnection
|
||||||
conn = TDengineConnection(host="127.0.0.1", user="root", password="taosdata", database="test")
|
conn = TDengineConnection(
|
||||||
|
host="127.0.0.1",
|
||||||
|
user="root",
|
||||||
|
password="taosdata",
|
||||||
|
database="test")
|
||||||
|
|
||||||
# Generate a cursor object to run SQL commands
|
# Generate a cursor object to run SQL commands
|
||||||
sub = conn.subscribe(True, "test", "select * from meters;", 1000)
|
sub = conn.subscribe(True, "test", "select * from meters;", 1000)
|
||||||
|
|
||||||
for i in range(0,10):
|
for i in range(0, 10):
|
||||||
data = sub.consume()
|
data = sub.consume()
|
||||||
for d in data:
|
for d in data:
|
||||||
print(d)
|
print(d)
|
||||||
|
|
||||||
sub.close()
|
sub.close()
|
||||||
conn.close()
|
conn.close()
|
||||||
|
|
|
@ -155,6 +155,7 @@ void httpReleaseContext(HttpContext *pContext, bool clearRes) {
|
||||||
|
|
||||||
if (clearRes) {
|
if (clearRes) {
|
||||||
httpClearParser(pContext->parser);
|
httpClearParser(pContext->parser);
|
||||||
|
memset(&pContext->singleCmd, 0, sizeof(HttpSqlCmd));
|
||||||
}
|
}
|
||||||
|
|
||||||
HttpContext **ppContext = pContext->ppContext;
|
HttpContext **ppContext = pContext->ppContext;
|
||||||
|
@ -185,9 +186,9 @@ void httpCloseContextByApp(HttpContext *pContext) {
|
||||||
pContext->parsed = false;
|
pContext->parsed = false;
|
||||||
bool keepAlive = true;
|
bool keepAlive = true;
|
||||||
|
|
||||||
if (parser->httpVersion == HTTP_VERSION_10 && parser->keepAlive != HTTP_KEEPALIVE_ENABLE) {
|
if (parser && parser->httpVersion == HTTP_VERSION_10 && parser->keepAlive != HTTP_KEEPALIVE_ENABLE) {
|
||||||
keepAlive = false;
|
keepAlive = false;
|
||||||
} else if (parser->httpVersion != HTTP_VERSION_10 && parser->keepAlive == HTTP_KEEPALIVE_DISABLE) {
|
} else if (parser && parser->httpVersion != HTTP_VERSION_10 && parser->keepAlive == HTTP_KEEPALIVE_DISABLE) {
|
||||||
keepAlive = false;
|
keepAlive = false;
|
||||||
} else {
|
} else {
|
||||||
}
|
}
|
||||||
|
|
|
@ -229,7 +229,7 @@ static int32_t httpOnParseHeaderField(HttpParser *parser, const char *key, const
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
else if (strncasecmp(key, "Connection: ", 12) == 0) {
|
else if (strncasecmp(key, "Connection", 10) == 0) {
|
||||||
if (strncasecmp(val, "Keep-Alive", 10) == 0) {
|
if (strncasecmp(val, "Keep-Alive", 10) == 0) {
|
||||||
parser->keepAlive = HTTP_KEEPALIVE_ENABLE;
|
parser->keepAlive = HTTP_KEEPALIVE_ENABLE;
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -67,7 +67,7 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.taosdata.jdbc</groupId>
|
<groupId>com.taosdata.jdbc</groupId>
|
||||||
<artifactId>taos-jdbcdriver</artifactId>
|
<artifactId>taos-jdbcdriver</artifactId>
|
||||||
<version>2.0.18</version>
|
<version>2.0.19</version>
|
||||||
<!-- <scope>system</scope>-->
|
<!-- <scope>system</scope>-->
|
||||||
<!-- <systemPath>${project.basedir}/src/main/resources/lib/taos-jdbcdriver-2.0.15-dist.jar</systemPath>-->
|
<!-- <systemPath>${project.basedir}/src/main/resources/lib/taos-jdbcdriver-2.0.15-dist.jar</systemPath>-->
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
|
@ -4,6 +4,7 @@ import com.taosdata.taosdemo.components.DataSourceFactory;
|
||||||
import com.taosdata.taosdemo.components.JdbcTaosdemoConfig;
|
import com.taosdata.taosdemo.components.JdbcTaosdemoConfig;
|
||||||
import com.taosdata.taosdemo.domain.SuperTableMeta;
|
import com.taosdata.taosdemo.domain.SuperTableMeta;
|
||||||
import com.taosdata.taosdemo.service.DatabaseService;
|
import com.taosdata.taosdemo.service.DatabaseService;
|
||||||
|
import com.taosdata.taosdemo.service.QueryService;
|
||||||
import com.taosdata.taosdemo.service.SubTableService;
|
import com.taosdata.taosdemo.service.SubTableService;
|
||||||
import com.taosdata.taosdemo.service.SuperTableService;
|
import com.taosdata.taosdemo.service.SuperTableService;
|
||||||
import com.taosdata.taosdemo.service.data.SuperTableMetaGenerator;
|
import com.taosdata.taosdemo.service.data.SuperTableMetaGenerator;
|
||||||
|
@ -34,6 +35,7 @@ public class TaosDemoApplication {
|
||||||
final DatabaseService databaseService = new DatabaseService(dataSource);
|
final DatabaseService databaseService = new DatabaseService(dataSource);
|
||||||
final SuperTableService superTableService = new SuperTableService(dataSource);
|
final SuperTableService superTableService = new SuperTableService(dataSource);
|
||||||
final SubTableService subTableService = new SubTableService(dataSource);
|
final SubTableService subTableService = new SubTableService(dataSource);
|
||||||
|
final QueryService queryService = new QueryService(dataSource);
|
||||||
// 创建数据库
|
// 创建数据库
|
||||||
long start = System.currentTimeMillis();
|
long start = System.currentTimeMillis();
|
||||||
Map<String, String> databaseParam = new HashMap<>();
|
Map<String, String> databaseParam = new HashMap<>();
|
||||||
|
@ -90,6 +92,11 @@ public class TaosDemoApplication {
|
||||||
int affectedRows = subTableService.insertMultiThreads(superTableMeta, threadSize, tableSize, startTime, gap, config);
|
int affectedRows = subTableService.insertMultiThreads(superTableMeta, threadSize, tableSize, startTime, gap, config);
|
||||||
end = System.currentTimeMillis();
|
end = System.currentTimeMillis();
|
||||||
logger.info("insert " + affectedRows + " rows, time cost: " + (end - start) + " ms");
|
logger.info("insert " + affectedRows + " rows, time cost: " + (end - start) + " ms");
|
||||||
|
/**********************************************************************************/
|
||||||
|
// 查询
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**********************************************************************************/
|
/**********************************************************************************/
|
||||||
// 删除表
|
// 删除表
|
||||||
if (config.dropTable) {
|
if (config.dropTable) {
|
||||||
|
|
|
@ -23,7 +23,6 @@ public class DataSourceFactory {
|
||||||
properties.load(is);
|
properties.load(is);
|
||||||
|
|
||||||
HikariConfig config = new HikariConfig();
|
HikariConfig config = new HikariConfig();
|
||||||
|
|
||||||
if (properties.containsKey("jdbc.driver")) {
|
if (properties.containsKey("jdbc.driver")) {
|
||||||
// String driverName = properties.getProperty("jdbc.driver");
|
// String driverName = properties.getProperty("jdbc.driver");
|
||||||
// System.out.println(">>> load driver : " + driverName);
|
// System.out.println(">>> load driver : " + driverName);
|
||||||
|
|
|
@ -0,0 +1,104 @@
|
||||||
|
package com.taosdata.taosdemo.service;
|
||||||
|
|
||||||
|
import com.taosdata.jdbc.utils.SqlSyntaxValidator;
|
||||||
|
|
||||||
|
import javax.sql.DataSource;
|
||||||
|
import java.sql.*;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
import java.util.stream.IntStream;
|
||||||
|
|
||||||
|
public class QueryService {
|
||||||
|
|
||||||
|
private final DataSource dataSource;
|
||||||
|
|
||||||
|
public QueryService(DataSource dataSource) {
|
||||||
|
this.dataSource = dataSource;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* only select or show SQL Statement is valid for executeQuery */
|
||||||
|
public Boolean[] areValidQueries(String[] sqls) {
|
||||||
|
Boolean[] ret = new Boolean[sqls.length];
|
||||||
|
for (int i = 0; i < sqls.length; i++) {
|
||||||
|
ret[i] = true;
|
||||||
|
if (!SqlSyntaxValidator.isValidForExecuteQuery(sqls[i])) {
|
||||||
|
ret[i] = false;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
try (Connection conn = dataSource.getConnection(); Statement stmt = conn.createStatement()) {
|
||||||
|
stmt.executeQuery(sqls[i]);
|
||||||
|
} catch (SQLException e) {
|
||||||
|
ret[i] = false;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String[] generateSuperTableQueries(String dbName) {
|
||||||
|
List<String> sqls = new ArrayList<>();
|
||||||
|
try (Connection conn = dataSource.getConnection(); Statement stmt = conn.createStatement()) {
|
||||||
|
stmt.execute("use " + dbName);
|
||||||
|
ResultSet rs = stmt.executeQuery("show stables");
|
||||||
|
while (rs.next()) {
|
||||||
|
String name = rs.getString("name");
|
||||||
|
sqls.add("select count(*) from " + dbName + "." + name);
|
||||||
|
sqls.add("select first(*) from " + dbName + "." + name);
|
||||||
|
sqls.add("select last(*) from " + dbName + "." + name);
|
||||||
|
sqls.add("select last_row(*) from " + dbName + "." + name);
|
||||||
|
}
|
||||||
|
} catch (SQLException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
String[] sqlArr = new String[sqls.size()];
|
||||||
|
return sqls.toArray(sqlArr);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void querySuperTable(String[] sqls, int interval, int threadCount, long queryTimes) {
|
||||||
|
List<Thread> threads = IntStream.range(0, threadCount).mapToObj(i -> new Thread(() -> {
|
||||||
|
// do query
|
||||||
|
try (Connection conn = dataSource.getConnection(); Statement stmt = conn.createStatement()) {
|
||||||
|
long count = queryTimes;
|
||||||
|
if (count == 0)
|
||||||
|
count = Long.MAX_VALUE;
|
||||||
|
while (count > 0) {
|
||||||
|
for (String sql : sqls) {
|
||||||
|
long start = System.currentTimeMillis();
|
||||||
|
ResultSet rs = stmt.executeQuery(sql);
|
||||||
|
printResultSet(rs);
|
||||||
|
long end = System.currentTimeMillis();
|
||||||
|
long timecost = end - start;
|
||||||
|
if (interval - timecost > 0) {
|
||||||
|
TimeUnit.MILLISECONDS.sleep(interval - timecost);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
count--;
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (SQLException | InterruptedException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
})).collect(Collectors.toList());
|
||||||
|
threads.stream().forEach(Thread::start);
|
||||||
|
for (Thread thread : threads) {
|
||||||
|
try {
|
||||||
|
thread.join();
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void printResultSet(ResultSet rs) throws SQLException {
|
||||||
|
ResultSetMetaData meta = rs.getMetaData();
|
||||||
|
while (rs.next()) {
|
||||||
|
for (int i = 1; i <= meta.getColumnCount(); i++) {
|
||||||
|
System.out.print(meta.getColumnLabel(i) + ": " + rs.getString(i) + "\t");
|
||||||
|
}
|
||||||
|
System.out.println();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,7 +2,6 @@ package com.taosdata.taosdemo.service;
|
||||||
|
|
||||||
import com.taosdata.taosdemo.dao.TableMapper;
|
import com.taosdata.taosdemo.dao.TableMapper;
|
||||||
import com.taosdata.taosdemo.domain.TableMeta;
|
import com.taosdata.taosdemo.domain.TableMeta;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
|
@ -7,10 +7,10 @@
|
||||||
"password": "taosdata",
|
"password": "taosdata",
|
||||||
"databases": "db01",
|
"databases": "db01",
|
||||||
"super_table_query":
|
"super_table_query":
|
||||||
{"rate":1, "concurrent":1,
|
{"rate":1, "concurrent":1,"time":10000,
|
||||||
"sqls": [{"sql": "select count(*) from stb01", "result": "./query_res0.txt"}]
|
"sqls": [{"sql": "select count(*) from stb01", "result": "./query_res0.txt"}]
|
||||||
},
|
},
|
||||||
"sub_table_query":
|
"sub_table_query":
|
||||||
{"stblname": "stb01", "rate":1, "threads":1,
|
{"stblname": "stb01", "rate":1, "threads":1,
|
||||||
"sqls": [{"sql": "select count(*) from xxxx", "result": "./query_res1.txt"}]
|
"sqls": [{"sql": "select count(*) from xxxx", "result": "./query_res1.txt"}]
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,41 @@
|
||||||
|
package com.taosdata.taosdemo.service;
|
||||||
|
|
||||||
|
import com.zaxxer.hikari.HikariConfig;
|
||||||
|
import com.zaxxer.hikari.HikariDataSource;
|
||||||
|
import org.junit.BeforeClass;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
public class QueryServiceTest {
|
||||||
|
private static QueryService queryService;
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void areValidQueries() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void generateSuperTableQueries() {
|
||||||
|
String[] sqls = queryService.generateSuperTableQueries("restful_test");
|
||||||
|
for (String sql : sqls) {
|
||||||
|
System.out.println(sql);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void querySuperTable() {
|
||||||
|
String[] sqls = queryService.generateSuperTableQueries("restful_test");
|
||||||
|
queryService.querySuperTable(sqls, 1000, 10, 10);
|
||||||
|
}
|
||||||
|
|
||||||
|
@BeforeClass
|
||||||
|
public static void beforeClass() throws ClassNotFoundException {
|
||||||
|
Class.forName("com.taosdata.jdbc.TSDBDriver");
|
||||||
|
HikariConfig config = new HikariConfig();
|
||||||
|
config.setJdbcUrl("jdbc:TAOS://127.0.0.1:6030/?charset=UTF-8&locale=en_US.UTF-8&timezone=UTC-8");
|
||||||
|
config.setUsername("root");
|
||||||
|
config.setPassword("taosdata");
|
||||||
|
HikariDataSource dataSource = new HikariDataSource(config);
|
||||||
|
queryService = new QueryService(dataSource);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -56,9 +56,9 @@ function runGeneralCaseOneByOne {
|
||||||
case=`echo $line | grep sim$ |awk '{print $NF}'`
|
case=`echo $line | grep sim$ |awk '{print $NF}'`
|
||||||
|
|
||||||
if [ -n "$case" ]; then
|
if [ -n "$case" ]; then
|
||||||
./test.sh -f $case > /dev/null 2>&1 && \
|
date +%F\ %T | tee -a $TDENGINE_COVERAGE_REPORT && ./test.sh -f $case > /dev/null 2>&1 && \
|
||||||
echo -e "${GREEN}$case success${NC}" | tee -a $TDENGINE_COVERAGE_REPORT || \
|
( grep -q 'script.*success.*m$' ../../sim/tsim/log/taoslog0.0 && echo -e "${GREEN}$case success${NC}" | tee -a $TDENGINE_COVERAGE_REPORT ) \
|
||||||
echo -e "${RED}$case failed${NC}" | tee -a $TDENGINE_COVERAGE_REPORT
|
|| echo -e "${RED}$case failed${NC}" | tee -a $TDENGINE_COVERAGE_REPORT
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
done < $1
|
done < $1
|
||||||
|
|
|
@ -64,7 +64,7 @@ function runQueryPerfTest {
|
||||||
[ -f $PERFORMANCE_TEST_REPORT ] && rm $PERFORMANCE_TEST_REPORT
|
[ -f $PERFORMANCE_TEST_REPORT ] && rm $PERFORMANCE_TEST_REPORT
|
||||||
nohup $WORK_DIR/TDengine/debug/build/bin/taosd -c /etc/taosperf/ > /dev/null 2>&1 &
|
nohup $WORK_DIR/TDengine/debug/build/bin/taosd -c /etc/taosperf/ > /dev/null 2>&1 &
|
||||||
echoInfo "Wait TDengine to start"
|
echoInfo "Wait TDengine to start"
|
||||||
sleep 60
|
sleep 120
|
||||||
echoInfo "Run Performance Test"
|
echoInfo "Run Performance Test"
|
||||||
cd $WORK_DIR/TDengine/tests/pytest
|
cd $WORK_DIR/TDengine/tests/pytest
|
||||||
|
|
||||||
|
@ -72,7 +72,7 @@ function runQueryPerfTest {
|
||||||
|
|
||||||
python3 insert/insertFromCSVPerformance.py -c $LOCAL_COMMIT | tee -a $PERFORMANCE_TEST_REPORT
|
python3 insert/insertFromCSVPerformance.py -c $LOCAL_COMMIT | tee -a $PERFORMANCE_TEST_REPORT
|
||||||
|
|
||||||
yes | taosdemo -c /etc/taosperf/ -d taosdemo_insert_test -t 1000 -n 1000 > taosdemoperf.txt
|
yes | taosdemo -c /etc/taosperf/ -d taosdemo_insert_test -x > taosdemoperf.txt
|
||||||
|
|
||||||
CREATETABLETIME=`grep 'Spent' taosdemoperf.txt | awk 'NR==1{print $2}'`
|
CREATETABLETIME=`grep 'Spent' taosdemoperf.txt | awk 'NR==1{print $2}'`
|
||||||
INSERTRECORDSTIME=`grep 'Spent' taosdemoperf.txt | awk 'NR==2{print $2}'`
|
INSERTRECORDSTIME=`grep 'Spent' taosdemoperf.txt | awk 'NR==2{print $2}'`
|
||||||
|
|
|
@ -26,7 +26,7 @@ class TDTestCase:
|
||||||
tdSql.prepare()
|
tdSql.prepare()
|
||||||
|
|
||||||
ret = tdSql.execute(
|
ret = tdSql.execute(
|
||||||
'create table tb (ts timestamp, speed bigint unsigned)')
|
'create table tb (ts timestamp, speed tinyint unsigned)')
|
||||||
|
|
||||||
insertRows = 10
|
insertRows = 10
|
||||||
tdLog.info("insert %d rows" % (insertRows))
|
tdLog.info("insert %d rows" % (insertRows))
|
||||||
|
@ -38,11 +38,11 @@ class TDTestCase:
|
||||||
tdLog.info("insert earlier data")
|
tdLog.info("insert earlier data")
|
||||||
tdSql.execute('insert into tb values (now - 5m , NULL)')
|
tdSql.execute('insert into tb values (now - 5m , NULL)')
|
||||||
tdSql.execute('insert into tb values (now - 6m , 10)')
|
tdSql.execute('insert into tb values (now - 6m , 10)')
|
||||||
tdSql.execute('insert into tb values (now - 7m , 10)')
|
tdSql.execute('insert into tb values (now - 7m , NULL)')
|
||||||
tdSql.execute('insert into tb values (now - 8m , 18446744073709551614)')
|
tdSql.execute('insert into tb values (now - 8m , 254)')
|
||||||
|
|
||||||
tdSql.error('insert into tb values (now - 9m, -1)')
|
tdSql.error('insert into tb values (now - 9m, -1)')
|
||||||
#tdSql.error('insert into tb values (now - 9m, 4294967295)')
|
tdSql.error('insert into tb values (now - 9m, 255)')
|
||||||
|
|
||||||
tdSql.query("select * from tb")
|
tdSql.query("select * from tb")
|
||||||
tdSql.checkRows(insertRows + 4)
|
tdSql.checkRows(insertRows + 4)
|
||||||
|
|
|
@ -41,7 +41,23 @@ class TDTestCase:
|
||||||
tdSql.query("select * from ampere")
|
tdSql.query("select * from ampere")
|
||||||
tdSql.checkRows(2)
|
tdSql.checkRows(2)
|
||||||
tdSql.checkData(0, 6, None)
|
tdSql.checkData(0, 6, None)
|
||||||
tdSql.checkData(1, 6, 'test')
|
tdSql.checkData(1, 6, 'test')
|
||||||
|
|
||||||
|
# Test case for: https://jira.taosdata.com:18080/browse/TD-2423
|
||||||
|
tdSql.execute("create table stb(ts timestamp, col1 int, col2 nchar(20)) tags(tg1 int, tg2 binary(20), tg3 nchar(25))")
|
||||||
|
tdSql.execute("insert into tb1 using stb(tg1, tg3) tags(1, 'test1') values(now, 1, 'test1')")
|
||||||
|
tdSql.query("select *, tg1, tg2, tg3 from tb1")
|
||||||
|
tdSql.checkRows(1)
|
||||||
|
tdSql.checkData(0, 3, 1)
|
||||||
|
tdSql.checkData(0, 4, None)
|
||||||
|
tdSql.checkData(0, 5, 'test1')
|
||||||
|
|
||||||
|
tdSql.execute("create table tb2 using stb(tg3, tg2) tags('test3', 'test2')")
|
||||||
|
tdSql.query("select tg1, tg2, tg3 from tb2")
|
||||||
|
tdSql.checkRows(1)
|
||||||
|
tdSql.checkData(0, 0, None)
|
||||||
|
tdSql.checkData(0, 1, 'test2')
|
||||||
|
tdSql.checkData(0, 2, 'test3')
|
||||||
|
|
||||||
def stop(self):
|
def stop(self):
|
||||||
tdSql.close()
|
tdSql.close()
|
||||||
|
|
|
@ -21,8 +21,8 @@ function runSimCaseOneByOne {
|
||||||
if [[ $line =~ ^./test.sh* ]] || [[ $line =~ ^run* ]]; then
|
if [[ $line =~ ^./test.sh* ]] || [[ $line =~ ^run* ]]; then
|
||||||
case=`echo $line | grep sim$ |awk '{print $NF}'`
|
case=`echo $line | grep sim$ |awk '{print $NF}'`
|
||||||
IN_TDINTERNAL="community"
|
IN_TDINTERNAL="community"
|
||||||
start_time=`date +%s`
|
start_time=`date +%s`
|
||||||
IN_TDINTERNAL="community"
|
date +%F\ %T | tee -a out.log
|
||||||
if [[ "$tests_dir" == *"$IN_TDINTERNAL"* ]]; then
|
if [[ "$tests_dir" == *"$IN_TDINTERNAL"* ]]; then
|
||||||
echo -n $case
|
echo -n $case
|
||||||
./test.sh -f $case > /dev/null 2>&1 && \
|
./test.sh -f $case > /dev/null 2>&1 && \
|
||||||
|
@ -53,6 +53,7 @@ function runSimCaseOneByOnefq {
|
||||||
|
|
||||||
start_time=`date +%s`
|
start_time=`date +%s`
|
||||||
IN_TDINTERNAL="community"
|
IN_TDINTERNAL="community"
|
||||||
|
date +%F\ %T | tee -a out.log
|
||||||
if [[ "$tests_dir" == *"$IN_TDINTERNAL"* ]]; then
|
if [[ "$tests_dir" == *"$IN_TDINTERNAL"* ]]; then
|
||||||
echo -n $case
|
echo -n $case
|
||||||
./test.sh -f $case > /dev/null 2>&1 && \
|
./test.sh -f $case > /dev/null 2>&1 && \
|
||||||
|
@ -94,6 +95,7 @@ function runPyCaseOneByOne {
|
||||||
case=`echo $line|awk '{print $NF}'`
|
case=`echo $line|awk '{print $NF}'`
|
||||||
fi
|
fi
|
||||||
start_time=`date +%s`
|
start_time=`date +%s`
|
||||||
|
date +%F\ %T | tee -a pytest-out.log
|
||||||
echo -n $case
|
echo -n $case
|
||||||
$line > /dev/null 2>&1 && \
|
$line > /dev/null 2>&1 && \
|
||||||
echo -e "${GREEN} success${NC}" | tee -a pytest-out.log || \
|
echo -e "${GREEN} success${NC}" | tee -a pytest-out.log || \
|
||||||
|
@ -122,6 +124,7 @@ function runPyCaseOneByOnefq {
|
||||||
case=`echo $line|awk '{print $NF}'`
|
case=`echo $line|awk '{print $NF}'`
|
||||||
fi
|
fi
|
||||||
start_time=`date +%s`
|
start_time=`date +%s`
|
||||||
|
date +%F\ %T | tee -a pytest-out.log
|
||||||
echo -n $case
|
echo -n $case
|
||||||
$line > /dev/null 2>&1 && \
|
$line > /dev/null 2>&1 && \
|
||||||
echo -e "${GREEN} success${NC}" | tee -a pytest-out.log || \
|
echo -e "${GREEN} success${NC}" | tee -a pytest-out.log || \
|
||||||
|
|
Loading…
Reference in New Issue