简体   繁体   中英

Async Method Invocation - Maintain Sequence

I have series of asyc methods that needs to be called in perticular sequence. The problem is that, all methods makes request to WCF service. Method that makes WCF call is common to whole project. In the callback function of WCF call, I determine whether WCF call was successful or not. If WCF call was successful I need to call another method. There are many methods to be called in sequence, one-after-other.

private Action<string> action;

public void MakeHttpPostRequest(string webserviceURL, string json, Action<string> response)
{
try
{
    this.action = response;

    if (Microsoft.Phone.Net.NetworkInformation.NetworkInterface.GetIsNetworkAvailable())
    {
        Uri uri = new Uri(webserviceURL);
        byte[] byteArray = System.Text.Encoding.UTF8.GetBytes(json);

        string data = Encoding.UTF8.GetString(byteArray.ToArray(), 0, (int)byteArray.Length);
        WebClient webClient = new WebClient();
        webClient.UploadStringCompleted += new UploadStringCompletedEventHandler(this.WebClient_UploadStringCompleted);
        webClient.Headers["Content-type"] = "application/json";
        webClient.Encoding = Encoding.UTF8;
        webClient.UploadStringAsync(uri, "POST", data);
    }
    else
    {
        this.action(string.Empty);
    }
}
catch (Exception ex)
{
    new ErrorException.ErrorException().HandleError(ex, string.Empty, Global.Modules.General);
}
}

private void WebClient_UploadStringCompleted(object sender, UploadStringCompletedEventArgs e)
{
try
{
    // Check whether to invoke any method
    if (this.action != null)
    {
        // Invoke the method passed to MakeHttpPostRequest by it's calling method
        this.action(e.Result);
    }
}
catch (Exception ex)
{
    new ErrorException.ErrorException().HandleError(ex, string.Empty, Global.Modules.General);
}
}

I do not think that writing different callback event for each method and calling next method is good idea.

It is really just a different rearranging of code, but you could simply create a queue of "Tasks" that need to be run one after another.

That "Task manager" could catch any completion events from each task and start the next task in the queue.

The Task interface is up to you, but it just needs a Start method and an OnCompleted event as a minimum, but you will need to handle failures sensibly as well.

Background

We did something like this over a year ago as we needed both parallel and sequential tasks to be executed, so built it so that each of our tasks could contain other tasks (our task manager just became a top level task itself). Your high-level code then just becomes a set of adds on the task manager to create an appropriate ordering of the child tasks followed by a manager call to Start the first task(s).

As a guide it is often better to write a complex subsystem (once), that gives you a very simple top level in all your apps, than to keep stitching together code and event handlers.

If I understand what you want correctly, just change your action field to a queue of actions. In WebClient_UploadStringCompleted , write:

if (actionQueue.Count > 0)
{
    var action = actionQueue.Dequeue();
    action(e.Result);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM