This is an automated email from the ASF dual-hosted git repository.
davsclaus pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git
The following commit(s) were added to refs/heads/main by this push:
new 55d5f8434ea0 CAMEL-23796: Fix wrong token in logical operator
right-hand-side error message
55d5f8434ea0 is described below
commit 55d5f8434ea09cde0b4dd967b0f50860a4dcb6f6
Author: Adriano Machado <[email protected]>
AuthorDate: Fri Jun 19 02:51:35 2026 -0400
CAMEL-23796: Fix wrong token in logical operator right-hand-side error
message
Fix SimplePredicateParser to report the correct token when the
right-hand side of a logical operator (&&/||) is invalid — it was
using left.getToken() instead of right.getToken().
Make LogicalExpression.acceptLeftNode/acceptRightNode enforce that
only BinaryExpression or LogicalExpression nodes are valid on each
side, making the error branch reachable and testable.
Closes #24118
---
.../language/simple/SimplePredicateParser.java | 2 +-
.../language/simple/ast/LogicalExpression.java | 6 +
.../simple/SimplePredicateParserLogicalTest.java | 136 +++++++++++++++++++++
3 files changed, 143 insertions(+), 1 deletion(-)
diff --git
a/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/SimplePredicateParser.java
b/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/SimplePredicateParser.java
index 016e819faa3d..d50831ce0529 100644
---
a/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/SimplePredicateParser.java
+++
b/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/SimplePredicateParser.java
@@ -552,7 +552,7 @@ public class SimplePredicateParser extends BaseSimpleParser
{
}
if (!logical.acceptRightNode(right)) {
throw new SimpleParserException(
- "Logical operator " + operator + " does not
support right hand side token " + left.getToken(),
+ "Logical operator " + operator + " does not
support right hand side token " + right.getToken(),
token.getToken().getIndex());
}
diff --git
a/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/ast/LogicalExpression.java
b/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/ast/LogicalExpression.java
index afbcd2efec08..535dce4fbfa8 100644
---
a/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/ast/LogicalExpression.java
+++
b/core/camel-core-languages/src/main/java/org/apache/camel/language/simple/ast/LogicalExpression.java
@@ -48,11 +48,17 @@ public class LogicalExpression extends BaseSimpleNode {
}
public boolean acceptLeftNode(SimpleNode lef) {
+ if (!(lef instanceof BinaryExpression) && !(lef instanceof
LogicalExpression)) {
+ return false;
+ }
this.left = lef;
return true;
}
public boolean acceptRightNode(SimpleNode right) {
+ if (!(right instanceof BinaryExpression) && !(right instanceof
LogicalExpression)) {
+ return false;
+ }
this.right = right;
return true;
}
diff --git
a/core/camel-core/src/test/java/org/apache/camel/language/simple/SimplePredicateParserLogicalTest.java
b/core/camel-core/src/test/java/org/apache/camel/language/simple/SimplePredicateParserLogicalTest.java
new file mode 100644
index 000000000000..bd62f2cb1089
--- /dev/null
+++
b/core/camel-core/src/test/java/org/apache/camel/language/simple/SimplePredicateParserLogicalTest.java
@@ -0,0 +1,136 @@
+/*
+ * 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.camel.language.simple;
+
+import org.apache.camel.ExchangeTestSupport;
+import org.apache.camel.Predicate;
+import org.apache.camel.language.simple.types.SimpleIllegalSyntaxException;
+import org.junit.jupiter.api.Test;
+
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertThrows;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
+/**
+ * Regression tests for prepareLogicalExpressions in SimplePredicateParser.
Covers the bug where the right-hand token
+ * was reported as the left-hand token in the "does not support right hand
side token" error message.
+ */
+public class SimplePredicateParserLogicalTest extends ExchangeTestSupport {
+
+ @Test
+ public void testAndWithFunctionRightHandSide() {
+ exchange.getIn().setBody("hello");
+ exchange.getIn().setHeader("active", true);
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} == 'hello' && ${header.active} == true",
true, null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertTrue(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testAndWithLiteralRightHandSide() {
+ exchange.getIn().setBody("foo");
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} == 'foo' && ${body} != 'bar'", true, null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertTrue(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testOrWithFunctionRightHandSide() {
+ exchange.getIn().setBody("hello");
+ exchange.getIn().setHeader("score", 5);
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} == 'world' || ${header.score} > 3", true,
null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertTrue(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testOrAllFalse() {
+ exchange.getIn().setBody("hello");
+ exchange.getIn().setHeader("score", 1);
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} == 'world' || ${header.score} > 3", true,
null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertFalse(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testAndWithNumericRightHandSide() {
+ exchange.getIn().setBody(42);
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} > 10 && ${body} < 100", true, null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertTrue(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testAndWithNullRightHandSide() {
+ exchange.getIn().setBody("present");
+ exchange.getIn().setHeader("tag", "x");
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} != null && ${header.tag} != null", true,
null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertTrue(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testChainedAndOrLogicalOperators() {
+ exchange.getIn().setBody("alpha");
+ exchange.getIn().setHeader("flag", true);
+
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} == 'alpha' && ${header.flag} == true ||
${body} == 'beta'", true, null);
+ Predicate predicate = parser.parsePredicate();
+ predicate.init(context);
+
+ assertTrue(predicate.matches(exchange));
+ }
+
+ @Test
+ public void testInvalidRightHandSideReportsRightToken() {
+ // "&&" followed by a bare numeric (not a binary expression) is
invalid syntax.
+ // The error message must say "right hand side token 42" (the actual
offending token),
+ // not "right hand side token ==" (which would indicate the left-hand
node was reported).
+ SimplePredicateParser parser = new SimplePredicateParser(
+ context, "${body} == 'foo' && 42", true, null);
+ SimpleIllegalSyntaxException ex =
assertThrows(SimpleIllegalSyntaxException.class, parser::parsePredicate);
+ assertTrue(ex.getMessage().contains("right hand side token 42"),
+ "Error message should say 'right hand side token 42', but was:
" + ex.getMessage());
+ assertFalse(ex.getMessage().contains("right hand side token =="),
+ "Error message must not say 'right hand side token ==', but
was: " + ex.getMessage());
+ }
+}