This is an automated email from the ASF dual-hosted git repository.

haonan 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 a2b704d  bug fix - skip illegal path when delete multi timeseries  
(#2567)
a2b704d is described below

commit a2b704d864334dafdc882254c411b9c6ab9c52b0
Author: Haimei Guo <[email protected]>
AuthorDate: Wed Feb 24 10:23:10 2021 +0800

    bug fix - skip illegal path when delete multi timeseries  (#2567)
    
    * delete multi timeseries and skip illegal path
    
    * add success status code for delete in batch
    
    Co-authored-by: Haonan <[email protected]>
---
 .../iotdb/cluster/log/applier/BaseApplier.java     |  3 ++
 .../apache/iotdb/db/qp/executor/PlanExecutor.java  | 43 ++++++++--------------
 .../db/qp/physical/sys/DeleteTimeSeriesPlan.java   | 22 +++++++++++
 .../apache/iotdb/session/IoTDBSessionSimpleIT.java | 20 ++++++++++
 4 files changed, 60 insertions(+), 28 deletions(-)

diff --git 
a/cluster/src/main/java/org/apache/iotdb/cluster/log/applier/BaseApplier.java 
b/cluster/src/main/java/org/apache/iotdb/cluster/log/applier/BaseApplier.java
index 8431fa2..460ba6e 100644
--- 
a/cluster/src/main/java/org/apache/iotdb/cluster/log/applier/BaseApplier.java
+++ 
b/cluster/src/main/java/org/apache/iotdb/cluster/log/applier/BaseApplier.java
@@ -26,6 +26,7 @@ import org.apache.iotdb.cluster.query.ClusterPlanExecutor;
 import org.apache.iotdb.cluster.rpc.thrift.Node;
 import org.apache.iotdb.cluster.server.member.DataGroupMember;
 import org.apache.iotdb.cluster.server.member.MetaGroupMember;
+import org.apache.iotdb.db.exception.BatchProcessException;
 import org.apache.iotdb.db.exception.StorageEngineException;
 import org.apache.iotdb.db.exception.metadata.MetadataException;
 import org.apache.iotdb.db.exception.metadata.PathNotExistException;
@@ -73,6 +74,8 @@ abstract class BaseApplier implements LogApplier {
       } catch (QueryProcessException e) {
         if (e.getCause() instanceof StorageGroupNotSetException) {
           executeAfterSync(plan);
+        } else if (e instanceof BatchProcessException) {
+          logger.warn("Exception occurred while processing non-query. ", e);
         } else {
           throw e;
         }
diff --git 
a/server/src/main/java/org/apache/iotdb/db/qp/executor/PlanExecutor.java 
b/server/src/main/java/org/apache/iotdb/db/qp/executor/PlanExecutor.java
index ce11e70..85fce24 100644
--- a/server/src/main/java/org/apache/iotdb/db/qp/executor/PlanExecutor.java
+++ b/server/src/main/java/org/apache/iotdb/db/qp/executor/PlanExecutor.java
@@ -40,7 +40,6 @@ import org.apache.iotdb.db.exception.BatchProcessException;
 import org.apache.iotdb.db.exception.QueryIdNotExsitException;
 import org.apache.iotdb.db.exception.StorageEngineException;
 import org.apache.iotdb.db.exception.UDFRegistrationException;
-import org.apache.iotdb.db.exception.metadata.DeleteFailedException;
 import org.apache.iotdb.db.exception.metadata.IllegalPathException;
 import org.apache.iotdb.db.exception.metadata.MetadataException;
 import org.apache.iotdb.db.exception.metadata.PathNotExistException;
@@ -143,7 +142,6 @@ import java.util.Collection;
 import java.util.Collections;
 import java.util.HashMap;
 import java.util.HashSet;
-import java.util.LinkedList;
 import java.util.List;
 import java.util.Map;
 import java.util.Map.Entry;
@@ -1293,37 +1291,26 @@ public class PlanExecutor implements IPlanExecutor {
   protected boolean deleteTimeSeries(DeleteTimeSeriesPlan deleteTimeSeriesPlan)
       throws QueryProcessException {
     List<PartialPath> deletePathList = deleteTimeSeriesPlan.getPaths();
-    try {
-      List<String> failedNames = new LinkedList<>();
-      List<String> nonExistPaths = new ArrayList<>();
-      for (PartialPath path : deletePathList) {
+    for (int i = 0; i < deletePathList.size(); i++) {
+      PartialPath path = deletePathList.get(i);
+      try {
         StorageEngine.getInstance().deleteTimeseries(path, 
deleteTimeSeriesPlan.getIndex());
-        String failedTimeseries = deleteTimeSeries(path, nonExistPaths);
-        if (failedTimeseries != null) {
-          failedNames.add(failedTimeseries);
+        String failed = IoTDB.metaManager.deleteTimeseries(path);
+        if (failed != null) {
+          deleteTimeSeriesPlan
+              .getResults()
+              .put(i, 
RpcUtils.getStatus(TSStatusCode.NODE_DELETE_FAILED_ERROR, failed));
         }
+      } catch (StorageEngineException | MetadataException e) {
+        deleteTimeSeriesPlan
+            .getResults()
+            .put(i, RpcUtils.getStatus(e.getErrorCode(), e.getMessage()));
       }
-      if (!nonExistPaths.isEmpty()) {
-        throw new PathNotExistException(nonExistPaths);
-      }
-      if (!failedNames.isEmpty()) {
-        throw new DeleteFailedException(String.join(",", failedNames));
-      }
-    } catch (MetadataException | StorageEngineException e) {
-      throw new QueryProcessException(e);
     }
-    return true;
-  }
-
-  private String deleteTimeSeries(PartialPath path, List<String> nonExistPaths)
-      throws MetadataException {
-    String failedTimeseries = null;
-    try {
-      failedTimeseries = IoTDB.metaManager.deleteTimeseries(path);
-    } catch (PathNotExistException e) {
-      nonExistPaths.add(path.getFullPath());
+    if (!deleteTimeSeriesPlan.getResults().isEmpty()) {
+      throw new BatchProcessException(deleteTimeSeriesPlan.getFailingStatus());
     }
-    return failedTimeseries;
+    return true;
   }
 
   private boolean alterTimeSeries(AlterTimeSeriesPlan alterTimeSeriesPlan)
diff --git 
a/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/DeleteTimeSeriesPlan.java
 
b/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/DeleteTimeSeriesPlan.java
index 72b0fde..20af1ea 100644
--- 
a/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/DeleteTimeSeriesPlan.java
+++ 
b/server/src/main/java/org/apache/iotdb/db/qp/physical/sys/DeleteTimeSeriesPlan.java
@@ -22,16 +22,22 @@ import 
org.apache.iotdb.db.exception.metadata.IllegalPathException;
 import org.apache.iotdb.db.metadata.PartialPath;
 import org.apache.iotdb.db.qp.logical.Operator;
 import org.apache.iotdb.db.qp.physical.PhysicalPlan;
+import org.apache.iotdb.rpc.RpcUtils;
+import org.apache.iotdb.service.rpc.thrift.TSStatus;
 
 import java.io.DataOutputStream;
 import java.io.IOException;
 import java.nio.ByteBuffer;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.List;
+import java.util.Map;
+import java.util.TreeMap;
 
 public class DeleteTimeSeriesPlan extends PhysicalPlan {
 
   private List<PartialPath> deletePathList;
+  private Map<Integer, TSStatus> results = new TreeMap<>();
 
   public DeleteTimeSeriesPlan(List<PartialPath> deletePathList) {
     super(false, Operator.OperatorType.DELETE_TIMESERIES);
@@ -90,4 +96,20 @@ public class DeleteTimeSeriesPlan extends PhysicalPlan {
   public void setPaths(List<PartialPath> fullPaths) {
     this.deletePathList = fullPaths;
   }
+
+  public Map<Integer, TSStatus> getResults() {
+    return results;
+  }
+
+  public TSStatus[] getFailingStatus() {
+    if (results.isEmpty()) {
+      return new TSStatus[0];
+    }
+    TSStatus[] failingStatus = new TSStatus[deletePathList.size()];
+    Arrays.fill(failingStatus, RpcUtils.SUCCESS_STATUS);
+    for (Map.Entry<Integer, TSStatus> status : results.entrySet()) {
+      failingStatus[status.getKey()] = status.getValue();
+    }
+    return failingStatus;
+  }
 }
diff --git 
a/session/src/test/java/org/apache/iotdb/session/IoTDBSessionSimpleIT.java 
b/session/src/test/java/org/apache/iotdb/session/IoTDBSessionSimpleIT.java
index fa1d754..ed72527 100644
--- a/session/src/test/java/org/apache/iotdb/session/IoTDBSessionSimpleIT.java
+++ b/session/src/test/java/org/apache/iotdb/session/IoTDBSessionSimpleIT.java
@@ -45,6 +45,7 @@ import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.HashMap;
 import java.util.HashSet;
 import java.util.List;
@@ -421,6 +422,25 @@ public class IoTDBSessionSimpleIT {
   }
 
   @Test
+  public void testDeleteNonExistTimeSeries()
+      throws StatementExecutionException, IoTDBConnectionException {
+    session = new Session("127.0.0.1", 6667, "root", "root");
+    session.open();
+    session.insertRecord(
+        "root.sg1.d1", 0, Arrays.asList("t1", "t2", "t3"), 
Arrays.asList("123", "333", "444"));
+    try {
+      session.deleteTimeseries(Arrays.asList("root.sg1.d1.t6", 
"root.sg1.d1.t2", "root.sg1.d1.t3"));
+    } catch (BatchExecutionException e) {
+      assertEquals("Path [root.sg1.d1.t6] does not exist;", e.getMessage());
+    }
+    assertTrue(session.checkTimeseriesExists("root.sg1.d1.t1"));
+    assertFalse(session.checkTimeseriesExists("root.sg1.d1.t2"));
+    assertFalse(session.checkTimeseriesExists("root.sg1.d1.t3"));
+
+    session.close();
+  }
+
+  @Test
   public void testInsertOneDeviceRecords()
       throws IoTDBConnectionException, StatementExecutionException {
     session = new Session("127.0.0.1", 6667, "root", "root");

Reply via email to