在异步任务完成之前返回

use*_*447 8 c# async-await asp.net-mvc-4 .net-4.5

我正在研究ASP.NET MVC 4 Web应用程序.我正在使用.NET 4.5,并试图利用新的异步API.

我有几种情况,我想安排一个异步任务以便稍后运行,而我立即返回一个立即重要的值.例如,这是一个"登录"方法,我希望尽快返回一个新的SessionID,但是一旦我返回了SessionID,我想清除旧的过期SessionID:

public async Task<Guid> LogIn(string UserName, string Password)
{
    //Asynchronously get ClientID from DB using UserName and Password

    Session NewSession = new Session()
    {
        ClientID = ClientID,
        TimeStamp = DateTime.Now
    };
    DB.Sessions.Add(NewSession);
    await DB.SaveChangesAsync();    //NewSession.ID is autopopulated by DB

    CleanSessions(ClientID);    //Async method which I want to execute later

    return NewSession.ID;
}

private async void CleanSessions(int ClientID)
{
    //Asynchronously get expired sessions from DB based on ClientID and mark them for removal
    await DB.SaveChangesAsync();
}
Run Code Online (Sandbox Code Playgroud)

我尝试了很多不同的东西,包括Task.Run()和Parallel.Invoke()的组合,但是CleanSessions永远不会被调用.如何实现后台任务调度?

Ste*_*ary 15

不建议在没有请求的情况下在ASP.NET中运行任务.这很危险.

也就是说,改变CleanSessions回归Task,你可以这样做:

Task.Run(() => CleanSessions());
Run Code Online (Sandbox Code Playgroud)

在你的情况下,我认为没关系,因为如果CleanSessions在执行过程中没有执行或终止(由于回收可能会在ASP.NET中发生),就没有长期问题.如果您想通知ASP.NET您有一些与请求无关的正在进行的工作,您可以使用BackgroundTaskManager我的博客,如下所示:

BackgroundTaskManager.Run(() => CleanSessions());
Run Code Online (Sandbox Code Playgroud)

  • 感谢更新。最终,将其移至WebJobs并调用API端点并稍后进行工作(预定时间) (2认同)