c# - 从操作返回文件时,流是否会被处置?

标签 c# asp.net-core asp.net-core-mvc streamwriter memorystream

<分区>

我正在向 MemoryStream 写入一个字符串,我需要将该流返回给 Controller 操作,以便我可以将其作为文件发送以供下载。

通常,我将 Stream 包装在 using 语句中,但在这种情况下,我需要返回它。我返回后它仍然会被处置吗?还是我需要自己以某种方式处理它?

//inside CsvOutputFormatter
public Stream GetStream(object genericObject)
{
    var stream = new MemoryStream();
    var writer = new StreamWriter(stream, Encoding.UTF8);
    writer.Write(_stringWriter.ToString());
    writer.Flush();
    stream.Position = 0;
    return stream;
}

返回文件的 Controller Action :

[HttpGet]
[Route("/Discussion/Export")]
public IActionResult GetDataAsCsv()
{
    var forums = _discussionService.GetForums(_userHelper.UserId);

    var csvFormatter = new CsvOutputFormatter(new CsvFormatterOptions());

    var stream = csvFormatter.GetStream(forums);
    return File(stream, "application/octet-stream", "forums.csv");

    //is the stream Disposed here automatically?
}

最佳答案

根据这里的源代码aspnet/AspNetWebStack/blob/master/src/System.Web.Mvc/FileStreamResult.cs

protected override void WriteFile(HttpResponseBase response)
{
    // grab chunks of data and write to the output stream
    Stream outputStream = response.OutputStream;
    using (FileStream)
    {
        byte[] buffer = new byte[BufferSize];

        while (true)
        {
            int bytesRead = FileStream.Read(buffer, 0, BufferSize);
            if (bytesRead == 0)
            {
                // no more data
                break;
            }

            outputStream.Write(buffer, 0, bytesRead);
        }
    }
}

FileStream 是您调用时传递的流

return File(stream, "application/octet-stream", "forums.csv");

更新。

您的问题最初被标记为 Asp.Net MVC,但代码看起来像是更新的核心框架。

在那里也找到了它,虽然写法不同,但它在技术上做同样的事情。

aspnet/AspNetCore/blob/master/src/Mvc/Mvc.Core/src/Infrastructure/FileResultExecutorBase.cs

protected static async Task WriteFileAsync(HttpContext context, Stream fileStream, RangeItemHeaderValue range, long rangeLength)
{
    var outputStream = context.Response.Body;
    using (fileStream)
    {
        try
        {
            if (range == null)
            {
                await StreamCopyOperation.CopyToAsync(fileStream, outputStream, count: null, bufferSize: BufferSize, cancel: context.RequestAborted);
            }
            else
            {
                fileStream.Seek(range.From.Value, SeekOrigin.Begin);
                await StreamCopyOperation.CopyToAsync(fileStream, outputStream, rangeLength, BufferSize, context.RequestAborted);
            }
        }
        catch (OperationCanceledException)
        {
            // Don't throw this exception, it's most likely caused by the client disconnecting.
            // However, if it was cancelled for any other reason we need to prevent empty responses.
            context.Abort();
        }
    }
}

关于c# - 从操作返回文件时,流是否会被处置?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42238826/

相关文章:

jquery - 搜索服务器名称文本时如何在 blazor 上实现多选?

c# - ASP.NET Core 5.0 RouteDataRequestCultureProvider 删除 url 中的默认文化

c# - User.Identity.Name 在 ASP.NET Core MVC 应用程序中返回 null

c# - 在共享_Layout中显示ViewComponent,仅在某些页面上

c# - 当前一个文件大于文件限制时,如何让 log4net 创建一个新文件?

c# - 将linq中的字符串转换为int到大数据库上的实体

c# - 如果我尝试选择一些数据 : 'windows-1252' is not a supported encoding name,我会收到此错误

c# - 为什么 IS 运算符在 false 时输入 IF 语句?

c# - TestContext.DataRow ["MyColumnName"的替代品是什么]

c# - ModelState 在非必需模型字段上返回 false