Class Fishbowl

java.lang.Object
com.github.stefanbirkner.fishbowl.Fishbowl

public class Fishbowl extends Object
Fishbowl provides helper methods for dealing with exceptions.

Wrap Exceptions

There are three options for dealing with checked exceptions that are thrown inside of a method.

  • Catch the exception and do some error handling.
  • Add the exception's class to the throws part of the method's signature and don't handle it.
  • Throw a RuntimeException that encloses the original exception.

The methods wrapCheckedException(Statement) (for statements without a return value) and wrapCheckedException(StatementWithReturnValue) (for statements with a return value) can be used for the third option. They replace the try-catch-throw-RuntimeException snippet that is usually used.

Default Values

Sometimes exceptions are best handled by returning a default value. This can be done by a single line of code with defaultIfException(StatementWithReturnValue, Class, Object)

Ignore Exceptions

Sometimes it is appropriate to continue if a void method fails. This can be done with ignoreException(Statement) or ignoreException(Statement, Class).

Expose Exceptions

Fishbowl can expose exceptions that are thrown by an arbitrary piece of code. Thus you can write tests for that piece of code by following the AAA (Arrange-Act-Assert) pattern. Use exceptionThrownBy(Statement) for catching any Throwable or use exceptionThrownBy(Statement, Class) for catching exceptions of a specific type only.

  • Constructor Details

    • Fishbowl

      private Fishbowl()
      This class only provides static methods. Hence nobody should create Fishbowl objects.
  • Method Details

    • defaultIfException

      public static <V> V defaultIfException(StatementWithReturnValue<V> statement, Class<? extends Throwable> exceptionType, V defaultValue)
      Executes the given statement and returns the statement's return value if no exception is thrown or the default value if an exception of the specified type is thrown.
         public void doSomething() {
           long value = defaultIfException(() -> parseLong("NaN"), NumberFormatException.class, 0L);
           //value is 0
         }
       

      (Any other checked exception is wrapped just as it is wrapped by wrapCheckedException(StatementWithReturnValue).)

      Type Parameters:
      V - type of the value that is returned by the statement.
      Parameters:
      statement - The statement that is executed.
      exceptionType - the type of exception for which the default value is returned.
      defaultValue - this value is returned if the statement throws an exception of the specified type.
      Returns:
      the return value of the statement or the default value.
    • exceptionThrownBy

      public static Throwable exceptionThrownBy(Statement statement)
      Executes the provided statement and returns the exception that has been thrown by the statement. This is useful for writing tests for exceptions according to the AAA (Arrange-Act-Assert) pattern.

      The following test verifies that the statement noString.trim() throws a NullPointerException.

       @Test
       public void anExceptionIsThrown() {
         String noString = null;
         Throwable exception = exceptionThrownBy}(() -> noString.trim());
         assertEquals(NullPointerException.class, exception.getClass());
       }
       
      Parameters:
      statement - an arbitrary piece of code.
      Returns:
      The exception thrown by the statement.
      Throws:
      ExceptionNotThrownFailure - if the statement didn't throw an exception.
      See Also:
    • exceptionThrownBy

      public static <T extends Throwable> T exceptionThrownBy(Statement statement, Class<T> type)
      Executes the provided statement and returns the exception that has been thrown by the statement if it has the specified type. This is useful for writing tests for exceptions according to the AAA (Arrange-Act-Assert) pattern in case that you need to check properties of the exception.

      Example:

       FooException exception = exceptionThrownBy(
               () -> { throw new FooException(3); }, FooException.class);
       assertEquals(3, exception.getValue())
       
      Type Parameters:
      T - the type of the exception that should be exposed.
      Parameters:
      statement - an arbitrary piece of code.
      type - the type of the exception that should be exposed.
      Returns:
      The exception thrown by the statement.
      Throws:
      ExceptionNotThrownFailure - if the statement didn't throw an exception.
      ExceptionWithWrongTypeThrownFailure - if the statement threw an exception of a different type.
      See Also:
    • wrapCheckedException

      public static void wrapCheckedException(Statement statement)
      Executes the given statement and encloses any checked exception thrown with an unchecked WrappedException, that is thrown instead. The method
         public void doSomething() {
           wrapCheckedException(() -> throw new IOException());
         }
       

      throws a WrappedException that encloses the IOException.

      This avoids adding throws IOException to the method's signature and is a replacement for the common try-catch-throw-RuntimeException pattern:

         public void doSomething() {
           try {
               throw new IOException();
           } catch (IOException e) {
               throw new RuntimeException(e);
           }
         }
       
      Parameters:
      statement - The statement that is executed.
      See Also:
    • wrapCheckedException

      public static <V> V wrapCheckedException(StatementWithReturnValue<V> statement)
      Executes the given statement and encloses any checked exception thrown with an unchecked WrappedException, that is thrown instead. Returns the statement's return value if no exception is thrown.
         public void doSomething() {
           URL url = wrapCheckedException(() -> new URL("http://something/"));
           ...
         }
       

      This avoids adding throws MalformedURLException to the method's signature and is a replacement for the common try-catch-throw-RuntimeException pattern:

         public void doSomething() {
           URL url;
           try {
               url = new URL("http://something/");
           } catch (MalformedURLException e) {
               throw new RuntimeException(e);
           }
           ...
         }
       
      Type Parameters:
      V - type of the value that is returned by the statement.
      Parameters:
      statement - The statement that is executed.
      Returns:
      the return value of the statement.
      See Also:
    • ignoreException

      public static void ignoreException(Statement statement)
      Executes the given statement and suppresses any exception thrown by the statement.
         public void doSomething() {
           MyWorker worker = new MyWorker();
           ignoreException(() -> worker.doSomethingThatThrowsAnException());
           //the following statement is executed even if the worker threw an
           //exception.
           doSomethingElse();
         }
       
      Parameters:
      statement - the statement that is executed.
      See Also:
    • ignoreException

      public static void ignoreException(Statement statement, Class<? extends Throwable> type)
      Executes the given statement and suppresses any exception of the specified type that is thrown by the statement.
         public void doSomething() {
           MyWorker worker = new MyWorker();
           ignoreException(
             () -> worker.doSomethingThatThrowsAnException(),
             IllegalArgumentException.class);
           //the following statement is executed even if the worker threw an
           //IllegalArgumentException.
           doSomethingElse();
         }
       

      RuntimeExceptions of a different type are rethrown. Other exceptions of a different type are wrapped by a WrappedException that is thrown instead.

      Parameters:
      statement - the statement that is executed.
      type - the type of exception that is ignored.
      Throws:
      WrappedException - if the statement throws a checked exception that is not of the specified type. The WrappedException's cause is the checked exception.
      RuntimeException - if the statement throws a RuntimeException that is not of the specified type.
      Error - if the statement throws an Error that is not of the specified type.
      See Also: