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    *      https://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  
18  package org.apache.commons.io.function;
19  
20  import static org.junit.jupiter.api.Assertions.assertEquals;
21  import static org.junit.jupiter.api.Assertions.assertThrows;
22  import static org.junit.jupiter.api.Assertions.assertTrue;
23  import static org.junit.jupiter.api.Assertions.fail;
24  
25  import java.io.ByteArrayInputStream;
26  import java.io.IOException;
27  import java.io.UncheckedIOException;
28  import java.util.concurrent.atomic.AtomicBoolean;
29  import java.util.concurrent.atomic.AtomicInteger;
30  import java.util.concurrent.atomic.AtomicLong;
31  import java.util.concurrent.atomic.AtomicReference;
32  import java.util.function.Supplier;
33  
34  import org.apache.commons.io.input.BrokenInputStream;
35  import org.junit.jupiter.api.BeforeEach;
36  import org.junit.jupiter.api.Test;
37  
38  /**
39   * Tests {@link Uncheck}.
40   */
41  class UncheckTest {
42  
43      private static final byte[] BYTES = { 'a', 'b' };
44      private static final String CAUSE_MESSAGE = "CauseMessage";
45      private static final String CUSTOM_MESSAGE = "Custom message";
46  
47      private AtomicInteger atomicInt;
48      private AtomicLong atomicLong;
49      private AtomicBoolean atomicBoolean;
50      private AtomicReference<String> ref1;
51      private AtomicReference<String> ref2;
52      private AtomicReference<String> ref3;
53      private AtomicReference<String> ref4;
54  
55      private void assertUncheckedIOException(final IOException expected, final UncheckedIOException e) {
56          assertEquals(CUSTOM_MESSAGE, e.getMessage());
57          final IOException cause = e.getCause();
58          assertEquals(expected.getClass(), cause.getClass());
59          assertEquals(CAUSE_MESSAGE, cause.getMessage());
60      }
61  
62      @BeforeEach
63      public void beforeEach() {
64          ref1 = new AtomicReference<>();
65          ref2 = new AtomicReference<>();
66          ref3 = new AtomicReference<>();
67          ref4 = new AtomicReference<>();
68          atomicInt = new AtomicInteger();
69          atomicLong = new AtomicLong();
70          atomicBoolean = new AtomicBoolean();
71      }
72  
73      private ByteArrayInputStream newInputStream() {
74          return new ByteArrayInputStream(BYTES);
75      }
76  
77      /**
78       * Tests {@link Uncheck#accept(IOConsumer, Object)}.
79       */
80      @Test
81      void testAccept() {
82          final ByteArrayInputStream stream = newInputStream();
83          Uncheck.accept(n -> stream.skip(n), 1);
84          assertEquals('b', Uncheck.get(stream::read).intValue());
85      }
86  
87      @Test
88      void testAcceptIOBiConsumerOfTUTU() {
89          assertThrows(UncheckedIOException.class, () -> Uncheck.accept((t, u) -> {
90              throw new IOException();
91          }, null, null));
92          assertThrows(UncheckedIOException.class, () -> Uncheck.accept(TestConstants.THROWING_IO_BI_CONSUMER, null, null));
93          Uncheck.accept((t, u) -> {
94              TestUtils.compareAndSetThrowsIO(ref1, t);
95              TestUtils.compareAndSetThrowsIO(ref2, u);
96          }, "new1", "new2");
97          assertEquals("new1", ref1.get());
98          assertEquals("new2", ref2.get());
99      }
100 
101     @Test
102     void testAcceptIOConsumerOfTT() {
103         assertThrows(UncheckedIOException.class, () -> Uncheck.accept(t -> {
104             throw new IOException();
105         }, null));
106         assertThrows(UncheckedIOException.class, () -> Uncheck.accept(TestUtils.throwingIOConsumer(), null));
107         Uncheck.accept(t -> TestUtils.compareAndSetThrowsIO(ref1, t), "new1");
108         assertEquals("new1", ref1.get());
109     }
110 
111     @Test
112     void testAcceptIOTriConsumerOfTUVTUV() {
113         assertThrows(UncheckedIOException.class, () -> Uncheck.accept((t, u, v) -> {
114             throw new IOException();
115         }, null, null, null));
116         assertThrows(UncheckedIOException.class, () -> Uncheck.accept(TestConstants.THROWING_IO_TRI_CONSUMER, null, null, null));
117         Uncheck.accept((t, u, v) -> {
118             TestUtils.compareAndSetThrowsIO(ref1, t);
119             TestUtils.compareAndSetThrowsIO(ref2, u);
120             TestUtils.compareAndSetThrowsIO(ref3, v);
121         }, "new1", "new2", "new3");
122         assertEquals("new1", ref1.get());
123         assertEquals("new2", ref2.get());
124         assertEquals("new3", ref3.get());
125     }
126 
127     /**
128      * Tests {@link Uncheck#apply(IOFunction, Object)}.
129      */
130     @Test
131     void testApply1() {
132         final ByteArrayInputStream stream = newInputStream();
133         assertEquals(1, Uncheck.apply(n -> stream.skip(n), 1).intValue());
134         assertEquals('b', Uncheck.get(stream::read).intValue());
135     }
136 
137     /**
138      * Tests {@link Uncheck#apply(IOBiFunction, Object, Object)}.
139      */
140     @Test
141     void testApply2() {
142         final ByteArrayInputStream stream = newInputStream();
143         final byte[] buf = new byte[BYTES.length];
144         assertEquals(1, Uncheck.apply((o, l) -> stream.read(buf, o, l), 0, 1).intValue());
145         assertEquals('a', buf[0]);
146     }
147 
148     /**
149      * Tests {@link Uncheck#apply(IOTriFunction, Object, Object, Object)}.
150      */
151     @Test
152     void testApply3() {
153         final ByteArrayInputStream stream = newInputStream();
154         final byte[] buf = new byte[BYTES.length];
155         assertEquals(1, Uncheck.apply((b, o, l) -> stream.read(b, o, l), buf, 0, 1).intValue());
156         assertEquals('a', buf[0]);
157     }
158 
159     @Test
160     void testApplyIOBiFunctionOfTURTU() {
161         assertThrows(UncheckedIOException.class, () -> Uncheck.apply((t, u) -> {
162             throw new IOException();
163         }, null, null));
164         assertThrows(UncheckedIOException.class, () -> Uncheck.apply(TestConstants.THROWING_IO_BI_FUNCTION, null, null));
165         assertEquals("new0", Uncheck.apply((t, u) -> {
166             TestUtils.compareAndSetThrowsIO(ref1, t);
167             TestUtils.compareAndSetThrowsIO(ref2, u);
168             return "new0";
169         }, "new1", "new2"));
170         assertEquals("new1", ref1.get());
171         assertEquals("new2", ref2.get());
172     }
173 
174     @Test
175     void testApplyIOFunctionOfTRT() {
176         assertThrows(UncheckedIOException.class, () -> Uncheck.apply(t -> {
177             throw new IOException();
178         }, null));
179         assertThrows(UncheckedIOException.class, () -> Uncheck.apply(TestConstants.THROWING_IO_FUNCTION, null));
180         Uncheck.apply(t -> TestUtils.compareAndSetThrowsIO(ref1, t), "new1");
181         assertEquals("new1", ref1.get());
182     }
183 
184     @Test
185     void testApplyIOQuadFunctionOfTUVWRTUVW() {
186         assertThrows(UncheckedIOException.class, () -> Uncheck.apply((t, u, v, w) -> {
187             throw new IOException();
188         }, null, null, null, null));
189         assertThrows(UncheckedIOException.class, () -> Uncheck.apply(TestConstants.THROWING_IO_QUAD_FUNCTION, null, null, null, null));
190         assertEquals("new0", Uncheck.apply((t, u, v, w) -> {
191             TestUtils.compareAndSetThrowsIO(ref1, t);
192             TestUtils.compareAndSetThrowsIO(ref2, u);
193             TestUtils.compareAndSetThrowsIO(ref3, v);
194             TestUtils.compareAndSetThrowsIO(ref4, w);
195             return "new0";
196         }, "new1", "new2", "new3", "new4"));
197         assertEquals("new1", ref1.get());
198         assertEquals("new2", ref2.get());
199         assertEquals("new3", ref3.get());
200         assertEquals("new4", ref4.get());
201     }
202 
203     @Test
204     void testApplyIOTriFunctionOfTUVRTUV() {
205         assertThrows(UncheckedIOException.class, () -> Uncheck.apply((t, u, v) -> {
206             throw new IOException();
207         }, null, null, null));
208         assertThrows(UncheckedIOException.class, () -> Uncheck.apply(TestConstants.THROWING_IO_TRI_FUNCTION, null, null, null));
209         assertEquals("new0", Uncheck.apply((t, u, v) -> {
210             TestUtils.compareAndSetThrowsIO(ref1, t);
211             TestUtils.compareAndSetThrowsIO(ref2, u);
212             TestUtils.compareAndSetThrowsIO(ref3, v);
213             return "new0";
214         }, "new1", "new2", "new3"));
215         assertEquals("new1", ref1.get());
216         assertEquals("new2", ref2.get());
217         assertEquals("new3", ref3.get());
218     }
219 
220     /**
221      * Tests {@link Uncheck#get(IOSupplier)}.
222      */
223     @Test
224     void testGet() {
225         assertEquals('a', Uncheck.get(() -> newInputStream().read()).intValue());
226         assertThrows(UncheckedIOException.class, () -> Uncheck.get(() -> {
227             throw new IOException();
228         }));
229         assertThrows(UncheckedIOException.class, () -> Uncheck.get(TestConstants.THROWING_IO_SUPPLIER));
230         assertEquals("new1", Uncheck.get(() -> TestUtils.compareAndSetThrowsIO(ref1, "new1")));
231         assertEquals("new1", ref1.get());
232     }
233 
234     @Test
235     void testGetAsBoolean() {
236         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsBoolean(() -> {
237             throw new IOException();
238         }));
239         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsBoolean(TestConstants.THROWING_IO_BOOLEAN_SUPPLIER));
240         assertTrue(Uncheck.getAsBoolean(() -> TestUtils.compareAndSetThrowsIO(atomicBoolean, true)));
241         assertTrue(atomicBoolean.get());
242     }
243 
244     @Test
245     void testGetAsInt() {
246         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsInt(() -> {
247             throw new IOException();
248         }));
249         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsInt(TestConstants.THROWING_IO_INT_SUPPLIER));
250         assertEquals(1, Uncheck.getAsInt(() -> TestUtils.compareAndSetThrowsIO(atomicInt, 1)));
251         assertEquals(1, atomicInt.get());
252     }
253 
254     @Test
255     void testGetAsIntMessage() {
256         // No exception
257         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsInt(() -> {
258             throw new IOException();
259         }, () -> CUSTOM_MESSAGE));
260         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsInt(TestConstants.THROWING_IO_INT_SUPPLIER, () -> CUSTOM_MESSAGE));
261         assertEquals(1, Uncheck.getAsInt(() -> TestUtils.compareAndSetThrowsIO(atomicInt, 1), () -> CUSTOM_MESSAGE));
262         assertEquals(1, atomicInt.get());
263         // exception
264         final IOException expected = new IOException(CAUSE_MESSAGE);
265         try {
266             Uncheck.getAsInt(() -> new BrokenInputStream(expected).read(), () -> CUSTOM_MESSAGE);
267             fail();
268         } catch (final UncheckedIOException e) {
269             assertUncheckedIOException(expected, e);
270         }
271     }
272 
273     @Test
274     void testGetAsLong() {
275         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsLong(() -> {
276             throw new IOException();
277         }));
278         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsLong(TestConstants.THROWING_IO_LONG_SUPPLIER));
279         assertEquals(1L, Uncheck.getAsLong(() -> TestUtils.compareAndSetThrowsIO(atomicLong, 1L)));
280         assertEquals(1L, atomicLong.get());
281     }
282 
283     @Test
284     void testGetAsLongMessage() {
285         // No exception
286         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsLong(() -> {
287             throw new IOException();
288         }, () -> CUSTOM_MESSAGE));
289         assertThrows(UncheckedIOException.class, () -> Uncheck.getAsLong(TestConstants.THROWING_IO_LONG_SUPPLIER, () -> CUSTOM_MESSAGE));
290         assertEquals(1L, Uncheck.getAsLong(() -> TestUtils.compareAndSetThrowsIO(atomicLong, 1L), () -> CUSTOM_MESSAGE));
291         assertEquals(1L, atomicLong.get());
292         // exception
293         final IOException expected = new IOException(CAUSE_MESSAGE);
294         try {
295             Uncheck.getAsLong(() -> new BrokenInputStream(expected).read(), () -> CUSTOM_MESSAGE);
296             fail();
297         } catch (final UncheckedIOException e) {
298             assertUncheckedIOException(expected, e);
299         }
300     }
301 
302     /**
303      * Tests {@link Uncheck#get(IOSupplier, Supplier)}.
304      */
305     @Test
306     void testGetMessage() {
307         // No exception
308         assertEquals('a', Uncheck.get(() -> newInputStream().read()).intValue(), () -> CUSTOM_MESSAGE);
309         // Exception
310         final IOException expected = new IOException(CAUSE_MESSAGE);
311         try {
312             Uncheck.get(() -> new BrokenInputStream(expected).read(), () -> CUSTOM_MESSAGE);
313             fail();
314         } catch (final UncheckedIOException e) {
315             assertUncheckedIOException(expected, e);
316         }
317     }
318 
319     /**
320      * Tests {@link Uncheck#run(IORunnable)}.
321      */
322     @Test
323     void testRun() {
324         final ByteArrayInputStream stream = newInputStream();
325         Uncheck.run(() -> stream.skip(1));
326         assertEquals('b', Uncheck.get(stream::read).intValue());
327         //
328         assertThrows(UncheckedIOException.class, () -> Uncheck.run(() -> {
329             throw new IOException();
330         }));
331         assertThrows(UncheckedIOException.class, () -> Uncheck.run(TestConstants.THROWING_IO_RUNNABLE));
332         Uncheck.run(() -> TestUtils.compareAndSetThrowsIO(ref1, "new1"));
333         assertEquals("new1", ref1.get());
334     }
335 
336     /**
337      * Tests {@link Uncheck#run(IORunnable, Supplier))}.
338      *
339      * @throws IOException
340      */
341     @Test
342     void testRunMessage() throws IOException {
343         // No exception
344         final ByteArrayInputStream stream = newInputStream();
345         Uncheck.run(() -> stream.skip(1), () -> CUSTOM_MESSAGE);
346         assertEquals('b', Uncheck.get(stream::read).intValue());
347         final IOException expected = new IOException(CAUSE_MESSAGE);
348         // Exception
349         try {
350             Uncheck.run(() -> new BrokenInputStream(expected).read(), () -> CUSTOM_MESSAGE);
351             fail();
352         } catch (final UncheckedIOException e) {
353             assertUncheckedIOException(expected, e);
354         }
355     }
356 
357     @Test
358     void testTest() {
359         assertThrows(UncheckedIOException.class, () -> Uncheck.test(t -> {
360             throw new IOException();
361         }, null));
362         assertThrows(UncheckedIOException.class, () -> Uncheck.test(TestConstants.THROWING_IO_PREDICATE, null));
363         assertTrue(Uncheck.test(t -> TestUtils.compareAndSetThrowsIO(ref1, t).equals(t), "new1"));
364         assertEquals("new1", ref1.get());
365     }
366 
367 }