Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

AsyncTask Android - Design Pattern and Return Values

Tags:

I'm writing an application that validates login credentials on an external webserver - so I have the basic issue of creating a login screen that when submitted will send an HTTP request to a server in the background and not cause the UI to hang - whilst providing a ProgressDialog to the user.

My problem lies in, I want to write a generic HTTP Request class that extends AsyncTask, so when I call .execute() I will then pass String parameters which may contain something like 'post', and when doInBackground is called this will see the 'post' string and then forward those parameters onto the respective call in my class. Pseudo code would be something like

public class HTTPOperations extends AsyncTask<String, Void, String>
{
doInBackground(String... string1,additionalParams)
{
  if string1.equals "post"
      response = httpPost(additionalParams)
       return response;
}

httpPost(params)
{
// do http post request
}
}

This is all I could think of, other than creating a class for every HTTP Post/GET etc request I wish to make and extending ASyncTask...

Which leads me to my next problem, if the HTTP POST is successful and it returns an authentication token, how do I access this token?

Because new httpOperations.execute(), does not return the string from doInBackground, but a value of type

Sorry if this doesn't make sense, I can't figure this out at all. Please ask for elaboration if you need it. AsyncTask design patterns and ideas are hugely welcomed.

like image 335
Tim Avatar asked Feb 20 '11 17:02

Tim


People also ask

What is AsyncTask in Android with example?

An asynchronous task is defined by a computation that runs on a background thread and whose result is published on the UI thread. An asynchronous task is defined by 3 generic types, called Params , Progress and Result , and 4 steps, called onPreExecute , doInBackground , onProgressUpdate and onPostExecute .

Is AsyncTask deprecated?

AsyncTask deprecated alternative Android – Java private final Executor executor = Executors. newSingleThreadExecutor(); A Handler gives you a mechanism to push tasks into the UI thread queue from any other threads thus allowing other threads to communicate with the UI thread.

What are the problems in AsyncTask?

In summary, the three most common issues with AsyncTask are: Memory leaks. Cancellation of background work. Computational cost.

How can I use AsyncTask in different activities in android?

Asynctask gives us the liberty to perform heavy tasks in the background and keep the UI thread light thus making the application more responsive and fast. AsyncTask class is used to do background operations that will update the UI(user interface).


1 Answers

If you are designing a reusable task for something like this, you need to identify a reusable return type. Its a design decision on your part. Ask yourself, "Are my HTTP operations similar in both the mechanisms with which they are called and in which their data is processed?" If so, you can design a single class to do both. If not, you probably need different classes for your different remote operations.

In my personal use, I have an object i attach key value pairs to and the common return type is the HttpEntity. This is the return type for both HTTP Get and Post, and this seems to work ok in my scenarios because i throw exceptions in exceptional HTTP result situations, like 404. Another nice aspect of this setup is that the code to attach parameters to a get or post are fairly similar, so this logic is pretty easy to construct.


An example would be something like this (psuedo):

public interface DownloadCallback {
   void onSuccess(String downloadedString);
   void onFailure(Exception exception);
}

Then in your code, where you go to do the download:

DownloadCallback dc = new DownloadCallback(){
   public void onSuccess(String downloadedString){
     Log.d("TEST", "Downloaded the string: "+ downloadedString);
   }
   public void onFailure(Exception e){
     Log.d("TEST", "Download had a serious failure: "+ e.getMessage());
   }
 }

 DownloadAsyncTask dlTask = new DownloadAsyncTask(dc);

Then inside the constructor of DownloadAsyncTask, store the DownloadCallback and, when the download is complete or fails, call the method on the download callback that corresponds to the event. So...

public class DownloadAsyncTask extends AsyncTask <X, Y, Z>(){
  DownloadCallback dc = null;

  DownloadAsyncTask(DownloadCallback dc){
    this.dc = dc;
  }

  ... other stuff ...

  protected void onPostExecute(String string){
    dc.onSuccess(string);
  }
}

I'm going to reiterate that I think for the good of yourself, you should pass back HttpEntities. String may seem like a good idea now, but it really leads to trouble later when you want to do more sophisticated logic behind your http calls. Of course, thats up to you. Hopefully this helps.

like image 142
Nick Campion Avatar answered Oct 14 '22 03:10

Nick Campion