简体   繁体   English

处理后台任务的返回值-异步等待

[英]Handle return value of background Task - Async Await

I have a long running method that I wish to run on a background thread. 我有一个长时间运行的方法,希望在后台线程上运行。 The method uses the MailChimp api to subscribe a long list of email addresses. 该方法使用MailChimp API订阅一长串电子邮件地址。

I don't want my "Web Forms" app to hang whilst this task runs but I do want to handle any exceptions that occur. 我不希望我的“ Web窗体”应用程序在此任务运行时挂起,但我想处理发生的任何异常。

We call the following method to get things running: 我们调用以下方法来使事情运行:

ExecuteAsyncBatchRegistration(mcitems);

Below is the method we just called: 下面是我们刚刚调用的方法:

public async Task ExecuteAsyncBatchRegistration(List<MailChimpItem> mcitems)
{
    GenericResponse response = new GenericResponse();

    await Task.Run(() =>
    {
        response = ExecuteBatchRegistration(mcitems);

        if (response.Success == false)
        {
            ErrorHandler.WriteError(response.Exception);
        }
    });
}

The method call ErrorHandler.WriteError() uses HttpContext.Current so that it can tell me the page URL, IP address etc. However, in this instance HttpContext.Current is NULL. 调用方法ErrorHandler.WriteError()使用HttpContext.Current,以便它可以告诉我页面URL,IP地址等。但是,在这种情况下, HttpContext.Current为NULL。

I can resolve this by changing the method as follows: 我可以通过如下更改方法来解决此问题:

public async Task ExecuteAsyncBatchRegistration(List<MailChimpItem> mcitems)
{
    GenericResponse response = new GenericResponse();

    response = await Task<GenericResponse>.Run(() =>
    {
        return ExecuteBatchRegistration(mcitems);
    });

    if (response.Success == false)
    {
        ErrorHandler.WriteError(response.Exception);
    }
}

The problem with the latter version of the method is that the app hangs: it doesn't appear to run asynchronously in the background. 后一种方法的问题在于应用程序挂起:它似乎在后台没有异步运行。

How can I run this method asynchronously and retain HttpContent.Current? 如何才能异步运行此方法并保留HttpContent.Current?

If you do not want your web form to hang (ie. you want to return the result to the user and offload the process) then you need to capture the data you need from the HttpContext and pass that to your offloaded long running Task. 如果您不希望Web表单挂起(即,您想将结果返回给用户并卸载进程),则需要从HttpContext捕获所需的数据并将其传递给已卸载的长期运行Task。 Do not access the HttpContext again in that Task because there will not be one. 不要再访问该任务中的HttpContext ,因为不会再访问HttpContext If you want the HttpContext to be available then you cannot end the request which means the form will "hang" and you do your processing on the Request thread. 如果希望HttpContext可用,则无法结束请求,这意味着表单将“挂起”,并在Request线程上进行处理。 The only other good alternative to keep the HttpContext without making the user's web browser hang is to make the call using javascript. 在不使用户的Web浏览器挂起的情况下保持HttpContext的唯一其他好方法是使用javascript进行调用。 Normally I suggest not running it at all in the web context but offload it to a service or use something like HangFire but both of these have the same limitation that you cannot communicate with any type of HttpContext , you have to gather the state and pass it to the off loaded Task. 通常我建议不要在Web上下文中完全运行它,而是将其卸载到服务中或使用诸如HangFire之类的东西,但是这两者都具有相同的限制,即您无法与任何类型的HttpContext通信,您必须收集状态并将其传递到卸载的任务。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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