mirror of
https://github.com/alibaba/druid.git
synced 2023-03-04 19:17:16 +00:00
增强Parser
git-svn-id: http://code.alibabatech.com/svn/druid/trunk@133 b9813039-fb51-4c41-a8b9-e21c2acb5095
This commit is contained in:
+4
-211
@@ -15,217 +15,10 @@
|
||||
*/
|
||||
package com.alibaba.druid.sql.dialect.oracle.ast.stmt;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import com.alibaba.druid.sql.ast.statement.SQLInsertStatement;
|
||||
|
||||
import com.alibaba.druid.sql.ast.SQLExpr;
|
||||
import com.alibaba.druid.sql.ast.SQLObjectImpl;
|
||||
import com.alibaba.druid.sql.ast.SQLStatementImpl;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.OracleHint;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.visitor.OracleASTVisitor;
|
||||
import com.alibaba.druid.sql.visitor.SQLASTVisitor;
|
||||
public class OracleInsertStatement extends SQLInsertStatement {
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
public class OracleInsertStatement extends SQLStatementImpl {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private final List<OracleHint> hints = new ArrayList<OracleHint>();
|
||||
private Insert insert;
|
||||
|
||||
public OracleInsertStatement(){
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void accept0(SQLASTVisitor visitor) {
|
||||
if (visitor instanceof OracleASTVisitor) {
|
||||
accept0((OracleASTVisitor) visitor);
|
||||
return;
|
||||
}
|
||||
super.accept0(visitor);
|
||||
}
|
||||
|
||||
protected void accept0(OracleASTVisitor visitor) {
|
||||
if (visitor.visit(this)) {
|
||||
acceptChild(visitor, this.hints);
|
||||
acceptChild(visitor, this.insert);
|
||||
}
|
||||
|
||||
visitor.endVisit(this);
|
||||
}
|
||||
|
||||
public OracleInsertStatement(Insert insert){
|
||||
|
||||
this.insert = insert;
|
||||
}
|
||||
|
||||
public List<OracleHint> getHints() {
|
||||
return this.hints;
|
||||
}
|
||||
|
||||
public Insert getInsert() {
|
||||
return this.insert;
|
||||
}
|
||||
|
||||
public void setInsert(Insert insert) {
|
||||
this.insert = insert;
|
||||
}
|
||||
|
||||
public static class IntoSubQuery extends OracleInsertStatement.InsertSource {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
public IntoSubQuery(){
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void accept0(SQLASTVisitor visitor) {
|
||||
this.accept0((OracleASTVisitor) visitor);
|
||||
}
|
||||
|
||||
protected void accept0(OracleASTVisitor visitor) {
|
||||
visitor.visit(this);
|
||||
|
||||
visitor.endVisit(this);
|
||||
}
|
||||
}
|
||||
|
||||
public static class IntoValues extends OracleInsertStatement.InsertSource {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private final List<SQLExpr> values = new ArrayList<SQLExpr>();
|
||||
|
||||
public IntoValues(){
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void accept0(SQLASTVisitor visitor) {
|
||||
this.accept0((OracleASTVisitor) visitor);
|
||||
}
|
||||
|
||||
protected void accept0(OracleASTVisitor visitor) {
|
||||
if (visitor.visit(this)) {
|
||||
acceptChild(visitor, this.values);
|
||||
}
|
||||
|
||||
visitor.endVisit(this);
|
||||
}
|
||||
|
||||
public List<SQLExpr> getValues() {
|
||||
return this.values;
|
||||
}
|
||||
}
|
||||
|
||||
public static abstract class InsertSource extends SQLObjectImpl {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
public InsertSource(){
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
public static class Into extends SQLObjectImpl {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private SQLExpr target;
|
||||
private String alias;
|
||||
private final List<SQLExpr> columns = new ArrayList<SQLExpr>();
|
||||
|
||||
public Into(){
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void accept0(SQLASTVisitor visitor) {
|
||||
this.accept0((OracleASTVisitor) visitor);
|
||||
}
|
||||
|
||||
protected void accept0(OracleASTVisitor visitor) {
|
||||
if (visitor.visit(this)) {
|
||||
acceptChild(visitor, this.target);
|
||||
acceptChild(visitor, this.columns);
|
||||
}
|
||||
|
||||
visitor.endVisit(this);
|
||||
}
|
||||
|
||||
public SQLExpr getTarget() {
|
||||
return this.target;
|
||||
}
|
||||
|
||||
public void setTarget(SQLExpr target) {
|
||||
this.target = target;
|
||||
}
|
||||
|
||||
public String getAlias() {
|
||||
return this.alias;
|
||||
}
|
||||
|
||||
public void setAlias(String alias) {
|
||||
this.alias = alias;
|
||||
}
|
||||
|
||||
public List<SQLExpr> getColumns() {
|
||||
return this.columns;
|
||||
}
|
||||
}
|
||||
|
||||
public static class MultiTableInsert {
|
||||
}
|
||||
|
||||
public static class SigleTableInert extends OracleInsertStatement.Insert {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
private OracleInsertStatement.Into into;
|
||||
private OracleInsertStatement.InsertSource source;
|
||||
|
||||
public SigleTableInert(){
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void accept0(SQLASTVisitor visitor) {
|
||||
this.accept0((OracleASTVisitor) visitor);
|
||||
}
|
||||
|
||||
protected void accept0(OracleASTVisitor visitor) {
|
||||
if (visitor.visit(this)) {
|
||||
acceptChild(visitor, this.into);
|
||||
acceptChild(visitor, this.source);
|
||||
}
|
||||
|
||||
visitor.endVisit(this);
|
||||
}
|
||||
|
||||
public OracleInsertStatement.Into getInto() {
|
||||
return this.into;
|
||||
}
|
||||
|
||||
public void setInto(OracleInsertStatement.Into into) {
|
||||
this.into = into;
|
||||
}
|
||||
|
||||
public OracleInsertStatement.InsertSource getSource() {
|
||||
return this.source;
|
||||
}
|
||||
|
||||
public void setSource(OracleInsertStatement.InsertSource source) {
|
||||
this.source = source;
|
||||
}
|
||||
}
|
||||
|
||||
public static abstract class Insert extends SQLObjectImpl {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
public Insert(){
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -40,7 +40,6 @@ import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleConstraintState;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleCreateViewStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleDeleteStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleForeignKey;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OraclePLSQLCommitStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OraclePrimaryKey;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleRefDataType;
|
||||
@@ -135,18 +134,6 @@ public interface OracleASTVisitor extends SQLASTVisitor {
|
||||
|
||||
void endVisit(OracleHint x);
|
||||
|
||||
void endVisit(OracleInsertStatement x);
|
||||
|
||||
void endVisit(OracleInsertStatement.InsertSource x);
|
||||
|
||||
void endVisit(OracleInsertStatement.Into x);
|
||||
|
||||
void endVisit(OracleInsertStatement.IntoSubQuery x);
|
||||
|
||||
void endVisit(OracleInsertStatement.IntoValues x);
|
||||
|
||||
void endVisit(OracleInsertStatement.SigleTableInert x);
|
||||
|
||||
void endVisit(OracleIntervalExpr x);
|
||||
|
||||
void endVisit(SQLObjectCreateExpr x);
|
||||
@@ -267,18 +254,6 @@ public interface OracleASTVisitor extends SQLASTVisitor {
|
||||
|
||||
boolean visit(OracleHint x);
|
||||
|
||||
boolean visit(OracleInsertStatement x);
|
||||
|
||||
boolean visit(OracleInsertStatement.InsertSource x);
|
||||
|
||||
boolean visit(OracleInsertStatement.Into x);
|
||||
|
||||
boolean visit(OracleInsertStatement.IntoSubQuery x);
|
||||
|
||||
boolean visit(OracleInsertStatement.IntoValues x);
|
||||
|
||||
boolean visit(OracleInsertStatement.SigleTableInert x);
|
||||
|
||||
boolean visit(OracleIntervalExpr x);
|
||||
|
||||
boolean visit(SQLObjectCreateExpr x);
|
||||
|
||||
+4
-80
@@ -66,12 +66,6 @@ import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleConstraintState;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleCreateViewStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleDeleteStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleForeignKey;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement.InsertSource;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement.Into;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement.IntoSubQuery;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement.IntoValues;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement.SigleTableInert;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OraclePLSQLCommitStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OraclePrimaryKey;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleRefDataType;
|
||||
@@ -382,40 +376,6 @@ public class OracleOutputVisitor extends SQLASTOutputVisitor implements OracleAS
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean visit(OracleInsertStatement x) {
|
||||
print("INSERT ");
|
||||
printHints(x.getHints());
|
||||
x.getInsert().accept(this);
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean visit(OracleInsertStatement.InsertSource x) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
public boolean visit(OracleInsertStatement.Into x) {
|
||||
print("INTO ");
|
||||
x.getTarget().accept(this);
|
||||
printAlias(x.getAlias());
|
||||
if (x.getColumns().size() > 0) {
|
||||
print("(");
|
||||
printAndAccept(x.getColumns(), ", ");
|
||||
print(")");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean visit(OracleInsertStatement.IntoSubQuery x) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
public boolean visit(OracleInsertStatement.IntoValues x) {
|
||||
print("VALUES (");
|
||||
printAndAccept(x.getValues(), ", ");
|
||||
print(")");
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean visit(OracleIntervalExpr x) {
|
||||
print("INTERVAL '");
|
||||
print(x.getValue());
|
||||
@@ -562,18 +522,18 @@ public class OracleOutputVisitor extends SQLASTOutputVisitor implements OracleAS
|
||||
public boolean visit(OracleSelectHierachicalQueryClause x) {
|
||||
print("START WITH ");
|
||||
x.getStartWith().accept(this);
|
||||
|
||||
|
||||
println();
|
||||
print("CONNECT BY ");
|
||||
|
||||
|
||||
if (x.isPrior()) {
|
||||
print("PRIOR ");
|
||||
}
|
||||
|
||||
|
||||
if (x.isNoCycle()) {
|
||||
print("NOCYCLE ");
|
||||
}
|
||||
|
||||
|
||||
x.getConnectBy().accept(this);
|
||||
|
||||
return false;
|
||||
@@ -1357,36 +1317,6 @@ public class OracleOutputVisitor extends SQLASTOutputVisitor implements OracleAS
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(OracleInsertStatement x) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(InsertSource x) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(Into x) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(IntoSubQuery x) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(IntoValues x) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(SigleTableInert x) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endVisit(OracleIntervalExpr x) {
|
||||
|
||||
@@ -1517,10 +1447,4 @@ public class OracleOutputVisitor extends SQLASTOutputVisitor implements OracleAS
|
||||
|
||||
}
|
||||
|
||||
public boolean visit(OracleInsertStatement.SigleTableInert x) {
|
||||
x.getInto().accept(this);
|
||||
print(" ");
|
||||
x.getSource().accept(this);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@ import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleSelectOrderByItem;
|
||||
import com.alibaba.druid.sql.parser.Lexer;
|
||||
import com.alibaba.druid.sql.parser.ParserException;
|
||||
import com.alibaba.druid.sql.parser.SQLExprParser;
|
||||
import com.alibaba.druid.sql.parser.SQLSelectParser;
|
||||
import com.alibaba.druid.sql.parser.Token;
|
||||
|
||||
public class OracleExprParser extends SQLExprParser {
|
||||
@@ -67,7 +68,14 @@ public class OracleExprParser extends SQLExprParser {
|
||||
String name = ":" + lexer.numberString();
|
||||
lexer.nextToken();
|
||||
return new SQLVariantRefExpr(name);
|
||||
} else{
|
||||
} else if (lexer.token() == Token.IDENTIFIER) {
|
||||
String name = lexer.stringVal();
|
||||
if (name.startsWith("B")) {
|
||||
lexer.nextToken();
|
||||
return new SQLVariantRefExpr(":" + name);
|
||||
}
|
||||
throw new ParserException("syntax error : " + lexer.token());
|
||||
} else {
|
||||
throw new ParserException("syntax error : " + lexer.token());
|
||||
}
|
||||
default:
|
||||
|
||||
@@ -15,12 +15,10 @@
|
||||
*/
|
||||
package com.alibaba.druid.sql.dialect.oracle.parser;
|
||||
|
||||
import com.alibaba.druid.sql.ast.SQLStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.stmt.OracleInsertStatement;
|
||||
import com.alibaba.druid.sql.parser.Lexer;
|
||||
import com.alibaba.druid.sql.parser.ParserException;
|
||||
import com.alibaba.druid.sql.parser.SQLExprParser;
|
||||
import com.alibaba.druid.sql.parser.SQLStatementParser;
|
||||
import com.alibaba.druid.sql.parser.Token;
|
||||
|
||||
public class OracleInsertParser extends SQLStatementParser {
|
||||
|
||||
@@ -32,64 +30,7 @@ public class OracleInsertParser extends SQLStatementParser {
|
||||
super(lexer);
|
||||
}
|
||||
|
||||
public SQLStatement parseInsert() throws ParserException {
|
||||
throw new ParserException("TODO");
|
||||
}
|
||||
|
||||
public OracleInsertStatement parseOracleInsert() throws ParserException {
|
||||
accept(Token.INSERT);
|
||||
|
||||
OracleInsertStatement insertStatement = new OracleInsertStatement();
|
||||
|
||||
parseHints(insertStatement);
|
||||
|
||||
if (lexer.token() == Token.INTO) {
|
||||
OracleInsertStatement.SigleTableInert sigleTableInsert = new OracleInsertStatement.SigleTableInert();
|
||||
sigleTableInsert.setInto(parseInto());
|
||||
|
||||
if (lexer.token() == Token.VALUES) {
|
||||
OracleInsertStatement.IntoValues values = new OracleInsertStatement.IntoValues();
|
||||
|
||||
lexer.nextToken();
|
||||
accept(Token.LPAREN);
|
||||
this.exprParser.exprList(values.getValues());
|
||||
accept(Token.RPAREN);
|
||||
|
||||
sigleTableInsert.setSource(values);
|
||||
}
|
||||
|
||||
if (identifierEquals("LOG")) {
|
||||
throw new ParserException("TODO");
|
||||
}
|
||||
|
||||
insertStatement.setInsert(sigleTableInsert);
|
||||
} else {
|
||||
if (lexer.token() == Token.ALL) {
|
||||
throw new ParserException("TODO");
|
||||
}
|
||||
throw new ParserException("syntax error");
|
||||
}
|
||||
|
||||
return insertStatement;
|
||||
}
|
||||
|
||||
private OracleInsertStatement.Into parseInto() throws ParserException {
|
||||
accept(Token.INTO);
|
||||
|
||||
OracleInsertStatement.Into into = new OracleInsertStatement.Into();
|
||||
into.setTarget(this.exprParser.expr());
|
||||
into.setAlias(as());
|
||||
|
||||
if (lexer.token() == (Token.LPAREN)) {
|
||||
lexer.nextToken();
|
||||
this.exprParser.exprList(into.getColumns());
|
||||
accept(Token.RPAREN);
|
||||
}
|
||||
|
||||
return into;
|
||||
}
|
||||
|
||||
private void parseHints(OracleInsertStatement parseInsert) throws ParserException {
|
||||
if (lexer.token() == Token.HINT) throw new ParserException("TODO");
|
||||
protected SQLExprParser createExprParser() {
|
||||
return new OracleExprParser(lexer);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -153,7 +153,7 @@ public class SQLStatementParser extends SQLParser {
|
||||
insertStatement.setValues(values);
|
||||
accept(Token.RPAREN);
|
||||
} else if (lexer.token() == (Token.SELECT)) {
|
||||
SQLQueryExpr queryExpr = (SQLQueryExpr) this.exprParser.expr();
|
||||
SQLQueryExpr queryExpr = (SQLQueryExpr) this.createExprParser().expr();
|
||||
insertStatement.setQuery(queryExpr);
|
||||
}
|
||||
return insertStatement;
|
||||
|
||||
@@ -11,13 +11,11 @@ import junit.framework.TestCase;
|
||||
import com.alibaba.druid.sql.ast.SQLStatement;
|
||||
import com.alibaba.druid.sql.dialect.oracle.ast.visitor.OracleOutputVisitor;
|
||||
import com.alibaba.druid.sql.dialect.oracle.parser.OracleStatementParser;
|
||||
import com.alibaba.druid.sql.parser.Lexer;
|
||||
import com.alibaba.druid.sql.parser.Token;
|
||||
import com.alibaba.druid.util.JdbcUtils;
|
||||
|
||||
public class OracleSQLParserTest extends TestCase {
|
||||
|
||||
public void test_1() throws Exception {
|
||||
public void f_test_1() throws Exception {
|
||||
InputStream is = null;
|
||||
|
||||
is = Thread.currentThread().getContextClassLoader().getResourceAsStream("bvt/parser/oracle-0.txt");
|
||||
|
||||
Reference in New Issue
Block a user