ufk
ufk

Reputation: 32144

How to display stack trace on a caught exception?

I have a generic function that prints exceptions (using log4j):

private void _showErrorMessage(Exception e) {
    log.error(e.getClass() + ": " +  e.getMessage() + ": " + e.getCause() + "\n" +  e.getStackTrace().toString());
}

Instead of seeing the stack trace I'm seeing:

[Ljava.lang.StackTraceElement;@49af7e68

How can I view the stack trace of the exception properly?

update

log.error(e) <- shows the error, but doesn't show stack trace

Upvotes: 34

Views: 80325

Answers (8)

vuhoanghiep1993
vuhoanghiep1993

Reputation: 881

I create a custom function return the beautiful stacktrace

public static Object errorStackTrace(Object obj) {
    if (obj instanceof BaseException) {
        BaseException e = (BaseException) obj;
        return JsonUtil.toJson(e);
    } else if (obj instanceof Exception) {
        Exception eObj = (Exception) obj;
        StringWriter sw = null;
        PrintWriter pw = null;
        try {
            sw = new StringWriter();
            pw = new PrintWriter(sw);
            String exceptionStack = "\r\n";
            eObj.printStackTrace(pw);
            exceptionStack = sw.toString();
            return exceptionStack;
        } catch (Exception e) {
            e.printStackTrace();
            return obj;
        } finally {
            try {
                pw.close();
                sw.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    } else {
        return obj;
    }
}

Upvotes: 0

Joachim Sauer
Joachim Sauer

Reputation: 308249

Your logging framework should have the ability to log exceptions, so simply passing the exception to the proper .error(Object, Throwable) call should be enough:

If your logging framework can't do that, or you need the stack trace in a String for any other reason, then it becomes a bit harder. You'll have to create a PrintWriter wrapping a StringWriter and call .printStackTrace() on the Exception:

StringWriter sw = new StringWriter();
ex.printStackTrace(new PrintWriter(sw));
String stacktrace = sw.toString();

Upvotes: 78

Guillaume
Guillaume

Reputation: 5557

I use the ExceptionUtils#getFullStackTrace method of Jakarta Commons Lang

Upvotes: 14

Marco C.
Marco C.

Reputation: 41

Exception Stacktrace logging shows two methods for this purpose, one based on Apache Commons and another using the standard JDK method.

Upvotes: 1

Yishai
Yishai

Reputation: 91931

The exact answer to your question is that you should call Log4J like this:

private void _showErrorMessage(Exception e) {
    log.error(e.getClass() + ": " +  e.getMessage() + ": " + e.getCause(), e);
}

Although I would dispense with the call to e.getCause() because the stacktrace will give that to you anyway, so:

private void _showErrorMessage(Exception e) {
    log.error(e.getClass() + ": " +  e.getMessage(), e);
}

ExceptionUtils is fine if you really need a string of the stacktrace, but since you are using Log4J, you lose a lot by not utilizing its built in exception handling.

Upvotes: 1

gpampara
gpampara

Reputation: 12049

You could also look at the Guava libraries from Google.

Throwables.getStackTraceAsString(Throwable throwable)

Upvotes: 4

Paul McKenzie
Paul McKenzie

Reputation: 20094

Have you tried?

private void _showErrorMessage(Exception e) {
    log.error("Hey! got an exception", e);
}

Upvotes: 21

coobird
coobird

Reputation: 161022

Throwable.getStackTrace returns an array of StackTraceElements, hence the toString method is returning a textual representation of the array itself.

In order to actually retrieve the stack trace information, one would have to go through each StackTraceElement to get more information.

Upvotes: 5

Related Questions