ExpressionTagQueryParser extends TagQueryBaseListener implements ANTLRErrorListener { public String parse(String expression) throws Exception { evalsPostfix = new ArrayList<>(); stack = new Stack<>(); error = false; errorMsg = null; ANTLRInputStream input = new ANTLRInputStream(expression); TagQueryLexer tql = new TagQueryLexer(input); tql.addErrorListener(this); CommonTokenStream tokens = new CommonTokenStream(tql); TagQueryParser parser = new TagQueryParser(tokens); ParseTree parseTree = parser.tagquery(); ParseTreeWalker.DEFAULT.walk(this, parseTree); if (error) { throw new IllegalArgumentException("Expression [" + expression + "] is malformed. Msg: " + errorMsg); } if (log.isDebugEnabled()) { log.debugf("Expression [%s] evaluated as [%s]", expression, evalsPostfix); } return prefix(evalsPostfix); } ExpressionTagQueryParser(ExpressionTagResolver resolver); Set<String> resolve(String expression); String parse(String expression); @Override void syntaxError(Recognizer<?, ?> recognizer, Object offendingSymbol, int line, int charPositionInLine, String msg, RecognitionException e); @Override void reportAmbiguity(Parser recognizer, DFA dfa, int startIndex, int stopIndex, boolean exact, BitSet ambigAlts, ATNConfigSet configs); @Override void reportAttemptingFullContext(Parser recognizer, DFA dfa, int startIndex, int stopIndex, BitSet conflictingAlts, ATNConfigSet configs); @Override void reportContextSensitivity(Parser recognizer, DFA dfa, int startIndex, int stopIndex, int prediction, ATNConfigSet configs); @Override void visitErrorNode(ErrorNode node); @Override void enterObject(TagQueryParser.ObjectContext ctx); @Override void exitObject(TagQueryParser.ObjectContext ctx);  }
@Test public void t04_complexGrouping() throws Exception { String e1 = "(tagA and not tagB) and (not tagC or tagD)"; assertEquals("and(and(tagA, not tagB), or(tagD, not tagC))", parser.parse(e1)); String e2 = "(not tagB and tagA) and (not tagC or tagD)"; assertEquals("and(and(tagA, not tagB), or(tagD, not tagC))", parser.parse(e2)); String e3 = "(not tagA and (not tagB and tagC)) and tagD"; assertEquals("and(tagD, and(and(tagC, not tagB), not tagA))", parser.parse(e3)); String e4 = "((not tagA and (not tagB and tagC)) and tagD) and tagE"; assertEquals("and(tagE, and(tagD, and(and(tagC, not tagB), not tagA)))", parser.parse(e4)); }
@Test public void t06_existUnnecessaryParentheses() throws Exception { String e1 = "((tagA and not tagB) and ((not tagC or tagD)))"; assertEquals("and(and(tagA, not tagB), or(tagD, not tagC))", parser.parse(e1)); }
@Test public void t07_checkDotsInTags() throws Exception { String e1 = "tagA.subA.subsubA"; assertEquals("tagA.subA.subsubA", parser.parse(e1)); assertEquals("[tagA.subA.subsubA]", getTokens(parser.parse(e1)).toString()); String e3 = "tagA.subA.subsubA = 'abc.abc.abc'"; assertEquals("tagA.subA.subsubA = 'abc.abc.abc'", parser.parse(e3)); assertEquals("[tagA.subA.subsubA, =, 'abc.abc.abc']", getTokens(parser.parse(e3)).toString()); }
@Test public void t08_checkSpacesInTagValues() throws Exception { String e1 = "tagA = 'a b'"; assertEquals("[tagA, =, 'a b']", getTokens(parser.parse(e1)).toString()); String e2 = "tagA IN ['a b', 'c d'] "; assertEquals("[tagA, in, ['a b','c d']]", getTokens(parser.parse(e2)).toString()); }
@Test public void t09_checkSpecialCharsInValue() throws Exception { String e1 = "test_tag = '/t;hawkular/f;my-agent/r;Local%20DMR~~_Server Availability'"; assertEquals("[test_tag, =, '/t;hawkular/f;my-agent/r;Local%20DMR~~_Server Availability']", getTokens(parser.parse(e1)).toString()); String e2 = "test_tag = '\\/t;hawkular\\/f;my-agent\\/r;Local%20DMR\\~\\~_Server Availability'"; assertEquals("[test_tag, =, '\\/t;hawkular\\/f;my-agent\\/r;Local%20DMR\\~\\~_Server Availability']", getTokens(parser.parse(e2)).toString()); }
@Test public void t00_singleTagExpression() throws Exception { String e1 = "tagA"; assertEquals("tagA", parser.parse(e1)); assertEquals("[tagA]", getTokens(parser.parse(e1)).toString()); String e2 = "not tagA"; assertEquals("not tagA", parser.parse(e2)); assertEquals("[not, tagA]", getTokens(parser.parse(e2)).toString()); String e3 = "tagA = 'abc'"; assertEquals("tagA = 'abc'", parser.parse(e3)); assertEquals("[tagA, =, 'abc']", getTokens(parser.parse(e3)).toString()); String e4 = " tagA != 'abc'"; assertEquals("tagA != 'abc'", parser.parse(e4)); assertEquals("[tagA, !=, 'abc']", getTokens(parser.parse(e4)).toString()); String e5 = "tagA IN ['abc', 'def', 'ghi']"; assertEquals("tagA in ['abc','def','ghi']", parser.parse(e5)); assertEquals("[tagA, in, ['abc','def','ghi']]", getTokens(parser.parse(e5)).toString()); String e5s1 = "tagA IN ['abc','def','ghi']"; assertEquals("tagA in ['abc','def','ghi']", parser.parse(e5s1)); assertEquals("[tagA, in, ['abc','def','ghi']]", getTokens(parser.parse(e5s1)).toString()); String e6 = "tagA NOT IN ['abc', 'def', 'ghi']"; assertEquals("tagA not in ['abc','def','ghi']", parser.parse(e6)); assertEquals("[tagA, not, in, ['abc','def','ghi']]", getTokens(parser.parse(e6)).toString()); String e7 = "tagA = '*'"; assertEquals("tagA = '*'", parser.parse(e7)); assertEquals("[tagA, =, '*']", getTokens(parser.parse(e7)).toString()); String e8 = "tagA = abc"; assertEquals("tagA = abc", parser.parse(e8)); assertEquals("[tagA, =, abc]", getTokens(parser.parse(e8)).toString()); String e9 = " tagA != abc"; assertEquals("tagA != abc", parser.parse(e9)); assertEquals("[tagA, !=, abc]", getTokens(parser.parse(e9)).toString()); String e10 = "tagA IN [abc, def, ghi]"; assertEquals("tagA in [abc,def,ghi]", parser.parse(e10)); assertEquals("[tagA, in, [abc,def,ghi]]", getTokens(parser.parse(e10)).toString()); String e11 = "tagA NOT IN [abc, def, ghi]"; assertEquals("tagA not in [abc,def,ghi]", parser.parse(e11)); assertEquals("[tagA, not, in, [abc,def,ghi]]", getTokens(parser.parse(e11)).toString()); String e12 = "tagA = *"; try { parser.parse(e12); fail("* should be used with single quotes"); } catch (Exception e) { } String e13 = "tagA-01"; assertEquals("tagA-01", parser.parse(e13)); assertEquals("[tagA-01]", getTokens(parser.parse(e13)).toString()); }
@Test public void t01_twoTagExpressions() throws Exception { String e1 = "tagA and not tagB"; assertEquals("and(tagA, not tagB)", parser.parse(e1)); String e2 = "not tagB and tagA"; assertEquals("and(tagA, not tagB)", parser.parse(e2)); String e3 = "not tagB or tagA"; assertEquals("or(tagA, not tagB)", parser.parse(e3)); String e4 = "tagA = 'abc' and tagB = 'def'"; assertEquals("and(tagA = 'abc', tagB = 'def')", parser.parse(e4)); }
@Test public void t02_defaultGrouping() throws Exception { String e1 = "tagA and not tagB or tagC"; assertEquals("or(tagC, and(tagA, not tagB))", parser.parse(e1)); String e2 = "not tagA and tagB or tagC"; assertEquals("or(tagC, and(tagB, not tagA))", parser.parse(e2)); String e3 = "not tagA or tagB and tagC"; assertEquals("and(tagC, or(tagB, not tagA))", parser.parse(e3)); }
@Test public void t03_simpleGrouping() throws Exception { String e1 = "tagA and (not tagB or tagC)"; assertEquals("and(tagA, or(tagC, not tagB))", parser.parse(e1)); String e2 = "tagA and (not tagB and tagC)"; assertEquals("and(tagA, and(tagC, not tagB))", parser.parse(e2)); String e3 = "(not tagB or tagC) and tagA"; assertEquals("and(tagA, or(tagC, not tagB))", parser.parse(e3)); }