Repository: hive
Updated Branches:
  refs/heads/branch-1 9285349fd -> ad54cce7d


HIVE-11100: Beeline should escape semi-colon in queries (Chaoyu via Xuefu)


Project: http://git-wip-us.apache.org/repos/asf/hive/repo
Commit: http://git-wip-us.apache.org/repos/asf/hive/commit/ad54cce7
Tree: http://git-wip-us.apache.org/repos/asf/hive/tree/ad54cce7
Diff: http://git-wip-us.apache.org/repos/asf/hive/diff/ad54cce7

Branch: refs/heads/branch-1
Commit: ad54cce7d1454618f4d239fce9edf16b11283933
Parents: 9285349
Author: xzhang <xzhang@xzdt>
Authored: Tue Jun 30 10:43:10 2015 -0700
Committer: xzhang <xzhang@xzdt>
Committed: Tue Jun 30 10:43:46 2015 -0700

----------------------------------------------------------------------
 .../java/org/apache/hive/beeline/Commands.java  | 22 +++--
 .../hive/beeline/TestBeeLineWithArgs.java       | 87 ++++++++++++++++++++
 2 files changed, 103 insertions(+), 6 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/hive/blob/ad54cce7/beeline/src/java/org/apache/hive/beeline/Commands.java
----------------------------------------------------------------------
diff --git a/beeline/src/java/org/apache/hive/beeline/Commands.java 
b/beeline/src/java/org/apache/hive/beeline/Commands.java
index 903849c..75e1063 100644
--- a/beeline/src/java/org/apache/hive/beeline/Commands.java
+++ b/beeline/src/java/org/apache/hive/beeline/Commands.java
@@ -43,6 +43,7 @@ import java.sql.ResultSet;
 import java.sql.SQLException;
 import java.sql.Statement;
 import java.sql.SQLWarning;
+import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Iterator;
 import java.util.LinkedList;
@@ -796,15 +797,24 @@ public class Commands {
     }
 
     line = line.trim();
-    String[] cmds;
+    List<String> cmdList = new ArrayList<String>();
     if (entireLineAsCommand) {
-      cmds = new String[1];
-      cmds[0] = line;
+      cmdList.add(line);
     } else {
-      cmds = line.split(";");
+      StringBuffer command = new StringBuffer();
+      for (String cmdpart: line.split(";")) {
+        if (cmdpart.endsWith("\\")) {
+          command.append(cmdpart.substring(0, cmdpart.length() 
-1)).append(";");
+          continue;
+        } else {
+          command.append(cmdpart);
+        }
+        cmdList.add(command.toString());
+        command.setLength(0);
+      }
     }
-    for (int i = 0; i < cmds.length; i++) {
-      String sql = cmds[i].trim();
+    for (int i = 0; i < cmdList.size(); i++) {
+      String sql = cmdList.get(i).trim();
       if (sql.length() != 0) {
         if (beeLine.isComment(sql)) {
           //skip this and rest cmds in the line

http://git-wip-us.apache.org/repos/asf/hive/blob/ad54cce7/itests/hive-unit/src/test/java/org/apache/hive/beeline/TestBeeLineWithArgs.java
----------------------------------------------------------------------
diff --git 
a/itests/hive-unit/src/test/java/org/apache/hive/beeline/TestBeeLineWithArgs.java
 
b/itests/hive-unit/src/test/java/org/apache/hive/beeline/TestBeeLineWithArgs.java
index f0795d2..19ee621 100644
--- 
a/itests/hive-unit/src/test/java/org/apache/hive/beeline/TestBeeLineWithArgs.java
+++ 
b/itests/hive-unit/src/test/java/org/apache/hive/beeline/TestBeeLineWithArgs.java
@@ -194,6 +194,31 @@ public class TestBeeLineWithArgs {
   }
 
   /**
+   * Attempt to execute the enclosed query with the -e option to BeeLine
+   * Test for presence of an expected pattern
+   * in the output (stdout or stderr), fail if not found
+   * Print PASSED or FAILED
+   * @param expectedPattern Text to look for in command output/error
+   * @param shouldMatch true if the pattern should be found, false if it 
should not
+   * @throws Exception on command execution error
+   */
+  private void testCommandEnclosedQuery(String enclosedQuery, String 
expectedPattern,
+      boolean shouldMatch, List<String> argList) throws Throwable {
+
+    List<String> copy = new ArrayList<String>(argList);
+    copy.add("-e");
+    copy.add(enclosedQuery);
+
+    String output = testCommandLineScript(copy, null);
+    boolean matches = output.contains(expectedPattern);
+    if (shouldMatch != matches) {
+      //failed
+      fail("Output" + output + " should" +  (shouldMatch ? "" : " not") +
+          " contain " + expectedPattern);
+    }
+  }
+
+  /**
    * Test that BeeLine will read comment lines that start with whitespace
    * @throws Throwable
    */
@@ -652,4 +677,66 @@ public class TestBeeLineWithArgs {
     final String EXPECTED_PATTERN = "Parsing command";
     testScriptFile(SCRIPT_TEXT, EXPECTED_PATTERN, false, 
getBaseArgs(miniHS2.getBaseJdbcURL()));
   }
+
+  @Test
+  public void testMultiCommandsInOneline() throws Throwable {
+    final String SCRIPT_TEXT = "drop table if exists multiCmdTbl;create table 
multiCmdTbl "
+        +"(key int);show tables; --multicommands in one line";
+    final String EXPECTED_PATTERN = " multicmdtbl ";
+    List<String> argList = getBaseArgs(miniHS2.getBaseJdbcURL());
+    testScriptFile(SCRIPT_TEXT, EXPECTED_PATTERN, true, argList);
+
+    final String SCRIPT_TEXT_DROP = "drop table multiCmdTbl;show tables;";
+    testScriptFile(SCRIPT_TEXT_DROP, EXPECTED_PATTERN, false, argList);
+  }
+
+  @Test
+  public void testMultiCommandsInOneEnclosedQuery() throws Throwable {
+    final String QUERY_TEXT = "drop table if exists multiCmdTbl;create table 
multiCmdTbl "
+        +"(key int);show tables; --multicommands in one line";
+    final String EXPECTED_PATTERN = " multicmdtbl ";
+    List<String> argList = getBaseArgs(miniHS2.getBaseJdbcURL());
+    testCommandEnclosedQuery(QUERY_TEXT, EXPECTED_PATTERN, true, argList);
+
+    final String QUERY_TEXT_DROP = "drop table multiCmdTbl;show tables;";
+    testCommandEnclosedQuery(QUERY_TEXT_DROP, EXPECTED_PATTERN, false, 
argList);
+  }
+
+  @Test
+  public void testOneCommandInMultiLines() throws Throwable {
+    final String SCRIPT_TEXT = "drop table if exists multiCmdTbl;create table 
\nmultiCmdTbl "
+        + "(key int);show tables; --one command in multiple lines";
+    final String EXPECTED_PATTERN = " multicmdtbl ";
+    List<String> argList = getBaseArgs(miniHS2.getBaseJdbcURL());
+    testScriptFile(SCRIPT_TEXT, EXPECTED_PATTERN, true, argList);
+
+    final String SCRIPT_TEXT_DROP = "drop table\nmultiCmdTbl;show tables;";
+    testScriptFile(SCRIPT_TEXT_DROP, EXPECTED_PATTERN, false, argList);
+  }
+
+  @Test
+  public void testEscapeSemiColonInQueries() throws Throwable {
+    final String SCRIPT_TEXT = "drop table if exists multiCmdTbl;create table 
multiCmdTbl "
+        + "(key int, value string) ROW FORMAT DELIMITED FIELDS TERMINATED BY 
'\\;' LINES "
+        + " TERMINATED BY '\\n';show tables; --one command in multiple lines";
+    final String EXPECTED_PATTERN = " multicmdtbl ";
+    List<String> argList = getBaseArgs(miniHS2.getBaseJdbcURL());
+    testScriptFile(SCRIPT_TEXT, EXPECTED_PATTERN, true, argList);
+
+    final String SCRIPT_TEXT_DROP = "drop table\nmultiCmdTbl;show tables;";
+    testScriptFile(SCRIPT_TEXT_DROP, EXPECTED_PATTERN, false, argList);
+  }
+
+  @Test
+  public void testEscapeSemiColonInEnclosedQuery() throws Throwable {
+    final String QUERY_TEXT = "drop table if exists multiCmdTbl;create table 
multiCmdTbl "
+        + "(key int, value string) ROW FORMAT DELIMITED FIELDS TERMINATED BY 
'\\;' LINES "
+        + " TERMINATED BY '\\n';show tables;";
+    final String EXPECTED_PATTERN = " multicmdtbl ";
+    List<String> argList = getBaseArgs(miniHS2.getBaseJdbcURL());
+    testCommandEnclosedQuery(QUERY_TEXT, EXPECTED_PATTERN, true, argList);
+
+    final String QUERY_TEXT_DROP = "drop table multiCmdTbl;show tables;";
+    testCommandEnclosedQuery(QUERY_TEXT_DROP, EXPECTED_PATTERN, false, 
argList);
+  }
 }

Reply via email to