public List<String> splitSql(String text) {
    List<String> queries = new ArrayList<>();
    StringBuilder query = new StringBuilder();
    char character;

    boolean multiLineComment = false;
    boolean singleLineComment = false;
    boolean singleQuoteString = false;
    boolean doubleQuoteString = false;

    for (int index = 0; index < text.length(); index++) {
      character = text.charAt(index);

      // end of single line comment
      if (singleLineComment && (character == '\n')) {
        singleLineComment = false;
        query.append(character);
        if (index == (text.length() - 1) && !query.toString().trim().isEmpty()) {
          // add query when it is the end of sql.
          queries.add(query.toString());
        }
        continue;
      }

      // end of multiple line comment
      if (multiLineComment && (index - 1) >= 0 && text.charAt(index - 1) == '/'
              && (index - 2) >= 0 && text.charAt(index - 2) == '*') {
        multiLineComment = false;
      }

      if (character == '\'' && !(singleLineComment || multiLineComment)) {
        if (singleQuoteString) {
          singleQuoteString = false;
        } else if (!doubleQuoteString) {
          singleQuoteString = true;
        }
      }

      if (character == '"' && !(singleLineComment || multiLineComment)) {
        if (doubleQuoteString && index > 0) {
          doubleQuoteString = false;
        } else if (!singleQuoteString) {
          doubleQuoteString = true;
        }
      }

      if (!singleQuoteString && !doubleQuoteString && !multiLineComment && !singleLineComment
              && text.length() > (index + 1)) {
        if (isSingleLineComment(text.charAt(index), text.charAt(index + 1))) {
          singleLineComment = true;
        } else if (text.charAt(index) == '/' && text.length() > (index + 2)
                && text.charAt(index + 1) == '*' && text.charAt(index + 2) != '+') {
          multiLineComment = true;
        }
      }

      if (character == ';' && !singleQuoteString && !doubleQuoteString && !multiLineComment && !singleLineComment) {
        // meet the end of semicolon
        if (!query.toString().trim().isEmpty()) {
          queries.add(query.toString());
          query = new StringBuilder();
        }
      } else if (index == (text.length() - 1)) {
        // meet the last character
        if ((!singleLineComment && !multiLineComment)) {
          query.append(character);
        }

        if (!query.toString().trim().isEmpty()) {
          queries.add(query.toString());
          query = new StringBuilder();
        }
      } else if (!singleLineComment && !multiLineComment) {
        // normal case, not in single line comment and not in multiple line comment
        query.append(character);
      } else if (character == '\n') {
        query.append(character);
      }
    }

    List<String> refinedQueries = new ArrayList<>();
    for (int i = 0; i < queries.size(); ++i) {
      String emptyLine = "";
      if (i > 0) {
        emptyLine = createEmptyLine(refinedQueries.get(i-1));
      }
      if (isSingleLineComment(queries.get(i)) || isMultipleLineComment(queries.get(i))) {
        // refine the last refinedQuery
        if (refinedQueries.size() > 0) {
          String lastRefinedQuery = refinedQueries.get(refinedQueries.size() - 1);
          refinedQueries.set(refinedQueries.size() - 1,
                  lastRefinedQuery + createEmptyLine(queries.get(i)));
        }
      } else {
        String refinedQuery = emptyLine + queries.get(i);
        refinedQueries.add(refinedQuery);
      }
    }

    return refinedQueries;
  }
@Test
  void testQuoteInComment() {
    SqlSplitter sqlSplitter = new SqlSplitter();
    List<String> sqls = sqlSplitter.splitSql("show tables;-- comment_1'\ndescribe table_1");
    assertEquals(2, sqls.size());
    assertEquals("show tables", sqls.get(0));
    assertEquals("\ndescribe table_1", sqls.get(1));

    sqls = sqlSplitter.splitSql("show tables;-- comment_1\"\ndescribe table_1");
    assertEquals(2, sqls.size());
    assertEquals("show tables", sqls.get(0));
    assertEquals("\ndescribe table_1", sqls.get(1));

    sqls = sqlSplitter.splitSql("show tables;/* comment_1' */\ndescribe table_1");
    assertEquals(2, sqls.size());
    assertEquals("show tables", sqls.get(0));
    assertEquals("\ndescribe table_1", sqls.get(1));

    sqls = sqlSplitter.splitSql("show tables;/* comment_1\" */\ndescribe table_1");
    assertEquals(2, sqls.size());
    assertEquals("show tables", sqls.get(0));
    assertEquals("\ndescribe table_1", sqls.get(1));
  }