This is an automated email from the ASF dual-hosted git repository.
vavrtom pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/qpid-broker-j.git
The following commit(s) were added to refs/heads/main by this push:
new 8f7909fbb2 QPID-8656: [Broker-J] Selector parsing logic error when
combining NOT and LIKE (#230)
8f7909fbb2 is described below
commit 8f7909fbb2d6f9eae22b84e3a4782af6d7d70bbc
Author: Daniil Kirilyuk <[email protected]>
AuthorDate: Wed Dec 13 09:30:32 2023 +0100
QPID-8656: [Broker-J] Selector parsing logic error when combining NOT and
LIKE (#230)
---
broker-core/src/main/grammar/SelectorParser.jj | 2 +-
.../server/filter/selector/ParseException.java | 2 +-
.../server/filter/selector/SelectorParser.java | 162 +++++------
.../selector/SelectorParserTokenManager.java | 11 +
.../server/filter/selector/SimpleCharStream.java | 2 +-
.../apache/qpid/server/filter/selector/Token.java | 3 +-
.../qpid/server/filter/selector/TokenMgrError.java | 3 +-
.../server/filter/JMSSelectorFilterSyntaxTest.java | 319 +++++++++++++++++++++
8 files changed, 416 insertions(+), 88 deletions(-)
diff --git a/broker-core/src/main/grammar/SelectorParser.jj
b/broker-core/src/main/grammar/SelectorParser.jj
index 8aea8295e8..4271907cd9 100644
--- a/broker-core/src/main/grammar/SelectorParser.jj
+++ b/broker-core/src/main/grammar/SelectorParser.jj
@@ -459,7 +459,7 @@ Expression unaryExpr() :
left = UnaryExpression.createNegate(left);
}
|
- <NOT> left=unaryExpr()
+ <NOT> left=orExpression()
{
left = UnaryExpression.createNOT( asBooleanExpression(left)
);
}
diff --git
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/ParseException.java
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/ParseException.java
index bb456ef2db..ea28826696 100644
---
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/ParseException.java
+++
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/ParseException.java
@@ -205,4 +205,4 @@ public class ParseException extends Exception {
}
}
-/* JavaCC - OriginalChecksum=d315306e736475f86f69c53861799960 (do not edit
this line) */
+/* JavaCC - OriginalChecksum=f191e3976fe6d5a6a93a2d6f845dcf9d (do not edit
this line) */
diff --git
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParser.java
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParser.java
index 0997a2d26f..80082f52c8 100644
---
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParser.java
+++
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParser.java
@@ -416,7 +416,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
break;
case NOT:
jj_consume_token(NOT);
- left = unaryExpr();
+ left = orExpression();
left = UnaryExpression.createNOT(
asBooleanExpression(left) );
break;
case TRUE:
@@ -611,7 +611,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3R_55() {
if (jj_scan_token(IN)) return true;
if (jj_scan_token(33)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
Token xsp;
while (true) {
xsp = jj_scanpos;
@@ -621,7 +621,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_47() {
+ private boolean jj_3R_46() {
if (jj_scan_token(IS)) return true;
if (jj_scan_token(NOT)) return true;
if (jj_scan_token(NULL)) return true;
@@ -634,7 +634,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_33() {
+ private boolean jj_3R_39() {
if (jj_scan_token(NULL)) return true;
return false;
}
@@ -661,13 +661,13 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_46() {
+ private boolean jj_3R_45() {
if (jj_scan_token(28)) return true;
- if (jj_3R_41()) return true;
+ if (jj_3R_30()) return true;
return false;
}
- private boolean jj_3R_32() {
+ private boolean jj_3R_38() {
if (jj_scan_token(FALSE)) return true;
return false;
}
@@ -675,28 +675,28 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3_3() {
if (jj_scan_token(NOT)) return true;
if (jj_scan_token(BETWEEN)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
if (jj_scan_token(AND)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
return false;
}
- private boolean jj_3R_45() {
+ private boolean jj_3R_44() {
if (jj_scan_token(27)) return true;
- if (jj_3R_41()) return true;
+ if (jj_3R_30()) return true;
return false;
}
- private boolean jj_3R_42() {
+ private boolean jj_3R_31() {
Token xsp;
xsp = jj_scanpos;
- if (jj_3R_45()) {
+ if (jj_3R_44()) {
jj_scanpos = xsp;
- if (jj_3R_46()) {
+ if (jj_3R_45()) {
jj_scanpos = xsp;
if (jj_3_1()) {
jj_scanpos = xsp;
- if (jj_3R_47()) return true;
+ if (jj_3R_46()) return true;
}
}
}
@@ -705,20 +705,20 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3R_54() {
if (jj_scan_token(BETWEEN)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
if (jj_scan_token(AND)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
return false;
}
- private boolean jj_3R_31() {
+ private boolean jj_3R_37() {
if (jj_scan_token(TRUE)) return true;
return false;
}
private boolean jj_3R_58() {
if (jj_scan_token(ESCAPE)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
return false;
}
@@ -728,17 +728,17 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_30() {
+ private boolean jj_3R_36() {
if (jj_scan_token(FLOATING_POINT_LITERAL)) return true;
return false;
}
- private boolean jj_3R_39() {
- if (jj_3R_41()) return true;
+ private boolean jj_3R_26() {
+ if (jj_3R_30()) return true;
Token xsp;
while (true) {
xsp = jj_scanpos;
- if (jj_3R_42()) { jj_scanpos = xsp; break; }
+ if (jj_3R_31()) { jj_scanpos = xsp; break; }
}
return false;
}
@@ -746,7 +746,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3_2() {
if (jj_scan_token(NOT)) return true;
if (jj_scan_token(LIKE)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
Token xsp;
xsp = jj_scanpos;
if (jj_3R_59()) jj_scanpos = xsp;
@@ -755,7 +755,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3R_53() {
if (jj_scan_token(LIKE)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
Token xsp;
xsp = jj_scanpos;
if (jj_3R_58()) jj_scanpos = xsp;
@@ -768,7 +768,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_29() {
+ private boolean jj_3R_35() {
if (jj_scan_token(OCTAL_LITERAL)) return true;
return false;
}
@@ -792,13 +792,13 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_40() {
+ private boolean jj_3R_27() {
if (jj_scan_token(AND)) return true;
- if (jj_3R_39()) return true;
+ if (jj_3R_26()) return true;
return false;
}
- private boolean jj_3R_28() {
+ private boolean jj_3R_34() {
if (jj_scan_token(HEX_LITERAL)) return true;
return false;
}
@@ -813,7 +813,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_27() {
+ private boolean jj_3R_33() {
if (jj_scan_token(DECIMAL_LITERAL)) return true;
return false;
}
@@ -824,12 +824,12 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_36() {
- if (jj_3R_39()) return true;
+ private boolean jj_3R_21() {
+ if (jj_3R_26()) return true;
Token xsp;
while (true) {
xsp = jj_scanpos;
- if (jj_3R_40()) { jj_scanpos = xsp; break; }
+ if (jj_3R_27()) { jj_scanpos = xsp; break; }
}
return false;
}
@@ -847,11 +847,11 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3R_52() {
if (jj_scan_token(32)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
return false;
}
- private boolean jj_3R_35() {
+ private boolean jj_3R_41() {
if (jj_scan_token(QUOTED_ID)) return true;
return false;
}
@@ -862,25 +862,25 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_26() {
- if (jj_3R_38()) return true;
+ private boolean jj_3R_32() {
+ if (jj_3R_47()) return true;
return false;
}
private boolean jj_3R_51() {
if (jj_scan_token(31)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
return false;
}
- private boolean jj_3R_34() {
+ private boolean jj_3R_40() {
if (jj_scan_token(ID)) return true;
return false;
}
private boolean jj_3R_61() {
if (jj_scan_token(34)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
return false;
}
@@ -894,30 +894,30 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_37() {
+ private boolean jj_3R_22() {
if (jj_scan_token(OR)) return true;
- if (jj_3R_36()) return true;
+ if (jj_3R_21()) return true;
return false;
}
- private boolean jj_3R_23() {
+ private boolean jj_3R_28() {
Token xsp;
xsp = jj_scanpos;
- if (jj_3R_26()) {
+ if (jj_3R_32()) {
jj_scanpos = xsp;
- if (jj_3R_27()) {
+ if (jj_3R_33()) {
jj_scanpos = xsp;
- if (jj_3R_28()) {
+ if (jj_3R_34()) {
jj_scanpos = xsp;
- if (jj_3R_29()) {
+ if (jj_3R_35()) {
jj_scanpos = xsp;
- if (jj_3R_30()) {
+ if (jj_3R_36()) {
jj_scanpos = xsp;
- if (jj_3R_31()) {
+ if (jj_3R_37()) {
jj_scanpos = xsp;
- if (jj_3R_32()) {
+ if (jj_3R_38()) {
jj_scanpos = xsp;
- if (jj_3R_33()) return true;
+ if (jj_3R_39()) return true;
}
}
}
@@ -930,27 +930,27 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3R_50() {
if (jj_scan_token(30)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
return false;
}
- private boolean jj_3R_24() {
+ private boolean jj_3R_29() {
Token xsp;
xsp = jj_scanpos;
- if (jj_3R_34()) {
+ if (jj_3R_40()) {
jj_scanpos = xsp;
- if (jj_3R_35()) return true;
+ if (jj_3R_41()) return true;
}
return false;
}
private boolean jj_3R_49() {
if (jj_scan_token(29)) return true;
- if (jj_3R_43()) return true;
+ if (jj_3R_42()) return true;
return false;
}
- private boolean jj_3R_44() {
+ private boolean jj_3R_43() {
Token xsp;
xsp = jj_scanpos;
if (jj_3R_49()) {
@@ -984,7 +984,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_43() {
+ private boolean jj_3R_42() {
if (jj_3R_9()) return true;
Token xsp;
while (true) {
@@ -994,58 +994,58 @@ public class SelectorParser<E> implements
SelectorParserConstants {
return false;
}
- private boolean jj_3R_25() {
- if (jj_3R_36()) return true;
+ private boolean jj_3R_19() {
+ if (jj_3R_21()) return true;
Token xsp;
while (true) {
xsp = jj_scanpos;
- if (jj_3R_37()) { jj_scanpos = xsp; break; }
+ if (jj_3R_22()) { jj_scanpos = xsp; break; }
}
return false;
}
- private boolean jj_3R_22() {
+ private boolean jj_3R_25() {
if (jj_scan_token(33)) return true;
- if (jj_3R_25()) return true;
+ if (jj_3R_19()) return true;
if (jj_scan_token(35)) return true;
return false;
}
- private boolean jj_3R_21() {
- if (jj_3R_24()) return true;
+ private boolean jj_3R_24() {
+ if (jj_3R_29()) return true;
return false;
}
- private boolean jj_3R_20() {
- if (jj_3R_23()) return true;
+ private boolean jj_3R_23() {
+ if (jj_3R_28()) return true;
return false;
}
private boolean jj_3R_60() {
if (jj_scan_token(34)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
return false;
}
- private boolean jj_3R_19() {
+ private boolean jj_3R_20() {
Token xsp;
xsp = jj_scanpos;
- if (jj_3R_20()) {
+ if (jj_3R_23()) {
jj_scanpos = xsp;
- if (jj_3R_21()) {
+ if (jj_3R_24()) {
jj_scanpos = xsp;
- if (jj_3R_22()) return true;
+ if (jj_3R_25()) return true;
}
}
return false;
}
- private boolean jj_3R_41() {
- if (jj_3R_43()) return true;
+ private boolean jj_3R_30() {
+ if (jj_3R_42()) return true;
Token xsp;
while (true) {
xsp = jj_scanpos;
- if (jj_3R_44()) { jj_scanpos = xsp; break; }
+ if (jj_3R_43()) { jj_scanpos = xsp; break; }
}
return false;
}
@@ -1054,7 +1054,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
if (jj_scan_token(NOT)) return true;
if (jj_scan_token(IN)) return true;
if (jj_scan_token(33)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
Token xsp;
while (true) {
xsp = jj_scanpos;
@@ -1072,23 +1072,23 @@ public class SelectorParser<E> implements
SelectorParserConstants {
private boolean jj_3R_59() {
if (jj_scan_token(ESCAPE)) return true;
- if (jj_3R_38()) return true;
+ if (jj_3R_47()) return true;
return false;
}
- private boolean jj_3R_38() {
+ private boolean jj_3R_47() {
if (jj_scan_token(STRING_LITERAL)) return true;
return false;
}
private boolean jj_3R_15() {
- if (jj_3R_19()) return true;
+ if (jj_3R_20()) return true;
return false;
}
private boolean jj_3R_14() {
if (jj_scan_token(NOT)) return true;
- if (jj_3R_10()) return true;
+ if (jj_3R_19()) return true;
return false;
}
@@ -1169,7 +1169,7 @@ public class SelectorParser<E> implements
SelectorParserConstants {
throw generateParseException();
}
- static private final class LookaheadSuccess extends java.lang.Error { }
+ static private final class LookaheadSuccess extends Error { }
final private LookaheadSuccess jj_ls = new LookaheadSuccess();
private boolean jj_scan_token(int kind) {
if (jj_scanpos == jj_lastpos) {
diff --git
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParserTokenManager.java
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParserTokenManager.java
index 287f5d221e..73e0db2152 100644
---
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParserTokenManager.java
+++
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SelectorParserTokenManager.java
@@ -21,6 +21,17 @@
*/
package org.apache.qpid.server.filter.selector;
+import java.io.StringReader;
+import java.util.ArrayList;
+import org.apache.qpid.server.filter.ArithmeticExpression;
+import org.apache.qpid.server.filter.BooleanExpression;
+import org.apache.qpid.server.filter.ComparisonExpression;
+import org.apache.qpid.server.filter.ConstantExpression;
+import org.apache.qpid.server.filter.Expression;
+import org.apache.qpid.server.filter.LogicExpression;
+import org.apache.qpid.server.filter.PropertyExpression;
+import org.apache.qpid.server.filter.PropertyExpressionFactory;
+import org.apache.qpid.server.filter.UnaryExpression;
/** Token Manager. */
public class SelectorParserTokenManager implements SelectorParserConstants
diff --git
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SimpleCharStream.java
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SimpleCharStream.java
index 64b169034c..7e41554f43 100644
---
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SimpleCharStream.java
+++
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/SimpleCharStream.java
@@ -489,4 +489,4 @@ public class SimpleCharStream
}
}
-/* JavaCC - OriginalChecksum=dcf3510e97e4ee9a841bdafac162a129 (do not edit
this line) */
+/* JavaCC - OriginalChecksum=dd31548eee2e798f7cd0fab4448f1d95 (do not edit
this line) */
diff --git
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/Token.java
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/Token.java
index 581cfd35a4..5a4d5681e7 100644
---
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/Token.java
+++
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/Token.java
@@ -118,7 +118,6 @@ public class Token implements java.io.Serializable {
/**
* Returns the image.
*/
- @Override
public String toString()
{
return image;
@@ -150,4 +149,4 @@ public class Token implements java.io.Serializable {
}
}
-/* JavaCC - OriginalChecksum=dfd1857bf2f000661cadfe9ef672245e (do not edit
this line) */
+/* JavaCC - OriginalChecksum=181874db027eea8b35f565d8393a0afa (do not edit
this line) */
diff --git
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/TokenMgrError.java
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/TokenMgrError.java
index e26f37f6e6..f85eec77e7 100644
---
a/broker-core/src/main/java/org/apache/qpid/server/filter/selector/TokenMgrError.java
+++
b/broker-core/src/main/java/org/apache/qpid/server/filter/selector/TokenMgrError.java
@@ -142,7 +142,6 @@ public class TokenMgrError extends Error
*
* from this method for such cases in the release version of your parser.
*/
- @Override
public String getMessage() {
return super.getMessage();
}
@@ -166,4 +165,4 @@ public class TokenMgrError extends Error
this(LexicalError(EOFSeen, lexState, errorLine, errorColumn, errorAfter,
curChar), reason);
}
}
-/* JavaCC - OriginalChecksum=795daaee93a15e0081e60f73df35399f (do not edit
this line) */
+/* JavaCC - OriginalChecksum=dbdd2965cdf45ffc1a6fe0e4cb1331df (do not edit
this line) */
diff --git
a/broker-core/src/test/java/org/apache/qpid/server/filter/JMSSelectorFilterSyntaxTest.java
b/broker-core/src/test/java/org/apache/qpid/server/filter/JMSSelectorFilterSyntaxTest.java
new file mode 100644
index 0000000000..629b048a94
--- /dev/null
+++
b/broker-core/src/test/java/org/apache/qpid/server/filter/JMSSelectorFilterSyntaxTest.java
@@ -0,0 +1,319 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.qpid.server.filter;
+
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+import org.junit.jupiter.api.Test;
+
+public class JMSSelectorFilterSyntaxTest
+{
+ @Test
+ public void equality() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("color")).thenReturn("red");
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("color = 'red'").matches(message));
+ assertTrue(new JMSSelectorFilter("price = 100").matches(message));
+ assertFalse(new JMSSelectorFilter("color = 'blue'").matches(message));
+ assertFalse(new JMSSelectorFilter("price = 200").matches(message));
+ }
+
+ @Test
+ public void inequality() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("color")).thenReturn("red");
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("color <> 'blue'").matches(message));
+ assertTrue(new JMSSelectorFilter("price <> 200").matches(message));
+ assertFalse(new JMSSelectorFilter("color <> 'red'").matches(message));
+ assertFalse(new JMSSelectorFilter("price <> 100").matches(message));
+ }
+
+ @Test
+ public void greaterThan() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("price > 10").matches(message));
+ assertFalse(new JMSSelectorFilter("price > 100").matches(message));
+ }
+
+ @Test
+ public void greaterThanOrEquals() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("price >= 10").matches(message));
+ assertTrue(new JMSSelectorFilter("price >= 100").matches(message));
+ assertFalse(new JMSSelectorFilter("price >= 200").matches(message));
+ }
+
+ @Test
+ public void lessThan() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("price < 110").matches(message));
+ assertFalse(new JMSSelectorFilter("price < 100").matches(message));
+ }
+
+ @Test
+ public void lessThanOrEquals() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("price <= 110").matches(message));
+ assertTrue(new JMSSelectorFilter("price <= 100").matches(message));
+ assertFalse(new JMSSelectorFilter("price <= 10").matches(message));
+ }
+
+ @Test
+ public void and() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("color")).thenReturn("red");
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("color = 'red' and price =
100").matches(message));
+ assertFalse(new JMSSelectorFilter("color = 'red' and price =
200").matches(message));
+ assertFalse(new JMSSelectorFilter("color = 'blue' and price =
100").matches(message));
+ assertFalse(new JMSSelectorFilter("color = 'blue' and price =
200").matches(message));
+ }
+
+ @Test
+ public void or() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("color")).thenReturn("red");
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("color = 'red' or price =
100").matches(message));
+ assertTrue(new JMSSelectorFilter("color = 'red' or price =
200").matches(message));
+ assertTrue(new JMSSelectorFilter("color = 'blue' or price =
100").matches(message));
+ assertFalse(new JMSSelectorFilter("color = 'blue' or price =
200").matches(message));
+ }
+
+ @Test
+ public void in() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+
+ when(message.getHeader("fruit")).thenReturn("apple");
+ assertTrue(new JMSSelectorFilter("fruit in ('apple', 'banana',
'cherry')").matches(message));
+
+ when(message.getHeader("fruit")).thenReturn("banana");
+ assertTrue(new JMSSelectorFilter("fruit in ('apple', 'banana',
'cherry')").matches(message));
+
+ when(message.getHeader("fruit")).thenReturn("cherry");
+ assertTrue(new JMSSelectorFilter("fruit in ('apple', 'banana',
'cherry')").matches(message));
+
+ when(message.getHeader("fruit")).thenReturn("mango");
+ assertFalse(new JMSSelectorFilter("fruit in ('apple', 'banana',
'cherry')").matches(message));
+ }
+
+ @Test
+ public void notIn() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+
+ when(message.getHeader("fruit")).thenReturn("apple");
+ assertFalse(new JMSSelectorFilter("fruit not in ('apple', 'banana',
'cherry')").matches(message));
+ assertFalse(new JMSSelectorFilter("not (fruit in ('apple', 'banana',
'cherry'))").matches(message));
+ assertFalse(new JMSSelectorFilter("not fruit in ('apple', 'banana',
'cherry')").matches(message));
+
+ when(message.getHeader("fruit")).thenReturn("banana");
+ assertFalse(new JMSSelectorFilter("fruit not in ('apple', 'banana',
'cherry')").matches(message));
+ assertFalse(new JMSSelectorFilter("not (fruit in ('apple', 'banana',
'cherry'))").matches(message));
+ assertFalse(new JMSSelectorFilter("not fruit in ('apple', 'banana',
'cherry')").matches(message));
+
+ when(message.getHeader("fruit")).thenReturn("cherry");
+ assertFalse(new JMSSelectorFilter("fruit not in ('apple', 'banana',
'cherry')").matches(message));
+ assertFalse(new JMSSelectorFilter("not (fruit in ('apple', 'banana',
'cherry'))").matches(message));
+ assertFalse(new JMSSelectorFilter("not fruit in ('apple', 'banana',
'cherry')").matches(message));
+
+ when(message.getHeader("fruit")).thenReturn("mango");
+ assertTrue(new JMSSelectorFilter("fruit not in ('apple', 'banana',
'cherry')").matches(message));
+ assertTrue(new JMSSelectorFilter("not (fruit in ('apple', 'banana',
'cherry'))").matches(message));
+ assertTrue(new JMSSelectorFilter("not fruit in ('apple', 'banana',
'cherry')").matches(message));
+ }
+
+ @Test
+ public void between() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("price between 90 and
110").matches(message));
+ assertTrue(new JMSSelectorFilter("price between 100 and
110").matches(message));
+ assertTrue(new JMSSelectorFilter("price between 90 and
100").matches(message));
+ assertFalse(new JMSSelectorFilter("price between 110 and
120").matches(message));
+ }
+
+ @Test
+ public void notBetween() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertFalse(new JMSSelectorFilter("price not between 90 and
110").matches(message));
+ assertFalse(new JMSSelectorFilter("price not between 100 and
110").matches(message));
+ assertFalse(new JMSSelectorFilter("price not between 90 and
100").matches(message));
+ assertTrue(new JMSSelectorFilter("price not between 110 and
120").matches(message));
+
+ assertFalse(new JMSSelectorFilter("not (price between 90 and
110)").matches(message));
+ assertFalse(new JMSSelectorFilter("not (price between 100 and
110)").matches(message));
+ assertFalse(new JMSSelectorFilter("not (price between 90 and
100)").matches(message));
+ assertTrue(new JMSSelectorFilter("not (price between 110 and
120)").matches(message));
+
+ assertFalse(new JMSSelectorFilter("not price between 90 and
110").matches(message));
+ assertFalse(new JMSSelectorFilter("not price between 100 and
110").matches(message));
+ assertFalse(new JMSSelectorFilter("not price between 90 and
100").matches(message));
+ assertTrue(new JMSSelectorFilter("not price between 110 and
120").matches(message));
+ }
+
+ @Test
+ public void like() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+
+ when(message.getHeader("entry")).thenReturn("bbb");
+ assertFalse(new JMSSelectorFilter("entry like
'%aaa%'").matches(message));
+
+ when(message.getHeader("entry")).thenReturn("aaa");
+ assertTrue(new JMSSelectorFilter("entry like
'%aaa%'").matches(message));
+ }
+
+ @Test
+ public void notLike() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("entry")).thenReturn("bbb");
+
+ assertTrue(new JMSSelectorFilter("entry NOT LIKE
'%aaa%'").matches(message));
+ assertTrue(new JMSSelectorFilter("(entry NOT LIKE
'%aaa%')").matches(message));
+
+ assertTrue(new JMSSelectorFilter("NOT (entry LIKE
'%aaa%')").matches(message));
+ assertTrue(new JMSSelectorFilter("NOT entry LIKE
'%aaa%'").matches(message));
+
+ when(message.getHeader("entry")).thenReturn("aaa");
+
+ assertFalse(new JMSSelectorFilter("entry NOT LIKE
'%aaa%'").matches(message));
+ assertFalse(new JMSSelectorFilter("(entry NOT LIKE
'%aaa%')").matches(message));
+
+ assertFalse(new JMSSelectorFilter("NOT (entry LIKE
'%aaa%')").matches(message));
+ assertFalse(new JMSSelectorFilter("NOT entry LIKE
'%aaa%'").matches(message));
+ }
+
+ @Test
+ public void isNull() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("entry")).thenReturn("aaa");
+
+ assertFalse(new JMSSelectorFilter("entry is null").matches(message));
+ assertTrue(new JMSSelectorFilter("another_entry is
null").matches(message));
+ }
+
+ @Test
+ public void isNotNull() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("entry")).thenReturn("aaa");
+
+ assertTrue(new JMSSelectorFilter("entry is not
null").matches(message));
+ assertTrue(new JMSSelectorFilter("not (entry is
null)").matches(message));
+ assertTrue(new JMSSelectorFilter("not entry is
null").matches(message));
+ assertFalse(new JMSSelectorFilter("another_entry is not
null").matches(message));
+ assertFalse(new JMSSelectorFilter("not (another_entry is
null)").matches(message));
+ assertFalse(new JMSSelectorFilter("not another_entry is
null").matches(message));
+ }
+
+ @Test
+ public void arithmetic() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("size")).thenReturn(10);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("size + price =
110").matches(message));
+ assertTrue(new JMSSelectorFilter("price - size =
90").matches(message));
+ assertTrue(new JMSSelectorFilter("price / size =
10").matches(message));
+ assertTrue(new JMSSelectorFilter("price * size =
1000").matches(message));
+
+ assertTrue(new JMSSelectorFilter("size / 4 = 2.5").matches(message));
+ assertTrue(new JMSSelectorFilter("size / 4.0 = 2.5").matches(message));
+
+ assertTrue(new JMSSelectorFilter("size * 2 = 20.0").matches(message));
+ assertTrue(new JMSSelectorFilter("size * 2.0 =
20.0").matches(message));
+ }
+
+ @Test
+ public void arithmeticOperatorsPrecedence() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+ when(message.getHeader("size")).thenReturn(10);
+ when(message.getHeader("price")).thenReturn(100);
+
+ assertTrue(new JMSSelectorFilter("1 + 1 * 10 = 11").matches(message));
+ assertTrue(new JMSSelectorFilter("(1 + 1) * 10 =
20").matches(message));
+
+ assertTrue(new JMSSelectorFilter("1 + 1 / 10 = 1.1").matches(message));
+ assertTrue(new JMSSelectorFilter("(1 + 1) / 10 =
0.2").matches(message));
+ }
+
+ @Test
+ public void logicOperatorsPrecedence() throws Exception
+ {
+ final Filterable message = mock(Filterable.class);
+
+ when(message.getHeader("a")).thenReturn(1);
+ when(message.getHeader("b")).thenReturn(2);
+ when(message.getHeader("c")).thenReturn(3);
+ assertTrue(new JMSSelectorFilter("a = 1 and b = 2 or c =
3").matches(message));
+ assertFalse(new JMSSelectorFilter("not a = 1 and b =
2").matches(message));
+ assertTrue(new JMSSelectorFilter("a = 1 and (b = 2 or c =
3)").matches(message));
+ assertTrue(new JMSSelectorFilter("a = 1 and (b = 2 or c =
4)").matches(message));
+ assertTrue(new JMSSelectorFilter("a = 1 and (b = 3 or c =
3)").matches(message));
+ assertFalse(new JMSSelectorFilter("a = 1 and (b = 3 or c =
4)").matches(message));
+ assertTrue(new JMSSelectorFilter("not (not a = 1)").matches(message));
+ assertTrue(new JMSSelectorFilter("not not a = 1").matches(message));
+
+ when(message.getHeader("a")).thenReturn(1);
+ when(message.getHeader("b")).thenReturn(2);
+ when(message.getHeader("c")).thenReturn(4);
+ assertTrue(new JMSSelectorFilter("a = 1 and b = 2 or c =
3").matches(message));
+
+ when(message.getHeader("a")).thenReturn(1);
+ when(message.getHeader("b")).thenReturn(1);
+ when(message.getHeader("c")).thenReturn(3);
+ assertTrue(new JMSSelectorFilter("a = 1 and b = 2 or c =
3").matches(message));
+ }
+}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]