Running asynchronous tasks off of the UI thread then modifying the UI is a common issue in android development, so I decided to take some time, research, and play around with different techniques and find what works best for me.
What I considered important factors:
- Should work reliably
- Code readability
Activity
orFragment
should be kept clean of as much of thread management as possible
Here is the summary of my impressions (which may be wrong and some are just opinions) about the various methods:
AsyncTask
I was using simple AsyncTask
without LoaderManager
when I first jumped into Android:
- Had intermittent issues, I wrote my own
AsyncTaskManager
to manage them with the activity life cycle. - There are some limitations to number of tasks and memory leaks have been reported before.
- Biggest issue with these was that they made my code extremely convoluted, and simplifying the code defeated the purpose of using them in the first place.
AsyncTaskLoader with LoaderManager
This seems to be the recommended way to do this, so I researched it a bit:
- After reading about these a bit, it seems the main reason this method is recommended is because it manages the tasks with the
Fragment
life cycle, and from my understanding basically just restarts the tasks if necessary. It doesn't seem to be able to receive the results of a task started before an activity was restarted after the activity restarts. - All the task parameters seem to have to be
Parcelable
orSerialiazable
to go into aBundle
object.
Handler, Threads, with Messages
This is the method I settled on:
- Easy to implement, extremely customizable.
- You get access to the thread executing the task: set priority, set thread name for debugging, set daemon, and etc.
- Seems much more responsive than with using AsyncTasks, based on an eye test where I click a button a lot of times and watch the results and threads flash by ;) I could benchmark this.
- To handle life cycle issues, can write a singleton class that manages messages (persists while the process is alive). Stores them when a given activity's handler is not set up, then forwards them to the activity handler if it asks for its missed messages. Meaning a task doesn't have to restart with the same parameters, which can be critical for tasks that are non-idempotent.
So I came to the conclusion that using Handler
, Threads
, and Messages
is a much better solution, but I'm convinced I'm missing something because nearly everywhere I looked the recommendation was to use the AsyncTaskLoader
method. What am I missing?
Thanks for the input.