How to Chain Async Task Sequentially (Starting One After the Previous Asynctask Completes)

Can I chain async task sequentially (starting one after the previous asynctask completes)

I also had some same situation the other day.
I had solved it in this way:
Pass the reference of your activity to the constructor of async class and execute the do in background function. Now in post execute function call a public method of ur activity from async class to execute the task again... or try this:

            if (asynclass.getStatus() == android.os.AsyncTask.Status.PENDING) {
asynclass.execute();
} else if (RF.getStatus() == android.os.AsyncTask.Status.FINISHED) {
asynclass = new asyncclass();
asynclass.execute();
} else {
Toast.maketoast(this, "Plz wait", 1).show();
}

Cheers

Execute two sequences of AsyncTasks serially

A simple queue will work for now:

public class OperationsQueue {

private Operation ongoingOperation;
private Queue<Operation> queue = new LinkedList<>();

public void execute(Operation operation) {
if (ongoingOperation != null)
queue.add(operation);
else {
ongoingOperation = operation;
operation.setOnFinishedCallback(() -> operationFinished(operation));
operation.execute();
}
}

private void operationFinished(Operation operation) {
ongoingOperation = null;
Operation nextOperation = queue.poll();
if (nextOperation != null)
execute(nextOperation);
}
}

public abstract class Operation {
protected Runnable onFinished = () -> { };

public abstract void execute();

public void setOnFinishedCallback(Runnable onFinished) {
this.onFinished = onFinished;
}
}

Concrete implementations of Operation need to start the first async task in the sequence and the last async task must call onFinished.

That is in case of this sequence:

A -> B

An operation passes a callback to async task A which it passes to async tasks it starts so that the last task B calls it in its onPostExecute:

class SomeOperation extends Operation {
public void execute() {
new A(() -> onFinished()).execute();
}
}

class A extends AsyncTask<Void, Void, Void> {
//...

public Runnable onSuccess;

public A(Runnable onSuccess) {
this.onSuccess = onSuccess;
}

onPostExecute() {
new B(onSuccess).execute();
}
}

class B extends AsyncTask<Void, Void, Void> {
//...

public Runnable onSuccess;

public B(Runnable onSuccess) {
this.onSuccess = onSuccess;
}

onPostExecute() {
onSuccess.run();
}
}

SomeOperation and its underlying tasks may now be executed serially:

OperationsQueue queue = new OperationsQueue();
queue.execute(new SomeOperation());
queue.execute(new SomeOperation());

Task A of the second SomeOperation will not execute until task B on the first finishes.

Is chaining AsyncTasks considered bad practice?

You can definitely do that and there is nothing wrong with chaining multiple AsyncTasks if you really have to. And I want to emphasise: only if you really have to.

AsyncTasks bring a certain overhead with them. If you chain two AsyncTasks you get twice the overhead. You don't want that. You should use the least amount of AsyncTasks possible.

In your case the solution actually seems quite simple: Perform all of the work in just one AsyncTask. Ask yourself: Is there really any need for two separate AsyncTasks? From your description it certainly doesn't seem like it. If you just use one AsyncTask your code will run a lot more efficiently than if you use two.


Please note that AsyncTasks should only be used for short operations that take a few seconds and which are started in response to a user action. If you need to perform some long running operation in the background than an AsyncTask is probably not the best solution. I can't really tell from your description if what you want to do is something suited for an AsyncTask or not, but if the work you are doing doesn't fall into the criteria I described above you are probably better of with an alternative solution.

Design pattern for modular AsyncTask in Android

Multiple AsyncTask can be run in serial or parallel way by using executeOnExecutor with parameter AsyncTask.SERIAL_EXECUTOR or AsyncTask.THREAD_POOL_EXECUTOR.

If you expect a result with a wait mechanism(e.g wait for a task to finish and return a result) then the better way is to use Future. One such implementation is FutureTask which relies on Callable like this:

ExecutorService pool = Executors.newFixedThreadPool(poolSize);
FutureTask<String> future = new FutureTask(new Callable() {
public String call() {
...
return res;
});
executor.execute(future);

String res = future.get();

The last line will block the operation until Callable inside returns its String result. In fact you can even set a timeout for it to finish.

Remember that AsyncTask doesn't only perform asynchronous operation. It also carries out its process on background thread. So you may still use an AsyncTask (or Thread) to do synchronous operations which otherwise would block the UI.

Android calling AsyncTask right after an another finished

you can use getStatus() checks whether the the AsyncTask is pending, running, or finished.and when finsh start your new task.like:

if(authTask .getStatus() == AsyncTask.Status.PENDING){
// My AsyncTask has not started yet
}

if(authTask .getStatus() == AsyncTask.Status.RUNNING){
// My AsyncTask is currently doing work in doInBackground()
}

if(authTask .getStatus() == AsyncTask.Status.FINISHED){
// START NEW TASK HERE
}

example for your app:

btn.setOnClickListener(new View.OnClickListener()
{
public void onClick(View v)
{
if (authTask != null && authTask.getStatus() == AsyncTask.Status.FINISHED) {
//START YOUR NEW TASK HERE
}
else
{
//IGNORE BUTTON CLICK
}
}
});

Execute Code only after async task complete

Create a callback in GetBitMapFromURL.

public class GetBitMapFromURL extends AsyncTask<Void, Void, Void> {

private GetBitMapFromURLCallback mCallback = null;

public WebService(GetBitMapFromURLCallback callback) {
mCallback = callback;
}

@Override
protected Boolean doInBackground(Void... params) {
// ...
}

@Override
protected void onPostExecute(Boolean result) {
super.onPostExecute(result);

if (mCallback != null) {
mCallback.onGetBitMapFromURLComplete(this);
}
}

public interface GetBitMapFromURLCallback {

public void onGetBitMapFromURLComplete(GetBitMapFromURL getBitMapFromUrl);
}
}

public class MyActivity extends Activity implements GetBitMapFromURLCallback {

// ...

public void onGetBitMapFromURLComplete(GetBitMapFromURL getBitMapFromUrl) {
// This code will get called the moment the AsyncTask finishes
}
}

And let your activity implements this callback and onGetBitMapFromURLComplete().

AsyncTask with Timer keeps on running

Following links can helps you, please have a look, Thanks.

Android: Can I chain Async task sequentially (starting one after the previous asynctask completes)

and

Android calling AsyncTask right after an another finished

How to Sequentially execute Asynctask in a Loop?

Simplest option: only have one AsyncTask, where you process all the work in a single doInBackground(), using publishProgress() and onProgressUpdate() to publish per-download results, if needed. I do not know why you think having N non-parallel AsyncTask instances is a good idea.

Or: don't use AsyncTask at all. Use your own ThreadPoolExecutor, so you have complete control over the characteristics of your jobs. Use an event bus (greenrobot's EventBus, Otto, LocalBroadcastManager, etc.) to publish the results on the UI thread.

Or: From onPostExecute() of the first AsyncTask, start the next AsyncTask in your chain.



Related Topics



Leave a reply



Submit