The last couple of posts have covered how to handle exceptions with Java 8 functional interfaces. This post discusses how to handle arbitrary functional interfaces as of KλudJe 0.2.
- Java 8 Method References can be Functional Interface Type Adapters
- Exploiting Adapters with KλudJe
- N-ary Interfaces
- Generating Exception Adapting Types
Java 8 Method References can be Functional Interface Type Adapters
Java 8 method references provide a limited mechanism to create type adapters.
A trivial application that adapts a Java 8 type to a Google Guava type:
public class Adaptation { public static void main(String[] args) { java.util.function.Supplier<?> java = () -> "Hello, World!"; com.google.common.base.Supplier<?> guava = java::get; System.out.println(guava.get()); } }
Exploiting Adapters with KλudJe
Here is an AutoCloseable
instance adapted to a Closeable
subtype:
import java.io.Closeable; import java.io.IOException; import static uk.kludje.fn.lang.URunnable.asURunnable; public class AdapterInTheMiddle { public static void main(String[] args) throws IOException { AutoCloseable original = () -> { throw new IOException("expected!"); }; Closeable adapter = asURunnable(original::close)::run; adapter.close(); } }
AutoCloseable
generally throws the overly broad Exception
type.
The URunnable
type acts as an intermediary even though it is neither an AutoCloseable
nor a Closeable
.
Just FYI, here is what the stack trace looks like:
Exception in thread "main" java.io.IOException: expected! at AdapterInTheMiddle.lambda$main$0(AdapterInTheMiddle.java:8) at AdapterInTheMiddle$$Lambda$1/1160460865.close(Unknown Source) at AdapterInTheMiddle$$Lambda$2/2001049719.$run(Unknown Source) at uk.kludje.fn.lang.URunnable.run(URunnable.java:18) at AdapterInTheMiddle$$Lambda$3/1746572565.close(Unknown Source) at AdapterInTheMiddle.main(AdapterInTheMiddle.java:11)
N-ary Interfaces
The Java 8 standard API provides 0, 1 & 2 arity functional interfaces with both void
and generic return types.
These are: Runnable;
Consumer; BiConsumer; Supplier; Function; BiFunction.
KλudJe 0.2 fills the gap in the 3-7 argument range just to provide base types for the exception-propagating versions. See the uk.kludje.fn.nary package for details. If you have more than seven arguments you probably need a copy of Code Complete.
Generating Exception Adapting Types
KλudJe does not provide mirrors for every functional interface or method reference signature imaginable. The n-ary interfaces provided may incur autoboxing costs for interfaces that use primitives.
The exception handling types in KλudJe are generated using annotation processors. Despite being standardized in Java 6 the annotation processor API has seen limited adoption and you may have to jump through hoops to enable processors in your development environment. Caveat emptor.
To generate your own equivalent types you need to depend on the kludje-annotation module. In Maven projects:
<dependency> <groupId>uk.kludje</groupId> <artifactId>kludje-annotation</artifactId> <version>0.2</version> </dependency>
Create a package for your functional types with a package-info.java
file specifying the types you want to process.
//package-info.java for foo @uk.kludje.annotation.UncheckedFunctionalInterface(foo.YourFuncIface1.class) @uk.kludje.annotation.UncheckedFunctionalInterface(foo.YourFuncIface2.class) package foo;
Your build environment will need to execute the
uk.kludje.annotation.processor.UncheckedFunctionalInterfaceProcessor
annotation processor if it doesn't do it automatically.
No comments:
Post a Comment
All comments are moderated