Try this little trick borrowed from Netty.
So you have an exception:
- you don't want to check
- you don't want to swallow
- you don't want to pollute the method signature
Consider the following class Throw
:
public class Throw {
public static <T> T unchecked(Throwable throwable) {
return Throw.<T, RuntimeException>_unchecked(throwable);
}
@SuppressWarnings("unchecked")
private static <T, E extends Throwable> T _unchecked(Throwable throwable)
throws E {
throw (E)throwable;
}
}
I can help with all of the above and is applied in the following way:
T methodWithExceptionToBubble() {
try {
return getT();
}
catch (Exception e) {
return Throw.unchecked(e);
}
}
Through the power of generics erasure, this trick forgets the type of throwable
, satisfies the return, and avoids the need to wrap the exception in a wrapper (such as RuntimeException).
Brilliant!
Note: There is a simplified version suggested by @bjhargrave below.
public class ThrowNoReturn {
public static void unchecked(Throwable throwable) {
ThrowNoReturn.<RuntimeException>_unchecked(throwable);
}
@SuppressWarnings("unchecked")
private static <E extends Throwable> void _unchecked(Throwable throwable)
throws E {
throw (E)throwable;
}
}
However, this removes the capacity to simplify the return case. One would have to add an extra return line to satisfy the compiler.
T methodWithExceptionToBubble() {
try {
return getA_T();
}
catch (Exception e) {
ThrowNoReturn.unchecked(e);
return null;
}
}
We could debate which is better, for simplicity of code over use, but since I didn't create this I'm going to stick with the original design as the choice option.