This commit is contained in:
shenfeng
2022-06-08 19:42:26 +08:00
parent c1e1f4e0a2
commit 042259bb68
5 changed files with 60 additions and 30 deletions
@@ -1752,8 +1752,7 @@ public class MySqlStatementParser extends SQLStatementParser {
if (lexer.token() == Token.IDENTIFIER) {
String label = lexer.stringVal();
char ch = lexer.current();
int bp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
lexer.nextToken();
if (lexer.token() == Token.VARIANT && lexer.stringVal().equals(":")) {
lexer.nextToken();
@@ -1773,7 +1772,7 @@ public class MySqlStatementParser extends SQLStatementParser {
}
return true;
} else {
lexer.reset(bp, ch, Token.IDENTIFIER);
lexer.reset(savePoint);
}
}
@@ -7909,26 +7908,24 @@ public class MySqlStatementParser extends SQLStatementParser {
if (dbType != DbType.mysql) {
while (lexer.token() == Token.COMMA) {
char markChar = lexer.current();
int markBp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
lexer.nextToken();
if (lexer.identifierEquals(FnvHash.Constants.CHANGE)
|| lexer.identifierEquals(FnvHash.Constants.MODIFY)) {
lexer.reset(markBp, markChar, Token.COMMA);
lexer.reset(savePoint);
break;
}
if (lexer.token() == Token.IDENTIFIER) {
if ("ADD".equalsIgnoreCase(lexer.stringVal())) {
lexer.reset(markBp, markChar, Token.COMMA);
lexer.reset(savePoint);
break;
}
name = exprParser.name();
name.setParent(item);
item.addColumn(name);
} else {
lexer.reset(markBp, markChar, Token.COMMA);
lexer.reset(savePoint);
break;
}
}
@@ -8718,12 +8715,11 @@ public class MySqlStatementParser extends SQLStatementParser {
// select
if (lexer.token() == Token.LPAREN) {
char ch = lexer.current();
int bp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
lexer.nextToken();
if (lexer.token() == Token.SELECT) {
lexer.reset(bp, ch, Token.LPAREN);
lexer.reset(savePoint);
statementList.add(this.parseSelect());
continue;
} else {
@@ -8811,8 +8807,7 @@ public class MySqlStatementParser extends SQLStatementParser {
if (lexer.token() == Token.IDENTIFIER) {
String label = lexer.stringVal();
char ch = lexer.current();
int bp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
lexer.nextToken();
if (lexer.token() == Token.VARIANT && lexer.stringVal().equals(":")) {
lexer.nextToken();
@@ -8831,7 +8826,7 @@ public class MySqlStatementParser extends SQLStatementParser {
}
continue;
} else {
lexer.reset(bp, ch, Token.IDENTIFIER);
lexer.reset(savePoint);
}
}
@@ -9040,30 +9035,29 @@ public class MySqlStatementParser extends SQLStatementParser {
* parse declare statement
*/
public SQLStatement parseDeclare() {
char markChar = lexer.current();
int markBp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
lexer.nextToken();
if (lexer.token() == Token.CONTINUE) {
lexer.reset(markBp, markChar, Token.DECLARE);
lexer.reset(savePoint);
return this.parseDeclareHandler();
}
lexer.nextToken();
if (lexer.token() == Token.CURSOR) {
lexer.reset(markBp, markChar, Token.DECLARE);
lexer.reset(savePoint);
return this.parseCursorDeclare();
} else if (lexer.identifierEquals("HANDLER")) {
//DECLARE异常处理程序 [add by zhujun 2016-04-16]
lexer.reset(markBp, markChar, Token.DECLARE);
lexer.reset(savePoint);
return this.parseDeclareHandler();
} else if (lexer.token() == Token.CONDITION) {
//DECLARE异常 [add by zhujun 2016-04-17]
lexer.reset(markBp, markChar, Token.DECLARE);
lexer.reset(savePoint);
return this.parseDeclareCondition();
} else {
lexer.reset(markBp, markChar, Token.DECLARE);
lexer.reset(savePoint);
}
MySqlDeclareStatement stmt = new MySqlDeclareStatement();
@@ -9274,12 +9268,11 @@ public class MySqlStatementParser extends SQLStatementParser {
// select
if (lexer.token() == Token.LPAREN) {
char ch = lexer.current();
int bp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
lexer.nextToken();
if (lexer.token() == Token.SELECT) {
lexer.reset(bp, ch, Token.LPAREN);
lexer.reset(savePoint);
return this.parseSelect();
} else {
throw new ParserException("TODO. " + lexer.info());
@@ -178,6 +178,7 @@ public class Lexer {
public static class SavePoint {
int bp;
int startPos;
int sp;
int np;
char ch;
@@ -191,7 +192,13 @@ public class Lexer {
return keywords;
}
//出现多次调用mark()后调用reset()会有问题
@Deprecated
public SavePoint mark() {
return this.savePoint = markOut();
}
public SavePoint markOut() {
SavePoint savePoint = new SavePoint();
savePoint.bp = pos;
savePoint.sp = bufPos;
@@ -201,9 +208,11 @@ public class Lexer {
savePoint.stringVal = stringVal;
savePoint.hash = hash;
savePoint.hash_lower = hash_lower;
return this.savePoint = savePoint;
savePoint.startPos = startPos;
return savePoint;
}
public void reset(SavePoint savePoint) {
this.pos = savePoint.bp;
this.bufPos = savePoint.sp;
@@ -213,8 +222,10 @@ public class Lexer {
this.stringVal = savePoint.stringVal;
this.hash = savePoint.hash;
this.hash_lower = savePoint.hash_lower;
this.startPos = savePoint.startPos;
}
//出现多次调用mark()后调用reset()会有问题
@Deprecated
public void reset() {
this.reset(this.savePoint);
}
@@ -3123,6 +3134,8 @@ public class Lexer {
return this.ch;
}
//todo fix reset reset字段会导致lexer的游标不对齐 不建议使用
@Deprecated
public void reset(int mark, char markChar, Token token) {
this.pos = mark;
this.ch = markChar;
@@ -87,6 +87,7 @@ public class SQLSelectListCache {
queryBlock.setCachedSelectList(entry.printSql, entry.printSqlHash);
int len = pos + block.length();
//todo fix reset
lexer.reset(len, text.charAt(len), Token.FROM);
return true;
}
@@ -570,8 +570,7 @@ public class SQLStatementParser extends SQLParser {
}
if (lexer.token == Token.LPAREN) {
char markChar = lexer.current();
int markBp = lexer.bp();
Lexer.SavePoint savePoint = lexer.markOut();
int parenCount = 0;
do {
@@ -585,7 +584,7 @@ public class SQLStatementParser extends SQLParser {
}
if (lexer.token == Token.SELECT) {
lexer.reset(markBp, markChar, Token.LPAREN);
lexer.reset(savePoint);
SQLStatement stmt = parseSelect();
statementList.add(stmt);
continue;
@@ -15,7 +15,12 @@
*/
package com.alibaba.druid.sql.parser;
import com.alibaba.druid.sql.ast.SQLStatement;
import com.alibaba.druid.sql.dialect.mysql.parser.MySqlStatementParser;
import junit.framework.TestCase;
import org.junit.Assert;
import java.util.List;
public class SQLLexerTest2 extends TestCase {
@@ -67,5 +72,24 @@ public class SQLLexerTest2 extends TestCase {
}
}
}
public void test_lexer_error_info(){
String line1 ="SELECT *";
String line2 ="FORM a";
String sql = line1 + "\n"+line2;
MySqlStatementParser parser=new MySqlStatementParser(sql);
Exception exception = null;
try {
parser.parseStatementList();
} catch (Exception e) {
exception = e;
}
assert exception != null;
Assert.assertEquals("not supported.pos 13, line 2, column 2, token IDENTIFIER FORM", exception.getMessage());
}
}