attribute MVC4 WebApi process launcher

1 Answers

The easiest way is to just change runProcessAsync to return a Task. Remember, async methods should return Task/Task<T> whenever possible, and only return void when they have to.

However, I must caution you that this is quite dangerous. ASP.NET is an HTTP server, so if there are no active requests, it will feel free to take down your AppDomain if it wants to. This would mean your "do more stuff with exitcode" will just drop off the face of the earth.

I have a blog post with a BackgroundTaskManager that you can use to register Tasks with the ASP.NET runtime. It will attempt to delay AppDomain shutdowns if there are registered Tasks that have not completed. However, it's just a "best effort"; there are no guarantees for that kind of thing. Any code running in ASP.NET that is not associated with an active request is a dangerous situation.

routing in rest api

I have a MVC4 API REST trying to launch a process in a new thread. I am working with framework 4.5 and trying to use sync and await clausules.

My code looks like:

public HttpResponseMessage Launch(string id)
    runProcessAsync(id);   // 1                                                        

    return Request.CreateResponse(HttpStatusCode.Accepted); // 2

protected async void runProcessAsync(string id)
    int exitcode = await runProcess(id);  // 3
    string exitcodesz = string.Format("exitcode: {0}", exitcode);  // 4
    // do more stuff with exitcode

protected Task<int> runProcess(string id)
    var tcs = new TaskCompletionSource<int>();

    var process = new Process
        StartInfo = { FileName = @"C:\a_very_slow_task.bat" },
            EnableRaisingEvents = true
        process.Exited += (sender, args) => tcs.SetResult(((Process)sender).ExitCode);            


        return tcs.Task;

Ideally, someone will perform a api rest call ( /task/slowtask/launch ) with POST verb and expect a 202 (accepted) very fast.

Using Fiddler Web Debugger I make the request, the code enters into Launch (// 1), then goes to the await (// 3), the slow task is created and started and a Accepted is returned (// 2). But at this point, Fiddler doesn't show the 202 result. See attached image:

When the slow task ends, the code continues capturing the exitcode (// 4) and then the 202 is captured into Fiddler.

That is very weird, because I did the return long time ago. What I am missing? how can I change that code in order to return a 202 very fast and forget about the task.

Note: I know how to do this with non framework 4.5 features, I am trying to learn how to use async / await.