androidexceptionuncaughtexceptionhandler

Use UncaughtExceptionHandler to do what Android usually does plus extra functionality I need


I am working on an Android library where I need to perform some action if an uncaught exception is seen.

I am successfully setting my uncaught exception handler and running the code I need, which is to post some information to a web server, but after my part is finished I want the app to then do what Android usually does, i.e. display a dialogue to the informing them that it has crashed and then exit the app, and post the details to the Google Play Developer Console.

At the moment, my uncaught exception successfully posts to the server, but then keeps the app running but in a bit of a weird state as the thread has party disappeared, where usually, if my an uncaught exception is thrown, then Android closes the app.

Below is how I am doing my uncaught exception handler:

private static void setUnhandledExceptionHandler()
    {
        Thread.setDefaultUncaughtExceptionHandler(new UncaughtExceptionHandler()
        {
            @Override
            public void uncaughtException(final Thread thread, final Throwable) {
                CrashReporter.ReportUnhandledCrash(((Exception) ex));
                Looper.loop();
            }
        });
    }

Basically, what I want to do is, have my app post to to my server via my unhandled exception handler and then quit the app, in the same way that Android usually does, i.e. display a force close error the use and close the app.


Solution

  • I had a similar problem when tracking to GoogleAnalytics - most Exceptions got lost when i tried to report them in the default handler. So i cached them and reported them on the next startup.

    The second trick (and this hopefully answers your question) to let the Application crash as it should is to store the 'old' DefaultUncaughtExceptionHandler and pass the exception to it.

    The onCreate method below is the one of my Application class

    @Override
    public void onCreate()
    {
         super.onCreate();
         trackCachedException();
         setupExceptionHandling();
    }
    
    
    private void setupExceptionHandling()
    {
        _systemExceptionHandler = Thread.getDefaultUncaughtExceptionHandler();
        Thread.UncaughtExceptionHandler myHandler = new Thread.UncaughtExceptionHandler()
        {
    
            @Override
            public void uncaughtException(Thread thread, Throwable ex)
            {
                cacheException(thread.getName(), ex);
                if (_systemExceptionHandler != null)
                {
                    _systemExceptionHandler.uncaughtException(thread, ex);
                }
            }
        };
        // Make myHandler the new default uncaught exception handler.
        Thread.setDefaultUncaughtExceptionHandler(myHandler);
    }