tags:

views:

83

answers:

4

I need to take a caught exception and get a String that is what would be printed using printStackTrace().

It looks like the simplest thing is to call printStackTrace(X), where X subclasses a PrintStream or PrintWriter, and gathers it to a StringBuilder and can return a String.

Does such a thing exist? If not, any suggestions how to do this?

edit: skaffman posted a solution that used getStackTrace(). (can you or moderators undelete?) This is actually the only solution that works "right". The problem with using PrintWriter on top of StringWriter, although it works easily, is that for deep stack traces it doesn't print all the elements.

A: 

ByteArrayOutputStream ?

Dmitry
+4  A: 

What you want is StringWriter

You can pass that into the constructor of a PrintWriter and then call getBuffer() on to the StringWriter or toString() to get the final string.

Milan Ramaiya
+1 for the only reasonable answer out of 5 ...
jarnbjo
well, it's the approach I had intended, and I voted it up, but it doesn't work best for deep stack traces.
Jason S
+1  A: 

How about, instead of printStackTrace, you call Throwable.getStackTrace(), which returns StackTraceElement[]? You still need to do some work to get it into a String, but it's arguably a cleaner solution than hacking about with string buffers and the like.

Once you have the StackTraceElement[], you can manipulate that. It may be that the layout as dictated by printStackTrace isn't really suitable for what you're going to use it for, and that more explicit formatting as provided by the StackTraceElement object model gives you more control. That is what it was provided for, after all.

skaffman
yeah, that's what I was thinking, I just didn't know how hard it was to print out each StackTraceElement.
Jason S
er, convert to a string, not print out.
Jason S
Why on earth should it be a cleaner solution to implement your own version of printStackTrace instead of using Reverend Gonzo's solution? Reimplementing JDK functionality falls into my definition of "ugly hacking".
jarnbjo
Jason specifically asked for a string with what would have been printed by printStackTrace().
jarnbjo
well, I did, but sometimes the thinking-about-the-bigger-picture approach has advantages over a more direct answer.
Jason S
A: 

Guava contains this in its com.google.common.base.Throwables class:

public static String getStackTraceAsString(Throwable throwable) {
  StringWriter sw = new StringWriter();
  throwable.printStackTrace(new PrintWriter(sw));
  return sw.toString();
}
Kevin Bourrillion
yes, that's what I did based on Reverend Gonzo's answer, but again it doesn't work well for deep stack traces.
Jason S
Are you sure it doesn't print all the elements?Are you seeing something of the form "... and 26 more"? And is there a chained exception? This happens when the chained and chaining exceptions share several (in this case, 26) frames in common. It's just a simple way to save space and make things clearer. But you still see *every* frame represented in the output.Explained here:http://java.sun.com/javase/6/docs/api/java/lang/Throwable.html#printStackTrace(java.io.PrintWriter)
Kevin Bourrillion