This is an automated email from the ASF dual-hosted git repository.
jackietien pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/iotdb.git
The following commit(s) were added to refs/heads/master by this push:
new 49e5b2f [IOTDB-1951] Support aggregation query without value filter
in new vector (#4441)
49e5b2f is described below
commit 49e5b2ffeee2b36589a41eafc431da1e70d784f1
Author: Chen YZ <[email protected]>
AuthorDate: Tue Nov 23 13:10:54 2021 +0800
[IOTDB-1951] Support aggregation query without value filter in new vector
(#4441)
---
.../apache/iotdb/db/metadata/path/AlignedPath.java | 6 +-
.../db/query/aggregation/impl/CountAggrResult.java | 1 +
.../db/query/executor/AggregationExecutor.java | 20 +-
.../reader/series/VectorSeriesAggregateReader.java | 24 ++
.../IoTDBAggregationWithoutValueFilter2IT.java | 63 +++
.../IoTDBAggregationWithoutValueFilterIT.java | 444 ++++++++++++++++++++
...gregationWithoutValueFilterWithDeletion2IT.java | 83 ++++
...ggregationWithoutValueFilterWithDeletionIT.java | 447 +++++++++++++++++++++
.../apache/iotdb/tsfile/read/common/BatchData.java | 16 +
9 files changed, 1095 insertions(+), 9 deletions(-)
diff --git
a/server/src/main/java/org/apache/iotdb/db/metadata/path/AlignedPath.java
b/server/src/main/java/org/apache/iotdb/db/metadata/path/AlignedPath.java
index 44457ad..7a8ee70 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/path/AlignedPath.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/path/AlignedPath.java
@@ -139,10 +139,14 @@ public class AlignedPath extends PartialPath {
this.measurementList = measurementList;
}
- public void addMeasurement(List<String> measurements) {
+ public void addMeasurements(List<String> measurements) {
this.measurementList.addAll(measurements);
}
+ public void addSchemas(List<IMeasurementSchema> schemas) {
+ this.schemaList.addAll(schemas);
+ }
+
public void addMeasurement(MeasurementPath measurementPath) {
if (measurementList == null) {
measurementList = new ArrayList<>();
diff --git
a/server/src/main/java/org/apache/iotdb/db/query/aggregation/impl/CountAggrResult.java
b/server/src/main/java/org/apache/iotdb/db/query/aggregation/impl/CountAggrResult.java
index 10b9ad0..57a3a7e 100644
---
a/server/src/main/java/org/apache/iotdb/db/query/aggregation/impl/CountAggrResult.java
+++
b/server/src/main/java/org/apache/iotdb/db/query/aggregation/impl/CountAggrResult.java
@@ -57,6 +57,7 @@ public class CountAggrResult extends AggregateResult {
public void updateResultFromPageData(
IBatchDataIterator batchIterator, long minBound, long maxBound) {
int cnt = 0;
+ int count = batchIterator.totalLength();
while (batchIterator.hasNext()) {
if (batchIterator.currentTime() >= maxBound ||
batchIterator.currentTime() < minBound) {
break;
diff --git
a/server/src/main/java/org/apache/iotdb/db/query/executor/AggregationExecutor.java
b/server/src/main/java/org/apache/iotdb/db/query/executor/AggregationExecutor.java
index 3db98b7..9d622af 100644
---
a/server/src/main/java/org/apache/iotdb/db/query/executor/AggregationExecutor.java
+++
b/server/src/main/java/org/apache/iotdb/db/query/executor/AggregationExecutor.java
@@ -27,6 +27,7 @@ import
org.apache.iotdb.db.engine.storagegroup.StorageGroupProcessor;
import org.apache.iotdb.db.exception.StorageEngineException;
import org.apache.iotdb.db.exception.query.QueryProcessException;
import org.apache.iotdb.db.metadata.path.AlignedPath;
+import org.apache.iotdb.db.metadata.path.MeasurementPath;
import org.apache.iotdb.db.metadata.path.PartialPath;
import org.apache.iotdb.db.qp.physical.crud.AggregationPlan;
import org.apache.iotdb.db.qp.physical.crud.QueryPlan;
@@ -401,7 +402,7 @@ public class AggregationExecutor {
while (seriesReader.hasNextFile()) {
// cal by file statistics
- if (seriesReader.canUseCurrentFileStatistics()) {
+ if (seriesReader.canUseCurrentTimeFileStatistics()) {
while (seriesReader.hasNextSubSeries()) {
Statistics fileStatistics = seriesReader.currentFileStatistics();
remainingToCalculate =
@@ -422,7 +423,7 @@ public class AggregationExecutor {
while (seriesReader.hasNextChunk()) {
// cal by chunk statistics
- if (seriesReader.canUseCurrentChunkStatistics()) {
+ if (seriesReader.canUseCurrentTimeChunkStatistics()) {
while (seriesReader.hasNextSubSeries()) {
Statistics chunkStatistics = seriesReader.currentChunkStatistics();
remainingToCalculate =
@@ -515,7 +516,7 @@ public class AggregationExecutor {
throws IOException, QueryProcessException {
while (seriesReader.hasNextPage()) {
// cal by page statistics
- if (seriesReader.canUseCurrentPageStatistics()) {
+ if (seriesReader.canUseCurrentTimePageStatistics()) {
while (seriesReader.hasNextSubSeries()) {
Statistics pageStatistic = seriesReader.currentPageStatistics();
remainingToCalculate =
@@ -754,18 +755,21 @@ public class AggregationExecutor {
List<PartialPath> seriesPaths = new
ArrayList<>(pathToAggrIndexesMap.keySet());
for (PartialPath seriesPath : seriesPaths) {
- if (seriesPath instanceof AlignedPath) {
+ if (seriesPath instanceof MeasurementPath
+ && ((MeasurementPath) seriesPath).isUnderAlignedEntity()) {
List<Integer> indexes = pathToAggrIndexesMap.remove(seriesPath);
- AlignedPath groupPath = temp.get(seriesPath.getFullPath());
+ AlignedPath exactPath = (AlignedPath) ((MeasurementPath)
seriesPath).transformToExactPath();
+ AlignedPath groupPath = temp.get(exactPath.getFullPath());
if (groupPath == null) {
- groupPath = (AlignedPath) seriesPath.copy();
- temp.put(seriesPath.getFullPath(), groupPath);
+ groupPath = exactPath;
+ temp.put(groupPath.getFullPath(), groupPath);
result.computeIfAbsent(groupPath, key -> new
ArrayList<>()).add(indexes);
} else {
// groupPath is changed here so we update it
List<List<Integer>> subIndexes = result.remove(groupPath);
subIndexes.add(indexes);
- groupPath.addMeasurement(((AlignedPath)
seriesPath).getMeasurementList());
+ groupPath.addMeasurements(exactPath.getMeasurementList());
+ groupPath.addSchemas(exactPath.getSchemaList());
result.put(groupPath, subIndexes);
}
}
diff --git
a/server/src/main/java/org/apache/iotdb/db/query/reader/series/VectorSeriesAggregateReader.java
b/server/src/main/java/org/apache/iotdb/db/query/reader/series/VectorSeriesAggregateReader.java
index 29cb347..719149d 100644
---
a/server/src/main/java/org/apache/iotdb/db/query/reader/series/VectorSeriesAggregateReader.java
+++
b/server/src/main/java/org/apache/iotdb/db/query/reader/series/VectorSeriesAggregateReader.java
@@ -84,6 +84,13 @@ public class VectorSeriesAggregateReader implements
IAggregateReader {
&& !seriesReader.currentFileModified();
}
+ public boolean canUseCurrentTimeFileStatistics() throws IOException {
+ Statistics fileStatistics = seriesReader.currentFileStatistics();
+ return !seriesReader.isFileOverlapped()
+ && containedByTimeFilter(fileStatistics)
+ && !seriesReader.currentFileModified();
+ }
+
@Override
public Statistics currentFileStatistics() throws IOException {
return seriesReader.currentFileStatistics(curIndex);
@@ -107,6 +114,13 @@ public class VectorSeriesAggregateReader implements
IAggregateReader {
&& !seriesReader.currentChunkModified();
}
+ public boolean canUseCurrentTimeChunkStatistics() throws IOException {
+ Statistics chunkStatistics = seriesReader.currentChunkStatistics();
+ return !seriesReader.isChunkOverlapped()
+ && containedByTimeFilter(chunkStatistics)
+ && !seriesReader.currentChunkModified();
+ }
+
@Override
public Statistics currentChunkStatistics() throws IOException {
return seriesReader.currentChunkStatistics(curIndex);
@@ -133,6 +147,16 @@ public class VectorSeriesAggregateReader implements
IAggregateReader {
&& !seriesReader.currentPageModified();
}
+ public boolean canUseCurrentTimePageStatistics() throws IOException {
+ Statistics currentPageStatistics = seriesReader.currentPageStatistics();
+ if (currentPageStatistics == null) {
+ return false;
+ }
+ return !seriesReader.isPageOverlapped()
+ && containedByTimeFilter(currentPageStatistics)
+ && !seriesReader.currentPageModified();
+ }
+
@Override
public Statistics currentPageStatistics() throws IOException {
return seriesReader.currentPageStatistics(curIndex);
diff --git
a/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilter2IT.java
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilter2IT.java
new file mode 100644
index 0000000..1c799e0
--- /dev/null
+++
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilter2IT.java
@@ -0,0 +1,63 @@
+/*
+ * 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.db.integration.aligned;
+
+import org.apache.iotdb.db.conf.IoTDBDescriptor;
+import org.apache.iotdb.db.utils.EnvironmentUtils;
+import org.apache.iotdb.tsfile.common.conf.TSFileDescriptor;
+
+import org.junit.AfterClass;
+import org.junit.BeforeClass;
+
+/** Let One chunk has more than one page. */
+public class IoTDBAggregationWithoutValueFilter2IT extends
IoTDBAggregationWithoutValueFilterIT {
+ private static int numOfPointsPerPage;
+
+ @BeforeClass
+ public static void setUp() throws Exception {
+ EnvironmentUtils.closeStatMonitor();
+ EnvironmentUtils.envSetUp();
+ // TODO When the aligned time series support compaction, we need to set
compaction to true
+ enableSeqSpaceCompaction =
+ IoTDBDescriptor.getInstance().getConfig().isEnableSeqSpaceCompaction();
+ enableUnseqSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableUnseqSpaceCompaction();
+ enableCrossSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableCrossSpaceCompaction();
+ numOfPointsPerPage =
TSFileDescriptor.getInstance().getConfig().getMaxNumberOfPointsInPage();
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableUnseqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableCrossSpaceCompaction(false);
+ TSFileDescriptor.getInstance().getConfig().setMaxNumberOfPointsInPage(3);
+ AlignedWriteUtil.insertData();
+ }
+
+ @AfterClass
+ public static void tearDown() throws Exception {
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(enableSeqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableUnseqSpaceCompaction(enableUnseqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableCrossSpaceCompaction(enableCrossSpaceCompaction);
+
TSFileDescriptor.getInstance().getConfig().setMaxNumberOfPointsInPage(numOfPointsPerPage);
+ EnvironmentUtils.cleanEnv();
+ }
+}
diff --git
a/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterIT.java
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterIT.java
new file mode 100644
index 0000000..2626105
--- /dev/null
+++
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterIT.java
@@ -0,0 +1,444 @@
+/*
+ * 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.db.integration.aligned;
+
+import org.apache.iotdb.db.conf.IoTDBDescriptor;
+import org.apache.iotdb.db.utils.EnvironmentUtils;
+import org.apache.iotdb.jdbc.Config;
+
+import org.junit.*;
+
+import java.sql.*;
+import java.util.HashMap;
+import java.util.Map;
+
+import static org.junit.Assert.*;
+
+public class IoTDBAggregationWithoutValueFilterIT {
+
+ private static final double DELTA = 1e-6;
+ protected static boolean enableSeqSpaceCompaction;
+ protected static boolean enableUnseqSpaceCompaction;
+ protected static boolean enableCrossSpaceCompaction;
+
+ @BeforeClass
+ public static void setUp() throws Exception {
+ EnvironmentUtils.closeStatMonitor();
+ EnvironmentUtils.envSetUp();
+ // TODO When the aligned time series support compaction, we need to set
compaction to true
+ enableSeqSpaceCompaction =
+ IoTDBDescriptor.getInstance().getConfig().isEnableSeqSpaceCompaction();
+ enableUnseqSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableUnseqSpaceCompaction();
+ enableCrossSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableCrossSpaceCompaction();
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableUnseqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableCrossSpaceCompaction(false);
+ AlignedWriteUtil.insertData();
+ }
+
+ @AfterClass
+ public static void tearDown() throws Exception {
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(enableSeqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableUnseqSpaceCompaction(enableUnseqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableCrossSpaceCompaction(enableCrossSpaceCompaction);
+ EnvironmentUtils.cleanEnv();
+ }
+
+ @Test
+ public void countAllAlignedWithoutTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"20", "29", "28", "19", "20"};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s2)",
+ "count(root.sg1.d1.s3)",
+ "count(root.sg1.d1.s4)",
+ "count(root.sg1.d1.s5)"
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet = statement.execute("select count(*) from
root.sg1.d1");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>(); // used to adjust result
sequence
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ String[] ans = new String[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = resultSet.getString(index);
+ }
+ assertArrayEquals(retArray, ans);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void countAllAlignedAndNonAlignedWithoutTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"20", "29", "28", "19", "20", "19",
"29", "28", "18", "19"};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s2)",
+ "count(root.sg1.d1.s3)",
+ "count(root.sg1.d1.s4)",
+ "count(root.sg1.d1.s5)",
+ "count(root.sg1.d2.s1)",
+ "count(root.sg1.d2.s2)",
+ "count(root.sg1.d2.s3)",
+ "count(root.sg1.d2.s4)",
+ "count(root.sg1.d2.s5)"
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet = statement.execute("select count(*) from
root.sg1.*");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ String[] ans = new String[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = resultSet.getString(index);
+ }
+ assertArrayEquals(retArray, ans);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void countAllAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"12", "15", "22", "13", "6"};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s2)",
+ "count(root.sg1.d1.s3)",
+ "count(root.sg1.d1.s4)",
+ "count(root.sg1.d1.s5)"
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select count(*) from root.sg1.d1 where time >= 9
and time <= 33");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ String[] ans = new String[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = resultSet.getString(index);
+ }
+ assertArrayEquals(retArray, ans);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ /** aggregate multi columns of aligned timeseries in one SQL */
+ @Test
+ public void aggregateSomeAlignedWithoutTimeFilterTest() throws
ClassNotFoundException {
+ double[] retArray =
+ new double[] {
+ 20, 29, 28, 390184, 130549, 390417, 19509.2, 4501.689655172413,
13943.464285714286
+ };
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s2)",
+ "count(root.sg1.d1.s3)",
+ "sum(root.sg1.d1.s1)",
+ "sum(root.sg1.d1.s2)",
+ "sum(root.sg1.d1.s3)",
+ "avg(root.sg1.d1.s1)",
+ "avg(root.sg1.d1.s2)",
+ "avg(root.sg1.d1.s3)",
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute(
+ "select count(s1),count (s2),count
(s3),sum(s1),sum(s2),sum(s3),avg(s1),avg(s2),avg(s3) from root.sg1.d1");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ double[] ans = new double[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = Double.parseDouble(resultSet.getString(index));
+ }
+ assertArrayEquals(retArray, ans, DELTA);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ /** aggregate multi columns of aligned timeseries in one SQL */
+ @Test
+ public void aggregateSomeAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ double[] retArray =
+ new double[] {
+ 6, 9, 15, 230090, 220, 230322, 38348.333333333336,
24.444444444444443, 15354.8
+ };
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s2)",
+ "count(root.sg1.d1.s3)",
+ "sum(root.sg1.d1.s1)",
+ "sum(root.sg1.d1.s2)",
+ "sum(root.sg1.d1.s3)",
+ "avg(root.sg1.d1.s1)",
+ "avg(root.sg1.d1.s2)",
+ "avg(root.sg1.d1.s3)",
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute(
+ "select count(s1),count (s2),count
(s3),sum(s1),sum(s2),sum(s3),avg(s1),avg(s2),avg(s3) from root.sg1.d1 where
time>=16 and time<=34");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ double[] ans = new double[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = Double.parseDouble(resultSet.getString(index));
+ }
+ assertArrayEquals(retArray, ans, DELTA);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void countSingleAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"9"};
+ String[] columnNames = {"count(root.sg1.d1.s2)"};
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select count(s2) from root.sg1.d1 where time>=16
and time<=34");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ // No need to add time column for aggregation query
+ for (String columnName : columnNames) {
+ int index = map.get(columnName);
+ if (builder.length() != 0) {
+ builder.append(",");
+ }
+ builder.append(resultSet.getString(index));
+ }
+ assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void sumSingleAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"230322.0"};
+ String[] columnNames = {"sum(root.sg1.d1.s3)"};
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select sum(s3) from root.sg1.d1 where time>=16
and time<=34");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ // No need to add time column for aggregation query
+ for (String columnName : columnNames) {
+ int index = map.get(columnName);
+ if (builder.length() != 0) {
+ builder.append(",");
+ }
+ builder.append(resultSet.getString(index));
+ }
+ assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void avgSingleAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ double[][] retArray = {{24.444444444444443}};
+ String[] columnNames = {"avg(root.sg1.d1.s2)"};
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select avg(s2) from root.sg1.d1 where time>=16
and time<=34");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ double[] ans = new double[columnNames.length];
+ StringBuilder builder = new StringBuilder();
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = Double.parseDouble(resultSet.getString(index));
+ }
+ assertArrayEquals(retArray[cnt], ans, DELTA);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+}
diff --git
a/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterWithDeletion2IT.java
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterWithDeletion2IT.java
new file mode 100644
index 0000000..40f14e4
--- /dev/null
+++
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterWithDeletion2IT.java
@@ -0,0 +1,83 @@
+/*
+ * 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.db.integration.aligned;
+
+import org.apache.iotdb.db.conf.IoTDBDescriptor;
+import org.apache.iotdb.db.utils.EnvironmentUtils;
+import org.apache.iotdb.jdbc.Config;
+import org.apache.iotdb.tsfile.common.conf.TSFileDescriptor;
+
+import org.junit.AfterClass;
+import org.junit.BeforeClass;
+
+import java.sql.Connection;
+import java.sql.DriverManager;
+import java.sql.Statement;
+
+/** Let One chunk has more than one page. */
+public class IoTDBAggregationWithoutValueFilterWithDeletion2IT
+ extends IoTDBAggregationWithoutValueFilterWithDeletionIT {
+
+ private static int numOfPointsPerPage;
+
+ @BeforeClass
+ public static void setUp() throws Exception {
+ EnvironmentUtils.closeStatMonitor();
+ EnvironmentUtils.envSetUp();
+
+ enableSeqSpaceCompaction =
+ IoTDBDescriptor.getInstance().getConfig().isEnableSeqSpaceCompaction();
+ enableUnseqSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableUnseqSpaceCompaction();
+ enableCrossSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableCrossSpaceCompaction();
+ numOfPointsPerPage =
TSFileDescriptor.getInstance().getConfig().getMaxNumberOfPointsInPage();
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableUnseqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableCrossSpaceCompaction(false);
+ TSFileDescriptor.getInstance().getConfig().setMaxNumberOfPointsInPage(3);
+ AlignedWriteUtil.insertData();
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+ // TODO currently aligned data in memory doesn't support deletion, so we
flush all data to
+ // disk before doing deletion
+ statement.execute("flush");
+ statement.execute("delete timeseries root.sg1.d1.s2");
+ statement.execute("delete from root.sg1.d1.s1 where time <= 21");
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ @AfterClass
+ public static void tearDown() throws Exception {
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(enableSeqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableUnseqSpaceCompaction(enableUnseqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableCrossSpaceCompaction(enableCrossSpaceCompaction);
+
TSFileDescriptor.getInstance().getConfig().setMaxNumberOfPointsInPage(numOfPointsPerPage);
+ EnvironmentUtils.cleanEnv();
+ }
+}
diff --git
a/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterWithDeletionIT.java
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterWithDeletionIT.java
new file mode 100644
index 0000000..bf68c50
--- /dev/null
+++
b/server/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBAggregationWithoutValueFilterWithDeletionIT.java
@@ -0,0 +1,447 @@
+/*
+ * 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.db.integration.aligned;
+
+import org.apache.iotdb.db.conf.IoTDBDescriptor;
+import org.apache.iotdb.db.utils.EnvironmentUtils;
+import org.apache.iotdb.jdbc.Config;
+
+import org.junit.AfterClass;
+import org.junit.Assert;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import java.sql.*;
+import java.util.HashMap;
+import java.util.Map;
+
+import static org.junit.Assert.*;
+
+public class IoTDBAggregationWithoutValueFilterWithDeletionIT {
+
+ private static final double DELTA = 1e-6;
+ protected static boolean enableSeqSpaceCompaction;
+ protected static boolean enableUnseqSpaceCompaction;
+ protected static boolean enableCrossSpaceCompaction;
+
+ @BeforeClass
+ public static void setUp() throws Exception {
+ EnvironmentUtils.closeStatMonitor();
+ EnvironmentUtils.envSetUp();
+
+ enableSeqSpaceCompaction =
+ IoTDBDescriptor.getInstance().getConfig().isEnableSeqSpaceCompaction();
+ enableUnseqSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableUnseqSpaceCompaction();
+ enableCrossSpaceCompaction =
+
IoTDBDescriptor.getInstance().getConfig().isEnableCrossSpaceCompaction();
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableUnseqSpaceCompaction(false);
+
IoTDBDescriptor.getInstance().getConfig().setEnableCrossSpaceCompaction(false);
+
+ AlignedWriteUtil.insertData();
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+ // TODO currently aligned data in memory doesn't support deletion, so we
flush all data to
+ // disk before doing deletion
+ statement.execute("flush");
+ statement.execute("delete timeseries root.sg1.d1.s2");
+ statement.execute("delete from root.sg1.d1.s1 where time <= 21");
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ @AfterClass
+ public static void tearDown() throws Exception {
+
IoTDBDescriptor.getInstance().getConfig().setEnableSeqSpaceCompaction(enableSeqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableUnseqSpaceCompaction(enableUnseqSpaceCompaction);
+ IoTDBDescriptor.getInstance()
+ .getConfig()
+ .setEnableCrossSpaceCompaction(enableCrossSpaceCompaction);
+ EnvironmentUtils.cleanEnv();
+ }
+
+ @Test
+ public void countAllAlignedWithoutTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"1", "28", "19", "20"};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s3)",
+ "count(root.sg1.d1.s4)",
+ "count(root.sg1.d1.s5)"
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet = statement.execute("select count(*) from
root.sg1.d1");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>(); // used to adjust result
sequence
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ String[] ans = new String[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = resultSet.getString(index);
+ }
+ assertArrayEquals(retArray, ans);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void countAllAlignedAndNonAlignedWithoutTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"1", "28", "19", "20", "19", "29", "28",
"18", "19"};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s3)",
+ "count(root.sg1.d1.s4)",
+ "count(root.sg1.d1.s5)",
+ "count(root.sg1.d2.s1)",
+ "count(root.sg1.d2.s2)",
+ "count(root.sg1.d2.s3)",
+ "count(root.sg1.d2.s4)",
+ "count(root.sg1.d2.s5)"
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet = statement.execute("select count(*) from
root.sg1.*");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ String[] ans = new String[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = resultSet.getString(index);
+ }
+ assertArrayEquals(retArray, ans);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void countAllAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"1", "22", "13", "6"};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s3)",
+ "count(root.sg1.d1.s4)",
+ "count(root.sg1.d1.s5)"
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select count(*) from root.sg1.d1 where time >= 9
and time <= 33");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ String[] ans = new String[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = resultSet.getString(index);
+ }
+ assertArrayEquals(retArray, ans);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ /** aggregate multi columns of aligned timeseries in one SQL */
+ @Test
+ public void aggregateSomeAlignedWithoutTimeFilterTest() throws
ClassNotFoundException {
+ double[] retArray = new double[] {1, 28, 230000, 390417, 230000,
13943.464285714286};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s3)",
+ "sum(root.sg1.d1.s1)",
+ "sum(root.sg1.d1.s3)",
+ "avg(root.sg1.d1.s1)",
+ "avg(root.sg1.d1.s3)",
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute(
+ "select count(s1),count (s3),sum(s1),sum(s3),avg(s1),avg(s3)
from root.sg1.d1");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ double[] ans = new double[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = Double.parseDouble(resultSet.getString(index));
+ }
+ assertArrayEquals(retArray, ans, DELTA);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ /** aggregate multi columns of aligned timeseries in one SQL */
+ @Test
+ public void aggregateSomeAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ double[] retArray = new double[] {1, 15, 230000, 230322, 230000, 15354.8};
+ String[] columnNames = {
+ "count(root.sg1.d1.s1)",
+ "count(root.sg1.d1.s3)",
+ "sum(root.sg1.d1.s1)",
+ "sum(root.sg1.d1.s3)",
+ "avg(root.sg1.d1.s1)",
+ "avg(root.sg1.d1.s3)",
+ };
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute(
+ "select count(s1),count (s3),sum(s1),sum(s3),avg(s1),avg(s3)
from root.sg1.d1 where time>=16 and time<=34");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ double[] ans = new double[columnNames.length];
+ // No need to add time column for aggregation query
+ for (int i = 0; i < columnNames.length; i++) {
+ String columnName = columnNames[i];
+ int index = map.get(columnName);
+ ans[i] = Double.parseDouble(resultSet.getString(index));
+ }
+ assertArrayEquals(retArray, ans, DELTA);
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void countSingleAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"0"};
+ String[] columnNames = {"count(root.sg1.d1.s1)"};
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select count(s1) from root.sg1.d1 where time>=16
and time<=20");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ // No need to add time column for aggregation query
+ for (String columnName : columnNames) {
+ int index = map.get(columnName);
+ if (builder.length() != 0) {
+ builder.append(",");
+ }
+ builder.append(resultSet.getString(index));
+ }
+ assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void sumSingleAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"null"};
+ String[] columnNames = {"sum(root.sg1.d1.s1)"};
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select sum(s1) from root.sg1.d1 where time>=16
and time<=20");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ // No need to add time column for aggregation query
+ for (String columnName : columnNames) {
+ int index = map.get(columnName);
+ if (builder.length() != 0) {
+ builder.append(",");
+ }
+ builder.append(resultSet.getString(index));
+ }
+ assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void avgSingleAlignedWithTimeFilterTest() throws
ClassNotFoundException {
+ String[] retArray = new String[] {"null"};
+ String[] columnNames = {"avg(root.sg1.d1.s1)"};
+ Class.forName(Config.JDBC_DRIVER_NAME);
+ try (Connection connection =
+ DriverManager.getConnection(
+ Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
+ Statement statement = connection.createStatement()) {
+
+ boolean hasResultSet =
+ statement.execute("select avg(s1) from root.sg1.d1 where time>=16
and time<=20");
+ Assert.assertTrue(hasResultSet);
+ try (ResultSet resultSet = statement.getResultSet()) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ Map<String, Integer> map = new HashMap<>();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ map.put(resultSetMetaData.getColumnName(i), i);
+ }
+ assertEquals(columnNames.length, resultSetMetaData.getColumnCount());
+ int cnt = 0;
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ // No need to add time column for aggregation query
+ for (String columnName : columnNames) {
+ int index = map.get(columnName);
+ if (builder.length() != 0) {
+ builder.append(",");
+ }
+ builder.append(resultSet.getString(index));
+ }
+ assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ assertEquals(1, cnt);
+ }
+ } catch (SQLException e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+}
diff --git
a/tsfile/src/main/java/org/apache/iotdb/tsfile/read/common/BatchData.java
b/tsfile/src/main/java/org/apache/iotdb/tsfile/read/common/BatchData.java
index 5907cfc..981a4f5 100644
--- a/tsfile/src/main/java/org/apache/iotdb/tsfile/read/common/BatchData.java
+++ b/tsfile/src/main/java/org/apache/iotdb/tsfile/read/common/BatchData.java
@@ -870,5 +870,21 @@ public class BatchData {
TsPrimitiveType v = getVector()[subIndex];
return v == null ? null : v.getValue();
}
+
+ @Override
+ public int totalLength() {
+ // aligned timeseries' BatchData length() may return the length of time
column
+ // we need traverse to VectorBatchDataIterator calculate the actual
value column's length
+ int cnt = 0;
+ int readCurArrayIndexSave = BatchData.this.readCurArrayIndex;
+ int readCurListIndexSave = BatchData.this.readCurListIndex;
+ while (hasNext()) {
+ cnt++;
+ next();
+ }
+ BatchData.this.readCurArrayIndex = readCurArrayIndexSave;
+ BatchData.this.readCurListIndex = readCurListIndexSave;
+ return cnt;
+ }
}
}