У меня есть сайт на Rackspace, который выполняет расчет, расчет может занять от 30 секунд до нескольких минут. Первоначально я реализовал это с помощью SignalR, но ему пришлось вырвать его из-за чрезмерного использования CC. Сайты Hosted Rackspace действительно не предназначены для такого использования. Билл прошел через крышу.MVC 5/.NET 4.5 - Долгосрочный процесс
Базовый код, как показано ниже, отлично работает на моем тестовом сервере, но, конечно же, получает ошибку тайм-аута в Rackspace, если расчет занимает более 30 секунд из-за того, что их наблюдатель убил его. (старый код) Мне сказали, что операция должна записываться в поток, чтобы сохранить его. В старые времена я бы начал поток и опросил сайт до тех пор, пока поток не будет выполнен. Если есть лучший способ, я бы предпочел взять его.
Кажется, что с .NET 4.5 я могу использовать HttpTaskAsyncHandler для этого. Но я не понимаю. Ниже (новый код) я понимаю обработчик, который вы использовали бы, используя старый код при использовании и помещая его в задачу ProcessRequestAsync. Когда я пытаюсь вызвать CalcHandler/Calc, я получаю ошибку 404, которая, скорее всего, связана с маршрутизацией. Я пытался следовать этой ссылке, но не мог заставить ее работать. Имя добавления - «myHandler», но ссылка на пример - «фид», как мы получили от одного к другому. Они упомянули, что создали библиотеку классов, но может ли код быть в том же проекте, что и текущий код, как?
http://codewala.net/2012/04/30/asynchronous-httphandlers-with-asp-net-4-5/
Как примечание стороны, будет HttpTaskAsyncHandler позвольте мне сохранить запрос в живых до тех пор, пока не будет завершен, если он занимает несколько минут? В основном я должен использовать что-то еще для того, что я пытаюсь выполнить.
Старый код
[Authorize]
[AsyncTimeout(5000)] // does not do anything on RackSpace
public async Task<JsonResult> Calculate(DataModel data)
{
try
{
using (var db = new ApplicationDbContext())
{
var result = await CalcualteResult(data);
return Json(result, JsonRequestBehavior.AllowGet);
}
}
catch (Exception ex)
{
LcDataLink.ProcessError(ex);
}
return Json(null, JsonRequestBehavior.AllowGet);
}
новый код
public class CalcHandler : HttpTaskAsyncHandler
{
public override System.Threading.Tasks.Task ProcessRequestAsync(HttpContext context)
{
Console.WriteLine("test");
return new Task(() => System.Threading.Thread.Sleep(5000));
}
}
Кажется, самым прямым решением является удаление/повышение ограничения тайм-аута запроса RackSpace. На стороне примечание «AsyncTimeout» должно использоваться в сочетании с «CancellationToken» - он не будет убивать ваш запрос, как синхронный таймаут; он попросит его отменить, установив «CancellationToken». –
Я согласен с тем, что Rackspace увеличивает время ожидания, но это не вариант. Есть ли у вас ссылка или пример использования CancellationToken с MVC 5 и .NET 4.5? –
http://www.asp.net/mvc/overview/performance/using-asynchronous-methods-in-aspnet-mvc-4#CancelToken –