none
System.OutOfMemory Exception при коммите большого бинарника через Entity Framework в SQL Filestream поле RRS feed

  • Вопрос

  •  using (var unitOfWork = _unitOfWorkFactory.Create())
     {
    	 var newFileVersionBin = new FileVersionBin();
    	 newFileVersionBin.Bin = System.IO.File.ReadAllBytes(UploadFileName);
    	 newFileVersionBin.ID = Guid.NewGuid();
    	 unitOfWork.FileVersionBinRepository.Create(newFileVersionBin);
    	 unitOfWork.Commit();
    }
    

    Используется Entity Framework 4, SQL Server 2008R2, Repository и UnitOf Work.

    Поле Bin в SQL Server - varbinary(max) filestream

    Гружу файл примерно до 40 мб - все ок.

    Больше - выдает Exception System.OutOfMemory.

    Как поступить?

    Exception выдает на коммите.

    Update:

    Только что сделал простенький проектик. В нем выполнить нужно скрипты развертывания элементарной Filestream базы в SSMS последовательно, потом обновить Entity и попробовать. При файлах размером ок 40 мб все ок, когда 400 мб - валится с ошибкой.

    http://dl.dropbox.com/u/2349288/FileStreamLargeTest.zip


    Трухин Юрий Владимирович
    22 ноября 2010 г. 13:19

Ответы

Все ответы

  • Используя ваш простеникий проектик, у меня такие вот результаты:

    Файлы до 100мб загружаются свободно. Далее попробовал файл на около 1.3 гб - OutOfMemory. Далее, заметив что проект настроен на x86, поменял это на Any CPU - т.к. у меня х64 система. Запустил, выбрал тот-же 1.3гб файлик - в результате громадный своп на диске, и зависшая мажина. НЕ сразу конечно - минут 5 оно память потихоньку отъедало, потом своп, и потом зависло. Из этого я делаю вывод что OutOfMemoryException на х86 системе из-за нехватки адресного пространства - ибо, если судить по коду, то сначала выделяется 1.3гб на прочтение всего файла, а потом еще и EF наверняка копирует это кудато, создавая ЕЩЕ 1.3гб. И т.д. - вот и OutofMemory. В х64 все лучше - памяти можно побольше использовать, но в истеме ее нету - и начинается создание свопа. Видимо его тоже не хватило, раз зависла.

    А на счет решения проблемы - идей нет. Думаю EF не предназначена для таких больших файлов. В общем - это уже к MS вопрос.

    23 ноября 2010 г. 0:14
  • Заливка через EF требует загрузки всего файла в память, в виде массива байт. 

    Для полноценной работы с FILESTREAM нужно использовать класс SqlFileStream (пример)

    23 ноября 2010 г. 1:00
    Модератор