View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.jexl3;
18  
19  import static org.junit.jupiter.api.Assertions.assertEquals;
20  import static org.junit.jupiter.api.Assertions.assertFalse;
21  import static org.junit.jupiter.api.Assertions.assertNotNull;
22  import static org.junit.jupiter.api.Assertions.assertThrows;
23  import static org.junit.jupiter.api.Assertions.assertTrue;
24  
25  import java.io.IOException;
26  
27  import org.junit.jupiter.api.Disabled;
28  import org.junit.jupiter.api.Test;
29  
30  public class TryCatchFinallyTest extends JexlTestCase {
31      public static class Circuit implements AutoCloseable {
32          boolean opened = true;
33  
34          @Override
35          public void close() throws IOException {
36              opened = false;
37          }
38  
39          public boolean isOpened() {
40              return opened;
41          }
42  
43          public void raiseError() {
44              throw new RuntimeException("raising error");
45          }
46      }
47  
48      public TryCatchFinallyTest() {
49          super(TryCatchFinallyTest.class.getSimpleName());
50      }
51  
52      @Test
53      public void testCloseable0x2b() {
54          final String src = "try(let x = c) { c.isOpened()? 42 : -42; } finally { 169; }";
55          final JexlScript script = JEXL.createScript(src, "c");
56          final Circuit circuit = new Circuit();
57          assertNotNull(script);
58          final Object result = script.execute(null, circuit);
59          assertEquals(42, result);
60          assertFalse(circuit.isOpened());
61      }
62  
63      @Test
64      public void testCloseable0x3b() {
65          final String src = "try(let x = c) { c.raiseError(); -42; } catch(const y) { 42; } finally { 169; }";
66          final JexlScript script = JEXL.createScript(src, "c");
67          final Circuit circuit = new Circuit();
68          assertNotNull(script);
69          final Object result = script.execute(null, circuit);
70          assertEquals(42, result);
71          assertFalse(circuit.isOpened());
72      }
73  
74      @Disabled
75      public void testEdgeTry() throws Exception {
76          int i = 0;
77          while (i++ < 5) {
78              // System.out.println("i: " + i);
79              try {
80                  throw new JexlException.Continue(null);
81              } finally {
82                  continue;
83              }
84          }
85          // System.out.println("iii: " + i);
86  
87          // int x = 0;
88          try (AutoCloseable x = new Circuit()) {
89              // empty
90          }
91      }
92  
93      @Test
94      public void testExceptionType() throws Exception {
95          final JexlScript e = JEXL.createScript("try { 'asb'.getBytes('NoSuchCharacterSet'); } catch (let ex) { ex }");
96          final JexlContext jc = new MapContext();
97          final Object o = e.execute(jc);
98          assertTrue(o instanceof java.io.UnsupportedEncodingException);
99      }
100 
101     @Test
102     public void testForm0x2a() {
103         final String src = "try(let x = 42) { x; } finally { 169; }";
104         final JexlScript script = JEXL.createScript(src);
105         assertNotNull(script);
106         final Object result = script.execute(null);
107         assertEquals(42, result);
108     }
109 
110     @Test
111     public void testForm0x2b() {
112         final String src = "try(let x = 19, y = 23) { x + y; } finally { 169; }";
113         final JexlScript script = JEXL.createScript(src);
114         assertNotNull(script);
115         final Object result = script.execute(null);
116         assertEquals(42, result);
117     }
118 
119     @Test
120     public void testForm0x2c() {
121         final String src = "try(const x = 19; let y = 23; ) { x + y; } finally { 169; }";
122         final JexlScript script = JEXL.createScript(src);
123         assertNotNull(script);
124         final Object result = script.execute(null);
125         assertEquals(42, result);
126     }
127 
128     @Test
129     public void testForm0x2d() {
130         final String src = "try(var x = 19; const y = 23;) { x + y; } finally { 169; }";
131         final JexlScript script = JEXL.createScript(src);
132         assertNotNull(script);
133         final Object result = script.execute(null);
134         assertEquals(42, result);
135     }
136 
137     @Test
138     public void testRedefinition0() {
139         final String src = "try(let x = c) { let x = 3; -42; }";
140         final JexlException.Parsing xvar = assertThrows(JexlException.Parsing.class, () -> JEXL.createScript(src, "c"));
141         assertTrue(xvar.getMessage().contains("x: variable is already declared"));
142     }
143 
144     @Test
145     public void testRedefinition1() {
146         final String src = "const x = 33; try(let x = c) { 169; }";
147         final JexlException.Parsing xvar = assertThrows(JexlException.Parsing.class, () -> JEXL.createScript(src, "c"));
148         assertTrue(xvar.getMessage().contains("x: variable is already declared"));
149     }
150 
151     @Test
152     public void testStandard0x2() {
153         final String src = "try { 42; } finally { 169; }";
154         final JexlScript script = JEXL.createScript(src);
155         assertNotNull(script);
156         final Object result = script.execute(null);
157         assertEquals(42, result);
158     }
159 
160     @Test
161     public void testThrow0x2a() {
162         final String src = "try(let x = 42) { throw x } finally { 169; }";
163         final JexlScript script = JEXL.createScript(src);
164         assertNotNull(script);
165         final JexlException.Throw xthrow = assertThrows(JexlException.Throw.class, () -> script.execute(null));
166         assertEquals(42, xthrow.getValue());
167     }
168 
169     @Test
170     public void testThrow0x2b() {
171         final String src = "try(let x = 42) { throw x } finally { throw 169 }";
172         final JexlScript script = JEXL.createScript(src);
173         assertNotNull(script);
174         final JexlException.Throw xthrow = assertThrows(JexlException.Throw.class, () -> script.execute(null));
175         assertEquals(169, xthrow.getValue());
176     }
177 
178     @Test
179     public void testThrowCatchBreakFinallyContinue() {
180         final String src = "let r = 0; for(let i : 37..42) { try(let x = 169) { r = i; throw -x } catch(const y) { break } finally { continue } } r";
181         final JexlScript script = JEXL.createScript(src);
182         assertNotNull(script);
183         final Object result = script.execute(null);
184         assertEquals(42, result);
185     }
186 
187     @Test
188     public void testThrowCatchContinueFinallyBreak() {
189         final String src = "let r = 0; for(let i : 42..37) { try(let x = 169) { r = i; throw -x } catch(const y) { continue } finally { break } } r";
190         final JexlScript script = JEXL.createScript(src);
191         assertNotNull(script);
192         final Object result = script.execute(null);
193         assertEquals(42, result);
194     }
195 
196     @Test
197     public void testThrowCatchThrow() {
198         final String src = "try(let x = 42) { throw x } catch(const y) { throw -(y.value) } ";
199         final JexlScript script = JEXL.createScript(src);
200         assertNotNull(script);
201         final JexlException.Throw xthrow = assertThrows(JexlException.Throw.class, () -> script.execute(null));
202         assertEquals(-42, xthrow.getValue());
203     }
204 
205     @Test
206     public void testThrowCatchThrowFinallyThrow() {
207         final String src = "try(let x = 42) { throw x } catch(const y) { throw -(y.value) } finally { throw 169 }";
208         final JexlScript script = JEXL.createScript(src);
209         assertNotNull(script);
210         final JexlException.Throw xthrow = assertThrows(JexlException.Throw.class, () -> script.execute(null));
211         assertEquals(169, xthrow.getValue());
212     }
213 
214     @Test
215     public void testThrowRecurse() {
216         final String src = "function fact(x, f) { if (x == 1) throw f; fact(x - 1, f * x); } fact(7, 1);";
217         final JexlScript script = JEXL.createScript(src);
218         assertNotNull(script);
219         final JexlException.Throw xthrow = assertThrows(JexlException.Throw.class, () -> script.execute(null));
220         assertEquals(5040, xthrow.getValue());
221     }
222 
223     @Test
224     public void testTryReturn() {
225         final String src = "try(let x = 42) { return x } catch(const y) { throw -(y.value) } ";
226         final JexlScript script = JEXL.createScript(src);
227         assertNotNull(script);
228         final Object result = script.execute(null);
229         assertEquals(42, result);
230     }
231 
232     @Test
233     public void testTryReturnFinallyReturn() {
234         final String src = "try(let x = 42) { return x } finally { return 169 } ";
235         final JexlScript script = JEXL.createScript(src);
236         assertNotNull(script);
237         final Object result = script.execute(null);
238         assertEquals(169, result);
239     }
240 }