You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@iotdb.apache.org by zy...@apache.org on 2022/09/16 07:15:28 UTC
[iotdb] branch master updated: [IOTDB-3184] Implement Delete Timeseries for Cluster (#7242)
This is an automated email from the ASF dual-hosted git repository.
zyk 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 2f61131359 [IOTDB-3184] Implement Delete Timeseries for Cluster (#7242)
2f61131359 is described below
commit 2f6113135904f9217b7f357f182d9cd15ce59bb1
Author: Marcos_Zyk <38...@users.noreply.github.com>
AuthorDate: Fri Sep 16 15:15:20 2022 +0800
[IOTDB-3184] Implement Delete Timeseries for Cluster (#7242)
[IOTDB-3184] Implement Delete Timeseries for Cluster (#7242)
---
.../confignode/client/DataNodeRequestType.java | 7 +
.../async/datanode/AsyncDataNodeClientPool.java | 94 +++
.../async/handlers/AbstractRetryHandler.java | 19 +
.../handlers/ConstructSchemaBlackListHandler.java | 95 +++
.../DeleteDataForDeleteTimeSeriesHandler.java | 103 ++++
.../async/handlers/DeleteTimeSeriesHandler.java | 93 +++
.../handlers/FetchSchemaBlackLsitHandler.java | 101 ++++
.../InvalidateMatchedSchemaCacheHandler.java | 95 +++
.../handlers/RollbackSchemaBlackListHandler.java | 99 ++++
.../AbstractDataNodeTask.java} | 45 +-
.../ConstructSchemaBlackListDataNodeTask.java} | 39 +-
...DeleteDataForDeleteTimeSeriesDataNodeTask.java} | 38 +-
.../DeleteTimeSeriesDataNodeTask.java} | 39 +-
.../FetchSchemaBlackListDataNodeTask.java} | 40 +-
.../InvalidateMatchedSchemaCacheDataNodeTask.java} | 38 +-
.../RollbackSchemaBlackListDataNodeTask.java} | 39 +-
.../iotdb/confignode/manager/ConfigManager.java | 80 +++
.../apache/iotdb/confignode/manager/IManager.java | 7 +
.../iotdb/confignode/manager/ProcedureManager.java | 69 ++-
.../procedure/impl/DeleteTimeSeriesProcedure.java | 639 +++++++++++++++++++++
.../state/DeleteTimeSeriesState.java} | 33 +-
.../procedure/store/ProcedureFactory.java | 9 +-
.../thrift/ConfigNodeRPCServiceProcessor.java | 6 +
.../impl/DeleteTimeSeriesProcedureTest.java | 67 +++
.../org/apache/iotdb/db/it/IoTDBCompleteIT.java | 495 ----------------
.../it/schema/IoTDBCreateAlignedTimeseriesIT.java | 9 +-
.../it/schema/IoTDBDeleteAlignedTimeseriesIT.java | 248 ++++++++
.../db/it/schema/IoTDBDeleteTimeseriesIT.java | 406 +++++++++++++
.../org/apache/iotdb/db/it/schema/IoTDBTagIT.java | 23 +-
.../iotdb/db/integration/IoTDBCompleteIT.java | 491 ----------------
.../IoTDBCreateAlignedTimeseriesIT.java | 115 ----
.../db/integration/IoTDBDeleteTimeseriesIT.java | 215 -------
.../apache/iotdb/db/integration/IoTDBTagIT.java | 315 ----------
.../aligned/IoTDBDeleteTimeseriesIT.java | 281 ---------
.../schemaregion/rocksdb/RSchemaRegion.java | 22 +
.../rocksdb/mnode/RMeasurementMNode.java | 8 +
.../apache/iotdb/db/client/ConfigNodeClient.java | 17 +
.../iotdb/db/client/DataNodeClientPoolFactory.java | 20 +
.../metadata/MeasurementInBlackListException.java} | 30 +-
.../db/metadata/cache/DataNodeSchemaCache.java | 33 ++
.../idtable/entry/InsertMeasurementMNode.java | 8 +
.../iotdb/db/metadata/mnode/IMeasurementMNode.java | 4 +
.../iotdb/db/metadata/mnode/MeasurementMNode.java | 12 +
.../db/metadata/mtree/MTreeBelowSGMemoryImpl.java | 39 +-
.../mtree/snapshot/MemMTreeSnapshotUtil.java | 2 +
.../db/metadata/schemaregion/ISchemaRegion.java | 27 +
.../schemaregion/SchemaRegionMemoryImpl.java | 103 ++++
.../schemaregion/SchemaRegionSchemaFileImpl.java | 22 +
.../metadata/visitor/SchemaExecutionVisitor.java | 38 ++
.../db/mpp/common/schematree/PathPatternTree.java | 10 +
.../db/mpp/plan/analyze/ClusterSchemaFetcher.java | 139 ++---
.../mpp/plan/execution/config/ConfigExecution.java | 5 +-
.../plan/execution/config/ConfigTaskVisitor.java | 21 +-
.../config/executor/ClusterConfigTaskExecutor.java | 67 +++
.../config/executor/IConfigTaskExecutor.java | 4 +
.../executor/StandaloneConfigTaskExecutor.java | 12 +
.../config/metadata/DeleteTimeSeriesTask.java | 45 ++
.../iotdb/db/mpp/plan/parser/ASTVisitor.java | 2 +-
.../mpp/plan/planner/plan/node/PlanNodeType.java | 10 +-
.../db/mpp/plan/planner/plan/node/PlanVisitor.java | 10 +
.../write/ConstructSchemaBlackListNode.java | 91 +++
.../node/metedata/write/DeleteTimeSeriesNode.java | 63 +-
.../write/RollbackSchemaBlackListNode.java | 91 +++
.../metadata/DeleteTimeSeriesStatement.java | 27 +-
.../org/apache/iotdb/db/qp/logical/Operator.java | 4 +-
.../apache/iotdb/db/qp/physical/PhysicalPlan.java | 12 +-
.../qp/physical/sys/PreDeleteTimeSeriesPlan.java | 79 +++
.../sys/RollbackPreDeleteTimeSeriesPlan.java | 79 +++
.../impl/DataNodeInternalRPCServiceImpl.java | 326 ++++++-----
.../service/thrift/impl/DataNodeRegionManager.java | 317 ++++++++++
.../write/DeleteTimeSeriesNodeSerdeTest.java | 15 +-
.../java/org/apache/iotdb/rpc/TSStatusCode.java | 4 +-
.../src/main/thrift/confignode.thrift | 14 +
thrift/src/main/thrift/datanode.thrift | 71 +++
74 files changed, 3965 insertions(+), 2430 deletions(-)
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java
index 7ed20d7e94..6dd63a384d 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java
@@ -45,4 +45,11 @@ public enum DataNodeRequestType {
FULL_MERGE,
LOAD_CONFIGURATION,
SET_SYSTEM_STATUS,
+
+ CONSTRUCT_SCHEMA_BLACK_LIST,
+ ROLLBACK_SCHEMA_BLACK_LIST,
+ FETCH_SCHEMA_BLACK_LIST,
+ INVALIDATE_MATCHED_SCHEMA_CACHE,
+ DELETE_DATA_FOR_DELETE_TIMESERIES,
+ DELETE_TIMESERIES
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/datanode/AsyncDataNodeClientPool.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/datanode/AsyncDataNodeClientPool.java
index 557d898ca3..e477fa4105 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/datanode/AsyncDataNodeClientPool.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/datanode/AsyncDataNodeClientPool.java
@@ -32,21 +32,34 @@ import org.apache.iotdb.commons.client.async.AsyncDataNodeInternalServiceClient;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
import org.apache.iotdb.confignode.client.async.handlers.ClearCacheHandler;
+import org.apache.iotdb.confignode.client.async.handlers.ConstructSchemaBlackListHandler;
import org.apache.iotdb.confignode.client.async.handlers.CreateRegionHandler;
+import org.apache.iotdb.confignode.client.async.handlers.DeleteDataForDeleteTimeSeriesHandler;
+import org.apache.iotdb.confignode.client.async.handlers.DeleteTimeSeriesHandler;
+import org.apache.iotdb.confignode.client.async.handlers.FetchSchemaBlackLsitHandler;
import org.apache.iotdb.confignode.client.async.handlers.FlushHandler;
import org.apache.iotdb.confignode.client.async.handlers.FunctionManagementHandler;
+import org.apache.iotdb.confignode.client.async.handlers.InvalidateMatchedSchemaCacheHandler;
import org.apache.iotdb.confignode.client.async.handlers.LoadConfigurationHandler;
import org.apache.iotdb.confignode.client.async.handlers.MergeHandler;
+import org.apache.iotdb.confignode.client.async.handlers.RollbackSchemaBlackListHandler;
import org.apache.iotdb.confignode.client.async.handlers.SetSystemStatusHandler;
import org.apache.iotdb.confignode.client.async.handlers.SetTTLHandler;
import org.apache.iotdb.confignode.client.async.handlers.UpdateConfigNodeGroupHandler;
import org.apache.iotdb.confignode.client.async.handlers.UpdateRegionRouteMapHandler;
+import org.apache.iotdb.confignode.client.async.task.AbstractDataNodeTask;
import org.apache.iotdb.confignode.consensus.request.write.CreateRegionGroupsPlan;
+import org.apache.iotdb.mpp.rpc.thrift.TConstructSchemaBlackListReq;
import org.apache.iotdb.mpp.rpc.thrift.TCreateDataRegionReq;
import org.apache.iotdb.mpp.rpc.thrift.TCreateFunctionRequest;
import org.apache.iotdb.mpp.rpc.thrift.TCreateSchemaRegionReq;
+import org.apache.iotdb.mpp.rpc.thrift.TDeleteDataForDeleteTimeSeriesReq;
+import org.apache.iotdb.mpp.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.mpp.rpc.thrift.TDropFunctionRequest;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListReq;
+import org.apache.iotdb.mpp.rpc.thrift.TInvalidateMatchedSchemaCacheReq;
import org.apache.iotdb.mpp.rpc.thrift.TRegionRouteReq;
+import org.apache.iotdb.mpp.rpc.thrift.TRollbackSchemaBlackListReq;
import org.apache.iotdb.mpp.rpc.thrift.TUpdateConfigNodeGroupReq;
import org.slf4j.Logger;
@@ -166,6 +179,35 @@ public class AsyncDataNodeClientPool {
new UpdateConfigNodeGroupHandler(
countDownLatch, requestType, targetDataNode, dataNodeLocationMap);
break;
+ case CONSTRUCT_SCHEMA_BLACK_LIST:
+ handler =
+ new ConstructSchemaBlackListHandler(
+ countDownLatch, targetDataNode, dataNodeLocationMap);
+ break;
+ case ROLLBACK_SCHEMA_BLACK_LIST:
+ handler =
+ new RollbackSchemaBlackListHandler(
+ countDownLatch, targetDataNode, dataNodeLocationMap);
+ break;
+ case FETCH_SCHEMA_BLACK_LIST:
+ handler =
+ new FetchSchemaBlackLsitHandler(
+ countDownLatch, targetDataNode, dataNodeLocationMap);
+ break;
+ case INVALIDATE_MATCHED_SCHEMA_CACHE:
+ handler =
+ new InvalidateMatchedSchemaCacheHandler(
+ countDownLatch, targetDataNode, dataNodeLocationMap);
+ break;
+ case DELETE_DATA_FOR_DELETE_TIMESERIES:
+ handler =
+ new DeleteDataForDeleteTimeSeriesHandler(
+ countDownLatch, targetDataNode, dataNodeLocationMap);
+ break;
+ case DELETE_TIMESERIES:
+ handler =
+ new DeleteTimeSeriesHandler(countDownLatch, targetDataNode, dataNodeLocationMap);
+ break;
default:
return;
}
@@ -183,6 +225,33 @@ public class AsyncDataNodeClientPool {
}
}
+ public void sendAsyncRequestToDataNodeWithRetry(
+ Object req, AbstractDataNodeTask<?> dataNodeTask) {
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap = dataNodeTask.getDataNodeLocationMap();
+ if (dataNodeLocationMap.isEmpty()) {
+ return;
+ }
+ for (int retry = 0; retry < MAX_RETRY_NUM; retry++) {
+ CountDownLatch countDownLatch = new CountDownLatch(dataNodeLocationMap.size());
+ for (TDataNodeLocation targetDataNode : dataNodeLocationMap.values()) {
+ AbstractRetryHandler handler = dataNodeTask.getSingleRequestHandler();
+ handler.setCountDownLatch(countDownLatch);
+ handler.setTargetDataNode(targetDataNode);
+ sendAsyncRequestToDataNode(targetDataNode, req, handler, retry);
+ }
+
+ try {
+ countDownLatch.await();
+ } catch (InterruptedException e) {
+ LOGGER.error("Interrupted during {} on ConfigNode", dataNodeTask.getDataNodeRequestType());
+ }
+ // Check if there is a node that fails to send the request, and retry if there is one
+ if (dataNodeLocationMap.isEmpty()) {
+ break;
+ }
+ }
+ }
+
public void sendAsyncRequestToDataNode(
TDataNodeLocation dataNodeLocation,
Object req,
@@ -230,6 +299,31 @@ public class AsyncDataNodeClientPool {
client.updateConfigNodeGroup(
(TUpdateConfigNodeGroupReq) req, (UpdateConfigNodeGroupHandler) handler);
break;
+ case CONSTRUCT_SCHEMA_BLACK_LIST:
+ client.constructSchemaBlackList(
+ (TConstructSchemaBlackListReq) req, (ConstructSchemaBlackListHandler) handler);
+ break;
+ case ROLLBACK_SCHEMA_BLACK_LIST:
+ client.rollbackSchemaBlackList(
+ (TRollbackSchemaBlackListReq) req, (RollbackSchemaBlackListHandler) handler);
+ break;
+ case FETCH_SCHEMA_BLACK_LIST:
+ client.fetchSchemaBlackList(
+ (TFetchSchemaBlackListReq) req, (FetchSchemaBlackLsitHandler) handler);
+ break;
+ case INVALIDATE_MATCHED_SCHEMA_CACHE:
+ client.invalidateMatchedSchemaCache(
+ (TInvalidateMatchedSchemaCacheReq) req,
+ (InvalidateMatchedSchemaCacheHandler) handler);
+ break;
+ case DELETE_DATA_FOR_DELETE_TIMESERIES:
+ client.deleteDataForDeleteTimeSeries(
+ (TDeleteDataForDeleteTimeSeriesReq) req,
+ (DeleteDataForDeleteTimeSeriesHandler) handler);
+ break;
+ case DELETE_TIMESERIES:
+ client.deleteTimeSeries((TDeleteTimeSeriesReq) req, (DeleteTimeSeriesHandler) handler);
+ break;
default:
LOGGER.error(
"Unexpected DataNode Request Type: {} when sendAsyncRequestToDataNode",
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
index 6d882ecbd2..b3a5fd9328 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
@@ -50,7 +50,26 @@ public abstract class AbstractRetryHandler {
this.targetDataNode = targetDataNode;
}
+ public AbstractRetryHandler(
+ DataNodeRequestType dataNodeRequestType,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ this.dataNodeLocationMap = dataNodeLocationMap;
+ this.dataNodeRequestType = dataNodeRequestType;
+ }
+
public DataNodeRequestType getDataNodeRequestType() {
return dataNodeRequestType;
}
+
+ public Map<Integer, TDataNodeLocation> getDataNodeLocationMap() {
+ return dataNodeLocationMap;
+ }
+
+ public void setCountDownLatch(CountDownLatch countDownLatch) {
+ this.countDownLatch = countDownLatch;
+ }
+
+ public void setTargetDataNode(TDataNodeLocation targetDataNode) {
+ this.targetDataNode = targetDataNode;
+ }
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/ConstructSchemaBlackListHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/ConstructSchemaBlackListHandler.java
new file mode 100644
index 0000000000..bce6a47d5b
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/ConstructSchemaBlackListHandler.java
@@ -0,0 +1,95 @@
+/*
+ * 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.confignode.client.async.handlers;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.apache.thrift.async.AsyncMethodCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CountDownLatch;
+
+public class ConstructSchemaBlackListHandler extends AbstractRetryHandler
+ implements AsyncMethodCallback<TSStatus> {
+
+ private static final Logger LOGGER =
+ LoggerFactory.getLogger(ConstructSchemaBlackListHandler.class);
+
+ private Map<Integer, TSStatus> dataNodeResponseStatusMap;
+
+ public ConstructSchemaBlackListHandler(
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap,
+ Map<Integer, TSStatus> dataNodeResponseStatusMap) {
+ super(DataNodeRequestType.CONSTRUCT_SCHEMA_BLACK_LIST, dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = dataNodeResponseStatusMap;
+ }
+
+ public ConstructSchemaBlackListHandler(
+ CountDownLatch countDownLatch,
+ TDataNodeLocation targetDataNode,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(
+ countDownLatch,
+ DataNodeRequestType.CONSTRUCT_SCHEMA_BLACK_LIST,
+ targetDataNode,
+ dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = new ConcurrentHashMap<>();
+ }
+
+ @Override
+ public void onComplete(TSStatus tsStatus) {
+ dataNodeResponseStatusMap.put(targetDataNode.getDataNodeId(), tsStatus);
+ if (tsStatus.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.info("Successfully construct schema black list on DataNode: {}", targetDataNode);
+ } else if (tsStatus.getCode() == TSStatusCode.MULTIPLE_ERROR.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.error(
+ "Failed to construct schema black list on DataNode {}, {}", targetDataNode, tsStatus);
+ } else {
+ LOGGER.error(
+ "Failed to construct schema black list on DataNode {}, {}", targetDataNode, tsStatus);
+ }
+ countDownLatch.countDown();
+ }
+
+ @Override
+ public void onError(Exception e) {
+ countDownLatch.countDown();
+ dataNodeResponseStatusMap.put(
+ targetDataNode.dataNodeId,
+ new TSStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode(),
+ "Construct schema black list error on DataNode: {id="
+ + targetDataNode.getDataNodeId()
+ + ", internalEndPoint="
+ + targetDataNode.getInternalEndPoint()
+ + "}"
+ + e.getMessage())));
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/DeleteDataForDeleteTimeSeriesHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/DeleteDataForDeleteTimeSeriesHandler.java
new file mode 100644
index 0000000000..d72fee586a
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/DeleteDataForDeleteTimeSeriesHandler.java
@@ -0,0 +1,103 @@
+/*
+ * 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.confignode.client.async.handlers;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.apache.thrift.async.AsyncMethodCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CountDownLatch;
+
+public class DeleteDataForDeleteTimeSeriesHandler extends AbstractRetryHandler
+ implements AsyncMethodCallback<TSStatus> {
+
+ private static final Logger LOGGER =
+ LoggerFactory.getLogger(DeleteDataForDeleteTimeSeriesHandler.class);
+
+ private Map<Integer, TSStatus> dataNodeResponseStatusMap;
+
+ public DeleteDataForDeleteTimeSeriesHandler(
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap,
+ Map<Integer, TSStatus> dataNodeResponseStatusMap) {
+ super(DataNodeRequestType.DELETE_DATA_FOR_DELETE_TIMESERIES, dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = dataNodeResponseStatusMap;
+ }
+
+ public DeleteDataForDeleteTimeSeriesHandler(
+ CountDownLatch countDownLatch,
+ TDataNodeLocation targetDataNode,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(
+ countDownLatch,
+ DataNodeRequestType.DELETE_DATA_FOR_DELETE_TIMESERIES,
+ targetDataNode,
+ dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = new ConcurrentHashMap<>();
+ }
+
+ public Map<Integer, TSStatus> getDataNodeResponseStatusMap() {
+ return dataNodeResponseStatusMap;
+ }
+
+ @Override
+ public void onComplete(TSStatus tsStatus) {
+ dataNodeResponseStatusMap.put(targetDataNode.getDataNodeId(), tsStatus);
+ if (tsStatus.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.info("Successfully delete data for delete timeseries on DataNode: {}", targetDataNode);
+ } else if (tsStatus.getCode() == TSStatusCode.MULTIPLE_ERROR.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.error(
+ "Failed to delete data for delete timeseries on DataNode {}, {}",
+ targetDataNode,
+ tsStatus);
+ } else {
+ LOGGER.error(
+ "Failed to delete data for delete timeseries on DataNode {}, {}",
+ targetDataNode,
+ tsStatus);
+ }
+ countDownLatch.countDown();
+ }
+
+ @Override
+ public void onError(Exception e) {
+ countDownLatch.countDown();
+ dataNodeResponseStatusMap.put(
+ targetDataNode.dataNodeId,
+ new TSStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode(),
+ "Delete data for delete timeseries error on DataNode: {id="
+ + targetDataNode.getDataNodeId()
+ + ", internalEndPoint="
+ + targetDataNode.getInternalEndPoint()
+ + "}"
+ + e.getMessage())));
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/DeleteTimeSeriesHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/DeleteTimeSeriesHandler.java
new file mode 100644
index 0000000000..e7c0cea47b
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/DeleteTimeSeriesHandler.java
@@ -0,0 +1,93 @@
+/*
+ * 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.confignode.client.async.handlers;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.apache.thrift.async.AsyncMethodCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CountDownLatch;
+
+public class DeleteTimeSeriesHandler extends AbstractRetryHandler
+ implements AsyncMethodCallback<TSStatus> {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(DeleteTimeSeriesHandler.class);
+
+ private Map<Integer, TSStatus> dataNodeResponseStatusMap;
+
+ public DeleteTimeSeriesHandler(
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap,
+ Map<Integer, TSStatus> dataNodeResponseStatusMap) {
+ super(DataNodeRequestType.DELETE_TIMESERIES, dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = dataNodeResponseStatusMap;
+ }
+
+ public DeleteTimeSeriesHandler(
+ CountDownLatch countDownLatch,
+ TDataNodeLocation targetDataNode,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(
+ countDownLatch, DataNodeRequestType.DELETE_TIMESERIES, targetDataNode, dataNodeLocationMap);
+ dataNodeResponseStatusMap = new ConcurrentHashMap<>();
+ }
+
+ public Map<Integer, TSStatus> getDataNodeResponseStatusMap() {
+ return dataNodeResponseStatusMap;
+ }
+
+ @Override
+ public void onComplete(TSStatus tsStatus) {
+ dataNodeResponseStatusMap.put(targetDataNode.getDataNodeId(), tsStatus);
+ if (tsStatus.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.info("Successfully delete timeseries on DataNode: {}", targetDataNode);
+ } else if (tsStatus.getCode() == TSStatusCode.MULTIPLE_ERROR.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.error("Failed to delete timeseries on DataNode {}, {}", targetDataNode, tsStatus);
+ } else {
+ LOGGER.error("Failed to delete timeseries on DataNode {}, {}", targetDataNode, tsStatus);
+ }
+ countDownLatch.countDown();
+ }
+
+ @Override
+ public void onError(Exception e) {
+ countDownLatch.countDown();
+ dataNodeResponseStatusMap.put(
+ targetDataNode.dataNodeId,
+ new TSStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode(),
+ "Delete timeseries error on DataNode: {id="
+ + targetDataNode.getDataNodeId()
+ + ", internalEndPoint="
+ + targetDataNode.getInternalEndPoint()
+ + "}"
+ + e.getMessage())));
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/FetchSchemaBlackLsitHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/FetchSchemaBlackLsitHandler.java
new file mode 100644
index 0000000000..9db74c5f59
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/FetchSchemaBlackLsitHandler.java
@@ -0,0 +1,101 @@
+/*
+ * 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.confignode.client.async.handlers;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListResp;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.apache.thrift.async.AsyncMethodCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CountDownLatch;
+
+public class FetchSchemaBlackLsitHandler extends AbstractRetryHandler
+ implements AsyncMethodCallback<TFetchSchemaBlackListResp> {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(FetchSchemaBlackLsitHandler.class);
+
+ private Map<Integer, TFetchSchemaBlackListResp> dataNodeResponseMap;
+
+ public FetchSchemaBlackLsitHandler(
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap,
+ Map<Integer, TFetchSchemaBlackListResp> dataNodeResponseMap) {
+ super(DataNodeRequestType.FETCH_SCHEMA_BLACK_LIST, dataNodeLocationMap);
+ this.dataNodeResponseMap = dataNodeResponseMap;
+ }
+
+ public FetchSchemaBlackLsitHandler(
+ CountDownLatch countDownLatch,
+ TDataNodeLocation targetDataNode,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(
+ countDownLatch,
+ DataNodeRequestType.FETCH_SCHEMA_BLACK_LIST,
+ targetDataNode,
+ dataNodeLocationMap);
+ this.dataNodeResponseMap = new ConcurrentHashMap<>();
+ }
+
+ public Map<Integer, TFetchSchemaBlackListResp> getDataNodeResponseMap() {
+ return dataNodeResponseMap;
+ }
+
+ @Override
+ public void onComplete(TFetchSchemaBlackListResp tFetchSchemaBlackListResp) {
+ TSStatus tsStatus = tFetchSchemaBlackListResp.getStatus();
+ dataNodeResponseMap.put(targetDataNode.getDataNodeId(), tFetchSchemaBlackListResp);
+ if (tsStatus.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.info("Successfully fetch schema black list on DataNode: {}", targetDataNode);
+ } else if (tsStatus.getCode() == TSStatusCode.MULTIPLE_ERROR.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.error(
+ "Failed to fetch schema black list on DataNode {}, {}", targetDataNode, tsStatus);
+ } else {
+ LOGGER.error(
+ "Failed to fetch schema black list on DataNode {}, {}", targetDataNode, tsStatus);
+ }
+ countDownLatch.countDown();
+ }
+
+ @Override
+ public void onError(Exception e) {
+ countDownLatch.countDown();
+ TFetchSchemaBlackListResp resp = new TFetchSchemaBlackListResp();
+ resp.setStatus(
+ new TSStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode(),
+ "Fetch schema black list error on DataNode: {id="
+ + targetDataNode.getDataNodeId()
+ + ", internalEndPoint="
+ + targetDataNode.getInternalEndPoint()
+ + "}"
+ + e.getMessage())));
+ dataNodeResponseMap.put(targetDataNode.getDataNodeId(), resp);
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/InvalidateMatchedSchemaCacheHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/InvalidateMatchedSchemaCacheHandler.java
new file mode 100644
index 0000000000..b620560fad
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/InvalidateMatchedSchemaCacheHandler.java
@@ -0,0 +1,95 @@
+/*
+ * 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.confignode.client.async.handlers;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.apache.thrift.async.AsyncMethodCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CountDownLatch;
+
+public class InvalidateMatchedSchemaCacheHandler extends AbstractRetryHandler
+ implements AsyncMethodCallback<TSStatus> {
+
+ private static final Logger LOGGER =
+ LoggerFactory.getLogger(InvalidateMatchedSchemaCacheHandler.class);
+
+ private Map<Integer, TSStatus> dataNodeResponseStatusMap;
+
+ public InvalidateMatchedSchemaCacheHandler(
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap,
+ Map<Integer, TSStatus> dataNodeResponseStatusMap) {
+ super(DataNodeRequestType.INVALIDATE_MATCHED_SCHEMA_CACHE, dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = dataNodeResponseStatusMap;
+ }
+
+ public InvalidateMatchedSchemaCacheHandler(
+ CountDownLatch countDownLatch,
+ TDataNodeLocation targetDataNode,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(
+ countDownLatch,
+ DataNodeRequestType.INVALIDATE_MATCHED_SCHEMA_CACHE,
+ targetDataNode,
+ dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = new ConcurrentHashMap<>();
+ }
+
+ public Map<Integer, TSStatus> getDataNodeResponseStatusMap() {
+ return dataNodeResponseStatusMap;
+ }
+
+ @Override
+ public void onComplete(TSStatus tsStatus) {
+ dataNodeResponseStatusMap.put(targetDataNode.getDataNodeId(), tsStatus);
+ if (tsStatus.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.info("Successfully invalidate matched schema cache on DataNode: {}", targetDataNode);
+ } else {
+ LOGGER.error(
+ "Failed to invalidate matched schema cache on DataNode {}, {}", targetDataNode, tsStatus);
+ }
+ countDownLatch.countDown();
+ }
+
+ @Override
+ public void onError(Exception e) {
+ countDownLatch.countDown();
+ dataNodeResponseStatusMap.put(
+ targetDataNode.getDataNodeId(),
+ new TSStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode(),
+ "Invalidate matched schema cache error on DataNode: {id="
+ + targetDataNode.getDataNodeId()
+ + ", internalEndPoint="
+ + targetDataNode.getInternalEndPoint()
+ + "}"
+ + e.getMessage())));
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/RollbackSchemaBlackListHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/RollbackSchemaBlackListHandler.java
new file mode 100644
index 0000000000..c1ea9b08f1
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/RollbackSchemaBlackListHandler.java
@@ -0,0 +1,99 @@
+/*
+ * 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.confignode.client.async.handlers;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.apache.thrift.async.AsyncMethodCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CountDownLatch;
+
+public class RollbackSchemaBlackListHandler extends AbstractRetryHandler
+ implements AsyncMethodCallback<TSStatus> {
+
+ private static final Logger LOGGER =
+ LoggerFactory.getLogger(RollbackSchemaBlackListHandler.class);
+
+ private Map<Integer, TSStatus> dataNodeResponseStatusMap;
+
+ public RollbackSchemaBlackListHandler(
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap,
+ Map<Integer, TSStatus> dataNodeResponseStatusMap) {
+ super(DataNodeRequestType.ROLLBACK_SCHEMA_BLACK_LIST, dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = dataNodeResponseStatusMap;
+ }
+
+ public RollbackSchemaBlackListHandler(
+ CountDownLatch countDownLatch,
+ TDataNodeLocation targetDataNode,
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(
+ countDownLatch,
+ DataNodeRequestType.ROLLBACK_SCHEMA_BLACK_LIST,
+ targetDataNode,
+ dataNodeLocationMap);
+ this.dataNodeResponseStatusMap = new ConcurrentHashMap<>();
+ }
+
+ public Map<Integer, TSStatus> getDataNodeResponseStatusMap() {
+ return dataNodeResponseStatusMap;
+ }
+
+ @Override
+ public void onComplete(TSStatus tsStatus) {
+ dataNodeResponseStatusMap.put(targetDataNode.getDataNodeId(), tsStatus);
+ if (tsStatus.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.info("Successfully rollback schema black list on DataNode: {}", targetDataNode);
+ } else if (tsStatus.getCode() == TSStatusCode.MULTIPLE_ERROR.getStatusCode()) {
+ dataNodeLocationMap.remove(targetDataNode.getDataNodeId());
+ LOGGER.error(
+ "Failed to rollback schema black list on DataNode {}, {}", targetDataNode, tsStatus);
+ } else {
+ LOGGER.error(
+ "Failed to rollback schema black list on DataNode {}, {}", targetDataNode, tsStatus);
+ }
+ countDownLatch.countDown();
+ }
+
+ @Override
+ public void onError(Exception e) {
+ countDownLatch.countDown();
+ dataNodeResponseStatusMap.put(
+ targetDataNode.getDataNodeId(),
+ new TSStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode(),
+ "Rollback schema black list error on DataNode: {id="
+ + targetDataNode.getDataNodeId()
+ + ", internalEndPoint="
+ + targetDataNode.getInternalEndPoint()
+ + "}"
+ + e.getMessage())));
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/AbstractDataNodeTask.java
similarity index 54%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/AbstractDataNodeTask.java
index 6d882ecbd2..10671031f0 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/AbstractDataNodeTask.java
@@ -17,40 +17,37 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.ConcurrentHashMap;
-public abstract class AbstractRetryHandler {
+public abstract class AbstractDataNodeTask<T> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
- Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
+
+ protected Map<Integer, T> dataNodeResponseMap = new ConcurrentHashMap<>();
+
+ /** Must provide thread-safe map */
+ public AbstractDataNodeTask(Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
}
- public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ public Map<Integer, TDataNodeLocation> getDataNodeLocationMap() {
+ return dataNodeLocationMap;
+ }
+
+ public abstract DataNodeRequestType getDataNodeRequestType();
+
+ /** Provide the handler for single rpc process */
+ public abstract AbstractRetryHandler getSingleRequestHandler();
+
+ /** Get the final responses from all dataNodes */
+ public Map<Integer, T> getDataNodeResponseMap() {
+ return dataNodeResponseMap;
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/ConstructSchemaBlackListDataNodeTask.java
similarity index 50%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/ConstructSchemaBlackListDataNodeTask.java
index 6d882ecbd2..9e12a1b61b 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/ConstructSchemaBlackListDataNodeTask.java
@@ -17,40 +17,29 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
+import org.apache.iotdb.confignode.client.async.handlers.ConstructSchemaBlackListHandler;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-public abstract class AbstractRetryHandler {
+public class ConstructSchemaBlackListDataNodeTask extends AbstractDataNodeTask<TSStatus> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
- protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
- Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
- this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
+ public ConstructSchemaBlackListDataNodeTask(Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(dataNodeLocationMap);
}
+ @Override
public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ return DataNodeRequestType.CONSTRUCT_SCHEMA_BLACK_LIST;
+ }
+
+ @Override
+ public AbstractRetryHandler getSingleRequestHandler() {
+ return new ConstructSchemaBlackListHandler(dataNodeLocationMap, dataNodeResponseMap);
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/DeleteDataForDeleteTimeSeriesDataNodeTask.java
similarity index 53%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/DeleteDataForDeleteTimeSeriesDataNodeTask.java
index 6d882ecbd2..089068aa51 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/DeleteDataForDeleteTimeSeriesDataNodeTask.java
@@ -17,40 +17,30 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
+import org.apache.iotdb.confignode.client.async.handlers.DeleteDataForDeleteTimeSeriesHandler;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-public abstract class AbstractRetryHandler {
+public class DeleteDataForDeleteTimeSeriesDataNodeTask extends AbstractDataNodeTask<TSStatus> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
- protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
+ public DeleteDataForDeleteTimeSeriesDataNodeTask(
Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
- this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
+ super(dataNodeLocationMap);
}
+ @Override
public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ return DataNodeRequestType.DELETE_DATA_FOR_DELETE_TIMESERIES;
+ }
+
+ @Override
+ public AbstractRetryHandler getSingleRequestHandler() {
+ return new DeleteDataForDeleteTimeSeriesHandler(dataNodeLocationMap, dataNodeResponseMap);
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/DeleteTimeSeriesDataNodeTask.java
similarity index 50%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/DeleteTimeSeriesDataNodeTask.java
index 6d882ecbd2..caf67790c2 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/DeleteTimeSeriesDataNodeTask.java
@@ -17,40 +17,29 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
+import org.apache.iotdb.confignode.client.async.handlers.DeleteTimeSeriesHandler;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-public abstract class AbstractRetryHandler {
+public class DeleteTimeSeriesDataNodeTask extends AbstractDataNodeTask<TSStatus> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
- protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
- Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
- this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
+ public DeleteTimeSeriesDataNodeTask(Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(dataNodeLocationMap);
}
+ @Override
public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ return DataNodeRequestType.DELETE_TIMESERIES;
+ }
+
+ @Override
+ public AbstractRetryHandler getSingleRequestHandler() {
+ return new DeleteTimeSeriesHandler(dataNodeLocationMap, dataNodeResponseMap);
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/FetchSchemaBlackListDataNodeTask.java
similarity index 50%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/FetchSchemaBlackListDataNodeTask.java
index 6d882ecbd2..8545b7dd5c 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/FetchSchemaBlackListDataNodeTask.java
@@ -17,40 +17,30 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
+import org.apache.iotdb.confignode.client.async.handlers.FetchSchemaBlackLsitHandler;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListResp;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-public abstract class AbstractRetryHandler {
+public class FetchSchemaBlackListDataNodeTask
+ extends AbstractDataNodeTask<TFetchSchemaBlackListResp> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
- protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
- Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
- this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
+ public FetchSchemaBlackListDataNodeTask(Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(dataNodeLocationMap);
}
+ @Override
public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ return DataNodeRequestType.FETCH_SCHEMA_BLACK_LIST;
+ }
+
+ @Override
+ public AbstractRetryHandler getSingleRequestHandler() {
+ return new FetchSchemaBlackLsitHandler(dataNodeLocationMap, dataNodeResponseMap);
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/InvalidateMatchedSchemaCacheDataNodeTask.java
similarity index 53%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/InvalidateMatchedSchemaCacheDataNodeTask.java
index 6d882ecbd2..2a08fdcb99 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/InvalidateMatchedSchemaCacheDataNodeTask.java
@@ -17,40 +17,30 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
+import org.apache.iotdb.confignode.client.async.handlers.InvalidateMatchedSchemaCacheHandler;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-public abstract class AbstractRetryHandler {
+public class InvalidateMatchedSchemaCacheDataNodeTask extends AbstractDataNodeTask<TSStatus> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
- protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
+ public InvalidateMatchedSchemaCacheDataNodeTask(
Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
- this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
+ super(dataNodeLocationMap);
}
+ @Override
public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ return DataNodeRequestType.INVALIDATE_MATCHED_SCHEMA_CACHE;
+ }
+
+ @Override
+ public AbstractRetryHandler getSingleRequestHandler() {
+ return new InvalidateMatchedSchemaCacheHandler(dataNodeLocationMap, dataNodeResponseMap);
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/RollbackSchemaBlackListDataNodeTask.java
similarity index 50%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/RollbackSchemaBlackListDataNodeTask.java
index 6d882ecbd2..3a24ae7898 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/async/handlers/AbstractRetryHandler.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/client/async/task/RollbackSchemaBlackListDataNodeTask.java
@@ -17,40 +17,29 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client.async.handlers;
+package org.apache.iotdb.confignode.client.async.task;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.confignode.client.DataNodeRequestType;
+import org.apache.iotdb.confignode.client.async.handlers.AbstractRetryHandler;
+import org.apache.iotdb.confignode.client.async.handlers.RollbackSchemaBlackListHandler;
import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-public abstract class AbstractRetryHandler {
+public class RollbackSchemaBlackListDataNodeTask extends AbstractDataNodeTask<TSStatus> {
- protected CountDownLatch countDownLatch;
-
- /**
- * Map<DataNodeId, TDataNodeLocation> The DataNode that successfully execute the request will be
- * removed from this list
- */
- protected Map<Integer, TDataNodeLocation> dataNodeLocationMap;
- /** Request type to DataNode */
- protected DataNodeRequestType dataNodeRequestType;
- /** Target DataNode */
- protected TDataNodeLocation targetDataNode;
-
- public AbstractRetryHandler(
- CountDownLatch countDownLatch,
- DataNodeRequestType dataNodeRequestType,
- TDataNodeLocation targetDataNode,
- Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
- this.countDownLatch = countDownLatch;
- this.dataNodeLocationMap = dataNodeLocationMap;
- this.dataNodeRequestType = dataNodeRequestType;
- this.targetDataNode = targetDataNode;
+ public RollbackSchemaBlackListDataNodeTask(Map<Integer, TDataNodeLocation> dataNodeLocationMap) {
+ super(dataNodeLocationMap);
}
+ @Override
public DataNodeRequestType getDataNodeRequestType() {
- return dataNodeRequestType;
+ return DataNodeRequestType.ROLLBACK_SCHEMA_BLACK_LIST;
+ }
+
+ @Override
+ public AbstractRetryHandler getSingleRequestHandler() {
+ return new RollbackSchemaBlackListHandler(dataNodeLocationMap, dataNodeResponseMap);
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/manager/ConfigManager.java b/confignode/src/main/java/org/apache/iotdb/confignode/manager/ConfigManager.java
index d19b889a7a..77766d78ed 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/manager/ConfigManager.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/manager/ConfigManager.java
@@ -25,8 +25,10 @@ import org.apache.iotdb.common.rpc.thrift.TConsensusGroupType;
import org.apache.iotdb.common.rpc.thrift.TDataNodeConfiguration;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
import org.apache.iotdb.common.rpc.thrift.TFlushReq;
+import org.apache.iotdb.common.rpc.thrift.TRegionReplicaSet;
import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.common.rpc.thrift.TSeriesPartitionSlot;
+import org.apache.iotdb.common.rpc.thrift.TTimePartitionSlot;
import org.apache.iotdb.commons.cluster.RegionRoleType;
import org.apache.iotdb.commons.conf.CommonDescriptor;
import org.apache.iotdb.commons.conf.IoTDBConstant;
@@ -79,6 +81,7 @@ import org.apache.iotdb.confignode.rpc.thrift.TConfigNodeRegisterReq;
import org.apache.iotdb.confignode.rpc.thrift.TCreateSchemaTemplateReq;
import org.apache.iotdb.confignode.rpc.thrift.TDataNodeInfo;
import org.apache.iotdb.confignode.rpc.thrift.TDataPartitionTableResp;
+import org.apache.iotdb.confignode.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.confignode.rpc.thrift.TGetAllTemplatesResp;
import org.apache.iotdb.confignode.rpc.thrift.TGetPathsSetTemplatesResp;
import org.apache.iotdb.confignode.rpc.thrift.TGetTemplateResp;
@@ -106,6 +109,7 @@ import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
+import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
@@ -966,4 +970,80 @@ public class ConfigManager implements IManager {
return new TGetPathsSetTemplatesResp(status);
}
}
+
+ @Override
+ public TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req) {
+ TSStatus status = confirmLeader();
+ if (status.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ return procedureManager.deleteTimeSeries(req);
+ } else {
+ return status;
+ }
+ }
+
+ /** Get all related schemaRegion which may contains the timeseries matched by given patternTree */
+ public Map<TConsensusGroupId, TRegionReplicaSet> getRelatedSchemaRegionGroup(
+ PathPatternTree patternTree) {
+ Map<String, Map<TSeriesPartitionSlot, TConsensusGroupId>> schemaPartitionTable =
+ getSchemaPartition(patternTree).getSchemaPartitionTable();
+
+ List<TRegionReplicaSet> allRegionReplicaSets = getPartitionManager().getAllReplicaSets();
+ Set<TConsensusGroupId> groupIdSet =
+ schemaPartitionTable.values().stream()
+ .flatMap(m -> m.values().stream())
+ .collect(Collectors.toSet());
+ Map<TConsensusGroupId, TRegionReplicaSet> filteredRegionReplicaSets = new HashMap<>();
+ for (TRegionReplicaSet regionReplicaSet : allRegionReplicaSets) {
+ if (groupIdSet.contains(regionReplicaSet.getRegionId())) {
+ filteredRegionReplicaSets.put(regionReplicaSet.getRegionId(), regionReplicaSet);
+ }
+ }
+ return filteredRegionReplicaSets;
+ }
+
+ /**
+ * Get all related dataRegion which may contains the data of specific timeseries matched by given
+ * patternTree
+ */
+ public Map<TConsensusGroupId, TRegionReplicaSet> getRelatedDataRegionGroup(
+ PathPatternTree patternTree) {
+ // get all storage group and slot by getting schema partition
+ Map<String, Map<TSeriesPartitionSlot, TConsensusGroupId>> schemaPartitionTable =
+ getSchemaPartition(patternTree).getSchemaPartitionTable();
+
+ // construct request for getting data partition
+ Map<String, Map<TSeriesPartitionSlot, List<TTimePartitionSlot>>> partitionSlotsMap =
+ new HashMap<>();
+ schemaPartitionTable.forEach(
+ (key, value) -> {
+ Map<TSeriesPartitionSlot, List<TTimePartitionSlot>> slotListMap = new HashMap<>();
+ value.keySet().forEach(slot -> slotListMap.put(slot, Collections.emptyList()));
+ partitionSlotsMap.put(key, slotListMap);
+ });
+
+ // get all data partitions
+ GetDataPartitionPlan getDataPartitionPlan = new GetDataPartitionPlan(partitionSlotsMap);
+ Map<String, Map<TSeriesPartitionSlot, Map<TTimePartitionSlot, List<TConsensusGroupId>>>>
+ dataPartitionTable = getDataPartition(getDataPartitionPlan).getDataPartitionTable();
+
+ // get all region replicaset of target data partitions
+ List<TRegionReplicaSet> allRegionReplicaSets = getPartitionManager().getAllReplicaSets();
+ Set<TConsensusGroupId> groupIdSet =
+ dataPartitionTable.values().stream()
+ .flatMap(
+ tSeriesPartitionSlotMapMap ->
+ tSeriesPartitionSlotMapMap.values().stream()
+ .flatMap(
+ tTimePartitionSlotListMap ->
+ tTimePartitionSlotListMap.values().stream()
+ .flatMap(Collection::stream)))
+ .collect(Collectors.toSet());
+ Map<TConsensusGroupId, TRegionReplicaSet> filteredRegionReplicaSets = new HashMap<>();
+ for (TRegionReplicaSet regionReplicaSet : allRegionReplicaSets) {
+ if (groupIdSet.contains(regionReplicaSet.getRegionId())) {
+ filteredRegionReplicaSets.put(regionReplicaSet.getRegionId(), regionReplicaSet);
+ }
+ }
+ return filteredRegionReplicaSets;
+ }
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/manager/IManager.java b/confignode/src/main/java/org/apache/iotdb/confignode/manager/IManager.java
index b989356542..08024d440f 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/manager/IManager.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/manager/IManager.java
@@ -41,6 +41,7 @@ import org.apache.iotdb.confignode.manager.load.LoadManager;
import org.apache.iotdb.confignode.rpc.thrift.TConfigNodeRegisterReq;
import org.apache.iotdb.confignode.rpc.thrift.TCreateSchemaTemplateReq;
import org.apache.iotdb.confignode.rpc.thrift.TDataPartitionTableResp;
+import org.apache.iotdb.confignode.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.confignode.rpc.thrift.TGetAllTemplatesResp;
import org.apache.iotdb.confignode.rpc.thrift.TGetPathsSetTemplatesResp;
import org.apache.iotdb.confignode.rpc.thrift.TGetTemplateResp;
@@ -350,4 +351,10 @@ public interface IManager {
* @return TGetPathsSetTemplatesResp
*/
TGetPathsSetTemplatesResp getPathsSetTemplate(String req);
+
+ /*
+ * delete timeseries
+ *
+ */
+ TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req);
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/manager/ProcedureManager.java b/confignode/src/main/java/org/apache/iotdb/confignode/manager/ProcedureManager.java
index a1cc6ad5f2..54f77248b0 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/manager/ProcedureManager.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/manager/ProcedureManager.java
@@ -20,6 +20,7 @@
package org.apache.iotdb.confignode.manager;
import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.commons.exception.IoTDBException;
import org.apache.iotdb.commons.utils.StatusUtils;
import org.apache.iotdb.confignode.conf.ConfigNodeConfig;
import org.apache.iotdb.confignode.conf.ConfigNodeDescriptor;
@@ -33,6 +34,7 @@ import org.apache.iotdb.confignode.procedure.env.ConfigNodeProcedureEnv;
import org.apache.iotdb.confignode.procedure.impl.AddConfigNodeProcedure;
import org.apache.iotdb.confignode.procedure.impl.CreateRegionGroupsProcedure;
import org.apache.iotdb.confignode.procedure.impl.DeleteStorageGroupProcedure;
+import org.apache.iotdb.confignode.procedure.impl.DeleteTimeSeriesProcedure;
import org.apache.iotdb.confignode.procedure.impl.RegionMigrateProcedure;
import org.apache.iotdb.confignode.procedure.impl.RemoveConfigNodeProcedure;
import org.apache.iotdb.confignode.procedure.impl.RemoveDataNodeProcedure;
@@ -40,16 +42,20 @@ import org.apache.iotdb.confignode.procedure.scheduler.ProcedureScheduler;
import org.apache.iotdb.confignode.procedure.scheduler.SimpleProcedureScheduler;
import org.apache.iotdb.confignode.procedure.store.ConfigProcedureStore;
import org.apache.iotdb.confignode.procedure.store.IProcedureStore;
+import org.apache.iotdb.confignode.procedure.store.ProcedureFactory;
import org.apache.iotdb.confignode.procedure.store.ProcedureStore;
import org.apache.iotdb.confignode.rpc.thrift.TConfigNodeRegisterReq;
+import org.apache.iotdb.confignode.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.confignode.rpc.thrift.TRegionMigrateResultReportReq;
import org.apache.iotdb.confignode.rpc.thrift.TStorageGroupSchema;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.rpc.RpcUtils;
import org.apache.iotdb.rpc.TSStatusCode;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import java.nio.ByteBuffer;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
@@ -121,6 +127,52 @@ public class ProcedureManager {
}
}
+ public TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req) {
+ String queryId = req.getQueryId();
+ PathPatternTree patternTree =
+ PathPatternTree.deserialize(ByteBuffer.wrap(req.getPathPatternTree()));
+ long procedureId = -1;
+ synchronized (this) {
+ boolean hasOverlappedTask = false;
+ ProcedureFactory.ProcedureType type;
+ DeleteTimeSeriesProcedure deleteTimeSeriesProcedure;
+ for (Procedure<?> procedure : executor.getProcedures().values()) {
+ type = ProcedureFactory.getProcedureType(procedure);
+ if (type == null
+ || !type.equals(ProcedureFactory.ProcedureType.DELETE_TIMESERIES_PROCEDURE)) {
+ continue;
+ }
+ deleteTimeSeriesProcedure = ((DeleteTimeSeriesProcedure) procedure);
+ if (queryId.equals(deleteTimeSeriesProcedure.getQueryId())) {
+ procedureId = deleteTimeSeriesProcedure.getProcId();
+ break;
+ }
+ if (patternTree.isOverlapWith(deleteTimeSeriesProcedure.getPatternTree())) {
+ hasOverlappedTask = true;
+ break;
+ }
+ }
+
+ if (procedureId == -1) {
+ if (hasOverlappedTask) {
+ return RpcUtils.getStatus(
+ TSStatusCode.OVERLAP_WITH_EXISTING_DELETE_TIMESERIES_TASK,
+ "Some other task is deleting some target timeseries.");
+ }
+ procedureId =
+ this.executor.submitProcedure(new DeleteTimeSeriesProcedure(queryId, patternTree));
+ }
+ }
+ List<TSStatus> procedureStatus = new ArrayList<>();
+ boolean isSucceed =
+ waitingProcedureFinished(Collections.singletonList(procedureId), procedureStatus);
+ if (isSucceed) {
+ return StatusUtils.OK;
+ } else {
+ return procedureStatus.get(0);
+ }
+ }
+
/** Generate a AddConfigNodeProcedure, and serially execute all the AddConfigNodeProcedure */
public void addConfigNode(TConfigNodeRegisterReq req) {
AddConfigNodeProcedure addConfigNodeProcedure =
@@ -189,12 +241,23 @@ public class ProcedureManager {
}
Procedure<ConfigNodeProcedureEnv> finishedProcedure =
executor.getResultOrProcedure(procedureId);
+ if (!finishedProcedure.isFinished()) {
+ // the procedure is still executing
+ statusList.add(RpcUtils.getStatus(TSStatusCode.STILL_EXECUTING_STATUS));
+ isSucceed = false;
+ continue;
+ }
if (finishedProcedure.isSuccess()) {
statusList.add(StatusUtils.OK);
} else {
- statusList.add(
- StatusUtils.EXECUTE_STATEMENT_ERROR.setMessage(
- finishedProcedure.getException().getMessage()));
+ if (finishedProcedure.getException().getCause() instanceof IoTDBException) {
+ IoTDBException e = (IoTDBException) finishedProcedure.getException().getCause();
+ statusList.add(RpcUtils.getStatus(e.getErrorCode(), e.getMessage()));
+ } else {
+ statusList.add(
+ StatusUtils.EXECUTE_STATEMENT_ERROR.setMessage(
+ finishedProcedure.getException().getMessage()));
+ }
isSucceed = false;
}
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/procedure/impl/DeleteTimeSeriesProcedure.java b/confignode/src/main/java/org/apache/iotdb/confignode/procedure/impl/DeleteTimeSeriesProcedure.java
new file mode 100644
index 0000000000..970ac36569
--- /dev/null
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/procedure/impl/DeleteTimeSeriesProcedure.java
@@ -0,0 +1,639 @@
+/*
+ * 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.confignode.procedure.impl;
+
+import org.apache.iotdb.common.rpc.thrift.TConsensusGroupId;
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TRegionReplicaSet;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.commons.exception.MetadataException;
+import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.confignode.client.async.datanode.AsyncDataNodeClientPool;
+import org.apache.iotdb.confignode.client.async.task.ConstructSchemaBlackListDataNodeTask;
+import org.apache.iotdb.confignode.client.async.task.DeleteDataForDeleteTimeSeriesDataNodeTask;
+import org.apache.iotdb.confignode.client.async.task.DeleteTimeSeriesDataNodeTask;
+import org.apache.iotdb.confignode.client.async.task.FetchSchemaBlackListDataNodeTask;
+import org.apache.iotdb.confignode.client.async.task.InvalidateMatchedSchemaCacheDataNodeTask;
+import org.apache.iotdb.confignode.client.async.task.RollbackSchemaBlackListDataNodeTask;
+import org.apache.iotdb.confignode.procedure.StateMachineProcedure;
+import org.apache.iotdb.confignode.procedure.env.ConfigNodeProcedureEnv;
+import org.apache.iotdb.confignode.procedure.exception.ProcedureException;
+import org.apache.iotdb.confignode.procedure.exception.ProcedureSuspendedException;
+import org.apache.iotdb.confignode.procedure.exception.ProcedureYieldException;
+import org.apache.iotdb.confignode.procedure.state.DeleteTimeSeriesState;
+import org.apache.iotdb.confignode.procedure.store.ProcedureFactory;
+import org.apache.iotdb.db.exception.metadata.PathNotExistException;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
+import org.apache.iotdb.mpp.rpc.thrift.TConstructSchemaBlackListReq;
+import org.apache.iotdb.mpp.rpc.thrift.TDeleteDataForDeleteTimeSeriesReq;
+import org.apache.iotdb.mpp.rpc.thrift.TDeleteTimeSeriesReq;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListReq;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListResp;
+import org.apache.iotdb.mpp.rpc.thrift.TInvalidateMatchedSchemaCacheReq;
+import org.apache.iotdb.mpp.rpc.thrift.TRollbackSchemaBlackListReq;
+import org.apache.iotdb.rpc.TSStatusCode;
+import org.apache.iotdb.tsfile.utils.ReadWriteIOUtils;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.stream.Collectors;
+
+public class DeleteTimeSeriesProcedure
+ extends StateMachineProcedure<ConfigNodeProcedureEnv, DeleteTimeSeriesState> {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(DeleteTimeSeriesProcedure.class);
+
+ private String queryId;
+
+ private PathPatternTree patternTree;
+ private ByteBuffer patternTreeBytes;
+
+ private String requestMessage;
+
+ public DeleteTimeSeriesProcedure() {
+ super();
+ }
+
+ public DeleteTimeSeriesProcedure(String queryId, PathPatternTree patternTree) {
+ super();
+ this.queryId = queryId;
+ setPatternTree(patternTree);
+ }
+
+ @Override
+ protected Flow executeFromState(ConfigNodeProcedureEnv env, DeleteTimeSeriesState state)
+ throws ProcedureSuspendedException, ProcedureYieldException, InterruptedException {
+ switch (state) {
+ case CONSTRUCT_BLACK_LIST:
+ LOGGER.info("Construct schema black list of timeseries {}", requestMessage);
+ if (constructBlackList(env) > 0) {
+ setNextState(DeleteTimeSeriesState.CLEAN_DATANODE_SCHEMA_CACHE);
+ break;
+ } else {
+ setFailure(
+ new ProcedureException(
+ new PathNotExistException(
+ patternTree.getAllPathPatterns().stream()
+ .map(PartialPath::getFullPath)
+ .collect(Collectors.toList()))));
+ return Flow.NO_MORE_STATE;
+ }
+ case CLEAN_DATANODE_SCHEMA_CACHE:
+ LOGGER.info("Invalidate cache of timeseries {}", requestMessage);
+ invalidateCache(env);
+ break;
+ case DELETE_DATA:
+ LOGGER.info("Delete data of timeseries {}", requestMessage);
+ deleteData(env);
+ break;
+ case DELETE_TIMESERIES:
+ LOGGER.info("Delete timeseries schema of {}", requestMessage);
+ deleteTimeSeries(env);
+ return Flow.NO_MORE_STATE;
+ default:
+ setFailure(new ProcedureException("Unrecognized state " + state.toString()));
+ return Flow.NO_MORE_STATE;
+ }
+ return Flow.HAS_MORE_STATE;
+ }
+
+ // return the total num of timeseries in schema black list
+ private int constructBlackList(ConfigNodeProcedureEnv env) {
+ Map<TConsensusGroupId, TRegionReplicaSet> targetSchemaRegionGroup =
+ env.getConfigManager().getRelatedSchemaRegionGroup(patternTree);
+ if (targetSchemaRegionGroup.isEmpty()) {
+ return 0;
+ }
+ RegionTask<TSStatus> constructBlackListTask =
+ new RegionTask<TSStatus>("construct schema black list", env, targetSchemaRegionGroup) {
+ @Override
+ Map<Integer, TSStatus> sendRequest(
+ TDataNodeLocation dataNodeLocation, List<TConsensusGroupId> consensusGroupIdList) {
+ // construct request and send
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap = new HashMap<>();
+ dataNodeLocationMap.put(dataNodeLocation.getDataNodeId(), dataNodeLocation);
+ ConstructSchemaBlackListDataNodeTask dataNodeTask =
+ new ConstructSchemaBlackListDataNodeTask(dataNodeLocationMap);
+ AsyncDataNodeClientPool.getInstance()
+ .sendAsyncRequestToDataNodeWithRetry(
+ new TConstructSchemaBlackListReq(consensusGroupIdList, patternTreeBytes),
+ dataNodeTask);
+ dataNodeTask
+ .getDataNodeResponseMap()
+ .forEach(
+ (k, v) -> {
+ if (v.getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ responseMap.put(k, v);
+ }
+ });
+ return dataNodeTask.getDataNodeResponseMap();
+ }
+ };
+ constructBlackListTask.execute();
+
+ if (isFailed()) {
+ return 0;
+ }
+
+ int preDeletedNum = 0;
+ for (TSStatus resp : constructBlackListTask.getResponseMap().values()) {
+ preDeletedNum += Integer.parseInt(resp.getMessage());
+ }
+ return preDeletedNum;
+ }
+
+ private void invalidateCache(ConfigNodeProcedureEnv env) {
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap =
+ env.getConfigManager().getNodeManager().getRegisteredDataNodeLocations();
+ InvalidateMatchedSchemaCacheDataNodeTask dataNodeTask =
+ new InvalidateMatchedSchemaCacheDataNodeTask(dataNodeLocationMap);
+ AsyncDataNodeClientPool.getInstance()
+ .sendAsyncRequestToDataNodeWithRetry(
+ new TInvalidateMatchedSchemaCacheReq(patternTreeBytes), dataNodeTask);
+ Map<Integer, TSStatus> statusMap = dataNodeTask.getDataNodeResponseMap();
+ for (TSStatus status : statusMap.values()) {
+ // all dataNodes must clear the related schema cache
+ if (status.getCode() != TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ LOGGER.error("Failed to invalidate schema cache of timeseries {}", requestMessage);
+ setFailure(new ProcedureException(new MetadataException("Invalidate schema cache failed")));
+ return;
+ }
+ }
+
+ setNextState(DeleteTimeSeriesState.DELETE_DATA);
+ }
+
+ private void deleteData(ConfigNodeProcedureEnv env) {
+ Map<TConsensusGroupId, TRegionReplicaSet> relatedSchemaRegionGroup =
+ env.getConfigManager().getRelatedSchemaRegionGroup(patternTree);
+ Map<TDataNodeLocation, List<TConsensusGroupId>> dataNodeSchemaRegionGroupGroupIdMap =
+ getLeaderDataNodeRegionGroupMap(
+ env.getConfigManager().getPartitionManager().getAllLeadership(),
+ relatedSchemaRegionGroup);
+
+ // fetch schema black list by dataNode
+ for (Map.Entry<TDataNodeLocation, List<TConsensusGroupId>> entry :
+ dataNodeSchemaRegionGroupGroupIdMap.entrySet()) {
+ Map<TConsensusGroupId, TRegionReplicaSet> targetSchemaRegionGroup = new HashMap<>();
+ entry
+ .getValue()
+ .forEach(
+ consensusGroupId ->
+ targetSchemaRegionGroup.put(
+ consensusGroupId, relatedSchemaRegionGroup.get(consensusGroupId)));
+ // resolve original path pattern into specific timeseries full path
+ PathPatternTree patternTree =
+ fetchSchemaBlackListOnTargetDataNode(env, targetSchemaRegionGroup);
+ if (isFailed()) {
+ return;
+ }
+ if (patternTree == null) {
+ LOGGER.error(
+ "Failed to fetch schema black list for delete data of timeseries {} on {}",
+ requestMessage,
+ entry.getKey());
+ setFailure(
+ new ProcedureException(
+ new MetadataException("Fetch schema black list forDelete data failed")));
+ return;
+ }
+
+ if (patternTree.isEmpty()) {
+ continue;
+ }
+
+ Map<TConsensusGroupId, TRegionReplicaSet> relatedDataRegionGroup =
+ env.getConfigManager().getRelatedDataRegionGroup(patternTree);
+
+ // target timeseries has no data
+ if (relatedDataRegionGroup.isEmpty()) {
+ continue;
+ }
+
+ RegionTask<TSStatus> deleteDataTask =
+ new RegionTask<TSStatus>("delete data", env, relatedDataRegionGroup) {
+ @Override
+ Map<Integer, TSStatus> sendRequest(
+ TDataNodeLocation dataNodeLocation, List<TConsensusGroupId> consensusGroupIdList) {
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap = new HashMap<>();
+ dataNodeLocationMap.put(dataNodeLocation.getDataNodeId(), dataNodeLocation);
+ DeleteDataForDeleteTimeSeriesDataNodeTask dataNodeTask =
+ new DeleteDataForDeleteTimeSeriesDataNodeTask(dataNodeLocationMap);
+ AsyncDataNodeClientPool.getInstance()
+ .sendAsyncRequestToDataNodeWithRetry(
+ new TDeleteDataForDeleteTimeSeriesReq(
+ new ArrayList<>(consensusGroupIdList),
+ preparePatternTreeBytesData(patternTree)),
+ dataNodeTask);
+ return dataNodeTask.getDataNodeResponseMap();
+ }
+ };
+ deleteDataTask.setExecuteOnAllReplicaset(true);
+ deleteDataTask.execute();
+ if (isFailed()) {
+ return;
+ }
+ }
+ setNextState(DeleteTimeSeriesState.DELETE_TIMESERIES);
+ }
+
+ private PathPatternTree fetchSchemaBlackListOnTargetDataNode(
+ ConfigNodeProcedureEnv env,
+ Map<TConsensusGroupId, TRegionReplicaSet> targetSchemaRegionGroup) {
+ RegionTask<TFetchSchemaBlackListResp> fetchSchemaBlackListTask =
+ new RegionTask<TFetchSchemaBlackListResp>(
+ "fetch schema black list", env, targetSchemaRegionGroup) {
+ @Override
+ Map<Integer, TSStatus> sendRequest(
+ TDataNodeLocation dataNodeLocation, List<TConsensusGroupId> consensusGroupIdList) {
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap = new HashMap<>();
+ dataNodeLocationMap.put(dataNodeLocation.getDataNodeId(), dataNodeLocation);
+ FetchSchemaBlackListDataNodeTask dataNodeTask =
+ new FetchSchemaBlackListDataNodeTask(dataNodeLocationMap);
+ AsyncDataNodeClientPool.getInstance()
+ .sendAsyncRequestToDataNodeWithRetry(
+ new TFetchSchemaBlackListReq(consensusGroupIdList, patternTreeBytes),
+ dataNodeTask);
+ Map<Integer, TFetchSchemaBlackListResp> respMap = dataNodeTask.getDataNodeResponseMap();
+ Map<Integer, TSStatus> statusMap = new HashMap<>();
+ respMap.forEach(
+ (k, v) -> {
+ if (v.getStatus().getCode() == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ responseMap.put(k, v);
+ }
+ statusMap.put(k, v.getStatus());
+ });
+ return statusMap;
+ }
+ };
+ fetchSchemaBlackListTask.execute();
+ if (isFailed()) {
+ return null;
+ }
+
+ Map<Integer, TFetchSchemaBlackListResp> respMap = fetchSchemaBlackListTask.getResponseMap();
+ PathPatternTree patternTree = new PathPatternTree();
+ for (TFetchSchemaBlackListResp resp : respMap.values()) {
+ for (PartialPath path :
+ PathPatternTree.deserialize(ByteBuffer.wrap(resp.getPathPatternTree()))
+ .getAllPathPatterns()) {
+ patternTree.appendFullPath(path);
+ }
+ }
+ patternTree.constructTree();
+ return patternTree;
+ }
+
+ private void deleteTimeSeries(ConfigNodeProcedureEnv env) {
+ RegionTask<TSStatus> deleteTimeSeriesTask =
+ new RegionTask<TSStatus>(
+ "delete timeseries",
+ env,
+ env.getConfigManager().getRelatedSchemaRegionGroup(patternTree)) {
+ @Override
+ Map<Integer, TSStatus> sendRequest(
+ TDataNodeLocation dataNodeLocation, List<TConsensusGroupId> consensusGroupIdList) {
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap = new HashMap<>();
+ dataNodeLocationMap.put(dataNodeLocation.getDataNodeId(), dataNodeLocation);
+ DeleteTimeSeriesDataNodeTask dataNodeTask =
+ new DeleteTimeSeriesDataNodeTask(dataNodeLocationMap);
+ AsyncDataNodeClientPool.getInstance()
+ .sendAsyncRequestToDataNodeWithRetry(
+ new TDeleteTimeSeriesReq(consensusGroupIdList, patternTreeBytes), dataNodeTask);
+ return dataNodeTask.getDataNodeResponseMap();
+ }
+ };
+ deleteTimeSeriesTask.execute();
+ }
+
+ /**
+ * Try to get and execute request on consensus group leader as possible. If fail to get leader,
+ * select some other replica for execution.
+ */
+ private Map<TDataNodeLocation, List<TConsensusGroupId>> getLeaderDataNodeRegionGroupMap(
+ Map<TConsensusGroupId, Integer> leaderMap,
+ Map<TConsensusGroupId, TRegionReplicaSet> regionReplicaSetMap) {
+ Map<TDataNodeLocation, List<TConsensusGroupId>> dataNodeConsensusGroupIdMap = new HashMap<>();
+ regionReplicaSetMap.forEach(
+ (consensusGroupId, regionReplicaSet) -> {
+ Integer leaderId = leaderMap.get(consensusGroupId);
+ TDataNodeLocation leaderDataNodeLocation = null;
+ if (leaderId == null || leaderId == -1) {
+ leaderDataNodeLocation = regionReplicaSet.getDataNodeLocations().get(0);
+ } else {
+ for (TDataNodeLocation dataNodeLocation : regionReplicaSet.getDataNodeLocations()) {
+ if (dataNodeLocation.getDataNodeId() == leaderId) {
+ leaderDataNodeLocation = dataNodeLocation;
+ break;
+ }
+ }
+ }
+ dataNodeConsensusGroupIdMap
+ .computeIfAbsent(leaderDataNodeLocation, k -> new ArrayList<>())
+ .add(regionReplicaSet.getRegionId());
+ });
+ return dataNodeConsensusGroupIdMap;
+ }
+
+ /**
+ * Try to execute request on all replica of one consensus group. If some replica failed, execute
+ * according request on some other replica and let consensus layer to sync it.
+ */
+ private Map<TDataNodeLocation, List<TConsensusGroupId>> getAllReplicaDataNodeRegionGroupMap(
+ Map<TConsensusGroupId, TRegionReplicaSet> regionReplicaSetMap) {
+ Map<TDataNodeLocation, List<TConsensusGroupId>> dataNodeConsensusGroupIdMap = new HashMap<>();
+ regionReplicaSetMap.forEach(
+ (consensusGroupId, regionReplicaSet) -> {
+ for (TDataNodeLocation dataNodeLocation : regionReplicaSet.getDataNodeLocations()) {
+ dataNodeConsensusGroupIdMap
+ .computeIfAbsent(dataNodeLocation, k -> new ArrayList<>())
+ .add(regionReplicaSet.getRegionId());
+ }
+ });
+ return dataNodeConsensusGroupIdMap;
+ }
+
+ @Override
+ protected void rollbackState(
+ ConfigNodeProcedureEnv env, DeleteTimeSeriesState deleteTimeSeriesState)
+ throws IOException, InterruptedException, ProcedureException {
+ RegionTask<TSStatus> rollbackStateTask =
+ new RegionTask<TSStatus>(
+ "roll back schema black list",
+ env,
+ env.getConfigManager().getRelatedSchemaRegionGroup(patternTree)) {
+ @Override
+ Map<Integer, TSStatus> sendRequest(
+ TDataNodeLocation dataNodeLocation, List<TConsensusGroupId> consensusGroupIdList) {
+ Map<Integer, TDataNodeLocation> dataNodeLocationMap = new HashMap<>();
+ dataNodeLocationMap.put(dataNodeLocation.getDataNodeId(), dataNodeLocation);
+ RollbackSchemaBlackListDataNodeTask dataNodeTask =
+ new RollbackSchemaBlackListDataNodeTask(dataNodeLocationMap);
+ AsyncDataNodeClientPool.getInstance()
+ .sendAsyncRequestToDataNodeWithRetry(
+ new TRollbackSchemaBlackListReq(consensusGroupIdList, patternTreeBytes),
+ dataNodeTask);
+ return dataNodeTask.getDataNodeResponseMap();
+ }
+ };
+ rollbackStateTask.execute();
+ }
+
+ @Override
+ protected boolean isRollbackSupported(DeleteTimeSeriesState deleteTimeSeriesState) {
+ return true;
+ }
+
+ @Override
+ protected DeleteTimeSeriesState getState(int stateId) {
+ return DeleteTimeSeriesState.values()[stateId];
+ }
+
+ @Override
+ protected int getStateId(DeleteTimeSeriesState deleteTimeSeriesState) {
+ return deleteTimeSeriesState.ordinal();
+ }
+
+ @Override
+ protected DeleteTimeSeriesState getInitialState() {
+ return DeleteTimeSeriesState.CONSTRUCT_BLACK_LIST;
+ }
+
+ public String getQueryId() {
+ return queryId;
+ }
+
+ public PathPatternTree getPatternTree() {
+ return patternTree;
+ }
+
+ public void setPatternTree(PathPatternTree patternTree) {
+ this.patternTree = patternTree;
+ requestMessage = patternTree.getAllPathPatterns().toString();
+ patternTreeBytes = preparePatternTreeBytesData(patternTree);
+ }
+
+ private ByteBuffer preparePatternTreeBytesData(PathPatternTree patternTree) {
+ ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
+ DataOutputStream dataOutputStream = new DataOutputStream(byteArrayOutputStream);
+ try {
+ patternTree.serialize(dataOutputStream);
+ } catch (IOException ignored) {
+
+ }
+ return ByteBuffer.wrap(byteArrayOutputStream.toByteArray());
+ }
+
+ @Override
+ public void serialize(DataOutputStream stream) throws IOException {
+ stream.writeInt(ProcedureFactory.ProcedureType.DELETE_TIMESERIES_PROCEDURE.ordinal());
+ super.serialize(stream);
+ ReadWriteIOUtils.write(queryId, stream);
+ patternTree.serialize(stream);
+ }
+
+ @Override
+ public void deserialize(ByteBuffer byteBuffer) {
+ super.deserialize(byteBuffer);
+ queryId = ReadWriteIOUtils.readString(byteBuffer);
+ setPatternTree(PathPatternTree.deserialize(byteBuffer));
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+ DeleteTimeSeriesProcedure that = (DeleteTimeSeriesProcedure) o;
+ return this.getProcId() == that.getProcId()
+ && this.getState() == that.getState()
+ && patternTree.equals(that.patternTree);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(getProcId(), getState(), patternTree);
+ }
+
+ private abstract class RegionTask<T> {
+
+ private final String taskName;
+ private final ConfigNodeProcedureEnv env;
+ private final Map<TConsensusGroupId, TRegionReplicaSet> targetSchemaRegionGroup;
+
+ private boolean executeOnAllReplicaset = false;
+
+ protected Map<Integer, T> responseMap = new ConcurrentHashMap<>();
+
+ RegionTask(
+ String taskName,
+ ConfigNodeProcedureEnv env,
+ Map<TConsensusGroupId, TRegionReplicaSet> targetSchemaRegionGroup) {
+ this.taskName = taskName;
+ this.env = env;
+ this.targetSchemaRegionGroup = targetSchemaRegionGroup;
+ }
+
+ private void execute() {
+ // organize schema region by dataNode
+ Set<TDataNodeLocation> allFailedDataNodeSet = new HashSet<>();
+ Map<TDataNodeLocation, List<TConsensusGroupId>> dataNodeConsensusGroupIdMap =
+ executeOnAllReplicaset
+ ? getAllReplicaDataNodeRegionGroupMap(targetSchemaRegionGroup)
+ : getLeaderDataNodeRegionGroupMap(
+ env.getConfigManager().getPartitionManager().getAllLeadership(),
+ targetSchemaRegionGroup);
+ while (!dataNodeConsensusGroupIdMap.isEmpty()) {
+ Map<TDataNodeLocation, List<TConsensusGroupId>> currentFailedDataNodeMap =
+ sendRegionRequest(dataNodeConsensusGroupIdMap);
+ if (isFailed()) {
+ // some dataNode execution failure
+ return;
+ }
+
+ if (currentFailedDataNodeMap.isEmpty()) {
+ // all succeeded
+ break;
+ }
+
+ // retry failed dataNode requests caused by unexpected error on other replicas on other
+ // dataNodes
+ currentFailedDataNodeMap.forEach(dataNodeConsensusGroupIdMap::remove);
+ // remove dataNodes that successfully executed request
+ allFailedDataNodeSet.removeAll(dataNodeConsensusGroupIdMap.keySet());
+ dataNodeConsensusGroupIdMap =
+ getAvailableDataNodeLocationForRetry(currentFailedDataNodeMap, allFailedDataNodeSet);
+ if (isFailed()) {
+ // some consensus group has no available dataNode
+ return;
+ }
+ }
+ }
+
+ private Map<TDataNodeLocation, List<TConsensusGroupId>> sendRegionRequest(
+ Map<TDataNodeLocation, List<TConsensusGroupId>> dataNodeConsensusGroupIdMap) {
+ // send request to each dataNode
+ Map<TDataNodeLocation, List<TConsensusGroupId>> failedDataNodeMap = new HashMap<>();
+ for (Map.Entry<TDataNodeLocation, List<TConsensusGroupId>> entry :
+ dataNodeConsensusGroupIdMap.entrySet()) {
+ // process response
+ Map<Integer, TSStatus> dataNodeResponseMap = sendRequest(entry.getKey(), entry.getValue());
+ TSStatus currentDataNodeResponse = dataNodeResponseMap.get(entry.getKey().getDataNodeId());
+ if (currentDataNodeResponse.getCode() != TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ if (currentDataNodeResponse.getCode() == TSStatusCode.MULTIPLE_ERROR.getStatusCode()) {
+ // dataNode execution error
+ LOGGER.error(
+ "Failed to execute [{}] of delete timeseries {} on {}",
+ taskName,
+ requestMessage,
+ entry.getKey());
+ setFailure(
+ new ProcedureException(
+ new MetadataException(
+ String.format(
+ "Delete timeseries %s failed when [%s]", requestMessage, taskName))));
+ break;
+ } else {
+ // unexpected error, retry on other replicates on other dataNodes
+ failedDataNodeMap.put(entry.getKey(), entry.getValue());
+ }
+ }
+ }
+ return failedDataNodeMap;
+ }
+
+ private Map<TDataNodeLocation, List<TConsensusGroupId>> getAvailableDataNodeLocationForRetry(
+ Map<TDataNodeLocation, List<TConsensusGroupId>> failedDataNodeConsensusGroupIdMap,
+ Set<TDataNodeLocation> allFailedDataNodeSet) {
+ Map<TConsensusGroupId, Integer> leaderMap =
+ env.getConfigManager().getPartitionManager().getAllLeadership();
+ Map<TDataNodeLocation, List<TConsensusGroupId>> availableDataNodeLocation = new HashMap<>();
+ for (List<TConsensusGroupId> consensusGroupIdList :
+ failedDataNodeConsensusGroupIdMap.values()) {
+ for (TConsensusGroupId consensusGroupId : consensusGroupIdList) {
+ TRegionReplicaSet regionReplicaSet = targetSchemaRegionGroup.get(consensusGroupId);
+ TDataNodeLocation selectedDataNode = null;
+ Integer leaderId = leaderMap.get(consensusGroupId);
+ if (leaderId == null || leaderId == -1) {
+ for (TDataNodeLocation candidateDataNode : regionReplicaSet.getDataNodeLocations()) {
+ if (!allFailedDataNodeSet.contains(candidateDataNode)) {
+ // since leader of this group is unknown, take the first available one
+ selectedDataNode = candidateDataNode;
+ break;
+ }
+ }
+ } else {
+ for (TDataNodeLocation candidateDataNode : regionReplicaSet.getDataNodeLocations()) {
+ if (!allFailedDataNodeSet.contains(candidateDataNode)) {
+ if (leaderId == candidateDataNode.getDataNodeId()) {
+ // retry on the new leader as possible
+ selectedDataNode = candidateDataNode;
+ break;
+ }
+ if (selectedDataNode == null) {
+ selectedDataNode = candidateDataNode;
+ }
+ }
+ }
+ }
+
+ if (selectedDataNode == null) {
+ setFailure(
+ new ProcedureException(
+ new MetadataException(
+ String.format(
+ "Delete timeseries %s failed when [%s] because all replicaset of schemaRegion %s failed.",
+ requestMessage, taskName, consensusGroupId.id))));
+ return availableDataNodeLocation;
+ } else {
+ availableDataNodeLocation
+ .compute(selectedDataNode, (k, v) -> new ArrayList<>())
+ .add(consensusGroupId);
+ }
+ }
+ }
+ return availableDataNodeLocation;
+ }
+
+ Map<Integer, T> getResponseMap() {
+ return responseMap == null ? Collections.emptyMap() : responseMap;
+ }
+
+ void setExecuteOnAllReplicaset(boolean executeOnAllReplicaset) {
+ this.executeOnAllReplicaset = executeOnAllReplicaset;
+ }
+
+ abstract Map<Integer, TSStatus> sendRequest(
+ TDataNodeLocation dataNodeLocation, List<TConsensusGroupId> consensusGroupIdList);
+ }
+}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java b/confignode/src/main/java/org/apache/iotdb/confignode/procedure/state/DeleteTimeSeriesState.java
similarity index 58%
copy from confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java
copy to confignode/src/main/java/org/apache/iotdb/confignode/procedure/state/DeleteTimeSeriesState.java
index 7ed20d7e94..1cf6e7e9e5 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/client/DataNodeRequestType.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/procedure/state/DeleteTimeSeriesState.java
@@ -17,32 +17,11 @@
* under the License.
*/
-package org.apache.iotdb.confignode.client;
+package org.apache.iotdb.confignode.procedure.state;
-public enum DataNodeRequestType {
- DELETE_REGIONS,
- INVALIDATE_PARTITION_CACHE,
- INVALIDATE_PERMISSION_CACHE,
- INVALIDATE_SCHEMA_CACHE,
- CREATE_NEW_REGION_PEER,
- ADD_REGION_PEER,
- REMOVE_REGION_PEER,
- DELETE_OLD_REGION_PEER,
- DISABLE_DATA_NODE,
- STOP_DATA_NODE,
-
- SET_TTL,
- CREATE_DATA_REGIONS,
- CREATE_SCHEMA_REGIONS,
- CREATE_FUNCTION,
- DROP_FUNCTION,
- FLUSH,
- UPDATE_REGION_ROUTE_MAP,
- BROADCAST_LATEST_CONFIG_NODE_GROUP,
- UPDATE_TEMPLATE,
- CLEAR_CACHE,
- MERGE,
- FULL_MERGE,
- LOAD_CONFIGURATION,
- SET_SYSTEM_STATUS,
+public enum DeleteTimeSeriesState {
+ CONSTRUCT_BLACK_LIST,
+ CLEAN_DATANODE_SCHEMA_CACHE,
+ DELETE_DATA,
+ DELETE_TIMESERIES
}
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/procedure/store/ProcedureFactory.java b/confignode/src/main/java/org/apache/iotdb/confignode/procedure/store/ProcedureFactory.java
index 57119408c9..fff4260307 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/procedure/store/ProcedureFactory.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/procedure/store/ProcedureFactory.java
@@ -23,6 +23,7 @@ import org.apache.iotdb.confignode.procedure.Procedure;
import org.apache.iotdb.confignode.procedure.impl.AddConfigNodeProcedure;
import org.apache.iotdb.confignode.procedure.impl.CreateRegionGroupsProcedure;
import org.apache.iotdb.confignode.procedure.impl.DeleteStorageGroupProcedure;
+import org.apache.iotdb.confignode.procedure.impl.DeleteTimeSeriesProcedure;
import org.apache.iotdb.confignode.procedure.impl.RegionMigrateProcedure;
import org.apache.iotdb.confignode.procedure.impl.RemoveConfigNodeProcedure;
import org.apache.iotdb.confignode.procedure.impl.RemoveDataNodeProcedure;
@@ -65,6 +66,9 @@ public class ProcedureFactory implements IProcedureFactory {
case CREATE_REGION_GROUPS:
procedure = new CreateRegionGroupsProcedure();
break;
+ case DELETE_TIMESERIES_PROCEDURE:
+ procedure = new DeleteTimeSeriesProcedure();
+ break;
default:
LOGGER.error("unknown Procedure type: " + typeNum);
throw new IOException("unknown Procedure type: " + typeNum);
@@ -86,6 +90,8 @@ public class ProcedureFactory implements IProcedureFactory {
return ProcedureType.REGION_MIGRATE_PROCEDURE;
} else if (procedure instanceof CreateRegionGroupsProcedure) {
return ProcedureType.CREATE_REGION_GROUPS;
+ } else if (procedure instanceof DeleteTimeSeriesProcedure) {
+ return ProcedureType.DELETE_TIMESERIES_PROCEDURE;
}
return null;
}
@@ -96,7 +102,8 @@ public class ProcedureFactory implements IProcedureFactory {
REMOVE_CONFIG_NODE_PROCEDURE,
REMOVE_DATA_NODE_PROCEDURE,
REGION_MIGRATE_PROCEDURE,
- CREATE_REGION_GROUPS
+ CREATE_REGION_GROUPS,
+ DELETE_TIMESERIES_PROCEDURE
}
private static class ProcedureFactoryHolder {
diff --git a/confignode/src/main/java/org/apache/iotdb/confignode/service/thrift/ConfigNodeRPCServiceProcessor.java b/confignode/src/main/java/org/apache/iotdb/confignode/service/thrift/ConfigNodeRPCServiceProcessor.java
index 28e22d33ce..7c008ecc0a 100644
--- a/confignode/src/main/java/org/apache/iotdb/confignode/service/thrift/ConfigNodeRPCServiceProcessor.java
+++ b/confignode/src/main/java/org/apache/iotdb/confignode/service/thrift/ConfigNodeRPCServiceProcessor.java
@@ -76,6 +76,7 @@ import org.apache.iotdb.confignode.rpc.thrift.TDataPartitionReq;
import org.apache.iotdb.confignode.rpc.thrift.TDataPartitionTableResp;
import org.apache.iotdb.confignode.rpc.thrift.TDeleteStorageGroupReq;
import org.apache.iotdb.confignode.rpc.thrift.TDeleteStorageGroupsReq;
+import org.apache.iotdb.confignode.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.confignode.rpc.thrift.TDropFunctionReq;
import org.apache.iotdb.confignode.rpc.thrift.TDropTriggerReq;
import org.apache.iotdb.confignode.rpc.thrift.TGetAllTemplatesResp;
@@ -583,4 +584,9 @@ public class ConfigNodeRPCServiceProcessor implements IConfigNodeRPCService.Ifac
public TGetPathsSetTemplatesResp getPathsSetTemplate(String req) throws TException {
return configManager.getPathsSetTemplate(req);
}
+
+ @Override
+ public TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req) throws TException {
+ return configManager.deleteTimeSeries(req);
+ }
}
diff --git a/confignode/src/test/java/org/apache/iotdb/confignode/procedure/impl/DeleteTimeSeriesProcedureTest.java b/confignode/src/test/java/org/apache/iotdb/confignode/procedure/impl/DeleteTimeSeriesProcedureTest.java
new file mode 100644
index 0000000000..cc62f1c0f8
--- /dev/null
+++ b/confignode/src/test/java/org/apache/iotdb/confignode/procedure/impl/DeleteTimeSeriesProcedureTest.java
@@ -0,0 +1,67 @@
+/*
+ * 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.confignode.procedure.impl;
+
+import org.apache.iotdb.commons.exception.IllegalPathException;
+import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.confignode.procedure.store.ProcedureFactory;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.List;
+
+public class DeleteTimeSeriesProcedureTest {
+
+ @Test
+ public void serializeDeserializeTest() throws IllegalPathException, IOException {
+ String queryId = "1";
+ PathPatternTree patternTree = new PathPatternTree();
+ patternTree.appendPathPattern(new PartialPath("root.sg1.**"));
+ patternTree.appendPathPattern(new PartialPath("root.sg2.*.s1"));
+ patternTree.constructTree();
+ DeleteTimeSeriesProcedure deleteTimeSeriesProcedure =
+ new DeleteTimeSeriesProcedure(queryId, patternTree);
+
+ ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
+ DataOutputStream dataOutputStream = new DataOutputStream(byteArrayOutputStream);
+ deleteTimeSeriesProcedure.serialize(dataOutputStream);
+
+ ByteBuffer byteBuffer = ByteBuffer.wrap(byteArrayOutputStream.toByteArray());
+
+ Assert.assertEquals(
+ ProcedureFactory.ProcedureType.DELETE_TIMESERIES_PROCEDURE.ordinal(), byteBuffer.getInt());
+
+ DeleteTimeSeriesProcedure deserializedProcedure = new DeleteTimeSeriesProcedure();
+ deserializedProcedure.deserialize(byteBuffer);
+
+ Assert.assertEquals(queryId, deserializedProcedure.getQueryId());
+
+ List<PartialPath> pathList = deserializedProcedure.getPatternTree().getAllPathPatterns();
+ pathList.sort(PartialPath::compareTo);
+ Assert.assertEquals("root.sg1.**", pathList.get(0).getFullPath());
+ Assert.assertEquals("root.sg2.*.s1", pathList.get(1).getFullPath());
+ }
+}
diff --git a/integration-test/src/test/java/org/apache/iotdb/db/it/IoTDBCompleteIT.java b/integration-test/src/test/java/org/apache/iotdb/db/it/IoTDBCompleteIT.java
deleted file mode 100644
index 716d4d3702..0000000000
--- a/integration-test/src/test/java/org/apache/iotdb/db/it/IoTDBCompleteIT.java
+++ /dev/null
@@ -1,495 +0,0 @@
-/*
- * 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.it;
-
-import org.apache.iotdb.it.env.ConfigFactory;
-import org.apache.iotdb.it.env.EnvFactory;
-import org.apache.iotdb.it.framework.IoTDBTestRunner;
-import org.apache.iotdb.itbase.category.ClusterIT;
-import org.apache.iotdb.itbase.category.LocalStandaloneIT;
-import org.apache.iotdb.itbase.constant.TestConstant;
-
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Ignore;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-import org.junit.runner.RunWith;
-
-import java.sql.Connection;
-import java.sql.DatabaseMetaData;
-import java.sql.ResultSet;
-import java.sql.ResultSetMetaData;
-import java.sql.Statement;
-
-/**
- * Notice that, all test begins with "IoTDB" is integration test. All test which will start the
- * IoTDB server should be defined as integration test.
- */
-@Ignore
-@RunWith(IoTDBTestRunner.class)
-@Category({LocalStandaloneIT.class, ClusterIT.class})
-public class IoTDBCompleteIT {
- private int prevDataRegionNum;
-
- @Before
- public void setUp() throws InterruptedException {
- // test different partition
- prevDataRegionNum = ConfigFactory.getConfig().getDataRegionNum();
- ConfigFactory.getConfig().setDataRegionNum(16);
- EnvFactory.getEnv().initBeforeClass();
- }
-
- @After
- public void tearDown() throws Exception {
- EnvFactory.getEnv().cleanAfterClass();
- ConfigFactory.getConfig().setDataRegionNum(prevDataRegionNum);
- }
-
- @Ignore
- @Test
- public void test() {
- String[] sqls = {"SET STORAGE GROUP TO root.vehicle"};
- executeSQL(sqls);
- // simpleTest();
- // insertTest();
- // selectTest();
- deleteTest();
- // groupByTest();
- // funcTest();
-
- // funcTestWithOutTimeGenerator();
- }
-
- public void simpleTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{\n"
- + "\t\t\t\"d0\":{\n"
- + "\t\t\t\t\"s0\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t}\n"
- + "\t\t}\n"
- + "\t}\n"
- + "}",
- "DELETE TIMESERIES root.vehicle.d0.s0",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{}\n"
- + "\t}\n"
- + "}",
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=BOOLEAN,ENCODING=PLAIN",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT64,ENCODING=TS_2DIFF",
- "CREATE TIMESERIES root.vehicle.d0.s2 WITH DATATYPE=FLOAT,ENCODING=GORILLA",
- "CREATE TIMESERIES root.vehicle.d0.s4 WITH DATATYPE=DOUBLE,ENCODING=RLE",
- "CREATE TIMESERIES root.vehicle.d1.s5 WITH DATATYPE=TEXT,ENCODING=PLAIN",
- "CREATE TIMESERIES root.vehicle.d2.s6 WITH DATATYPE=INT32,ENCODING=TS_2DIFF,compressor=UNCOMPRESSED",
- "CREATE TIMESERIES root.vehicle.d3.s7 WITH DATATYPE=INT32,ENCODING=RLE,compressor=SNAPPY",
- "CREATE TIMESERIES root.vehicle.d4.s8 WITH DATATYPE=INT32,ENCODING=RLE,MAX_POINT_NUMBER=100",
- "CREATE TIMESERIES root.vehicle.d5.s9 WITH DATATYPE=FLOAT,ENCODING=PLAIN,compressor=SNAPPY,MAX_POINT_NUMBER=10",
- "CREATE TIMESERIES root.vehicle.d6.s10 WITH DATATYPE=DOUBLE,ENCODING=RLE,compressor=UNCOMPRESSED,MAX_POINT_NUMBER=10",
- "DELETE TIMESERIES root.vehicle.d0.**",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{\n"
- + "\t\t\t\"d4\":{\n"
- + "\t\t\t\t\"s8\":{\n"
- + "\t\t\t\t\t\"args\":\"{max_point_number=100}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d5\":{\n"
- + "\t\t\t\t\"s9\":{\n"
- + "\t\t\t\t\t\"args\":\"{max_point_number=10}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"FLOAT\",\n"
- + "\t\t\t\t\t\"Compressor\":\"SNAPPY\",\n"
- + "\t\t\t\t\t\"Encoding\":\"PLAIN\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d6\":{\n"
- + "\t\t\t\t\"s10\":{\n"
- + "\t\t\t\t\t\"args\":\"{max_point_number=10}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"DOUBLE\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d1\":{\n"
- + "\t\t\t\t\"s5\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"TEXT\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"PLAIN\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d2\":{\n"
- + "\t\t\t\t\"s6\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"TS_2DIFF\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d3\":{\n"
- + "\t\t\t\t\"s7\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"SNAPPY\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t}\n"
- + "\t\t}\n"
- + "\t}\n"
- + "}",
- "DELETE TIMESERIES root.vehicle.**",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{}\n"
- + "\t}\n"
- + "}"
- };
- executeSQL(sqlS);
- }
-
- public void insertTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,101)",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0,s1) values(2,102,202)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2000-01-01T08:00:00+08:00,105)",
- "SELECT * FROM root.vehicle.d0",
- "1,101,null,\n" + "2,102,202,\n" + "946684800000,105,null,\n" + "NOW(),104,null,\n",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void deleteTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,101)",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0,s1) values(2,102,202)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2000-01-01T08:00:00+08:00,105)",
- "SELECT * FROM root.vehicle.d0",
- "1,101,null,\n" + "2,102,202,\n" + "946684800000,105,null,\n" + "NOW(),104,null,\n",
- "DELETE TIMESERIES root.vehicle.**",
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,1)",
- "SELECT * FROM root.vehicle.d0",
- "1,1,\n" + "2,1,\n" + "3,1,\n" + "4,1,\n" + "5,1,\n" + "6,1,\n" + "7,1,\n" + "8,1,\n"
- + "9,1,\n" + "10,1,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time < 8",
- "SELECT * FROM root.vehicle.d0",
- "8,1,\n" + "9,1,\n" + "10,1,\n",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2000-01-01T08:00:00+08:00,1)",
- "SELECT * FROM root.vehicle.d0",
- "8,1,\n" + "9,1,\n" + "10,1,\n" + "946684800000,1,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time < 2000-01-02T08:00:00+08:00",
- "SELECT * FROM root.vehicle.d0",
- "",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),1)",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),1,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "",
- "CREATE TIMESERIES root.vehicle.d1.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,1)",
- "INSERT INTO root.vehicle.d1(timestamp,s1) values(1,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,5)",
- "INSERT INTO root.vehicle.d1(timestamp,s1) values(5,5)",
- "SELECT * FROM root.vehicle.*",
- "1,1,1,\n" + "5,5,5,\n",
- "DELETE FROM root.vehicle.d0.s0,root.vehicle.d1.s1 WHERE time < 3",
- "SELECT * FROM root.vehicle.*",
- "5,5,5,\n",
- "DELETE FROM root.vehicle.** WHERE time < 7",
- "SELECT * FROM root.vehicle.*",
- "",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void selectTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,101)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,110)",
- "SELECT * FROM root.vehicle.d0 WHERE s0 < 104",
- "1,101,\n" + "2,102,\n" + "3,103,\n",
- "SELECT * FROM root.vehicle.d0 WHERE s0 > 105 and time < 8",
- "6,106,\n" + "7,107,\n",
- "SELECT * FROM root.vehicle.d0",
- "1,101,\n"
- + "2,102,\n"
- + "3,103,\n"
- + "4,104,\n"
- + "5,105,\n"
- + "6,106,\n"
- + "7,107,\n"
- + "8,108,\n"
- + "9,109,\n"
- + "10,110,\n",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void funcTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,110)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,101)",
- "SELECT COUNT(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT COUNT(s0) FROM root.vehicle.d0 WHERE root.vehicle.d0.s0 < 105",
- "0,4,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0 WHERE root.vehicle.d0.s0 > 105",
- "0,5,\n",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0",
- "0,1,\n",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0 WHERE root.vehicle.d0.s0 < 106",
- "0,6,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0",
- "0,110,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0 WHERE time > 4",
- "0,106,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0",
- "0,101,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0 WHERE time < 5",
- "0,107,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= 10",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),5)",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),5,\n",
- "UPDATE root.vehicle.d0 SET s0 = 10 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),10,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void funcTestWithOutTimeGenerator() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,110)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,101)",
- "SELECT COUNT(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0",
- "0,1,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0",
- "0,110,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0 WHERE time > 4",
- "0,106,\n",
- "SELECT SUM(s0) FROM root.vehicle.d0 WHERE time > 4",
- "0,621.0,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0",
- "0,101,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0 WHERE time < 5",
- "0,107,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= 10",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),5)",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),5,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "",
- "SELECT COUNT(s0) FROM root.vehicle.d0",
- "0,0,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0",
- "",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0",
- "",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0",
- "",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0 WHERE time > 4",
- "",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0",
- "",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0 WHERE time < 5",
- "",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void groupByTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,110)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,101)",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(1,101)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(2,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(3,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(4,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(5,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(6,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(7,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(8,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(9,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(10,110)",
- "SELECT COUNT(s0), COUNT(s1) FROM root.vehicle.d0 WHERE s1 < 109 GROUP BY(4ms,[1,10])",
- "1,3,3,\n" + "4,4,4,\n" + "8,1,1,\n",
- "SELECT COUNT(s0), MAX_VALUE(s1) FROM root.vehicle.d0 WHERE time < 7 GROUP BY(3ms,2,[1,5])",
- "1,1,101,\n" + "2,3,104,\n" + "5,1,105,\n",
- "SELECT MIN_VALUE(s0), MAX_TIME(s1) FROM root.vehicle.d0 WHERE s1 > 102 and time < 9 GROUP BY(3ms,1,[1,4],[6,9])",
- "1,108,3,\n" + "4,105,6,\n" + "7,103,8,\n",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- private void executeSQL(String[] sqls) {
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- String result = "";
- Long now_start = 0L;
- boolean cmp = false;
-
- for (String sql : sqls) {
- if (cmp) {
- Assert.assertEquals(sql, result);
- cmp = false;
- } else if (sql.equals("SHOW TIMESERIES")) {
- DatabaseMetaData data = connection.getMetaData();
- result = data.toString();
- cmp = true;
- } else {
- if (sql.contains("NOW()") && now_start == 0L) {
- now_start = System.currentTimeMillis();
- }
-
- if (sql.split(" ")[0].equals("SELECT")) {
- ResultSet resultSet = statement.executeQuery(sql);
- ResultSetMetaData metaData = resultSet.getMetaData();
- int count = metaData.getColumnCount();
- String[] column = new String[count];
- for (int i = 0; i < count; i++) {
- column[i] = metaData.getColumnName(i + 1);
- }
- result = "";
- while (resultSet.next()) {
- for (int i = 1; i <= count; i++) {
- if (now_start > 0L && column[i - 1].equals(TestConstant.TIMESTAMP_STR)) {
- String timestr = resultSet.getString(i);
- Long tn = Long.valueOf(timestr);
- Long now = System.currentTimeMillis();
- if (tn >= now_start && tn <= now) {
- timestr = "NOW()";
- }
- result += timestr + ',';
- } else {
- result += resultSet.getString(i) + ',';
- }
- }
- result += '\n';
- }
- cmp = true;
- }
- }
- }
- } catch (Exception e) {
- e.printStackTrace();
- }
- }
-}
diff --git a/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBCreateAlignedTimeseriesIT.java b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBCreateAlignedTimeseriesIT.java
index c61f215e87..3116295ad2 100644
--- a/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBCreateAlignedTimeseriesIT.java
+++ b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBCreateAlignedTimeseriesIT.java
@@ -26,7 +26,6 @@ import org.apache.iotdb.itbase.category.LocalStandaloneIT;
import org.junit.After;
import org.junit.Assert;
import org.junit.Before;
-import org.junit.Ignore;
import org.junit.Test;
import org.junit.experimental.categories.Category;
import org.junit.runner.RunWith;
@@ -41,7 +40,6 @@ import java.sql.Statement;
* IoTDB server should be defined as integration test.
*/
@RunWith(IoTDBTestRunner.class)
-@Category({LocalStandaloneIT.class, ClusterIT.class})
public class IoTDBCreateAlignedTimeseriesIT {
private Statement statement;
@@ -63,6 +61,7 @@ public class IoTDBCreateAlignedTimeseriesIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void testCreateAlignedTimeseries() throws Exception {
String[] timeSeriesArray =
new String[] {
@@ -90,8 +89,8 @@ public class IoTDBCreateAlignedTimeseriesIT {
// assertTimeseriesEquals(timeSeriesArray);
}
- @Ignore
@Test
+ @Category({ClusterIT.class})
public void testCreateAlignedTimeseriesWithDeletion() throws Exception {
String[] timeSeriesArray =
new String[] {
@@ -112,11 +111,9 @@ public class IoTDBCreateAlignedTimeseriesIT {
// ensure that current storage group in cache is right.
assertTimeseriesEquals(timeSeriesArray);
- statement.close();
- connection.close();
// todo
// EnvironmentUtils.stopDaemon();
- setUp();
+ // setUp();
// ensure storage group in cache is right after recovering.
assertTimeseriesEquals(timeSeriesArray);
diff --git a/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBDeleteAlignedTimeseriesIT.java b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBDeleteAlignedTimeseriesIT.java
new file mode 100644
index 0000000000..7d9d71ad7a
--- /dev/null
+++ b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBDeleteAlignedTimeseriesIT.java
@@ -0,0 +1,248 @@
+/*
+ * 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.it.schema;
+
+import org.apache.iotdb.it.env.ConfigFactory;
+import org.apache.iotdb.it.env.EnvFactory;
+import org.apache.iotdb.it.framework.IoTDBTestRunner;
+import org.apache.iotdb.itbase.category.ClusterIT;
+
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+import org.junit.runner.RunWith;
+
+import java.sql.Connection;
+import java.sql.ResultSet;
+import java.sql.ResultSetMetaData;
+import java.sql.SQLException;
+import java.sql.Statement;
+
+import static org.apache.iotdb.itbase.constant.TestConstant.TIMESTAMP_STR;
+import static org.apache.iotdb.itbase.constant.TestConstant.count;
+import static org.junit.Assert.fail;
+
+@RunWith(IoTDBTestRunner.class)
+@Category({ClusterIT.class})
+public class IoTDBDeleteAlignedTimeseriesIT {
+
+ private long memtableSizeThreshold;
+
+ private Statement statement;
+ private Connection connection;
+
+ @Before
+ public void setUp() throws ClassNotFoundException, SQLException, InterruptedException {
+ memtableSizeThreshold = ConfigFactory.getConfig().getMemtableSizeThreshold();
+ ConfigFactory.getConfig().setMemtableSizeThreshold(2);
+
+ EnvFactory.getEnv().initBeforeTest();
+
+ connection = EnvFactory.getEnv().getConnection();
+ statement = connection.createStatement();
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ statement.close();
+ connection.close();
+ EnvFactory.getEnv().cleanAfterTest();
+ ConfigFactory.getConfig().setMemtableSizeThreshold(memtableSizeThreshold);
+ }
+
+ @Test
+ public void deleteTimeseriesAndCreateDifferentTypeTest() throws Exception {
+ String[] retArray = new String[] {"1,1,", "2,1.1,"};
+ int cnt = 0;
+
+ statement.execute(
+ "create aligned timeseries root.turbine1.d1(s1 INT64 encoding=PLAIN compression=SNAPPY, "
+ + "s2 INT64 encoding=PLAIN compression=SNAPPY)");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+
+ statement.execute("DELETE timeseries root.turbine1.d1.s1");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) ALIGNED VALUES(2,1.1)");
+ statement.execute("FLUSH");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+
+ // todo
+ // EnvironmentUtils.restartDaemon();
+ //
+ // hasResult = statement.execute("SELECT * FROM root.**");
+ // Assert.assertTrue(hasResult);
+ }
+
+ @Test
+ public void deleteTimeseriesAndCreateSameTypeTest() throws Exception {
+ String[] retArray = new String[] {"1,1.0,", "2,5.0,"};
+ int cnt = 0;
+
+ statement.execute(
+ "create aligned timeseries root.turbine1.d1(s1 FLOAT encoding=PLAIN compression=SNAPPY, "
+ + "s2 INT64 encoding=PLAIN compression=SNAPPY)");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+ statement.execute("DELETE timeseries root.turbine1.d1.s1");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) ALIGNED VALUES(2,5)");
+ statement.execute("FLUSH");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+
+ // todo
+ // EnvironmentUtils.restartDaemon();
+ //
+ // hasResult = statement.execute("SELECT * FROM root.**");
+ // Assert.assertTrue(hasResult);
+ }
+
+ @Test
+ public void deleteTimeseriesAndChangeDeviceAlignmentTest() throws Exception {
+ String[] retArray = new String[] {"1,1.0,2.0,"};
+ int cnt = 0;
+
+ statement.execute("INSERT INTO root.sg3.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
+ try (ResultSet resultSet = statement.executeQuery("SHOW DEVICES")) {
+ while (resultSet.next()) {
+ Assert.assertEquals("true", resultSet.getString("isAligned"));
+ }
+ }
+ cnt = 0;
+ statement.execute("DELETE timeseries root.sg3.d1.s1");
+ statement.execute("DELETE timeseries root.sg3.d1.s2");
+ statement.execute("INSERT INTO root.sg3.d1(timestamp,s1,s2) VALUES(1,1,2)");
+ try (ResultSet resultSet = statement.executeQuery("SHOW DEVICES")) {
+ while (resultSet.next()) {
+ Assert.assertEquals("false", resultSet.getString("isAligned"));
+ }
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT * FROM root.sg3.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+ cnt = 0;
+ statement.execute("DELETE timeseries root.sg3.d1.s1");
+ statement.execute("DELETE timeseries root.sg3.d1.s2");
+ statement.execute("INSERT INTO root.sg3.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
+ try (ResultSet resultSet = statement.executeQuery("SHOW DEVICES")) {
+ while (resultSet.next()) {
+ Assert.assertEquals("true", resultSet.getString("isAligned"));
+ }
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT * FROM root.sg3.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+ }
+
+ @Test
+ public void deleteTimeSeriesMultiIntervalTest() {
+ String[] retArray1 = new String[] {"0,0"};
+
+ try {
+ String insertSql = "insert into root.sg.d1(time, s1) aligned values(%d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ statement.execute(String.format(insertSql, i, i));
+ }
+ statement.execute("flush");
+
+ statement.execute("delete from root.sg.d1.s1 where time >= 1 and time <= 2");
+ statement.execute("delete from root.sg.d1.s1 where time >= 3 and time <= 4");
+
+ int cnt = 0;
+ try (ResultSet resultSet =
+ statement.executeQuery(
+ "select count(s1) from root.sg.d1 where time >= 3 and time <= 4")) {
+ while (resultSet.next()) {
+ String ans =
+ resultSet.getString(TIMESTAMP_STR)
+ + ","
+ + resultSet.getString(count("root.sg.d1.s1"));
+ Assert.assertEquals(retArray1[cnt], ans);
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+ } catch (Exception e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+}
diff --git a/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBDeleteTimeseriesIT.java b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBDeleteTimeseriesIT.java
new file mode 100644
index 0000000000..ca75bd914c
--- /dev/null
+++ b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBDeleteTimeseriesIT.java
@@ -0,0 +1,406 @@
+/*
+ * 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.it.schema;
+
+import org.apache.iotdb.it.env.ConfigFactory;
+import org.apache.iotdb.it.env.EnvFactory;
+import org.apache.iotdb.it.framework.IoTDBTestRunner;
+import org.apache.iotdb.itbase.category.ClusterIT;
+
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.experimental.categories.Category;
+import org.junit.runner.RunWith;
+
+import java.sql.Connection;
+import java.sql.ResultSet;
+import java.sql.ResultSetMetaData;
+import java.sql.SQLException;
+import java.sql.Statement;
+
+import static org.apache.iotdb.itbase.constant.TestConstant.TIMESTAMP_STR;
+import static org.apache.iotdb.itbase.constant.TestConstant.count;
+import static org.junit.Assert.fail;
+
+@RunWith(IoTDBTestRunner.class)
+@Category({ClusterIT.class})
+public class IoTDBDeleteTimeseriesIT {
+
+ private long memtableSizeThreshold;
+
+ private Statement statement;
+ private Connection connection;
+
+ @Before
+ public void setUp() throws Exception {
+ memtableSizeThreshold = ConfigFactory.getConfig().getMemtableSizeThreshold();
+ ConfigFactory.getConfig().setMemtableSizeThreshold(2);
+
+ EnvFactory.getEnv().initBeforeTest();
+
+ connection = EnvFactory.getEnv().getConnection();
+ statement = connection.createStatement();
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ statement.close();
+ connection.close();
+ EnvFactory.getEnv().cleanAfterTest();
+ ConfigFactory.getConfig().setMemtableSizeThreshold(memtableSizeThreshold);
+ }
+
+ @Test
+ public void deleteTimeseriesAndCreateDifferentTypeTest() throws Exception {
+ String[] retArray = new String[] {"1,1,", "2,1.1,"};
+ int cnt = 0;
+
+ statement.execute(
+ "create timeseries root.turbine1.d1.s1 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
+ statement.execute(
+ "create timeseries root.turbine1.d1.s2 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) VALUES(1,1,2)");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+ statement.execute("DELETE timeseries root.turbine1.d1.s1");
+ statement.execute(
+ "create timeseries root.turbine1.d1.s1 with datatype=DOUBLE, encoding=PLAIN, compression=SNAPPY");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) VALUES(2,1.1)");
+ statement.execute("FLUSH");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+
+ // EnvironmentUtils.restartDaemon();
+ //
+ // try (Connection connection = EnvFactory.getEnv().getConnection();
+ // Statement statement = connection.createStatement()) {
+ // boolean hasResult = statement.execute("SELECT * FROM root.**");
+ // Assert.assertTrue(hasResult);
+ // }
+ }
+
+ @Test
+ public void deleteTimeseriesAndCreateSameTypeTest() throws Exception {
+ String[] retArray = new String[] {"1,1,", "2,5,"};
+ int cnt = 0;
+
+ statement.execute(
+ "create timeseries root.turbine1.d1.s1 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
+ statement.execute(
+ "create timeseries root.turbine1.d1.s2 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) VALUES(1,1,2)");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+ statement.execute("DELETE timeseries root.turbine1.d1.s1");
+ statement.execute(
+ "create timeseries root.turbine1.d1.s1 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
+ statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) VALUES(2,5)");
+ statement.execute("FLUSH");
+
+ try (ResultSet resultSet = statement.executeQuery("SELECT s1 FROM root.turbine1.d1")) {
+ ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
+ while (resultSet.next()) {
+ StringBuilder builder = new StringBuilder();
+ for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
+ builder.append(resultSet.getString(i)).append(",");
+ }
+ Assert.assertEquals(retArray[cnt], builder.toString());
+ cnt++;
+ }
+ }
+
+ // EnvironmentUtils.restartDaemon();
+ //
+ // try (Connection connection = EnvFactory.getEnv().getConnection();
+ // Statement statement = connection.createStatement()) {
+ // boolean hasResult = statement.execute("SELECT * FROM root.**");
+ // Assert.assertTrue(hasResult);
+ // }
+ }
+
+ @Test
+ public void deleteTimeSeriesMultiIntervalTest() {
+ String[] retArray1 = new String[] {"0,0"};
+
+ try {
+ String insertSql = "insert into root.sg.d1(time, s1) values(%d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ statement.execute(String.format(insertSql, i, i));
+ }
+ statement.execute("flush");
+
+ statement.execute("delete from root.sg.d1.s1 where time >= 1 and time <= 2");
+ statement.execute("delete from root.sg.d1.s1 where time >= 3 and time <= 4");
+
+ int cnt = 0;
+ try (ResultSet resultSet =
+ statement.executeQuery(
+ "select count(s1) from root.sg.d1 where time >= 3 and time <= 4")) {
+ while (resultSet.next()) {
+ String ans =
+ resultSet.getString(TIMESTAMP_STR)
+ + ","
+ + resultSet.getString(count("root.sg.d1.s1"));
+ Assert.assertEquals(retArray1[cnt], ans);
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+ } catch (Exception e) {
+ e.printStackTrace();
+ fail(e.getMessage());
+ }
+ }
+
+ @Test
+ public void deleteTimeSeriesAndAutoDeleteDeviceTest() throws Exception {
+ String[] retArray1 = new String[] {"0,4,4,4,4"};
+
+ String insertSql = "insert into root.sg.d1(time, s1, s2, s3, s4) values(%d, %d, %d, %d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ statement.execute(String.format(insertSql, i, i, i, i, i));
+ }
+
+ int cnt = 0;
+ try (ResultSet resultSet =
+ statement.executeQuery(
+ "select count(s1), count(s2), count(s3), count(s4) from root.sg.d1")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg.d1.s" + i)));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+
+ statement.execute("delete timeseries root.sg.d1.*");
+ try (ResultSet resultSet = statement.executeQuery("select * from root.sg.d1")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("show timeseries root.sg.d1.*")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("show devices root.sg.d1")) {
+ Assert.assertFalse(resultSet.next());
+ }
+ }
+
+ @Test
+ public void deleteTimeSeriesCrossSchemaRegionTest() throws Exception {
+ String[] retArray1 = new String[] {"0,4,4,4,4"};
+
+ String insertSql = "insert into root.sg.d%d(time, s1, s2) values(%d, %d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ for (int j = 1; j <= 4; j++) {
+ statement.execute(String.format(insertSql, j, i, i, i));
+ }
+ }
+
+ int cnt = 0;
+ try (ResultSet resultSet = statement.executeQuery("select count(s1) from root.sg.*")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg.d" + i + ".s1")));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+
+ statement.execute("delete timeseries root.sg.*.s1");
+ try (ResultSet resultSet = statement.executeQuery("select s1 from root.sg.*")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("show timeseries root.sg.*.s1")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ cnt = 0;
+ try (ResultSet resultSet = statement.executeQuery("select count(s2) from root.sg.*")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg.d" + i + ".s2")));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+ }
+
+ @Test
+ public void deleteTimeSeriesCrossStorageGroupTest() throws Exception {
+ String[] retArray1 = new String[] {"0,4,4,4,4"};
+
+ String insertSql = "insert into root.sg%d.d1(time, s1, s2) values(%d, %d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ for (int j = 1; j <= 4; j++) {
+ statement.execute(String.format(insertSql, j, i, i, i));
+ }
+ }
+
+ int cnt = 0;
+ try (ResultSet resultSet = statement.executeQuery("select count(s1) from root.*.d1")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg" + i + ".d1.s1")));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+
+ statement.execute("delete timeseries root.*.d1.s1");
+ try (ResultSet resultSet = statement.executeQuery("select s1 from root.*.*")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("show timeseries root.*.*.s1")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ cnt = 0;
+ try (ResultSet resultSet = statement.executeQuery("select count(s2) from root.*.*")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg" + i + ".d1.s2")));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+ }
+
+ @Test
+ public void deleteTimeSeriesWithMultiPatternTest() throws Exception {
+ String[] retArray1 = new String[] {"0,4,4,4,4"};
+
+ String insertSql = "insert into root.sg%d.d1(time, s1, s2) values(%d, %d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ for (int j = 1; j <= 4; j++) {
+ statement.execute(String.format(insertSql, j, i, i, i));
+ }
+ }
+
+ int cnt = 0;
+ try (ResultSet resultSet = statement.executeQuery("select count(s1) from root.*.d1")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg" + i + ".d1.s1")));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+
+ statement.execute("delete timeseries root.*.d1.s1, root.*.d1.s2");
+ try (ResultSet resultSet = statement.executeQuery("select * from root.*.*")) {
+ Assert.assertFalse(resultSet.next());
+ }
+
+ try (ResultSet resultSet = statement.executeQuery("show timeseries root.*.*.*")) {
+ Assert.assertFalse(resultSet.next());
+ }
+ }
+
+ @Test
+ public void deleteTimeSeriesAndReturnPathNotExistsTest() throws Exception {
+ try {
+ statement.execute("delete timeseries root.**");
+ } catch (SQLException e) {
+ Assert.assertTrue(e.getMessage().contains("304: Path [root.**] does not exist"));
+ }
+
+ String[] retArray1 = new String[] {"0,4,4,4,4"};
+
+ String insertSql = "insert into root.sg%d.d1(time, s1, s2) values(%d, %d, %d)";
+ for (int i = 1; i <= 4; i++) {
+ for (int j = 1; j <= 4; j++) {
+ statement.execute(String.format(insertSql, j, i, i, i));
+ }
+ }
+
+ int cnt = 0;
+ try (ResultSet resultSet = statement.executeQuery("select count(s1) from root.*.d1")) {
+ while (resultSet.next()) {
+ StringBuilder ans = new StringBuilder(resultSet.getString(TIMESTAMP_STR));
+ for (int i = 1; i <= 4; i++) {
+ ans.append(",").append(resultSet.getString(count("root.sg" + i + ".d1.s1")));
+ }
+ Assert.assertEquals(retArray1[cnt], ans.toString());
+ cnt++;
+ }
+ Assert.assertEquals(retArray1.length, cnt);
+ }
+
+ try {
+ statement.execute("delete timeseries root.*.d1.s3");
+ } catch (SQLException e) {
+ Assert.assertTrue(e.getMessage().contains("304: Path [root.*.d1.s3] does not exist"));
+ }
+ }
+}
diff --git a/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBTagIT.java b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBTagIT.java
index 9bc20cbe71..4a373d92fd 100644
--- a/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBTagIT.java
+++ b/integration-test/src/test/java/org/apache/iotdb/db/it/schema/IoTDBTagIT.java
@@ -25,7 +25,6 @@ import org.apache.iotdb.itbase.category.LocalStandaloneIT;
import org.junit.After;
import org.junit.Before;
-import org.junit.Ignore;
import org.junit.Test;
import org.junit.experimental.categories.Category;
import org.junit.runner.RunWith;
@@ -45,7 +44,6 @@ import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
@RunWith(IoTDBTestRunner.class)
-@Category({LocalStandaloneIT.class, ClusterIT.class})
public class IoTDBTagIT {
@Before
@@ -59,6 +57,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void createOneTimeseriesTest() {
List<String> ret =
Collections.singletonList(
@@ -105,6 +104,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void createMultiTimeseriesTest() {
List<String> ret =
Arrays.asList(
@@ -159,6 +159,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void showTimeseriesTest() {
List<String> ret =
Arrays.asList(
@@ -212,6 +213,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void createDuplicateAliasTimeseriesTest1() {
String sql1 =
"create timeseries root.turbine.d3.s1(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
@@ -239,6 +241,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void createDuplicateAliasTimeseriesTest2() {
String sql1 =
"create timeseries root.turbine.d4.s1(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
@@ -264,6 +267,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void createDuplicateAliasTimeseriesTest3() {
String sql1 =
"create timeseries root.turbine.d5.s1(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
@@ -290,6 +294,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void queryWithAliasTest() {
List<String> ret =
Collections.singletonList(
@@ -334,6 +339,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void queryWithLimitTest() {
List<String> ret =
Arrays.asList(
@@ -387,8 +393,8 @@ public class IoTDBTagIT {
}
}
- @Ignore
@Test
+ @Category({ClusterIT.class})
public void deleteTest() {
List<String> ret1 =
Arrays.asList(
@@ -471,8 +477,8 @@ public class IoTDBTagIT {
}
}
- @Ignore
@Test
+ @Category({ClusterIT.class})
public void deleteWithAliasTest() {
List<String> ret1 =
Arrays.asList(
@@ -556,6 +562,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void queryWithWhereTest1() {
List<String> ret1 =
Arrays.asList(
@@ -679,6 +686,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void queryWithWhereTest2() {
Set<String> ret = new HashSet<>();
ret.add(
@@ -798,8 +806,8 @@ public class IoTDBTagIT {
}
}
- @Ignore
@Test
+ @Category({ClusterIT.class})
public void queryWithWhereAndDeleteTest() {
Set<String> ret = new HashSet<>();
ret.add(
@@ -882,6 +890,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void queryWithWhereContainsTest() {
Set<String> ret = new HashSet<>();
ret.add(
@@ -1001,6 +1010,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void queryWithWhereOnNoneTagTest() {
String[] sqls = {
"create timeseries root.turbine.d0.s0(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
@@ -1047,6 +1057,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void sameNameTest() {
String sql =
"create timeseries root.turbine.d1.s1(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
@@ -1062,6 +1073,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void deleteStorageGroupTest() {
List<String> ret =
Collections.singletonList(
@@ -1111,6 +1123,7 @@ public class IoTDBTagIT {
}
@Test
+ @Category({LocalStandaloneIT.class, ClusterIT.class})
public void insertWithAliasTest() {
List<String> ret = Collections.singletonList("1,36.5,36.5");
String[] sqls = {
diff --git a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBCompleteIT.java b/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBCompleteIT.java
deleted file mode 100644
index f6f1a04170..0000000000
--- a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBCompleteIT.java
+++ /dev/null
@@ -1,491 +0,0 @@
-/*
- * 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;
-
-import org.apache.iotdb.db.conf.IoTDBDescriptor;
-import org.apache.iotdb.db.constant.TestConstant;
-import org.apache.iotdb.integration.env.ConfigFactory;
-import org.apache.iotdb.integration.env.EnvFactory;
-import org.apache.iotdb.itbase.category.ClusterTest;
-import org.apache.iotdb.itbase.category.LocalStandaloneTest;
-
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-
-import java.sql.Connection;
-import java.sql.DatabaseMetaData;
-import java.sql.ResultSet;
-import java.sql.ResultSetMetaData;
-import java.sql.Statement;
-
-/**
- * Notice that, all test begins with "IoTDB" is integration test. All test which will start the
- * IoTDB server should be defined as integration test.
- */
-@Category({LocalStandaloneTest.class, ClusterTest.class})
-public class IoTDBCompleteIT {
- private int prevDataRegionNum;
-
- @Before
- public void setUp() throws InterruptedException {
- // test different partition
- prevDataRegionNum = IoTDBDescriptor.getInstance().getConfig().getDataRegionNum();
- ConfigFactory.getConfig().setDataRegionNum(16);
- EnvFactory.getEnv().initBeforeClass();
- }
-
- @After
- public void tearDown() throws Exception {
- EnvFactory.getEnv().cleanAfterClass();
- ConfigFactory.getConfig().setDataRegionNum(prevDataRegionNum);
- }
-
- @Test
- public void test() {
- String[] sqls = {"SET STORAGE GROUP TO root.vehicle"};
- executeSQL(sqls);
- // simpleTest();
- // insertTest();
- // selectTest();
- deleteTest();
- // groupByTest();
- // funcTest();
-
- // funcTestWithOutTimeGenerator();
- }
-
- public void simpleTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{\n"
- + "\t\t\t\"d0\":{\n"
- + "\t\t\t\t\"s0\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t}\n"
- + "\t\t}\n"
- + "\t}\n"
- + "}",
- "DELETE TIMESERIES root.vehicle.d0.s0",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{}\n"
- + "\t}\n"
- + "}",
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=BOOLEAN,ENCODING=PLAIN",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT64,ENCODING=TS_2DIFF",
- "CREATE TIMESERIES root.vehicle.d0.s2 WITH DATATYPE=FLOAT,ENCODING=GORILLA",
- "CREATE TIMESERIES root.vehicle.d0.s4 WITH DATATYPE=DOUBLE,ENCODING=RLE",
- "CREATE TIMESERIES root.vehicle.d1.s5 WITH DATATYPE=TEXT,ENCODING=PLAIN",
- "CREATE TIMESERIES root.vehicle.d2.s6 WITH DATATYPE=INT32,ENCODING=TS_2DIFF,compressor=UNCOMPRESSED",
- "CREATE TIMESERIES root.vehicle.d3.s7 WITH DATATYPE=INT32,ENCODING=RLE,compressor=SNAPPY",
- "CREATE TIMESERIES root.vehicle.d4.s8 WITH DATATYPE=INT32,ENCODING=RLE,MAX_POINT_NUMBER=100",
- "CREATE TIMESERIES root.vehicle.d5.s9 WITH DATATYPE=FLOAT,ENCODING=PLAIN,compressor=SNAPPY,MAX_POINT_NUMBER=10",
- "CREATE TIMESERIES root.vehicle.d6.s10 WITH DATATYPE=DOUBLE,ENCODING=RLE,compressor=UNCOMPRESSED,MAX_POINT_NUMBER=10",
- "DELETE TIMESERIES root.vehicle.d0.**",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{\n"
- + "\t\t\t\"d4\":{\n"
- + "\t\t\t\t\"s8\":{\n"
- + "\t\t\t\t\t\"args\":\"{max_point_number=100}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d5\":{\n"
- + "\t\t\t\t\"s9\":{\n"
- + "\t\t\t\t\t\"args\":\"{max_point_number=10}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"FLOAT\",\n"
- + "\t\t\t\t\t\"Compressor\":\"SNAPPY\",\n"
- + "\t\t\t\t\t\"Encoding\":\"PLAIN\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d6\":{\n"
- + "\t\t\t\t\"s10\":{\n"
- + "\t\t\t\t\t\"args\":\"{max_point_number=10}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"DOUBLE\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d1\":{\n"
- + "\t\t\t\t\"s5\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"TEXT\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"PLAIN\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d2\":{\n"
- + "\t\t\t\t\"s6\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"UNCOMPRESSED\",\n"
- + "\t\t\t\t\t\"Encoding\":\"TS_2DIFF\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t},\n"
- + "\t\t\t\"d3\":{\n"
- + "\t\t\t\t\"s7\":{\n"
- + "\t\t\t\t\t\"args\":\"{}\",\n"
- + "\t\t\t\t\t\"StorageGroup\":\"root.vehicle\",\n"
- + "\t\t\t\t\t\"DataType\":\"INT32\",\n"
- + "\t\t\t\t\t\"Compressor\":\"SNAPPY\",\n"
- + "\t\t\t\t\t\"Encoding\":\"RLE\"\n"
- + "\t\t\t\t}\n"
- + "\t\t\t}\n"
- + "\t\t}\n"
- + "\t}\n"
- + "}",
- "DELETE TIMESERIES root.vehicle.**",
- "SHOW TIMESERIES",
- "=== Timeseries Tree ===\n"
- + "\n"
- + "{\n"
- + "\t\"root\":{\n"
- + "\t\t\"vehicle\":{}\n"
- + "\t}\n"
- + "}"
- };
- executeSQL(sqlS);
- }
-
- public void insertTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,101)",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0,s1) values(2,102,202)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2000-01-01T08:00:00+08:00,105)",
- "SELECT * FROM root.vehicle.d0",
- "1,101,null,\n" + "2,102,202,\n" + "946684800000,105,null,\n" + "NOW(),104,null,\n",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void deleteTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,101)",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0,s1) values(2,102,202)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2000-01-01T08:00:00+08:00,105)",
- "SELECT * FROM root.vehicle.d0",
- "1,101,null,\n" + "2,102,202,\n" + "946684800000,105,null,\n" + "NOW(),104,null,\n",
- "DELETE TIMESERIES root.vehicle.**",
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,1)",
- "SELECT * FROM root.vehicle.d0",
- "1,1,\n" + "2,1,\n" + "3,1,\n" + "4,1,\n" + "5,1,\n" + "6,1,\n" + "7,1,\n" + "8,1,\n"
- + "9,1,\n" + "10,1,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time < 8",
- "SELECT * FROM root.vehicle.d0",
- "8,1,\n" + "9,1,\n" + "10,1,\n",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2000-01-01T08:00:00+08:00,1)",
- "SELECT * FROM root.vehicle.d0",
- "8,1,\n" + "9,1,\n" + "10,1,\n" + "946684800000,1,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time < 2000-01-02T08:00:00+08:00",
- "SELECT * FROM root.vehicle.d0",
- "",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),1)",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),1,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "",
- "CREATE TIMESERIES root.vehicle.d1.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,1)",
- "INSERT INTO root.vehicle.d1(timestamp,s1) values(1,1)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,5)",
- "INSERT INTO root.vehicle.d1(timestamp,s1) values(5,5)",
- "SELECT * FROM root.vehicle.*",
- "1,1,1,\n" + "5,5,5,\n",
- "DELETE FROM root.vehicle.d0.s0,root.vehicle.d1.s1 WHERE time < 3",
- "SELECT * FROM root.vehicle.*",
- "5,5,5,\n",
- "DELETE FROM root.vehicle.** WHERE time < 7",
- "SELECT * FROM root.vehicle.*",
- "",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void selectTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,101)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,110)",
- "SELECT * FROM root.vehicle.d0 WHERE s0 < 104",
- "1,101,\n" + "2,102,\n" + "3,103,\n",
- "SELECT * FROM root.vehicle.d0 WHERE s0 > 105 and time < 8",
- "6,106,\n" + "7,107,\n",
- "SELECT * FROM root.vehicle.d0",
- "1,101,\n"
- + "2,102,\n"
- + "3,103,\n"
- + "4,104,\n"
- + "5,105,\n"
- + "6,106,\n"
- + "7,107,\n"
- + "8,108,\n"
- + "9,109,\n"
- + "10,110,\n",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void funcTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,110)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,101)",
- "SELECT COUNT(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT COUNT(s0) FROM root.vehicle.d0 WHERE root.vehicle.d0.s0 < 105",
- "0,4,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0 WHERE root.vehicle.d0.s0 > 105",
- "0,5,\n",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0",
- "0,1,\n",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0 WHERE root.vehicle.d0.s0 < 106",
- "0,6,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0",
- "0,110,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0 WHERE time > 4",
- "0,106,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0",
- "0,101,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0 WHERE time < 5",
- "0,107,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= 10",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),5)",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),5,\n",
- "UPDATE root.vehicle.d0 SET s0 = 10 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),10,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void funcTestWithOutTimeGenerator() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,110)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,101)",
- "SELECT COUNT(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0",
- "0,10,\n",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0",
- "0,1,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0",
- "0,110,\n",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0 WHERE time > 4",
- "0,106,\n",
- "SELECT SUM(s0) FROM root.vehicle.d0 WHERE time > 4",
- "0,621.0,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0",
- "0,101,\n",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0 WHERE time < 5",
- "0,107,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= 10",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(NOW(),5)",
- "SELECT * FROM root.vehicle.d0",
- "NOW(),5,\n",
- "DELETE FROM root.vehicle.d0.s0 WHERE time <= NOW()",
- "SELECT * FROM root.vehicle.d0",
- "",
- "SELECT COUNT(s0) FROM root.vehicle.d0",
- "0,0,\n",
- "SELECT MAX_TIME(s0) FROM root.vehicle.d0",
- "",
- "SELECT MIN_TIME(s0) FROM root.vehicle.d0",
- "",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0",
- "",
- "SELECT MAX_VALUE(s0) FROM root.vehicle.d0 WHERE time > 4",
- "",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0",
- "",
- "SELECT MIN_VALUE(s0) FROM root.vehicle.d0 WHERE time < 5",
- "",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- public void groupByTest() {
- String[] sqlS = {
- "CREATE TIMESERIES root.vehicle.d0.s0 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(1,110)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(2,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(3,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(4,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(5,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(6,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(7,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(8,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(9,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s0) values(10,101)",
- "CREATE TIMESERIES root.vehicle.d0.s1 WITH DATATYPE=INT32,ENCODING=RLE",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(1,101)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(2,102)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(3,103)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(4,104)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(5,105)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(6,106)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(7,107)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(8,108)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(9,109)",
- "INSERT INTO root.vehicle.d0(timestamp,s1) values(10,110)",
- "SELECT COUNT(s0), COUNT(s1) FROM root.vehicle.d0 WHERE s1 < 109 GROUP BY(4ms,[1,10])",
- "1,3,3,\n" + "4,4,4,\n" + "8,1,1,\n",
- "SELECT COUNT(s0), MAX_VALUE(s1) FROM root.vehicle.d0 WHERE time < 7 GROUP BY(3ms,2,[1,5])",
- "1,1,101,\n" + "2,3,104,\n" + "5,1,105,\n",
- "SELECT MIN_VALUE(s0), MAX_TIME(s1) FROM root.vehicle.d0 WHERE s1 > 102 and time < 9 GROUP BY(3ms,1,[1,4],[6,9])",
- "1,108,3,\n" + "4,105,6,\n" + "7,103,8,\n",
- "DELETE TIMESERIES root.vehicle.**"
- };
- executeSQL(sqlS);
- }
-
- private void executeSQL(String[] sqls) {
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- String result = "";
- Long now_start = 0L;
- boolean cmp = false;
-
- for (String sql : sqls) {
- if (cmp) {
- Assert.assertEquals(sql, result);
- cmp = false;
- } else if (sql.equals("SHOW TIMESERIES")) {
- DatabaseMetaData data = connection.getMetaData();
- result = data.toString();
- cmp = true;
- } else {
- if (sql.contains("NOW()") && now_start == 0L) {
- now_start = System.currentTimeMillis();
- }
-
- statement.execute(sql);
- if (sql.split(" ")[0].equals("SELECT")) {
- ResultSet resultSet = statement.getResultSet();
- ResultSetMetaData metaData = resultSet.getMetaData();
- int count = metaData.getColumnCount();
- String[] column = new String[count];
- for (int i = 0; i < count; i++) {
- column[i] = metaData.getColumnName(i + 1);
- }
- result = "";
- while (resultSet.next()) {
- for (int i = 1; i <= count; i++) {
- if (now_start > 0L && column[i - 1] == TestConstant.TIMESTAMP_STR) {
- String timestr = resultSet.getString(i);
- Long tn = Long.valueOf(timestr);
- Long now = System.currentTimeMillis();
- if (tn >= now_start && tn <= now) {
- timestr = "NOW()";
- }
- result += timestr + ',';
- } else {
- result += resultSet.getString(i) + ',';
- }
- }
- result += '\n';
- }
- cmp = true;
- }
- }
- }
- } catch (Exception e) {
- e.printStackTrace();
- }
- }
-}
diff --git a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBCreateAlignedTimeseriesIT.java b/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBCreateAlignedTimeseriesIT.java
deleted file mode 100644
index b5327716e8..0000000000
--- a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBCreateAlignedTimeseriesIT.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * 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;
-
-import org.apache.iotdb.db.utils.EnvironmentUtils;
-import org.apache.iotdb.itbase.category.LocalStandaloneTest;
-import org.apache.iotdb.jdbc.Config;
-import org.apache.iotdb.jdbc.IoTDBSQLException;
-
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-
-import java.sql.Connection;
-import java.sql.DriverManager;
-import java.sql.ResultSet;
-import java.sql.SQLException;
-import java.sql.Statement;
-
-/**
- * Notice that, all test begins with "IoTDB" is integration test. All test which will start the
- * IoTDB server should be defined as integration test.
- */
-@Category({LocalStandaloneTest.class})
-public class IoTDBCreateAlignedTimeseriesIT {
-
- private Statement statement;
- private Connection connection;
-
- @Before
- public void setUp() throws Exception {
- EnvironmentUtils.envSetUp();
-
- Class.forName(Config.JDBC_DRIVER_NAME);
- connection = DriverManager.getConnection("jdbc:iotdb://127.0.0.1:6667/", "root", "root");
- statement = connection.createStatement();
- }
-
- @After
- public void tearDown() throws Exception {
- statement.close();
- connection.close();
- EnvironmentUtils.cleanEnv();
- }
-
- @Test
- public void testCreateAlignedTimeseriesWithDeletion() throws Exception {
- String[] timeSeriesArray =
- new String[] {
- "root.sg1.d1.vector1.s1,DOUBLE,PLAIN,SNAPPY", "root.sg1.d1.vector1.s2,INT64,RLE,SNAPPY"
- };
-
- statement.execute("SET STORAGE GROUP TO root.sg1");
- try {
- statement.execute(
- "CREATE ALIGNED TIMESERIES root.sg1.d1.vector1(s1 FLOAT encoding=PLAIN compressor=UNCOMPRESSED,s2 INT64 encoding=RLE)");
- statement.execute("DELETE TIMESERIES root.sg1.d1.vector1.s1");
- statement.execute(
- "CREATE ALIGNED TIMESERIES root.sg1.d1.vector1(s1 DOUBLE encoding=PLAIN compressor=SNAPPY)");
- } catch (IoTDBSQLException e) {
- e.printStackTrace();
- }
-
- // ensure that current storage group in cache is right.
- assertTimeseriesEquals(timeSeriesArray);
-
- statement.close();
- connection.close();
- EnvironmentUtils.stopDaemon();
- setUp();
-
- // ensure storage group in cache is right after recovering.
- assertTimeseriesEquals(timeSeriesArray);
- }
-
- private void assertTimeseriesEquals(String[] timeSeriesArray) throws SQLException {
- boolean hasResult = statement.execute("SHOW TIMESERIES");
- Assert.assertTrue(hasResult);
-
- int count = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ActualResult =
- resultSet.getString("timeseries")
- + ","
- + resultSet.getString("dataType")
- + ","
- + resultSet.getString("encoding")
- + ","
- + resultSet.getString("compression");
- Assert.assertEquals(timeSeriesArray[count], ActualResult);
- count++;
- }
- }
- Assert.assertEquals(timeSeriesArray.length, count);
- }
-}
diff --git a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBDeleteTimeseriesIT.java b/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBDeleteTimeseriesIT.java
deleted file mode 100644
index 8df643e9b4..0000000000
--- a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBDeleteTimeseriesIT.java
+++ /dev/null
@@ -1,215 +0,0 @@
-/*
- * 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;
-
-import org.apache.iotdb.db.conf.IoTDBDescriptor;
-import org.apache.iotdb.db.utils.EnvironmentUtils;
-import org.apache.iotdb.integration.env.ConfigFactory;
-import org.apache.iotdb.integration.env.EnvFactory;
-import org.apache.iotdb.itbase.category.LocalStandaloneTest;
-
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-
-import java.sql.Connection;
-import java.sql.ResultSet;
-import java.sql.ResultSetMetaData;
-import java.sql.Statement;
-
-import static org.apache.iotdb.db.constant.TestConstant.TIMESTAMP_STR;
-import static org.apache.iotdb.db.constant.TestConstant.count;
-import static org.junit.Assert.fail;
-
-@Category({LocalStandaloneTest.class})
-public class IoTDBDeleteTimeseriesIT {
-
- private long memtableSizeThreshold;
-
- @Before
- public void setUp() throws Exception {
- memtableSizeThreshold = IoTDBDescriptor.getInstance().getConfig().getMemtableSizeThreshold();
- ConfigFactory.getConfig().setMemtableSizeThreshold(16);
- EnvFactory.getEnv().initBeforeTest();
- }
-
- @After
- public void tearDown() throws Exception {
- ConfigFactory.getConfig().setMemtableSizeThreshold(memtableSizeThreshold);
- EnvFactory.getEnv().cleanAfterTest();
- }
-
- @Test
- public void deleteTimeseriesAndCreateDifferentTypeTest() throws Exception {
- String[] retArray = new String[] {"1,1,", "2,1.1,"};
- int cnt = 0;
-
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- statement.execute(
- "create timeseries root.turbine1.d1.s1 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
- statement.execute(
- "create timeseries root.turbine1.d1.s2 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) VALUES(1,1,2)");
- boolean hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- statement.execute("DELETE timeseries root.turbine1.d1.s1");
- statement.execute(
- "create timeseries root.turbine1.d1.s1 with datatype=DOUBLE, encoding=PLAIN, compression=SNAPPY");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) VALUES(2,1.1)");
- statement.execute("FLUSH");
-
- hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- }
-
- EnvironmentUtils.restartDaemon();
-
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- boolean hasResult = statement.execute("SELECT * FROM root.**");
- Assert.assertTrue(hasResult);
- }
- }
-
- @Test
- public void deleteTimeseriesAndCreateSameTypeTest() throws Exception {
- String[] retArray = new String[] {"1,1,", "2,5,"};
- int cnt = 0;
-
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- statement.execute(
- "create timeseries root.turbine1.d1.s1 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
- statement.execute(
- "create timeseries root.turbine1.d1.s2 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) VALUES(1,1,2)");
- boolean hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- statement.execute("DELETE timeseries root.turbine1.d1.s1");
- statement.execute(
- "create timeseries root.turbine1.d1.s1 with datatype=INT64, encoding=PLAIN, compression=SNAPPY");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) VALUES(2,5)");
- statement.execute("FLUSH");
-
- hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- }
-
- EnvironmentUtils.restartDaemon();
-
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- boolean hasResult = statement.execute("SELECT * FROM root.**");
- Assert.assertTrue(hasResult);
- }
- }
-
- @Test
- public void deleteTimeSeriesMultiIntervalTest() {
- String[] retArray1 = new String[] {"0,0"};
-
- int preAvgSeriesPointNumberThreshold =
- IoTDBDescriptor.getInstance().getConfig().getAvgSeriesPointNumberThreshold();
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
-
- IoTDBDescriptor.getInstance().getConfig().setAvgSeriesPointNumberThreshold(2);
- String insertSql = "insert into root.sg.d1(time, s1) values(%d, %d)";
- for (int i = 1; i <= 4; i++) {
- statement.execute(String.format(insertSql, i, i));
- }
- statement.execute("flush");
-
- statement.execute("delete from root.sg.d1.s1 where time >= 1 and time <= 2");
- statement.execute("delete from root.sg.d1.s1 where time >= 3 and time <= 4");
-
- boolean hasResultSet =
- statement.execute("select count(s1) from root.sg.d1 where time >= 3 and time <= 4");
-
- Assert.assertTrue(hasResultSet);
- int cnt = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(TIMESTAMP_STR)
- + ","
- + resultSet.getString(count("root.sg.d1.s1"));
- Assert.assertEquals(retArray1[cnt], ans);
- cnt++;
- }
- Assert.assertEquals(retArray1.length, cnt);
- }
- } catch (Exception e) {
- e.printStackTrace();
- fail(e.getMessage());
- } finally {
- IoTDBDescriptor.getInstance()
- .getConfig()
- .setAvgSeriesPointNumberThreshold(preAvgSeriesPointNumberThreshold);
- }
- }
-}
diff --git a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBTagIT.java b/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBTagIT.java
deleted file mode 100644
index eaac40ef72..0000000000
--- a/integration/src/test/java/org/apache/iotdb/db/integration/IoTDBTagIT.java
+++ /dev/null
@@ -1,315 +0,0 @@
-/*
- * 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;
-
-import org.apache.iotdb.db.mpp.common.header.ColumnHeaderConstant;
-import org.apache.iotdb.integration.env.EnvFactory;
-import org.apache.iotdb.itbase.category.ClusterTest;
-import org.apache.iotdb.itbase.category.LocalStandaloneTest;
-import org.apache.iotdb.itbase.category.RemoteTest;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-
-import java.sql.Connection;
-import java.sql.ResultSet;
-import java.sql.Statement;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-import static org.junit.Assert.fail;
-
-@Category({LocalStandaloneTest.class, ClusterTest.class, RemoteTest.class})
-public class IoTDBTagIT {
-
- @Before
- public void setUp() throws Exception {
- EnvFactory.getEnv().initBeforeTest();
- }
-
- @After
- public void tearDown() throws Exception {
- EnvFactory.getEnv().cleanAfterTest();
- }
-
- @Test
- public void deleteTest() {
- List<String> ret1 =
- Arrays.asList(
- "root.turbine.d7.s1,temperature,root.turbine,FLOAT,RLE,SNAPPY,"
- + "{\"tag1\":\"t1\",\"tag2\":\"t2\"},{\"attr2\":\"a2\",\"attr1\":\"a1\"}",
- "root.turbine.d7.s2,status,root.turbine,INT32,RLE,SNAPPY,{\"tag2\""
- + ":\"t2\",\"tag3\":\"t3\"},{\"attr4\":\"a4\",\"attr3\":\"a3\"}");
- List<String> ret2 =
- Collections.singletonList(
- "root.turbine.d7.s1,temperature,root.turbine,FLOAT,RLE,SNAPPY,"
- + "{\"tag1\":\"t1\",\"tag2\":\"t2\"},{\"attr2\":\"a2\",\"attr1\":\"a1\"}");
-
- String sql1 =
- "create timeseries root.turbine.d7.s1(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('tag1'='t1', 'tag2'='t2') "
- + "attributes('attr1'='a1', 'attr2'='a2')";
- String sql2 =
- "create timeseries root.turbine.d7.s2(status) with datatype=INT32, encoding=RLE "
- + "tags('tag2'='t2', 'tag3'='t3') "
- + "attributes('attr3'='a3', 'attr4'='a4')";
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- statement.execute(sql1);
- statement.execute(sql2);
- boolean hasResult = statement.execute("show timeseries");
- assertTrue(hasResult);
- int count = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ALIAS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_STORAGE_GROUP)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_DATATYPE)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ENCODING)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_COMPRESSION)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TAGS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_ATTRIBUTES);
-
- assertTrue(ret1.contains(ans));
- count++;
- }
- }
- assertEquals(ret1.size(), count);
-
- statement.execute("delete timeseries root.turbine.d7.s2");
- hasResult = statement.execute("show timeseries");
- assertTrue(hasResult);
- count = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ALIAS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_STORAGE_GROUP)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_DATATYPE)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ENCODING)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_COMPRESSION)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TAGS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_ATTRIBUTES);
-
- assertTrue(ret2.contains(ans));
- count++;
- }
- }
- assertEquals(ret2.size(), count);
- } catch (Exception e) {
- e.printStackTrace();
- fail();
- }
- }
-
- @Test
- public void deleteWithAliasTest() {
- List<String> ret1 =
- Arrays.asList(
- "root.turbine.d7.s1,temperature,root.turbine,FLOAT,RLE,SNAPPY,"
- + "{\"tag1\":\"t1\",\"tag2\":\"t2\"},{\"attr2\":\"a2\",\"attr1\":\"a1\"}",
- "root.turbine.d7.s2,status,root.turbine,INT32,RLE,SNAPPY,"
- + "{\"tag2\":\"t2\",\"tag3\":\"t3\"},{\"attr4\":\"a4\",\"attr3\":\"a3\"}");
- List<String> ret2 =
- Collections.singletonList(
- "root.turbine.d7.s1,temperature,root.turbine,FLOAT,RLE,SNAPPY,"
- + "{\"tag1\":\"t1\",\"tag2\":\"t2\"},{\"attr2\":\"a2\",\"attr1\":\"a1\"}");
-
- String sql1 =
- "create timeseries root.turbine.d7.s1(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('tag1'='t1', 'tag2'='t2') "
- + "attributes('attr1'='a1', 'attr2'='a2')";
- String sql2 =
- "create timeseries root.turbine.d7.s2(status) with datatype=INT32, encoding=RLE "
- + "tags('tag2'='t2', 'tag3'='t3') "
- + "attributes('attr3'='a3', 'attr4'='a4')";
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- statement.execute(sql1);
- statement.execute(sql2);
- boolean hasResult = statement.execute("show timeseries");
- assertTrue(hasResult);
- int count = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ALIAS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_STORAGE_GROUP)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_DATATYPE)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ENCODING)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_COMPRESSION)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TAGS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_ATTRIBUTES);
-
- assertTrue(ret1.contains(ans));
- count++;
- }
- }
- assertEquals(ret1.size(), count);
-
- statement.execute("delete timeseries root.turbine.d7.status");
- hasResult = statement.execute("show timeseries");
- assertTrue(hasResult);
- count = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ALIAS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_STORAGE_GROUP)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_DATATYPE)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ENCODING)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_COMPRESSION)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TAGS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_ATTRIBUTES);
-
- assertTrue(ret2.contains(ans));
- count++;
- }
- }
- assertEquals(ret2.size(), count);
- } catch (Exception e) {
- e.printStackTrace();
- fail();
- }
- }
-
- @Test
- public void queryWithWhereAndDeleteTest() {
- Set<String> ret = new HashSet<>();
- ret.add(
- "root.turbine.d0.s0,temperature,root.turbine,FLOAT,RLE,SNAPPY,{\"description\":\""
- + "turbine this is a test1\",\"unit\":\"f\"},{\"H_Alarm\":\"100\",\"M_Alarm\":\"50\"}");
- ret.add(
- "root.ln.d0.s0,temperature,root.ln,FLOAT,RLE,SNAPPY,{\"description\":\"ln this "
- + "is a test1\",\"unit\":\"f\"},{\"H_Alarm\":\"1000\",\"M_Alarm\":\"500\"}");
-
- String[] sqls = {
- "create timeseries root.turbine.d0.s0(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('unit'='f', 'description'='turbine this is a test1') "
- + "attributes('H_Alarm'='100', 'M_Alarm'='50')",
- "create timeseries root.turbine.d0.s1(power) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('unit'='kw', 'description'='turbine this is a test2') "
- + "attributes('H_Alarm'='99.9', 'M_Alarm'='44.4')",
- "create timeseries root.turbine.d1.s0(status) with datatype=INT32, encoding=RLE "
- + "tags('description'='turbine this is a test3') "
- + "attributes('H_Alarm'='9', 'M_Alarm'='5')",
- "create timeseries root.turbine.d2.s0(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('unit'='f', 'description'='turbine d2 this is a test1') "
- + "attributes('MaxValue'='100', 'MinValue'='1')",
- "create timeseries root.turbine.d2.s1(power) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('unit'='kw', 'description'='turbine d2 this is a test2') "
- + "attributes('MaxValue'='99.9', 'MinValue'='44.4')",
- "create timeseries root.turbine.d2.s3(status) with datatype=INT32, encoding=RLE "
- + "tags('description'='turbine d2 this is a test3') "
- + "attributes('MaxValue'='9', 'MinValue'='5')",
- "create timeseries root.ln.d0.s0(temperature) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('unit'='f', 'description'='ln this is a test1') "
- + "attributes('H_Alarm'='1000', 'M_Alarm'='500')",
- "create timeseries root.ln.d0.s1(power) with datatype=FLOAT, encoding=RLE, compression=SNAPPY "
- + "tags('unit'='w', 'description'='ln this is a test2') "
- + "attributes('H_Alarm'='9.9', 'M_Alarm'='4.4')",
- "create timeseries root.ln.d1.s0(status) with datatype=INT32, encoding=RLE "
- + "tags('description'='ln this is a test3') "
- + "attributes('H_Alarm'='90', 'M_Alarm'='50')",
- };
- try (Connection connection = EnvFactory.getEnv().getConnection();
- Statement statement = connection.createStatement()) {
- for (String sql : sqls) {
- statement.execute(sql);
- }
-
- statement.execute("delete timeseries root.turbine.d2.s0");
-
- // with *
- boolean hasResult = statement.execute("show timeseries where 'unit'='f'");
- assertTrue(hasResult);
- int count = 0;
- Set<String> res = new HashSet<>();
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ALIAS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_STORAGE_GROUP)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_DATATYPE)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_ENCODING)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TIMESERIES_COMPRESSION)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_TAGS)
- + ","
- + resultSet.getString(ColumnHeaderConstant.COLUMN_ATTRIBUTES);
-
- res.add(ans);
- count++;
- }
- }
- assertEquals(ret, res);
- assertEquals(ret.size(), count);
-
- } catch (Exception e) {
- e.printStackTrace();
- fail();
- }
- }
-}
diff --git a/integration/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBDeleteTimeseriesIT.java b/integration/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBDeleteTimeseriesIT.java
deleted file mode 100644
index a86b591b02..0000000000
--- a/integration/src/test/java/org/apache/iotdb/db/integration/aligned/IoTDBDeleteTimeseriesIT.java
+++ /dev/null
@@ -1,281 +0,0 @@
-/*
- * 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.itbase.category.LocalStandaloneTest;
-import org.apache.iotdb.jdbc.Config;
-
-import org.junit.After;
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-
-import java.sql.Connection;
-import java.sql.DriverManager;
-import java.sql.ResultSet;
-import java.sql.ResultSetMetaData;
-import java.sql.Statement;
-
-import static org.apache.iotdb.db.constant.TestConstant.TIMESTAMP_STR;
-import static org.apache.iotdb.db.constant.TestConstant.count;
-import static org.junit.Assert.fail;
-
-@Category({LocalStandaloneTest.class})
-public class IoTDBDeleteTimeseriesIT {
-
- private long memtableSizeThreshold;
-
- @Before
- public void setUp() throws ClassNotFoundException {
- Class.forName(Config.JDBC_DRIVER_NAME);
- EnvironmentUtils.envSetUp();
- memtableSizeThreshold = IoTDBDescriptor.getInstance().getConfig().getMemtableSizeThreshold();
- IoTDBDescriptor.getInstance().getConfig().setMemtableSizeThreshold(16);
- }
-
- @After
- public void tearDown() throws Exception {
- IoTDBDescriptor.getInstance().getConfig().setMemtableSizeThreshold(memtableSizeThreshold);
- EnvironmentUtils.cleanEnv();
- }
-
- @Test
- public void deleteTimeseriesAndCreateDifferentTypeTest() throws Exception {
- String[] retArray = new String[] {"1,1,", "2,1.1,"};
- int cnt = 0;
-
- try (Connection connection =
- DriverManager.getConnection("jdbc:iotdb://127.0.0.1:6667/", "root", "root");
- Statement statement = connection.createStatement()) {
- statement.execute(
- "create aligned timeseries root.turbine1.d1(s1 INT64 encoding=PLAIN compression=SNAPPY, "
- + "s2 INT64 encoding=PLAIN compression=SNAPPY)");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
- boolean hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- statement.execute("DELETE timeseries root.turbine1.d1.s1");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) ALIGNED VALUES(2,1.1)");
- statement.execute("FLUSH");
-
- hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- }
-
- EnvironmentUtils.restartDaemon();
-
- try (Connection connection =
- DriverManager.getConnection(
- Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
- Statement statement = connection.createStatement()) {
- boolean hasResult = statement.execute("SELECT * FROM root.**");
- Assert.assertTrue(hasResult);
- }
- }
-
- @Test
- public void deleteTimeseriesAndCreateSameTypeTest() throws Exception {
- String[] retArray = new String[] {"1,1.0,", "2,5.0,"};
- int cnt = 0;
-
- try (Connection connection =
- DriverManager.getConnection("jdbc:iotdb://127.0.0.1:6667/", "root", "root");
- Statement statement = connection.createStatement()) {
- statement.execute(
- "create aligned timeseries root.turbine1.d1(s1 FLOAT encoding=PLAIN compression=SNAPPY, "
- + "s2 INT64 encoding=PLAIN compression=SNAPPY)");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
- boolean hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- statement.execute("DELETE timeseries root.turbine1.d1.s1");
- statement.execute("INSERT INTO root.turbine1.d1(timestamp,s1) ALIGNED VALUES(2,5)");
- statement.execute("FLUSH");
-
- hasResult = statement.execute("SELECT s1 FROM root.turbine1.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- }
-
- EnvironmentUtils.restartDaemon();
-
- try (Connection connection =
- DriverManager.getConnection(
- Config.IOTDB_URL_PREFIX + "127.0.0.1:6667/", "root", "root");
- Statement statement = connection.createStatement()) {
- boolean hasResult = statement.execute("SELECT * FROM root.**");
- Assert.assertTrue(hasResult);
- }
- }
-
- @Test
- public void deleteTimeseriesAndChangeDeviceAlignmentTest() throws Exception {
- String[] retArray = new String[] {"1,1.0,2.0,"};
- int cnt = 0;
-
- try (Connection connection =
- DriverManager.getConnection("jdbc:iotdb://127.0.0.1:6667/", "root", "root");
- Statement statement = connection.createStatement()) {
- statement.execute("INSERT INTO root.sg3.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
- statement.execute("SHOW DEVICES");
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- Assert.assertEquals("true", resultSet.getString("isAligned"));
- }
- }
- cnt = 0;
- statement.execute("DELETE timeseries root.sg3.d1.s1");
- statement.execute("DELETE timeseries root.sg3.d1.s2");
- statement.execute("INSERT INTO root.sg3.d1(timestamp,s1,s2) VALUES(1,1,2)");
- statement.execute("SHOW DEVICES");
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- Assert.assertEquals("false", resultSet.getString("isAligned"));
- }
- }
- boolean hasResult = statement.execute("SELECT * FROM root.sg3.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- cnt = 0;
- statement.execute("DELETE timeseries root.sg3.d1.s1");
- statement.execute("DELETE timeseries root.sg3.d1.s2");
- statement.execute("INSERT INTO root.sg3.d1(timestamp,s1,s2) ALIGNED VALUES(1,1,2)");
- statement.execute("SHOW DEVICES");
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- Assert.assertEquals("true", resultSet.getString("isAligned"));
- }
- }
- hasResult = statement.execute("SELECT * FROM root.sg3.d1");
- Assert.assertTrue(hasResult);
- try (ResultSet resultSet = statement.getResultSet()) {
- ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
- while (resultSet.next()) {
- StringBuilder builder = new StringBuilder();
- for (int i = 1; i <= resultSetMetaData.getColumnCount(); i++) {
- builder.append(resultSet.getString(i)).append(",");
- }
- Assert.assertEquals(retArray[cnt], builder.toString());
- cnt++;
- }
- }
- }
- }
-
- @Test
- public void deleteTimeSeriesMultiIntervalTest() {
- String[] retArray1 = new String[] {"0,0"};
-
- int preAvgSeriesPointNumberThreshold =
- IoTDBDescriptor.getInstance().getConfig().getAvgSeriesPointNumberThreshold();
- try (Connection connection =
- DriverManager.getConnection("jdbc:iotdb://127.0.0.1:6667/", "root", "root");
- Statement statement = connection.createStatement()) {
-
- IoTDBDescriptor.getInstance().getConfig().setAvgSeriesPointNumberThreshold(2);
- String insertSql = "insert into root.sg.d1(time, s1) aligned values(%d, %d)";
- for (int i = 1; i <= 4; i++) {
- statement.execute(String.format(insertSql, i, i));
- }
- statement.execute("flush");
-
- statement.execute("delete from root.sg.d1.s1 where time >= 1 and time <= 2");
- statement.execute("delete from root.sg.d1.s1 where time >= 3 and time <= 4");
-
- boolean hasResultSet =
- statement.execute("select count(s1) from root.sg.d1 where time >= 3 and time <= 4");
-
- Assert.assertTrue(hasResultSet);
- int cnt = 0;
- try (ResultSet resultSet = statement.getResultSet()) {
- while (resultSet.next()) {
- String ans =
- resultSet.getString(TIMESTAMP_STR)
- + ","
- + resultSet.getString(count("root.sg.d1.s1"));
- Assert.assertEquals(retArray1[cnt], ans);
- cnt++;
- }
- Assert.assertEquals(retArray1.length, cnt);
- }
- } catch (Exception e) {
- e.printStackTrace();
- fail(e.getMessage());
- } finally {
- IoTDBDescriptor.getInstance()
- .getConfig()
- .setAvgSeriesPointNumberThreshold(preAvgSeriesPointNumberThreshold);
- }
- }
-}
diff --git a/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/RSchemaRegion.java b/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/RSchemaRegion.java
index f82465708f..6aed5211f7 100644
--- a/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/RSchemaRegion.java
+++ b/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/RSchemaRegion.java
@@ -56,6 +56,7 @@ import org.apache.iotdb.db.metadata.schemaregion.rocksdb.mnode.RMeasurementMNode
import org.apache.iotdb.db.metadata.template.Template;
import org.apache.iotdb.db.metadata.utils.MetaFormatUtils;
import org.apache.iotdb.db.mpp.common.schematree.DeviceSchemaInfo;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.qp.physical.crud.InsertPlan;
import org.apache.iotdb.db.qp.physical.crud.InsertRowPlan;
import org.apache.iotdb.db.qp.physical.crud.InsertTabletPlan;
@@ -681,6 +682,27 @@ public class RSchemaRegion implements ISchemaRegion {
}
}
+ @Override
+ public int constructSchemaBlackList(PathPatternTree patternTree) throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public void rollbackSchemaBlackList(PathPatternTree patternTree) throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public List<PartialPath> fetchSchemaBlackList(PathPatternTree patternTree)
+ throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public void deleteTimeseriesInBlackList(PathPatternTree patternTree) throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
private void traverseOutcomeBasins(
String[] nodes,
int maxLevel,
diff --git a/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/mnode/RMeasurementMNode.java b/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/mnode/RMeasurementMNode.java
index fe52cb7207..fc87ad1321 100644
--- a/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/mnode/RMeasurementMNode.java
+++ b/schema-engine-rocksdb/src/main/java/org/apache/iotdb/db/metadata/schemaregion/rocksdb/mnode/RMeasurementMNode.java
@@ -151,6 +151,14 @@ public class RMeasurementMNode extends RMNode implements IMeasurementMNode {
throw new UnsupportedOperationException();
}
+ @Override
+ public boolean isPreDeleted() {
+ return false;
+ }
+
+ @Override
+ public void setPreDeleted(boolean preDeleted) {}
+
@Override
public void serializeTo(MLogWriter logWriter) throws IOException {
throw new UnsupportedOperationException();
diff --git a/server/src/main/java/org/apache/iotdb/db/client/ConfigNodeClient.java b/server/src/main/java/org/apache/iotdb/db/client/ConfigNodeClient.java
index de2bc80f93..2dceb33ed5 100644
--- a/server/src/main/java/org/apache/iotdb/db/client/ConfigNodeClient.java
+++ b/server/src/main/java/org/apache/iotdb/db/client/ConfigNodeClient.java
@@ -51,6 +51,7 @@ import org.apache.iotdb.confignode.rpc.thrift.TDataPartitionReq;
import org.apache.iotdb.confignode.rpc.thrift.TDataPartitionTableResp;
import org.apache.iotdb.confignode.rpc.thrift.TDeleteStorageGroupReq;
import org.apache.iotdb.confignode.rpc.thrift.TDeleteStorageGroupsReq;
+import org.apache.iotdb.confignode.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.confignode.rpc.thrift.TDropFunctionReq;
import org.apache.iotdb.confignode.rpc.thrift.TDropTriggerReq;
import org.apache.iotdb.confignode.rpc.thrift.TGetAllTemplatesResp;
@@ -982,6 +983,22 @@ public class ConfigNodeClient
throw new TException(MSG_RECONNECTION_FAIL);
}
+ @Override
+ public TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req) throws TException {
+ for (int i = 0; i < RETRY_NUM; i++) {
+ try {
+ TSStatus status = client.deleteTimeSeries(req);
+ if (!updateConfigNodeLeader(status)) {
+ return status;
+ }
+ } catch (TException e) {
+ configLeader = null;
+ }
+ reconnect();
+ }
+ throw new TException(MSG_RECONNECTION_FAIL);
+ }
+
public static class Factory extends BaseClientFactory<PartitionRegionId, ConfigNodeClient> {
public Factory(
diff --git a/server/src/main/java/org/apache/iotdb/db/client/DataNodeClientPoolFactory.java b/server/src/main/java/org/apache/iotdb/db/client/DataNodeClientPoolFactory.java
index 996e2372d5..09305eeeb3 100644
--- a/server/src/main/java/org/apache/iotdb/db/client/DataNodeClientPoolFactory.java
+++ b/server/src/main/java/org/apache/iotdb/db/client/DataNodeClientPoolFactory.java
@@ -158,4 +158,24 @@ public class DataNodeClientPoolFactory {
new ClientPoolProperty.Builder<ConfigNodeClient>().build().getConfig());
}
}
+
+ public static class ClusterDeletionConfigNodeClientPoolFactory
+ implements IClientPoolFactory<PartitionRegionId, ConfigNodeClient> {
+ @Override
+ public KeyedObjectPool<PartitionRegionId, ConfigNodeClient> createClientPool(
+ ClientManager<PartitionRegionId, ConfigNodeClient> manager) {
+ return new GenericKeyedObjectPool<>(
+ new ConfigNodeClient.Factory(
+ manager,
+ new ClientFactoryProperty.Builder()
+ .setConnectionTimeoutMs(conf.getConnectionTimeoutInMS() * 10)
+ .setRpcThriftCompressionEnabled(conf.isRpcThriftCompressionEnable())
+ .setSelectorNumOfAsyncClientManager(
+ conf.getSelectorNumOfClientManager() / 10 > 0
+ ? conf.getSelectorNumOfClientManager() / 10
+ : 1)
+ .build()),
+ new ClientPoolProperty.Builder<ConfigNodeClient>().build().getConfig());
+ }
+ }
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java b/server/src/main/java/org/apache/iotdb/db/exception/metadata/MeasurementInBlackListException.java
similarity index 58%
copy from server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java
copy to server/src/main/java/org/apache/iotdb/db/exception/metadata/MeasurementInBlackListException.java
index 99cb5b57ff..3aef42cec0 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java
+++ b/server/src/main/java/org/apache/iotdb/db/exception/metadata/MeasurementInBlackListException.java
@@ -15,31 +15,27 @@
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
+ *
*/
-package org.apache.iotdb.db.mpp.plan.statement.metadata;
+package org.apache.iotdb.db.exception.metadata;
+import org.apache.iotdb.commons.exception.MetadataException;
import org.apache.iotdb.commons.path.PartialPath;
-import org.apache.iotdb.db.mpp.plan.statement.Statement;
-import org.apache.iotdb.db.mpp.plan.statement.StatementVisitor;
-
-import java.util.List;
+import org.apache.iotdb.rpc.TSStatusCode;
-public class DeleteTimeSeriesStatement extends Statement {
+public class MeasurementInBlackListException extends MetadataException {
- List<PartialPath> partialPaths;
-
- @Override
- public List<PartialPath> getPaths() {
- return partialPaths;
- }
+ private final PartialPath path;
- public void setPartialPaths(List<PartialPath> partialPaths) {
- this.partialPaths = partialPaths;
+ public MeasurementInBlackListException(PartialPath path) {
+ super(
+ String.format("Some task is deleting timeseries [%s]", path),
+ TSStatusCode.MEASUREMENT_IN_BLACK_LIST.getStatusCode());
+ this.path = path;
}
- @Override
- public <R, C> R accept(StatementVisitor<R, C> visitor, C context) {
- return visitor.visitDeleteTimeseries(this, context);
+ public PartialPath getPath() {
+ return path;
}
}
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/cache/DataNodeSchemaCache.java b/server/src/main/java/org/apache/iotdb/db/metadata/cache/DataNodeSchemaCache.java
index 6c88cbb870..bc8ae11d08 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/cache/DataNodeSchemaCache.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/cache/DataNodeSchemaCache.java
@@ -34,6 +34,8 @@ import com.github.benmanes.caffeine.cache.Caffeine;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+
/**
* This class takes the responsibility of metadata cache management of all DataRegions under
* StorageEngine
@@ -45,6 +47,9 @@ public class DataNodeSchemaCache {
private final Cache<PartialPath, SchemaCacheEntry> cache;
+ // cache update or clean have higher priority than cache read
+ private final ReentrantReadWriteLock readWriteLock = new ReentrantReadWriteLock(false);
+
private DataNodeSchemaCache() {
cache =
Caffeine.newBuilder()
@@ -69,6 +74,23 @@ public class DataNodeSchemaCache {
private static final DataNodeSchemaCache INSTANCE = new DataNodeSchemaCache();
}
+ public void takeReadLock() {
+ readWriteLock.readLock().lock();
+ }
+
+ public void releaseReadLock() {
+ readWriteLock.readLock().unlock();
+ }
+
+ public void takeWriteLock() {
+ readWriteLock.writeLock().lock();
+ ;
+ }
+
+ public void releaseWriteLock() {
+ readWriteLock.writeLock().unlock();
+ }
+
/**
* Get SchemaEntity info without auto create schema
*
@@ -176,6 +198,17 @@ public class DataNodeSchemaCache {
cache.invalidate(partialPath);
}
+ public void invalidateMatchedSchema(PartialPath pathPattern) {
+ cache
+ .asMap()
+ .forEach(
+ (k, v) -> {
+ if (pathPattern.matchFullPath(k)) {
+ cache.invalidate(k);
+ }
+ });
+ }
+
public long estimatedSize() {
return cache.estimatedSize();
}
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/idtable/entry/InsertMeasurementMNode.java b/server/src/main/java/org/apache/iotdb/db/metadata/idtable/entry/InsertMeasurementMNode.java
index eb3b6e8e47..816de2d3eb 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/idtable/entry/InsertMeasurementMNode.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/idtable/entry/InsertMeasurementMNode.java
@@ -98,6 +98,14 @@ public class InsertMeasurementMNode implements IMeasurementMNode {
@Override
public void setLastCacheContainer(ILastCacheContainer lastCacheContainer) {}
+ @Override
+ public boolean isPreDeleted() {
+ return false;
+ }
+
+ @Override
+ public void setPreDeleted(boolean preDeleted) {}
+
@Override
public IMeasurementSchema getSchema() {
return schema;
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/mnode/IMeasurementMNode.java b/server/src/main/java/org/apache/iotdb/db/metadata/mnode/IMeasurementMNode.java
index fca21a9cbd..2ef5f09da7 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/mnode/IMeasurementMNode.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/mnode/IMeasurementMNode.java
@@ -51,4 +51,8 @@ public interface IMeasurementMNode extends IMNode {
ILastCacheContainer getLastCacheContainer();
void setLastCacheContainer(ILastCacheContainer lastCacheContainer);
+
+ boolean isPreDeleted();
+
+ void setPreDeleted(boolean preDeleted);
}
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/mnode/MeasurementMNode.java b/server/src/main/java/org/apache/iotdb/db/metadata/mnode/MeasurementMNode.java
index da8e92bffb..f15e71911d 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/mnode/MeasurementMNode.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/mnode/MeasurementMNode.java
@@ -46,6 +46,8 @@ public class MeasurementMNode extends MNode implements IMeasurementMNode {
private long offset = -1;
/** measurement's Schema for one timeseries represented by current leaf node */
private IMeasurementSchema schema;
+ /** whether this measurement is pre deleted and considered in black list */
+ private boolean preDeleted = false;
/** last value cache */
private volatile ILastCacheContainer lastCacheContainer = null;
@@ -149,6 +151,16 @@ public class MeasurementMNode extends MNode implements IMeasurementMNode {
this.lastCacheContainer = lastCacheContainer;
}
+ @Override
+ public boolean isPreDeleted() {
+ return preDeleted;
+ }
+
+ @Override
+ public void setPreDeleted(boolean preDeleted) {
+ this.preDeleted = preDeleted;
+ }
+
@Override
public void serializeTo(MLogWriter logWriter) throws IOException {
logWriter.serializeMeasurementMNode(this);
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/mtree/MTreeBelowSGMemoryImpl.java b/server/src/main/java/org/apache/iotdb/db/metadata/mtree/MTreeBelowSGMemoryImpl.java
index 4151063116..4f7b87209b 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/mtree/MTreeBelowSGMemoryImpl.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/mtree/MTreeBelowSGMemoryImpl.java
@@ -28,6 +28,7 @@ import org.apache.iotdb.db.exception.metadata.AliasAlreadyExistException;
import org.apache.iotdb.db.exception.metadata.AlignedTimeseriesException;
import org.apache.iotdb.db.exception.metadata.MNodeTypeMismatchException;
import org.apache.iotdb.db.exception.metadata.MeasurementAlreadyExistException;
+import org.apache.iotdb.db.exception.metadata.MeasurementInBlackListException;
import org.apache.iotdb.db.exception.metadata.PathAlreadyExistException;
import org.apache.iotdb.db.exception.metadata.PathNotExistException;
import org.apache.iotdb.db.exception.metadata.template.TemplateImcompatibeException;
@@ -208,8 +209,12 @@ public class MTreeBelowSGMemoryImpl implements IMTreeBelowSG {
if (device.hasChild(leafName)) {
IMNode node = device.getChild(leafName);
if (node.isMeasurement()) {
- throw new MeasurementAlreadyExistException(
- path.getFullPath(), node.getAsMeasurementMNode().getMeasurementPath());
+ if (node.getAsMeasurementMNode().isPreDeleted()) {
+ throw new MeasurementInBlackListException(path);
+ } else {
+ throw new MeasurementAlreadyExistException(
+ path.getFullPath(), node.getAsMeasurementMNode().getMeasurementPath());
+ }
} else {
throw new PathAlreadyExistException(path.getFullPath());
}
@@ -284,9 +289,13 @@ public class MTreeBelowSGMemoryImpl implements IMTreeBelowSG {
if (device.hasChild(measurements.get(i))) {
IMNode node = device.getChild(measurements.get(i));
if (node.isMeasurement()) {
- throw new MeasurementAlreadyExistException(
- devicePath.getFullPath() + "." + measurements.get(i),
- node.getAsMeasurementMNode().getMeasurementPath());
+ if (node.getAsMeasurementMNode().isPreDeleted()) {
+ throw new MeasurementInBlackListException(devicePath.concatNode(measurements.get(i)));
+ } else {
+ throw new MeasurementAlreadyExistException(
+ devicePath.getFullPath() + "." + measurements.get(i),
+ node.getAsMeasurementMNode().getMeasurementPath());
+ }
} else {
throw new PathAlreadyExistException(
devicePath.getFullPath() + "." + measurements.get(i));
@@ -442,6 +451,23 @@ public class MTreeBelowSGMemoryImpl implements IMTreeBelowSG {
&& node.getChildren().isEmpty();
}
+ public List<PartialPath> getPreDeleteTimeseries(PartialPath pathPattern)
+ throws MetadataException {
+ List<PartialPath> result = new LinkedList<>();
+ MeasurementCollector<List<PartialPath>> collector =
+ new MeasurementCollector<List<PartialPath>>(storageGroupMNode, pathPattern, store) {
+ @Override
+ protected void collectMeasurement(IMeasurementMNode node) throws MetadataException {
+ if (node.isPreDeleted()) {
+ result.add(getCurrentPartialPath(node));
+ }
+ }
+ };
+ collector.setResultSet(result);
+ collector.traverse();
+ return result;
+ }
+
@Override
public void setAlias(IMeasurementMNode measurementMNode, String alias) throws MetadataException {
store.setAlias(measurementMNode, alias);
@@ -675,6 +701,9 @@ public class MTreeBelowSGMemoryImpl implements IMTreeBelowSG {
new MeasurementCollector<List<PartialPath>>(storageGroupMNode, pathPattern, store) {
@Override
protected void collectMeasurement(IMeasurementMNode node) {
+ if (node.isPreDeleted()) {
+ return;
+ }
MeasurementPath path = getCurrentMeasurementPathInTraverse(node);
if (nodes[nodes.length - 1].equals(node.getAlias())) {
// only when user query with alias, the alias in path will be set
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/mtree/snapshot/MemMTreeSnapshotUtil.java b/server/src/main/java/org/apache/iotdb/db/metadata/mtree/snapshot/MemMTreeSnapshotUtil.java
index 6059872c20..a95af2a670 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/mtree/snapshot/MemMTreeSnapshotUtil.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/mtree/snapshot/MemMTreeSnapshotUtil.java
@@ -289,6 +289,7 @@ public class MemMTreeSnapshotUtil {
node.getSchema().serializeTo(outputStream);
ReadWriteIOUtils.write(node.getAlias(), outputStream);
ReadWriteIOUtils.write(node.getOffset(), outputStream);
+ ReadWriteIOUtils.write(node.isPreDeleted(), outputStream);
return true;
} catch (IOException e) {
logger.error(SERIALIZE_ERROR_INFO, e);
@@ -347,6 +348,7 @@ public class MemMTreeSnapshotUtil {
long tagOffset = ReadWriteIOUtils.readLong(inputStream);
MeasurementMNode node = new MeasurementMNode(null, name, schema, alias);
node.setOffset(tagOffset);
+ node.setPreDeleted(ReadWriteIOUtils.readBool(inputStream));
return node;
}
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/ISchemaRegion.java b/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/ISchemaRegion.java
index 860d5b2005..e8b444a480 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/ISchemaRegion.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/ISchemaRegion.java
@@ -30,6 +30,7 @@ import org.apache.iotdb.db.metadata.mnode.IMeasurementMNode;
import org.apache.iotdb.db.metadata.path.MeasurementPath;
import org.apache.iotdb.db.metadata.template.Template;
import org.apache.iotdb.db.mpp.common.schematree.DeviceSchemaInfo;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.qp.physical.crud.InsertPlan;
import org.apache.iotdb.db.qp.physical.sys.ActivateTemplateInClusterPlan;
import org.apache.iotdb.db.qp.physical.sys.ActivateTemplatePlan;
@@ -118,6 +119,32 @@ public interface ISchemaRegion {
*/
Pair<Integer, Set<String>> deleteTimeseries(PartialPath pathPattern, boolean isPrefixMatch)
throws MetadataException;
+
+ /**
+ * Construct schema black list via setting matched timeseries to pre deleted.
+ *
+ * @param patternTree
+ * @throws MetadataException
+ */
+ int constructSchemaBlackList(PathPatternTree patternTree) throws MetadataException;
+
+ /**
+ * Rollback schema black list via setting matched timeseries to not pre deleted.
+ *
+ * @param patternTree
+ * @throws MetadataException
+ */
+ void rollbackSchemaBlackList(PathPatternTree patternTree) throws MetadataException;
+
+ List<PartialPath> fetchSchemaBlackList(PathPatternTree patternTree) throws MetadataException;
+
+ /**
+ * Delete timeseries in schema black list.
+ *
+ * @param patternTree
+ * @throws MetadataException
+ */
+ void deleteTimeseriesInBlackList(PathPatternTree patternTree) throws MetadataException;
// endregion
// region Interfaces for auto create device
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionMemoryImpl.java b/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionMemoryImpl.java
index 90394b6041..b52936f158 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionMemoryImpl.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionMemoryImpl.java
@@ -59,6 +59,7 @@ import org.apache.iotdb.db.metadata.template.Template;
import org.apache.iotdb.db.metadata.template.TemplateManager;
import org.apache.iotdb.db.mpp.common.schematree.DeviceSchemaInfo;
import org.apache.iotdb.db.mpp.common.schematree.MeasurementSchemaInfo;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.qp.constant.SQLConstant;
import org.apache.iotdb.db.qp.physical.PhysicalPlan;
import org.apache.iotdb.db.qp.physical.crud.InsertPlan;
@@ -72,6 +73,8 @@ import org.apache.iotdb.db.qp.physical.sys.ChangeTagOffsetPlan;
import org.apache.iotdb.db.qp.physical.sys.CreateAlignedTimeSeriesPlan;
import org.apache.iotdb.db.qp.physical.sys.CreateTimeSeriesPlan;
import org.apache.iotdb.db.qp.physical.sys.DeleteTimeSeriesPlan;
+import org.apache.iotdb.db.qp.physical.sys.PreDeleteTimeSeriesPlan;
+import org.apache.iotdb.db.qp.physical.sys.RollbackPreDeleteTimeSeriesPlan;
import org.apache.iotdb.db.qp.physical.sys.SetTemplatePlan;
import org.apache.iotdb.db.qp.physical.sys.ShowDevicesPlan;
import org.apache.iotdb.db.qp.physical.sys.ShowTimeSeriesPlan;
@@ -441,6 +444,15 @@ public class SchemaRegionMemoryImpl implements ISchemaRegion {
(ActivateTemplateInClusterPlan) plan;
recoverActivatingSchemaTemplate(activateTemplateInClusterPlan);
break;
+ case PRE_DELETE_TIMESERIES_IN_CLUSTER:
+ PreDeleteTimeSeriesPlan preDeleteTimeSeriesPlan = (PreDeleteTimeSeriesPlan) plan;
+ recoverPreDeleteTimeseries(preDeleteTimeSeriesPlan.getPath());
+ break;
+ case ROLLBACK_PRE_DELETE_TIMESERIES:
+ RollbackPreDeleteTimeSeriesPlan rollbackPreDeleteTimeSeriesPlan =
+ (RollbackPreDeleteTimeSeriesPlan) plan;
+ recoverRollbackPreDeleteTimeseries(rollbackPreDeleteTimeSeriesPlan.getPath());
+ break;
default:
logger.error("Unrecognizable command {}", plan.getOperatorType());
}
@@ -831,6 +843,97 @@ public class SchemaRegionMemoryImpl implements ISchemaRegion {
}
}
+ @Override
+ public int constructSchemaBlackList(PathPatternTree patternTree) throws MetadataException {
+ int preDeletedNum = 0;
+ for (PartialPath pathPattern : patternTree.getAllPathPatterns()) {
+ for (PartialPath path : mtree.getMeasurementPaths(pathPattern)) {
+ IMeasurementMNode measurementMNode = mtree.getMeasurementMNode(path);
+ // Given pathPatterns may match one timeseries multi times, which may results in the
+ // preDeletedNum larger than the actual num of timeseries. It doesn't matter since the main
+ // purpose is to check whether there's timeseries to be deleted.
+ preDeletedNum++;
+ measurementMNode.setPreDeleted(true);
+ try {
+ writeToMLog(new PreDeleteTimeSeriesPlan(path));
+ } catch (IOException e) {
+ throw new MetadataException(e);
+ }
+ }
+ }
+ return preDeletedNum;
+ }
+
+ private void recoverPreDeleteTimeseries(PartialPath path) throws MetadataException {
+ IMeasurementMNode measurementMNode = mtree.getMeasurementMNode(path);
+ measurementMNode.setPreDeleted(true);
+ }
+
+ @Override
+ public void rollbackSchemaBlackList(PathPatternTree patternTree) throws MetadataException {
+ for (PartialPath pathPattern : patternTree.getAllPathPatterns()) {
+ for (PartialPath path : mtree.getMeasurementPaths(pathPattern)) {
+ IMeasurementMNode measurementMNode = mtree.getMeasurementMNode(path);
+ measurementMNode.setPreDeleted(false);
+ try {
+ writeToMLog(new RollbackPreDeleteTimeSeriesPlan(path));
+ } catch (IOException e) {
+ throw new MetadataException(e);
+ }
+ }
+ }
+ }
+
+ @Override
+ public List<PartialPath> fetchSchemaBlackList(PathPatternTree patternTree)
+ throws MetadataException {
+ List<PartialPath> pathList = new ArrayList<>();
+ for (PartialPath pathPattern : patternTree.getAllPathPatterns()) {
+ pathList.addAll(mtree.getPreDeleteTimeseries(pathPattern));
+ }
+ return pathList;
+ }
+
+ @Override
+ public void deleteTimeseriesInBlackList(PathPatternTree patternTree) throws MetadataException {
+ for (PartialPath pathPattern : patternTree.getAllPathPatterns()) {
+ for (PartialPath path : mtree.getPreDeleteTimeseries(pathPattern)) {
+ try {
+ deleteSingleTimeseriesInBlackList(path);
+ writeToMLog(new DeleteTimeSeriesPlan(Collections.singletonList(path)));
+ } catch (IOException e) {
+ throw new MetadataException(e);
+ }
+ }
+ }
+ }
+
+ private void deleteSingleTimeseriesInBlackList(PartialPath path)
+ throws MetadataException, IOException {
+ Pair<PartialPath, IMeasurementMNode> pair =
+ mtree.deleteTimeseriesAndReturnEmptyStorageGroup(path);
+
+ IMeasurementMNode measurementMNode = pair.right;
+ removeFromTagInvertedIndex(measurementMNode);
+
+ IMNode node = measurementMNode.getParent();
+
+ if (node.isUseTemplate() && node.getSchemaTemplate().hasSchema(measurementMNode.getName())) {
+ // measurement represent by template doesn't affect the MTree structure and memory control
+ return;
+ }
+
+ mNodeCache.invalidate(node.getPartialPath());
+
+ schemaStatisticsManager.deleteTimeseries(1);
+ seriesNumerLimiter.deleteTimeSeries(1);
+ }
+
+ private void recoverRollbackPreDeleteTimeseries(PartialPath path) throws MetadataException {
+ IMeasurementMNode measurementMNode = mtree.getMeasurementMNode(path);
+ measurementMNode.setPreDeleted(false);
+ }
+
/**
* Delete all timeseries matching the given path pattern
*
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionSchemaFileImpl.java b/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionSchemaFileImpl.java
index 051f78898f..1ce7ecf550 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionSchemaFileImpl.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/schemaregion/SchemaRegionSchemaFileImpl.java
@@ -56,6 +56,7 @@ import org.apache.iotdb.db.metadata.tag.TagManager;
import org.apache.iotdb.db.metadata.template.Template;
import org.apache.iotdb.db.metadata.template.TemplateManager;
import org.apache.iotdb.db.mpp.common.schematree.DeviceSchemaInfo;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.qp.constant.SQLConstant;
import org.apache.iotdb.db.qp.physical.PhysicalPlan;
import org.apache.iotdb.db.qp.physical.crud.InsertPlan;
@@ -753,6 +754,27 @@ public class SchemaRegionSchemaFileImpl implements ISchemaRegion {
}
}
+ @Override
+ public int constructSchemaBlackList(PathPatternTree patternTree) throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public void rollbackSchemaBlackList(PathPatternTree patternTree) throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public List<PartialPath> fetchSchemaBlackList(PathPatternTree patternTree)
+ throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public void deleteTimeseriesInBlackList(PathPatternTree patternTree) throws MetadataException {
+ throw new UnsupportedOperationException();
+ }
+
/**
* Delete all timeseries matching the given path pattern
*
diff --git a/server/src/main/java/org/apache/iotdb/db/metadata/visitor/SchemaExecutionVisitor.java b/server/src/main/java/org/apache/iotdb/db/metadata/visitor/SchemaExecutionVisitor.java
index be37ccf002..d44af00add 100644
--- a/server/src/main/java/org/apache/iotdb/db/metadata/visitor/SchemaExecutionVisitor.java
+++ b/server/src/main/java/org/apache/iotdb/db/metadata/visitor/SchemaExecutionVisitor.java
@@ -32,11 +32,14 @@ import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanVisitor;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ActivateTemplateNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.AlterTimeSeriesNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ConstructSchemaBlackListNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateAlignedTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateMultiTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateTimeSeriesNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.DeleteTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.InternalCreateTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.MeasurementGroup;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.RollbackSchemaBlackListNode;
import org.apache.iotdb.db.qp.physical.PhysicalPlan;
import org.apache.iotdb.db.qp.physical.sys.ActivateTemplateInClusterPlan;
import org.apache.iotdb.db.qp.physical.sys.CreateAlignedTimeSeriesPlan;
@@ -303,6 +306,41 @@ public class SchemaExecutionVisitor extends PlanVisitor<TSStatus, ISchemaRegion>
}
}
+ @Override
+ public TSStatus visitConstructSchemaBlackList(
+ ConstructSchemaBlackListNode node, ISchemaRegion schemaRegion) {
+ try {
+ int preDeletedNum = schemaRegion.constructSchemaBlackList(node.getPatternTree());
+ return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS, String.valueOf(preDeletedNum));
+ } catch (MetadataException e) {
+ logger.error(e.getMessage(), e);
+ return RpcUtils.getStatus(e.getErrorCode(), e.getMessage());
+ }
+ }
+
+ @Override
+ public TSStatus visitRollbackSchemaBlackList(
+ RollbackSchemaBlackListNode node, ISchemaRegion schemaRegion) {
+ try {
+ schemaRegion.rollbackSchemaBlackList(node.getPatternTree());
+ return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS);
+ } catch (MetadataException e) {
+ logger.error(e.getMessage(), e);
+ return RpcUtils.getStatus(e.getErrorCode(), e.getMessage());
+ }
+ }
+
+ @Override
+ public TSStatus visitDeleteTimeseries(DeleteTimeSeriesNode node, ISchemaRegion schemaRegion) {
+ try {
+ schemaRegion.deleteTimeseriesInBlackList(node.getPatternTree());
+ return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS);
+ } catch (MetadataException e) {
+ logger.error(e.getMessage(), e);
+ return RpcUtils.getStatus(e.getErrorCode(), e.getMessage());
+ }
+ }
+
@Override
public TSStatus visitPlan(PlanNode node, ISchemaRegion context) {
return null;
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/common/schematree/PathPatternTree.java b/server/src/main/java/org/apache/iotdb/db/mpp/common/schematree/PathPatternTree.java
index df8b8f3b35..970e8715cc 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/common/schematree/PathPatternTree.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/common/schematree/PathPatternTree.java
@@ -218,6 +218,16 @@ public class PathPatternTree {
return new PartialPath(nodeList.toArray(new String[0]));
}
+ public boolean isOverlapWith(PathPatternTree patternTree) {
+ // todo improve this implementation
+ for (PartialPath pathPattern : getAllPathPatterns()) {
+ if (!patternTree.getOverlappedPathPatterns(pathPattern).isEmpty()) {
+ return true;
+ }
+ }
+ return false;
+ }
+
/////////////////////////////////////////////////////////////////////////////////////////////////
// serialize & deserialize
/////////////////////////////////////////////////////////////////////////////////////////////////
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/analyze/ClusterSchemaFetcher.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/analyze/ClusterSchemaFetcher.java
index c3dbb79aea..49daadf555 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/analyze/ClusterSchemaFetcher.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/analyze/ClusterSchemaFetcher.java
@@ -176,42 +176,47 @@ public class ClusterSchemaFetcher implements ISchemaFetcher {
String[] measurements,
Function<Integer, TSDataType> getDataType,
boolean isAligned) {
- ClusterSchemaTree schemaTree = schemaCache.get(devicePath, measurements);
- List<Integer> indexOfMissingMeasurements =
- checkMissingMeasurements(schemaTree, devicePath, measurements);
+ schemaCache.takeReadLock();
+ try {
+ ClusterSchemaTree schemaTree = schemaCache.get(devicePath, measurements);
+ List<Integer> indexOfMissingMeasurements =
+ checkMissingMeasurements(schemaTree, devicePath, measurements);
- if (indexOfMissingMeasurements.isEmpty()) {
- return schemaTree;
- }
+ if (indexOfMissingMeasurements.isEmpty()) {
+ return schemaTree;
+ }
- PathPatternTree patternTree = new PathPatternTree();
- for (int index : indexOfMissingMeasurements) {
- patternTree.appendFullPath(devicePath, measurements[index]);
- }
+ PathPatternTree patternTree = new PathPatternTree();
+ for (int index : indexOfMissingMeasurements) {
+ patternTree.appendFullPath(devicePath, measurements[index]);
+ }
- ClusterSchemaTree remoteSchemaTree = fetchSchema(patternTree);
- if (!remoteSchemaTree.isEmpty()) {
- schemaTree.mergeSchemaTree(remoteSchemaTree);
- schemaCache.put(remoteSchemaTree);
- }
+ ClusterSchemaTree remoteSchemaTree = fetchSchema(patternTree);
+ if (!remoteSchemaTree.isEmpty()) {
+ schemaTree.mergeSchemaTree(remoteSchemaTree);
+ schemaCache.put(remoteSchemaTree);
+ }
- if (!config.isAutoCreateSchemaEnabled()) {
- return schemaTree;
- }
+ if (!config.isAutoCreateSchemaEnabled()) {
+ return schemaTree;
+ }
- ClusterSchemaTree missingSchemaTree =
- checkAndAutoCreateMissingMeasurements(
- remoteSchemaTree,
- devicePath,
- indexOfMissingMeasurements,
- measurements,
- getDataType,
- isAligned);
+ ClusterSchemaTree missingSchemaTree =
+ checkAndAutoCreateMissingMeasurements(
+ remoteSchemaTree,
+ devicePath,
+ indexOfMissingMeasurements,
+ measurements,
+ getDataType,
+ isAligned);
- schemaTree.mergeSchemaTree(missingSchemaTree);
- schemaCache.put(missingSchemaTree);
+ schemaTree.mergeSchemaTree(missingSchemaTree);
+ schemaCache.put(missingSchemaTree);
- return schemaTree;
+ return schemaTree;
+ } finally {
+ schemaCache.releaseReadLock();
+ }
}
@Override
@@ -220,49 +225,53 @@ public class ClusterSchemaFetcher implements ISchemaFetcher {
List<String[]> measurementsList,
List<TSDataType[]> tsDataTypesList,
List<Boolean> isAlignedList) {
+ schemaCache.takeReadLock();
+ try {
+ ClusterSchemaTree schemaTree = new ClusterSchemaTree();
+ PathPatternTree patternTree = new PathPatternTree();
+ List<List<Integer>> indexOfMissingMeasurementsList = new ArrayList<>(devicePathList.size());
+ for (int i = 0; i < devicePathList.size(); i++) {
+ schemaTree.mergeSchemaTree(schemaCache.get(devicePathList.get(i), measurementsList.get(i)));
+ List<Integer> indexOfMissingMeasurements =
+ checkMissingMeasurements(schemaTree, devicePathList.get(i), measurementsList.get(i));
+ indexOfMissingMeasurementsList.add(indexOfMissingMeasurements);
+ for (int index : indexOfMissingMeasurements) {
+ patternTree.appendFullPath(devicePathList.get(i), measurementsList.get(i)[index]);
+ }
+ }
- ClusterSchemaTree schemaTree = new ClusterSchemaTree();
- PathPatternTree patternTree = new PathPatternTree();
- List<List<Integer>> indexOfMissingMeasurementsList = new ArrayList<>(devicePathList.size());
- for (int i = 0; i < devicePathList.size(); i++) {
- schemaTree.mergeSchemaTree(schemaCache.get(devicePathList.get(i), measurementsList.get(i)));
- List<Integer> indexOfMissingMeasurements =
- checkMissingMeasurements(schemaTree, devicePathList.get(i), measurementsList.get(i));
- indexOfMissingMeasurementsList.add(indexOfMissingMeasurements);
- for (int index : indexOfMissingMeasurements) {
- patternTree.appendFullPath(devicePathList.get(i), measurementsList.get(i)[index]);
+ if (patternTree.isEmpty()) {
+ return schemaTree;
}
- }
- if (patternTree.isEmpty()) {
- return schemaTree;
- }
+ ClusterSchemaTree remoteSchemaTree = fetchSchema(patternTree);
+ if (!remoteSchemaTree.isEmpty()) {
+ schemaTree.mergeSchemaTree(remoteSchemaTree);
+ schemaCache.put(remoteSchemaTree);
+ }
- ClusterSchemaTree remoteSchemaTree = fetchSchema(patternTree);
- if (!remoteSchemaTree.isEmpty()) {
- schemaTree.mergeSchemaTree(remoteSchemaTree);
- schemaCache.put(remoteSchemaTree);
- }
+ if (!config.isAutoCreateSchemaEnabled()) {
+ return schemaTree;
+ }
- if (!config.isAutoCreateSchemaEnabled()) {
+ ClusterSchemaTree missingSchemaTree;
+ for (int i = 0; i < devicePathList.size(); i++) {
+ int finalI = i;
+ missingSchemaTree =
+ checkAndAutoCreateMissingMeasurements(
+ schemaTree,
+ devicePathList.get(i),
+ indexOfMissingMeasurementsList.get(i),
+ measurementsList.get(i),
+ index -> tsDataTypesList.get(finalI)[index],
+ isAlignedList.get(i));
+ schemaTree.mergeSchemaTree(missingSchemaTree);
+ schemaCache.put(missingSchemaTree);
+ }
return schemaTree;
+ } finally {
+ schemaCache.releaseReadLock();
}
-
- ClusterSchemaTree missingSchemaTree;
- for (int i = 0; i < devicePathList.size(); i++) {
- int finalI = i;
- missingSchemaTree =
- checkAndAutoCreateMissingMeasurements(
- schemaTree,
- devicePathList.get(i),
- indexOfMissingMeasurementsList.get(i),
- measurementsList.get(i),
- index -> tsDataTypesList.get(finalI)[index],
- isAlignedList.get(i));
- schemaTree.mergeSchemaTree(missingSchemaTree);
- schemaCache.put(missingSchemaTree);
- }
- return schemaTree;
}
@Override
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigExecution.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigExecution.java
index 91260063a5..be8a4491f1 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigExecution.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigExecution.java
@@ -68,7 +68,10 @@ public class ConfigExecution implements IQueryExecution {
this.executor = executor;
this.stateMachine = new QueryStateMachine(context.getQueryId(), executor);
this.taskFuture = SettableFuture.create();
- this.task = statement.accept(new ConfigTaskVisitor(), new ConfigTaskVisitor.TaskContext());
+ this.task =
+ statement.accept(
+ new ConfigTaskVisitor(),
+ new ConfigTaskVisitor.TaskContext(context.getQueryId().getId()));
this.resultSetConsumed = false;
if (config.isClusterMode()) {
configTaskExecutor = ClusterConfigTaskExecutor.getInstance();
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigTaskVisitor.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigTaskVisitor.java
index 931ea8a0d6..aee5e3fff9 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigTaskVisitor.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/ConfigTaskVisitor.java
@@ -23,6 +23,7 @@ import org.apache.iotdb.db.mpp.plan.execution.config.metadata.CountStorageGroupT
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.CreateFunctionTask;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.CreateTriggerTask;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.DeleteStorageGroupTask;
+import org.apache.iotdb.db.mpp.plan.execution.config.metadata.DeleteTimeSeriesTask;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.DropFunctionTask;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.DropTriggerTask;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.SetStorageGroupTask;
@@ -61,6 +62,7 @@ import org.apache.iotdb.db.mpp.plan.statement.metadata.CountStorageGroupStatemen
import org.apache.iotdb.db.mpp.plan.statement.metadata.CreateFunctionStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.CreateTriggerStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteStorageGroupStatement;
+import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteTimeSeriesStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.DropFunctionStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.DropTriggerStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetStorageGroupStatement;
@@ -302,5 +304,22 @@ public class ConfigTaskVisitor
return new StopPipeTask(stopPipeStatement);
}
- public static class TaskContext {}
+ @Override
+ public IConfigTask visitDeleteTimeseries(
+ DeleteTimeSeriesStatement deleteTimeSeriesStatement, TaskContext context) {
+ return new DeleteTimeSeriesTask(context.getQueryId(), deleteTimeSeriesStatement);
+ }
+
+ public static class TaskContext {
+
+ private final String queryId;
+
+ public TaskContext(String queryId) {
+ this.queryId = queryId;
+ }
+
+ public String getQueryId() {
+ return queryId;
+ }
+ }
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/ClusterConfigTaskExecutor.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/ClusterConfigTaskExecutor.java
index cc1ee8e967..d4bd990140 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/ClusterConfigTaskExecutor.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/ClusterConfigTaskExecutor.java
@@ -32,6 +32,7 @@ import org.apache.iotdb.confignode.rpc.thrift.TCountStorageGroupResp;
import org.apache.iotdb.confignode.rpc.thrift.TCreateFunctionReq;
import org.apache.iotdb.confignode.rpc.thrift.TCreateTriggerReq;
import org.apache.iotdb.confignode.rpc.thrift.TDeleteStorageGroupsReq;
+import org.apache.iotdb.confignode.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.confignode.rpc.thrift.TDropFunctionReq;
import org.apache.iotdb.confignode.rpc.thrift.TDropTriggerReq;
import org.apache.iotdb.confignode.rpc.thrift.TGetTemplateResp;
@@ -50,6 +51,7 @@ import org.apache.iotdb.db.client.DataNodeClientPoolFactory;
import org.apache.iotdb.db.localconfignode.LocalConfigNode;
import org.apache.iotdb.db.metadata.template.ClusterTemplateManager;
import org.apache.iotdb.db.metadata.template.Template;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.mpp.plan.execution.config.ConfigTaskResult;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.CountStorageGroupTask;
import org.apache.iotdb.db.mpp.plan.execution.config.metadata.SetStorageGroupTask;
@@ -65,6 +67,7 @@ import org.apache.iotdb.db.mpp.plan.execution.config.metadata.template.ShowSchem
import org.apache.iotdb.db.mpp.plan.statement.metadata.CountStorageGroupStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.CreateTriggerStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteStorageGroupStatement;
+import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteTimeSeriesStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetStorageGroupStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetTTLStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.ShowDataNodesStatement;
@@ -84,15 +87,21 @@ import org.apache.iotdb.db.mpp.plan.statement.sys.sync.ShowPipeSinkStatement;
import org.apache.iotdb.db.mpp.plan.statement.sys.sync.ShowPipeStatement;
import org.apache.iotdb.db.mpp.plan.statement.sys.sync.StartPipeStatement;
import org.apache.iotdb.db.mpp.plan.statement.sys.sync.StopPipeStatement;
+import org.apache.iotdb.rpc.RpcUtils;
import org.apache.iotdb.rpc.StatementExecutionException;
import org.apache.iotdb.rpc.TSStatusCode;
import com.google.common.util.concurrent.SettableFuture;
import org.apache.thrift.TException;
+import org.apache.thrift.transport.TTransportException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
import java.io.IOException;
+import java.net.SocketTimeoutException;
+import java.nio.ByteBuffer;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
@@ -108,6 +117,12 @@ public class ClusterConfigTaskExecutor implements IConfigTaskExecutor {
new IClientManager.Factory<PartitionRegionId, ConfigNodeClient>()
.createClientManager(new DataNodeClientPoolFactory.ConfigNodeClientPoolFactory());
+ private static final IClientManager<PartitionRegionId, ConfigNodeClient>
+ CLUSTER_DELETION_CONFIG_NODE_CLIENT_MANAGER =
+ new IClientManager.Factory<PartitionRegionId, ConfigNodeClient>()
+ .createClientManager(
+ new DataNodeClientPoolFactory.ClusterDeletionConfigNodeClientPoolFactory());
+
private static final class ClusterConfigTaskExecutorHolder {
private static final ClusterConfigTaskExecutor INSTANCE = new ClusterConfigTaskExecutor();
@@ -758,4 +773,56 @@ public class ClusterConfigTaskExecutor implements IConfigTaskExecutor {
TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode()));
return future;
}
+
+ @Override
+ public SettableFuture<ConfigTaskResult> deleteTimeSeries(
+ String queryId, DeleteTimeSeriesStatement deleteTimeSeriesStatement) {
+ SettableFuture<ConfigTaskResult> future = SettableFuture.create();
+ PathPatternTree patternTree = new PathPatternTree();
+ for (PartialPath pathPattern : deleteTimeSeriesStatement.getPathPatternList()) {
+ patternTree.appendPathPattern(pathPattern);
+ }
+ patternTree.constructTree();
+ ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
+ DataOutputStream dataOutputStream = new DataOutputStream(byteArrayOutputStream);
+ try {
+ patternTree.serialize(dataOutputStream);
+ } catch (IOException ignored) {
+ // memory operation, won't happen
+ }
+ TDeleteTimeSeriesReq req =
+ new TDeleteTimeSeriesReq(queryId, ByteBuffer.wrap(byteArrayOutputStream.toByteArray()));
+ try (ConfigNodeClient client =
+ CLUSTER_DELETION_CONFIG_NODE_CLIENT_MANAGER.borrowClient(
+ ConfigNodeInfo.partitionRegionId)) {
+ TSStatus tsStatus = null;
+ do {
+ try {
+ tsStatus = client.deleteTimeSeries(req);
+ } catch (TTransportException e) {
+ if (e.getType() == TTransportException.TIMED_OUT
+ || e.getCause() instanceof SocketTimeoutException) {
+ // time out mainly caused by slow execution, wait until
+ tsStatus = RpcUtils.getStatus(TSStatusCode.STILL_EXECUTING_STATUS);
+ } else {
+ throw e;
+ }
+ }
+ // keep waiting until task ends
+ } while (TSStatusCode.STILL_EXECUTING_STATUS.getStatusCode() == tsStatus.getCode());
+
+ if (TSStatusCode.SUCCESS_STATUS.getStatusCode() != tsStatus.getCode()) {
+ LOGGER.error(
+ "Failed to execute delete timeseries {} in config node, status is {}.",
+ deleteTimeSeriesStatement.getPathPatternList(),
+ tsStatus);
+ future.setException(new IoTDBException(tsStatus.getMessage(), tsStatus.getCode()));
+ } else {
+ future.set(new ConfigTaskResult(TSStatusCode.SUCCESS_STATUS));
+ }
+ } catch (TException | IOException e) {
+ future.setException(e);
+ }
+ return future;
+ }
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/IConfigTaskExecutor.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/IConfigTaskExecutor.java
index 90750c2526..d6b69f7a5d 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/IConfigTaskExecutor.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/IConfigTaskExecutor.java
@@ -25,6 +25,7 @@ import org.apache.iotdb.db.mpp.plan.execution.config.ConfigTaskResult;
import org.apache.iotdb.db.mpp.plan.statement.metadata.CountStorageGroupStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.CreateTriggerStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteStorageGroupStatement;
+import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteTimeSeriesStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetStorageGroupStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetTTLStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.ShowDataNodesStatement;
@@ -124,4 +125,7 @@ public interface IConfigTaskExecutor {
SettableFuture<ConfigTaskResult> stopPipe(StopPipeStatement stopPipeStatement);
SettableFuture<ConfigTaskResult> showPipe(ShowPipeStatement showPipeStatement);
+
+ SettableFuture<ConfigTaskResult> deleteTimeSeries(
+ String queryId, DeleteTimeSeriesStatement deleteTimeSeriesStatement);
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/StandaloneConfigTaskExecutor.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/StandaloneConfigTaskExecutor.java
index acb6bda290..aca6198bd1 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/StandaloneConfigTaskExecutor.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/executor/StandaloneConfigTaskExecutor.java
@@ -41,6 +41,7 @@ import org.apache.iotdb.db.mpp.plan.execution.config.sys.sync.ShowPipeTask;
import org.apache.iotdb.db.mpp.plan.statement.metadata.CountStorageGroupStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.CreateTriggerStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteStorageGroupStatement;
+import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteTimeSeriesStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetStorageGroupStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.SetTTLStatement;
import org.apache.iotdb.db.mpp.plan.statement.metadata.ShowDataNodesStatement;
@@ -561,4 +562,15 @@ public class StandaloneConfigTaskExecutor implements IConfigTaskExecutor {
ShowPipeTask.buildTSBlock(showPipeResp.getPipeInfoList(), future);
return future;
}
+
+ @Override
+ public SettableFuture<ConfigTaskResult> deleteTimeSeries(
+ String queryId, DeleteTimeSeriesStatement deleteTimeSeriesStatement) {
+ SettableFuture<ConfigTaskResult> future = SettableFuture.create();
+ future.setException(
+ new IoTDBException(
+ "Executing delete timeseries is not supported",
+ TSStatusCode.EXECUTE_STATEMENT_ERROR.getStatusCode()));
+ return future;
+ }
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/metadata/DeleteTimeSeriesTask.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/metadata/DeleteTimeSeriesTask.java
new file mode 100644
index 0000000000..530c1eb508
--- /dev/null
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/execution/config/metadata/DeleteTimeSeriesTask.java
@@ -0,0 +1,45 @@
+/*
+ * 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.mpp.plan.execution.config.metadata;
+
+import org.apache.iotdb.db.mpp.plan.execution.config.ConfigTaskResult;
+import org.apache.iotdb.db.mpp.plan.execution.config.IConfigTask;
+import org.apache.iotdb.db.mpp.plan.execution.config.executor.IConfigTaskExecutor;
+import org.apache.iotdb.db.mpp.plan.statement.metadata.DeleteTimeSeriesStatement;
+
+import com.google.common.util.concurrent.ListenableFuture;
+
+public class DeleteTimeSeriesTask implements IConfigTask {
+
+ private final String queryId;
+
+ private final DeleteTimeSeriesStatement deleteTimeSeriesStatement;
+
+ public DeleteTimeSeriesTask(String queryId, DeleteTimeSeriesStatement deleteTimeSeriesStatement) {
+ this.queryId = queryId;
+ this.deleteTimeSeriesStatement = deleteTimeSeriesStatement;
+ }
+
+ @Override
+ public ListenableFuture<ConfigTaskResult> execute(IConfigTaskExecutor configTaskExecutor)
+ throws InterruptedException {
+ return configTaskExecutor.deleteTimeSeries(queryId, deleteTimeSeriesStatement);
+ }
+}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/parser/ASTVisitor.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/parser/ASTVisitor.java
index c766671e84..f6f5be5ee1 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/parser/ASTVisitor.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/parser/ASTVisitor.java
@@ -528,7 +528,7 @@ public class ASTVisitor extends IoTDBSqlParserBaseVisitor<Statement> {
for (IoTDBSqlParser.PrefixPathContext prefixPathContext : ctx.prefixPath()) {
partialPaths.add(parsePrefixPath(prefixPathContext));
}
- deleteTimeSeriesStatement.setPartialPaths(partialPaths);
+ deleteTimeSeriesStatement.setPathPatternList(partialPaths);
return deleteTimeSeriesStatement;
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanNodeType.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanNodeType.java
index d7f4c3cfb9..caa84ee5da 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanNodeType.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanNodeType.java
@@ -35,12 +35,14 @@ import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.read.TimeSeriesCo
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.read.TimeSeriesSchemaScanNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ActivateTemplateNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.AlterTimeSeriesNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ConstructSchemaBlackListNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateAlignedTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateMultiTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.DeleteTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.InternalCreateTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.InvalidateSchemaCacheNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.RollbackSchemaBlackListNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.process.AggregationNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.process.DeviceMergeNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.process.DeviceViewNode;
@@ -132,7 +134,9 @@ public enum PlanNodeType {
NODE_PATHS_COUNT((short) 51),
INTERNAL_CREATE_TIMESERIES((short) 52),
ACTIVATE_TEMPLATE((short) 53),
- PATHS_USING_TEMPLATE_SCAN((short) 54);
+ PATHS_USING_TEMPLATE_SCAN((short) 54),
+ CONSTRUCT_SCHEMA_BLACK_LIST_NODE((short) 55),
+ ROLLBACK_SCHEMA_BLACK_LIST_NODE((short) 56);
public static final int BYTES = Short.BYTES;
@@ -291,6 +295,10 @@ public enum PlanNodeType {
return ActivateTemplateNode.deserialize(buffer);
case 54:
return PathsUsingTemplateScanNode.deserialize(buffer);
+ case 55:
+ return ConstructSchemaBlackListNode.deserialize(buffer);
+ case 56:
+ return RollbackSchemaBlackListNode.deserialize(buffer);
default:
throw new IllegalArgumentException("Invalid node type: " + nodeType);
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanVisitor.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanVisitor.java
index 83fc883018..a8cea87284 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanVisitor.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/PlanVisitor.java
@@ -35,11 +35,13 @@ import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.read.TimeSeriesCo
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.read.TimeSeriesSchemaScanNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ActivateTemplateNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.AlterTimeSeriesNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ConstructSchemaBlackListNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateAlignedTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateMultiTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.CreateTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.DeleteTimeSeriesNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.InternalCreateTimeSeriesNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.RollbackSchemaBlackListNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.process.AggregationNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.process.DeviceMergeNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.process.DeviceViewNode;
@@ -275,6 +277,14 @@ public abstract class PlanVisitor<R, C> {
return visitPlan(node, context);
}
+ public R visitConstructSchemaBlackList(ConstructSchemaBlackListNode node, C context) {
+ return visitPlan(node, context);
+ }
+
+ public R visitRollbackSchemaBlackList(RollbackSchemaBlackListNode node, C context) {
+ return visitPlan(node, context);
+ }
+
public R visitDeleteData(DeleteDataNode node, C context) {
return visitPlan(node, context);
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/ConstructSchemaBlackListNode.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/ConstructSchemaBlackListNode.java
new file mode 100644
index 0000000000..4d71b22096
--- /dev/null
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/ConstructSchemaBlackListNode.java
@@ -0,0 +1,91 @@
+/*
+ * 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.mpp.plan.planner.plan.node.metedata.write;
+
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeId;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeType;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanVisitor;
+
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.List;
+
+public class ConstructSchemaBlackListNode extends PlanNode {
+
+ private final PathPatternTree patternTree;
+
+ public ConstructSchemaBlackListNode(PlanNodeId id, PathPatternTree patternTree) {
+ super(id);
+ this.patternTree = patternTree;
+ }
+
+ public PathPatternTree getPatternTree() {
+ return patternTree;
+ }
+
+ @Override
+ public List<PlanNode> getChildren() {
+ return null;
+ }
+
+ @Override
+ public void addChild(PlanNode child) {}
+
+ @Override
+ public PlanNode clone() {
+ return new ConstructSchemaBlackListNode(getPlanNodeId(), patternTree);
+ }
+
+ @Override
+ public int allowedChildCount() {
+ return 0;
+ }
+
+ @Override
+ public List<String> getOutputColumnNames() {
+ return null;
+ }
+
+ @Override
+ public <R, C> R accept(PlanVisitor<R, C> visitor, C context) {
+ return visitor.visitConstructSchemaBlackList(this, context);
+ }
+
+ @Override
+ protected void serializeAttributes(ByteBuffer byteBuffer) {
+ PlanNodeType.CONSTRUCT_SCHEMA_BLACK_LIST_NODE.serialize(byteBuffer);
+ patternTree.serialize(byteBuffer);
+ }
+
+ @Override
+ protected void serializeAttributes(DataOutputStream stream) throws IOException {
+ PlanNodeType.CONSTRUCT_SCHEMA_BLACK_LIST_NODE.serialize(stream);
+ patternTree.serialize(stream);
+ }
+
+ public static ConstructSchemaBlackListNode deserialize(ByteBuffer buffer) {
+ PathPatternTree patternTree = PathPatternTree.deserialize(buffer);
+ PlanNodeId planNodeId = PlanNodeId.deserialize(buffer);
+ return new ConstructSchemaBlackListNode(planNodeId, patternTree);
+ }
+}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/DeleteTimeSeriesNode.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/DeleteTimeSeriesNode.java
index a1bf8ac56a..9e70f6100a 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/DeleteTimeSeriesNode.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/DeleteTimeSeriesNode.java
@@ -19,52 +19,41 @@
package org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write;
-import org.apache.iotdb.common.rpc.thrift.TRegionReplicaSet;
-import org.apache.iotdb.commons.path.PartialPath;
-import org.apache.iotdb.db.metadata.path.PathDeserializeUtil;
-import org.apache.iotdb.db.mpp.plan.planner.plan.node.IPartitionRelatedNode;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeId;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeType;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanVisitor;
-import org.apache.iotdb.tsfile.utils.ReadWriteIOUtils;
import java.io.DataOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
-import java.util.ArrayList;
import java.util.List;
-public class DeleteTimeSeriesNode extends PlanNode implements IPartitionRelatedNode {
+public class DeleteTimeSeriesNode extends PlanNode {
- private final List<PartialPath> pathList;
+ private final PathPatternTree patternTree;
- private TRegionReplicaSet regionReplicaSet;
- private List<PlanNode> children;
-
- public DeleteTimeSeriesNode(PlanNodeId id, List<PartialPath> pathList) {
+ public DeleteTimeSeriesNode(PlanNodeId id, PathPatternTree patternTree) {
super(id);
- this.pathList = pathList;
- this.children = new ArrayList<>();
+ this.patternTree = patternTree;
}
- public List<PartialPath> getPathList() {
- return pathList;
+ public PathPatternTree getPatternTree() {
+ return patternTree;
}
@Override
public List<PlanNode> getChildren() {
- return children;
+ return null;
}
@Override
- public void addChild(PlanNode child) {
- children.add(child);
- }
+ public void addChild(PlanNode child) {}
@Override
public PlanNode clone() {
- return new DeleteTimeSeriesNode(getPlanNodeId(), pathList);
+ return new DeleteTimeSeriesNode(getPlanNodeId(), patternTree);
}
@Override
@@ -85,45 +74,23 @@ public class DeleteTimeSeriesNode extends PlanNode implements IPartitionRelatedN
@Override
protected void serializeAttributes(ByteBuffer byteBuffer) {
PlanNodeType.DELETE_TIMESERIES.serialize(byteBuffer);
- ReadWriteIOUtils.write(pathList.size(), byteBuffer);
- for (PartialPath path : pathList) {
- path.serialize(byteBuffer);
- }
+ patternTree.serialize(byteBuffer);
}
@Override
protected void serializeAttributes(DataOutputStream stream) throws IOException {
PlanNodeType.DELETE_TIMESERIES.serialize(stream);
- ReadWriteIOUtils.write(pathList.size(), stream);
- for (PartialPath path : pathList) {
- path.serialize(stream);
- }
+ patternTree.serialize(stream);
}
public static DeleteTimeSeriesNode deserialize(ByteBuffer byteBuffer) {
- int size = ReadWriteIOUtils.readInt(byteBuffer);
- List<PartialPath> pathList = new ArrayList<>(size);
- for (int i = 0; i < size; i++) {
- pathList.add((PartialPath) PathDeserializeUtil.deserialize(byteBuffer));
- }
+ PathPatternTree patternTree = PathPatternTree.deserialize(byteBuffer);
PlanNodeId planNodeId = PlanNodeId.deserialize(byteBuffer);
- return new DeleteTimeSeriesNode(planNodeId, pathList);
- }
-
- @Override
- public TRegionReplicaSet getRegionReplicaSet() {
- return regionReplicaSet;
- }
-
- public void setRegionReplicaSet(TRegionReplicaSet regionReplicaSet) {
- this.regionReplicaSet = regionReplicaSet;
+ return new DeleteTimeSeriesNode(planNodeId, patternTree);
}
public String toString() {
return String.format(
- "DeleteTimeseriesNode-%s: %s. Region: %s",
- getPlanNodeId(),
- pathList,
- regionReplicaSet == null ? "Not Assigned" : regionReplicaSet.getRegionId());
+ "DeleteTimeseriesNode-%s: %s. Region: %s", getPlanNodeId(), patternTree, "Not Assigned");
}
}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/RollbackSchemaBlackListNode.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/RollbackSchemaBlackListNode.java
new file mode 100644
index 0000000000..f79b814bff
--- /dev/null
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/planner/plan/node/metedata/write/RollbackSchemaBlackListNode.java
@@ -0,0 +1,91 @@
+/*
+ * 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.mpp.plan.planner.plan.node.metedata.write;
+
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeId;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeType;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanVisitor;
+
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.List;
+
+public class RollbackSchemaBlackListNode extends PlanNode {
+
+ private final PathPatternTree patternTree;
+
+ public RollbackSchemaBlackListNode(PlanNodeId id, PathPatternTree patternTree) {
+ super(id);
+ this.patternTree = patternTree;
+ }
+
+ public PathPatternTree getPatternTree() {
+ return patternTree;
+ }
+
+ @Override
+ public List<PlanNode> getChildren() {
+ return null;
+ }
+
+ @Override
+ public void addChild(PlanNode child) {}
+
+ @Override
+ public PlanNode clone() {
+ return new RollbackSchemaBlackListNode(getPlanNodeId(), patternTree);
+ }
+
+ @Override
+ public int allowedChildCount() {
+ return 0;
+ }
+
+ @Override
+ public List<String> getOutputColumnNames() {
+ return null;
+ }
+
+ @Override
+ public <R, C> R accept(PlanVisitor<R, C> visitor, C context) {
+ return visitor.visitRollbackSchemaBlackList(this, context);
+ }
+
+ @Override
+ protected void serializeAttributes(ByteBuffer byteBuffer) {
+ PlanNodeType.ROLLBACK_SCHEMA_BLACK_LIST_NODE.serialize(byteBuffer);
+ patternTree.serialize(byteBuffer);
+ }
+
+ @Override
+ protected void serializeAttributes(DataOutputStream stream) throws IOException {
+ PlanNodeType.ROLLBACK_SCHEMA_BLACK_LIST_NODE.serialize(stream);
+ patternTree.serialize(stream);
+ }
+
+ public static RollbackSchemaBlackListNode deserialize(ByteBuffer buffer) {
+ PathPatternTree patternTree = PathPatternTree.deserialize(buffer);
+ PlanNodeId planNodeId = PlanNodeId.deserialize(buffer);
+ return new RollbackSchemaBlackListNode(planNodeId, patternTree);
+ }
+}
diff --git a/server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java b/server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java
index 99cb5b57ff..ffc653f597 100644
--- a/server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java
+++ b/server/src/main/java/org/apache/iotdb/db/mpp/plan/statement/metadata/DeleteTimeSeriesStatement.java
@@ -20,26 +20,43 @@
package org.apache.iotdb.db.mpp.plan.statement.metadata;
import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.db.mpp.plan.analyze.QueryType;
+import org.apache.iotdb.db.mpp.plan.constant.StatementType;
+import org.apache.iotdb.db.mpp.plan.statement.IConfigStatement;
import org.apache.iotdb.db.mpp.plan.statement.Statement;
import org.apache.iotdb.db.mpp.plan.statement.StatementVisitor;
import java.util.List;
-public class DeleteTimeSeriesStatement extends Statement {
+public class DeleteTimeSeriesStatement extends Statement implements IConfigStatement {
- List<PartialPath> partialPaths;
+ List<PartialPath> pathPatternList;
+
+ public DeleteTimeSeriesStatement() {
+ super();
+ statementType = StatementType.DELETE_TIMESERIES;
+ }
@Override
public List<PartialPath> getPaths() {
- return partialPaths;
+ return pathPatternList;
+ }
+
+ public List<PartialPath> getPathPatternList() {
+ return pathPatternList;
}
- public void setPartialPaths(List<PartialPath> partialPaths) {
- this.partialPaths = partialPaths;
+ public void setPathPatternList(List<PartialPath> pathPatternList) {
+ this.pathPatternList = pathPatternList;
}
@Override
public <R, C> R accept(StatementVisitor<R, C> visitor, C context) {
return visitor.visitDeleteTimeseries(this, context);
}
+
+ @Override
+ public QueryType getQueryType() {
+ return QueryType.WRITE;
+ }
}
diff --git a/server/src/main/java/org/apache/iotdb/db/qp/logical/Operator.java b/server/src/main/java/org/apache/iotdb/db/qp/logical/Operator.java
index 48fad9c0a0..32292b5b0d 100644
--- a/server/src/main/java/org/apache/iotdb/db/qp/logical/Operator.java
+++ b/server/src/main/java/org/apache/iotdb/db/qp/logical/Operator.java
@@ -206,6 +206,8 @@ public abstract class Operator {
START_PIPE,
DROP_PIPE,
- ACTIVATE_TEMPLATE_IN_CLUSTER
+ ACTIVATE_TEMPLATE_IN_CLUSTER,
+ PRE_DELETE_TIMESERIES_IN_CLUSTER,
+ ROLLBACK_PRE_DELETE_TIMESERIES
}
}
diff --git a/server/src/main/java/org/apache/iotdb/db/qp/physical/PhysicalPlan.java b/server/src/main/java/org/apache/iotdb/db/qp/physical/PhysicalPlan.java
index e49be4304e..070b198c35 100644
--- a/server/src/main/java/org/apache/iotdb/db/qp/physical/PhysicalPlan.java
+++ b/server/src/main/java/org/apache/iotdb/db/qp/physical/PhysicalPlan.java
@@ -63,7 +63,9 @@ import org.apache.iotdb.db.qp.physical.sys.LogPlan;
import org.apache.iotdb.db.qp.physical.sys.MNodePlan;
import org.apache.iotdb.db.qp.physical.sys.MeasurementMNodePlan;
import org.apache.iotdb.db.qp.physical.sys.MergePlan;
+import org.apache.iotdb.db.qp.physical.sys.PreDeleteTimeSeriesPlan;
import org.apache.iotdb.db.qp.physical.sys.PruneTemplatePlan;
+import org.apache.iotdb.db.qp.physical.sys.RollbackPreDeleteTimeSeriesPlan;
import org.apache.iotdb.db.qp.physical.sys.SetStorageGroupPlan;
import org.apache.iotdb.db.qp.physical.sys.SetSystemModePlan;
import org.apache.iotdb.db.qp.physical.sys.SetTTLPlan;
@@ -491,6 +493,12 @@ public abstract class PhysicalPlan implements IConsensusRequest {
case ACTIVATE_TEMPLATE_IN_CLUSTER:
plan = new ActivateTemplateInClusterPlan();
break;
+ case PRE_DELETE_TIMESERIES_IN_CLUSTER:
+ plan = new PreDeleteTimeSeriesPlan();
+ break;
+ case ROLLBACK_PRE_DELETE_TIMESERIES:
+ plan = new RollbackPreDeleteTimeSeriesPlan();
+ break;
default:
throw new IOException("unrecognized log type " + type);
}
@@ -563,7 +571,9 @@ public abstract class PhysicalPlan implements IConsensusRequest {
START_PIPE_SERVER,
STOP_PIPE_SERVER,
DROP_TEMPLATE,
- ACTIVATE_TEMPLATE_IN_CLUSTER
+ ACTIVATE_TEMPLATE_IN_CLUSTER,
+ PRE_DELETE_TIMESERIES_IN_CLUSTER,
+ ROLLBACK_PRE_DELETE_TIMESERIES
}
public long getIndex() {
diff --git a/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/PreDeleteTimeSeriesPlan.java b/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/PreDeleteTimeSeriesPlan.java
new file mode 100644
index 0000000000..2c3e51952f
--- /dev/null
+++ b/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/PreDeleteTimeSeriesPlan.java
@@ -0,0 +1,79 @@
+/*
+ * 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.qp.physical.sys;
+
+import org.apache.iotdb.commons.exception.IllegalPathException;
+import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.db.metadata.path.PathDeserializeUtil;
+import org.apache.iotdb.db.qp.logical.Operator;
+import org.apache.iotdb.db.qp.physical.PhysicalPlan;
+
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.Collections;
+import java.util.List;
+
+public class PreDeleteTimeSeriesPlan extends PhysicalPlan {
+
+ private PartialPath path;
+
+ public PreDeleteTimeSeriesPlan() {
+ super(Operator.OperatorType.PRE_DELETE_TIMESERIES_IN_CLUSTER);
+ }
+
+ public PreDeleteTimeSeriesPlan(PartialPath path) {
+ super(Operator.OperatorType.PRE_DELETE_TIMESERIES_IN_CLUSTER);
+ this.path = path;
+ }
+
+ public PartialPath getPath() {
+ return path;
+ }
+
+ public void setPath(PartialPath path) {
+ this.path = path;
+ }
+
+ @Override
+ public List<? extends PartialPath> getPaths() {
+ return Collections.singletonList(path);
+ }
+
+ @Override
+ public void serialize(DataOutputStream stream) throws IOException {
+ stream.write((byte) PhysicalPlanType.PRE_DELETE_TIMESERIES_IN_CLUSTER.ordinal());
+ path.serialize(stream);
+ stream.writeLong(index);
+ }
+
+ @Override
+ protected void serializeImpl(ByteBuffer buffer) {
+ buffer.put((byte) PhysicalPlanType.PRE_DELETE_TIMESERIES_IN_CLUSTER.ordinal());
+ path.serialize(buffer);
+ buffer.putLong(index);
+ }
+
+ @Override
+ public void deserialize(ByteBuffer buffer) throws IllegalPathException, IOException {
+ path = (PartialPath) PathDeserializeUtil.deserialize(buffer);
+ index = buffer.getLong();
+ }
+}
diff --git a/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/RollbackPreDeleteTimeSeriesPlan.java b/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/RollbackPreDeleteTimeSeriesPlan.java
new file mode 100644
index 0000000000..019472a254
--- /dev/null
+++ b/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/RollbackPreDeleteTimeSeriesPlan.java
@@ -0,0 +1,79 @@
+/*
+ * 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.qp.physical.sys;
+
+import org.apache.iotdb.commons.exception.IllegalPathException;
+import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.db.metadata.path.PathDeserializeUtil;
+import org.apache.iotdb.db.qp.logical.Operator;
+import org.apache.iotdb.db.qp.physical.PhysicalPlan;
+
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.Collections;
+import java.util.List;
+
+public class RollbackPreDeleteTimeSeriesPlan extends PhysicalPlan {
+
+ private PartialPath path;
+
+ public RollbackPreDeleteTimeSeriesPlan() {
+ super(Operator.OperatorType.ROLLBACK_PRE_DELETE_TIMESERIES);
+ }
+
+ public RollbackPreDeleteTimeSeriesPlan(PartialPath path) {
+ super(Operator.OperatorType.ROLLBACK_PRE_DELETE_TIMESERIES);
+ this.path = path;
+ }
+
+ public PartialPath getPath() {
+ return path;
+ }
+
+ public void setPath(PartialPath path) {
+ this.path = path;
+ }
+
+ @Override
+ public List<? extends PartialPath> getPaths() {
+ return Collections.singletonList(path);
+ }
+
+ @Override
+ public void serialize(DataOutputStream stream) throws IOException {
+ stream.write((byte) PhysicalPlanType.ROLLBACK_PRE_DELETE_TIMESERIES.ordinal());
+ path.serialize(stream);
+ stream.writeLong(index);
+ }
+
+ @Override
+ protected void serializeImpl(ByteBuffer buffer) {
+ buffer.put((byte) PhysicalPlanType.ROLLBACK_PRE_DELETE_TIMESERIES.ordinal());
+ path.serialize(buffer);
+ buffer.putLong(index);
+ }
+
+ @Override
+ public void deserialize(ByteBuffer buffer) throws IllegalPathException, IOException {
+ path = (PartialPath) PathDeserializeUtil.deserialize(buffer);
+ index = buffer.getLong();
+ }
+}
diff --git a/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeInternalRPCServiceImpl.java b/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeInternalRPCServiceImpl.java
index 7b74027cef..bc487251b2 100644
--- a/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeInternalRPCServiceImpl.java
+++ b/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeInternalRPCServiceImpl.java
@@ -24,16 +24,13 @@ import org.apache.iotdb.common.rpc.thrift.TConsensusGroupId;
import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
import org.apache.iotdb.common.rpc.thrift.TEndPoint;
import org.apache.iotdb.common.rpc.thrift.TFlushReq;
-import org.apache.iotdb.common.rpc.thrift.TRegionReplicaSet;
import org.apache.iotdb.common.rpc.thrift.TSStatus;
import org.apache.iotdb.common.rpc.thrift.TSetTTLReq;
import org.apache.iotdb.commons.cluster.NodeStatus;
import org.apache.iotdb.commons.conf.CommonDescriptor;
-import org.apache.iotdb.commons.conf.IoTDBConstant;
import org.apache.iotdb.commons.consensus.ConsensusGroupId;
import org.apache.iotdb.commons.consensus.DataRegionId;
import org.apache.iotdb.commons.consensus.SchemaRegionId;
-import org.apache.iotdb.commons.exception.IllegalPathException;
import org.apache.iotdb.commons.exception.MetadataException;
import org.apache.iotdb.commons.path.PartialPath;
import org.apache.iotdb.commons.trigger.TriggerInformation;
@@ -44,7 +41,6 @@ import org.apache.iotdb.confignode.rpc.thrift.TTriggerState;
import org.apache.iotdb.consensus.common.Peer;
import org.apache.iotdb.consensus.common.response.ConsensusGenericResponse;
import org.apache.iotdb.consensus.common.response.ConsensusReadResponse;
-import org.apache.iotdb.consensus.common.response.ConsensusWriteResponse;
import org.apache.iotdb.consensus.exception.PeerNotInConsensusGroupException;
import org.apache.iotdb.db.auth.AuthorizerManager;
import org.apache.iotdb.db.client.ConfigNodeInfo;
@@ -55,24 +51,26 @@ import org.apache.iotdb.db.engine.StorageEngineV2;
import org.apache.iotdb.db.engine.cache.BloomFilterCache;
import org.apache.iotdb.db.engine.cache.ChunkCache;
import org.apache.iotdb.db.engine.cache.TimeSeriesMetadataCache;
-import org.apache.iotdb.db.exception.DataRegionException;
import org.apache.iotdb.db.exception.StorageEngineException;
import org.apache.iotdb.db.exception.query.QueryProcessException;
-import org.apache.iotdb.db.exception.sql.SemanticException;
import org.apache.iotdb.db.metadata.cache.DataNodeSchemaCache;
import org.apache.iotdb.db.metadata.schemaregion.SchemaEngine;
import org.apache.iotdb.db.metadata.template.ClusterTemplateManager;
import org.apache.iotdb.db.metadata.template.TemplateInternalRPCUpdateType;
import org.apache.iotdb.db.mpp.common.FragmentInstanceId;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.mpp.execution.fragment.FragmentInstanceInfo;
import org.apache.iotdb.db.mpp.execution.fragment.FragmentInstanceManager;
import org.apache.iotdb.db.mpp.execution.fragment.FragmentInstanceState;
import org.apache.iotdb.db.mpp.plan.analyze.ClusterPartitionFetcher;
-import org.apache.iotdb.db.mpp.plan.analyze.SchemaValidator;
import org.apache.iotdb.db.mpp.plan.planner.plan.FragmentInstance;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeId;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeType;
-import org.apache.iotdb.db.mpp.plan.planner.plan.node.write.InsertNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.ConstructSchemaBlackListNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.DeleteTimeSeriesNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.metedata.write.RollbackSchemaBlackListNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.write.DeleteDataNode;
import org.apache.iotdb.db.service.DataNode;
import org.apache.iotdb.db.service.RegionMigrateService;
import org.apache.iotdb.db.service.metrics.MetricService;
@@ -88,22 +86,29 @@ import org.apache.iotdb.mpp.rpc.thrift.TCancelFragmentInstanceReq;
import org.apache.iotdb.mpp.rpc.thrift.TCancelPlanFragmentReq;
import org.apache.iotdb.mpp.rpc.thrift.TCancelQueryReq;
import org.apache.iotdb.mpp.rpc.thrift.TCancelResp;
+import org.apache.iotdb.mpp.rpc.thrift.TConstructSchemaBlackListReq;
import org.apache.iotdb.mpp.rpc.thrift.TCreateDataRegionReq;
import org.apache.iotdb.mpp.rpc.thrift.TCreateFunctionRequest;
import org.apache.iotdb.mpp.rpc.thrift.TCreatePeerReq;
import org.apache.iotdb.mpp.rpc.thrift.TCreateSchemaRegionReq;
+import org.apache.iotdb.mpp.rpc.thrift.TDeleteDataForDeleteTimeSeriesReq;
+import org.apache.iotdb.mpp.rpc.thrift.TDeleteTimeSeriesReq;
import org.apache.iotdb.mpp.rpc.thrift.TDisableDataNodeReq;
import org.apache.iotdb.mpp.rpc.thrift.TDropFunctionRequest;
import org.apache.iotdb.mpp.rpc.thrift.TDropTriggerInstanceReq;
import org.apache.iotdb.mpp.rpc.thrift.TFetchFragmentInstanceStateReq;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListReq;
+import org.apache.iotdb.mpp.rpc.thrift.TFetchSchemaBlackListResp;
import org.apache.iotdb.mpp.rpc.thrift.TFragmentInstanceStateResp;
import org.apache.iotdb.mpp.rpc.thrift.THeartbeatReq;
import org.apache.iotdb.mpp.rpc.thrift.THeartbeatResp;
import org.apache.iotdb.mpp.rpc.thrift.TInvalidateCacheReq;
+import org.apache.iotdb.mpp.rpc.thrift.TInvalidateMatchedSchemaCacheReq;
import org.apache.iotdb.mpp.rpc.thrift.TInvalidatePermissionCacheReq;
import org.apache.iotdb.mpp.rpc.thrift.TMaintainPeerReq;
import org.apache.iotdb.mpp.rpc.thrift.TRegionLeaderChangeReq;
import org.apache.iotdb.mpp.rpc.thrift.TRegionRouteReq;
+import org.apache.iotdb.mpp.rpc.thrift.TRollbackSchemaBlackListReq;
import org.apache.iotdb.mpp.rpc.thrift.TSchemaFetchRequest;
import org.apache.iotdb.mpp.rpc.thrift.TSchemaFetchResponse;
import org.apache.iotdb.mpp.rpc.thrift.TSendFragmentInstanceReq;
@@ -123,6 +128,10 @@ import org.apache.thrift.TException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
@@ -138,8 +147,11 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
private final SchemaEngine schemaEngine = SchemaEngine.getInstance();
private final StorageEngineV2 storageEngine = StorageEngineV2.getInstance();
+ private final DataNodeRegionManager regionManager;
+
public DataNodeInternalRPCServiceImpl() {
super();
+ regionManager = new DataNodeRegionManager(schemaEngine, storageEngine);
}
@Override
@@ -209,62 +221,8 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
LOGGER.info("receive PlanNode to group[{}]", req.getConsensusGroupId());
ConsensusGroupId groupId =
ConsensusGroupId.Factory.createFromTConsensusGroupId(req.getConsensusGroupId());
- TSendPlanNodeResp response = new TSendPlanNodeResp();
- ConsensusWriteResponse writeResponse;
-
PlanNode planNode = PlanNodeType.deserialize(req.planNode.body);
- boolean hasFailedMeasurement = false;
- String partialInsertMessage = null;
- if (planNode instanceof InsertNode) {
- InsertNode insertNode = (InsertNode) planNode;
- try {
- SchemaValidator.validate(insertNode);
- } catch (SemanticException e) {
- response.setAccepted(false);
- response.setMessage(e.getMessage());
- return response;
- }
- hasFailedMeasurement = insertNode.hasFailedMeasurements();
- if (hasFailedMeasurement) {
- partialInsertMessage =
- String.format(
- "Fail to insert measurements %s caused by %s",
- insertNode.getFailedMeasurements(), insertNode.getFailedMessages());
- LOGGER.warn(partialInsertMessage);
- }
- }
- if (groupId instanceof DataRegionId) {
-
- writeResponse = DataRegionConsensusImpl.getInstance().write(groupId, planNode);
-
- } else {
- writeResponse = SchemaRegionConsensusImpl.getInstance().write(groupId, planNode);
- }
- // TODO need consider more status
- if (writeResponse.getStatus() != null) {
- response.setAccepted(
- !hasFailedMeasurement
- && TSStatusCode.SUCCESS_STATUS.getStatusCode()
- == writeResponse.getStatus().getCode());
- if (TSStatusCode.SUCCESS_STATUS.getStatusCode() != writeResponse.getStatus().getCode()) {
- response.setMessage(writeResponse.getStatus().message);
- response.setStatus(writeResponse.getStatus());
- } else if (hasFailedMeasurement) {
- response.setMessage(partialInsertMessage);
- response.setStatus(
- RpcUtils.getStatus(TSStatusCode.METADATA_ERROR.getStatusCode(), partialInsertMessage));
- } else {
- response.setMessage(writeResponse.getStatus().message);
- }
- } else {
- LOGGER.error(
- "Something wrong happened while calling consensus layer's write API.",
- writeResponse.getException());
- response.setAccepted(false);
- response.setMessage(writeResponse.getException().getMessage());
- }
-
- return response;
+ return regionManager.executePlanNode(groupId, planNode);
}
@Override
@@ -311,73 +269,13 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
@Override
public TSStatus createSchemaRegion(TCreateSchemaRegionReq req) {
- TSStatus tsStatus;
- try {
- PartialPath storageGroupPartitionPath = new PartialPath(req.getStorageGroup());
- TRegionReplicaSet regionReplicaSet = req.getRegionReplicaSet();
- SchemaRegionId schemaRegionId = new SchemaRegionId(regionReplicaSet.getRegionId().getId());
- schemaEngine.createSchemaRegion(storageGroupPartitionPath, schemaRegionId);
- List<Peer> peers = new ArrayList<>();
- for (TDataNodeLocation dataNodeLocation : regionReplicaSet.getDataNodeLocations()) {
- TEndPoint endpoint =
- new TEndPoint(
- dataNodeLocation.getSchemaRegionConsensusEndPoint().getIp(),
- dataNodeLocation.getSchemaRegionConsensusEndPoint().getPort());
- peers.add(new Peer(schemaRegionId, endpoint));
- }
- ConsensusGenericResponse consensusGenericResponse =
- SchemaRegionConsensusImpl.getInstance().createPeer(schemaRegionId, peers);
- if (consensusGenericResponse.isSuccess()) {
- tsStatus = new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
- } else {
- tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
- tsStatus.setMessage(consensusGenericResponse.getException().getMessage());
- }
- } catch (IllegalPathException e1) {
- LOGGER.error(
- "Create Schema Region {} failed because path is illegal.", req.getStorageGroup());
- tsStatus = new TSStatus(TSStatusCode.PATH_ILLEGAL.getStatusCode());
- tsStatus.setMessage("Create Schema Region failed because storageGroup path is illegal.");
- } catch (MetadataException e2) {
- LOGGER.error(
- "Create Schema Region {} failed because {}", req.getStorageGroup(), e2.getMessage());
- tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
- tsStatus.setMessage(
- String.format("Create Schema Region failed because of %s", e2.getMessage()));
- }
- return tsStatus;
+ return regionManager.createSchemaRegion(req.getRegionReplicaSet(), req.getStorageGroup());
}
@Override
public TSStatus createDataRegion(TCreateDataRegionReq req) {
- TSStatus tsStatus;
- try {
- TRegionReplicaSet regionReplicaSet = req.getRegionReplicaSet();
- DataRegionId dataRegionId = new DataRegionId(regionReplicaSet.getRegionId().getId());
- storageEngine.createDataRegion(dataRegionId, req.storageGroup, req.ttl);
- List<Peer> peers = new ArrayList<>();
- for (TDataNodeLocation dataNodeLocation : regionReplicaSet.getDataNodeLocations()) {
- TEndPoint endpoint =
- new TEndPoint(
- dataNodeLocation.getDataRegionConsensusEndPoint().getIp(),
- dataNodeLocation.getDataRegionConsensusEndPoint().getPort());
- peers.add(new Peer(dataRegionId, endpoint));
- }
- ConsensusGenericResponse consensusGenericResponse =
- DataRegionConsensusImpl.getInstance().createPeer(dataRegionId, peers);
- if (consensusGenericResponse.isSuccess()) {
- tsStatus = new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
- } else {
- tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
- tsStatus.setMessage(consensusGenericResponse.getException().getMessage());
- }
- } catch (DataRegionException e) {
- LOGGER.error(
- "Create Data Region {} failed because {}", req.getStorageGroup(), e.getMessage());
- tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
- tsStatus.setMessage(String.format("Create Data Region failed because of %s", e.getMessage()));
- }
- return tsStatus;
+ return regionManager.createDataRegion(
+ req.getRegionReplicaSet(), req.getStorageGroup(), req.getTtl());
}
@Override
@@ -392,6 +290,154 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
return new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
}
+ @Override
+ public TSStatus constructSchemaBlackList(TConstructSchemaBlackListReq req) throws TException {
+ PathPatternTree patternTree =
+ PathPatternTree.deserialize(ByteBuffer.wrap(req.getPathPatternTree()));
+ List<TSStatus> failureList = new ArrayList<>();
+ TSStatus status;
+ int preDeletedNum = 0;
+ for (TConsensusGroupId consensusGroupId : req.getSchemaRegionIdList()) {
+ status =
+ regionManager.executeSchemaPlanNode(
+ new SchemaRegionId(consensusGroupId.getId()),
+ new ConstructSchemaBlackListNode(new PlanNodeId(""), patternTree));
+ if (status.code == TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ preDeletedNum += Integer.parseInt(status.getMessage());
+ } else {
+ failureList.add(status);
+ }
+ }
+
+ if (!failureList.isEmpty()) {
+ return RpcUtils.getStatus(failureList);
+ }
+
+ return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS, String.valueOf(preDeletedNum));
+ }
+
+ @Override
+ public TSStatus rollbackSchemaBlackList(TRollbackSchemaBlackListReq req) throws TException {
+ PathPatternTree patternTree =
+ PathPatternTree.deserialize(ByteBuffer.wrap(req.getPathPatternTree()));
+ List<TSStatus> failureList = new ArrayList<>();
+ TSStatus status;
+ for (TConsensusGroupId consensusGroupId : req.getSchemaRegionIdList()) {
+ status =
+ regionManager.executeSchemaPlanNode(
+ new SchemaRegionId(consensusGroupId.getId()),
+ new RollbackSchemaBlackListNode(new PlanNodeId(""), patternTree));
+ if (status.code != TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ failureList.add(status);
+ }
+ }
+
+ if (!failureList.isEmpty()) {
+ return RpcUtils.getStatus(failureList);
+ }
+
+ return RpcUtils.SUCCESS_STATUS;
+ }
+
+ @Override
+ public TSStatus invalidateMatchedSchemaCache(TInvalidateMatchedSchemaCacheReq req)
+ throws TException {
+ DataNodeSchemaCache cache = DataNodeSchemaCache.getInstance();
+ cache.takeWriteLock();
+ try {
+ for (PartialPath pathPattern :
+ PathPatternTree.deserialize(ByteBuffer.wrap(req.getPathPatternTree()))
+ .getAllPathPatterns()) {
+ cache.invalidateMatchedSchema(pathPattern);
+ }
+ } finally {
+ cache.releaseWriteLock();
+ }
+ return RpcUtils.SUCCESS_STATUS;
+ }
+
+ @Override
+ public TFetchSchemaBlackListResp fetchSchemaBlackList(TFetchSchemaBlackListReq req)
+ throws TException {
+ PathPatternTree patternTree = PathPatternTree.deserialize(req.pathPatternTree);
+ TFetchSchemaBlackListResp resp = new TFetchSchemaBlackListResp();
+ PathPatternTree result = new PathPatternTree();
+ for (TConsensusGroupId consensusGroupId : req.getSchemaRegionIdList()) {
+ // todo implement as consensus layer read request
+ try {
+ for (PartialPath path :
+ schemaEngine
+ .getSchemaRegion(new SchemaRegionId(consensusGroupId.getId()))
+ .fetchSchemaBlackList(patternTree)) {
+ result.appendFullPath(path);
+ }
+ } catch (MetadataException e) {
+ LOGGER.error(e.getMessage(), e);
+ resp.setStatus(RpcUtils.getStatus(e.getErrorCode(), e.getMessage()));
+ return resp;
+ }
+ }
+ resp.setStatus(RpcUtils.SUCCESS_STATUS);
+ ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
+ DataOutputStream dataOutputStream = new DataOutputStream(outputStream);
+ result.constructTree();
+ try {
+ result.serialize(dataOutputStream);
+ } catch (IOException ignored) {
+ // won't reach here
+ }
+ resp.setPathPatternTree(outputStream.toByteArray());
+ return resp;
+ }
+
+ @Override
+ public TSStatus deleteDataForDeleteTimeSeries(TDeleteDataForDeleteTimeSeriesReq req)
+ throws TException {
+ PathPatternTree patternTree =
+ PathPatternTree.deserialize(ByteBuffer.wrap(req.getPathPatternTree()));
+ List<PartialPath> pathList = patternTree.getAllPathPatterns();
+ List<TSStatus> failureList = new ArrayList<>();
+ TSStatus status;
+ for (TConsensusGroupId consensusGroupId : req.getDataRegionIdList()) {
+ status =
+ regionManager.executeDeleteDataForDeleteTimeSeries(
+ new DataRegionId(consensusGroupId.getId()),
+ new DeleteDataNode(new PlanNodeId(""), pathList, Long.MIN_VALUE, Long.MAX_VALUE));
+ if (status.code != TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ failureList.add(status);
+ }
+ }
+
+ if (!failureList.isEmpty()) {
+ return RpcUtils.getStatus(failureList);
+ }
+
+ return RpcUtils.SUCCESS_STATUS;
+ }
+
+ @Override
+ public TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req) throws TException {
+ PathPatternTree patternTree =
+ PathPatternTree.deserialize(ByteBuffer.wrap(req.getPathPatternTree()));
+ List<TSStatus> failureList = new ArrayList<>();
+ TSStatus status;
+ for (TConsensusGroupId consensusGroupId : req.getSchemaRegionIdList()) {
+ status =
+ regionManager.executeSchemaPlanNode(
+ new SchemaRegionId(consensusGroupId.getId()),
+ new DeleteTimeSeriesNode(new PlanNodeId(""), patternTree));
+ if (status.code != TSStatusCode.SUCCESS_STATUS.getStatusCode()) {
+ failureList.add(status);
+ }
+ }
+
+ if (!failureList.isEmpty()) {
+ return RpcUtils.getStatus(failureList);
+ }
+
+ return RpcUtils.SUCCESS_STATUS;
+ }
+
@Override
public THeartbeatResp getDataNodeHeartBeat(THeartbeatReq req) throws TException {
THeartbeatResp resp = new THeartbeatResp();
@@ -580,7 +626,7 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
return RpcUtils.getStatus(
TSStatusCode.DELETE_REGION_ERROR, response.getException().getMessage());
}
- StorageEngineV2.getInstance().deleteDataRegion((DataRegionId) consensusGroupId);
+ return regionManager.deleteDataRegion((DataRegionId) consensusGroupId);
} else {
ConsensusGenericResponse response =
SchemaRegionConsensusImpl.getInstance().deletePeer(consensusGroupId);
@@ -589,14 +635,8 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
return RpcUtils.getStatus(
TSStatusCode.DELETE_REGION_ERROR, response.getException().getMessage());
}
- try {
- SchemaEngine.getInstance().deleteSchemaRegion((SchemaRegionId) consensusGroupId);
- } catch (MetadataException e) {
- LOGGER.error("{}: MetaData error: ", IoTDBConstant.GLOBAL_DB_NAME, e);
- return RpcUtils.getStatus(TSStatusCode.METADATA_ERROR, e.getMessage());
- }
+ return regionManager.deleteSchemaRegion((SchemaRegionId) consensusGroupId);
}
- return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS, "Execute successfully");
}
public TSStatus changeRegionLeader(TRegionLeaderChangeReq req) throws TException {
@@ -716,23 +756,7 @@ public class DataNodeInternalRPCServiceImpl implements IDataNodeRPCService.Iface
}
private TSStatus createNewRegion(ConsensusGroupId regionId, String storageGroup, long ttl) {
- TSStatus status = new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
- LOGGER.info("start to create new region {}", regionId);
- try {
- if (regionId instanceof DataRegionId) {
- storageEngine.createDataRegion((DataRegionId) regionId, storageGroup, ttl);
- } else {
- schemaEngine.createSchemaRegion(new PartialPath(storageGroup), (SchemaRegionId) regionId);
- }
- } catch (Exception e) {
- LOGGER.error("create new region {} error", regionId, e);
- status.setCode(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
- status.setMessage("create new region " + regionId + "error, exception:" + e.getMessage());
- return status;
- }
- status.setMessage("create new region " + regionId + " succeed");
- LOGGER.info("succeed to create new region {}", regionId);
- return status;
+ return regionManager.createNewRegion(regionId, storageGroup, ttl);
}
@Override
diff --git a/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeRegionManager.java b/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeRegionManager.java
new file mode 100644
index 0000000000..574ac8be54
--- /dev/null
+++ b/server/src/main/java/org/apache/iotdb/db/service/thrift/impl/DataNodeRegionManager.java
@@ -0,0 +1,317 @@
+/*
+ * 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.service.thrift.impl;
+
+import org.apache.iotdb.common.rpc.thrift.TDataNodeLocation;
+import org.apache.iotdb.common.rpc.thrift.TEndPoint;
+import org.apache.iotdb.common.rpc.thrift.TRegionReplicaSet;
+import org.apache.iotdb.common.rpc.thrift.TSStatus;
+import org.apache.iotdb.commons.conf.IoTDBConstant;
+import org.apache.iotdb.commons.consensus.ConsensusGroupId;
+import org.apache.iotdb.commons.consensus.DataRegionId;
+import org.apache.iotdb.commons.consensus.SchemaRegionId;
+import org.apache.iotdb.commons.exception.IllegalPathException;
+import org.apache.iotdb.commons.exception.MetadataException;
+import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.consensus.common.Peer;
+import org.apache.iotdb.consensus.common.response.ConsensusGenericResponse;
+import org.apache.iotdb.consensus.common.response.ConsensusWriteResponse;
+import org.apache.iotdb.db.consensus.DataRegionConsensusImpl;
+import org.apache.iotdb.db.consensus.SchemaRegionConsensusImpl;
+import org.apache.iotdb.db.engine.StorageEngineV2;
+import org.apache.iotdb.db.exception.DataRegionException;
+import org.apache.iotdb.db.exception.sql.SemanticException;
+import org.apache.iotdb.db.metadata.schemaregion.SchemaEngine;
+import org.apache.iotdb.db.mpp.plan.analyze.SchemaValidator;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
+import org.apache.iotdb.db.mpp.plan.planner.plan.node.write.InsertNode;
+import org.apache.iotdb.mpp.rpc.thrift.TSendPlanNodeResp;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.rpc.TSStatusCode;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+
+/**
+ * This class takes the responsibility of managing regions, executing PlanNode of write type on
+ * according regions and controlling the execution concurrency.
+ */
+public class DataNodeRegionManager {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(DataNodeRegionManager.class);
+
+ private final SchemaEngine schemaEngine;
+ private final StorageEngineV2 storageEngine;
+
+ private final Map<SchemaRegionId, ReentrantReadWriteLock> schemaRegionLockMap =
+ new ConcurrentHashMap<>();
+ private final Map<DataRegionId, ReentrantReadWriteLock> dataRegionLockMap =
+ new ConcurrentHashMap<>();
+
+ public DataNodeRegionManager(SchemaEngine schemaEngine, StorageEngineV2 storageEngine) {
+ this.schemaEngine = schemaEngine;
+ this.storageEngine = storageEngine;
+ schemaEngine
+ .getAllSchemaRegions()
+ .forEach(
+ schemaRegion -> {
+ schemaRegionLockMap.put(
+ schemaRegion.getSchemaRegionId(), new ReentrantReadWriteLock(false));
+ });
+
+ storageEngine
+ .getAllDataRegionIds()
+ .forEach(
+ dataRegionId -> dataRegionLockMap.put(dataRegionId, new ReentrantReadWriteLock(false)));
+ }
+
+ public TSendPlanNodeResp executePlanNode(ConsensusGroupId groupId, PlanNode planNode) {
+ if (planNode instanceof InsertNode) {
+ return executeDataInsert((DataRegionId) groupId, (InsertNode) planNode);
+ } else {
+ TSendPlanNodeResp response = new TSendPlanNodeResp();
+ ConsensusWriteResponse writeResponse = executePlanNodeInConsensusLayer(groupId, planNode);
+ // TODO need consider more status
+ if (writeResponse.getStatus() != null) {
+ response.setAccepted(
+ TSStatusCode.SUCCESS_STATUS.getStatusCode() == writeResponse.getStatus().getCode());
+ response.setMessage(writeResponse.getStatus().message);
+ response.setStatus(writeResponse.getStatus());
+ } else {
+ LOGGER.error(
+ "Something wrong happened while calling consensus layer's write API.",
+ writeResponse.getException());
+ response.setAccepted(false);
+ response.setMessage(writeResponse.getException().getMessage());
+ }
+ return response;
+ }
+ }
+
+ private ConsensusWriteResponse executePlanNodeInConsensusLayer(
+ ConsensusGroupId groupId, PlanNode planNode) {
+ if (groupId instanceof DataRegionId) {
+ return DataRegionConsensusImpl.getInstance().write(groupId, planNode);
+ } else {
+ return SchemaRegionConsensusImpl.getInstance().write(groupId, planNode);
+ }
+ }
+
+ private TSendPlanNodeResp executeDataInsert(DataRegionId dataRegionId, InsertNode insertNode) {
+ TSendPlanNodeResp response = new TSendPlanNodeResp();
+ dataRegionLockMap.get(dataRegionId).readLock().lock();
+ try {
+ try {
+ SchemaValidator.validate(insertNode);
+ } catch (SemanticException e) {
+ response.setAccepted(false);
+ response.setMessage(e.getMessage());
+ return response;
+ }
+ boolean hasFailedMeasurement = insertNode.hasFailedMeasurements();
+ String partialInsertMessage = null;
+ if (hasFailedMeasurement) {
+ partialInsertMessage =
+ String.format(
+ "Fail to insert measurements %s caused by %s",
+ insertNode.getFailedMeasurements(), insertNode.getFailedMessages());
+ LOGGER.warn(partialInsertMessage);
+ }
+
+ ConsensusWriteResponse writeResponse =
+ executePlanNodeInConsensusLayer(dataRegionId, insertNode);
+
+ // TODO need consider more status
+ if (writeResponse.getStatus() != null) {
+ response.setAccepted(
+ !hasFailedMeasurement
+ && TSStatusCode.SUCCESS_STATUS.getStatusCode()
+ == writeResponse.getStatus().getCode());
+ if (TSStatusCode.SUCCESS_STATUS.getStatusCode() != writeResponse.getStatus().getCode()) {
+ response.setMessage(writeResponse.getStatus().message);
+ response.setStatus(writeResponse.getStatus());
+ } else if (hasFailedMeasurement) {
+ response.setMessage(partialInsertMessage);
+ response.setStatus(
+ RpcUtils.getStatus(
+ TSStatusCode.METADATA_ERROR.getStatusCode(), partialInsertMessage));
+ } else {
+ response.setMessage(writeResponse.getStatus().message);
+ }
+ } else {
+ LOGGER.error(
+ "Something wrong happened while calling consensus layer's write API.",
+ writeResponse.getException());
+ response.setAccepted(false);
+ response.setMessage(writeResponse.getException().getMessage());
+ }
+
+ return response;
+ } finally {
+ dataRegionLockMap.get(dataRegionId).readLock().unlock();
+ }
+ }
+
+ public TSStatus executeSchemaPlanNode(SchemaRegionId schemaRegionId, PlanNode planNode) {
+ ConsensusWriteResponse writeResponse =
+ executePlanNodeInConsensusLayer(schemaRegionId, planNode);
+ TSStatus status = writeResponse.getStatus();
+ if (status == null) {
+ LOGGER.error(
+ "Something wrong happened while calling consensus layer's write API.",
+ writeResponse.getException());
+ return RpcUtils.getStatus(TSStatusCode.EXECUTE_STATEMENT_ERROR);
+ }
+ return status;
+ }
+
+ public TSStatus executeDeleteDataForDeleteTimeSeries(
+ DataRegionId dataRegionId, PlanNode planNode) {
+ dataRegionLockMap.get(dataRegionId).writeLock().lock();
+ try {
+ ConsensusWriteResponse writeResponse =
+ executePlanNodeInConsensusLayer(dataRegionId, planNode);
+ TSStatus status = writeResponse.getStatus();
+ if (status == null) {
+ LOGGER.error(
+ "Something wrong happened while calling consensus layer's write API.",
+ writeResponse.getException());
+ return RpcUtils.getStatus(TSStatusCode.EXECUTE_STATEMENT_ERROR);
+ }
+ return status;
+ } finally {
+ dataRegionLockMap.get(dataRegionId).writeLock().unlock();
+ }
+ }
+
+ public TSStatus createSchemaRegion(TRegionReplicaSet regionReplicaSet, String storageGroup) {
+ TSStatus tsStatus;
+ try {
+ PartialPath storageGroupPartitionPath = new PartialPath(storageGroup);
+ SchemaRegionId schemaRegionId = new SchemaRegionId(regionReplicaSet.getRegionId().getId());
+ schemaEngine.createSchemaRegion(storageGroupPartitionPath, schemaRegionId);
+ schemaRegionLockMap.put(schemaRegionId, new ReentrantReadWriteLock(false));
+ List<Peer> peers = new ArrayList<>();
+ for (TDataNodeLocation dataNodeLocation : regionReplicaSet.getDataNodeLocations()) {
+ TEndPoint endpoint =
+ new TEndPoint(
+ dataNodeLocation.getSchemaRegionConsensusEndPoint().getIp(),
+ dataNodeLocation.getSchemaRegionConsensusEndPoint().getPort());
+ peers.add(new Peer(schemaRegionId, endpoint));
+ }
+ ConsensusGenericResponse consensusGenericResponse =
+ SchemaRegionConsensusImpl.getInstance().createPeer(schemaRegionId, peers);
+ if (consensusGenericResponse.isSuccess()) {
+ tsStatus = new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
+ } else {
+ tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
+ tsStatus.setMessage(consensusGenericResponse.getException().getMessage());
+ }
+ } catch (IllegalPathException e1) {
+ LOGGER.error("Create Schema Region {} failed because path is illegal.", storageGroup);
+ tsStatus = new TSStatus(TSStatusCode.PATH_ILLEGAL.getStatusCode());
+ tsStatus.setMessage("Create Schema Region failed because storageGroup path is illegal.");
+ } catch (MetadataException e2) {
+ LOGGER.error("Create Schema Region {} failed because {}", storageGroup, e2.getMessage());
+ tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
+ tsStatus.setMessage(
+ String.format("Create Schema Region failed because of %s", e2.getMessage()));
+ }
+ return tsStatus;
+ }
+
+ public TSStatus createDataRegion(
+ TRegionReplicaSet regionReplicaSet, String storageGroup, long ttl) {
+ TSStatus tsStatus;
+ try {
+ DataRegionId dataRegionId = new DataRegionId(regionReplicaSet.getRegionId().getId());
+ storageEngine.createDataRegion(dataRegionId, storageGroup, ttl);
+ dataRegionLockMap.put(dataRegionId, new ReentrantReadWriteLock(false));
+ List<Peer> peers = new ArrayList<>();
+ for (TDataNodeLocation dataNodeLocation : regionReplicaSet.getDataNodeLocations()) {
+ TEndPoint endpoint =
+ new TEndPoint(
+ dataNodeLocation.getDataRegionConsensusEndPoint().getIp(),
+ dataNodeLocation.getDataRegionConsensusEndPoint().getPort());
+ peers.add(new Peer(dataRegionId, endpoint));
+ }
+ ConsensusGenericResponse consensusGenericResponse =
+ DataRegionConsensusImpl.getInstance().createPeer(dataRegionId, peers);
+ if (consensusGenericResponse.isSuccess()) {
+ tsStatus = new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
+ } else {
+ tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
+ tsStatus.setMessage(consensusGenericResponse.getException().getMessage());
+ }
+ } catch (DataRegionException e) {
+ LOGGER.error("Create Data Region {} failed because {}", storageGroup, e.getMessage());
+ tsStatus = new TSStatus(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
+ tsStatus.setMessage(String.format("Create Data Region failed because of %s", e.getMessage()));
+ }
+ return tsStatus;
+ }
+
+ public TSStatus createNewRegion(ConsensusGroupId regionId, String storageGroup, long ttl) {
+ TSStatus status = new TSStatus(TSStatusCode.SUCCESS_STATUS.getStatusCode());
+ LOGGER.info("start to create new region {}", regionId);
+ try {
+ if (regionId instanceof DataRegionId) {
+ DataRegionId dataRegionId = (DataRegionId) regionId;
+ storageEngine.createDataRegion(dataRegionId, storageGroup, ttl);
+ dataRegionLockMap.put(dataRegionId, new ReentrantReadWriteLock(false));
+ } else {
+ SchemaRegionId schemaRegionId = (SchemaRegionId) regionId;
+ schemaEngine.createSchemaRegion(new PartialPath(storageGroup), schemaRegionId);
+ schemaRegionLockMap.put(schemaRegionId, new ReentrantReadWriteLock(false));
+ }
+ } catch (Exception e) {
+ LOGGER.error("create new region {} error", regionId, e);
+ status.setCode(TSStatusCode.CREATE_REGION_ERROR.getStatusCode());
+ status.setMessage("create new region " + regionId + "error, exception:" + e.getMessage());
+ return status;
+ }
+ status.setMessage("create new region " + regionId + " succeed");
+ LOGGER.info("succeed to create new region {}", regionId);
+ return status;
+ }
+
+ public TSStatus deleteDataRegion(DataRegionId dataRegionId) {
+ storageEngine.deleteDataRegion(dataRegionId);
+ dataRegionLockMap.remove(dataRegionId);
+ return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS, "Execute successfully");
+ }
+
+ public TSStatus deleteSchemaRegion(SchemaRegionId schemaRegionId) {
+ try {
+ schemaEngine.deleteSchemaRegion(schemaRegionId);
+ schemaRegionLockMap.remove(schemaRegionId);
+ return RpcUtils.getStatus(TSStatusCode.SUCCESS_STATUS, "Execute successfully");
+ } catch (MetadataException e) {
+ LOGGER.error("{}: MetaData error: ", IoTDBConstant.GLOBAL_DB_NAME, e);
+ return RpcUtils.getStatus(TSStatusCode.METADATA_ERROR, e.getMessage());
+ }
+ }
+}
diff --git a/server/src/test/java/org/apache/iotdb/db/mpp/plan/plan/node/metadata/write/DeleteTimeSeriesNodeSerdeTest.java b/server/src/test/java/org/apache/iotdb/db/mpp/plan/plan/node/metadata/write/DeleteTimeSeriesNodeSerdeTest.java
index 4cc69bd672..e2c17af9c7 100644
--- a/server/src/test/java/org/apache/iotdb/db/mpp/plan/plan/node/metadata/write/DeleteTimeSeriesNodeSerdeTest.java
+++ b/server/src/test/java/org/apache/iotdb/db/mpp/plan/plan/node/metadata/write/DeleteTimeSeriesNodeSerdeTest.java
@@ -21,6 +21,7 @@ package org.apache.iotdb.db.mpp.plan.plan.node.metadata.write;
import org.apache.iotdb.commons.exception.IllegalPathException;
import org.apache.iotdb.commons.path.PartialPath;
+import org.apache.iotdb.db.mpp.common.schematree.PathPatternTree;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNode;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeId;
import org.apache.iotdb.db.mpp.plan.planner.plan.node.PlanNodeType;
@@ -30,7 +31,6 @@ import org.junit.Assert;
import org.junit.Test;
import java.nio.ByteBuffer;
-import java.util.ArrayList;
import java.util.List;
public class DeleteTimeSeriesNodeSerdeTest {
@@ -38,10 +38,11 @@ public class DeleteTimeSeriesNodeSerdeTest {
@Test
public void testSerializeAndDeserialize() throws IllegalPathException {
PlanNodeId planNodeId = new PlanNodeId("DeleteTimeSeriesNode");
- List<PartialPath> pathList = new ArrayList<>();
- pathList.add(new PartialPath("root.sg.d1.s1"));
- pathList.add(new PartialPath("root.sg.d2.*"));
- DeleteTimeSeriesNode deleteTimeSeriesNode = new DeleteTimeSeriesNode(planNodeId, pathList);
+ PathPatternTree patternTree = new PathPatternTree();
+ patternTree.appendPathPattern(new PartialPath("root.sg.d1.s1"));
+ patternTree.appendPathPattern(new PartialPath("root.sg.d2.*"));
+ patternTree.constructTree();
+ DeleteTimeSeriesNode deleteTimeSeriesNode = new DeleteTimeSeriesNode(planNodeId, patternTree);
ByteBuffer byteBuffer = ByteBuffer.allocate(1024);
deleteTimeSeriesNode.serialize(byteBuffer);
@@ -52,7 +53,9 @@ public class DeleteTimeSeriesNodeSerdeTest {
Assert.assertEquals(planNodeId, deserializedNode.getPlanNodeId());
deleteTimeSeriesNode = (DeleteTimeSeriesNode) deserializedNode;
- List<PartialPath> deserializedPathList = deleteTimeSeriesNode.getPathList();
+ PathPatternTree deserializedPatternTree = deleteTimeSeriesNode.getPatternTree();
+ List<PartialPath> pathList = patternTree.getAllPathPatterns();
+ List<PartialPath> deserializedPathList = deserializedPatternTree.getAllPathPatterns();
Assert.assertEquals(pathList.size(), deserializedPathList.size());
for (int i = 0; i < pathList.size(); i++) {
Assert.assertEquals(pathList.get(i), deserializedPathList.get(i));
diff --git a/service-rpc/src/main/java/org/apache/iotdb/rpc/TSStatusCode.java b/service-rpc/src/main/java/org/apache/iotdb/rpc/TSStatusCode.java
index d611b32bd8..4c11f4b5df 100644
--- a/service-rpc/src/main/java/org/apache/iotdb/rpc/TSStatusCode.java
+++ b/service-rpc/src/main/java/org/apache/iotdb/rpc/TSStatusCode.java
@@ -72,6 +72,7 @@ public enum TSStatusCode {
CREATE_TEMPLATE_ERROR(340),
SYNC_FILE_REBASE(341),
SYNC_FILE_ERROR(342),
+ MEASUREMENT_IN_BLACK_LIST(343),
EXECUTE_STATEMENT_ERROR(400),
SQL_PARSE_ERROR(401),
@@ -153,7 +154,8 @@ public enum TSStatusCode {
LACK_REPLICATION(916),
DATANODE_STOP_ERROR(917),
REGION_LEADER_CHANGE_FAILED(918),
- REMOVE_DATANODE_FAILED(919);
+ REMOVE_DATANODE_FAILED(919),
+ OVERLAP_WITH_EXISTING_DELETE_TIMESERIES_TASK(920);
private int statusCode;
diff --git a/thrift-confignode/src/main/thrift/confignode.thrift b/thrift-confignode/src/main/thrift/confignode.thrift
index e4c12899c1..78de4b094f 100644
--- a/thrift-confignode/src/main/thrift/confignode.thrift
+++ b/thrift-confignode/src/main/thrift/confignode.thrift
@@ -390,6 +390,11 @@ struct TShowPipeResp {
2: optional list<TPipeInfo> pipeInfoList
}
+struct TDeleteTimeSeriesReq{
+ 1: required string queryId
+ 2: required binary pathPatternTree
+}
+
service IConfigNodeRPCService {
// ======================================================
@@ -715,5 +720,14 @@ service IConfigNodeRPCService {
TGetPathsSetTemplatesResp getPathsSetTemplate(string req)
+
+ /**
+ * Generate a set of DeleteTimeSeriesProcedure to delete some specific TimeSeries
+ *
+ * @return SUCCESS_STATUS if the DeleteTimeSeriesProcedure submitted and executed successfully
+ * TIMESERIES_NOT_EXIST if the specific TimeSeries doesn't exist
+ * EXECUTE_STATEMENT_ERROR if failed to submit or execute the DeleteTimeSeriesProcedure
+ */
+ common.TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req)
}
diff --git a/thrift/src/main/thrift/datanode.thrift b/thrift/src/main/thrift/datanode.thrift
index d62800c275..db8ebf20fb 100644
--- a/thrift/src/main/thrift/datanode.thrift
+++ b/thrift/src/main/thrift/datanode.thrift
@@ -216,6 +216,40 @@ struct TUpdateTemplateReq{
2: required binary templateInfo
}
+struct TConstructSchemaBlackListReq{
+ 1: required list<common.TConsensusGroupId> schemaRegionIdList
+ 2: required binary pathPatternTree
+}
+
+struct TRollbackSchemaBlackListReq{
+ 1: required list<common.TConsensusGroupId> schemaRegionIdList
+ 2: required binary pathPatternTree
+}
+
+struct TInvalidateMatchedSchemaCacheReq{
+ 1: required binary pathPatternTree
+}
+
+struct TFetchSchemaBlackListReq{
+ 1: required list<common.TConsensusGroupId> schemaRegionIdList
+ 2: required binary pathPatternTree
+}
+
+struct TFetchSchemaBlackListResp{
+ 1: required common.TSStatus status
+ 2: required binary pathPatternTree
+}
+
+struct TDeleteDataForDeleteTimeSeriesReq{
+ 1: required list<common.TConsensusGroupId> dataRegionIdList
+ 2: required binary pathPatternTree
+}
+
+struct TDeleteTimeSeriesReq{
+ 1: required list<common.TConsensusGroupId> schemaRegionIdList
+ 2: required binary pathPatternTree
+}
+
service IDataNodeRPCService {
// -----------------------------------For Data Node-----------------------------------------------
@@ -404,7 +438,44 @@ service IDataNodeRPCService {
*/
common.TSStatus updateConfigNodeGroup(TUpdateConfigNodeGroupReq req)
+ /**
+ * Update template cache when template info or template set info is updated
+ */
common.TSStatus updateTemplate(TUpdateTemplateReq req)
+
+ /**
+ * Construct schema black list in target schemaRegion to block R/W on matched timeseries
+ */
+ common.TSStatus constructSchemaBlackList(TConstructSchemaBlackListReq req)
+
+ /**
+ * Remove the schema black list to recover R/W on matched timeseries
+ */
+ common.TSStatus rollbackSchemaBlackList(TRollbackSchemaBlackListReq req)
+
+ /**
+ * Config node will invalidate Schema Info cache, which matched by given pathPatternTree.
+ *
+ * @param binary: pathPatternTree
+ */
+ common.TSStatus invalidateMatchedSchemaCache(TInvalidateMatchedSchemaCacheReq req)
+
+ /**
+ * Config node will fetch the schema info in black list.
+ *
+ * @param binary: pathPatternTree
+ */
+ TFetchSchemaBlackListResp fetchSchemaBlackList(TFetchSchemaBlackListReq req)
+
+ /**
+ * Config node inform this dataNode to execute a distribution data deleion mpp task
+ */
+ common.TSStatus deleteDataForDeleteTimeSeries(TDeleteDataForDeleteTimeSeriesReq req)
+
+ /**
+ * Delete matched timeseries and remove according schema black list in target schemRegion
+ */
+ common.TSStatus deleteTimeSeries(TDeleteTimeSeriesReq req)
}
service MPPDataExchangeService {