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 2023/01/03 00:32:32 UTC
[iotdb] branch master updated: [IOTDB-5329] Exception handler for AbstractTreeVisitor (#8700)
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 3b770954e4 [IOTDB-5329] Exception handler for AbstractTreeVisitor (#8700)
3b770954e4 is described below
commit 3b770954e4b4a979383eb217143c04c4ff45e731
Author: Chen YZ <43...@users.noreply.github.com>
AuthorDate: Tue Jan 3 08:32:26 2023 +0800
[IOTDB-5329] Exception handler for AbstractTreeVisitor (#8700)
[IOTDB-5329] Exception handler for AbstractTreeVisitor (#8700)
---
.../commons/schema/tree/AbstractTreeVisitor.java | 133 ++++++++++++++++-----
.../tree/AbstractTreeVisitorWithLimitOffset.java | 2 +-
2 files changed, 102 insertions(+), 33 deletions(-)
diff --git a/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitor.java b/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitor.java
index 63e3daaeff..2a92d8126c 100644
--- a/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitor.java
+++ b/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitor.java
@@ -62,7 +62,8 @@ import java.util.NoSuchElementException;
* @param <N> The node consisting the tree.
* @param <R> The result extracted from the tree.
*/
-public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Iterator<R> {
+public abstract class AbstractTreeVisitor<N extends ITreeNode, R>
+ implements Iterator<R>, AutoCloseable {
// command parameters
protected final N root;
@@ -85,6 +86,8 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
private IStateMatchInfo currentStateMatchInfo;
// whether to visit the subtree of current node
private boolean shouldVisitSubtree;
+ // record exception if failed
+ private Throwable throwable;
// cached result variables
protected N nextMatchedNode;
@@ -127,6 +130,14 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
ancestorStack.add(new AncestorStackEntry(root, currentStateMatchInfo));
}
+ public boolean isSuccess() {
+ return throwable != null;
+ }
+
+ public Throwable getThrowable() {
+ return throwable;
+ }
+
public void reset() {
visitorStack.clear();
ancestorStack.clear();
@@ -135,12 +146,23 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
initStack();
}
+ @Override
+ public void close() {
+ while (!visitorStack.isEmpty()) {
+ popStack();
+ }
+ }
+
@Override
public boolean hasNext() {
- if (nextMatchedNode == null) {
- getNext();
+ if (throwable == null && nextMatchedNode == null) {
+ try {
+ getNext();
+ } catch (Throwable e) {
+ setFailure(e);
+ }
}
- return nextMatchedNode != null;
+ return throwable == null && nextMatchedNode != null;
}
@Override
@@ -153,7 +175,7 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
return result;
}
- protected void getNext() {
+ protected void getNext() throws Exception {
nextMatchedNode = null;
VisitorStackEntry stackEntry;
N node;
@@ -191,7 +213,7 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
ancestorStack.add(new AncestorStackEntry(parent, currentStateMatchInfo));
}
- private Iterator<N> createChildrenIterator(N parent) {
+ private AbstractChildrenIterator createChildrenIterator(N parent) {
if (firstAncestorOfTraceback > -1) {
// there may be traceback when try to find the matched state of node
return new TraceBackChildrenIterator(parent, currentStateMatchInfo);
@@ -212,7 +234,8 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
}
private void popStack() {
- visitorStack.pop();
+ VisitorStackEntry stackEntry = visitorStack.pop();
+ stackEntry.iterator.close();
// The ancestor pop operation with level check supports the children of one node pushed by
// batch.
if (!visitorStack.isEmpty() && visitorStack.peek().level < ancestorStack.size()) {
@@ -246,10 +269,16 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
}
// Get a child with the given childName.
- protected abstract N getChild(N parent, String childName);
+ protected abstract N getChild(N parent, String childName) throws Exception;
+
+ // Get an iterator of all children.
+ protected abstract Iterator<N> getChildrenIterator(N parent) throws Exception;
- // Get a iterator of all children.
- protected abstract Iterator<N> getChildrenIterator(N parent);
+ // Release a child with the given childName.
+ protected void releaseChild(N child) {}
+
+ // Release an iterator of all children.
+ protected void releaseChildrenIterator(Iterator<N> childrenIterator) {}
/**
* Internal-match means the node matches an internal node name of the given path pattern. root.sg
@@ -260,7 +289,7 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
* process will keep traversing the subtree. If return false, the traversing process will skip the
* subtree of given node.
*/
- protected abstract boolean processInternalMatchedNode(N node);
+ protected abstract boolean processInternalMatchedNode(N node) throws Exception;
/**
* Full-match means the node matches the last node name of the given path pattern. root.sg.d full
@@ -270,7 +299,11 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
* process will keep traversing the subtree. If return false, the traversing process will skip the
* subtree of given node.
*/
- protected abstract boolean processFullMatchedNode(N node);
+ protected abstract boolean processFullMatchedNode(N node) throws Exception;
+
+ protected void setFailure(Throwable e) {
+ this.throwable = e;
+ }
/** The method used for generating the result based on the matched node. */
protected abstract R generateResult();
@@ -278,12 +311,12 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
private class VisitorStackEntry {
// children iterator
- private final Iterator<N> iterator;
+ private final AbstractChildrenIterator iterator;
// level of children taken from iterator
private final int level;
- VisitorStackEntry(Iterator<N> iterator, int level) {
+ VisitorStackEntry(AbstractChildrenIterator iterator, int level) {
this.iterator = iterator;
this.level = level;
}
@@ -308,7 +341,12 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
@Override
public boolean hasNext() {
if (nextMatchedChild == null) {
- getNext();
+ try {
+ getNext();
+ } catch (Throwable e) {
+ setFailure(e);
+ return false;
+ }
}
return nextMatchedChild != null;
}
@@ -328,16 +366,19 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
currentStateMatchInfo = stateMatchInfo;
}
- protected abstract void getNext();
+ protected abstract void getNext() throws Exception;
+
+ protected abstract void close();
}
// the child can be got directly with the precise value of transition, there's no traceback
private class PreciseMatchChildrenIterator extends AbstractChildrenIterator {
private final N parent;
private final IFAState sourceState;
-
private final Iterator<IFATransition> transitionIterator;
+ private N child;
+
private PreciseMatchChildrenIterator(N parent, IFAState sourceState) {
this.parent = parent;
this.sourceState = sourceState;
@@ -345,8 +386,7 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
}
@Override
- protected void getNext() {
- N child;
+ protected void getNext() throws Exception {
IFATransition transition;
while (transitionIterator.hasNext()) {
transition = transitionIterator.next();
@@ -360,6 +400,11 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
return;
}
}
+
+ @Override
+ protected void close() {
+ releaseChild(child);
+ }
}
// only one fuzzy transition which may match batch children, need to iterate and check all
@@ -368,23 +413,25 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
private class SingleFuzzyMatchChildrenIterator extends AbstractChildrenIterator {
private final IFAState sourceState;
-
private final IFATransition transition;
-
private final StateSingleMatchInfo stateMatchInfo;
+ private final N parent;
- private final Iterator<N> childrenIterator;
+ private Iterator<N> childrenIterator;
private SingleFuzzyMatchChildrenIterator(N parent, IFAState sourceState) {
this.sourceState = sourceState;
this.transition = patternFA.getFuzzyMatchTransitionIterator(sourceState).next();
this.stateMatchInfo =
new StateSingleMatchInfo(patternFA, patternFA.getNextState(sourceState, transition));
- this.childrenIterator = getChildrenIterator(parent);
+ this.parent = parent;
}
@Override
- protected void getNext() {
+ protected void getNext() throws Exception {
+ if (childrenIterator == null) {
+ this.childrenIterator = getChildrenIterator(parent);
+ }
N child;
while (childrenIterator.hasNext()) {
child = childrenIterator.next();
@@ -395,6 +442,11 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
return;
}
}
+
+ @Override
+ protected void close() {
+ releaseChildrenIterator(childrenIterator);
+ }
}
// child may be matched by multi transitions, precise match or fuzzy match,
@@ -404,19 +456,22 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
private class MultiMatchTransitionChildrenIterator extends AbstractChildrenIterator {
private final IFAState sourceState;
-
private final Map<String, IFATransition> preciseMatchTransitionMap;
+ private final N parent;
- private final Iterator<N> iterator;
+ private Iterator<N> iterator;
private MultiMatchTransitionChildrenIterator(N parent, IFAState sourceState) {
this.sourceState = sourceState;
- this.iterator = getChildrenIterator(parent);
this.preciseMatchTransitionMap = patternFA.getPreciseMatchTransition(sourceState);
+ this.parent = parent;
}
@Override
- protected void getNext() {
+ protected void getNext() throws Exception {
+ if (iterator == null) {
+ this.iterator = getChildrenIterator(parent);
+ }
N child;
IFAState matchedState = null;
@@ -456,23 +511,32 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
return;
}
}
+
+ @Override
+ protected void close() {
+ releaseChildrenIterator(iterator);
+ }
}
// there may be traceback when try to find the matched state of node;
// the iterating process will try to get the first matched state of a child.
private class TraceBackChildrenIterator extends AbstractChildrenIterator {
- private final Iterator<N> iterator;
-
+ private final N parent;
private final IStateMatchInfo sourceStateMatchInfo;
+ private Iterator<N> iterator;
+
TraceBackChildrenIterator(N parent, IStateMatchInfo sourceStateMatchInfo) {
this.sourceStateMatchInfo = sourceStateMatchInfo;
- this.iterator = getChildrenIterator(parent);
+ this.parent = parent;
}
@Override
- protected void getNext() {
+ protected void getNext() throws Exception {
+ if (iterator == null) {
+ iterator = getChildrenIterator(parent);
+ }
N child;
IFAState sourceState;
@@ -507,6 +571,11 @@ public abstract class AbstractTreeVisitor<N extends ITreeNode, R> implements Ite
}
}
+ @Override
+ protected void close() {
+ releaseChildrenIterator(iterator);
+ }
+
/**
* Try to get next matched state from sourceState and add it into currentStateMatchInfo
*
diff --git a/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitorWithLimitOffset.java b/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitorWithLimitOffset.java
index 122231eb6f..5208043ab8 100644
--- a/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitorWithLimitOffset.java
+++ b/node-commons/src/main/java/org/apache/iotdb/commons/schema/tree/AbstractTreeVisitorWithLimitOffset.java
@@ -60,7 +60,7 @@ public abstract class AbstractTreeVisitorWithLimitOffset<N extends ITreeNode, R>
}
@Override
- protected void getNext() {
+ protected void getNext() throws Exception {
if (hasLimit) {
if (curOffset < offset) {
while (curOffset < offset) {