You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@iotdb.apache.org by ro...@apache.org on 2024/09/04 02:44:59 UTC
(iotdb) 01/03: yes
This is an automated email from the ASF dual-hosted git repository.
rong pushed a commit to branch iotdb-influxdb-proto-example
in repository https://gitbox.apache.org/repos/asf/iotdb.git
commit 0adadac9796cfb89fda3a894c448ee9d1816638b
Author: Steve Yurong Su <ro...@apache.org>
AuthorDate: Tue Sep 3 18:17:37 2024 +0800
yes
---
example/influxdb-proto-example/pom.xml | 43 +
.../iotdb/AlignedTimeseriesSessionExample.java | 637 ++++++++++++++
.../org/apache/iotdb/DataMigrationExample.java | 211 +++++
.../iotdb/HybridTimeseriesSessionExample.java | 131 +++
.../org/apache/iotdb/SessionConcurrentExample.java | 197 +++++
.../main/java/org/apache/iotdb/SessionExample.java | 914 +++++++++++++++++++++
.../java/org/apache/iotdb/SessionPoolExample.java | 154 ++++
.../apache/iotdb/SubscriptionSessionExample.java | 345 ++++++++
.../iotdb/SyntaxConventionRelatedExample.java | 156 ++++
.../org/apache/iotdb/TableModelSessionExample.java | 136 +++
.../apache/iotdb/TableModelSessionPoolExample.java | 147 ++++
.../main/java/org/apache/iotdb/TabletExample.java | 204 +++++
example/pom.xml | 1 +
iotdb-client/session/pom.xml | 5 +
.../iotdb/session/influxdb/IoTDBInfluxDB.java | 393 +++++++++
.../influxdb/IoTDBInfluxDBProtoFactory.java | 74 ++
.../influxdb/example/InfluxProtoExample.java | 72 ++
.../protocol/constant/InfluxDBConstant.java | 25 +
.../influxdb/protocol/dto/SessionPoint.java | 88 ++
.../protocol/impl/IoTDBInfluxDBService.java | 77 ++
.../influxdb/protocol/util/ParameterUtils.java | 36 +
.../session/influxdb/session/InfluxDBSession.java | 219 +++++
22 files changed, 4265 insertions(+)
diff --git a/example/influxdb-proto-example/pom.xml b/example/influxdb-proto-example/pom.xml
new file mode 100644
index 00000000000..92d8e9b5b4d
--- /dev/null
+++ b/example/influxdb-proto-example/pom.xml
@@ -0,0 +1,43 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <parent>
+ <groupId>org.apache.iotdb</groupId>
+ <artifactId>iotdb-examples</artifactId>
+ <version>1.4.0-SNAPSHOT</version>
+ </parent>
+ <artifactId>influxdb-proto-example</artifactId>
+ <name>IoTDB: Example: InfluxDB Proto</name>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.iotdb</groupId>
+ <artifactId>iotdb-session</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.iotdb</groupId>
+ <artifactId>node-commons</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ </dependencies>
+</project>
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/AlignedTimeseriesSessionExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/AlignedTimeseriesSessionExample.java
new file mode 100644
index 00000000000..1c412482800
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/AlignedTimeseriesSessionExample.java
@@ -0,0 +1,637 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.isession.template.Template;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.Session;
+import org.apache.iotdb.session.template.InternalNode;
+import org.apache.iotdb.session.template.MeasurementNode;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.file.metadata.enums.CompressionType;
+import org.apache.tsfile.file.metadata.enums.TSEncoding;
+import org.apache.tsfile.utils.BitMap;
+import org.apache.tsfile.write.record.Tablet;
+import org.apache.tsfile.write.schema.IMeasurementSchema;
+import org.apache.tsfile.write.schema.MeasurementSchema;
+
+import java.io.IOException;
+import java.security.SecureRandom;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+@SuppressWarnings({"squid:S106", "squid:S1144", "squid:S125"})
+public class AlignedTimeseriesSessionExample {
+
+ private static Session session;
+ private static final String ROOT_SG1_D1 = "root.sg_1.d1";
+ private static final String ROOT_SG1_D1_VECTOR2 = "root.sg_1.d1.vector2";
+ private static final String ROOT_SG1_D1_VECTOR3 = "root.sg_1.d1.vector3";
+ private static final String ROOT_SG2_D1_VECTOR4 = "root.sg_2.d1.vector4";
+ private static final String ROOT_SG2_D1_VECTOR5 = "root.sg_2.d1.vector5";
+ private static final String ROOT_SG2_D1_VECTOR6 = "root.sg_2.d1.vector6";
+ private static final String ROOT_SG2_D1_VECTOR7 = "root.sg_2.d1.vector7";
+ private static final String ROOT_SG2_D1_VECTOR8 = "root.sg_2.d1.vector8";
+ public static final String FLUSH = "flush";
+
+ public static void main(String[] args)
+ throws IoTDBConnectionException, StatementExecutionException {
+ session = new Session("127.0.0.1", 6667, "root", "root");
+ session.open(false);
+
+ // set session fetchSize
+ session.setFetchSize(10000);
+
+ // createTemplate();
+ createAlignedTimeseries();
+
+ insertAlignedRecord();
+ // insertAlignedRecords();
+ // insertAlignedRecordsOfOneDevice();
+
+ // insertAlignedStringRecord();
+ // insertAlignedStringRecords();
+
+ // insertTabletWithAlignedTimeseriesMethod1();
+ // insertTabletWithAlignedTimeseriesMethod2();
+ // insertNullableTabletWithAlignedTimeseries();
+ // insertTabletsWithAlignedTimeseries();
+ session.executeNonQueryStatement(FLUSH);
+ selectTest();
+ selectWithValueFilterTest();
+ selectWithLastTest();
+ selectWithLastTestWithoutValueFilter();
+ session.executeNonQueryStatement("delete from root.sg_1.d1.s1 where time <= 5");
+ System.out.println("execute sql delete from root.sg_1.d1.s1 where time <= 5");
+ selectTest();
+ selectWithValueFilterTest();
+ selectWithLastTest();
+ selectWithLastTestWithoutValueFilter();
+ session.executeNonQueryStatement("delete from root.sg_1.d1.s2 where time <= 3");
+ System.out.println("execute sql delete from root.sg_1.d1.s2 where time <= 3");
+
+ selectTest();
+ selectWithValueFilterTest();
+ selectWithLastTest();
+ selectWithLastTestWithoutValueFilter();
+ session.executeNonQueryStatement("delete from root.sg_1.d1.s1 where time <= 10");
+ System.out.println("execute sql delete from root.sg_1.d1.s1 where time <= 10");
+ selectTest();
+ selectWithValueFilterTest();
+ selectWithLastTest();
+ selectWithLastTestWithoutValueFilter();
+
+ // selectWithValueFilterTest();
+ // selectWithGroupByTest();
+ // selectWithLastTest();
+
+ // selectWithAggregationTest();
+
+ // selectWithAlignByDeviceTest();
+
+ session.close();
+ }
+
+ private static void selectTest() throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet = session.executeQueryStatement("select s1 from root.sg_1.d1");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ dataSet = session.executeQueryStatement("select * from root.sg_1.d1");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ private static void selectWithAlignByDeviceTest()
+ throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet =
+ session.executeQueryStatement("select * from root.sg_1 align by device");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ private static void selectWithValueFilterTest()
+ throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet =
+ session.executeQueryStatement("select s1 from root.sg_1.d1 where s1 > 3 and time < 9");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ dataSet =
+ session.executeQueryStatement(
+ "select * from root.sg_1.d1 where time < 8 and s1 > 3 and s2 > 5");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ private static void selectWithAggregationTest()
+ throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet = session.executeQueryStatement("select count(s1) from root.sg_1.d1");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ dataSet = session.executeQueryStatement("select count(*) from root.sg_1.d1");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ dataSet =
+ session.executeQueryStatement(
+ "select sum(*) from root.sg_1.d1.vector where time > 50 and s1 > 0 and s2 > 10000");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ private static void selectWithGroupByTest()
+ throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet =
+ session.executeQueryStatement(
+ "select count(s1) from root.sg_1.d1.vector GROUP BY ([1, 100), 20ms)");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ dataSet =
+ session.executeQueryStatement(
+ "select count(*) from root.sg_1.d1.vector where time > 50 and s1 > 0 and s2 > 10000"
+ + " GROUP BY ([50, 100), 10ms)");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ private static void selectWithLastTest()
+ throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet = session.executeQueryStatement("select last s1 from root.sg_1.d1");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ dataSet = session.executeQueryStatement("select last * from root.sg_1.d1");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ private static void selectWithLastTestWithoutValueFilter()
+ throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet =
+ session.executeQueryStatement("select last s1 from root.sg_1.d1 where time >= 5");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+
+ dataSet = session.executeQueryStatement("select last * from root.sg_1.d1 where time >= 5");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ dataSet.closeOperationHandle();
+
+ dataSet = session.executeQueryStatement("select last * from root.sg_1.d1 where time >= 20");
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ dataSet.closeOperationHandle();
+ }
+
+ private static void createAlignedTimeseries()
+ throws StatementExecutionException, IoTDBConnectionException {
+ List<String> measurements = new ArrayList<>();
+ for (int i = 1; i <= 2; i++) {
+ measurements.add("s" + i);
+ }
+ List<TSDataType> dataTypes = new ArrayList<>();
+ dataTypes.add(TSDataType.INT64);
+ dataTypes.add(TSDataType.INT32);
+ List<TSEncoding> encodings = new ArrayList<>();
+ List<CompressionType> compressors = new ArrayList<>();
+ for (int i = 1; i <= 2; i++) {
+ encodings.add(TSEncoding.RLE);
+ compressors.add(CompressionType.SNAPPY);
+ }
+ session.createAlignedTimeseries(
+ ROOT_SG1_D1, measurements, dataTypes, encodings, compressors, null, null, null);
+ }
+
+ // be sure template is coordinate with tablet
+ private static void createTemplate()
+ throws StatementExecutionException, IoTDBConnectionException, IOException {
+ Template template = new Template("template1");
+ InternalNode iNodeVector = new InternalNode("vector", true);
+ MeasurementNode mNodeS1 =
+ new MeasurementNode("s1", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ MeasurementNode mNodeS2 =
+ new MeasurementNode("s2", TSDataType.INT32, TSEncoding.RLE, CompressionType.SNAPPY);
+
+ iNodeVector.addChild(mNodeS1);
+ iNodeVector.addChild(mNodeS2);
+
+ template.addToTemplate(iNodeVector);
+
+ session.createSchemaTemplate(template);
+ session.setSchemaTemplate("template1", "root.sg_1");
+ }
+
+ /** Method 1 for insert tablet with aligned timeseries */
+ private static void insertTabletWithAlignedTimeseriesMethod1()
+ throws IoTDBConnectionException, StatementExecutionException {
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT32));
+
+ Tablet tablet = new Tablet(ROOT_SG1_D1, schemaList);
+ long timestamp = 1;
+
+ for (long row = 1; row < 100; row++) {
+ int rowIndex = tablet.rowSize++;
+ tablet.addTimestamp(rowIndex, timestamp);
+ tablet.addValue(
+ schemaList.get(0).getMeasurementId(), rowIndex, new SecureRandom().nextLong());
+ tablet.addValue(schemaList.get(1).getMeasurementId(), rowIndex, new SecureRandom().nextInt());
+
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertAlignedTablet(tablet, true);
+ tablet.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertAlignedTablet(tablet);
+ tablet.reset();
+ }
+
+ session.executeNonQueryStatement(FLUSH);
+ }
+
+ /** Method 2 for insert tablet with aligned timeseries */
+ private static void insertTabletWithAlignedTimeseriesMethod2()
+ throws IoTDBConnectionException, StatementExecutionException {
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT32));
+
+ Tablet tablet = new Tablet(ROOT_SG1_D1_VECTOR2, schemaList);
+ long[] timestamps = tablet.timestamps;
+ Object[] values = tablet.values;
+
+ for (long time = 100; time < 200; time++) {
+ int row = tablet.rowSize++;
+ timestamps[row] = time;
+
+ long[] sensor1 = (long[]) values[0];
+ sensor1[row] = new SecureRandom().nextLong();
+
+ int[] sensor2 = (int[]) values[1];
+ sensor2[row] = new SecureRandom().nextInt();
+
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertAlignedTablet(tablet, true);
+ tablet.reset();
+ }
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertAlignedTablet(tablet, true);
+ tablet.reset();
+ }
+
+ session.executeNonQueryStatement(FLUSH);
+ }
+
+ private static void insertNullableTabletWithAlignedTimeseries()
+ throws IoTDBConnectionException, StatementExecutionException {
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT32));
+
+ Tablet tablet = new Tablet(ROOT_SG1_D1_VECTOR3, schemaList);
+
+ long[] timestamps = tablet.timestamps;
+ Object[] values = tablet.values;
+ // Use the bitMap to mark the null value point
+ BitMap[] bitMaps = new BitMap[values.length];
+ tablet.bitMaps = bitMaps;
+
+ bitMaps[1] = new BitMap(tablet.getMaxRowNumber());
+ for (long time = 200; time < 300; time++) {
+ int row = tablet.rowSize++;
+ timestamps[row] = time;
+
+ long[] sensor1 = (long[]) values[0];
+ sensor1[row] = new SecureRandom().nextLong();
+
+ int[] sensor2 = (int[]) values[1];
+ sensor2[row] = new SecureRandom().nextInt();
+
+ // mark this point as null value
+ if (time % 5 == 0) {
+ bitMaps[1].mark(row);
+ }
+
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertAlignedTablet(tablet, true);
+ tablet.reset();
+ bitMaps[1].reset();
+ }
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertAlignedTablet(tablet, true);
+ tablet.reset();
+ }
+
+ session.executeNonQueryStatement(FLUSH);
+ }
+
+ private static void insertAlignedRecord()
+ throws IoTDBConnectionException, StatementExecutionException {
+ // first file we have both sensots' data
+ List<String> measurements = new ArrayList<>();
+ List<TSDataType> types = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT32);
+
+ for (long time = 0; time < 10; time++) {
+ List<Object> values = new ArrayList<>();
+ values.add(time);
+ values.add((int) time);
+ session.insertAlignedRecord(ROOT_SG1_D1, time, measurements, types, values);
+ }
+ session.executeNonQueryStatement(FLUSH);
+ // second file we only have s1's data
+ measurements.clear();
+ types.clear();
+ measurements.add("s1");
+ types.add(TSDataType.INT64);
+ for (long time = 10; time < 20; time++) {
+ List<Object> values = new ArrayList<>();
+ values.add(time);
+ session.insertAlignedRecord(ROOT_SG1_D1, time, measurements, types, values);
+ }
+ }
+
+ private static void insertAlignedStringRecord()
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+
+ for (long time = 0; time < 1; time++) {
+ List<String> values = new ArrayList<>();
+ values.add("3");
+ values.add("4");
+ session.insertAlignedRecord(ROOT_SG2_D1_VECTOR5, time, measurements, values);
+ }
+ }
+
+ private static void insertAlignedRecords()
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<String> deviceIds = new ArrayList<>();
+ List<List<String>> measurementsList = new ArrayList<>();
+ List<List<TSDataType>> typeList = new ArrayList<>();
+ List<Long> times = new ArrayList<>();
+ List<List<Object>> valueList = new ArrayList<>();
+
+ for (long time = 1; time < 5; time++) {
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+
+ List<TSDataType> types = new ArrayList<>();
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT32);
+
+ List<Object> values = new ArrayList<>();
+ values.add(1L);
+ values.add(2);
+
+ deviceIds.add(ROOT_SG2_D1_VECTOR4);
+ times.add(time);
+ measurementsList.add(measurements);
+ typeList.add(types);
+ valueList.add(values);
+ }
+ session.insertAlignedRecords(deviceIds, times, measurementsList, typeList, valueList);
+ }
+
+ private static void insertAlignedStringRecords()
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<String> deviceIds = new ArrayList<>();
+ List<List<String>> measurementsList = new ArrayList<>();
+ List<Long> times = new ArrayList<>();
+ List<List<String>> valueList = new ArrayList<>();
+
+ for (long time = 1; time < 5; time++) {
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+
+ List<String> values = new ArrayList<>();
+ values.add("3");
+ values.add("4");
+
+ deviceIds.add(ROOT_SG2_D1_VECTOR5);
+ times.add(time);
+ measurementsList.add(measurements);
+ valueList.add(values);
+ }
+ session.insertAlignedRecords(deviceIds, times, measurementsList, valueList);
+ }
+
+ private static void insertAlignedRecordsOfOneDevice()
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<List<String>> measurementsList = new ArrayList<>();
+ List<List<TSDataType>> typeList = new ArrayList<>();
+ List<Long> times = new ArrayList<>();
+ List<List<Object>> valueList = new ArrayList<>();
+
+ for (long time = 10; time < 15; time++) {
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+
+ List<TSDataType> types = new ArrayList<>();
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT32);
+
+ List<Object> values = new ArrayList<>();
+ values.add(1L);
+ values.add(2);
+
+ times.add(time);
+ measurementsList.add(measurements);
+ typeList.add(types);
+ valueList.add(values);
+ }
+ session.insertAlignedRecordsOfOneDevice(
+ ROOT_SG2_D1_VECTOR4, times, measurementsList, typeList, valueList);
+ }
+
+ private static void insertTabletsWithAlignedTimeseries()
+ throws IoTDBConnectionException, StatementExecutionException {
+
+ List<IMeasurementSchema> schemaList1 = new ArrayList<>();
+ schemaList1.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList1.add(new MeasurementSchema("s2", TSDataType.INT64));
+
+ List<IMeasurementSchema> schemaList2 = new ArrayList<>();
+ schemaList2.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList2.add(new MeasurementSchema("s2", TSDataType.INT64));
+
+ List<IMeasurementSchema> schemaList3 = new ArrayList<>();
+ schemaList3.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList3.add(new MeasurementSchema("s2", TSDataType.INT64));
+
+ Tablet tablet1 = new Tablet(ROOT_SG2_D1_VECTOR6, schemaList1, 100);
+ Tablet tablet2 = new Tablet(ROOT_SG2_D1_VECTOR7, schemaList2, 100);
+ Tablet tablet3 = new Tablet(ROOT_SG2_D1_VECTOR8, schemaList3, 100);
+
+ Map<String, Tablet> tabletMap = new HashMap<>();
+ tabletMap.put(ROOT_SG2_D1_VECTOR6, tablet1);
+ tabletMap.put(ROOT_SG2_D1_VECTOR7, tablet2);
+ tabletMap.put(ROOT_SG2_D1_VECTOR8, tablet3);
+
+ // Method 1 to add tablet data
+ long timestamp = System.currentTimeMillis();
+ for (long row = 0; row < 100; row++) {
+ int row1 = tablet1.rowSize++;
+ int row2 = tablet2.rowSize++;
+ int row3 = tablet3.rowSize++;
+ tablet1.addTimestamp(row1, timestamp);
+ tablet2.addTimestamp(row2, timestamp);
+ tablet3.addTimestamp(row3, timestamp);
+ for (int i = 0; i < 2; i++) {
+ long value = new SecureRandom().nextLong();
+ tablet1.addValue(schemaList1.get(i).getMeasurementId(), row1, value);
+ tablet2.addValue(schemaList2.get(i).getMeasurementId(), row2, value);
+ tablet3.addValue(schemaList3.get(i).getMeasurementId(), row3, value);
+ }
+ if (tablet1.rowSize == tablet1.getMaxRowNumber()) {
+ session.insertAlignedTablets(tabletMap, true);
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet1.rowSize != 0) {
+ session.insertAlignedTablets(tabletMap, true);
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+
+ // Method 2 to add tablet data
+ long[] timestamps1 = tablet1.timestamps;
+ Object[] values1 = tablet1.values;
+ long[] timestamps2 = tablet2.timestamps;
+ Object[] values2 = tablet2.values;
+ long[] timestamps3 = tablet3.timestamps;
+ Object[] values3 = tablet3.values;
+
+ for (long time = 0; time < 100; time++) {
+ int row1 = tablet1.rowSize++;
+ int row2 = tablet2.rowSize++;
+ int row3 = tablet3.rowSize++;
+ timestamps1[row1] = time;
+ timestamps2[row2] = time;
+ timestamps3[row3] = time;
+ for (int i = 0; i < 2; i++) {
+ long[] sensor1 = (long[]) values1[i];
+ sensor1[row1] = i;
+ long[] sensor2 = (long[]) values2[i];
+ sensor2[row2] = i;
+ long[] sensor3 = (long[]) values3[i];
+ sensor3[row3] = i;
+ }
+ if (tablet1.rowSize == tablet1.getMaxRowNumber()) {
+ session.insertAlignedTablets(tabletMap, true);
+
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+ }
+
+ if (tablet1.rowSize != 0) {
+ session.insertAlignedTablets(tabletMap, true);
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/DataMigrationExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/DataMigrationExample.java
new file mode 100644
index 00000000000..288ed7eaa03
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/DataMigrationExample.java
@@ -0,0 +1,211 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.commons.path.MeasurementPath;
+import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.isession.SessionDataSet.DataIterator;
+import org.apache.iotdb.isession.pool.SessionDataSetWrapper;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.pool.SessionPool;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.write.record.Tablet;
+import org.apache.tsfile.write.schema.IMeasurementSchema;
+import org.apache.tsfile.write.schema.MeasurementSchema;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.Future;
+
+/**
+ * Migrate all data belongs to a path from one IoTDB to another IoTDB Each thread migrate one
+ * series, the concurrent thread can be configured by CONCURRENCY
+ *
+ * <p>This example is migrating all timeseries from a local IoTDB with 6667 port to a local IoTDB
+ * with 6668 port
+ */
+public class DataMigrationExample {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(DataMigrationExample.class);
+
+ // used to read data from the source IoTDB
+ private static SessionPool readerPool;
+ // used to write data into the destination IoTDB
+ private static SessionPool writerPool;
+ // concurrent thread of loading timeseries data
+ private static final int CONCURRENCY = 5;
+
+ public static void main(String[] args)
+ throws IoTDBConnectionException,
+ StatementExecutionException,
+ ExecutionException,
+ InterruptedException {
+
+ // the thread used for dataMigration must be smaller than session pool size
+ ExecutorService executorService = Executors.newFixedThreadPool(CONCURRENCY);
+
+ String path = "root.**";
+
+ if (args.length != 0) {
+ path = args[0];
+ }
+
+ readerPool = new SessionPool("127.0.0.1", 6667, "root", "root", CONCURRENCY);
+ writerPool = new SessionPool("127.0.0.1", 6668, "root", "root", CONCURRENCY);
+
+ SessionDataSetWrapper deviceDataSet = readerPool.executeQueryStatement("count devices " + path);
+ DataIterator deviceIter = deviceDataSet.iterator();
+ int total;
+ if (deviceIter.next()) {
+ total = deviceIter.getInt(1);
+ LOGGER.info("Total devices: {}", total);
+ } else {
+ LOGGER.error("Can not get devices schema");
+ System.exit(1);
+ }
+ readerPool.closeResultSet(deviceDataSet);
+
+ deviceDataSet = readerPool.executeQueryStatement("show devices " + path);
+ deviceIter = deviceDataSet.iterator();
+
+ List<Future<Void>> futureList = new ArrayList<>();
+ int count = 0;
+ while (deviceIter.next()) {
+ count++;
+ Future<Void> future =
+ executorService.submit(new LoadThread(count, deviceIter.getString("Device")));
+ futureList.add(future);
+ }
+ readerPool.closeResultSet(deviceDataSet);
+
+ for (Future<Void> future : futureList) {
+ future.get();
+ }
+ executorService.shutdown();
+
+ readerPool.close();
+ writerPool.close();
+ }
+
+ static class LoadThread implements Callable<Void> {
+
+ String device;
+ Tablet tablet;
+ int i;
+
+ public LoadThread(int i, String device) {
+ this.i = i;
+ this.device = device;
+ }
+
+ @Override
+ public Void call() {
+ SessionDataSetWrapper dataSet = null;
+ long startTime = System.currentTimeMillis();
+ try {
+ dataSet = readerPool.executeQueryStatement(String.format("select * from %s", device));
+ DataIterator dataIter = dataSet.iterator();
+ List<String> columnNameList = dataIter.getColumnNameList();
+ List<String> columnTypeList = dataIter.getColumnTypeList();
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ for (int j = 1; j < columnNameList.size(); j++) {
+ PartialPath currentPath = new MeasurementPath(columnNameList.get(j));
+ schemaList.add(
+ new MeasurementSchema(
+ currentPath.getMeasurement(), TSDataType.valueOf(columnTypeList.get(j))));
+ }
+ tablet = new Tablet(device, schemaList, 300000);
+ while (dataIter.next()) {
+ int row = tablet.rowSize++;
+ tablet.timestamps[row] = dataIter.getLong(1);
+ for (int j = 0; j < schemaList.size(); ++j) {
+ if (dataIter.isNull(j + 2)) {
+ tablet.addValue(schemaList.get(j).getMeasurementId(), row, null);
+ continue;
+ }
+ switch (schemaList.get(j).getType()) {
+ case BOOLEAN:
+ tablet.addValue(
+ schemaList.get(j).getMeasurementId(), row, dataIter.getBoolean(j + 2));
+ break;
+ case INT32:
+ tablet.addValue(schemaList.get(j).getMeasurementId(), row, dataIter.getInt(j + 2));
+ break;
+ case INT64:
+ case TIMESTAMP:
+ tablet.addValue(schemaList.get(j).getMeasurementId(), row, dataIter.getLong(j + 2));
+ break;
+ case FLOAT:
+ tablet.addValue(
+ schemaList.get(j).getMeasurementId(), row, dataIter.getFloat(j + 2));
+ break;
+ case DOUBLE:
+ tablet.addValue(
+ schemaList.get(j).getMeasurementId(), row, dataIter.getDouble(j + 2));
+ break;
+ case TEXT:
+ case STRING:
+ tablet.addValue(
+ schemaList.get(j).getMeasurementId(), row, dataIter.getString(j + 2));
+ break;
+ case DATE:
+ case BLOB:
+ tablet.addValue(
+ schemaList.get(j).getMeasurementId(), row, dataIter.getObject(j + 2));
+ break;
+ default:
+ LOGGER.info("Migration of this type of data is not supported");
+ }
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ writerPool.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ }
+ if (tablet.rowSize != 0) {
+ writerPool.insertTablet(tablet);
+ tablet.reset();
+ }
+
+ } catch (Exception e) {
+ LOGGER.error("Loading the {}-th device: {} failed {}", i, device, e.getMessage());
+ return null;
+ } finally {
+ if (dataSet != null) {
+ readerPool.closeResultSet(dataSet);
+ }
+ long endTime = System.currentTimeMillis();
+ long totalTime = endTime - startTime;
+ LOGGER.info("migrate device :{} using {} ms", device, totalTime);
+ }
+
+ LOGGER.info("Loading the {}-th device: {} success", i, device);
+ return null;
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/HybridTimeseriesSessionExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/HybridTimeseriesSessionExample.java
new file mode 100644
index 00000000000..63f91072c39
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/HybridTimeseriesSessionExample.java
@@ -0,0 +1,131 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.Session;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.write.record.Tablet;
+import org.apache.tsfile.write.schema.IMeasurementSchema;
+import org.apache.tsfile.write.schema.MeasurementSchema;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * This example shows how to insert and select Hybrid Timeseries by session Hybrid Timeseries
+ * includes Aligned Timeseries and Normal Timeseries
+ */
+public class HybridTimeseriesSessionExample {
+
+ private static final Logger LOGGER =
+ LoggerFactory.getLogger(HybridTimeseriesSessionExample.class);
+
+ private static Session session;
+ private static final String ROOT_SG1_ALIGNEDDEVICE = "root.sg_1.aligned_device";
+ private static final String ROOT_SG1_D1 = "root.sg_1.d1";
+ private static final String ROOT_SG1_D2 = "root.sg_1.d2";
+
+ public static void main(String[] args)
+ throws IoTDBConnectionException, StatementExecutionException {
+ session = new Session("127.0.0.1", 6667, "root", "root");
+ session.open(false);
+
+ // set session fetchSize
+ session.setFetchSize(10000);
+
+ insertRecord(ROOT_SG1_D2, 0, 100);
+ insertTabletWithAlignedTimeseriesMethod(0, 100);
+ insertRecord(ROOT_SG1_D1, 0, 100);
+ session.executeNonQueryStatement("flush");
+ selectTest();
+
+ session.close();
+ }
+
+ private static void selectTest() throws StatementExecutionException, IoTDBConnectionException {
+ SessionDataSet dataSet = session.executeQueryStatement("select ** from root.sg_1");
+ LOGGER.info("columnNames = {}", dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ LOGGER.info("data = {}", dataSet.next());
+ }
+
+ dataSet.closeOperationHandle();
+ }
+
+ /** Method 1 for insert tablet with aligned timeseries */
+ private static void insertTabletWithAlignedTimeseriesMethod(int minTime, int maxTime)
+ throws IoTDBConnectionException, StatementExecutionException {
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT32));
+
+ Tablet tablet = new Tablet(ROOT_SG1_ALIGNEDDEVICE, schemaList);
+ long timestamp = minTime;
+
+ for (long row = minTime; row < maxTime; row++) {
+ int rowIndex = tablet.rowSize++;
+ tablet.addTimestamp(rowIndex, timestamp);
+ tablet.addValue(schemaList.get(0).getMeasurementId(), rowIndex, row * 10 + 1L);
+ tablet.addValue(schemaList.get(1).getMeasurementId(), rowIndex, (int) (row * 10 + 2));
+
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertAlignedTablet(tablet, true);
+ tablet.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertAlignedTablet(tablet);
+ tablet.reset();
+ }
+ }
+
+ private static void insertRecord(String deviceId, int minTime, int maxTime)
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<String> measurements = new ArrayList<>();
+ List<TSDataType> types = new ArrayList<>();
+ measurements.add("s2");
+ measurements.add("s4");
+ measurements.add("s5");
+ measurements.add("s6");
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+
+ for (long time = minTime; time < maxTime; time++) {
+ List<Object> values = new ArrayList<>();
+ values.add(time * 10 + 3L);
+ values.add(time * 10 + 4L);
+ values.add(time * 10 + 5L);
+ values.add(time * 10 + 6L);
+ session.insertRecord(deviceId, time, measurements, types, values);
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionConcurrentExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionConcurrentExample.java
new file mode 100644
index 00000000000..68e2696724d
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionConcurrentExample.java
@@ -0,0 +1,197 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.template.Template;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.Session;
+import org.apache.iotdb.session.template.MeasurementNode;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.file.metadata.enums.CompressionType;
+import org.apache.tsfile.file.metadata.enums.TSEncoding;
+import org.apache.tsfile.write.record.Tablet;
+import org.apache.tsfile.write.schema.IMeasurementSchema;
+import org.apache.tsfile.write.schema.MeasurementSchema;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Random;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+public class SessionConcurrentExample {
+ private static final Logger LOGGER = LoggerFactory.getLogger(SessionConcurrentExample.class);
+
+ private static final int SG_NUM = 20;
+ private static final int DEVICE_NUM = 100;
+ private static final int PARALLEL_DEGREE_FOR_ONE_SG = 3;
+ private static Random random = new Random();
+
+ public static void main(String[] args)
+ throws IoTDBConnectionException, StatementExecutionException, IOException {
+
+ try (Session session = new Session("127.0.0.1", 6667, "root", "root")) {
+ session.open(false);
+ createTemplate(session);
+ } catch (Exception e) {
+ LOGGER.error("create template with Session error", e);
+ }
+
+ CountDownLatch latch = new CountDownLatch(SG_NUM * PARALLEL_DEGREE_FOR_ONE_SG);
+ ExecutorService es = Executors.newFixedThreadPool(SG_NUM * PARALLEL_DEGREE_FOR_ONE_SG);
+
+ for (int i = 0; i < SG_NUM * PARALLEL_DEGREE_FOR_ONE_SG; i++) {
+ int currentIndex = i;
+ es.execute(() -> concurrentOperation(latch, currentIndex));
+ }
+
+ es.shutdown();
+
+ try {
+ latch.await();
+ } catch (InterruptedException e) {
+ LOGGER.warn("CountDownLatch interrupted", e);
+ Thread.currentThread().interrupt();
+ }
+ }
+
+ private static void concurrentOperation(CountDownLatch latch, int currentIndex) {
+
+ Session session = new Session("127.0.0.1", 6667, "root", "root");
+ try {
+ session.open(false);
+ } catch (IoTDBConnectionException e) {
+ LOGGER.error("Open Session error", e);
+ }
+
+ for (int j = 0; j < DEVICE_NUM; j++) {
+ try {
+ insertTablet(
+ session,
+ String.format("root.sg_%d.d_%d", currentIndex / PARALLEL_DEGREE_FOR_ONE_SG, j));
+ } catch (IoTDBConnectionException | StatementExecutionException e) {
+ LOGGER.error("Insert tablet error", e);
+ }
+ }
+
+ try {
+ session.close();
+ } catch (IoTDBConnectionException e) {
+ LOGGER.error("Close session error", e);
+ }
+
+ latch.countDown();
+ }
+
+ private static void createTemplate(Session session)
+ throws IoTDBConnectionException, StatementExecutionException, IOException {
+
+ Template template = new Template("template1", false);
+ MeasurementNode mNodeS1 =
+ new MeasurementNode("s1", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ MeasurementNode mNodeS2 =
+ new MeasurementNode("s2", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ MeasurementNode mNodeS3 =
+ new MeasurementNode("s3", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+
+ template.addToTemplate(mNodeS1);
+ template.addToTemplate(mNodeS2);
+ template.addToTemplate(mNodeS3);
+
+ session.createSchemaTemplate(template);
+ for (int i = 0; i < SG_NUM; i++) {
+ session.setSchemaTemplate("template1", "root.sg_" + i);
+ }
+ }
+
+ /**
+ * insert the data of a device. For each timestamp, the number of measurements is the same.
+ *
+ * <p>Users need to control the count of Tablet and write a batch when it reaches the maxBatchSize
+ */
+ private static void insertTablet(Session session, String deviceId)
+ throws IoTDBConnectionException, StatementExecutionException {
+ /*
+ * A Tablet example:
+ * device1
+ * time s1, s2, s3
+ * 1, 1, 1, 1
+ * 2, 2, 2, 2
+ * 3, 3, 3, 3
+ */
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s3", TSDataType.INT64));
+
+ Tablet tablet = new Tablet(deviceId, schemaList, 100);
+
+ // Method 1 to add tablet data
+ long timestamp = System.currentTimeMillis();
+ for (long row = 0; row < 100; row++) {
+ int rowIndex = tablet.rowSize++;
+ tablet.addTimestamp(rowIndex, timestamp);
+ for (int s = 0; s < 3; s++) {
+ long value = random.nextLong();
+ tablet.addValue(schemaList.get(s).getMeasurementId(), rowIndex, value);
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertTablet(tablet);
+ tablet.reset();
+ }
+
+ // Method 2 to add tablet data
+ long[] timestamps = tablet.timestamps;
+ Object[] values = tablet.values;
+
+ for (long time = 0; time < 100; time++) {
+ int row = tablet.rowSize++;
+ timestamps[row] = time;
+ for (int i = 0; i < 3; i++) {
+ long[] sensor = (long[]) values[i];
+ sensor[row] = i;
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertTablet(tablet);
+ tablet.reset();
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionExample.java
new file mode 100644
index 00000000000..47254abfae6
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionExample.java
@@ -0,0 +1,914 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.common.rpc.thrift.TAggregationType;
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.isession.SessionDataSet.DataIterator;
+import org.apache.iotdb.isession.template.Template;
+import org.apache.iotdb.isession.util.Version;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.rpc.TSStatusCode;
+import org.apache.iotdb.session.Session;
+import org.apache.iotdb.session.template.MeasurementNode;
+
+import org.apache.tsfile.common.conf.TSFileConfig;
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.file.metadata.enums.CompressionType;
+import org.apache.tsfile.file.metadata.enums.TSEncoding;
+import org.apache.tsfile.utils.Binary;
+import org.apache.tsfile.utils.BitMap;
+import org.apache.tsfile.write.record.Tablet;
+import org.apache.tsfile.write.schema.IMeasurementSchema;
+import org.apache.tsfile.write.schema.MeasurementSchema;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Random;
+
+@SuppressWarnings({"squid:S106", "squid:S1144", "squid:S125"})
+public class SessionExample {
+
+ private static Session session;
+ private static Session sessionEnableRedirect;
+ private static final String ROOT_SG1_D1_S1 = "root.sg1.d1.s1";
+ private static final String ROOT_SG1_D1_S2 = "root.sg1.d1.s2";
+ private static final String ROOT_SG1_D1_S3 = "root.sg1.d1.s3";
+ private static final String ROOT_SG1_D1_S4 = "root.sg1.d1.s4";
+ private static final String ROOT_SG1_D1_S5 = "root.sg1.d1.s5";
+ private static final String ROOT_SG1_D1 = "root.sg1.d1";
+ private static final String ROOT_SG1 = "root.sg1";
+ private static final String LOCAL_HOST = "127.0.0.1";
+ public static final String SELECT_D1 = "select * from root.sg1.d1";
+
+ private static Random random = new Random();
+
+ public static void main(String[] args)
+ throws IoTDBConnectionException, StatementExecutionException {
+ session =
+ new Session.Builder()
+ .host(LOCAL_HOST)
+ .port(6667)
+ .username("root")
+ .password("root")
+ .version(Version.V_1_0)
+ .build();
+ session.open(false);
+
+ // set session fetchSize
+ session.setFetchSize(10000);
+
+ try {
+ session.createDatabase("root.sg1");
+ } catch (StatementExecutionException e) {
+ if (e.getStatusCode() != TSStatusCode.DATABASE_ALREADY_EXISTS.getStatusCode()) {
+ throw e;
+ }
+ }
+
+ // createTemplate();
+ createTimeseries();
+ createMultiTimeseries();
+ insertRecord();
+ insertTablet();
+ // insertTabletWithNullValues();
+ // insertTablets();
+ // insertRecords();
+ // insertText();
+ // selectInto();
+ // createAndDropContinuousQueries();
+ // nonQuery();
+ query();
+ // queryWithTimeout();
+ rawDataQuery();
+ lastDataQuery();
+ aggregationQuery();
+ groupByQuery();
+ // queryByIterator();
+ // deleteData();
+ // deleteTimeseries();
+ // setTimeout();
+
+ sessionEnableRedirect = new Session(LOCAL_HOST, 6667, "root", "root");
+ sessionEnableRedirect.setEnableQueryRedirection(true);
+ sessionEnableRedirect.open(false);
+
+ // set session fetchSize
+ sessionEnableRedirect.setFetchSize(10000);
+
+ fastLastDataQueryForOneDevice();
+ insertRecord4Redirect();
+ query4Redirect();
+ sessionEnableRedirect.close();
+ session.close();
+ }
+
+ private static void createAndDropContinuousQueries()
+ throws StatementExecutionException, IoTDBConnectionException {
+ session.executeNonQueryStatement(
+ "CREATE CONTINUOUS QUERY cq1 "
+ + "BEGIN SELECT max_value(s1) INTO temperature_max FROM root.sg1.* "
+ + "GROUP BY time(10s) END");
+ session.executeNonQueryStatement(
+ "CREATE CONTINUOUS QUERY cq2 "
+ + "BEGIN SELECT count(s2) INTO temperature_cnt FROM root.sg1.* "
+ + "GROUP BY time(10s), level=1 END");
+ session.executeNonQueryStatement(
+ "CREATE CONTINUOUS QUERY cq3 "
+ + "RESAMPLE EVERY 20s FOR 20s "
+ + "BEGIN SELECT avg(s3) INTO temperature_avg FROM root.sg1.* "
+ + "GROUP BY time(10s), level=1 END");
+ session.executeNonQueryStatement("DROP CONTINUOUS QUERY cq1");
+ session.executeNonQueryStatement("DROP CONTINUOUS QUERY cq2");
+ session.executeNonQueryStatement("DROP CONTINUOUS QUERY cq3");
+ }
+
+ private static void createTimeseries()
+ throws IoTDBConnectionException, StatementExecutionException {
+
+ if (!session.checkTimeseriesExists(ROOT_SG1_D1_S1)) {
+ session.createTimeseries(
+ ROOT_SG1_D1_S1, TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ }
+ if (!session.checkTimeseriesExists(ROOT_SG1_D1_S2)) {
+ session.createTimeseries(
+ ROOT_SG1_D1_S2, TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ }
+ if (!session.checkTimeseriesExists(ROOT_SG1_D1_S3)) {
+ session.createTimeseries(
+ ROOT_SG1_D1_S3, TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ }
+
+ // create timeseries with tags and attributes
+ if (!session.checkTimeseriesExists(ROOT_SG1_D1_S4)) {
+ Map<String, String> tags = new HashMap<>();
+ tags.put("tag1", "v1");
+ Map<String, String> attributes = new HashMap<>();
+ attributes.put("description", "v1");
+ session.createTimeseries(
+ ROOT_SG1_D1_S4,
+ TSDataType.INT64,
+ TSEncoding.RLE,
+ CompressionType.SNAPPY,
+ null,
+ tags,
+ attributes,
+ "temperature");
+ }
+
+ // create timeseries with SDT property, SDT will take place when flushing
+ if (!session.checkTimeseriesExists(ROOT_SG1_D1_S5)) {
+ // COMPDEV is required
+ // COMPMAXTIME and COMPMINTIME are optional and their unit is ms
+ Map<String, String> props = new HashMap<>();
+ props.put("LOSS", "sdt");
+ props.put("COMPDEV", "0.01");
+ props.put("COMPMINTIME", "2");
+ props.put("COMPMAXTIME", "10");
+ session.createTimeseries(
+ ROOT_SG1_D1_S5,
+ TSDataType.INT64,
+ TSEncoding.RLE,
+ CompressionType.SNAPPY,
+ props,
+ null,
+ null,
+ null);
+ }
+ }
+
+ private static void createMultiTimeseries()
+ throws IoTDBConnectionException, StatementExecutionException {
+
+ if (!session.checkTimeseriesExists("root.sg1.d2.s1")
+ && !session.checkTimeseriesExists("root.sg1.d2.s2")) {
+ List<String> paths = new ArrayList<>();
+ paths.add("root.sg1.d2.s1");
+ paths.add("root.sg1.d2.s2");
+ List<TSDataType> tsDataTypes = new ArrayList<>();
+ tsDataTypes.add(TSDataType.INT64);
+ tsDataTypes.add(TSDataType.INT64);
+ List<TSEncoding> tsEncodings = new ArrayList<>();
+ tsEncodings.add(TSEncoding.RLE);
+ tsEncodings.add(TSEncoding.RLE);
+ List<CompressionType> compressionTypes = new ArrayList<>();
+ compressionTypes.add(CompressionType.SNAPPY);
+ compressionTypes.add(CompressionType.SNAPPY);
+
+ List<Map<String, String>> tagsList = new ArrayList<>();
+ Map<String, String> tags = new HashMap<>();
+ tags.put("unit", "kg");
+ tagsList.add(tags);
+ tagsList.add(tags);
+
+ List<Map<String, String>> attributesList = new ArrayList<>();
+ Map<String, String> attributes = new HashMap<>();
+ attributes.put("minValue", "1");
+ attributes.put("maxValue", "100");
+ attributesList.add(attributes);
+ attributesList.add(attributes);
+
+ List<String> alias = new ArrayList<>();
+ alias.add("weight1");
+ alias.add("weight2");
+
+ session.createMultiTimeseries(
+ paths, tsDataTypes, tsEncodings, compressionTypes, null, tagsList, attributesList, alias);
+ }
+ }
+
+ private static void createTemplate()
+ throws IoTDBConnectionException, StatementExecutionException, IOException {
+
+ Template template = new Template("template1", false);
+ MeasurementNode mNodeS1 =
+ new MeasurementNode("s1", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ MeasurementNode mNodeS2 =
+ new MeasurementNode("s2", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+ MeasurementNode mNodeS3 =
+ new MeasurementNode("s3", TSDataType.INT64, TSEncoding.RLE, CompressionType.SNAPPY);
+
+ template.addToTemplate(mNodeS1);
+ template.addToTemplate(mNodeS2);
+ template.addToTemplate(mNodeS3);
+
+ session.createSchemaTemplate(template);
+ session.setSchemaTemplate("template1", "root.sg1");
+ }
+
+ private static void insertRecord() throws IoTDBConnectionException, StatementExecutionException {
+ String deviceId = ROOT_SG1_D1;
+ List<String> measurements = new ArrayList<>();
+ List<TSDataType> types = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ measurements.add("s3");
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+
+ for (long time = 0; time < 100; time++) {
+ List<Object> values = new ArrayList<>();
+ values.add(1L);
+ values.add(2L);
+ values.add(3L);
+ session.insertRecord(deviceId, time, measurements, types, values);
+ }
+ }
+
+ private static void insertRecord4Redirect()
+ throws IoTDBConnectionException, StatementExecutionException {
+ for (int i = 0; i < 6; i++) {
+ for (int j = 0; j < 2; j++) {
+ String deviceId = "root.redirect" + i + ".d" + j;
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ measurements.add("s3");
+ List<TSDataType> types = new ArrayList<>();
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+
+ for (long time = 0; time < 5; time++) {
+ List<Object> values = new ArrayList<>();
+ values.add(1L + time);
+ values.add(2L + time);
+ values.add(3L + time);
+ session.insertRecord(deviceId, time, measurements, types, values);
+ }
+ }
+ }
+ }
+
+ private static void insertStrRecord()
+ throws IoTDBConnectionException, StatementExecutionException {
+ String deviceId = ROOT_SG1_D1;
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ measurements.add("s3");
+
+ for (long time = 0; time < 10; time++) {
+ List<String> values = new ArrayList<>();
+ values.add("1");
+ values.add("2");
+ values.add("3");
+ session.insertRecord(deviceId, time, measurements, values);
+ }
+ }
+
+ private static void insertRecordInObject()
+ throws IoTDBConnectionException, StatementExecutionException {
+ String deviceId = ROOT_SG1_D1;
+ List<String> measurements = new ArrayList<>();
+ List<TSDataType> types = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ measurements.add("s3");
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+
+ for (long time = 0; time < 100; time++) {
+ session.insertRecord(deviceId, time, measurements, types, 1L, 1L, 1L);
+ }
+ }
+
+ private static void insertRecords() throws IoTDBConnectionException, StatementExecutionException {
+ String deviceId = ROOT_SG1_D1;
+ List<String> measurements = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ measurements.add("s3");
+ List<String> deviceIds = new ArrayList<>();
+ List<List<String>> measurementsList = new ArrayList<>();
+ List<List<Object>> valuesList = new ArrayList<>();
+ List<Long> timestamps = new ArrayList<>();
+ List<List<TSDataType>> typesList = new ArrayList<>();
+
+ for (long time = 0; time < 500; time++) {
+ List<Object> values = new ArrayList<>();
+ List<TSDataType> types = new ArrayList<>();
+ values.add(1L);
+ values.add(2L);
+ values.add(3L);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+
+ deviceIds.add(deviceId);
+ measurementsList.add(measurements);
+ valuesList.add(values);
+ typesList.add(types);
+ timestamps.add(time);
+ if (time != 0 && time % 100 == 0) {
+ session.insertRecords(deviceIds, timestamps, measurementsList, typesList, valuesList);
+ deviceIds.clear();
+ measurementsList.clear();
+ valuesList.clear();
+ typesList.clear();
+ timestamps.clear();
+ }
+ }
+
+ session.insertRecords(deviceIds, timestamps, measurementsList, typesList, valuesList);
+ }
+
+ /**
+ * insert the data of a device. For each timestamp, the number of measurements is the same.
+ *
+ * <p>Users need to control the count of Tablet and write a batch when it reaches the maxBatchSize
+ */
+ private static void insertTablet() throws IoTDBConnectionException, StatementExecutionException {
+ /*
+ * A Tablet example:
+ * device1
+ * time s1, s2, s3
+ * 1, 1, 1, 1
+ * 2, 2, 2, 2
+ * 3, 3, 3, 3
+ */
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s3", TSDataType.INT64));
+
+ Tablet tablet = new Tablet(ROOT_SG1_D1, schemaList, 100);
+
+ // Method 1 to add tablet data
+ long timestamp = System.currentTimeMillis();
+
+ for (long row = 0; row < 100; row++) {
+ int rowIndex = tablet.rowSize++;
+ tablet.addTimestamp(rowIndex, timestamp);
+ for (int s = 0; s < 3; s++) {
+ long value = random.nextLong();
+ tablet.addValue(schemaList.get(s).getMeasurementId(), rowIndex, value);
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertTablet(tablet);
+ tablet.reset();
+ }
+
+ // Method 2 to add tablet data
+ long[] timestamps = tablet.timestamps;
+ Object[] values = tablet.values;
+
+ for (long time = 0; time < 100; time++) {
+ int row = tablet.rowSize++;
+ timestamps[row] = time;
+ for (int i = 0; i < 3; i++) {
+ long[] sensor = (long[]) values[i];
+ sensor[row] = i;
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertTablet(tablet);
+ tablet.reset();
+ }
+ }
+
+ private static void insertTabletWithNullValues()
+ throws IoTDBConnectionException, StatementExecutionException {
+ /*
+ * A Tablet example:
+ * device1
+ * time s1, s2, s3
+ * 1, null, 1, 1
+ * 2, 2, null, 2
+ * 3, 3, 3, null
+ */
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s3", TSDataType.INT64));
+
+ Tablet tablet = new Tablet(ROOT_SG1_D1, schemaList, 100);
+
+ // Method 1 to add tablet data
+ insertTablet1(schemaList, tablet);
+
+ // Method 2 to add tablet data
+ insertTablet2(schemaList, tablet);
+ }
+
+ private static void insertTablet1(List<IMeasurementSchema> schemaList, Tablet tablet)
+ throws IoTDBConnectionException, StatementExecutionException {
+ tablet.initBitMaps();
+
+ long timestamp = System.currentTimeMillis();
+ for (long row = 0; row < 100; row++) {
+ int rowIndex = tablet.rowSize++;
+ tablet.addTimestamp(rowIndex, timestamp);
+ for (int s = 0; s < 3; s++) {
+ long value = random.nextLong();
+ // mark null value
+ if (row % 3 == s) {
+ tablet.bitMaps[s].mark((int) row);
+ }
+ tablet.addValue(schemaList.get(s).getMeasurementId(), rowIndex, value);
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertTablet(tablet);
+ tablet.reset();
+ }
+ }
+
+ private static void insertTablet2(List<IMeasurementSchema> schemaList, Tablet tablet)
+ throws IoTDBConnectionException, StatementExecutionException {
+ long[] timestamps = tablet.timestamps;
+ Object[] values = tablet.values;
+ BitMap[] bitMaps = new BitMap[schemaList.size()];
+ for (int s = 0; s < 3; s++) {
+ bitMaps[s] = new BitMap(tablet.getMaxRowNumber());
+ }
+ tablet.bitMaps = bitMaps;
+
+ for (long time = 0; time < 100; time++) {
+ int row = tablet.rowSize++;
+ timestamps[row] = time;
+ for (int i = 0; i < 3; i++) {
+ long[] sensor = (long[]) values[i];
+ // mark null value
+ if (row % 3 == i) {
+ bitMaps[i].mark(row);
+ }
+ sensor[row] = i;
+ }
+ if (tablet.rowSize == tablet.getMaxRowNumber()) {
+ session.insertTablet(tablet, true);
+ tablet.reset();
+ }
+ }
+
+ if (tablet.rowSize != 0) {
+ session.insertTablet(tablet);
+ tablet.reset();
+ }
+ }
+
+ private static void insertTablets() throws IoTDBConnectionException, StatementExecutionException {
+ // The schema of measurements of one device
+ // only measurementId and data type in MeasurementSchema take effects in Tablet
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s1", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s2", TSDataType.INT64));
+ schemaList.add(new MeasurementSchema("s3", TSDataType.INT64));
+
+ Tablet tablet1 = new Tablet(ROOT_SG1_D1, schemaList, 100);
+ Tablet tablet2 = new Tablet("root.sg1.d2", schemaList, 100);
+ Tablet tablet3 = new Tablet("root.sg1.d3", schemaList, 100);
+
+ Map<String, Tablet> tabletMap = new HashMap<>();
+ tabletMap.put(ROOT_SG1_D1, tablet1);
+ tabletMap.put("root.sg1.d2", tablet2);
+ tabletMap.put("root.sg1.d3", tablet3);
+
+ // Method 1 to add tablet data
+ long timestamp = System.currentTimeMillis();
+ for (long row = 0; row < 100; row++) {
+ int row1 = tablet1.rowSize++;
+ int row2 = tablet2.rowSize++;
+ int row3 = tablet3.rowSize++;
+ tablet1.addTimestamp(row1, timestamp);
+ tablet2.addTimestamp(row2, timestamp);
+ tablet3.addTimestamp(row3, timestamp);
+ for (int i = 0; i < 3; i++) {
+ long value = random.nextLong();
+ tablet1.addValue(schemaList.get(i).getMeasurementId(), row1, value);
+ tablet2.addValue(schemaList.get(i).getMeasurementId(), row2, value);
+ tablet3.addValue(schemaList.get(i).getMeasurementId(), row3, value);
+ }
+ if (tablet1.rowSize == tablet1.getMaxRowNumber()) {
+ session.insertTablets(tabletMap, true);
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+ timestamp++;
+ }
+
+ if (tablet1.rowSize != 0) {
+ session.insertTablets(tabletMap, true);
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+
+ // Method 2 to add tablet data
+ long[] timestamps1 = tablet1.timestamps;
+ Object[] values1 = tablet1.values;
+ long[] timestamps2 = tablet2.timestamps;
+ Object[] values2 = tablet2.values;
+ long[] timestamps3 = tablet3.timestamps;
+ Object[] values3 = tablet3.values;
+
+ for (long time = 0; time < 100; time++) {
+ int row1 = tablet1.rowSize++;
+ int row2 = tablet2.rowSize++;
+ int row3 = tablet3.rowSize++;
+ timestamps1[row1] = time;
+ timestamps2[row2] = time;
+ timestamps3[row3] = time;
+ for (int i = 0; i < 3; i++) {
+ long[] sensor1 = (long[]) values1[i];
+ sensor1[row1] = i;
+ long[] sensor2 = (long[]) values2[i];
+ sensor2[row2] = i;
+ long[] sensor3 = (long[]) values3[i];
+ sensor3[row3] = i;
+ }
+ if (tablet1.rowSize == tablet1.getMaxRowNumber()) {
+ session.insertTablets(tabletMap, true);
+
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+ }
+
+ if (tablet1.rowSize != 0) {
+ session.insertTablets(tabletMap, true);
+ tablet1.reset();
+ tablet2.reset();
+ tablet3.reset();
+ }
+ }
+
+ /**
+ * This example shows how to insert data of TSDataType.TEXT. You can use the session interface to
+ * write data of String type or Binary type.
+ */
+ private static void insertText() throws IoTDBConnectionException, StatementExecutionException {
+ String device = "root.sg1.text";
+ // the first data is String type and the second data is Binary type
+ List<Object> datas = Arrays.asList("String", new Binary("Binary", TSFileConfig.STRING_CHARSET));
+ // insertRecord example
+ for (int i = 0; i < datas.size(); i++) {
+ // write data of String type or Binary type
+ session.insertRecord(
+ device,
+ i,
+ Collections.singletonList("s1"),
+ Collections.singletonList(TSDataType.TEXT),
+ datas.get(i));
+ }
+
+ // insertTablet example
+ List<IMeasurementSchema> schemaList = new ArrayList<>();
+ schemaList.add(new MeasurementSchema("s2", TSDataType.TEXT));
+ Tablet tablet = new Tablet(device, schemaList, 100);
+ for (int i = 0; i < datas.size(); i++) {
+ int rowIndex = tablet.rowSize++;
+ tablet.addTimestamp(rowIndex, i);
+ // write data of String type or Binary type
+ tablet.addValue(schemaList.get(0).getMeasurementId(), rowIndex, datas.get(i));
+ }
+ session.insertTablet(tablet);
+ try (SessionDataSet dataSet = session.executeQueryStatement("select s1, s2 from " + device)) {
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ private static void selectInto() throws IoTDBConnectionException, StatementExecutionException {
+ session.executeNonQueryStatement(
+ "select s1, s2, s3 into into_s1, into_s2, into_s3 from root.sg1.d1");
+
+ try (SessionDataSet dataSet =
+ session.executeQueryStatement("select into_s1, into_s2, into_s3 from root.sg1.d1")) {
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ private static void deleteData() throws IoTDBConnectionException, StatementExecutionException {
+ String path = ROOT_SG1_D1_S1;
+ long deleteTime = 99;
+ session.deleteData(path, deleteTime);
+ }
+
+ private static void deleteTimeseries()
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<String> paths = new ArrayList<>();
+ paths.add(ROOT_SG1_D1_S1);
+ paths.add(ROOT_SG1_D1_S2);
+ paths.add(ROOT_SG1_D1_S3);
+ session.deleteTimeseries(paths);
+ }
+
+ private static void query() throws IoTDBConnectionException, StatementExecutionException {
+ try (SessionDataSet dataSet = session.executeQueryStatement(SELECT_D1)) {
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ private static void query4Redirect()
+ throws IoTDBConnectionException, StatementExecutionException {
+ String selectPrefix = "select * from root.redirect";
+ for (int i = 0; i < 6; i++) {
+ try (SessionDataSet dataSet =
+ sessionEnableRedirect.executeQueryStatement(selectPrefix + i + ".d1")) {
+
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ for (int i = 0; i < 6; i++) {
+ try (SessionDataSet dataSet =
+ sessionEnableRedirect.executeQueryStatement(
+ selectPrefix + i + ".d1 where time >= 1 and time < 10")) {
+
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ for (int i = 0; i < 6; i++) {
+ try (SessionDataSet dataSet =
+ sessionEnableRedirect.executeQueryStatement(
+ selectPrefix + i + ".d1 where time >= 1 and time < 10 align by device")) {
+
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ for (int i = 0; i < 6; i++) {
+ try (SessionDataSet dataSet =
+ sessionEnableRedirect.executeQueryStatement(
+ selectPrefix
+ + i
+ + ".d1 where time >= 1 and time < 10 and root.redirect"
+ + i
+ + ".d1.s1 > 1")) {
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+ }
+
+ private static void queryWithTimeout()
+ throws IoTDBConnectionException, StatementExecutionException {
+ try (SessionDataSet dataSet = session.executeQueryStatement(SELECT_D1, 2000)) {
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ private static void rawDataQuery() throws IoTDBConnectionException, StatementExecutionException {
+ List<String> paths = new ArrayList<>();
+ paths.add(ROOT_SG1_D1_S1);
+ paths.add(ROOT_SG1_D1_S2);
+ paths.add(ROOT_SG1_D1_S3);
+ long startTime = 10L;
+ long endTime = 200L;
+ long timeOut = 60000;
+
+ try (SessionDataSet dataSet = session.executeRawDataQuery(paths, startTime, endTime, timeOut)) {
+
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024);
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+
+ private static void lastDataQuery() throws IoTDBConnectionException, StatementExecutionException {
+ List<String> paths = new ArrayList<>();
+ paths.add(ROOT_SG1_D1_S1);
+ paths.add(ROOT_SG1_D1_S2);
+ paths.add(ROOT_SG1_D1_S3);
+ try (SessionDataSet sessionDataSet = session.executeLastDataQuery(paths, 3, 60000)) {
+ System.out.println(sessionDataSet.getColumnNames());
+ sessionDataSet.setFetchSize(1024);
+ while (sessionDataSet.hasNext()) {
+ System.out.println(sessionDataSet.next());
+ }
+ }
+ }
+
+ private static void fastLastDataQueryForOneDevice()
+ throws IoTDBConnectionException, StatementExecutionException {
+ System.out.println("-------fastLastQuery------");
+ List<String> paths = new ArrayList<>();
+ paths.add("s1");
+ paths.add("s2");
+ paths.add("s3");
+ try (SessionDataSet sessionDataSet =
+ sessionEnableRedirect.executeLastDataQueryForOneDevice(
+ ROOT_SG1, ROOT_SG1_D1, paths, true)) {
+ System.out.println(sessionDataSet.getColumnNames());
+ sessionDataSet.setFetchSize(1024);
+ while (sessionDataSet.hasNext()) {
+ System.out.println(sessionDataSet.next());
+ }
+ }
+ }
+
+ private static void aggregationQuery()
+ throws IoTDBConnectionException, StatementExecutionException {
+ List<String> paths = new ArrayList<>();
+ paths.add(ROOT_SG1_D1_S1);
+ paths.add(ROOT_SG1_D1_S2);
+ paths.add(ROOT_SG1_D1_S3);
+
+ List<TAggregationType> aggregations = new ArrayList<>();
+ aggregations.add(TAggregationType.COUNT);
+ aggregations.add(TAggregationType.SUM);
+ aggregations.add(TAggregationType.MAX_VALUE);
+ try (SessionDataSet sessionDataSet = session.executeAggregationQuery(paths, aggregations)) {
+ System.out.println(sessionDataSet.getColumnNames());
+ sessionDataSet.setFetchSize(1024);
+ while (sessionDataSet.hasNext()) {
+ System.out.println(sessionDataSet.next());
+ }
+ }
+ }
+
+ private static void groupByQuery() throws IoTDBConnectionException, StatementExecutionException {
+ List<String> paths = new ArrayList<>();
+ paths.add(ROOT_SG1_D1_S1);
+ paths.add(ROOT_SG1_D1_S2);
+ paths.add(ROOT_SG1_D1_S3);
+
+ List<TAggregationType> aggregations = new ArrayList<>();
+ aggregations.add(TAggregationType.COUNT);
+ aggregations.add(TAggregationType.SUM);
+ aggregations.add(TAggregationType.MAX_VALUE);
+ try (SessionDataSet sessionDataSet =
+ session.executeAggregationQuery(paths, aggregations, 0, 100, 10, 20)) {
+ System.out.println(sessionDataSet.getColumnNames());
+ sessionDataSet.setFetchSize(1024);
+ while (sessionDataSet.hasNext()) {
+ System.out.println(sessionDataSet.next());
+ }
+ }
+ }
+
+ private static void queryByIterator()
+ throws IoTDBConnectionException, StatementExecutionException {
+ try (SessionDataSet dataSet = session.executeQueryStatement(SELECT_D1)) {
+
+ DataIterator iterator = dataSet.iterator();
+ System.out.println(dataSet.getColumnNames());
+ dataSet.setFetchSize(1024); // default is 10000
+ while (iterator.next()) {
+ StringBuilder builder = new StringBuilder();
+ // get time
+ builder.append(iterator.getLong(1)).append(",");
+ // get second column
+ if (!iterator.isNull(2)) {
+ builder.append(iterator.getLong(2)).append(",");
+ } else {
+ builder.append("null").append(",");
+ }
+
+ // get third column
+ if (!iterator.isNull(ROOT_SG1_D1_S2)) {
+ builder.append(iterator.getLong(ROOT_SG1_D1_S2)).append(",");
+ } else {
+ builder.append("null").append(",");
+ }
+
+ // get forth column
+ if (!iterator.isNull(4)) {
+ builder.append(iterator.getLong(4)).append(",");
+ } else {
+ builder.append("null").append(",");
+ }
+
+ // get fifth column
+ if (!iterator.isNull(ROOT_SG1_D1_S4)) {
+ builder.append(iterator.getObject(ROOT_SG1_D1_S4));
+ } else {
+ builder.append("null");
+ }
+
+ System.out.println(builder);
+ }
+ }
+ }
+
+ private static void nonQuery() throws IoTDBConnectionException, StatementExecutionException {
+ session.executeNonQueryStatement("insert into root.sg1.d1(timestamp,s1) values(200, 1)");
+ }
+
+ private static void setTimeout() throws IoTDBConnectionException {
+ try (Session tempSession = new Session(LOCAL_HOST, 6667, "root", "root", 10000, 20000)) {
+ tempSession.setQueryTimeout(60000);
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionPoolExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionPoolExample.java
new file mode 100644
index 00000000000..578a82d4b84
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SessionPoolExample.java
@@ -0,0 +1,154 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.SessionDataSet.DataIterator;
+import org.apache.iotdb.isession.pool.SessionDataSetWrapper;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.pool.SessionPool;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+@SuppressWarnings({"squid:S106", "squid:S1144"})
+public class SessionPoolExample {
+ private static final Logger LOGGER = LoggerFactory.getLogger(SessionPoolExample.class);
+
+ private static SessionPool sessionPool;
+ private static ExecutorService service;
+
+ /** Build a custom SessionPool for this example */
+ private static void constructCustomSessionPool() {
+ sessionPool =
+ new SessionPool.Builder()
+ .host("127.0.0.1")
+ .port(6667)
+ .user("root")
+ .password("root")
+ .maxSize(3)
+ .build();
+ }
+
+ /** Build a redirect-able SessionPool for this example */
+ private static void constructRedirectSessionPool() {
+ List<String> nodeUrls = new ArrayList<>();
+ nodeUrls.add("127.0.0.1:6667");
+ nodeUrls.add("127.0.0.1:6668");
+ sessionPool =
+ new SessionPool.Builder()
+ .nodeUrls(nodeUrls)
+ .user("root")
+ .password("root")
+ .maxSize(3)
+ .build();
+ }
+
+ public static void main(String[] args)
+ throws StatementExecutionException, IoTDBConnectionException, InterruptedException {
+ // Choose the SessionPool you going to use
+ constructRedirectSessionPool();
+
+ service = Executors.newFixedThreadPool(10);
+ insertRecord();
+ queryByRowRecord();
+ Thread.sleep(1000);
+ queryByIterator();
+ sessionPool.close();
+ service.shutdown();
+ }
+
+ // more insert example, see SessionExample.java
+ private static void insertRecord() throws StatementExecutionException, IoTDBConnectionException {
+ String deviceId = "root.sg1.d1";
+ List<String> measurements = new ArrayList<>();
+ List<TSDataType> types = new ArrayList<>();
+ measurements.add("s1");
+ measurements.add("s2");
+ measurements.add("s3");
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+ types.add(TSDataType.INT64);
+
+ for (long time = 0; time < 10; time++) {
+ List<Object> values = new ArrayList<>();
+ values.add(1L);
+ values.add(2L);
+ values.add(3L);
+ sessionPool.insertRecord(deviceId, time, measurements, types, values);
+ }
+ }
+
+ private static void queryByRowRecord() {
+ for (int i = 0; i < 1; i++) {
+ service.submit(
+ () -> {
+ SessionDataSetWrapper wrapper = null;
+ try {
+ wrapper = sessionPool.executeQueryStatement("select * from root.sg1.d1");
+ System.out.println(wrapper.getColumnNames());
+ System.out.println(wrapper.getColumnTypes());
+ while (wrapper.hasNext()) {
+ System.out.println(wrapper.next());
+ }
+ } catch (IoTDBConnectionException | StatementExecutionException e) {
+ LOGGER.error("Query by row record error", e);
+ } finally {
+ // remember to close data set finally!
+ sessionPool.closeResultSet(wrapper);
+ }
+ });
+ }
+ }
+
+ private static void queryByIterator() {
+ for (int i = 0; i < 1; i++) {
+ service.submit(
+ () -> {
+ SessionDataSetWrapper wrapper = null;
+ try {
+ wrapper = sessionPool.executeQueryStatement("select * from root.sg1.d1");
+ // get DataIterator like JDBC
+ DataIterator dataIterator = wrapper.iterator();
+ System.out.println(wrapper.getColumnNames());
+ System.out.println(wrapper.getColumnTypes());
+ while (dataIterator.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (String columnName : wrapper.getColumnNames()) {
+ builder.append(dataIterator.getString(columnName) + " ");
+ }
+ System.out.println(builder);
+ }
+ } catch (IoTDBConnectionException | StatementExecutionException e) {
+ LOGGER.error("Query by Iterator error", e);
+ } finally {
+ // remember to close data set finally!
+ sessionPool.closeResultSet(wrapper);
+ }
+ });
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SubscriptionSessionExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SubscriptionSessionExample.java
new file mode 100644
index 00000000000..1ec74a34a29
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SubscriptionSessionExample.java
@@ -0,0 +1,345 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.isession.util.Version;
+import org.apache.iotdb.rpc.subscription.config.ConsumerConstant;
+import org.apache.iotdb.rpc.subscription.config.TopicConstant;
+import org.apache.iotdb.session.Session;
+import org.apache.iotdb.session.subscription.SubscriptionSession;
+import org.apache.iotdb.session.subscription.consumer.AckStrategy;
+import org.apache.iotdb.session.subscription.consumer.ConsumeResult;
+import org.apache.iotdb.session.subscription.consumer.SubscriptionPullConsumer;
+import org.apache.iotdb.session.subscription.consumer.SubscriptionPushConsumer;
+import org.apache.iotdb.session.subscription.payload.SubscriptionMessage;
+import org.apache.iotdb.session.subscription.payload.SubscriptionSessionDataSet;
+import org.apache.iotdb.session.subscription.payload.SubscriptionTsFileHandler;
+
+import org.apache.tsfile.read.TsFileReader;
+import org.apache.tsfile.read.common.Path;
+import org.apache.tsfile.read.expression.QueryExpression;
+import org.apache.tsfile.read.query.dataset.QueryDataSet;
+
+import java.io.IOException;
+import java.net.URLEncoder;
+import java.nio.file.Paths;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+import java.util.Properties;
+import java.util.concurrent.atomic.AtomicLong;
+import java.util.concurrent.locks.LockSupport;
+
+public class SubscriptionSessionExample {
+
+ private static Session session;
+
+ private static final String HOST = "127.0.0.1";
+ private static final int PORT = 6667;
+
+ private static final String TOPIC_1 = "topic1";
+ private static final String TOPIC_2 = "`'topic2'`";
+ private static final String TOPIC_3 = "`\"topic3\"`";
+ private static final String TOPIC_4 = "`\"top \\.i.c4\"`";
+
+ private static final long SLEEP_NS = 1_000_000_000L;
+ private static final long POLL_TIMEOUT_MS = 10_000L;
+ private static final int MAX_RETRY_TIMES = 3;
+ private static final int PARALLELISM = 8;
+ private static final long CURRENT_TIME = System.currentTimeMillis();
+
+ private static void prepareData() throws Exception {
+ // Open session
+ session =
+ new Session.Builder()
+ .host(HOST)
+ .port(PORT)
+ .username("root")
+ .password("root")
+ .version(Version.V_1_0)
+ .build();
+ session.open(false);
+
+ // Insert some historical data
+ for (int i = 0; i < 100; ++i) {
+ session.executeNonQueryStatement(
+ String.format("insert into root.db.d1(time, s1, s2) values (%s, 1, 2)", i));
+ session.executeNonQueryStatement(
+ String.format(
+ "insert into root.db.d2(time, s1, s2) values (%s, 3, 4)", CURRENT_TIME + i));
+ session.executeNonQueryStatement(
+ String.format("insert into root.sg.d3(time, s1) values (%s, 5)", CURRENT_TIME + 2 * i));
+ }
+ session.executeNonQueryStatement("flush");
+
+ // Close session
+ session.close();
+ session = null;
+ }
+
+ private static void dataQuery() throws Exception {
+ // Open session
+ session =
+ new Session.Builder()
+ .host(HOST)
+ .port(PORT)
+ .username("root")
+ .password("root")
+ .version(Version.V_1_0)
+ .build();
+ session.open(false);
+
+ // Query
+ final SessionDataSet dataSet = session.executeQueryStatement("select ** from root.**");
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+
+ // Close session
+ session.close();
+ session = null;
+ }
+
+ /** single pull consumer subscribe topic with path and time range */
+ private static void dataSubscription1() throws Exception {
+ // Create topics
+ try (final SubscriptionSession subscriptionSession = new SubscriptionSession(HOST, PORT)) {
+ subscriptionSession.open();
+ final Properties config = new Properties();
+ config.put(TopicConstant.PATH_KEY, "root.db.d1.s1");
+ config.put(TopicConstant.START_TIME_KEY, 25);
+ config.put(TopicConstant.END_TIME_KEY, 75);
+ subscriptionSession.createTopic(TOPIC_1, config);
+ }
+
+ int retryCount = 0;
+ // Subscription: property-style ctor
+ final Properties config = new Properties();
+ config.put(ConsumerConstant.CONSUMER_ID_KEY, "c1");
+ config.put(ConsumerConstant.CONSUMER_GROUP_ID_KEY, "cg1");
+ try (SubscriptionPullConsumer consumer1 = new SubscriptionPullConsumer(config)) {
+ consumer1.open();
+ consumer1.subscribe(TOPIC_1);
+ while (true) {
+ final List<SubscriptionMessage> messages = consumer1.poll(POLL_TIMEOUT_MS);
+ if (messages.isEmpty()) {
+ retryCount++;
+ if (retryCount >= MAX_RETRY_TIMES) {
+ break;
+ }
+ }
+ for (final SubscriptionMessage message : messages) {
+ for (final SubscriptionSessionDataSet dataSet : message.getSessionDataSetsHandler()) {
+ System.out.println(dataSet.getColumnNames());
+ System.out.println(dataSet.getColumnTypes());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+ // Auto commit
+ }
+
+ // Show topics and subscriptions
+ try (final SubscriptionSession subscriptionSession = new SubscriptionSession(HOST, PORT)) {
+ subscriptionSession.open();
+ subscriptionSession.getTopics().forEach((System.out::println));
+ subscriptionSession.getSubscriptions().forEach((System.out::println));
+ }
+
+ consumer1.unsubscribe(TOPIC_1);
+ }
+ }
+
+ /** multi pull consumer subscribe topic with tsfile format */
+ private static void dataSubscription2() throws Exception {
+ try (final SubscriptionSession subscriptionSession = new SubscriptionSession(HOST, PORT)) {
+ subscriptionSession.open();
+ final Properties config = new Properties();
+ config.put(TopicConstant.START_TIME_KEY, CURRENT_TIME + 33);
+ config.put(TopicConstant.END_TIME_KEY, CURRENT_TIME + 66);
+ config.put(TopicConstant.FORMAT_KEY, TopicConstant.FORMAT_TS_FILE_HANDLER_VALUE);
+ subscriptionSession.createTopic(TOPIC_2, config);
+ }
+
+ final List<Thread> threads = new ArrayList<>();
+ for (int i = 0; i < PARALLELISM; ++i) {
+ final int idx = i;
+ final Thread thread =
+ new Thread(
+ () -> {
+ int retryCount = 0;
+ // Subscription: builder-style ctor
+ try (final SubscriptionPullConsumer consumer2 =
+ new SubscriptionPullConsumer.Builder()
+ .consumerId("c" + idx)
+ .consumerGroupId("cg2")
+ .autoCommit(false)
+ .buildPullConsumer()) {
+ consumer2.open();
+ consumer2.subscribe(TOPIC_2);
+ while (true) {
+ final List<SubscriptionMessage> messages =
+ consumer2.poll(Collections.singleton(TOPIC_2), POLL_TIMEOUT_MS);
+ if (messages.isEmpty()) {
+ retryCount++;
+ if (retryCount >= MAX_RETRY_TIMES) {
+ break;
+ }
+ }
+ for (final SubscriptionMessage message : messages) {
+ try (final TsFileReader reader = message.getTsFileHandler().openReader()) {
+ final QueryDataSet dataSet =
+ reader.query(
+ QueryExpression.create(
+ Arrays.asList(
+ new Path("root.db.d2", "s2", true),
+ new Path("root.sg.d3", "s1", true)),
+ null));
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+ }
+ consumer2.commitSync(messages);
+ }
+ consumer2.unsubscribe(TOPIC_2);
+ } catch (final IOException e) {
+ throw new RuntimeException(e);
+ }
+ });
+ thread.start();
+ threads.add(thread);
+ }
+
+ for (final Thread thread : threads) {
+ thread.join();
+ }
+ }
+
+ /** multi push consumer subscribe topic with tsfile format and snapshot mode */
+ private static void dataSubscription3() throws Exception {
+ try (final SubscriptionSession subscriptionSession = new SubscriptionSession(HOST, PORT)) {
+ subscriptionSession.open();
+ final Properties config = new Properties();
+ config.put(TopicConstant.FORMAT_KEY, TopicConstant.FORMAT_TS_FILE_HANDLER_VALUE);
+ config.put(TopicConstant.MODE_KEY, TopicConstant.MODE_SNAPSHOT_VALUE);
+ subscriptionSession.createTopic(TOPIC_3, config);
+ }
+
+ final List<Thread> threads = new ArrayList<>();
+ for (int i = 0; i < PARALLELISM; ++i) {
+ final int idx = i;
+ final Thread thread =
+ new Thread(
+ () -> {
+ // Subscription: builder-style ctor
+ try (final SubscriptionPushConsumer consumer3 =
+ new SubscriptionPushConsumer.Builder()
+ .consumerId("c" + idx)
+ .consumerGroupId("cg3")
+ .ackStrategy(AckStrategy.AFTER_CONSUME)
+ .consumeListener(
+ message -> {
+ // do something for SubscriptionTsFileHandler
+ System.out.println(
+ message.getTsFileHandler().getFile().getAbsolutePath());
+ return ConsumeResult.SUCCESS;
+ })
+ .buildPushConsumer()) {
+ consumer3.open();
+ consumer3.subscribe(TOPIC_3);
+ while (!consumer3.allSnapshotTopicMessagesHaveBeenConsumed()) {
+ LockSupport.parkNanos(SLEEP_NS); // wait some time
+ }
+ }
+ });
+ thread.start();
+ threads.add(thread);
+ }
+
+ for (final Thread thread : threads) {
+ thread.join();
+ }
+ }
+
+ /** multi pull consumer subscribe topic with tsfile format and snapshot mode */
+ private static void dataSubscription4() throws Exception {
+ try (final SubscriptionSession subscriptionSession = new SubscriptionSession(HOST, PORT)) {
+ subscriptionSession.open();
+ final Properties config = new Properties();
+ config.put(TopicConstant.FORMAT_KEY, TopicConstant.FORMAT_TS_FILE_HANDLER_VALUE);
+ config.put(TopicConstant.MODE_KEY, TopicConstant.MODE_SNAPSHOT_VALUE);
+ subscriptionSession.createTopic(TOPIC_4, config);
+ }
+
+ final AtomicLong counter = new AtomicLong();
+ final List<Thread> threads = new ArrayList<>();
+ for (int i = 0; i < PARALLELISM; ++i) {
+ final int idx = i;
+ final Thread thread =
+ new Thread(
+ () -> {
+ // Subscription: builder-style ctor
+ try (final SubscriptionPullConsumer consumer4 =
+ new SubscriptionPullConsumer.Builder()
+ .consumerId("c" + idx)
+ .consumerGroupId("cg4")
+ .autoCommit(true)
+ .fileSaveFsync(true)
+ .buildPullConsumer()) {
+ consumer4.open();
+ consumer4.subscribe(TOPIC_4);
+ while (!consumer4.allSnapshotTopicMessagesHaveBeenConsumed()) {
+ for (final SubscriptionMessage message : consumer4.poll(POLL_TIMEOUT_MS)) {
+ final SubscriptionTsFileHandler handler = message.getTsFileHandler();
+ handler.moveFile(
+ Paths.get(System.getProperty("user.dir"), "exported-tsfiles")
+ .resolve(
+ URLEncoder.encode(TOPIC_4)
+ + "-"
+ + counter.getAndIncrement()
+ + ".tsfile"));
+ }
+ }
+ } catch (final IOException e) {
+ throw new RuntimeException(e);
+ }
+ });
+ thread.start();
+ threads.add(thread);
+ }
+
+ for (final Thread thread : threads) {
+ thread.join();
+ }
+ }
+
+ public static void main(final String[] args) throws Exception {
+ prepareData();
+ // dataQuery();
+ // dataSubscription1();
+ // dataSubscription2();
+ // dataSubscription3();
+ dataSubscription4();
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SyntaxConventionRelatedExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SyntaxConventionRelatedExample.java
new file mode 100644
index 00000000000..ada3646fcce
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/SyntaxConventionRelatedExample.java
@@ -0,0 +1,156 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.isession.util.Version;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.rpc.TSStatusCode;
+import org.apache.iotdb.session.Session;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.file.metadata.enums.CompressionType;
+import org.apache.tsfile.file.metadata.enums.TSEncoding;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * When using session API, measurement, device, database and path are represented by String. The
+ * content of the String should be the same as what you would write in a SQL statement. This class
+ * is an example to help you understand better.
+ */
+public class SyntaxConventionRelatedExample {
+
+ private static final Logger LOGGER =
+ LoggerFactory.getLogger(SyntaxConventionRelatedExample.class);
+
+ private static Session session;
+ private static final String LOCAL_HOST = "127.0.0.1";
+
+ /**
+ * if you want to create a time series named root.sg1.select, a possible SQL statement would be
+ * like: create timeseries root.sg1.select with datatype=FLOAT, encoding=RLE As described before,
+ * when using session API, path is represented using String. The path should be written as
+ * "root.sg1.select".
+ */
+ private static final String ROOT_SG1_KEYWORD_EXAMPLE = "root.sg1.select";
+
+ /**
+ * if you want to create a time series named root.sg1.111, a possible SQL statement would be like:
+ * create timeseries root.sg1.`111` with datatype=FLOAT, encoding=RLE The path should be written
+ * as "root.sg1.`111`".
+ */
+ private static final String ROOT_SG1_DIGITS_EXAMPLE = "root.sg1.`111`";
+
+ /**
+ * if you want to create a time series named root.sg1.`a"b'c``, a possible SQL statement would be
+ * like: create timeseries root.sg1.`a"b'c``` with datatype=FLOAT, encoding=RLE The path should be
+ * written as "root.sg1.`a"b`c```".
+ */
+ private static final String ROOT_SG1_SPECIAL_CHARACTER_EXAMPLE = "root.sg1.`a\"b'c```";
+
+ /**
+ * if you want to create a time series named root.sg1.a, a possible SQL statement would be like:
+ * create timeseries root.sg1.a with datatype=FLOAT, encoding=RLE The path should be written as
+ * "root.sg1.a".
+ */
+ private static final String ROOT_SG1_NORMAL_NODE_EXAMPLE = "root.sg1.a";
+
+ public static void main(String[] args)
+ throws IoTDBConnectionException, StatementExecutionException {
+ session =
+ new Session.Builder()
+ .host(LOCAL_HOST)
+ .port(6667)
+ .username("root")
+ .password("root")
+ .version(Version.V_1_0)
+ .build();
+ session.open(false);
+
+ // set session fetchSize
+ session.setFetchSize(10000);
+
+ try {
+ session.setStorageGroup("root.sg1");
+ } catch (StatementExecutionException e) {
+ if (e.getStatusCode() != TSStatusCode.PATH_ALREADY_EXIST.getStatusCode()) {
+ throw e;
+ }
+ }
+
+ // createTimeSeries
+ createTimeSeries();
+ SessionDataSet dataSet = session.executeQueryStatement("show timeseries root.sg1.*");
+ // the expected paths would be:
+ // [root.sg1.select, root.sg1.`111`, root.sg1.`a"b'c```, root.sg1.a]
+ // You could see that time series in dataSet are exactly the same as
+ // the initial String you used as path. Node names consist of digits or contain special
+ // characters are quoted with ``, both in SQL statement and in header of result dataset.
+ // It's convenient that you can use the result of show timeseries as input parameter directly
+ // for other
+ // session APIs such as insertRecord or executeRawDataQuery.
+ List<String> paths = new ArrayList<>();
+ while (dataSet.hasNext()) {
+ paths.add(dataSet.next().getFields().get(0).toString());
+ }
+
+ long startTime = 1L;
+ long endTime = 100L;
+ long timeOut = 60000;
+
+ try (SessionDataSet dataSet1 =
+ session.executeRawDataQuery(paths, startTime, endTime, timeOut)) {
+
+ LOGGER.info("columnNames = {}", dataSet1.getColumnNames());
+ dataSet1.setFetchSize(1024);
+ while (dataSet1.hasNext()) {
+ LOGGER.info("data = {}", dataSet1.next());
+ }
+ }
+ }
+
+ private static void createTimeSeries()
+ throws IoTDBConnectionException, StatementExecutionException {
+ if (!session.checkTimeseriesExists(ROOT_SG1_KEYWORD_EXAMPLE)) {
+ session.createTimeseries(
+ ROOT_SG1_KEYWORD_EXAMPLE, TSDataType.FLOAT, TSEncoding.RLE, CompressionType.SNAPPY);
+ }
+ if (!session.checkTimeseriesExists(ROOT_SG1_DIGITS_EXAMPLE)) {
+ session.createTimeseries(
+ ROOT_SG1_DIGITS_EXAMPLE, TSDataType.FLOAT, TSEncoding.RLE, CompressionType.SNAPPY);
+ }
+ if (!session.checkTimeseriesExists(ROOT_SG1_SPECIAL_CHARACTER_EXAMPLE)) {
+ session.createTimeseries(
+ ROOT_SG1_SPECIAL_CHARACTER_EXAMPLE,
+ TSDataType.FLOAT,
+ TSEncoding.RLE,
+ CompressionType.SNAPPY);
+ }
+ if (!session.checkTimeseriesExists(ROOT_SG1_NORMAL_NODE_EXAMPLE)) {
+ session.createTimeseries(
+ ROOT_SG1_NORMAL_NODE_EXAMPLE, TSDataType.FLOAT, TSEncoding.RLE, CompressionType.SNAPPY);
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TableModelSessionExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TableModelSessionExample.java
new file mode 100644
index 00000000000..b57b5903e07
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TableModelSessionExample.java
@@ -0,0 +1,136 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.isession.util.Version;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.Session;
+
+public class TableModelSessionExample {
+
+ private static final String LOCAL_HOST = "127.0.0.1";
+
+ public static void main(String[] args) {
+
+ // don't specify database in constructor
+ Session session =
+ new Session.Builder()
+ .host(LOCAL_HOST)
+ .port(6667)
+ .username("root")
+ .password("root")
+ .version(Version.V_1_0)
+ .sqlDialect("table")
+ .build();
+
+ try {
+ session.open(false);
+
+ session.executeNonQueryStatement("CREATE DATABASE test1");
+ session.executeNonQueryStatement("CREATE DATABASE test2");
+
+ session.executeNonQueryStatement("use test2");
+
+ // or use full qualified table name
+ session.executeNonQueryStatement(
+ "create table test1.table1(region_id STRING ID, plant_id STRING ID, device_id STRING ID, model STRING ATTRIBUTE, temperature FLOAT MEASUREMENT, humidity DOUBLE MEASUREMENT) with (TTL=3600000)");
+
+ session.executeNonQueryStatement(
+ "create table table2(region_id STRING ID, plant_id STRING ID, color STRING ATTRIBUTE, temperature FLOAT MEASUREMENT, speed DOUBLE MEASUREMENT) with (TTL=6600000)");
+
+ // show tables from current database
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ // show tables by specifying another database
+ // using SHOW tables FROM
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES FROM test1")) {
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ } catch (StatementExecutionException e) {
+ e.printStackTrace();
+ } finally {
+ try {
+ session.close();
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ }
+ }
+
+ // specify database in constructor
+ session =
+ new Session.Builder()
+ .host(LOCAL_HOST)
+ .port(6667)
+ .username("root")
+ .password("root")
+ .version(Version.V_1_0)
+ .sqlDialect("table")
+ .database("test1")
+ .build();
+
+ try {
+ session.open(false);
+
+ // show tables from current database
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ // change database to test2
+ session.executeNonQueryStatement("use test2");
+
+ // show tables by specifying another database
+ // using SHOW tables FROM
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ } catch (StatementExecutionException e) {
+ e.printStackTrace();
+ } finally {
+ try {
+ session.close();
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ }
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TableModelSessionPoolExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TableModelSessionPoolExample.java
new file mode 100644
index 00000000000..78af9efdd6d
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TableModelSessionPoolExample.java
@@ -0,0 +1,147 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.isession.IPooledSession;
+import org.apache.iotdb.isession.SessionDataSet;
+import org.apache.iotdb.rpc.IoTDBConnectionException;
+import org.apache.iotdb.rpc.StatementExecutionException;
+import org.apache.iotdb.session.pool.SessionPool;
+
+public class TableModelSessionPoolExample {
+
+ private static final String LOCAL_HOST = "127.0.0.1";
+
+ public static void main(String[] args) {
+
+ // don't specify database in constructor
+ SessionPool sessionPool =
+ new SessionPool.Builder()
+ .host(LOCAL_HOST)
+ .port(6667)
+ .user("root")
+ .password("root")
+ .maxSize(1)
+ .sqlDialect("table")
+ .build();
+
+ try (IPooledSession session = sessionPool.getPooledSession()) {
+
+ session.executeNonQueryStatement("CREATE DATABASE test1");
+ session.executeNonQueryStatement("CREATE DATABASE test2");
+
+ session.executeNonQueryStatement("use test2");
+
+ // or use full qualified table name
+ session.executeNonQueryStatement(
+ "create table test1.table1(region_id STRING ID, plant_id STRING ID, device_id STRING ID, model STRING ATTRIBUTE, temperature FLOAT MEASUREMENT, humidity DOUBLE MEASUREMENT) with (TTL=3600000)");
+
+ session.executeNonQueryStatement(
+ "create table table2(region_id STRING ID, plant_id STRING ID, color STRING ATTRIBUTE, temperature FLOAT MEASUREMENT, speed DOUBLE MEASUREMENT) with (TTL=6600000)");
+
+ // show tables from current database
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ System.out.println(dataSet.getColumnTypes());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ // show tables by specifying another database
+ // using SHOW tables FROM
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES FROM test1")) {
+ System.out.println(dataSet.getColumnNames());
+ System.out.println(dataSet.getColumnTypes());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ } catch (StatementExecutionException e) {
+ e.printStackTrace();
+ } finally {
+ sessionPool.close();
+ }
+
+ // specify database in constructor
+ sessionPool =
+ new SessionPool.Builder()
+ .host(LOCAL_HOST)
+ .port(6667)
+ .user("root")
+ .password("root")
+ .maxSize(1)
+ .sqlDialect("table")
+ .database("test1")
+ .build();
+
+ try (IPooledSession session = sessionPool.getPooledSession()) {
+
+ // show tables from current database
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ System.out.println(dataSet.getColumnTypes());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ // change database to test2
+ session.executeNonQueryStatement("use test2");
+
+ // show tables by specifying another database
+ // using SHOW tables FROM
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ System.out.println(dataSet.getColumnTypes());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ } catch (StatementExecutionException e) {
+ e.printStackTrace();
+ }
+
+ try (IPooledSession session = sessionPool.getPooledSession()) {
+
+ // show tables from default database test1
+ try (SessionDataSet dataSet = session.executeQueryStatement("SHOW TABLES")) {
+ System.out.println(dataSet.getColumnNames());
+ System.out.println(dataSet.getColumnTypes());
+ while (dataSet.hasNext()) {
+ System.out.println(dataSet.next());
+ }
+ }
+
+ } catch (IoTDBConnectionException e) {
+ e.printStackTrace();
+ } catch (StatementExecutionException e) {
+ e.printStackTrace();
+ } finally {
+ sessionPool.close();
+ }
+ }
+}
diff --git a/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TabletExample.java b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TabletExample.java
new file mode 100644
index 00000000000..39f1223efca
--- /dev/null
+++ b/example/influxdb-proto-example/src/main/java/org/apache/iotdb/TabletExample.java
@@ -0,0 +1,204 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb;
+
+import org.apache.iotdb.session.Session;
+
+import org.apache.tsfile.enums.TSDataType;
+import org.apache.tsfile.utils.BytesUtils;
+import org.apache.tsfile.write.record.Tablet;
+import org.apache.tsfile.write.schema.IMeasurementSchema;
+import org.apache.tsfile.write.schema.MeasurementSchema;
+
+import java.io.BufferedReader;
+import java.io.FileReader;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+
+@SuppressWarnings({"squid:S106"})
+public class TabletExample {
+
+ private static final String TIME_STR = "time";
+
+ /**
+ * load csv data.
+ *
+ * @param measureTSTypeInfos key: measurement name, value: measurement data type
+ * @param dataFileName the csv file name to load
+ * @return key: measurement name, value: series in format of {@link ArrayList}
+ * @throws IOException if the csv format is incorrect
+ */
+ private static Map<String, ArrayList<Object>> loadCSVData(
+ Map<String, TSDataType> measureTSTypeInfos, String dataFileName) throws IOException {
+ measureTSTypeInfos.put(TIME_STR, TSDataType.INT64);
+ try (BufferedReader reader = new BufferedReader(new FileReader(dataFileName))) {
+ String headline = reader.readLine();
+ if (headline == null) {
+ throw new IOException("Given csv data file has not headers");
+ }
+ // check the csv file format
+ String[] fileColumns = headline.split(",");
+ Map<String, Integer> columnToIdMap = new HashMap<>();
+ for (int col = 0; col < fileColumns.length; col++) {
+ String columnName = fileColumns[col];
+ if (columnToIdMap.containsKey(columnName)) {
+ throw new IOException(
+ String.format("csv file contains duplicate columns: %s", columnName));
+ }
+ columnToIdMap.put(columnName, col);
+ }
+ Map<String, ArrayList<Object>> ret = new HashMap<>();
+ // make sure that all measurements can be found from the data file
+ for (Entry<String, TSDataType> entry : measureTSTypeInfos.entrySet()) {
+ String measurement = entry.getKey();
+ if (!columnToIdMap.containsKey(entry.getKey())) {
+ throw new IOException(String.format("measurement %s's is not in csv file.", measurement));
+ } else {
+ ret.put(measurement, new ArrayList<>());
+ }
+ }
+
+ String line;
+ while ((line = reader.readLine()) != null) {
+ String[] items = line.split(",");
+ for (Entry<String, TSDataType> entry : measureTSTypeInfos.entrySet()) {
+ String measurement = entry.getKey();
+ TSDataType dataType = entry.getValue();
+ int idx = columnToIdMap.get(measurement);
+ switch (dataType) {
+ case BOOLEAN:
+ ret.get(measurement).add(Boolean.parseBoolean(items[idx]));
+ break;
+ case DATE:
+ case INT32:
+ ret.get(measurement).add(Integer.parseInt(items[idx]));
+ break;
+ case TIMESTAMP:
+ case INT64:
+ ret.get(measurement).add(Long.parseLong(items[idx]));
+ break;
+ case FLOAT:
+ ret.get(measurement).add(Float.parseFloat(items[idx]));
+ break;
+ case DOUBLE:
+ ret.get(measurement).add(Double.parseDouble(items[idx]));
+ break;
+ case STRING:
+ case BLOB:
+ case TEXT:
+ ret.get(measurement).add(BytesUtils.valueOf(items[idx]));
+ break;
+ case VECTOR:
+ throw new IOException(String.format("data type %s is not yet.", TSDataType.VECTOR));
+ default:
+ throw new IOException("no type");
+ }
+ }
+ }
+ return ret;
+ } finally {
+ measureTSTypeInfos.remove(TIME_STR);
+ }
+ }
+
+ /**
+ * Read csv file and insert tablet to IoTDB
+ *
+ * @param args: arg(with default value): arg0: dataFileName(sample.csv), arg1: rowSize(10000),
+ * arg2: colSize(5000).
+ */
+ public static void main(String[] args) throws Exception {
+
+ try (Session session = new Session("127.0.0.1", 6667, "root", "root")) {
+ session.open();
+ String dataFileName = "sample.csv";
+ int rowSize = 10000;
+ int colSize = 5000;
+ if (args.length > 1) {
+ dataFileName = args[0];
+ }
+ if (args.length > 2) {
+ rowSize = Integer.parseInt(args[1]);
+ }
+ if (args.length > 3) {
+ colSize = Integer.parseInt(args[2]);
+ }
+
+ // construct the tablet's measurements.
+ Map<String, TSDataType> measureTSTypeInfos = new HashMap<>();
+ measureTSTypeInfos.put("s0", TSDataType.BOOLEAN);
+ measureTSTypeInfos.put("s1", TSDataType.FLOAT);
+ measureTSTypeInfos.put("s2", TSDataType.INT32);
+ measureTSTypeInfos.put("s3", TSDataType.DOUBLE);
+ measureTSTypeInfos.put("s4", TSDataType.INT64);
+ measureTSTypeInfos.put("s5", TSDataType.TEXT);
+ List<IMeasurementSchema> schemas = new ArrayList<>();
+ measureTSTypeInfos.forEach((mea, type) -> schemas.add(new MeasurementSchema(mea, type)));
+
+ System.out.println(
+ String.format(
+ "Test Java: csv file name: %s, row: %d, col: %d", dataFileName, rowSize, colSize));
+ System.out.println(String.format("Total points: %d", rowSize * colSize * schemas.size()));
+
+ // test start
+ long allStart = System.nanoTime();
+
+ Map<String, ArrayList<Object>> data = loadCSVData(measureTSTypeInfos, dataFileName);
+ long loadCost = System.nanoTime() - allStart;
+
+ long insertCost = 0;
+ for (int i = 0; i < colSize; i++) {
+ String deviceId = "root.sg" + i % 8 + "." + i;
+
+ Tablet ta = new Tablet(deviceId, schemas, rowSize);
+ ta.rowSize = rowSize;
+ for (int t = 0; t < ta.rowSize; t++) {
+ ta.addTimestamp(t, (Long) data.get(TIME_STR).get(t));
+ for (Entry<String, TSDataType> entry : measureTSTypeInfos.entrySet()) {
+ String mea = entry.getKey();
+ ta.addValue(mea, t, data.get(mea).get(t));
+ }
+ }
+ long insertSt = System.nanoTime();
+ session.insertTablet(ta, false);
+ insertCost += (System.nanoTime() - insertSt);
+ }
+ // test end
+ long allEnd = System.nanoTime();
+
+ session.executeNonQueryStatement("delete timeseries root.*");
+
+ System.out.println(String.format("load cost: %.3f", ((float) loadCost / 1000_000_000)));
+ System.out.println(
+ String.format(
+ "construct tablet cost: %.3f",
+ ((float) (allEnd - allStart - insertCost - loadCost) / 1000_000_000)));
+ System.out.println(
+ String.format("insert tablet cost: %.3f", ((float) insertCost / 1000_000_000)));
+ System.out.println(
+ String.format("total cost: %.3f", ((float) (allEnd - allStart) / 1000_000_000)));
+ System.out.println(String.format("%.3f", ((float) loadCost / 1000_000_000)));
+ }
+ }
+}
diff --git a/example/pom.xml b/example/pom.xml
index 094ca541af4..78adf4430cf 100644
--- a/example/pom.xml
+++ b/example/pom.xml
@@ -40,6 +40,7 @@
<module>session</module>
<module>trigger</module>
<module>udf</module>
+ <module>influxdb-proto-example</module>
</modules>
<build>
<pluginManagement>
diff --git a/iotdb-client/session/pom.xml b/iotdb-client/session/pom.xml
index b465de97ed0..80c6ce30a62 100644
--- a/iotdb-client/session/pom.xml
+++ b/iotdb-client/session/pom.xml
@@ -87,6 +87,11 @@
<artifactId>powermock-reflect</artifactId>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>org.influxdb</groupId>
+ <artifactId>influxdb-java</artifactId>
+ <version>2.21</version>
+ </dependency>
</dependencies>
<build>
<plugins>
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/IoTDBInfluxDB.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/IoTDBInfluxDB.java
new file mode 100644
index 00000000000..946521723c2
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/IoTDBInfluxDB.java
@@ -0,0 +1,393 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb;
+
+import org.influxdb.InfluxDB;
+
+import java.util.*;
+
+public abstract class IoTDBInfluxDB implements InfluxDB {
+
+ // private final IoTDBInfluxDBService influxDBService;
+ //
+ // public IoTDBInfluxDB(String url, String userName, String password) {
+ // URI uri;
+ // try {
+ // uri = new URI(url);
+ // } catch (URISyntaxException e) {
+ // throw new IllegalArgumentException("Unable to parse url: " + url, e);
+ // }
+ // influxDBService = new IoTDBInfluxDBService(uri.getHost(), uri.getPort(), userName,
+ // password);
+ // }
+ //
+ // public IoTDBInfluxDB(String host, int rpcPort, String userName, String password) {
+ // influxDBService = new IoTDBInfluxDBService(host, rpcPort, userName, password);
+ // }
+ //
+ // public IoTDBInfluxDB(Session.Builder builder) {
+ // this(builder.build());
+ // }
+
+ // public IoTDBInfluxDB(Session session) {
+ // SessionPoint sessionPoint = new SessionPoint(session);
+ // influxDBService =
+ // new IoTDBInfluxDBService(
+ // sessionPoint.getHost(),
+ // sessionPoint.getRpcPort(),
+ // sessionPoint.getUsername(),
+ // sessionPoint.getPassword());
+ // }
+ //
+ // @Override
+ // public void write(final Point point) {
+ // write(null, null, point);
+ // }
+ //
+ // @Override
+ // public void write(final String database, final String retentionPolicy, final Point point) {
+ // TimeUnit precision = TimeUnit.NANOSECONDS;
+ // // Get the precision of point in influxdb by reflection
+ // for (java.lang.reflect.Field reflectField : point.getClass().getDeclaredFields()) {
+ // reflectField.setAccessible(true);
+ // try {
+ // if (reflectField.getType().getName().equalsIgnoreCase("java.util.concurrent.TimeUnit")
+ // && reflectField.getName().equalsIgnoreCase("precision")) {
+ // precision = (TimeUnit) reflectField.get(point);
+ // }
+ // } catch (IllegalAccessException e) {
+ // throw new IllegalArgumentException(e.getMessage());
+ // }
+ // }
+ // BatchPoints batchPoints =
+ // BatchPoints.database(database)
+ // .retentionPolicy(retentionPolicy)
+ // .precision(precision)
+ // .build();
+ // batchPoints.point(point);
+ // write(batchPoints);
+ // }
+ //
+ // @Override
+ // public void write(final int udpPort, final Point point) {
+ // write(null, null, point);
+ // }
+ //
+ // @Override
+ // public void write(final BatchPoints batchPoints) {
+ // influxDBService.writePoints(
+ // batchPoints.getDatabase(),
+ // batchPoints.getRetentionPolicy(),
+ // TimeUtil.toTimePrecision(batchPoints.getPrecision()),
+ // batchPoints.getConsistency().value(),
+ // batchPoints.lineProtocol());
+ // }
+ //
+ // @Override
+ // public void writeWithRetry(final BatchPoints batchPoints) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void write(final String records) {
+ // write(null, null, null, null, records);
+ // }
+ //
+ // @Override
+ // public void write(final List<String> records) {
+ // write(String.join("\n", records));
+ // }
+ //
+ // @Override
+ // public void write(
+ // final String database,
+ // final String retentionPolicy,
+ // final ConsistencyLevel consistency,
+ // final String records) {
+ // write(database, retentionPolicy, consistency, null, records);
+ // }
+ //
+ // @Override
+ // public void write(
+ // final String database,
+ // final String retentionPolicy,
+ // final ConsistencyLevel consistency,
+ // final TimeUnit precision,
+ // final String records) {
+ // influxDBService.writePoints(
+ // database,
+ // retentionPolicy,
+ // consistency.value(),
+ // precision == null ? "" : TimeUtil.toTimePrecision(precision),
+ // records);
+ // }
+ //
+ // @Override
+ // public void write(
+ // final String database,
+ // final String retentionPolicy,
+ // final ConsistencyLevel consistency,
+ // final List<String> records) {
+ // write(database, retentionPolicy, consistency, null, String.join("\n", records));
+ // }
+ //
+ // @Override
+ // public void write(
+ // final String database,
+ // final String retentionPolicy,
+ // final ConsistencyLevel consistency,
+ // final TimeUnit precision,
+ // final List<String> records) {
+ // write(database, retentionPolicy, consistency, precision, String.join("\n", records));
+ // }
+ //
+ // @Override
+ // public void write(final int udpPort, final String records) {
+ // write(records);
+ // }
+ //
+ // @Override
+ // public void write(final int udpPort, final List<String> records) {
+ // write(String.join("\n", records));
+ // }
+ //
+ // @Override
+ // public QueryResult query(final Query query) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void createDatabase(final String name) {
+ // ParameterUtils.checkNonEmptyString(name, "database name");
+ // influxDBService.createDatabase(name);
+ // }
+ //
+ // @Override
+ // public void deleteDatabase(final String name) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB setDatabase(final String database) {
+ // ParameterUtils.checkNonEmptyString(database, "database name");
+ // influxDBService.setDatabase(database);
+ // return this;
+ // }
+ //
+ // @Override
+ // public void query(
+ // final Query query,
+ // final Consumer<QueryResult> onSuccess,
+ // final Consumer<Throwable> onFailure) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void query(Query query, int chunkSize, Consumer<QueryResult> onNext) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void query(Query query, int chunkSize, BiConsumer<Cancellable, QueryResult> onNext) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void query(Query query, int chunkSize, Consumer<QueryResult> onNext, Runnable
+ // onComplete) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void query(
+ // Query query,
+ // int chunkSize,
+ // BiConsumer<Cancellable, QueryResult> onNext,
+ // Runnable onComplete) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void query(
+ // Query query,
+ // int chunkSize,
+ // BiConsumer<Cancellable, QueryResult> onNext,
+ // Runnable onComplete,
+ // Consumer<Throwable> onFailure) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public QueryResult query(Query query, TimeUnit timeUnit) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public List<String> describeDatabases() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public boolean databaseExists(final String name) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void flush() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void close() {
+ // influxDBService.close();
+ // }
+ //
+ // @Override
+ // public InfluxDB setConsistency(final ConsistencyLevel consistencyLevel) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB setRetentionPolicy(final String retentionPolicy) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void createRetentionPolicy(
+ // final String rpName,
+ // final String database,
+ // final String duration,
+ // final String shardDuration,
+ // final int replicationFactor,
+ // final boolean isDefault) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void createRetentionPolicy(
+ // final String rpName,
+ // final String database,
+ // final String duration,
+ // final int replicationFactor,
+ // final boolean isDefault) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void createRetentionPolicy(
+ // final String rpName,
+ // final String database,
+ // final String duration,
+ // final String shardDuration,
+ // final int replicationFactor) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void dropRetentionPolicy(final String rpName, final String database) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB setLogLevel(LogLevel logLevel) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableGzip() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB disableGzip() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public boolean isGzipEnabled() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableBatch() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableBatch(BatchOptions batchOptions) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableBatch(
+ // final int actions, final int flushDuration, final TimeUnit flushDurationTimeUnit) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableBatch(
+ // final int actions,
+ // final int flushDuration,
+ // final TimeUnit flushDurationTimeUnit,
+ // final ThreadFactory threadFactory) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableBatch(
+ // int actions,
+ // int flushDuration,
+ // TimeUnit flushDurationTimeUnit,
+ // ThreadFactory threadFactory,
+ // BiConsumer<Iterable<Point>, Throwable> exceptionHandler,
+ // ConsistencyLevel consistency) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public InfluxDB enableBatch(
+ // final int actions,
+ // final int flushDuration,
+ // final TimeUnit flushDurationTimeUnit,
+ // final ThreadFactory threadFactory,
+ // final BiConsumer<Iterable<Point>, Throwable> exceptionHandler) {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public void disableBatch() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public boolean isBatchEnabled() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public Pong ping() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+ //
+ // @Override
+ // public String version() {
+ // throw new UnsupportedOperationException(InfluxDBConstant.METHOD_NOT_SUPPORTED);
+ // }
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/IoTDBInfluxDBProtoFactory.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/IoTDBInfluxDBProtoFactory.java
new file mode 100644
index 00000000000..8ebc0f761f9
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/IoTDBInfluxDBProtoFactory.java
@@ -0,0 +1,74 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb;
+
+import org.apache.iotdb.session.pool.SessionPool;
+
+import okhttp3.OkHttpClient;
+import org.influxdb.InfluxDB;
+import org.influxdb.impl.InfluxDBImpl;
+
+public enum IoTDBInfluxDBProtoFactory {
+ INSTANCE;
+
+ private static final SessionPool sessionPool =
+ new SessionPool("127.0.0.1", 6667, "root", "root", 2);
+
+ IoTDBInfluxDBProtoFactory() {}
+
+ //
+
+ public static InfluxDB connect(
+ String url, String username, String password, final OkHttpClient.Builder client) {
+ return new InfluxDBImpl(url, username, password, client) {};
+ }
+ //
+ // public static InfluxDB connect(String host, int rpcPort, String userName, String password) {
+ // ParameterUtils.checkNonEmptyString(host, "host");
+ // ParameterUtils.checkNonEmptyString(userName, "username");
+ // return new IoTDBInfluxDB(host, rpcPort, userName, password);
+ // }
+ //
+ // public static InfluxDB connect(
+ // String url, String username, String password, OkHttpClient.Builder client) {
+ // ParameterUtils.checkNonEmptyString(url, "url");
+ // ParameterUtils.checkNonEmptyString(username, "username");
+ // return connect(url, username, password);
+ // }
+ //
+ // public static InfluxDB connect(
+ // String url,
+ // String username,
+ // String password,
+ // OkHttpClient.Builder client,
+ // InfluxDB.ResponseFormat responseFormat) {
+ // ParameterUtils.checkNonEmptyString(url, "url");
+ // ParameterUtils.checkNonEmptyString(username, "username");
+ // return connect(url, username, password);
+ // }
+ //
+ // public static InfluxDB connect(Session.Builder builder) {
+ // return new IoTDBInfluxDB(builder);
+ // }
+ //
+ // public static InfluxDB connect(Session session) {
+ // return new IoTDBInfluxDB(session);
+ // }
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/example/InfluxProtoExample.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/example/InfluxProtoExample.java
new file mode 100644
index 00000000000..d13594bb59b
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/example/InfluxProtoExample.java
@@ -0,0 +1,72 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb.example;
+
+import org.apache.iotdb.session.influxdb.IoTDBInfluxDBProtoFactory;
+
+import okhttp3.OkHttpClient;
+import org.influxdb.InfluxDB;
+import org.influxdb.dto.Point;
+import org.influxdb.dto.Query;
+import org.influxdb.dto.QueryResult;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.TimeUnit;
+
+public class InfluxProtoExample {
+
+ private static InfluxDB influxDB;
+
+ public static void main(String[] args) {
+ influxDB =
+ IoTDBInfluxDBProtoFactory.connect(
+ "http://127.0.0.1:8883/", "root", "root", new OkHttpClient.Builder());
+ influxDB.deleteDatabase("db_test");
+ influxDB.createDatabase("db_test");
+ influxDB.setDatabase("db_test");
+
+ insertData();
+ queryData();
+
+ influxDB.close();
+ }
+
+ private static void insertData() {
+ Point.Builder builder = Point.measurement("student");
+ Map<String, String> tags = new HashMap<>();
+ Map<String, Object> fields = new HashMap<>();
+ tags.put("name", "xie");
+ tags.put("country", "china");
+ fields.put("score", 86.0);
+ builder.tag(tags);
+ builder.fields(fields);
+ builder.time(System.currentTimeMillis(), TimeUnit.MILLISECONDS);
+ Point point = builder.build();
+ influxDB.write(point);
+ }
+
+ private static void queryData() {
+ QueryResult queryResult = influxDB.query(new Query("select * from student", "database"));
+ for (QueryResult.Result result : queryResult.getResults()) {
+ System.out.println(result);
+ }
+ }
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/constant/InfluxDBConstant.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/constant/InfluxDBConstant.java
new file mode 100644
index 00000000000..7a0705f1114
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/constant/InfluxDBConstant.java
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb.protocol.constant;
+
+public class InfluxDBConstant {
+
+ public static final String METHOD_NOT_SUPPORTED = "Method not supported.";
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/dto/SessionPoint.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/dto/SessionPoint.java
new file mode 100644
index 00000000000..5fee3f40fb2
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/dto/SessionPoint.java
@@ -0,0 +1,88 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.iotdb.session.influxdb.protocol.dto;
+
+public class SessionPoint {
+ // private final String host;
+ // private final int rpcPort;
+ // private final String username;
+ // private final String password;
+ //
+ // public SessionPoint(String host, int rpcPort, String username, String password) {
+ // this.host = host;
+ // this.rpcPort = rpcPort;
+ // this.username = username;
+ // this.password = password;
+ // }
+ //
+ // public SessionPoint(Session session) {
+ //
+ // EndPoint endPoint = null;
+ // String username = null;
+ // String password = null;
+ //
+ // // Get the property of session by reflection
+ // for (java.lang.reflect.Field reflectField : session.getClass().getDeclaredFields()) {
+ // reflectField.setAccessible(true);
+ // try {
+ // if (reflectField
+ // .getType()
+ // .getName()
+ // .equalsIgnoreCase("org.apache.iotdb.service.rpc.thrift.EndPoint")
+ // && reflectField.getName().equalsIgnoreCase("defaultEndPoint")) {
+ // endPoint = (EndPoint) reflectField.get(session);
+ // }
+ // if (reflectField.getType().getName().equalsIgnoreCase("java.lang.String")
+ // && reflectField.getName().equalsIgnoreCase("username")) {
+ // username = (String) reflectField.get(session);
+ // }
+ // if (reflectField.getType().getName().equalsIgnoreCase("java.lang.String")
+ // && reflectField.getName().equalsIgnoreCase("password")) {
+ // password = (String) reflectField.get(session);
+ // }
+ // } catch (IllegalAccessException e) {
+ // throw new IllegalArgumentException(e.getMessage());
+ // }
+ // }
+ // if (endPoint == null) {
+ // throw new InfluxDBException("session's ip and port is null");
+ // }
+ //
+ // this.host = endPoint.ip;
+ // this.rpcPort = endPoint.port;
+ // this.username = username;
+ // this.password = password;
+ // }
+ //
+ // public String getHost() {
+ // return host;
+ // }
+ //
+ // public int getRpcPort() {
+ // return rpcPort;
+ // }
+ //
+ // public String getUsername() {
+ // return username;
+ // }
+ //
+ // public String getPassword() {
+ // return password;
+ // }
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/impl/IoTDBInfluxDBService.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/impl/IoTDBInfluxDBService.java
new file mode 100644
index 00000000000..30ed4dfefbe
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/impl/IoTDBInfluxDBService.java
@@ -0,0 +1,77 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb.protocol.impl;
+
+public class IoTDBInfluxDBService {
+ //
+ // private String currentDatabase;
+ //
+ // private final InfluxDBSession influxDBSession;
+ //
+ // public IoTDBInfluxDBService(String host, int rpcPort, String username, String password) {
+ // influxDBSession = new InfluxDBSession(host, rpcPort, username, password);
+ // try {
+ // influxDBSession.open();
+ // } catch (IoTDBConnectionException e) {
+ // throw new InfluxDBException(e.getMessage());
+ // }
+ // }
+ //
+ // public void writePoints(
+ // String database,
+ // String retentionPolicy,
+ // String precision,
+ // String consistency,
+ // String lineProtocol) {
+ // TSWritePointsReq tsWritePointsReq = new TSWritePointsReq();
+ // if (database == null) {
+ // tsWritePointsReq.setDatabase(currentDatabase);
+ // } else {
+ // tsWritePointsReq.setDatabase(database);
+ // }
+ // tsWritePointsReq.setRetentionPolicy(retentionPolicy);
+ // tsWritePointsReq.setPrecision(precision);
+ // tsWritePointsReq.setConsistency(consistency);
+ // tsWritePointsReq.setLineProtocol(lineProtocol);
+ // try {
+ // influxDBSession.writePoints(tsWritePointsReq);
+ // } catch (StatementExecutionException | IoTDBConnectionException e) {
+ // throw new InfluxDBException(e.getMessage());
+ // }
+ // }
+ //
+ // public void setDatabase(String database) {
+ // currentDatabase = database;
+ // }
+ //
+ // public void createDatabase(String database) {
+ // TSCreateDatabaseReq tsCreateDatabaseReq = new TSCreateDatabaseReq();
+ // tsCreateDatabaseReq.setDatabase(database);
+ // try {
+ // influxDBSession.createDatabase(tsCreateDatabaseReq);
+ // } catch (StatementExecutionException | IoTDBConnectionException e) {
+ // throw new InfluxDBException(e.getMessage());
+ // }
+ // }
+ //
+ // public void close() {
+ // influxDBSession.close();
+ // }
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/util/ParameterUtils.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/util/ParameterUtils.java
new file mode 100644
index 00000000000..9b2c76ada7b
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/protocol/util/ParameterUtils.java
@@ -0,0 +1,36 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb.protocol.util;
+
+public class ParameterUtils {
+
+ /**
+ * check whether the field is empty. If it is empty, an error will be thrown
+ *
+ * @param string string to check
+ * @param name prompt information in error throwing
+ */
+ public static void checkNonEmptyString(String string, String name)
+ throws IllegalArgumentException {
+ if (string == null || string.isEmpty()) {
+ throw new IllegalArgumentException("Expecting a non-empty string for " + name);
+ }
+ }
+}
diff --git a/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/session/InfluxDBSession.java b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/session/InfluxDBSession.java
new file mode 100644
index 00000000000..91ed05e3d9b
--- /dev/null
+++ b/iotdb-client/session/src/main/java/org/apache/iotdb/session/influxdb/session/InfluxDBSession.java
@@ -0,0 +1,219 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.iotdb.session.influxdb.session;
+
+public class InfluxDBSession {
+ // private static final Logger logger = LoggerFactory.getLogger(InfluxDBSession.class);
+ //
+ // private TTransport transport;
+ // private InfluxDBService.Iface client;
+ // private List<EndPoint> endPointList = new ArrayList<>();
+ // private long sessionId;
+ //
+ // protected String username;
+ // protected String password;
+ // protected int fetchSize;
+ // protected ZoneId zoneId;
+ // protected EndPoint defaultEndPoint;
+ // protected int thriftDefaultBufferSize;
+ // protected int thriftMaxFrameSize;
+ //
+ // private boolean isClosed = true;
+ // protected boolean enableRPCCompression;
+ // protected int connectionTimeoutInMs;
+ //
+ // public InfluxDBSession(String host, int rpcPort, String username, String password) {
+ // this(
+ // host,
+ // rpcPort,
+ // username,
+ // password,
+ // Config.DEFAULT_FETCH_SIZE,
+ // ZoneId.systemDefault(),
+ // Config.DEFAULT_INITIAL_BUFFER_CAPACITY,
+ // Config.DEFAULT_MAX_FRAME_SIZE);
+ // }
+ //
+ // public InfluxDBSession(
+ // String host,
+ // int rpcPort,
+ // String username,
+ // String password,
+ // int fetchSize,
+ // ZoneId zoneId,
+ // int thriftDefaultBufferSize,
+ // int thriftMaxFrameSize) {
+ // this.defaultEndPoint = new EndPoint(host, rpcPort);
+ // this.username = username;
+ // this.password = password;
+ // this.fetchSize = fetchSize;
+ // this.zoneId = zoneId;
+ // this.thriftDefaultBufferSize = thriftDefaultBufferSize;
+ // this.thriftMaxFrameSize = thriftMaxFrameSize;
+ // }
+ //
+ // public synchronized void open() throws IoTDBConnectionException {
+ // open(false, Config.DEFAULT_CONNECTION_TIMEOUT_MS);
+ // }
+ //
+ // public synchronized void open(boolean enableRPCCompression, int connectionTimeoutInMs)
+ // throws IoTDBConnectionException {
+ // if (!isClosed) {
+ // return;
+ // }
+ // this.enableRPCCompression = enableRPCCompression;
+ // this.connectionTimeoutInMs = connectionTimeoutInMs;
+ // this.endPointList.add(defaultEndPoint);
+ //
+ // init();
+ // isClosed = false;
+ // }
+ //
+ // public void init() throws IoTDBConnectionException {
+ // RpcTransportFactory.setDefaultBufferCapacity(thriftDefaultBufferSize);
+ // RpcTransportFactory.setThriftMaxFrameSize(thriftMaxFrameSize);
+ // try {
+ // transport =
+ // RpcTransportFactory.INSTANCE.getTransport(
+ // // as there is a try-catch already, we do not need to use TSocket.wrap
+ // defaultEndPoint.getIp(), defaultEndPoint.getPort(), connectionTimeoutInMs);
+ // transport.open();
+ // } catch (TTransportException e) {
+ // throw new IoTDBConnectionException(e);
+ // }
+ //
+ // if (IoTDBDescriptor.getInstance().getConfig().isRpcThriftCompressionEnable()) {
+ // client = new InfluxDBService.Client(new TCompactProtocol(transport));
+ // } else {
+ // client = new InfluxDBService.Client(new TBinaryProtocol(transport));
+ // }
+ // client = RpcUtils.newSynchronizedClient(client);
+ //
+ // TSOpenSessionReq openReq = new TSOpenSessionReq();
+ // openReq.setUsername(username);
+ // openReq.setPassword(password);
+ // openReq.setZoneId(zoneId.toString());
+ //
+ // try {
+ // TSOpenSessionResp openResp = client.openSession(openReq);
+ // RpcUtils.verifySuccess(openResp.getStatus());
+ // sessionId = openResp.getSessionId();
+ //
+ // } catch (Exception e) {
+ // transport.close();
+ // throw new IoTDBConnectionException(e);
+ // }
+ // }
+ //
+ // public void writePoints(TSWritePointsReq request)
+ // throws StatementExecutionException, IoTDBConnectionException {
+ // request.setSessionId(sessionId);
+ // try {
+ // RpcUtils.verifySuccess(client.writePoints(request));
+ // } catch (TException e) {
+ // logger.error(e.getMessage());
+ // if (reconnect()) {
+ // try {
+ // request.setSessionId(sessionId);
+ // RpcUtils.verifySuccess(client.writePoints(request));
+ // } catch (TException tException) {
+ // throw new IoTDBConnectionException(tException);
+ // }
+ // } else {
+ // throw new IoTDBConnectionException(MSG_RECONNECTION_FAIL);
+ // }
+ // }
+ // }
+ //
+ // public void createDatabase(TSCreateDatabaseReq request)
+ // throws StatementExecutionException, IoTDBConnectionException {
+ // request.setSessionId(sessionId);
+ // try {
+ // RpcUtils.verifySuccess(client.createDatabase(request));
+ // } catch (TException e) {
+ // e.printStackTrace();
+ // logger.error(e.getMessage());
+ // if (reconnect()) {
+ // try {
+ // request.setSessionId(sessionId);
+ // RpcUtils.verifySuccess(client.createDatabase(request));
+ // } catch (TException tException) {
+ // throw new IoTDBConnectionException(tException);
+ // }
+ // } else {
+ // throw new IoTDBConnectionException(MSG_RECONNECTION_FAIL);
+ // }
+ // }
+ // }
+ //
+ // public synchronized void close() {
+ // if (isClosed) {
+ // return;
+ // }
+ // try {
+ // client.closeSession(new TSCloseSessionReq(sessionId));
+ // } catch (TException e) {
+ // throw new InfluxDBException(
+ // "Error occurs when closing session at server. Maybe server is down.", e);
+ // } finally {
+ // if (transport != null) {
+ // transport.close();
+ // }
+ // if (!isClosed) {
+ // isClosed = true;
+ // }
+ // }
+ // }
+ //
+ // private boolean reconnect() {
+ // boolean connectedSuccess = false;
+ // Random random = new Random();
+ // for (int i = 1; i <= Config.RETRY_NUM; i++) {
+ // if (transport != null) {
+ // transport.close();
+ // int currHostIndex = random.nextInt(endPointList.size());
+ // int tryHostNum = 0;
+ // for (int j = currHostIndex; j < endPointList.size(); j++) {
+ // if (tryHostNum == endPointList.size()) {
+ // break;
+ // }
+ // defaultEndPoint = endPointList.get(j);
+ // if (j == endPointList.size() - 1) {
+ // j = -1;
+ // }
+ // tryHostNum++;
+ // try {
+ // init();
+ // connectedSuccess = true;
+ // } catch (IoTDBConnectionException e) {
+ // logger.error("The current node may have been down {},try next node",
+ // defaultEndPoint);
+ // continue;
+ // }
+ // break;
+ // }
+ // }
+ // if (connectedSuccess) {
+ // break;
+ // }
+ // }
+ // return connectedSuccess;
+ // }
+}