You seem to be interested in the expr
production. In that case, you can attach a base listener to the parse tree and override its enterExpr
method:
String sql = "select * from table where a = \"g\" and b = \"h\"";
SQLiteLexer lexer = new SQLiteLexer(new ANTLRInputStream(sql));
SQLiteParser parser = new SQLiteParser(new CommonTokenStream(lexer));
ParseTree tree = parser.select_stmt();
ParseTreeWalker.DEFAULT.walk(new SQLiteBaseListener(){
@Override
public void enterExpr(@NotNull SQLiteParser.ExprContext ctx) {
if (ctx.children.size() == 3 && (ctx.children.get(1) instanceof TerminalNode)) {
String leftHandSide = ctx.children.get(0).getText();
String operator = ctx.children.get(1).getText();
String rightHandSide = ctx.children.get(2).getText();
System.out.printf("leftHandSide=%s, operator=%s, leftHandSide=%s\n",
leftHandSide, operator, rightHandSide);
}
}
}, tree);
which will print the following:
leftHandSide=a="g", operator=and, leftHandSide=b="h"
leftHandSide=a, operator==, leftHandSide="g"
leftHandSide=b, operator==, leftHandSide="h"
Instead of performing such an ugly (ctx.children.size() == 3 && (ctx.children.get(1) instanceof TerminalNode))
, you can (greatly) improve things by adding labels to the grammar:
ANTLR 4 tree inject/rewrite operator
Also note that the operator precedence in the grammar is wrong, see the following pull request:
https://github.com/antlr/grammars-v4/pull/47
The grammar with fixed operator precedence can also be found here:
https://github.com/bkiers/sqlite-parser/blob/master/src/main/antlr4/nl/bigo/sqliteparser/SQLite.g4