提交 f3bde281 authored 作者: S.Vladykin's avatar S.Vladykin

we have to hide current subQueryInfo if we are going to optimize query expression

上级 b860455f
...@@ -17,6 +17,7 @@ import org.h2.command.Command; ...@@ -17,6 +17,7 @@ import org.h2.command.Command;
import org.h2.command.CommandInterface; import org.h2.command.CommandInterface;
import org.h2.command.Parser; import org.h2.command.Parser;
import org.h2.command.Prepared; import org.h2.command.Prepared;
import org.h2.command.dml.Query;
import org.h2.command.dml.SetTypes; import org.h2.command.dml.SetTypes;
import org.h2.constraint.Constraint; import org.h2.constraint.Constraint;
import org.h2.index.Index; import org.h2.index.Index;
...@@ -115,6 +116,7 @@ public class Session extends SessionWithState { ...@@ -115,6 +116,7 @@ public class Session extends SessionWithState {
private long modificationMetaID = -1; private long modificationMetaID = -1;
private SubQueryInfo subQueryInfo; private SubQueryInfo subQueryInfo;
private int parsingView; private int parsingView;
private int preparingQueryExpression;
private volatile SmallLRUCache<Object, ViewIndex> viewIndexCache; private volatile SmallLRUCache<Object, ViewIndex> viewIndexCache;
private HashMap<Object, ViewIndex> subQueryIndexCache; private HashMap<Object, ViewIndex> subQueryIndexCache;
private boolean joinBatchEnabled; private boolean joinBatchEnabled;
...@@ -187,6 +189,24 @@ public class Session extends SessionWithState { ...@@ -187,6 +189,24 @@ public class Session extends SessionWithState {
return parsingView != 0; return parsingView != 0;
} }
public void optimizeQueryExpression(Query query) {
// we have to hide current subQueryInfo if we are going to optimize query expression
SubQueryInfo tmp = subQueryInfo;
subQueryInfo = null;
preparingQueryExpression++;
try {
query.prepare();
} finally {
subQueryInfo = tmp;
preparingQueryExpression--;
}
}
public boolean isPreparingQueryExpression() {
assert preparingQueryExpression >= 0;
return preparingQueryExpression != 0;
}
@Override @Override
public ArrayList<String> getClusterServers() { public ArrayList<String> getClusterServers() {
return new ArrayList<String>(); return new ArrayList<String>();
......
...@@ -9,6 +9,7 @@ import org.h2.command.dml.Query; ...@@ -9,6 +9,7 @@ import org.h2.command.dml.Query;
import org.h2.engine.Session; import org.h2.engine.Session;
import org.h2.result.LocalResult; import org.h2.result.LocalResult;
import org.h2.table.ColumnResolver; import org.h2.table.ColumnResolver;
import org.h2.table.SubQueryInfo;
import org.h2.table.TableFilter; import org.h2.table.TableFilter;
import org.h2.util.StringUtils; import org.h2.util.StringUtils;
import org.h2.value.Value; import org.h2.value.Value;
...@@ -36,7 +37,7 @@ public class ConditionExists extends Condition { ...@@ -36,7 +37,7 @@ public class ConditionExists extends Condition {
@Override @Override
public Expression optimize(Session session) { public Expression optimize(Session session) {
query.prepare(); session.optimizeQueryExpression(query);
return this; return this;
} }
......
...@@ -13,6 +13,7 @@ import org.h2.index.IndexCondition; ...@@ -13,6 +13,7 @@ import org.h2.index.IndexCondition;
import org.h2.message.DbException; import org.h2.message.DbException;
import org.h2.result.LocalResult; import org.h2.result.LocalResult;
import org.h2.table.ColumnResolver; import org.h2.table.ColumnResolver;
import org.h2.table.SubQueryInfo;
import org.h2.table.TableFilter; import org.h2.table.TableFilter;
import org.h2.util.StringUtils; import org.h2.util.StringUtils;
import org.h2.value.Value; import org.h2.value.Value;
...@@ -117,7 +118,7 @@ public class ConditionInSelect extends Condition { ...@@ -117,7 +118,7 @@ public class ConditionInSelect extends Condition {
public Expression optimize(Session session) { public Expression optimize(Session session) {
left = left.optimize(session); left = left.optimize(session);
query.setRandomAccessResult(true); query.setRandomAccessResult(true);
query.prepare(); session.optimizeQueryExpression(query);
if (query.getColumnCount() != 1) { if (query.getColumnCount() != 1) {
throw DbException.get(ErrorCode.SUBQUERY_IS_NOT_SINGLE_COLUMN); throw DbException.get(ErrorCode.SUBQUERY_IS_NOT_SINGLE_COLUMN);
} }
......
...@@ -6,13 +6,13 @@ ...@@ -6,13 +6,13 @@
package org.h2.expression; package org.h2.expression;
import java.util.ArrayList; import java.util.ArrayList;
import org.h2.api.ErrorCode; import org.h2.api.ErrorCode;
import org.h2.command.dml.Query; import org.h2.command.dml.Query;
import org.h2.engine.Session; import org.h2.engine.Session;
import org.h2.message.DbException; import org.h2.message.DbException;
import org.h2.result.ResultInterface; import org.h2.result.ResultInterface;
import org.h2.table.ColumnResolver; import org.h2.table.ColumnResolver;
import org.h2.table.SubQueryInfo;
import org.h2.table.TableFilter; import org.h2.table.TableFilter;
import org.h2.value.Value; import org.h2.value.Value;
import org.h2.value.ValueArray; import org.h2.value.ValueArray;
...@@ -70,7 +70,7 @@ public class Subquery extends Expression { ...@@ -70,7 +70,7 @@ public class Subquery extends Expression {
@Override @Override
public Expression optimize(Session session) { public Expression optimize(Session session) {
query.prepare(); session.optimizeQueryExpression(query);
return this; return this;
} }
......
...@@ -73,6 +73,7 @@ public class TestTableEngines extends TestBase { ...@@ -73,6 +73,7 @@ public class TestTableEngines extends TestBase {
@Override @Override
public void test() throws Exception { public void test() throws Exception {
testQueryExpressionFlag();
testSubQueryInfo(); testSubQueryInfo();
testEarlyFilter(); testEarlyFilter();
testEngineParams(); testEngineParams();
...@@ -347,6 +348,21 @@ public class TestTableEngines extends TestBase { ...@@ -347,6 +348,21 @@ public class TestTableEngines extends TestBase {
deleteDb("tableEngine"); deleteDb("tableEngine");
} }
private void testQueryExpressionFlag() throws SQLException {
deleteDb("testQueryExpressionFlag");
Connection conn = getConnection("testQueryExpressionFlag");
Statement stat = conn.createStatement();
stat.execute("create table QRY_EXPR_TEST(id int) ENGINE \"" +
TreeSetIndexTableEngine.class.getName() + "\"");
stat.execute("create table QRY_EXPR_TEST_NO(id int) ENGINE \"" +
TreeSetIndexTableEngine.class.getName() + "\"");
stat.executeQuery("select 1 + (select 1 from QRY_EXPR_TEST)").next();
stat.executeQuery("select 1 from QRY_EXPR_TEST_NO where id in (select id from QRY_EXPR_TEST)");
stat.executeQuery("select 1 from QRY_EXPR_TEST_NO n "
+ "where exists(select 1 from QRY_EXPR_TEST y where y.id = n.id)");
deleteDb("testQueryExpressionFlag");
}
private void testSubQueryInfo() throws SQLException { private void testSubQueryInfo() throws SQLException {
deleteDb("testSubQueryInfo"); deleteDb("testSubQueryInfo");
Connection conn = getConnection("testSubQueryInfo"); Connection conn = getConnection("testSubQueryInfo");
...@@ -1130,6 +1146,7 @@ public class TestTableEngines extends TestBase { ...@@ -1130,6 +1146,7 @@ public class TestTableEngines extends TestBase {
@Override @Override
public double getCost(Session session, int[] masks, public double getCost(Session session, int[] masks,
TableFilter[] filters, int filter, SortOrder sortOrder) { TableFilter[] filters, int filter, SortOrder sortOrder) {
doTests(session);
return getRowCount(session) + Constants.COST_ROW_OFFSET; return getRowCount(session) + Constants.COST_ROW_OFFSET;
} }
}; };
...@@ -1312,7 +1329,7 @@ public class TestTableEngines extends TestBase { ...@@ -1312,7 +1329,7 @@ public class TestTableEngines extends TestBase {
@Override @Override
public IndexLookupBatch createLookupBatch(final TableFilter filter) { public IndexLookupBatch createLookupBatch(final TableFilter filter) {
assert filter.getMasks() != null || "scan".equals(getName()); assert0(filter.getMasks() != null || "scan".equals(getName()), "masks");
final int preferedSize = preferedBatchSize; final int preferedSize = preferedBatchSize;
if (preferedSize == 0) { if (preferedSize == 0) {
return null; return null;
...@@ -1454,9 +1471,7 @@ public class TestTableEngines extends TestBase { ...@@ -1454,9 +1471,7 @@ public class TestTableEngines extends TestBase {
} }
} }
@Override protected void doTests(Session session) {
public double getCost(Session session, int[] masks,
TableFilter[] filters, int filter, SortOrder sortOrder) {
if (getTable().getName().equals("SUB_QUERY_TEST")) { if (getTable().getName().equals("SUB_QUERY_TEST")) {
checkInfo(session.getSubQueryInfo()); checkInfo(session.getSubQueryInfo());
} else if (getTable().getName().equals("EXPR_TEST")) { } else if (getTable().getName().equals("EXPR_TEST")) {
...@@ -1465,7 +1480,17 @@ public class TestTableEngines extends TestBase { ...@@ -1465,7 +1480,17 @@ public class TestTableEngines extends TestBase {
String alias = alias(session.getSubQueryInfo()); String alias = alias(session.getSubQueryInfo());
assert0(alias.equals("ZZ"), "select expression sub-query: " + alias); assert0(alias.equals("ZZ"), "select expression sub-query: " + alias);
assert0(session.getSubQueryInfo().getUpper() == null, "upper"); assert0(session.getSubQueryInfo().getUpper() == null, "upper");
} else if (getTable().getName().equals("QRY_EXPR_TEST")) {
assert0(session.isPreparingQueryExpression(), "preparing query expression");
} else if (getTable().getName().equals("QRY_EXPR_TEST_NO")) {
assert0(!session.isPreparingQueryExpression(), "not preparing query expression");
}
} }
@Override
public double getCost(Session session, int[] masks,
TableFilter[] filters, int filter, SortOrder sortOrder) {
doTests(session);
return getCostRangeIndex(masks, set.size(), filters, filter, sortOrder); return getCostRangeIndex(masks, set.size(), filters, filter, sortOrder);
} }
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论