Как передать частичный контент с помощью ASP.NET MVC FileStreamResult

Мы используем FileStreamResult для передачи видеоданных в видеопроигрыватель на основе Silverlight MediaElement:

public ActionResult Preview(Guid id) {
    return new FileStreamResult(
        Services.AssetStore.GetStream(id, ContentType.Preview),
        "application/octet-stream");
}

К сожалению, видеопроигрыватель Silverlight загружает весь видеофайл до того, как он начнет воспроизводиться. Такое поведение ожидается, так как наше действие Preview не поддерживает загрузку частичного содержимого.

(примечание: если файл размещен в виртуальном каталоге IIS, мы можем начать воспроизведение в любом месте видео, пока оно еще загружается. однако по соображениям безопасности и аудита мы не можем предоставить прямую ссылку для скачивания. так что это не опция.)

Как мы можем улучшить действие контроллера для поддержки частичного содержимого HTTP?

Я предполагаю, что сначала мы должны сообщить клиенту, что мы его поддерживаем (добавив заголовок «Accept-Ranges: bytes» к запросу HEAD), затем мы должны оценить заголовок HTTP «Range» и передать запрошенный диапазон файлов с ответом. код 206. Будет ли это работать с ASP.NET MVC, размещенным на IIS6? Есть ли уже какой-то код?

Также см:


person o_o    schedule 21.07.2009    source источник


Ответы (3)


На CodePlex есть проект, который дает именно эту функциональность.

http://mediastreamingmvc.codeplex.com/

Посмотри. Он был создан специально для этого сценария, когда вы хотите иметь действие, представляющее запрос на виртуальный ресурс, и возвращать частичное содержимое, если это запрошено, не требуя от разработчика особых действий для его поддержки (фильтр действий и выбор типов результатов).

person Erik Noren    schedule 16.11.2010

  1. Вы должны реализовать это самостоятельно. И да, это будет работать на IIS6.
  2. Если вы можете использовать IIS7, вам, вероятно, лучше использовать расширяемость IIS7 (пример) .
person Mike Chaliy    schedule 21.07.2009

Тогда вам нужно переделать модуль дросселирования :)

Идея состоит в том, чтобы рассчитать битрейт вашего видеопотока, а затем отправить столько, сколько требуется клиенту. Итак, вам нужно (очень кратко) прочитать блок из вашего потока и отправить его клиенту и заснуть на секунду.

Thread.Sleep(1000) на самом деле не очень хорошая идея для обработки ресурсов IIS, поэтому вам нужно делать что-то асинхронно. IAsyncResult будет вашим другом.

Существует много возможностей для всех видов оптимизации.

И последнее... Я заставил его работать как обычный httphandler, а не как MVC ActionResult. Если это возможно на вашем веб-сайте, я рекомендую сделать это в качестве обработчика.

person tomo    schedule 21.07.2009