From 234a1c894df919d224510a52fe9085f729d52e41 Mon Sep 17 00:00:00 2001 From: Andras Katona Date: Wed, 1 Dec 2021 15:48:47 +0100 Subject: [PATCH 1/3] Fixing reject filter evaluation when it has argument(s) --- .../jinjava/lib/filter/RejectFilter.java | 9 +++- .../jinjava/lib/filter/RejectFilterTest.java | 43 +++++++++++++++++++ 2 files changed, 51 insertions(+), 1 deletion(-) create mode 100644 src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java diff --git a/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java b/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java index 0e9e0b882..f2292944c 100644 --- a/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java +++ b/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java @@ -11,6 +11,7 @@ import com.hubspot.jinjava.util.ForLoop; import com.hubspot.jinjava.util.ObjectIterator; import java.util.ArrayList; +import java.util.Arrays; import java.util.List; @JinjavaDoc( @@ -54,6 +55,12 @@ public Object filter(Object var, JinjavaInterpreter interpreter, String... args) throw new InvalidArgumentException(interpreter, this, InvalidReason.NULL, 0); } + Object[] expArgs = new Object[] {}; + + if (args.length > 1) { + expArgs = Arrays.copyOfRange(args, 1, args.length); + } + ExpTest expTest = interpreter.getContext().getExpTest(args[0]); if (expTest == null) { throw new InvalidArgumentException( @@ -69,7 +76,7 @@ public Object filter(Object var, JinjavaInterpreter interpreter, String... args) while (loop.hasNext()) { Object val = loop.next(); - if (!expTest.evaluate(val, interpreter)) { + if (!expTest.evaluate(val, interpreter, expArgs)) { result.add(val); } } diff --git a/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java b/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java new file mode 100644 index 000000000..8d6b671b3 --- /dev/null +++ b/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java @@ -0,0 +1,43 @@ +package com.hubspot.jinjava.lib.filter; + +import com.google.common.collect.Lists; +import com.hubspot.jinjava.BaseJinjavaTest; +import org.junit.Before; +import org.junit.Test; + +import java.util.HashMap; +import java.util.Map; + + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +public class RejectFilterTest extends BaseJinjavaTest { + + @Before + public void setup() { + jinjava.getGlobalContext().put("numbers", Lists.newArrayList(1L, 2L, 3L, 4L, 5L)); + } + + @Test + public void testReject() { + assertThat(jinjava.render("{{numbers|reject('odd')}}", new HashMap<>())) + .isEqualTo("[2, 4]"); + assertThat(jinjava.render("{{numbers|reject('even')}}", new HashMap<>())) + .isEqualTo("[1, 3, 5]"); + } + + @Test + public void testRejectWithEqualToAttr() { + assertThat(jinjava.render("{{numbers|reject('equalto', 3)}}", new HashMap<>())) + .isEqualTo("[1, 2, 4, 5]"); + } + + @Test + public void itThrowsInvalidArgumentForNullExpTestArgument() { + Map context = new HashMap<>(); + context.put("test", null); + assertThatThrownBy(() -> jinjava.render("{{numbers|reject(test, 3)}}", context)) + .hasMessageContaining("1st argument cannot be null"); + } +} From defcc57c40d54528cb86e7de7129cac11244bedf Mon Sep 17 00:00:00 2001 From: Andras Katona Date: Wed, 1 Dec 2021 15:56:43 +0100 Subject: [PATCH 2/3] Make RejectFilter more like SelectFilter --- .../com/hubspot/jinjava/lib/filter/RejectFilter.java | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java b/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java index f2292944c..0f9b646ba 100644 --- a/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java +++ b/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java @@ -13,6 +13,7 @@ import java.util.ArrayList; import java.util.Arrays; import java.util.List; +import java.util.Map; @JinjavaDoc( value = "Filters a sequence of objects by applying a test to the object and rejecting the ones with the test succeeding.", @@ -32,7 +33,7 @@ ) } ) -public class RejectFilter implements Filter { +public class RejectFilter implements AdvancedFilter { @Override public String getName() { @@ -40,7 +41,12 @@ public String getName() { } @Override - public Object filter(Object var, JinjavaInterpreter interpreter, String... args) { + public Object filter( + Object var, + JinjavaInterpreter interpreter, + Object[] args, + Map kwargs + ) { List result = new ArrayList<>(); if (args.length < 1) { @@ -61,7 +67,7 @@ public Object filter(Object var, JinjavaInterpreter interpreter, String... args) expArgs = Arrays.copyOfRange(args, 1, args.length); } - ExpTest expTest = interpreter.getContext().getExpTest(args[0]); + ExpTest expTest = interpreter.getContext().getExpTest(args[0].toString()); if (expTest == null) { throw new InvalidArgumentException( interpreter, From 2173bdc953e59538ccabfe8e7f377fa48db44dd7 Mon Sep 17 00:00:00 2001 From: Andras Katona Date: Wed, 1 Dec 2021 16:00:31 +0100 Subject: [PATCH 3/3] RejectFilter is just the invert of SelectFilter --- .../jinjava/lib/filter/RejectFilter.java | 52 +++---------------- .../jinjava/lib/filter/SelectFilter.java | 11 +++- .../jinjava/lib/filter/RejectFilterTest.java | 2 +- 3 files changed, 17 insertions(+), 48 deletions(-) diff --git a/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java b/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java index 0f9b646ba..f4eb16879 100644 --- a/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java +++ b/src/main/java/com/hubspot/jinjava/lib/filter/RejectFilter.java @@ -33,7 +33,7 @@ ) } ) -public class RejectFilter implements AdvancedFilter { +public class RejectFilter extends SelectFilter { @Override public String getName() { @@ -41,52 +41,12 @@ public String getName() { } @Override - public Object filter( - Object var, + boolean evaluate( JinjavaInterpreter interpreter, - Object[] args, - Map kwargs + Object[] expArgs, + ExpTest expTest, + Object val ) { - List result = new ArrayList<>(); - - if (args.length < 1) { - throw new TemplateSyntaxException( - interpreter, - getName(), - "requires 1 argument (name of expression test to filter by)" - ); - } - - if (args[0] == null) { - throw new InvalidArgumentException(interpreter, this, InvalidReason.NULL, 0); - } - - Object[] expArgs = new Object[] {}; - - if (args.length > 1) { - expArgs = Arrays.copyOfRange(args, 1, args.length); - } - - ExpTest expTest = interpreter.getContext().getExpTest(args[0].toString()); - if (expTest == null) { - throw new InvalidArgumentException( - interpreter, - this, - InvalidReason.EXPRESSION_TEST, - 0, - args[0] - ); - } - - ForLoop loop = ObjectIterator.getLoop(var); - while (loop.hasNext()) { - Object val = loop.next(); - - if (!expTest.evaluate(val, interpreter, expArgs)) { - result.add(val); - } - } - - return result; + return !super.evaluate(interpreter, expArgs, expTest, val); } } diff --git a/src/main/java/com/hubspot/jinjava/lib/filter/SelectFilter.java b/src/main/java/com/hubspot/jinjava/lib/filter/SelectFilter.java index b1a846f9b..da4922922 100644 --- a/src/main/java/com/hubspot/jinjava/lib/filter/SelectFilter.java +++ b/src/main/java/com/hubspot/jinjava/lib/filter/SelectFilter.java @@ -92,11 +92,20 @@ public Object filter( while (loop.hasNext()) { Object val = loop.next(); - if (expTest.evaluate(val, interpreter, expArgs)) { + if (evaluate(interpreter, expArgs, expTest, val)) { result.add(val); } } return result; } + + boolean evaluate( + JinjavaInterpreter interpreter, + Object[] expArgs, + ExpTest expTest, + Object val + ) { + return expTest.evaluate(val, interpreter, expArgs); + } } diff --git a/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java b/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java index 8d6b671b3..f452070ea 100644 --- a/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java +++ b/src/test/java/com/hubspot/jinjava/lib/filter/RejectFilterTest.java @@ -38,6 +38,6 @@ public void itThrowsInvalidArgumentForNullExpTestArgument() { Map context = new HashMap<>(); context.put("test", null); assertThatThrownBy(() -> jinjava.render("{{numbers|reject(test, 3)}}", context)) - .hasMessageContaining("1st argument cannot be null"); + .hasMessageContaining("'exp_test' argument cannot be null"); } }