This is an automated email from the ASF dual-hosted git repository.

ddekany pushed a commit to branch 2.3-gae
in repository https://gitbox.apache.org/repos/asf/freemarker.git


The following commit(s) were added to refs/heads/2.3-gae by this push:
     new ece9abc  ?min and ?max will now immediately stop with error when 
applied on a right unbounded numerical range (like 1..), as that would run 
forever anyway.
ece9abc is described below

commit ece9abc578475770a98f5f5caaa3229fac0c25b7
Author: ddekany <[email protected]>
AuthorDate: Thu Aug 1 22:33:07 2019 +0200

    ?min and ?max will now immediately stop with error when applied on a right 
unbounded numerical range (like 1..), as that would run forever anyway.
---
 .../java/freemarker/core/BuiltInsForSequences.java | 22 ++++++++++++++--------
 src/manual/en_US/book.xml                          |  7 +++++++
 src/test/java/freemarker/core/MinMaxBITest.java    | 10 ++++++++++
 .../java/freemarker/core/SequenceBuiltInTest.java  |  3 +--
 4 files changed, 32 insertions(+), 10 deletions(-)

diff --git a/src/main/java/freemarker/core/BuiltInsForSequences.java 
b/src/main/java/freemarker/core/BuiltInsForSequences.java
index 153be79..2ba6b11 100644
--- a/src/main/java/freemarker/core/BuiltInsForSequences.java
+++ b/src/main/java/freemarker/core/BuiltInsForSequences.java
@@ -245,10 +245,7 @@ class BuiltInsForSequences {
         TemplateModel _eval(Environment env) throws TemplateException {
             TemplateModel model = target.eval(env);
             if (model instanceof TemplateCollectionModel) {
-                if (model instanceof RightUnboundedRangeModel) {
-                    throw new _TemplateModelException(
-                            "The sequence to join was right-unbounded 
numerical range, thus it's infinitely long.");
-                }
+                checkNotRightUnboundedNumericalRange(model);
                 return new BIMethodForCollection(env, 
(TemplateCollectionModel) model);
             } else if (model instanceof TemplateSequenceModel) {
                 return new BIMethodForCollection(env, new 
CollectionAndSequence((TemplateSequenceModel) model));
@@ -907,7 +904,15 @@ class BuiltInsForSequences {
                 ? !((CollectionModel) model).getSupportsIndexedAccess()
                 : false;
     }
-    
+
+    private static void checkNotRightUnboundedNumericalRange(TemplateModel 
model) throws TemplateModelException {
+        if (model instanceof RightUnboundedRangeModel) {
+            throw new _TemplateModelException(
+                    "The input sequence is a right-unbounded numerical range, 
thus, it's infinitely long, and can't " +
+                    "processed with this built-in.");
+        }
+    }
+
     private static boolean modelsEqual(
             int seqItemIndex, TemplateModel seqItem, TemplateModel 
searchedItem,
             Environment env)
@@ -945,7 +950,8 @@ class BuiltInsForSequences {
                 throws TemplateException {
             TemplateModel model = target.eval(env);
             if (model instanceof TemplateCollectionModel) {
-                return calculateResultForColletion((TemplateCollectionModel) 
model, env);
+                checkNotRightUnboundedNumericalRange(model);
+                return calculateResultForCollection((TemplateCollectionModel) 
model, env);
             } else if (model instanceof TemplateSequenceModel) {
                 return calculateResultForSequence((TemplateSequenceModel) 
model, env);
             } else {
@@ -953,7 +959,7 @@ class BuiltInsForSequences {
             }
         }        
 
-        private TemplateModel 
calculateResultForColletion(TemplateCollectionModel coll, Environment env)
+        private TemplateModel 
calculateResultForCollection(TemplateCollectionModel coll, Environment env)
         throws TemplateException {
             TemplateModel best = null;
             TemplateModelIterator iter = coll.iterator();
@@ -982,7 +988,7 @@ class BuiltInsForSequences {
             return best;
         }
         
-    }    
+    }
 
     static class maxBI extends MinOrMaxBI {
 
diff --git a/src/manual/en_US/book.xml b/src/manual/en_US/book.xml
index 017e7c0..3681a02 100644
--- a/src/manual/en_US/book.xml
+++ b/src/manual/en_US/book.xml
@@ -27961,6 +27961,13 @@ TemplateModel x = env.getVariable("x");  // get 
variable x</programlisting>
               <quote>multiplier</quote> was incorrectly written as
               <quote>multipier</quote>. Now both words are recognized.</para>
             </listitem>
+
+            <listitem>
+              <para><literal>?min</literal> and <literal>?max</literal> will
+              now immediately stop with error when applied on a right
+              unbounded numerical range (like <literal>1..</literal>), as that
+              would run forever anyway.</para>
+            </listitem>
           </itemizedlist>
         </section>
 
diff --git a/src/test/java/freemarker/core/MinMaxBITest.java 
b/src/test/java/freemarker/core/MinMaxBITest.java
index 3bff7ba..fe48ce5 100644
--- a/src/test/java/freemarker/core/MinMaxBITest.java
+++ b/src/test/java/freemarker/core/MinMaxBITest.java
@@ -28,6 +28,7 @@ import org.junit.Test;
 
 import com.google.common.collect.ImmutableList;
 
+import freemarker.template.Configuration;
 import freemarker.template.DefaultIterableAdapter;
 import freemarker.template.utility.DateUtil;
 import freemarker.template.utility.ObjectWrapperWithAPISupport;
@@ -83,5 +84,14 @@ public class MinMaxBITest extends TemplateTest {
         assertErrorContains("${['a', 'x']?min}", "less-than", "string");
         assertErrorContains("${[0, true]?min}", "number", "boolean");
     }
+
+    @Test
+    public void rightUnboundedNumericalRangeTest() throws Exception {
+        
getConfiguration().setIncompatibleImprovements(Configuration.VERSION_2_3_21); 
// So (1..) is listable at all
+        assertErrorContains("${(1..)?min}", "right-unbounded", "infinite");
+        assertErrorContains("${(1..)?max}", "right-unbounded", "infinite");
+        assertOutput("${(1..2)?min}", "1");
+        assertOutput("${(1..2)?max}", "2");
+    }
     
 }
diff --git a/src/test/java/freemarker/core/SequenceBuiltInTest.java 
b/src/test/java/freemarker/core/SequenceBuiltInTest.java
index 4f4aab9..a86725e 100644
--- a/src/test/java/freemarker/core/SequenceBuiltInTest.java
+++ b/src/test/java/freemarker/core/SequenceBuiltInTest.java
@@ -88,8 +88,7 @@ public class SequenceBuiltInTest extends TemplateTest {
     @Test
     public void testWithSequence() throws TemplateException, IOException {
         assertOutput("${[11, 12]?sequence[1]}", "12");
-        
-        
+
         
getConfiguration().setIncompatibleImprovements(Configuration.VERSION_2_3_23);
         // As it returns the sequence as is, it works with an infinite 
sequence:
         assertOutput("${(11..)?sequence[1]}", "12");

Reply via email to