2012-10-04 2 views
0

Чтобы преодолеть (кажущееся) 4-минутное время ожидания простоя на балансировщике нагрузки Azure, кажется необходимым отправить некоторые данные по трубопроводу клиенту время от времени, чтобы соединение не считалось незанятым.MVC3 AsyncController - Можем ли мы отправить данные о сердцебиении клиенту?

Наш контроллер настроен как AsyncController, и он запускает несколько разных асинхронных методов для других объектов, все из которых настроены на использование портов ввода-вывода IO. Таким образом, мы немедленно возвращаемся из нашего метода, и когда пакет завершения обрабатывается, IIS перехватывает исходный запрос, чтобы мы могли визуализировать наш вид.

Есть ли способ периодически отправлять несколько байтов по проводам в этом случае? В «классической» ситуации мы могли бы выполнить этот метод, а затем просто развернуться, пока мы ждали, отправляя данные каждые несколько секунд, пока асинхронный метод не будет завершен. Но в этой ситуации поток IIS освобождается, чтобы заниматься другими делами, и мы подключаемся к нему в нашем обратном вызове завершения. Что делать? Это возможно?

ответ

0

В то время как ваш конкретный случай относится к конкретному окну Azure (4-минутный тайм-аут LB), вопрос является чистым IIS/ASP.NET. Во всяком случае, я не думаю, что можно отправить «ping-backs» клиенту в AsyncController/AsyncPage. Это идея AsyncPages/Controllers. IIS оставляет сокет в стороне, когда поток обслуживает другие запросы. И возвращается только тогда, когда вы получаете OutstandingOperations в ноль с помощью AsyncManager.OutstandingOperations.Decrement(); Только тогда управление возвращается, чтобы отправить окончательный ответ клиенту. И как только вы отправляете ответ, нет возврата назад.

Я бы предпочел аргументировать архитектурный подход, почему вы что-то подождали 4 минуты, чтобы получить ответ (даже с хорошим анимированным «пожалуйста, подождите»)? За это время может случиться много чего. Из-за сбоя браузера через интернет-сбой на полную потерю/сбой мощности у клиента. Если вы делаете настоящий Azure, почему бы просто не отправлять задачи для роли рабочего в очереди (очереди очередей Azure или очереди служебной шины). Другой вариант, который стоит перед вами для выполнения столь длительных задач, - использовать SingalR и полностью AJAXed решение. Когда вы связываете через SignalR статус продолжительной операции.

UPDATE 1 из-за комментарии

В дополнении к подходу, предложенному @knightpfhor это может быть также достигается с очередями. Requestor создает задачу с некоторым уникальным идентификатором и отправляет ее в «очередь выполнения задач». Затем «прослушивает» (или опросы с регулярными/нерегулярными интервалами) очередь «Завершение задачи» для сообщения с заданным идентификатором задачи.

В любом случае я не вижу причины поддерживать связь клиента на протяжении всей длительной задачи. Существует несколько способов отделить такое сообщение.

+0

Хороший вопрос. Это для сценария сервера с сервером, выполняющего длинные процессы в облаке. Вызывающие могут выполнять только стандартный запрос/ответ, поэтому они должны ждать. –

+1

Не могли ли серверы отправить первоначальный запрос, а затем опрос для прогресса? Если это так, это может быть полезно: http://stackoverflow.com/questions/6184752/set-timeout-for-controller-action/6192680#6192680 – knightpfhor

+0

@knightpfhor Спасибо, что ответили. Нет, как я упоминал в своем комментарии, эти серверы способны только на базовый запрос/ответ. Они не могут опросить, иначе я бы сразу ответил и давал им опрос на результат, или я бы принял URL-адрес обратного вызова, который я бы позже вызвал с ответом. –

Смежные вопросы