Tips and Hints with Exceptions

We list some tips and hints here that are no best practices in the strict sense, but may prove helpful anyway.

No Generic Exceptions

A generic class must not subclass Throwable or any of its subclasses.

public class MyException <T> extends Throwable { // DOES NOT COMPILE!

The generic information is not available at runtime and catching exceptions by their generic type will not work.

try {
  ...
  }
  catch(final MyException<String> e) { // DOES NOT WORK!
  ...
  }

So keep in mind that there is no generic exception.

Exception with no Cause

Just in case you have a root cause, but the exception you want to throw does not support setting the root cause throwable in the constructor. You can use Throwable.initCause(Throwable) instead.

final Throwable t = new IllegalArgumentException("Wrong arg...");
final NullPointerException npe = new NullPointerException("NPE...");
npe.initCause(t);

Calling npe.printStackTrace() will print the following to standard error:

java.lang.NullPointerException: NPE...
  at de.smartics.exceptions.Main.main(Main.java:62)
Caused by: java.lang.IllegalArgumentException: Wrong arg...
  at de.smartics.exceptions.Main.main(Main.java:60)

Testing Serializability

It is often useful to proof that instances of a class are serializable. Open an object stream for writing and reading. There is an example where we test ConfigurationExceptionTest for serializability. The logic of serializing and deserializing can be found in a

The test looks like this:

@Test
  public void testSerial() throws Exception
  {
    final ConfigurationException uut = new MethodAccessConfigurationException(
        null, ConfigurationExceptionCode.GENERIC, "propertyName", Object.class,
        "methodName");
    SerialTestUtil.runSerialization(uut);
    assertTrue("Serialization successful.", true);
  }

The methods of the helper class are as follows:

public static <T> T runSerialization(final T uut) throws IOException,
      ClassNotFoundException
  {
    final byte[] data = writeObject(uut);
    return SerialTestUtils.<T>readObject(data);
  }

  private static <T> T readObject(final byte[] data) throws IOException,
      ClassNotFoundException
  {
    final ByteArrayInputStream in = new ByteArrayInputStream(data);
    ObjectInputStream ois = null;
    try
    {
      ois = new ObjectInputStream(in);
      @SuppressWarnings("unchecked")
      final T result = (T) ois.readObject();
      return result;
    }
    finally
    {
      IOUtils.closeQuietly(ois);
    }
  }

  private static <T> byte[] writeObject(final T uut) throws IOException
  {
    final ByteArrayOutputStream out = new ByteArrayOutputStream();
    ObjectOutputStream oos = null;
    try
    {
      oos = new ObjectOutputStream(out);
      oos.writeObject(uut);
    }
    finally
    {
      IOUtils.closeQuietly(oos);
    }
    return out.toByteArray();
  }