You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@calcite.apache.org by jh...@apache.org on 2014/07/18 06:30:54 UTC
git commit: [OPTIQ-347] In SqlRun, add '!plan' command
Repository: incubator-optiq
Updated Branches:
refs/heads/master a1baf68df -> 4b9fba42e
[OPTIQ-347] In SqlRun, add '!plan' command
Project: http://git-wip-us.apache.org/repos/asf/incubator-optiq/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-optiq/commit/4b9fba42
Tree: http://git-wip-us.apache.org/repos/asf/incubator-optiq/tree/4b9fba42
Diff: http://git-wip-us.apache.org/repos/asf/incubator-optiq/diff/4b9fba42
Branch: refs/heads/master
Commit: 4b9fba42e40a1c745de27e089dea1ca7749af160
Parents: a1baf68
Author: Julian Hyde <jh...@apache.org>
Authored: Thu Jul 17 20:09:32 2014 -0700
Committer: Julian Hyde <jh...@apache.org>
Committed: Thu Jul 17 21:11:53 2014 -0700
----------------------------------------------------------------------
.../java/net/hydromatic/optiq/tools/SqlRun.java | 49 ++++++++++--
.../net/hydromatic/optiq/tools/SqlRunTest.java | 79 ++++++++++++++++++++
2 files changed, 123 insertions(+), 5 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-optiq/blob/4b9fba42/core/src/main/java/net/hydromatic/optiq/tools/SqlRun.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/net/hydromatic/optiq/tools/SqlRun.java b/core/src/main/java/net/hydromatic/optiq/tools/SqlRun.java
index b4871c0..577ac4e 100644
--- a/core/src/main/java/net/hydromatic/optiq/tools/SqlRun.java
+++ b/core/src/main/java/net/hydromatic/optiq/tools/SqlRun.java
@@ -19,9 +19,8 @@ package net.hydromatic.optiq.tools;
import net.hydromatic.optiq.prepare.OptiqPrepareImpl;
-import org.eigenbase.util.Util;
-
import com.google.common.base.Function;
+import com.google.common.base.Preconditions;
import com.google.common.collect.*;
import java.io.*;
@@ -197,9 +196,13 @@ public class SqlRun {
return new UseCommand(lines, parts[1]);
}
if (line.startsWith("ok")) {
- SqlCommand command = (SqlCommand) Util.last(commands);
+ SqlCommand command = previousSqlCommand();
return new CheckResultCommand(lines, command);
}
+ if (line.startsWith("plan")) {
+ SqlCommand command = previousSqlCommand();
+ return new ExplainCommand(lines, command);
+ }
if (line.startsWith("skip")) {
return new SkipCommand(lines);
}
@@ -251,6 +254,15 @@ public class SqlRun {
return new SqlCommand(sqlLines, sql, outputLines);
}
+ private SqlCommand previousSqlCommand() {
+ for (int i = commands.size() - 1; i >= 0; i--) {
+ Command command = commands.get(i);
+ if (command instanceof SqlCommand) {
+ return (SqlCommand) command;
+ }
+ }
+ throw new AssertionError("no previous SQL command");
+ }
private void pushLine() {
if (pushedLine != null) {
@@ -544,6 +556,33 @@ public class SqlRun {
}
}
+ /** Command that prints the plan for the current query. */
+ class ExplainCommand extends SimpleCommand {
+ private final SqlCommand sqlCommand;
+
+ public ExplainCommand(List<String> lines, SqlCommand sqlCommand) {
+ super(lines);
+ this.sqlCommand = sqlCommand;
+ }
+
+ public void execute(boolean execute) throws Exception {
+ if (execute) {
+ final Statement statement = connection.createStatement();
+ final ResultSet resultSet =
+ statement.executeQuery("explain plan for " + sqlCommand.sql);
+ if (!resultSet.next()) {
+ throw new AssertionError("explain returned 0 records");
+ }
+ printWriter.print(resultSet.getString(1));
+ if (resultSet.next()) {
+ throw new AssertionError("explain returned more than 1 record");
+ }
+ printWriter.flush();
+ }
+ echo(lines);
+ }
+ }
+
/** Command that executes a SQL statement. */
private class SqlCommand extends SimpleCommand {
private final String sql;
@@ -551,7 +590,7 @@ public class SqlRun {
protected SqlCommand(List<String> lines, String sql, List<String> output) {
super(lines);
- this.sql = sql;
+ this.sql = Preconditions.checkNotNull(sql);
this.output = ImmutableList.copyOf(output);
}
@@ -563,7 +602,7 @@ public class SqlRun {
}
final Statement statement = connection.createStatement();
if (resultSet != null) {
- throw new AssertionError("result set already present");
+ resultSet.close();
}
try {
if (OptiqPrepareImpl.DEBUG) {
http://git-wip-us.apache.org/repos/asf/incubator-optiq/blob/4b9fba42/core/src/test/java/net/hydromatic/optiq/tools/SqlRunTest.java
----------------------------------------------------------------------
diff --git a/core/src/test/java/net/hydromatic/optiq/tools/SqlRunTest.java b/core/src/test/java/net/hydromatic/optiq/tools/SqlRunTest.java
index 14800a4..8314c70 100644
--- a/core/src/test/java/net/hydromatic/optiq/tools/SqlRunTest.java
+++ b/core/src/test/java/net/hydromatic/optiq/tools/SqlRunTest.java
@@ -76,6 +76,85 @@ public class SqlRunTest {
+ "\": From line 1, column 18 to line 1, column 21: Table 'BLAH' not found"));
}
+ @Test public void testPlan() {
+ check(
+ "!use foodmart\n"
+ + "values (1), (2);\n"
+ + "!plan\n"
+ + "\n",
+ containsString(
+ "!use foodmart\n"
+ + "values (1), (2);\n"
+ + "EnumerableValuesRel(tuples=[[{ 1 }, { 2 }]])\n"
+ + "!plan\n"));
+ }
+
+ @Test public void testPlanAfterOk() {
+ check(
+ "!use foodmart\n"
+ + "values (1), (2);\n"
+ + "!ok\n"
+ + "!plan\n"
+ + "\n",
+ containsString(
+ "!use foodmart\n"
+ + "values (1), (2);\n"
+ + "EXPR$0\n"
+ + "1\n"
+ + "2\n"
+ + "!ok\n"
+ + "EnumerableValuesRel(tuples=[[{ 1 }, { 2 }]])\n"
+ + "!plan\n"
+ + "\n"));
+ }
+
+ /** It is OK to have consecutive '!plan' calls and no '!ok'.
+ * (Previously there was a "result already open" error.) */
+ @Test public void testPlanPlan() {
+ check(
+ "!use foodmart\n"
+ + "values (1), (2);\n"
+ + "!plan\n"
+ + "values (3), (4);\n"
+ + "!plan\n"
+ + "!ok\n"
+ + "\n",
+ containsString(
+ "!use foodmart\n"
+ + "values (1), (2);\n"
+ + "EnumerableValuesRel(tuples=[[{ 1 }, { 2 }]])\n"
+ + "!plan\n"
+ + "values (3), (4);\n"
+ + "EnumerableValuesRel(tuples=[[{ 3 }, { 4 }]])\n"
+ + "!plan\n"
+ + "EXPR$0\n"
+ + "3\n"
+ + "4\n"
+ + "!ok\n"
+ + "\n"));
+ }
+
+ @Test public void testPlanDisabled() {
+ check(
+ "!use foodmart\n"
+ + "!if (false) {\n"
+ + "values (1), (2);\n"
+ + "anything\n"
+ + "you like\n"
+ + "!plan\n"
+ + "!}\n"
+ + "\n",
+ containsString(
+ "!use foodmart\n"
+ + "!if (false) {\n"
+ + "values (1), (2);\n"
+ + "anything\n"
+ + "you like\n"
+ + "!plan\n"
+ + "!}\n"
+ + "\n"));
+ }
+
static void check(String input, String expected) {
check(input, CoreMatchers.equalTo(expected));
}