Подтвердить что ты не робот

Не удается получить доступ к закрытому потоку при создании загружаемого текстового файла в ASP MVC 3

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

Невозможно получить доступ к закрытому потоку.

Я рассмотрел вопросы, связанные с имитацией: Не удается получить доступ к закрытому потоку Но это было не очень полезно.

Вот мой код:

    private FileStreamResult Export()
    {
        string name = "filename.txt";

        MemoryStream stream = new MemoryStream();
        using (StreamWriter writer = new StreamWriter(stream))
        {
            StringBuilder sb = new StringBuilder();
            sb.Append("A text...");
            writer.WriteLine(sb.ToString());
        }

        return File(stream, "text/plain", name);
    }

ОБНОВЛЕНИЕ (рабочая копия):

Это дает мне пустой текстовый файл.

private FileResult Export()
{
    string name = "filename.txt";

    MemoryStream stream = new MemoryStream();
    StreamWriter writer = new StreamWriter(stream);

    StringBuilder sb = new StringBuilder();
    sb.Append("A text...");
    writer.WriteLine(sb.ToString());

    writer.Flush();
    stream.Seek(0, SeekOrigin.Begin);

    return File(stream, "text/plain", name);
}
4b9b3361

Ответ 1

Это верно, когда вы переносите поток в другой поток, вызов .Close() или .Dispose() для любого из них будет уничтожать весь поток. В этом случае обертка MemoryStream в StreamWriter означает, что когда оператор using завершает StreamWriter и MemoryStream, оба расположены.

Моя догадка заключается в том, что вы возвращаете FileStreamResult инкапсулирующий File закроет поток для вас после того, как поток больше не будет использоваться. В этом случае вы не хотите использовать оператор using и захотите оставить поток открытым при его возврате.

UPDATE

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

stream.Seek(0, SeekOrigin.Begin);

Ответ 2

Просто удалите этот оператор using - вы передаете ссылку на объект в метод File, и вы объяснили причину исключения. Из MSDN,

Объект StreamWriter вызывает Dispose на предоставленном объекте Stream когда вызывается StreamWriter.Dispose.

Я полагаю, что File будет утилизировать поток сам по себе после использования (не проверяется, глядя на исходный код).

UPDATE:

writer.Flush(); перед возвратом должно помочь вам

Ответ 3

Замените тип FileStreamResult на действие с помощью FileResult.

Ответ 4

Вы должны установить положение запоминающего потока на 0 перед его использованием в файле FileStreamResult, иначе он будет считан из текущей позиции (IE конец потока).

stream.Position = 0;
return File(stream, "text/plain", name);

Просто одно и то же.

Я знаю, что эта ветка древняя, просто надеясь помочь другим, имеющим ту же проблему.