Sentry is cross-platform application monitoring, with a focus on error reporting.
在Sentry提供的Java SDK中,提供了项目异常收集功能。对于已捕获的异常,可以通过logger框架集成对应的appender实现自动上传; 对于未捕获的异常,比如runtimeException或者人工吃掉的异常,可以通过 Thread.setDefaultUncaughtExceptionHandler() 设置默认的全局异常处理器来收集。
Sentry异常收集.png
io.sentry.SentryUncaughtExceptionHandler
package io.sentry;
public class SentryUncaughtExceptionHandler implements Thread.UncaughtExceptionHandler {
/**
* Configures an uncaught exception handler which sends events to
* Sentry, then calls the preexisting uncaught exception handler.
*
* @return {@link SentryUncaughtExceptionHandler} that was setup.
*/
public static SentryUncaughtExceptionHandler setup() {
logger.debug("Configuring uncaught exception handler.");
Thread.UncaughtExceptionHandler currentHandler = Thread.getDefaultUncaughtExceptionHandler();
if (currentHandler != null) {
logger.debug("default UncaughtExceptionHandler class='" + currentHandler.getClass().getName() + "'");
}
SentryUncaughtExceptionHandler handler = new SentryUncaughtExceptionHandler(currentHandler);
Thread.setDefaultUncaughtExceptionHandler(handler);
return handler;
}
·····省略
/**
* Sends any uncaught exception to Sentry, then passes the exception on to the pre-existing
* uncaught exception handler.
*
* @param thread thread that threw the error
* @param thrown the uncaught throwable
*/
@Override
public void uncaughtException(Thread thread, Throwable thrown) {
if (enabled) {
logger.trace("Uncaught exception received.");
EventBuilder eventBuilder = new EventBuilder()
.withMessage(thrown.getMessage())
.withLevel(Event.Level.FATAL)
.withSentryInterface(new ExceptionInterface(thrown));
try {
Sentry.capture(eventBuilder);
} catch (RuntimeException e) {
logger.error("Error sending uncaught exception to Sentry.", e);
}
}
// taken from ThreadGroup#uncaughtException
if (defaultExceptionHandler != null) {
// call the original handler
defaultExceptionHandler.uncaughtException(thread, thrown);
} else if (!(thrown instanceof ThreadDeath)) {
// CHECKSTYLE.OFF: RegexpSinglelineJava
System.err.print("Exception in thread \"" + thread.getName() + "\" ");
thrown.printStackTrace(System.err);
// CHECKSTYLE.ON: RegexpSinglelineJava
}
}
}