我有需要。我有一个MVC5网站。我正在使用正常的控制器模型结构。我从Javascript执行控制器功能的地方。我必须在上传时处理一些xml文件。当控制器第一次执行该功能时,如果处理完所有xml文件,它将不会返回浏览器,会发生什么。
所以这就是我想要的。我想执行控制器功能来执行模型方法。在那个方法中,我想选择所有的xml文件,然后我想异步处理它们。这是代码:
var raw = new DirectoryInfo(xconfig.Directory.FullName + "//raw");
if (raw.Exists)
{
var xmls = raw.GetFiles("*.xml");
foreach (var xml in xmls)
{
if(ProcessedXmlFiles != null)
{
if(!ProcessedXmlFiles.Contains(xml.Name))
{
ExportData(xml);
ProcessedXmlFiles.Add(xml.Name);
}
}
}
}
当执行上面的代码时,我调用另一个javascript方法来获取更新使用普通ajax调用处理了多少文件。所以我只是调用另一个控制器方法,我返回ProcessedXmlFiles.Count,知道到目前为止已处理了多少这些方法!
答案 0 :(得分:1)
您只需让您的操作返回Task
,然后将您的流程置于Task.Run内。
public async Task<ActionResult> MyAction(object param)
{
var raw = new DirectoryInfo(xconfig.Directory.FullName + "//raw");
if (raw.Exists)
{
await Task.Run(() =>
{
var xmls = raw.GetFiles("*.xml");
foreach (var xml in xmls)
{
if(ProcessedXmlFiles != null)
{
if(!ProcessedXmlFiles.Contains(xml.Name))
{
ExportData(xml);
ProcessedXmlFiles.Add(xml.Name);
}
}
}
});
// Do something
}
return View();
}
编辑:由于OP似乎期望与异步编程提供的行为不同,我建议使用后台工作者,但请注意在Web应用程序中使用后台工作程序是不可取的。 ASP.NET以请求 - 响应方式工作。我建议让用户在渲染视图之前等待进程结束。
public ActionResult MyAction(object param)
{
ExecuteBackgroundWorker(param); // your model containing the method you want to execute
return View(); // This will return the view while the background worker proceeds.
}
public void ExecuteBackgroundWorker(object param)
{
BackgroundWorker bgWorker = new BackgroundWorker();
bgWorker.DoWork += bgWorker_DoWork;
bgWorker.RunWorkerCompleted += bgWorker_RunWorkerCompleted;
bgWorker.RunWorkerAsync(param);
}
void bgWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
// Do Something when work ends
}
void bgWorker_DoWork(object sender, DoWorkEventArgs e)
{
var OPsModel = (MyModel)e.Argument; // Cast object back to original model
OPsModel.ExecuteProcess(); // Execute the process
}