Get detail messages of chained exceptions Java
Asked Answered
V

7

28

I'd like to know how I could throw a "final" Exception, containing a detailed message with all the detailed messages of a number of chained exceptions.

For example suppose a code like this:

try {
  try {
    try {
      try {
        //Some error here
      } catch (Exception e) {
        throw new Exception("FIRST EXCEPTION", e);
      }
    } catch (Exception e) {
      throw new Exception("SECOND EXCEPTION", e);
    }
  } catch (Exception e) {
    throw new Exception("THIRD EXCEPTION", e);
  }
} catch (Exception e) {
  String allMessages = //all the messages
  throw new Exception(allMessages, e);
}

I'm not interested in the full stackTrace, but only in the messages, I wrote. I mean, I'd like to have a result like this:

java.lang.Exception: THIRD EXCEPTION + SECOND EXCEPTION + FIRST EXCEPTION
Virginium answered 13/4, 2013 at 11:24 Comment(0)
J
43

I think what you need is:

public static List<String> getExceptionMessageChain(Throwable throwable) {
    List<String> result = new ArrayList<String>();
    while (throwable != null) {
        result.add(throwable.getMessage());
        throwable = throwable.getCause();
    }
    return result; //["THIRD EXCEPTION", "SECOND EXCEPTION", "FIRST EXCEPTION"]
}
Juvenility answered 13/4, 2013 at 11:33 Comment(1)
Excellent solution, thanx! Other suggestions were also good, but this way I have the code centralised in a single method, and I only have to modify the methods from where I throw the final Exception...Virginium
K
3

you can better use it this way, merge the message() of previous Exception with the message() of new Exception you are throwing:

      } catch (Exception e) {
          throw new Exception("FIRST EXCEPTION" + e.getMessage(), e);
      }
Kinesiology answered 13/4, 2013 at 11:27 Comment(0)
P
1

Cycle through the exception cause and append the message in each exception.

    try
    {
        try
        {
            try
            {
                try
                {
                    throw new RuntimeException("Message");
                }
                catch (Exception e)
                {
                    throw new Exception("FIRST EXCEPTION", e);
                }
            }
            catch (Exception e)
            {
                throw new Exception("SECOND EXCEPTION", e);
            }
        }
        catch (Exception e)
        {
            throw new Exception("THIRD EXCEPTION", e);
        }
    }
    catch (Exception e)
    {
        String message = e.getMessage();
        Throwable inner = null;
        Throwable root = e;
        while ((inner = root.getCause()) != null)
        {
            message += " " + inner.getMessage();
            root = inner;
        }
        System.out.println(message);
    }

Which prints

THIRD EXCEPTION SECOND EXCEPTION FIRST EXCEPTION Message

Propene answered 13/4, 2013 at 11:31 Comment(0)
A
1

You can just add the previous exception message on each exception

This is an example :

public static void main(String[] args) {

    try {
        try {
            try {
                try {
                    throw new Exception();
                    // Some error here
                } catch (Exception e) {
                    throw new Exception("FIRST EXCEPTION", e);
                }
            } catch (Exception e) {
                Exception e2 = new Exception("SECOND EXCEPTION + " + e.getMessage());
                throw e2;
            }
        } catch (Exception e) {
            Exception e3 = new Exception("THIRD EXCEPTION + " + e.getMessage());
            throw e3;
        }
    } catch (Exception e) {
        System.out.println(e);
    }
}

The result is : java.lang.Exception: THIRD EXCEPTION + SECOND EXCEPTION + FIRST EXCEPTION

Ashram answered 13/4, 2013 at 11:34 Comment(0)
A
1

Here is a nice utility for converting chained exceptions to string:

public final class ThrowableUtil {

    private ThrowableUtil() {}

    public static String chainedString(@NonNull Throwable throwable) {
        StringBuilder SB = new StringBuilder(throwable.toString());
        while((throwable = throwable.getCause()) != null)
            SB.append("\ncaused by ").append(throwable);
        return SB.toString();
    }

    public static String chainedString(@NonNull String msg, @NonNull Throwable throwable) {
        StringBuilder SB = new StringBuilder(msg);
        do {
            SB.append("\ncaused by ").append(throwable);
        } while((throwable = throwable.getCause()) != null);
        return SB.toString();
    }

}

Example output:

ThrowableUtil.chainedString(e);

produces

java.io.IOException: Failed to create required video encoder
caused by java.lang.RuntimeException: Invalid mime type

Another example output:

ThrowableUtil.chainedString("Writing of media file failed", e);

produces

Writing of media file failed
caused by java.io.IOException: Failed to create required video encoder
caused by java.lang.RuntimeException: Invalid mime type
Aniseed answered 24/1, 2021 at 16:26 Comment(1)
wondering if it's already implemented in some of many 'exception utils' by apache or google.. but couldn't find :(Week
N
0

I had saved all attributes in a class object with the following example:

public List<ErrorMessage> getMessageList(Throwable throwable) {
        List<ErrorMessage> errorMessageList =  new ArrayList<ErrorMessage>();
        while (throwable != null) {
            ErrorMessage message = new ErrorMessage();
            message.set_message( throwable.getMessage());
            message.set_line(throwable.getStackTrace()[0].getLineNumber());
            message.set_methodName(throwable.getStackTrace()[0].getMethodName());
            message.set_fileName(throwable.getStackTrace()[0].getFileName() );
            message.set_className(throwable.getStackTrace()[0].getClassName());
            errorMessageList.add(message);
            throwable = throwable.getCause();
        }
        return errorMessageList; 
    }
Naphthol answered 30/3, 2018 at 20:11 Comment(0)
A
0

Maybe simpler

try {
   // code that throws exception
} catch(Throwable e ) {
    var messages = new ArrayList<String>();
    
    do {
        messages.add(e.getMessage());
        e = e.getCause();
    } while( e!= null ); 
    
    var message = String.join(" -> ", messages);    
    System.out.println(message);
}
Arlenarlena answered 24/1, 2022 at 15:0 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.