001/*
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.commons.lang3;
018
019import java.io.IOException;
020import java.io.UncheckedIOException;
021import java.lang.reflect.UndeclaredThrowableException;
022import java.util.Collection;
023import java.util.Objects;
024import java.util.concurrent.Callable;
025import java.util.function.BiConsumer;
026import java.util.function.BiFunction;
027import java.util.function.BiPredicate;
028import java.util.function.Consumer;
029import java.util.function.Function;
030import java.util.function.Predicate;
031import java.util.function.Supplier;
032import java.util.stream.Stream;
033
034import org.apache.commons.lang3.Streams.FailableStream;
035
036
037/** This class provides utility functions, and classes for working with the
038 * {@code java.util.function} package, or more generally, with Java 8
039 * lambdas.
040 * More specifically, it attempts to address the fact that lambdas are supposed
041 * not to throw Exceptions, at least not checked Exceptions, aka instances of
042 * {@link Exception}. This enforces the use of constructs like
043 * <pre>{@code
044 *   Consumer<java.lang.reflect.Method> consumer = (m) -> {
045 *       try {
046 *           m.invoke(o, args);
047 *       } catch (Throwable t) {
048 *           throw Functions.rethrow(t);
049 *       }
050 *   };
051 * }</pre>
052 * By replacing a {@link java.util.function.Consumer Consumer&lt;O&gt;} with a
053 * {@link FailableConsumer FailableConsumer&lt;O,? extends Throwable&gt;}, this can be
054 * written like follows:
055 * <pre>{@code
056 *   Functions.accept((m) -> m.invoke(o,args));
057 * }</pre>
058 * Obviously, the second version is much more concise and the spirit of
059 * Lambda expressions is met better than the second version.
060 */
061public class Functions {
062
063    @FunctionalInterface
064    public interface FailableRunnable<T extends Throwable> {
065        /**
066         * Runs the function.
067         * @throws T if the function fails
068         */
069        void run() throws T;
070    }
071
072    @FunctionalInterface
073    public interface FailableCallable<O, T extends Throwable> {
074        /**
075         * Calls the callable.
076         * @return The value returned from the callable
077         * @throws T if the callable fails
078         */
079        O call() throws T;
080    }
081
082    @FunctionalInterface
083    public interface FailableConsumer<O, T extends Throwable> {
084        /**
085         * Accepts the consumer.
086         * @param object the parameter for the consumable to accept
087         * @throws T if the consumer fails
088         */
089        void accept(O object) throws T;
090    }
091
092    @FunctionalInterface
093    public interface FailableBiConsumer<O1, O2, T extends Throwable> {
094        /**
095         * Accepts the consumer.
096         * @param object1 the first parameter for the consumable to accept
097         * @param object2 the second parameter for the consumable to accept
098         * @throws T if the consumer fails
099         */
100        void accept(O1 object1, O2 object2) throws T;
101    }
102
103    @FunctionalInterface
104    public interface FailableFunction<I, O, T extends Throwable> {
105        /**
106         * Apply the function.
107         * @param input the input for the function
108         * @return the result of the function
109         * @throws T if the function fails
110         */
111        O apply(I input) throws T;
112    }
113
114    @FunctionalInterface
115    public interface FailableBiFunction<I1, I2, O, T extends Throwable> {
116        /**
117         * Apply the function.
118         * @param input1 the first input for the function
119         * @param input2 the second input for the function
120         * @return the result of the function
121         * @throws T if the function fails
122         */
123        O apply(I1 input1, I2 input2) throws T;
124    }
125
126    @FunctionalInterface
127    public interface FailablePredicate<O, T extends Throwable> {
128        /**
129         * Test the predicate.
130         * @param object the object to test the predicate on
131         * @return the predicate's evaluation
132         * @throws T if the predicate fails
133         */
134        boolean test(O object) throws T;
135    }
136
137    @FunctionalInterface
138    public interface FailableBiPredicate<O1, O2, T extends Throwable> {
139        /**
140         * Test the predicate.
141         * @param object1 the first object to test the predicate on
142         * @param object2 the second object to test the predicate on
143         * @return the predicate's evaluation
144         * @throws T if the predicate fails
145         */
146        boolean test(O1 object1, O2 object2) throws T;
147    }
148
149    @FunctionalInterface
150    public interface FailableSupplier<O, T extends Throwable> {
151        /**
152         * Supplies an object
153         * @return the suppliers result
154         * @throws T if the supplier fails
155         */
156        O get() throws T;
157    }
158
159    /**
160     * Converts the given {@link FailableRunnable} into a standard {@link Runnable}.
161     *
162     * @param runnable a {@code FailableRunnable}
163     * @return a standard {@code Runnable}
164     */
165    public static Runnable asRunnable(final FailableRunnable<?> runnable) {
166        return () -> run(runnable);
167    }
168
169    /**
170     * Converts the given {@link FailableConsumer} into a standard {@link Consumer}.
171     *
172     * @param <I> the type used by the consumers
173     * @param consumer a {@code FailableConsumer}
174     * @return a standard {@code Consumer}
175     */
176    public static <I> Consumer<I> asConsumer(final FailableConsumer<I, ?> consumer) {
177        return input -> accept(consumer, input);
178    }
179
180    /**
181     * Converts the given {@link FailableCallable} into a standard {@link Callable}.
182     *
183     * @param <O> the type used by the callables
184     * @param callable a {@code FailableCallable}
185     * @return a standard {@code Callable}
186     */
187    public static <O> Callable<O> asCallable(final FailableCallable<O, ?> callable) {
188        return () -> call(callable);
189    }
190
191    /**
192     * Converts the given {@link FailableBiConsumer} into a standard {@link BiConsumer}.
193     *
194     * @param <I1> the type of the first argument of the consumers
195     * @param <I2> the type of the second argument of the consumers
196     * @param consumer a failable {@code BiConsumer}
197     * @return a standard {@code BiConsumer}
198     */
199    public static <I1, I2> BiConsumer<I1, I2> asBiConsumer(final FailableBiConsumer<I1, I2, ?> consumer) {
200        return (input1, input2) -> accept(consumer, input1, input2);
201    }
202
203    /**
204     * Converts the given {@link FailableFunction} into a standard {@link Function}.
205     *
206     * @param <I> the type of the input of the functions
207     * @param <O> the type of the output of the functions
208     * @param function a {code FailableFunction}
209     * @return a standard {@code Function}
210     */
211    public static <I, O> Function<I, O> asFunction(final FailableFunction<I, O, ?> function) {
212        return input -> apply(function, input);
213    }
214
215    /**
216     * Converts the given {@link FailableBiFunction} into a standard {@link BiFunction}.
217     *
218     * @param <I1> the type of the first argument of the input of the functions
219     * @param <I2> the type of the second argument of the input of the functions
220     * @param <O> the type of the output of the functions
221     * @param function a {@code FailableBiFunction}
222     * @return a standard {@code BiFunction}
223     */
224    public static <I1, I2, O> BiFunction<I1, I2, O> asBiFunction(final FailableBiFunction<I1, I2, O, ?> function) {
225        return (input1, input2) -> apply(function, input1, input2);
226    }
227
228    /**
229     * Converts the given {@link FailablePredicate} into a standard {@link Predicate}.
230     *
231     * @param <I> the type used by the predicates
232     * @param predicate a {@code FailablePredicate}
233     * @return a standard {@code Predicate}
234     */
235    public static <I> Predicate<I> asPredicate(final FailablePredicate<I, ?> predicate) {
236        return input -> test(predicate, input);
237    }
238
239    /**
240     * Converts the given {@link FailableBiPredicate} into a standard {@link BiPredicate}.
241     *
242     * @param <I1> the type of the first argument used by the predicates
243     * @param <I2> the type of the second argument used by the predicates
244     * @param predicate a {@code FailableBiPredicate}
245     * @return a standard {@code BiPredicate}
246     */
247    public static <I1, I2> BiPredicate<I1, I2> asBiPredicate(final FailableBiPredicate<I1, I2, ?> predicate) {
248        return (input1, input2) -> test(predicate, input1, input2);
249    }
250
251    /**
252     * Converts the given {@link FailableSupplier} into a standard {@link Supplier}.
253     *
254     * @param <O> the type supplied by the suppliers
255     * @param supplier a {@code FailableSupplier}
256     * @return a standard {@code Supplier}
257     */
258    public static <O> Supplier<O> asSupplier(final FailableSupplier<O, ?> supplier) {
259        return () -> get(supplier);
260    }
261
262    /**
263     * Runs a runnable and rethrows any exception as a {@link RuntimeException}.
264     * @param runnable The runnable to run
265     * @param <T> the type of checked exception the runnable may throw
266     */
267    public static <T extends Throwable> void run(final FailableRunnable<T> runnable) {
268        try {
269            runnable.run();
270        } catch (final Throwable t) {
271            throw rethrow(t);
272        }
273    }
274
275    /**
276     * Calls a callable and rethrows any exception as a {@link RuntimeException}.
277     * @param callable the callable to call
278     * @param <O> the return type of the callable
279     * @param <T> the type of checked exception the callable may throw
280     * @return the value returned from the callable
281     */
282    public static <O, T extends Throwable> O call(final FailableCallable<O, T> callable) {
283        return get(callable::call);
284    }
285
286    /**
287     * Consumes a consumer and rethrows any exception as a {@link RuntimeException}.
288     * @param consumer the consumer to consume
289     * @param object the object to consume by {@code consumer}
290     * @param <O> the type the consumer accepts
291     * @param <T> the type of checked exception the consumer may throw
292     */
293    public static <O, T extends Throwable> void accept(final FailableConsumer<O, T> consumer, final O object) {
294        run(() -> consumer.accept(object));
295    }
296
297    /**
298     * Consumes a consumer and rethrows any exception as a {@link RuntimeException}.
299     * @param consumer the consumer to consume
300     * @param object1 the first object to consume by {@code consumer}
301     * @param object2 the second object to consume by {@code consumer}
302     * @param <O1> the type of the first argument the consumer accepts
303     * @param <O2> the type of the second argument the consumer accepts
304     * @param <T> the type of checked exception the consumer may throw
305     */
306    public static <O1, O2, T extends Throwable> void accept(final FailableBiConsumer<O1, O2, T> consumer, final O1 object1, final O2 object2) {
307        run(() -> consumer.accept(object1, object2));
308    }
309
310    /**
311     * Applies a function and rethrows any exception as a {@link RuntimeException}.
312     * @param function the function to apply
313     * @param input the input to apply {@code function} on
314     * @param <I> the type of the argument the function accepts
315     * @param <O> the return type of the function
316     * @param <T> the type of checked exception the function may throw
317     * @return the value returned from the function
318     */
319    public static <I, O, T extends Throwable> O apply(final FailableFunction<I, O, T> function, final I input) {
320        return get(() -> function.apply(input));
321    }
322
323    /**
324     * Applies a function and rethrows any exception as a {@link RuntimeException}.
325     * @param function the function to apply
326     * @param input1 the first input to apply {@code function} on
327     * @param input2 the second input to apply {@code function} on
328     * @param <I1> the type of the first argument the function accepts
329     * @param <I2> the type of the second argument the function accepts
330     * @param <O> the return type of the function
331     * @param <T> the type of checked exception the function may throw
332     * @return the value returned from the function
333     */
334    public static <I1, I2, O, T extends Throwable> O apply(final FailableBiFunction<I1, I2, O, T> function, final I1 input1, final I2 input2) {
335        return get(() -> function.apply(input1, input2));
336    }
337
338    /**
339     * Tests a predicate and rethrows any exception as a {@link RuntimeException}.
340     * @param predicate the predicate to test
341     * @param object the input to test by {@code predicate}
342     * @param <O> the type of argument the predicate tests
343     * @param <T> the type of checked exception the predicate may throw
344     * @return the boolean value returned by the predicate
345     */
346    public static <O, T extends Throwable> boolean test(final FailablePredicate<O, T> predicate, final O object) {
347        return get(() -> predicate.test(object));
348    }
349
350    /**
351     * Tests a predicate and rethrows any exception as a {@link RuntimeException}.
352     * @param predicate the predicate to test
353     * @param object1 the first input to test by {@code predicate}
354     * @param object2 the second input to test by {@code predicate}
355     * @param <O1> the type of the first argument the predicate tests
356     * @param <O2> the type of the second argument the predicate tests
357     * @param <T> the type of checked exception the predicate may throw
358     * @return the boolean value returned by the predicate
359     */
360    public static <O1, O2, T extends Throwable> boolean test(final FailableBiPredicate<O1, O2, T> predicate, final O1 object1, final O2 object2) {
361        return get(() -> predicate.test(object1, object2));
362    }
363
364    /**
365     * Invokes the supplier, and returns the result.
366     * @param supplier The supplier to invoke.
367     * @param <O> The suppliers output type.
368     * @param <T> The type of checked exception, which the supplier can throw.
369     * @return The object, which has been created by the supplier
370     */
371    public static <O, T extends Throwable> O get(final FailableSupplier<O, T> supplier) {
372        try {
373            return supplier.get();
374        } catch (final Throwable t) {
375            throw rethrow(t);
376        }
377    }
378
379    /**
380     * Converts the given stream into a {@link FailableStream}. The
381     * {@link FailableStream} consists of the same elements, than the
382     * input stream. However, failable lambdas, like
383     * {@link FailablePredicate}, {@link FailableFunction}, and
384     * {@link FailableConsumer} may be applied, rather than
385     * {@link Predicate}, {@link Function}, {@link Consumer}, etc.
386     * @param stream The stream, which is being converted into a
387     *   {@link FailableStream}.
388     * @param <O> The streams element type.
389     * @return The created {@link FailableStream}.
390     */
391    public static <O> FailableStream<O> stream(final Stream<O> stream) {
392        return new FailableStream<>(stream);
393    }
394
395    /**
396     * Converts the given collection into a {@link FailableStream}.
397     * The {@link FailableStream} consists of the collections
398     * elements. Shortcut for
399     * <pre>
400     *   Functions.stream(collection.stream());
401     * </pre>
402     * @param collection The collection, which is being converted into a
403     *   {@link FailableStream}.
404     * @param <O> The collections element type. (In turn, the result
405     *   streams element type.)
406     * @return The created {@link FailableStream}.
407     */
408    public static <O> FailableStream<O> stream(final Collection<O> collection) {
409        return new FailableStream<>(collection.stream());
410    }
411
412
413    /**
414     * A simple try-with-resources implementation, that can be used, if your
415     * objects do not implement the {@link AutoCloseable} interface. The method
416     * executes the {@code action}. The method guarantees, that <em>all</em>
417     * the {@code resources} are being executed, in the given order, afterwards,
418     * and regardless of success, or failure. If either the original action, or
419     * any of the resource action fails, then the <em>first</em> failure (aka
420     * {@link Throwable} is rethrown. Example use:
421     * <pre>{@code
422     *   final FileInputStream fis = new FileInputStream("my.file");
423     *   Functions.tryWithResources(useInputStream(fis), null, () -> fis.close());
424     * }</pre>
425     * @param action The action to execute. This object <em>will</em> always
426     *   be invoked.
427     * @param errorHandler An optional error handler, which will be invoked finally,
428     *   if any error occurred. The error handler will receive the first
429     *   error, aka {@link Throwable}.
430     * @param resources The resource actions to execute. <em>All</em> resource
431     *   actions will be invoked, in the given order. A resource action is an
432     *   instance of {@link FailableRunnable}, which will be executed.
433     * @see #tryWithResources(FailableRunnable, FailableRunnable...)
434     */
435    @SafeVarargs
436    public static void tryWithResources(final FailableRunnable<? extends Throwable> action,
437                                            final FailableConsumer<Throwable, ? extends Throwable> errorHandler,
438                                            final FailableRunnable<? extends Throwable>... resources) {
439        final FailableConsumer<Throwable, ? extends Throwable> actualErrorHandler;
440        if (errorHandler == null) {
441            actualErrorHandler = Functions::rethrow;
442        } else {
443            actualErrorHandler = errorHandler;
444        }
445        if (resources != null) {
446            for (final FailableRunnable<? extends Throwable> failableRunnable : resources) {
447                Objects.requireNonNull(failableRunnable, "runnable");
448            }
449        }
450        Throwable th = null;
451        try {
452            action.run();
453        } catch (final Throwable t) {
454            th = t;
455        }
456        if (resources != null) {
457            for (final FailableRunnable<?> runnable : resources) {
458                try {
459                    runnable.run();
460                } catch (final Throwable t) {
461                    if (th == null) {
462                        th = t;
463                    }
464                }
465            }
466        }
467        if (th != null) {
468            try {
469                actualErrorHandler.accept(th);
470            } catch (final Throwable t) {
471                throw rethrow(t);
472            }
473        }
474    }
475
476    /**
477     * A simple try-with-resources implementation, that can be used, if your
478     * objects do not implement the {@link AutoCloseable} interface. The method
479     * executes the {@code action}. The method guarantees, that <em>all</em>
480     * the {@code resources} are being executed, in the given order, afterwards,
481     * and regardless of success, or failure. If either the original action, or
482     * any of the resource action fails, then the <em>first</em> failure (aka
483     * {@link Throwable} is rethrown. Example use:
484     * <pre>{@code
485     *   final FileInputStream fis = new FileInputStream("my.file");
486     *   Functions.tryWithResources(useInputStream(fis), () -> fis.close());
487     * }</pre>
488     * @param action The action to execute. This object <em>will</em> always
489     *   be invoked.
490     * @param resources The resource actions to execute. <em>All</em> resource
491     *   actions will be invoked, in the given order. A resource action is an
492     *   instance of {@link FailableRunnable}, which will be executed.
493     * @see #tryWithResources(FailableRunnable, FailableConsumer, FailableRunnable...)
494     */
495    @SafeVarargs
496    public static void tryWithResources(final FailableRunnable<? extends Throwable> action,
497                                            final FailableRunnable<? extends Throwable>... resources) {
498        tryWithResources(action, null, resources);
499    }
500
501    /**
502     * <p>Rethrows a {@link Throwable} as an unchecked exception. If the argument is
503     * already unchecked, namely a {@code RuntimeException} or {@code Error} then
504     * the argument will be rethrown without modification. If the exception is
505     * {@code IOException} then it will be wrapped into a {@code UncheckedIOException}.
506     * In every other cases the exception will be wrapped into a {@code
507     * UndeclaredThrowableException}</p>
508     *
509     * <p>Note that there is a declared return type for this method, even though it
510     * never returns. The reason for that is to support the usual pattern:</p>
511     *
512     * <pre>
513     *      throw rethrow(myUncheckedException);
514     * </pre>
515     *
516     * <p>instead of just calling the method. This pattern may help the Java compiler to
517     * recognize that at that point an exception will be thrown and the code flow
518     * analysis will not demand otherwise mandatory commands that could follow the
519     * method call, like a {@code return} statement from a value returning method.</p>
520     *
521     * @param throwable The throwable to rethrow ossibly wrapped into an unchecked exception
522     * @return Never returns anything, this method never terminates normally.
523     */
524    public static RuntimeException rethrow(final Throwable throwable) {
525        Objects.requireNonNull(throwable, "throwable");
526        if (throwable instanceof RuntimeException) {
527            throw (RuntimeException) throwable;
528        } else if (throwable instanceof Error) {
529            throw (Error) throwable;
530        } else if (throwable instanceof IOException) {
531            throw new UncheckedIOException((IOException) throwable);
532        } else {
533            throw new UndeclaredThrowableException(throwable);
534        }
535    }
536}