If you are using Fragments in your Android app, there’s a good chance you will eventually see the error message like the one below.
Uh, what’s going on here? Reading a Java stacktrace can be a daunting task, but don’t worry, we’ll unravel it step by step.
java.lang.IllegalStateException: Fatal Exception thrown on Scheduler.
at java.lang.reflect.Method.invoke(Native Method)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference
Let’s start with the ‘Caused by’ phrase, which identifies the root cause of the exception:
Caused by: java.lang.NullPointerException:
Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()'
on a null object reference
So now we know that a NullPointerException occurred when executing the getResources() method on a context object when making the call Toast.makeText().
Let’s take a look at the Toast.makeText() signature:
The first parameter of this method is a context object, so putting 2 and 2 together we can assume that the context passed in was null and thus the getResources() call inside the method failed.
If you remember the Fragment life cycle, the Fragment receives it’s context during the OnAttach() method and loses it in the OnDetach() event. So putting all the pieces together, we can conclude that the Fragment was detached from it’s host Activity at the time, when the makeToast() method was trying to use the context.
This situation occurs often when a task is started on a background thread – like a request to the server – and at the same time, the user performs and action that causes the Fragment to disappear, e.g. hitting the back button. The server request returns and you want to display some kind of feedback message, but since the user moved away from the page, the Fragment has lost it’s context and any method using the context will fail, e.g. showing an AlertDialog.
There is an easy way to prevent this and that’s by checking if the context is null when you try to execute methods requiring context after any operations that run on the background thread.
// Background operation returns
if (this.getContext() != null)
Toast.makeText(this.getContext(), "Your feedback message", Toast.LENGTH_LONG).show();
So the bottom line is, after executing background operation and calling methods requiring context, make sure you still have one by checking if the context is null.