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.lang3;
18
19 import java.io.IOException;
20 import java.io.UncheckedIOException;
21 import java.lang.reflect.UndeclaredThrowableException;
22 import java.util.Arrays;
23 import java.util.Collection;
24 import java.util.Objects;
25 import java.util.concurrent.Callable;
26 import java.util.function.BiConsumer;
27 import java.util.function.BiFunction;
28 import java.util.function.BiPredicate;
29 import java.util.function.Consumer;
30 import java.util.function.Function;
31 import java.util.function.Predicate;
32 import java.util.function.Supplier;
33 import java.util.stream.Stream;
34
35 import org.apache.commons.lang3.Streams.FailableStream;
36 import org.apache.commons.lang3.exception.ExceptionUtils;
37 import org.apache.commons.lang3.function.Failable;
38 import org.apache.commons.lang3.function.FailableBooleanSupplier;
39
40 /**
41 * This class provides utility functions, and classes for working with the {@code java.util.function} package, or more
42 * generally, with Java 8 lambdas. More specifically, it attempts to address the fact that lambdas are supposed not to
43 * throw Exceptions, at least not checked Exceptions, AKA instances of {@link Exception}. This enforces the use of
44 * constructs like:
45 *
46 * <pre>
47 * {@code
48 * Consumer<java.lang.reflect.Method> consumer = m -> {
49 * try {
50 * m.invoke(o, args);
51 * } catch (Throwable t) {
52 * throw Functions.rethrow(t);
53 * }
54 * };
55 * }</pre>
56 *
57 * <p>
58 * By replacing a {@link java.util.function.Consumer Consumer<O>} with a {@link FailableConsumer
59 * FailableConsumer<O,? extends Throwable>}, this can be written like follows:
60 * </p>
61 *
62 * <pre>
63 * {@code
64 * Functions.accept((m) -> m.invoke(o,args));
65 * }</pre>
66 *
67 * <p>
68 * Obviously, the second version is much more concise and the spirit of Lambda expressions is met better than the second
69 * version.
70 * </p>
71 * @since 3.9
72 * @deprecated Use {@link org.apache.commons.lang3.function.Failable}.
73 */
74 @Deprecated
75 public class Functions {
76
77 /**
78 * A functional interface like {@link BiConsumer} that declares a {@link Throwable}.
79 *
80 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
81 *
82 * @param <O1> Consumed type 1.
83 * @param <O2> Consumed type 2.
84 * @param <T> Thrown exception.
85 * @deprecated Use {@link org.apache.commons.lang3.function.FailableBiConsumer}.
86 */
87 @Deprecated
88 @FunctionalInterface
89 public interface FailableBiConsumer<O1, O2, T extends Throwable> {
90
91 /**
92 * Accepts the consumer.
93 *
94 * @param object1 the first parameter for the consumable to accept
95 * @param object2 the second parameter for the consumable to accept
96 * @throws T Thrown when the consumer fails.
97 */
98 void accept(O1 object1, O2 object2) throws T;
99 }
100
101 /**
102 * A functional interface like {@link BiFunction} that declares a {@link Throwable}.
103 *
104 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
105 *
106 * @param <O1> Input type 1.
107 * @param <O2> Input type 2.
108 * @param <R> Return type.
109 * @param <T> Thrown exception.
110 * @deprecated Use {@link org.apache.commons.lang3.function.FailableBiFunction}.
111 */
112 @Deprecated
113 @FunctionalInterface
114 public interface FailableBiFunction<O1, O2, R, T extends Throwable> {
115
116 /**
117 * Applies this function.
118 *
119 * @param input1 the first input for the function
120 * @param input2 the second input for the function
121 * @return the result of the function
122 * @throws T Thrown when the function fails.
123 */
124 R apply(O1 input1, O2 input2) throws T;
125 }
126
127 /**
128 * A functional interface like {@link BiPredicate} that declares a {@link Throwable}.
129 *
130 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
131 *
132 * @param <O1> Predicate type 1.
133 * @param <O2> Predicate type 2.
134 * @param <T> Thrown exception.
135 * @deprecated Use {@link org.apache.commons.lang3.function.FailableBiPredicate}.
136 */
137 @Deprecated
138 @FunctionalInterface
139 public interface FailableBiPredicate<O1, O2, T extends Throwable> {
140
141 /**
142 * Tests the predicate.
143 *
144 * @param object1 the first object to test the predicate on
145 * @param object2 the second object to test the predicate on
146 * @return the predicate's evaluation
147 * @throws T if the predicate fails
148 */
149 boolean test(O1 object1, O2 object2) throws T;
150 }
151
152 /**
153 * A functional interface like {@link java.util.concurrent.Callable} that declares a {@link Throwable}.
154 *
155 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
156 *
157 * @param <R> Return type.
158 * @param <T> Thrown exception.
159 * @deprecated Use {@link org.apache.commons.lang3.function.FailableCallable}.
160 */
161 @Deprecated
162 @FunctionalInterface
163 public interface FailableCallable<R, T extends Throwable> {
164
165 /**
166 * Calls the callable.
167 *
168 * @return The value returned from the callable
169 * @throws T if the callable fails
170 */
171 R call() throws T;
172 }
173
174 /**
175 * A functional interface like {@link Consumer} that declares a {@link Throwable}.
176 *
177 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
178 *
179 * @param <O> Consumed type 1.
180 * @param <T> Thrown exception.
181 * @deprecated Use {@link org.apache.commons.lang3.function.FailableConsumer}.
182 */
183 @Deprecated
184 @FunctionalInterface
185 public interface FailableConsumer<O, T extends Throwable> {
186
187 /**
188 * Accepts the consumer.
189 *
190 * @param object the parameter for the consumable to accept
191 * @throws T Thrown when the consumer fails.
192 */
193 void accept(O object) throws T;
194 }
195
196 /**
197 * A functional interface like {@link Function} that declares a {@link Throwable}.
198 *
199 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
200 *
201 * @param <I> Input type 1.
202 * @param <R> Return type.
203 * @param <T> Thrown exception.
204 * @deprecated Use {@link org.apache.commons.lang3.function.FailableFunction}.
205 */
206 @Deprecated
207 @FunctionalInterface
208 public interface FailableFunction<I, R, T extends Throwable> {
209
210 /**
211 * Applies this function.
212 *
213 * @param input the input for the function
214 * @return the result of the function
215 * @throws T Thrown when the function fails.
216 */
217 R apply(I input) throws T;
218 }
219
220 /**
221 * A functional interface like {@link Predicate} that declares a {@link Throwable}.
222 *
223 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
224 *
225 * @param <I> Predicate type 1.
226 * @param <T> Thrown exception.
227 * @deprecated Use {@link org.apache.commons.lang3.function.FailablePredicate}.
228 */
229 @Deprecated
230 @FunctionalInterface
231 public interface FailablePredicate<I, T extends Throwable> {
232
233 /**
234 * Tests the predicate.
235 *
236 * @param object the object to test the predicate on
237 * @return the predicate's evaluation
238 * @throws T if the predicate fails
239 */
240 boolean test(I object) throws T;
241 }
242
243 /**
244 * A functional interface like {@link Runnable} that declares a {@link Throwable}.
245 *
246 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
247 *
248 * @param <T> Thrown exception.
249 * @deprecated Use {@link org.apache.commons.lang3.function.FailableRunnable}.
250 */
251 @Deprecated
252 @FunctionalInterface
253 public interface FailableRunnable<T extends Throwable> {
254
255 /**
256 * Runs the function.
257 *
258 * @throws T Thrown when the function fails.
259 */
260 void run() throws T;
261 }
262
263 /**
264 * A functional interface like {@link Supplier} that declares a {@link Throwable}.
265 *
266 * <p>TODO for 4.0: Move to org.apache.commons.lang3.function.</p>
267 *
268 * @param <R> Return type.
269 * @param <T> Thrown exception.
270 * @deprecated Use {@link org.apache.commons.lang3.function.FailableSupplier}.
271 */
272 @Deprecated
273 @FunctionalInterface
274 public interface FailableSupplier<R, T extends Throwable> {
275
276 /**
277 * Supplies an object
278 *
279 * @return a result
280 * @throws T if the supplier fails
281 */
282 R get() throws T;
283 }
284
285 /**
286 * Consumes a consumer and rethrows any exception as a {@link RuntimeException}.
287 *
288 * @param consumer the consumer to consume
289 * @param object1 the first object to consume by {@code consumer}
290 * @param object2 the second object to consume by {@code consumer}
291 * @param <O1> the type of the first argument the consumer accepts
292 * @param <O2> the type of the second argument the consumer accepts
293 * @param <T> the type of checked exception the consumer may throw
294 */
295 public static <O1, O2, T extends Throwable> void accept(final FailableBiConsumer<O1, O2, T> consumer,
296 final O1 object1, final O2 object2) {
297 run(() -> consumer.accept(object1, object2));
298 }
299
300 /**
301 * Consumes a consumer and rethrows any exception as a {@link RuntimeException}.
302 *
303 * @param consumer the consumer to consume
304 * @param object the object to consume by {@code consumer}
305 * @param <O> the type the consumer accepts
306 * @param <T> the type of checked exception the consumer may throw
307 */
308 public static <O, T extends Throwable> void accept(final FailableConsumer<O, T> consumer, final O object) {
309 run(() -> consumer.accept(object));
310 }
311
312 /**
313 * Applies a function and rethrows any exception as a {@link RuntimeException}.
314 *
315 * @param function the function to apply
316 * @param input1 the first input to apply {@code function} on
317 * @param input2 the second input to apply {@code function} on
318 * @param <O1> the type of the first argument the function accepts
319 * @param <O2> the type of the second argument the function accepts
320 * @param <O> the return type of the function
321 * @param <T> the type of checked exception the function may throw
322 * @return the value returned from the function
323 */
324 public static <O1, O2, O, T extends Throwable> O apply(final FailableBiFunction<O1, O2, O, T> function,
325 final O1 input1, final O2 input2) {
326 return get(() -> function.apply(input1, input2));
327 }
328
329 /**
330 * Applies a function and rethrows any exception as a {@link RuntimeException}.
331 *
332 * @param function the function to apply
333 * @param input the input to apply {@code function} on
334 * @param <I> the type of the argument the function accepts
335 * @param <O> the return type of the function
336 * @param <T> the type of checked exception the function may throw
337 * @return the value returned from the function
338 */
339 public static <I, O, T extends Throwable> O apply(final FailableFunction<I, O, T> function, final I input) {
340 return get(() -> function.apply(input));
341 }
342
343 /**
344 * Converts the given {@link FailableBiConsumer} into a standard {@link BiConsumer}.
345 *
346 * @param <O1> the type of the first argument of the consumers
347 * @param <O2> the type of the second argument of the consumers
348 * @param consumer a failable {@link BiConsumer}
349 * @return a standard {@link BiConsumer}
350 * @since 3.10
351 */
352 public static <O1, O2> BiConsumer<O1, O2> asBiConsumer(final FailableBiConsumer<O1, O2, ?> consumer) {
353 return (input1, input2) -> accept(consumer, input1, input2);
354 }
355
356 /**
357 * Converts the given {@link FailableBiFunction} into a standard {@link BiFunction}.
358 *
359 * @param <O1> the type of the first argument of the input of the functions
360 * @param <O2> the type of the second argument of the input of the functions
361 * @param <O> the type of the output of the functions
362 * @param function a {@link FailableBiFunction}
363 * @return a standard {@link BiFunction}
364 * @since 3.10
365 */
366 public static <O1, O2, O> BiFunction<O1, O2, O> asBiFunction(final FailableBiFunction<O1, O2, O, ?> function) {
367 return (input1, input2) -> apply(function, input1, input2);
368 }
369
370 /**
371 * Converts the given {@link FailableBiPredicate} into a standard {@link BiPredicate}.
372 *
373 * @param <O1> the type of the first argument used by the predicates
374 * @param <O2> the type of the second argument used by the predicates
375 * @param predicate a {@link FailableBiPredicate}
376 * @return a standard {@link BiPredicate}
377 * @since 3.10
378 */
379 public static <O1, O2> BiPredicate<O1, O2> asBiPredicate(final FailableBiPredicate<O1, O2, ?> predicate) {
380 return (input1, input2) -> test(predicate, input1, input2);
381 }
382
383 /**
384 * Converts the given {@link FailableCallable} into a standard {@link Callable}.
385 *
386 * @param <O> the type used by the callables
387 * @param callable a {@link FailableCallable}
388 * @return a standard {@link Callable}
389 * @since 3.10
390 */
391 public static <O> Callable<O> asCallable(final FailableCallable<O, ?> callable) {
392 return () -> call(callable);
393 }
394
395 /**
396 * Converts the given {@link FailableConsumer} into a standard {@link Consumer}.
397 *
398 * @param <I> the type used by the consumers
399 * @param consumer a {@link FailableConsumer}
400 * @return a standard {@link Consumer}
401 * @since 3.10
402 */
403 public static <I> Consumer<I> asConsumer(final FailableConsumer<I, ?> consumer) {
404 return input -> accept(consumer, input);
405 }
406
407 /**
408 * Converts the given {@link FailableFunction} into a standard {@link Function}.
409 *
410 * @param <I> the type of the input of the functions
411 * @param <O> the type of the output of the functions
412 * @param function a {code FailableFunction}
413 * @return a standard {@link Function}
414 * @since 3.10
415 */
416 public static <I, O> Function<I, O> asFunction(final FailableFunction<I, O, ?> function) {
417 return input -> apply(function, input);
418 }
419
420 /**
421 * Converts the given {@link FailablePredicate} into a standard {@link Predicate}.
422 *
423 * @param <I> the type used by the predicates
424 * @param predicate a {@link FailablePredicate}
425 * @return a standard {@link Predicate}
426 * @since 3.10
427 */
428 public static <I> Predicate<I> asPredicate(final FailablePredicate<I, ?> predicate) {
429 return input -> test(predicate, input);
430 }
431
432 /**
433 * Converts the given {@link FailableRunnable} into a standard {@link Runnable}.
434 *
435 * @param runnable a {@link FailableRunnable}
436 * @return a standard {@link Runnable}
437 * @since 3.10
438 */
439 public static Runnable asRunnable(final FailableRunnable<?> runnable) {
440 return () -> run(runnable);
441 }
442
443 /**
444 * Converts the given {@link FailableSupplier} into a standard {@link Supplier}.
445 *
446 * @param <O> the type supplied by the suppliers
447 * @param supplier a {@link FailableSupplier}
448 * @return a standard {@link Supplier}
449 * @since 3.10
450 */
451 public static <O> Supplier<O> asSupplier(final FailableSupplier<O, ?> supplier) {
452 return () -> get(supplier);
453 }
454
455 /**
456 * Calls a callable and rethrows any exception as a {@link RuntimeException}.
457 *
458 * @param callable the callable to call
459 * @param <O> the return type of the callable
460 * @param <T> the type of checked exception the callable may throw
461 * @return the value returned from the callable
462 */
463 public static <O, T extends Throwable> O call(final FailableCallable<O, T> callable) {
464 return get(callable::call);
465 }
466
467 /**
468 * Invokes a supplier, and returns the result.
469 *
470 * @param supplier The supplier to invoke.
471 * @param <O> The suppliers output type.
472 * @param <T> The type of checked exception, which the supplier can throw.
473 * @return The object, which has been created by the supplier
474 * @since 3.10
475 */
476 public static <O, T extends Throwable> O get(final FailableSupplier<O, T> supplier) {
477 try {
478 return supplier.get();
479 } catch (final Throwable t) {
480 throw rethrow(t);
481 }
482 }
483
484 /**
485 * Invokes a boolean supplier, and returns the result.
486 *
487 * @param supplier The boolean supplier to invoke.
488 * @param <T> The type of checked exception, which the supplier can throw.
489 * @return The boolean, which has been created by the supplier
490 */
491 private static <T extends Throwable> boolean getAsBoolean(final FailableBooleanSupplier<T> supplier) {
492 try {
493 return supplier.getAsBoolean();
494 } catch (final Throwable t) {
495 throw rethrow(t);
496 }
497 }
498
499 /**
500 * Rethrows a {@link Throwable} as an unchecked exception. If the argument is already unchecked, namely a
501 * {@link RuntimeException} or {@link Error} then the argument will be rethrown without modification. If the
502 * exception is {@link IOException} then it will be wrapped into a {@link UncheckedIOException}. In every other
503 * cases the exception will be wrapped into a {@code
504 * UndeclaredThrowableException}
505 *
506 * <p>
507 * Note that there is a declared return type for this method, even though it never returns. The reason for that is
508 * to support the usual pattern:
509 * </p>
510 *
511 * <pre>
512 * throw rethrow(myUncheckedException);</pre>
513 *
514 * <p>
515 * instead of just calling the method. This pattern may help the Java compiler to recognize that at that point an
516 * exception will be thrown and the code flow analysis will not demand otherwise mandatory commands that could
517 * follow the method call, like a {@code return} statement from a value returning method.
518 * </p>
519 *
520 * @param throwable The throwable to rethrow possibly wrapped into an unchecked exception
521 * @return Never returns anything, this method never terminates normally.
522 */
523 public static RuntimeException rethrow(final Throwable throwable) {
524 Objects.requireNonNull(throwable, "throwable");
525 ExceptionUtils.throwUnchecked(throwable);
526 if (throwable instanceof IOException) {
527 throw new UncheckedIOException((IOException) throwable);
528 }
529 throw new UndeclaredThrowableException(throwable);
530 }
531
532 /**
533 * Runs a runnable and rethrows any exception as a {@link RuntimeException}.
534 *
535 * @param runnable The runnable to run
536 * @param <T> the type of checked exception the runnable may throw
537 */
538 public static <T extends Throwable> void run(final FailableRunnable<T> runnable) {
539 try {
540 runnable.run();
541 } catch (final Throwable t) {
542 throw rethrow(t);
543 }
544 }
545
546 /**
547 * Converts the given collection into a {@link FailableStream}. The {@link FailableStream} consists of the
548 * collections elements. Shortcut for
549 *
550 * <pre>
551 * Functions.stream(collection.stream());</pre>
552 *
553 * @param collection The collection, which is being converted into a {@link FailableStream}.
554 * @param <O> The collections element type. (In turn, the result streams element type.)
555 * @return The created {@link FailableStream}.
556 * @since 3.10
557 */
558 public static <O> FailableStream<O> stream(final Collection<O> collection) {
559 return new FailableStream<>(collection.stream());
560 }
561
562 /**
563 * Converts the given stream into a {@link FailableStream}. The {@link FailableStream} consists of the same
564 * elements, than the input stream. However, failable lambdas, like {@link FailablePredicate},
565 * {@link FailableFunction}, and {@link FailableConsumer} may be applied, rather than {@link Predicate},
566 * {@link Function}, {@link Consumer}, etc.
567 *
568 * @param stream The stream, which is being converted into a {@link FailableStream}.
569 * @param <O> The streams element type.
570 * @return The created {@link FailableStream}.
571 * @since 3.10
572 */
573 public static <O> FailableStream<O> stream(final Stream<O> stream) {
574 return new FailableStream<>(stream);
575 }
576
577 /**
578 * Tests a predicate and rethrows any exception as a {@link RuntimeException}.
579 *
580 * @param predicate the predicate to test
581 * @param object1 the first input to test by {@code predicate}
582 * @param object2 the second input to test by {@code predicate}
583 * @param <O1> the type of the first argument the predicate tests
584 * @param <O2> the type of the second argument the predicate tests
585 * @param <T> the type of checked exception the predicate may throw
586 * @return the boolean value returned by the predicate
587 */
588 public static <O1, O2, T extends Throwable> boolean test(final FailableBiPredicate<O1, O2, T> predicate,
589 final O1 object1, final O2 object2) {
590 return getAsBoolean(() -> predicate.test(object1, object2));
591 }
592
593 /**
594 * Tests a predicate and rethrows any exception as a {@link RuntimeException}.
595 *
596 * @param predicate the predicate to test
597 * @param object the input to test by {@code predicate}
598 * @param <O> the type of argument the predicate tests
599 * @param <T> the type of checked exception the predicate may throw
600 * @return the boolean value returned by the predicate
601 */
602 public static <O, T extends Throwable> boolean test(final FailablePredicate<O, T> predicate, final O object) {
603 return getAsBoolean(() -> predicate.test(object));
604 }
605
606 /**
607 * A simple try-with-resources implementation, that can be used, if your objects do not implement the
608 * {@link AutoCloseable} interface. The method executes the {@code action}. The method guarantees, that <em>all</em>
609 * the {@code resources} are being executed, in the given order, afterwards, and regardless of success, or failure.
610 * If either the original action, or any of the resource action fails, then the <em>first</em> failure (AKA
611 * {@link Throwable}) is rethrown. Example use:
612 *
613 * <pre>
614 * {@code
615 * final FileInputStream fis = new FileInputStream("my.file");
616 * Functions.tryWithResources(useInputStream(fis), null, () -> fis.close());
617 * }</pre>
618 *
619 * @param action The action to execute. This object <em>will</em> always be invoked.
620 * @param errorHandler An optional error handler, which will be invoked finally, if any error occurred. The error
621 * handler will receive the first error, AKA {@link Throwable}.
622 * @param resources The resource actions to execute. <em>All</em> resource actions will be invoked, in the given
623 * order. A resource action is an instance of {@link FailableRunnable}, which will be executed.
624 * @see #tryWithResources(FailableRunnable, FailableRunnable...)
625 */
626 @SafeVarargs
627 public static void tryWithResources(final FailableRunnable<? extends Throwable> action,
628 final FailableConsumer<Throwable, ? extends Throwable> errorHandler,
629 final FailableRunnable<? extends Throwable>... resources) {
630 final org.apache.commons.lang3.function.FailableRunnable<?>[] fr = new org.apache.commons.lang3.function.FailableRunnable[resources.length];
631 Arrays.setAll(fr, i -> () -> resources[i].run());
632 Failable.tryWithResources(action::run, errorHandler != null ? errorHandler::accept : null, fr);
633 }
634
635 /**
636 * A simple try-with-resources implementation, that can be used, if your objects do not implement the
637 * {@link AutoCloseable} interface. The method executes the {@code action}. The method guarantees, that <em>all</em>
638 * the {@code resources} are being executed, in the given order, afterwards, and regardless of success, or failure.
639 * If either the original action, or any of the resource action fails, then the <em>first</em> failure (AKA
640 * {@link Throwable}) is rethrown. Example use:
641 *
642 * <pre>
643 * {@code
644 * final FileInputStream fis = new FileInputStream("my.file");
645 * Functions.tryWithResources(useInputStream(fis), () -> fis.close());
646 * }</pre>
647 *
648 * @param action The action to execute. This object <em>will</em> always be invoked.
649 * @param resources The resource actions to execute. <em>All</em> resource actions will be invoked, in the given
650 * order. A resource action is an instance of {@link FailableRunnable}, which will be executed.
651 * @see #tryWithResources(FailableRunnable, FailableConsumer, FailableRunnable...)
652 */
653 @SafeVarargs
654 public static void tryWithResources(final FailableRunnable<? extends Throwable> action,
655 final FailableRunnable<? extends Throwable>... resources) {
656 tryWithResources(action, null, resources);
657 }
658
659 /**
660 * Constructs a new instance.
661 */
662 public Functions() {
663 // empty
664 }
665 }