Question

I'm trying to make an async action in my async controller. All I need to do is when I press the button in the view it give me an alert indicating that the work has been sent for getting done. and when the job get's done I can do something (For example returning a json or redirect to another view). Here is my code:

Server side:

    public void DoWork()
    {
       var a = MakeADelay();
    }

    public async Task<ActionResult> MakeADelay()
    {
       await Task.Delay(5000);
       return  RedirectToAction("UploadComplete");
    }

    public ActionResult UploadComplete()
    {
       return View();
    }

and this is my client side code :

        $("#btnAsync").click(function () {
        $.ajax({
            url: '/Upload/DoWork',
            type: "post",
            success: function () {
                alert("Work in Progress!!");
            }
        });
    });

When this code runs all seems to execute as expected but when the server side code reaches the statement return RedirectToAction("UploadComplete"); it does nothing ! I think it runs in another thread or something.

what is the problem ?

Second question is what does aync action actually mean ? I never want my action to await for statements to get complete. I always want my actions to sent jobs to execution queue and return back to client, and when the jobs has completed I can notify the client in some way. How can I notify the client anyway ? with SignalR or something ?

Was it helpful?

Solution

what is the problem ?

It's here:

public void DoWork()
{
   var a = MakeADelay();
}

What this does is start MakeADelay and then immediately returns to its caller, which presumably finishes creating the response and sends it.

After the delay completes, your MakeADelay will attempt to continue executing by calling RedirectToAction. However, the response for that request has already been sent, so this will most likely cause an exception (which will be ignored since you never await the task a). Or maybe it just won't do anything, but what it certainly won't do is go back in time and rewrite the response that was already sent.

Second question is what does aync action actually mean ?

I have an introduction on the subject that you may find useful. I also describe on my blog that async does not change the HTTP protocol - you still just get one response for every request. What you're trying to do is send two responses for one request, and that just won't work.

I always want my actions to sent jobs to execution queue and return back to client, and when the jobs has completed I can notify the client in some way. How can I notify the client anyway ? with SignalR or something ?

Then you'll need a queue. I recommend something out-of-process with persistence guarantees. E.g., an Azure queue, MSMQ, WebSphere MQ, etc.

And, yes, you could use SignalR for notification. I'd recommend that.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top