我有以下代码:
import org.apache.commons.lang.exception.ExceptionUtils;
public void myMethod() {
try {
// do something
} catch (Exception e) {
System.out.println(ExceptionUtils.getStackTrace(e)); // prints "java.lang.NullPointerException"
System.out.println(ExceptionUtils.getFullStackTrace(e)); // prints "java.lang.NullPointerException"
e.printStackTrace(); // prints "java.lang.NullPointerException"
}
}
我希望看到的输出是一个完整的堆栈跟踪,其中包含行号和失败的类的层次结构。例如,
Exception in thread "main" java.lang.NullPointerException
at org.Test.myMethod(Test.java:674)
at org.TestRunner.anotherMethod(TestRunner.java:505)
at java.util.ArrayList(ArrayList.java:405)
此代码正在一个更大的应用程序中运行,该应用程序也有log4j,但我希望能够将异常转换为字符串,以便我可以将其作为电子邮件发送给Java开发人员。
有没有人对如何将完整的堆栈跟踪捕获到字符串有任何想法?我不能使用Thread.currentThread()。getStackTrace(),因为这个应用程序在Java 4上运行。什么可能阻止上面的代码打印完整的堆栈跟踪?
答案 0 :(得分:13)
这是因为java在服务器模式下运行时会进行一些代码优化(java -server)
跳过这个。在java args中使用-XX:-OmitStackTraceInFastThrow
请参阅以下链接了解详情:
答案 1 :(得分:11)
如果反复抛出异常,JVM会停止填充堆栈跟踪。我不确定为什么,但它可能是减少JVM上的负载。您需要查看较早的堆栈跟踪以查看详细信息。
for (int n = 0; ; n++) {
try {
Integer i = null;
i.hashCode();
} catch (Exception e) {
if (e.getStackTrace().length == 0) {
System.out.println("No more stack trace after " + n + " thrown.");
break;
}
}
打印
No more stack trace after 20707 thrown.
答案 2 :(得分:3)
异常可能会在catch块之前被捕获并抛出。也许在另一个你打算做逻辑的课上。
像Exception
一样创建的new Exception(new Throwable("java.lang.NullPointerException"));
将打印出类似于您所看到的内容。
答案 3 :(得分:2)
有没有人对如何将完整的堆栈跟踪捕获到字符串有任何想法?
您可以使用以下方式(StringWriter.toString())将堆栈跟踪转移到String中。
StringWriter writer = new StringWriter();
e.printStackTrace( new PrintWriter(writer,true ));
System. out.println("exeption stack is :\n"+writer.toString());
答案 4 :(得分:1)
可能是你没有控制台输出的appender。你考虑加一个。如果没有,请将其记录为LOGGER.error(ex);使用log4j或SLF4J
答案 5 :(得分:1)
我只能想到e.printStackTrace()
可能只输出字符串"java.lang.NullPointerException"
的两个原因。
setStackTrace(new StackTraceElement[0])
。printStackTrace()
或其他一些方法来返回误导性信息。答案 6 :(得分:1)
什么可能阻止上述代码显示完整的堆栈跟踪?
就我而言,我正在捕获的Exception
的超类具有以下代码:
/* avoid the expensive and useless stack trace for API exceptions */
@Override
public Throwable fillInStackTrace() {
return this;
}
这意味着堆栈跟踪数组从未填充,所以我得到的只是:
org.apache.kafka.AuthException: Auth failed: Invalid username or password
没有堆栈信息,所以不知道它发生在哪里。可爱。
我能够通过捕获Exception
的源代码,将其复制到我的项目中,然后删除fillInStackTrace()
方法来覆盖此行为。这是骇客,但我需要该Exception
的信息。
答案 7 :(得分:0)
确保您使用的是e.printStackTrace()而不是e.getStackTrace();