From 7ae82934e4c46a171216c78789ad2017389537b3 Mon Sep 17 00:00:00 2001 From: wenshao Date: Mon, 15 Jun 2015 11:11:14 +0800 Subject: [PATCH] improved sql parser for odps --- .../odps/ast/OdpsCreateTableStatement.java | 18 +++++++++++--- .../odps/parser/OdpsCreateTableParser.java | 13 ++++++++++ .../odps/visitor/OdpsOutputVisitor.java | 5 ++++ .../bvt/sql/odps/OdpsCreateTableTest2.java | 24 +++++++++++++++++++ 4 files changed, 57 insertions(+), 3 deletions(-) create mode 100644 src/test/java/com/alibaba/druid/bvt/sql/odps/OdpsCreateTableTest2.java diff --git a/src/main/java/com/alibaba/druid/sql/dialect/odps/ast/OdpsCreateTableStatement.java b/src/main/java/com/alibaba/druid/sql/dialect/odps/ast/OdpsCreateTableStatement.java index 38a522a415..2a84066af0 100644 --- a/src/main/java/com/alibaba/druid/sql/dialect/odps/ast/OdpsCreateTableStatement.java +++ b/src/main/java/com/alibaba/druid/sql/dialect/odps/ast/OdpsCreateTableStatement.java @@ -23,6 +23,7 @@ import com.alibaba.druid.sql.ast.SQLName; import com.alibaba.druid.sql.ast.statement.SQLColumnDefinition; import com.alibaba.druid.sql.ast.statement.SQLCreateTableStatement; import com.alibaba.druid.sql.ast.statement.SQLExprTableSource; +import com.alibaba.druid.sql.ast.statement.SQLSelect; import com.alibaba.druid.sql.dialect.odps.visitor.OdpsASTVisitor; import com.alibaba.druid.sql.visitor.SQLASTVisitor; import com.alibaba.druid.util.JdbcConstants; @@ -36,9 +37,11 @@ public class OdpsCreateTableStatement extends SQLCreateTableStatement { protected List partitionColumns = new ArrayList(2); protected SQLExpr lifecycle; - - public OdpsCreateTableStatement() { - super (JdbcConstants.ODPS); + + protected SQLSelect select; + + public OdpsCreateTableStatement(){ + super(JdbcConstants.ODPS); } public SQLExprTableSource getLike() { @@ -73,6 +76,14 @@ public class OdpsCreateTableStatement extends SQLCreateTableStatement { this.lifecycle = lifecycle; } + public SQLSelect getSelect() { + return select; + } + + public void setSelect(SQLSelect select) { + this.select = select; + } + @Override protected void accept0(SQLASTVisitor visitor) { accept0((OdpsASTVisitor) visitor); @@ -84,6 +95,7 @@ public class OdpsCreateTableStatement extends SQLCreateTableStatement { this.acceptChild(visitor, tableElementList); this.acceptChild(visitor, partitionColumns); this.acceptChild(visitor, lifecycle); + this.acceptChild(visitor, select); } visitor.endVisit(this); } diff --git a/src/main/java/com/alibaba/druid/sql/dialect/odps/parser/OdpsCreateTableParser.java b/src/main/java/com/alibaba/druid/sql/dialect/odps/parser/OdpsCreateTableParser.java index c17837fd3b..1013714fd5 100644 --- a/src/main/java/com/alibaba/druid/sql/dialect/odps/parser/OdpsCreateTableParser.java +++ b/src/main/java/com/alibaba/druid/sql/dialect/odps/parser/OdpsCreateTableParser.java @@ -18,6 +18,7 @@ package com.alibaba.druid.sql.dialect.odps.parser; import com.alibaba.druid.sql.ast.SQLName; import com.alibaba.druid.sql.ast.statement.SQLColumnDefinition; import com.alibaba.druid.sql.ast.statement.SQLCreateTableStatement; +import com.alibaba.druid.sql.ast.statement.SQLSelect; import com.alibaba.druid.sql.dialect.odps.ast.OdpsCreateTableStatement; import com.alibaba.druid.sql.parser.ParserException; import com.alibaba.druid.sql.parser.SQLCreateTableParser; @@ -52,11 +53,23 @@ public class OdpsCreateTableParser extends SQLCreateTableParser { } stmt.setName(this.exprParser.name()); + + if (identifierEquals("LIFECYCLE")) { + lexer.nextToken(); + stmt.setLifecycle(this.exprParser.expr()); + } if (lexer.token() == Token.LIKE) { lexer.nextToken(); SQLName name = this.exprParser.name(); stmt.setLike(name); + } else if (lexer.token() == Token.AS) { + lexer.nextToken(); + + OdpsSelectParser selectParser = new OdpsSelectParser(this.exprParser); + SQLSelect select = selectParser.select(); + + stmt.setSelect(select); } else { accept(Token.LPAREN); diff --git a/src/main/java/com/alibaba/druid/sql/dialect/odps/visitor/OdpsOutputVisitor.java b/src/main/java/com/alibaba/druid/sql/dialect/odps/visitor/OdpsOutputVisitor.java index 86a6244d5f..afde1c53bb 100644 --- a/src/main/java/com/alibaba/druid/sql/dialect/odps/visitor/OdpsOutputVisitor.java +++ b/src/main/java/com/alibaba/druid/sql/dialect/odps/visitor/OdpsOutputVisitor.java @@ -101,6 +101,11 @@ public class OdpsOutputVisitor extends SQLASTOutputVisitor implements OdpsASTVis print("LIFECYCLE "); x.getLifecycle().accept(this); } + + if (x.getSelect() != null) { + println(); + x.getSelect().accept(this); + } return false; } diff --git a/src/test/java/com/alibaba/druid/bvt/sql/odps/OdpsCreateTableTest2.java b/src/test/java/com/alibaba/druid/bvt/sql/odps/OdpsCreateTableTest2.java new file mode 100644 index 0000000000..b33be6d2a8 --- /dev/null +++ b/src/test/java/com/alibaba/druid/bvt/sql/odps/OdpsCreateTableTest2.java @@ -0,0 +1,24 @@ +package com.alibaba.druid.bvt.sql.odps; + +import junit.framework.TestCase; + +import org.junit.Assert; + +import com.alibaba.druid.sql.SQLUtils; +import com.alibaba.druid.sql.ast.SQLStatement; +import com.alibaba.druid.sql.dialect.odps.parser.OdpsStatementParser; +import com.alibaba.druid.sql.parser.Token; + +public class OdpsCreateTableTest2 extends TestCase { + + public void test_0() throws Exception { + String sql = "CREATE TABLE sale_detail as select * from dual;"; + OdpsStatementParser parser = new OdpsStatementParser(sql); + SQLStatement stmt = parser.parseStatementList().get(0); + parser.match(Token.EOF); + String output = SQLUtils.toOdpsString(stmt); + Assert.assertEquals("CREATE TABLE sale_detailsale_detail" + + "\nSELECT *" // + + "\nFROM dual", output); + } +}