diff --git a/Jenkinsfile2 b/Jenkinsfile2
index 9c28489a39..916437b914 100644
--- a/Jenkinsfile2
+++ b/Jenkinsfile2
@@ -387,7 +387,7 @@ pipeline {
}
steps {
catchError(buildResult: 'FAILURE', stageResult: 'FAILURE') {
- timeout(time: 75, unit: 'MINUTES'){
+ timeout(time: 126, unit: 'MINUTES'){
pre_test_win()
pre_test_build_win()
run_win_ctest()
@@ -423,7 +423,7 @@ pipeline {
echo "${WKDIR}/restore.sh -p ${BRANCH_NAME} -n ${BUILD_ID} -c {container name}"
}
catchError(buildResult: 'FAILURE', stageResult: 'FAILURE') {
- timeout(time: 120, unit: 'MINUTES'){
+ timeout(time: 130, unit: 'MINUTES'){
pre_test()
script {
sh '''
diff --git a/cmake/cmake.version b/cmake/cmake.version
index a30618157b..d0d455c73d 100644
--- a/cmake/cmake.version
+++ b/cmake/cmake.version
@@ -2,7 +2,7 @@
IF (DEFINED VERNUMBER)
SET(TD_VER_NUMBER ${VERNUMBER})
ELSE ()
- SET(TD_VER_NUMBER "3.0.2.5")
+ SET(TD_VER_NUMBER "3.0.2.6")
ENDIF ()
IF (DEFINED VERCOMPATIBLE)
diff --git a/cmake/taosadapter_CMakeLists.txt.in b/cmake/taosadapter_CMakeLists.txt.in
index 8df50af03c..a0e50a02d3 100644
--- a/cmake/taosadapter_CMakeLists.txt.in
+++ b/cmake/taosadapter_CMakeLists.txt.in
@@ -2,7 +2,7 @@
# taosadapter
ExternalProject_Add(taosadapter
GIT_REPOSITORY https://github.com/taosdata/taosadapter.git
- GIT_TAG db6c843
+ GIT_TAG 9cfe416
SOURCE_DIR "${TD_SOURCE_DIR}/tools/taosadapter"
BINARY_DIR ""
#BUILD_IN_SOURCE TRUE
diff --git a/cmake/taostools_CMakeLists.txt.in b/cmake/taostools_CMakeLists.txt.in
index ae3b626f88..db2ae92f6e 100644
--- a/cmake/taostools_CMakeLists.txt.in
+++ b/cmake/taostools_CMakeLists.txt.in
@@ -2,7 +2,7 @@
# taos-tools
ExternalProject_Add(taos-tools
GIT_REPOSITORY https://github.com/taosdata/taos-tools.git
- GIT_TAG 61cbfd2
+ GIT_TAG 1e15545
SOURCE_DIR "${TD_SOURCE_DIR}/tools/taos-tools"
BINARY_DIR ""
#BUILD_IN_SOURCE TRUE
diff --git a/docs/en/07-develop/07-tmq.mdx b/docs/en/07-develop/07-tmq.mdx
index 92db7d4cbf..20bc718fc0 100644
--- a/docs/en/07-develop/07-tmq.mdx
+++ b/docs/en/07-develop/07-tmq.mdx
@@ -7,6 +7,7 @@ title: Data Subscription
import Tabs from "@theme/Tabs";
import TabItem from "@theme/TabItem";
import Java from "./_sub_java.mdx";
+import JavaWS from "./_sub_java_ws.mdx"
import Python from "./_sub_python.mdx";
import Go from "./_sub_go.mdx";
import Rust from "./_sub_rust.mdx";
@@ -222,7 +223,7 @@ A database including one supertable and two subtables is created as follows:
```sql
DROP DATABASE IF EXISTS tmqdb;
CREATE DATABASE tmqdb;
-CREATE TABLE tmqdb.stb (ts TIMESTAMP, c1 INT, c2 FLOAT, c3 VARCHAR(16) TAGS(t1 INT, t3 VARCHAR(16));
+CREATE TABLE tmqdb.stb (ts TIMESTAMP, c1 INT, c2 FLOAT, c3 VARCHAR(16)) TAGS(t1 INT, t3 VARCHAR(16));
CREATE TABLE tmqdb.ctb0 USING tmqdb.stb TAGS(0, "subtable0");
CREATE TABLE tmqdb.ctb1 USING tmqdb.stb TAGS(1, "subtable1");
INSERT INTO tmqdb.ctb0 VALUES(now, 0, 0, 'a0')(now+1s, 0, 0, 'a00');
@@ -807,7 +808,14 @@ The following section shows sample code in various languages.
-
+
+
+
+
+
+
+
+
diff --git a/docs/en/07-develop/_sub_java.mdx b/docs/en/07-develop/_sub_java.mdx
index d14b5fd609..c0e9e6c937 100644
--- a/docs/en/07-develop/_sub_java.mdx
+++ b/docs/en/07-develop/_sub_java.mdx
@@ -1,11 +1,9 @@
```java
{{#include docs/examples/java/src/main/java/com/taos/example/SubscribeDemo.java}}
-{{#include docs/examples/java/src/main/java/com/taos/example/MetersDeserializer.java}}
-{{#include docs/examples/java/src/main/java/com/taos/example/Meters.java}}
```
```java
{{#include docs/examples/java/src/main/java/com/taos/example/MetersDeserializer.java}}
```
```java
{{#include docs/examples/java/src/main/java/com/taos/example/Meters.java}}
-```
\ No newline at end of file
+```
diff --git a/docs/en/07-develop/_sub_java_ws.mdx b/docs/en/07-develop/_sub_java_ws.mdx
new file mode 100644
index 0000000000..2a48713358
--- /dev/null
+++ b/docs/en/07-develop/_sub_java_ws.mdx
@@ -0,0 +1,9 @@
+```java
+{{#include docs/examples/java/src/main/java/com/taos/example/WebsocketSubscribeDemo.java}}
+```
+```java
+{{#include docs/examples/java/src/main/java/com/taos/example/MetersDeserializer.java}}
+```
+```java
+{{#include docs/examples/java/src/main/java/com/taos/example/Meters.java}}
+```
diff --git a/docs/en/12-taos-sql/10-function.md b/docs/en/12-taos-sql/10-function.md
index 2eb4bba309..b32d2af5bb 100644
--- a/docs/en/12-taos-sql/10-function.md
+++ b/docs/en/12-taos-sql/10-function.md
@@ -796,19 +796,23 @@ HISTOGRAM(expr,bin_type, bin_description, normalized)
### PERCENTILE
```sql
-PERCENTILE(expr, p)
+PERCENTILE(expr, p [, p1] ...)
```
**Description**: The value whose rank in a specific column matches the specified percentage. If such a value matching the specified percentage doesn't exist in the column, an interpolation value will be returned.
-**Return value type**: DOUBLE
+**Return value type**: This function takes 2 minumum and 11 maximum parameters, and it can simultaneously return 10 percentiles at most. If 2 parameters are given, a single percentile is returned and the value type is DOUBLE.
+ If more than 2 parameters are given, the return value type is a VARCHAR string, the format of which is a JSON ARRAY containing all return values.
**Applicable column types**: Numeric
**Applicable table types**: table only
-**More explanations**: _p_ is in range [0,100], when _p_ is 0, the result is same as using function MIN; when _p_ is 100, the result is same as function MAX.
+**More explanations**:
+- _p_ is in range [0,100], when _p_ is 0, the result is same as using function MIN; when _p_ is 100, the result is same as function MAX.
+- When calculating multiple percentiles of a specific column, a single PERCENTILE function with multiple parameters is adviced, as this can largely reduce the query response time.
+ For example, using SELECT percentile(col, 90, 95, 99) FROM table will perform better than SELECT percentile(col, 90), percentile(col, 95), percentile(col, 99) from table.
## Selection Functions
diff --git a/docs/en/14-reference/03-connector/04-java.mdx b/docs/en/14-reference/03-connector/04-java.mdx
index 61ce166069..36992da636 100644
--- a/docs/en/14-reference/03-connector/04-java.mdx
+++ b/docs/en/14-reference/03-connector/04-java.mdx
@@ -696,6 +696,9 @@ TaosConsumer consumer = new TaosConsumer<>(config);
- enable.auto.commit: Specifies whether to commit automatically.
- group.id: consumer: Specifies the group that the consumer is in.
- value.deserializer: To deserialize the results, you can inherit `com.taosdata.jdbc.tmq.ReferenceDeserializer` and specify the result set bean. You can also inherit `com.taosdata.jdbc.tmq.Deserializer` and perform custom deserialization based on the SQL result set.
+- td.connect.type: Specifies the type connect with TDengine, `jni` or `WebSocket`. default is `jni`
+- httpConnectTimeout:WebSocket connection timeout in milliseconds, the default value is 5000 ms. It only takes effect when using WebSocket type.
+- messageWaitTimeout:socket timeout in milliseconds, the default value is 10000 ms. It only takes effect when using WebSocket type.
- For more information, see [Consumer Parameters](../../../develop/tmq).
#### Subscribe to consume data
@@ -724,6 +727,11 @@ For more information, see [Data Subscription](../../../develop/tmq).
### Usage examples
+
+
+
+In addition to the native connection, the Java Connector also supports subscribing via websocket.
+
```java
public abstract class ConsumerLoop {
private final TaosConsumer consumer;
@@ -795,6 +803,87 @@ public abstract class ConsumerLoop {
}
```
+
+
+
+```java
+public abstract class ConsumerLoop {
+ private final TaosConsumer consumer;
+ private final List topics;
+ private final AtomicBoolean shutdown;
+ private final CountDownLatch shutdownLatch;
+
+ public ConsumerLoop() throws SQLException {
+ Properties config = new Properties();
+ config.setProperty("bootstrap.servers", "localhost:6041");
+ config.setProperty("td.connect.type", "ws");
+ config.setProperty("msg.with.table.name", "true");
+ config.setProperty("enable.auto.commit", "true");
+ config.setProperty("group.id", "group2");
+ config.setProperty("value.deserializer", "com.taosdata.jdbc.tmq.ConsumerTest.ConsumerLoop$ResultDeserializer");
+
+ this.consumer = new TaosConsumer<>(config);
+ this.topics = Collections.singletonList("topic_speed");
+ this.shutdown = new AtomicBoolean(false);
+ this.shutdownLatch = new CountDownLatch(1);
+ }
+
+ public abstract void process(ResultBean result);
+
+ public void pollData() throws SQLException {
+ try {
+ consumer.subscribe(topics);
+
+ while (!shutdown.get()) {
+ ConsumerRecords records = consumer.poll(Duration.ofMillis(100));
+ for (ResultBean record : records) {
+ process(record);
+ }
+ }
+ consumer.unsubscribe();
+ } finally {
+ consumer.close();
+ shutdownLatch.countDown();
+ }
+ }
+
+ public void shutdown() throws InterruptedException {
+ shutdown.set(true);
+ shutdownLatch.await();
+ }
+
+ public static class ResultDeserializer extends ReferenceDeserializer {
+
+ }
+
+ public static class ResultBean {
+ private Timestamp ts;
+ private int speed;
+
+ public Timestamp getTs() {
+ return ts;
+ }
+
+ public void setTs(Timestamp ts) {
+ this.ts = ts;
+ }
+
+ public int getSpeed() {
+ return speed;
+ }
+
+ public void setSpeed(int speed) {
+ this.speed = speed;
+ }
+ }
+}
+```
+
+
+
+
+> **Note**: The value of value.deserializer should be adjusted based on the package path of the test environment.
+
### Use with connection pool
#### HikariCP
@@ -878,8 +967,8 @@ The source code of the sample application is under `TDengine/examples/JDBC`:
| taos-jdbcdriver version | major changes |
| :---------------------: | :--------------------------------------------: |
-| 3.0.3 | fix timestamp resolution error for REST connection in jdk17+ version |
-| 3.0.1 - 3.0.2 | fix the resultSet data is parsed incorrectly sometimes. 3.0.1 is compiled on JDK 11, you are advised to use 3.0.2 in the JDK 8 environment |
+| 3.1.0 | JDBC REST connection supports subscription over WebSocket |
+| 3.0.1 - 3.0.4 | fix the resultSet data is parsed incorrectly sometimes. 3.0.1 is compiled on JDK 11, you are advised to use other version in the JDK 8 environment |
| 3.0.0 | Support for TDengine 3.0 |
| 2.0.42 | fix wasNull interface return value in WebSocket connection |
| 2.0.41 | fix decode method of username and password in REST connection |
diff --git a/docs/en/14-reference/11-docker/index.md b/docs/en/14-reference/11-docker/index.md
index b9278c6961..5a48f2e4b1 100644
--- a/docs/en/14-reference/11-docker/index.md
+++ b/docs/en/14-reference/11-docker/index.md
@@ -273,49 +273,48 @@ password: taosdata
## Start the TDengine cluster with docker-compose
-1. The following docker-compose file starts a TDengine cluster with two replicas, two management nodes, two data nodes, and one arbitrator.
+1. The following docker-compose file starts a TDengine cluster with three nodes.
- ```docker
- version: "3"
- services:
- arbitrator:
- image: tdengine/tdengine:$VERSION
- command: tarbitrator
- td-1:
- image: tdengine/tdengine:$VERSION
- environment:
- TAOS_FQDN: "td-1"
- TAOS_FIRST_EP: "td-1"
- TAOS_NUM_OF_MNODES: "2"
- TAOS_REPLICA: "2"
- TAOS_ARBITRATOR: arbitrator:6042
- volumes:
- - taosdata-td1:/var/lib/taos/
- - taoslog-td1:/var/log/taos/
- td-2:
- image: tdengine/tdengine:$VERSION
- environment:
- TAOS_FQDN: "td-2"
- TAOS_FIRST_EP: "td-1"
- TAOS_NUM_OF_MNODES: "2"
- TAOS_REPLICA: "2"
- TAOS_ARBITRATOR: arbitrator:6042
- volumes:
- - taosdata-td2:/var/lib/taos/
- - taoslog-td2:/var/log/taos/
- volumes:
- taosdata-td1:
- taoslog-td1:
- taosdata-td2:
- taoslog-td2:
- ```
+```yml
+version: "3"
+services:
+ td-1:
+ image: tdengine/tdengine:$VERSION
+ environment:
+ TAOS_FQDN: "td-1"
+ TAOS_FIRST_EP: "td-1"
+ volumes:
+ - taosdata-td1:/var/lib/taos/
+ - taoslog-td1:/var/log/taos/
+ td-2:
+ image: tdengine/tdengine:$VERSION
+ environment:
+ TAOS_FQDN: "td-2"
+ TAOS_FIRST_EP: "td-1"
+ volumes:
+ - taosdata-td2:/var/lib/taos/
+ - taoslog-td2:/var/log/taos/
+ td-3:
+ image: tdengine/tdengine:$VERSION
+ environment:
+ TAOS_FQDN: "td-3"
+ TAOS_FIRST_EP: "td-1"
+ volumes:
+ - taosdata-td3:/var/lib/taos/
+ - taoslog-td3:/var/log/taos/
+volumes:
+ taosdata-td1:
+ taoslog-td1:
+ taosdata-td2:
+ taoslog-td2:
+ taosdata-td3:
+ taoslog-td3:
+```
:::note
- The `VERSION` environment variable is used to set the tdengine image tag
- `TAOS_FIRST_EP` must be set on the newly created instance so that it can join the TDengine cluster; if there is a high availability requirement, `TAOS_SECOND_EP` needs to be used at the same time
-- `TAOS_REPLICA` is used to set the default number of database replicas. Its value range is [1,3]
- We recommend setting it with `TAOS_ARBITRATOR` to use arbitrator in a two-nodes environment.
:::
2. Start the cluster
@@ -345,17 +344,18 @@ password: taosdata
4. Show dnodes via TDengine CLI
- ```shell
- $ docker-compose exec td-1 taos -s "show dnodes"
+```shell
+$ docker-compose exec td-1 taos -s "show dnodes"
- taos> show dnodes
- id | end_point | vnodes | cores | status | role | create_time | offline reason |
- ======================================================================================================================================
- 1 | td-1:6030 | 1 | 8 | ready | any | 2022-01-18 02:47:42.871 | |
- 2 | td-2:6030 | 0 | 8 | ready | any | 2022-01-18 02:47:43.518 | |
- 0 | arbitrator:6042 | 0 | 0 | ready | arb | 2022-01-18 02:47:43.633 | - |
- Query OK, 3 row(s) in set (0.000811s)
- ```
+taos> show dnodes
+ id | endpoint | vnodes | support_vnodes | status | create_time | note |
+======================================================================================================================================
+ 1 | td-1:6030 | 0 | 32 | ready | 2022-08-19 07:57:29.971 | |
+ 2 | td-2:6030 | 0 | 32 | ready | 2022-08-19 07:57:31.415 | |
+ 3 | td-3:6030 | 0 | 32 | ready | 2022-08-19 07:57:31.417 | |
+Query OK, 3 rows in database (0.021262s)
+
+```
## taosAdapter
@@ -373,83 +373,70 @@ password: taosdata
Suppose you want to deploy multiple taosAdapters to improve throughput and provide high availability. In that case, the recommended configuration method uses a reverse proxy such as Nginx to offer a unified access entry. For specific configuration methods, please refer to the official documentation of Nginx. Here is an example:
- ```docker
- version: "3"
+```yml
+version: "3"
- networks:
- inter:
- api:
+networks:
+ inter:
- services:
- arbitrator:
- image: tdengine/tdengine:$VERSION
- command: tarbitrator
- networks:
- - inter
- td-1:
- image: tdengine/tdengine:$VERSION
- networks:
- - inter
- environment:
- TAOS_FQDN: "td-1"
- TAOS_FIRST_EP: "td-1"
- TAOS_NUM_OF_MNODES: "2"
- TAOS_REPLICA: "2"
- TAOS_ARBITRATOR: arbitrator:6042
- volumes:
- - taosdata-td1:/var/lib/taos/
- - taoslog-td1:/var/log/taos/
- td-2:
- image: tdengine/tdengine:$VERSION
- networks:
- - inter
- environment:
- TAOS_FQDN: "td-2"
- TAOS_FIRST_EP: "td-1"
- TAOS_NUM_OF_MNODES: "2"
- TAOS_REPLICA: "2"
- TAOS_ARBITRATOR: arbitrator:6042
- volumes:
- - taosdata-td2:/var/lib/taos/
- - taoslog-td2:/var/log/taos/
- adapter:
- image: tdengine/tdengine:$VERSION
- command: taosadapter
- networks:
- - inter
- environment:
- TAOS_FIRST_EP: "td-1"
- TAOS_SECOND_EP: "td-2"
- deploy:
- replicas: 4
- nginx:
- image: nginx
- depends_on:
- - adapter
- networks:
- - inter
- - api
- ports:
- - 6041:6041
- - 6044:6044/udp
- command: [
- "sh",
- "-c",
- "while true;
- do curl -s http://adapter:6041/-/ping >/dev/null && break;
- done;
- printf 'server{listen 6041;location /{proxy_pass http://adapter:6041;}}'
- > /etc/nginx/conf.d/rest.conf;
- printf 'stream{server{listen 6044 udp;proxy_pass adapter:6044;}}'
- >> /etc/nginx/nginx.conf;cat /etc/nginx/nginx.conf;
- nginx -g 'daemon off;'",
- ]
- volumes:
- taosdata-td1:
- taoslog-td1:
- taosdata-td2:
- taoslog-td2:
- ```
+services:
+ td-1:
+ image: tdengine/tdengine:$VERSION
+ networks:
+ - inter
+ environment:
+ TAOS_FQDN: "td-1"
+ TAOS_FIRST_EP: "td-1"
+ volumes:
+ - taosdata-td1:/var/lib/taos/
+ - taoslog-td1:/var/log/taos/
+ td-2:
+ image: tdengine/tdengine:$VERSION
+ networks:
+ - inter
+ environment:
+ TAOS_FQDN: "td-2"
+ TAOS_FIRST_EP: "td-1"
+ volumes:
+ - taosdata-td2:/var/lib/taos/
+ - taoslog-td2:/var/log/taos/
+ adapter:
+ image: tdengine/tdengine:$VERSION
+ entrypoint: "taosadapter"
+ networks:
+ - inter
+ environment:
+ TAOS_FIRST_EP: "td-1"
+ TAOS_SECOND_EP: "td-2"
+ deploy:
+ replicas: 4
+ nginx:
+ image: nginx
+ depends_on:
+ - adapter
+ networks:
+ - inter
+ ports:
+ - 6041:6041
+ - 6044:6044/udp
+ command: [
+ "sh",
+ "-c",
+ "while true;
+ do curl -s http://adapter:6041/-/ping >/dev/null && break;
+ done;
+ printf 'server{listen 6041;location /{proxy_pass http://adapter:6041;}}'
+ > /etc/nginx/conf.d/rest.conf;
+ printf 'stream{server{listen 6044 udp;proxy_pass adapter:6044;}}'
+ >> /etc/nginx/nginx.conf;cat /etc/nginx/nginx.conf;
+ nginx -g 'daemon off;'",
+ ]
+volumes:
+ taosdata-td1:
+ taoslog-td1:
+ taosdata-td2:
+ taoslog-td2:
+```
## Deploy with docker swarm
diff --git a/docs/en/28-releases/01-tdengine.md b/docs/en/28-releases/01-tdengine.md
index 0c5ccf3aef..6a62108062 100644
--- a/docs/en/28-releases/01-tdengine.md
+++ b/docs/en/28-releases/01-tdengine.md
@@ -10,6 +10,10 @@ For TDengine 2.x installation packages by version, please visit [here](https://w
import Release from "/components/ReleaseV3";
+## 3.0.2.6
+
+
+
## 3.0.2.5
diff --git a/docs/en/28-releases/02-tools.md b/docs/en/28-releases/02-tools.md
index 29dd605c8c..91eb0c9b8d 100644
--- a/docs/en/28-releases/02-tools.md
+++ b/docs/en/28-releases/02-tools.md
@@ -10,6 +10,10 @@ For other historical version installers, please visit [here](https://www.taosdat
import Release from "/components/ReleaseV3";
+## 2.4.6
+
+
+
## 2.4.3
diff --git a/docs/examples/java/pom.xml b/docs/examples/java/pom.xml
index 634c3f75a8..01d0ce936c 100644
--- a/docs/examples/java/pom.xml
+++ b/docs/examples/java/pom.xml
@@ -1,6 +1,7 @@
-
4.0.0
@@ -17,13 +18,13 @@
-
+
com.taosdata.jdbc
taos-jdbcdriver
- 3.0.0
+ 3.1.0
-
+
junit
junit
@@ -32,4 +33,4 @@
-
+
\ No newline at end of file
diff --git a/docs/examples/java/src/main/java/com/taos/example/WebsocketSubscribeDemo.java b/docs/examples/java/src/main/java/com/taos/example/WebsocketSubscribeDemo.java
new file mode 100644
index 0000000000..d953a73641
--- /dev/null
+++ b/docs/examples/java/src/main/java/com/taos/example/WebsocketSubscribeDemo.java
@@ -0,0 +1,79 @@
+package com.taos.example;
+
+import com.taosdata.jdbc.tmq.ConsumerRecords;
+import com.taosdata.jdbc.tmq.TMQConstants;
+import com.taosdata.jdbc.tmq.TaosConsumer;
+
+import java.sql.Connection;
+import java.sql.DriverManager;
+import java.sql.SQLException;
+import java.sql.Statement;
+import java.time.Duration;
+import java.util.Collections;
+import java.util.Properties;
+import java.util.Timer;
+import java.util.TimerTask;
+import java.util.concurrent.atomic.AtomicBoolean;
+
+public class WebsocketSubscribeDemo {
+ private static final String TOPIC = "tmq_topic_ws";
+ private static final String DB_NAME = "meters_ws";
+ private static final AtomicBoolean shutdown = new AtomicBoolean(false);
+
+ public static void main(String[] args) {
+ Timer timer = new Timer();
+ timer.schedule(new TimerTask() {
+ public void run() {
+ shutdown.set(true);
+ }
+ }, 3_000);
+ try {
+ // prepare
+ Class.forName("com.taosdata.jdbc.rs.RestfulDriver");
+ String jdbcUrl = "jdbc:TAOS-RS://127.0.0.1:6041/?user=root&password=taosdata&batchfetch=true";
+ try (Connection connection = DriverManager.getConnection(jdbcUrl);
+ Statement statement = connection.createStatement()) {
+ statement.executeUpdate("drop topic if exists " + TOPIC);
+ statement.executeUpdate("drop database if exists " + DB_NAME);
+ statement.executeUpdate("create database " + DB_NAME);
+ statement.executeUpdate("use " + DB_NAME);
+ statement.executeUpdate(
+ "CREATE TABLE `meters` (`ts` TIMESTAMP, `current` FLOAT, `voltage` INT) TAGS (`groupid` INT, `location` BINARY(24))");
+ statement.executeUpdate("CREATE TABLE `d0` USING `meters` TAGS(0, 'California.LosAngles')");
+ statement.executeUpdate("INSERT INTO `d0` values(now - 10s, 0.32, 116)");
+ statement.executeUpdate("INSERT INTO `d0` values(now - 8s, NULL, NULL)");
+ statement.executeUpdate(
+ "INSERT INTO `d1` USING `meters` TAGS(1, 'California.SanFrancisco') values(now - 9s, 10.1, 119)");
+ statement.executeUpdate(
+ "INSERT INTO `d1` values (now-8s, 10, 120) (now - 6s, 10, 119) (now - 4s, 11.2, 118)");
+ // create topic
+ statement.executeUpdate("create topic " + TOPIC + " as select * from meters");
+ }
+
+ // create consumer
+ Properties properties = new Properties();
+ properties.setProperty(TMQConstants.BOOTSTRAP_SERVERS, "127.0.0.1:6041");
+ properties.setProperty(TMQConstants.CONNECT_TYPE, "ws");
+ properties.setProperty(TMQConstants.MSG_WITH_TABLE_NAME, "true");
+ properties.setProperty(TMQConstants.ENABLE_AUTO_COMMIT, "true");
+ properties.setProperty(TMQConstants.GROUP_ID, "test");
+ properties.setProperty(TMQConstants.VALUE_DESERIALIZER,
+ "com.taos.example.MetersDeserializer");
+
+ // poll data
+ try (TaosConsumer consumer = new TaosConsumer<>(properties)) {
+ consumer.subscribe(Collections.singletonList(TOPIC));
+ while (!shutdown.get()) {
+ ConsumerRecords meters = consumer.poll(Duration.ofMillis(100));
+ for (Meters meter : meters) {
+ System.out.println(meter);
+ }
+ }
+ consumer.unsubscribe();
+ }
+ } catch (ClassNotFoundException | SQLException e) {
+ e.printStackTrace();
+ }
+ timer.cancel();
+ }
+}
diff --git a/docs/examples/java/src/test/java/com/taos/test/TestAll.java b/docs/examples/java/src/test/java/com/taos/test/TestAll.java
index 8d201da074..f24156d8b1 100644
--- a/docs/examples/java/src/test/java/com/taos/test/TestAll.java
+++ b/docs/examples/java/src/test/java/com/taos/test/TestAll.java
@@ -64,21 +64,15 @@ public class TestAll {
@Test
public void testSubscribe() {
-
- Thread thread = new Thread(() -> {
- try {
- Thread.sleep(1000);
- insertData();
- } catch (SQLException e) {
- e.printStackTrace();
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- });
- thread.start();
SubscribeDemo.main(args);
}
+
+ @Test
+ public void testSubscribeOverWebsocket() {
+ WebsocketSubscribeDemo.main(args);
+ }
+
@Test
public void testSchemaless() throws SQLException {
LineProtocolExample.main(args);
diff --git a/docs/zh/07-develop/07-tmq.mdx b/docs/zh/07-develop/07-tmq.mdx
index fb171042d9..52fd0c42c3 100644
--- a/docs/zh/07-develop/07-tmq.mdx
+++ b/docs/zh/07-develop/07-tmq.mdx
@@ -7,6 +7,7 @@ title: 数据订阅
import Tabs from "@theme/Tabs";
import TabItem from "@theme/TabItem";
import Java from "./_sub_java.mdx";
+import JavaWS from "./_sub_java_ws.mdx";
import Python from "./_sub_python.mdx";
import Go from "./_sub_go.mdx";
import Rust from "./_sub_rust.mdx";
@@ -807,7 +808,14 @@ SHOW SUBSCRIPTIONS;
-
+
+
+
+
+
+
+
+
diff --git a/docs/zh/07-develop/_sub_java.mdx b/docs/zh/07-develop/_sub_java.mdx
index e7de158cc8..60810ec275 100644
--- a/docs/zh/07-develop/_sub_java.mdx
+++ b/docs/zh/07-develop/_sub_java.mdx
@@ -6,4 +6,3 @@
```
```java
{{#include docs/examples/java/src/main/java/com/taos/example/Meters.java}}
-```
\ No newline at end of file
diff --git a/docs/zh/07-develop/_sub_java_ws.mdx b/docs/zh/07-develop/_sub_java_ws.mdx
new file mode 100644
index 0000000000..5a4211d059
--- /dev/null
+++ b/docs/zh/07-develop/_sub_java_ws.mdx
@@ -0,0 +1,9 @@
+```java
+{{#include docs/examples/java/src/main/java/com/taos/example/WebsocketSubscribeDemo.java}}
+```
+```java
+{{#include docs/examples/java/src/main/java/com/taos/example/MetersDeserializer.java}}
+```
+```java
+{{#include docs/examples/java/src/main/java/com/taos/example/Meters.java}}
+```
\ No newline at end of file
diff --git a/docs/zh/08-connector/14-java.mdx b/docs/zh/08-connector/14-java.mdx
index fc6dc57138..061475f51e 100644
--- a/docs/zh/08-connector/14-java.mdx
+++ b/docs/zh/08-connector/14-java.mdx
@@ -699,7 +699,10 @@ TaosConsumer consumer = new TaosConsumer<>(config);
- enable.auto.commit: 是否允许自动提交。
- group.id: consumer: 所在的 group。
- value.deserializer: 结果集反序列化方法,可以继承 `com.taosdata.jdbc.tmq.ReferenceDeserializer`,并指定结果集 bean,实现反序列化。也可以继承 `com.taosdata.jdbc.tmq.Deserializer`,根据 SQL 的 resultSet 自定义反序列化方式。
-- 其他参数请参考:[Consumer 参数列表](../../../develop/tmq#创建-consumer-以及consumer-group)
+- td.connect.type: 连接方式。jni:表示使用动态库连接的方式,ws/WebSocket:表示使用 WebSocket 进行数据通信。默认为 jni 方式。
+- httpConnectTimeout:创建连接超时参数,单位 ms,默认为 5000 ms。仅在 WebSocket 连接下有效。
+- messageWaitTimeout:数据传输超时参数,单位 ms,默认为 10000 ms。仅在 WebSocket 连接下有效。
+其他参数请参考:[Consumer 参数列表](../../../develop/tmq#创建-consumer-以及consumer-group)
#### 订阅消费数据
@@ -727,6 +730,9 @@ consumer.close()
### 使用示例如下:
+
+
+
```java
public abstract class ConsumerLoop {
private final TaosConsumer consumer;
@@ -798,6 +804,89 @@ public abstract class ConsumerLoop {
}
```
+
+
+
+除了原生的连接方式,Java 连接器还支持通过 WebSocket 订阅数据。
+
+```java
+public abstract class ConsumerLoop {
+ private final TaosConsumer consumer;
+ private final List topics;
+ private final AtomicBoolean shutdown;
+ private final CountDownLatch shutdownLatch;
+
+ public ConsumerLoop() throws SQLException {
+ Properties config = new Properties();
+ config.setProperty("bootstrap.servers", "localhost:6041");
+ config.setProperty("td.connect.type", "ws");
+ config.setProperty("msg.with.table.name", "true");
+ config.setProperty("enable.auto.commit", "true");
+ config.setProperty("group.id", "group2");
+ config.setProperty("value.deserializer", "com.taosdata.jdbc.tmq.ConsumerTest.ConsumerLoop$ResultDeserializer");
+
+ this.consumer = new TaosConsumer<>(config);
+ this.topics = Collections.singletonList("topic_speed");
+ this.shutdown = new AtomicBoolean(false);
+ this.shutdownLatch = new CountDownLatch(1);
+ }
+
+ public abstract void process(ResultBean result);
+
+ public void pollData() throws SQLException {
+ try {
+ consumer.subscribe(topics);
+
+ while (!shutdown.get()) {
+ ConsumerRecords records = consumer.poll(Duration.ofMillis(100));
+ for (ResultBean record : records) {
+ process(record);
+ }
+ }
+ consumer.unsubscribe();
+ } finally {
+ consumer.close();
+ shutdownLatch.countDown();
+ }
+ }
+
+ public void shutdown() throws InterruptedException {
+ shutdown.set(true);
+ shutdownLatch.await();
+ }
+
+ public static class ResultDeserializer extends ReferenceDeserializer {
+
+ }
+
+ public static class ResultBean {
+ private Timestamp ts;
+ private int speed;
+
+ public Timestamp getTs() {
+ return ts;
+ }
+
+ public void setTs(Timestamp ts) {
+ this.ts = ts;
+ }
+
+ public int getSpeed() {
+ return speed;
+ }
+
+ public void setSpeed(int speed) {
+ this.speed = speed;
+ }
+ }
+}
+```
+
+
+
+
+> **注意**:这里的 value.deserializer 配置参数值应该根据测试环境的包路径做相应的调整。
+
### 与连接池使用
#### HikariCP
@@ -881,8 +970,8 @@ public static void main(String[] args) throws Exception {
| taos-jdbcdriver 版本 | 主要变化 |
| :------------------: | :----------------------------: |
-| 3.0.3 | 修复 REST 连接在 jdk17+ 版本时间戳解析错误问题 |
-| 3.0.1 - 3.0.2 | 修复一些情况下结果集数据解析错误的问题。3.0.1 在 JDK 11 环境编译,JDK 8 环境下建议使用 3.0.2 版本 |
+| 3.1.0 | WebSocket 连接支持订阅功能 |
+| 3.0.1 - 3.0.4 | 修复一些情况下结果集数据解析错误的问题。3.0.1 在 JDK 11 环境编译,JDK 8 环境下建议使用其他版本 |
| 3.0.0 | 支持 TDengine 3.0 |
| 2.0.42 | 修在 WebSocket 连接中 wasNull 接口返回值 |
| 2.0.41 | 修正 REST 连接中用户名和密码转码方式 |
diff --git a/docs/zh/12-taos-sql/10-function.md b/docs/zh/12-taos-sql/10-function.md
index 647f917422..94f8052051 100644
--- a/docs/zh/12-taos-sql/10-function.md
+++ b/docs/zh/12-taos-sql/10-function.md
@@ -798,18 +798,22 @@ HISTOGRAM(expr,bin_type, bin_description, normalized)
### PERCENTILE
```sql
-PERCENTILE(expr, p)
+PERCENTILE(expr, p [, p1] ... )
```
**功能说明**:统计表中某列的值百分比分位数。
-**返回数据类型**: DOUBLE。
+**返回数据类型**: 该函数最小参数个数为 2 个,最大参数个数为 11 个。可以最多同时返回 10 个百分比分位数。当参数个数为 2 时, 返回一个分位数, 类型为DOUBLE,当参数个数大于 2 时,返回类型为VARCHAR, 格式为包含多个返回值的JSON数组。
**应用字段**:数值类型。
**适用于**:表。
-**使用说明**:*P*值取值范围 0≤*P*≤100,为 0 的时候等同于 MIN,为 100 的时候等同于 MAX。
+**使用说明**:
+
+- *P*值取值范围 0≤*P*≤100,为 0 的时候等同于 MIN,为 100 的时候等同于 MAX;
+- 同时计算针对同一列的多个分位数时,建议使用一个PERCENTILE函数和多个参数的方式,能很大程度上降低查询的响应时间。
+ 比如,使用查询SELECT percentile(col, 90, 95, 99) FROM table, 性能会优于SELECT percentile(col, 90), percentile(col, 95), percentile(col, 99) from table。
## 选择函数
diff --git a/docs/zh/12-taos-sql/24-show.md b/docs/zh/12-taos-sql/24-show.md
index 0a326729f2..aad4ed294e 100644
--- a/docs/zh/12-taos-sql/24-show.md
+++ b/docs/zh/12-taos-sql/24-show.md
@@ -191,37 +191,39 @@ SHOW TABLE DISTRIBUTED table_name;
_block_dist: Total_Blocks=[5] Total_Size=[93.65 Kb] Average_size=[18.73 Kb] Compression_Ratio=[23.98 %]
-Total_Blocks : 表d0 占用的 block 个数为 5 个
+Total_Blocks: 表 d0 占用的 block 个数为 5 个
-Total_Size. : 表 d0 所有 block 在文件中占用的大小为 93.65 KB
+Total_Size: 表 d0 所有 block 在文件中占用的大小为 93.65 KB
Average_size: 平均每个 block 在文件中占用的空间大小为 18.73 KB
-Compression_Ratio: 数据压缩率为 23.98%
+Compression_Ratio: 数据压缩率 23.98%
*************************** 2.row ***************************
_block_dist: Total_Rows=[20000] Inmem_Rows=[0] MinRows=[3616] MaxRows=[4096] Average_Rows=[4000]
-Total_Rows: 统计表 d0 的所有行数 为20000 行
+Total_Rows: 统计表 d0 的存储在磁盘上行数 20000 行(该数值仅供参考,不是精确的行数。获得精确的行数需要使用 count 函数)
-Inmem_Rows: 表示仍然还存放在内存中的行数,即没有落盘的行数,为 0行,表示没有
+Inmem_Rows: 存储在写缓存中的数据行数(没有落盘),0 行表示内存缓存中没有数据
-MinRows: BLOCK 中最小的行数,为 3616 行
+MinRows: BLOCK 中最小的行数,为 3616 行
-MaxRows: BLOCK 中最大的行数,为 4096行
+MaxRows: BLOCK 中最大的行数,为 4096 行
-Average_Rows: BLOCK 中的平均行数,为4000 行
+Average_Rows: 每个 BLOCK 中的平均行数,此时为 4000 行
*************************** 3.row ***************************
-_block_dist: Total_Tables=[1] Total_Files=[2]
+_block_dist: Total_Tables=[1] Total_Files=[2] Total_Vgroups=[1]
-Total_Tables: 表示子表的个数,这里为1
+Total_Tables: 子表的个数,这里为 1
-Total_Files: 表数据保存在几个文件中,这里保存在 2 个文件中
+Total_Files: 表数据被分别保存的数据文件数量,这里是 2 个文件
+
+Total_Vgroups: 表数据分布的虚拟节点(vnode)数量
*************************** 5.row ***************************
diff --git a/docs/zh/14-reference/11-docker/index.md b/docs/zh/14-reference/11-docker/index.md
index 086d72940c..a6696977f9 100644
--- a/docs/zh/14-reference/11-docker/index.md
+++ b/docs/zh/14-reference/11-docker/index.md
@@ -309,7 +309,7 @@ services:
TAOS_FIRST_EP: "td-1"
volumes:
- taosdata-td3:/var/lib/taos/
- - taoslog-td3:/var/log/taos/
+ - taoslog-td3:/var/log/taos/
volumes:
taosdata-td1:
taoslog-td1:
@@ -473,18 +473,18 @@ Creating service taos_adapter
```shell
$ docker stack ps taos
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE ERROR PORTS
-7m3sbf532bqp taos_adapter.1 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
-pj403n6ofmmh taos_adapter.2 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
-rxqfwsyk5q1h taos_adapter.3 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
-qj40lpxr40oc taos_adapter.4 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
-oe3455ulxpze taos_nginx.1 nginx:latest vm98 Running Running about a minute ago
-o0tsg70nrrc6 taos_td-1.1 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
+7m3sbf532bqp taos_adapter.1 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
+pj403n6ofmmh taos_adapter.2 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
+rxqfwsyk5q1h taos_adapter.3 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
+qj40lpxr40oc taos_adapter.4 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
+oe3455ulxpze taos_nginx.1 nginx:latest vm98 Running Running about a minute ago
+o0tsg70nrrc6 taos_td-1.1 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
q5m1oxs589cp taos_td-2.1 tdengine/tdengine:3.0.0.0 vm98 Running Running about a minute ago
$ docker service ls
ID NAME MODE REPLICAS IMAGE PORTS
-ozuklorgl8bs taos_adapter replicated 4/4 tdengine/tdengine:3.0.0.0
+ozuklorgl8bs taos_adapter replicated 4/4 tdengine/tdengine:3.0.0.0
crmhdjw6vxw0 taos_nginx replicated 1/1 nginx:latest *:6041->6041/tcp, *:6044->6044/udp
-o86ngy7csv5n taos_td-1 replicated 1/1 tdengine/tdengine:3.0.0.0
+o86ngy7csv5n taos_td-1 replicated 1/1 tdengine/tdengine:3.0.0.0
rma040ny4tb0 taos_td-2 replicated 1/1 tdengine/tdengine:3.0.0.0
```
@@ -495,11 +495,11 @@ rma040ny4tb0 taos_td-2 replicated 1/1 tdengine/tdengine:3.0.0.0
```shell
$ docker service scale taos_adapter=1
taos_adapter scaled to 1
-overall progress: 1 out of 1 tasks
-1/1: running [==================================================>]
+overall progress: 1 out of 1 tasks
+1/1: running [==================================================>]
verify: Service converged
$ docker service ls -f name=taos_adapter
ID NAME MODE REPLICAS IMAGE PORTS
-ozuklorgl8bs taos_adapter replicated 1/1 tdengine/tdengine:3.0.0.0
+ozuklorgl8bs taos_adapter replicated 1/1 tdengine/tdengine:3.0.0.0
```
diff --git a/docs/zh/28-releases/01-tdengine.md b/docs/zh/28-releases/01-tdengine.md
index cf7bf83164..c9505d95a5 100644
--- a/docs/zh/28-releases/01-tdengine.md
+++ b/docs/zh/28-releases/01-tdengine.md
@@ -10,6 +10,10 @@ TDengine 2.x 各版本安装包请访问[这里](https://www.taosdata.com/all-do
import Release from "/components/ReleaseV3";
+## 3.0.2.6
+
+
+
## 3.0.2.5
diff --git a/docs/zh/28-releases/02-tools.md b/docs/zh/28-releases/02-tools.md
index 5f277b4873..69d35f95c8 100644
--- a/docs/zh/28-releases/02-tools.md
+++ b/docs/zh/28-releases/02-tools.md
@@ -10,6 +10,10 @@ taosTools 各版本安装包下载链接如下:
import Release from "/components/ReleaseV3";
+## 2.4.6
+
+
+
## 2.4.3
diff --git a/examples/JDBC/springbootdemo/readme.md b/examples/JDBC/springbootdemo/readme.md
index a3942a6a51..a89e21c009 100644
--- a/examples/JDBC/springbootdemo/readme.md
+++ b/examples/JDBC/springbootdemo/readme.md
@@ -1,6 +1,13 @@
## TDengine SpringBoot + Mybatis Demo
## 需要提前创建 test 数据库
+
+```
+$ taos -s 'create database if not exists test'
+
+$ curl http://localhost:8080/weather/init
+```
+
### 配置 application.properties
```properties
# datasource config
diff --git a/examples/JDBC/springbootdemo/src/main/java/com/taosdata/example/springbootdemo/dao/WeatherMapper.xml b/examples/JDBC/springbootdemo/src/main/java/com/taosdata/example/springbootdemo/dao/WeatherMapper.xml
index 99d5893ec1..4899ec4654 100644
--- a/examples/JDBC/springbootdemo/src/main/java/com/taosdata/example/springbootdemo/dao/WeatherMapper.xml
+++ b/examples/JDBC/springbootdemo/src/main/java/com/taosdata/example/springbootdemo/dao/WeatherMapper.xml
@@ -7,6 +7,7 @@
+
- insert into test.t#{groupId} (ts, temperature, humidity, note)
- values (#{ts}, ${temperature}, ${humidity}, #{note})
+ insert into test.t#{groupId} (ts, temperature, humidity, note, bytes)
+ values (#{ts}, ${temperature}, ${humidity}, #{note}, #{bytes})