Handling background tasks and activity configuration changes

250 Views Asked by At

Here is problem which I'm trying to solve for three days:

For example, REST client app perfoms a lot of background work (network calls) and posts result back to UI thread. It is obvious that it should be done asynchronously. Android allows to do this in several ways (for example AsyncTasks and IntentServices).

The biggest problem of running asynchronous tasks from activity is configuration change. For example we have activity which starts download process in AsyncTask and shows ProgressDialog. After screen rotation, activity is being recreated by OS. As the result when asynctask will try to dismiss progressdialog of old (dead) activity, it will fail.

There are several solutions to this problem:

  • first one is to retain asynctask in worker fragment: Great post how to do that is here. Big advantage of this solution is that OS knows when to call onPostExecute() method. In some cases onPostExecute() maybe called in moment when old activity is destroyed and new one is still not created. But that doesn't happen because OS doesn't allow execution of onPostExecute() before onAttach() is called. Disadvantage is that AsyncTasks are not suitable for long term operations and behaves differently depending on OS version.

  • the second approach is using LocalBroadcastManager and IntentService. Here is another post which shows how to use it. What will happen if service will send message to BroadcastReceiver when it is unregistered (the moment when activity is being recreated)?

  • the third solution is dirty hack: declare this in mainfest android:configChanges="keyboardHidden|orientation". Is not appropriate for me.

Maybe someone knows another solution?

1

There are 1 best solutions below

0
On

You can prevent screen orientations before the task with setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_NOSENSOR) and restore it after.

The othet other idea is a service. You're worried that when one orientation is closed and before the other is loaded you may miss a broadcast. In that case the service should store the data somewhere the fresh activity can load it. (SqlLite, a file, sharedPrefs)

Also note broadcastRecievers can be registered in the manifest. So always on, so to speak.