asp.net-mvc 从动作写入输出流
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/943122/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Writing to Output Stream from Action
提问by Palani
For some strange reasons, I want to write HTML directly to the Response stream from a controller action. (I understand MVC separation, but this is a special case.)
出于一些奇怪的原因,我想将 HTML 直接从控制器操作写入响应流。(我理解MVC分离,但这是一个特例。)
Can I write directly into the HttpResponsestream? In that case, which IViewobject should the controller action should return? Can I return 'null'?
我可以直接写入HttpResponse流吗?在这种情况下,IView控制器操作应该返回哪个对象?我可以返回“空”吗?
回答by Kna?is
I used a class derived from FileResultto achieve this using normal MVC pattern:
我使用了一个派生自的类FileResult来使用普通的 MVC 模式实现这一点:
/// <summary>
/// MVC action result that generates the file content using a delegate that writes the content directly to the output stream.
/// </summary>
public class FileGeneratingResult : FileResult
{
/// <summary>
/// The delegate that will generate the file content.
/// </summary>
private readonly Action<System.IO.Stream> content;
private readonly bool bufferOutput;
/// <summary>
/// Initializes a new instance of the <see cref="FileGeneratingResult" /> class.
/// </summary>
/// <param name="fileName">Name of the file.</param>
/// <param name="contentType">Type of the content.</param>
/// <param name="content">Delegate with Stream parameter. This is the stream to which content should be written.</param>
/// <param name="bufferOutput">use output buffering. Set to false for large files to prevent OutOfMemoryException.</param>
public FileGeneratingResult(string fileName, string contentType, Action<System.IO.Stream> content,bool bufferOutput=true)
: base(contentType)
{
if (content == null)
throw new ArgumentNullException("content");
this.content = content;
this.bufferOutput = bufferOutput;
FileDownloadName = fileName;
}
/// <summary>
/// Writes the file to the response.
/// </summary>
/// <param name="response">The response object.</param>
protected override void WriteFile(System.Web.HttpResponseBase response)
{
response.Buffer = bufferOutput;
content(response.OutputStream);
}
}
The controller method would now be like this:
控制器方法现在是这样的:
public ActionResult Export(int id)
{
return new FileGeneratingResult(id + ".csv", "text/csv",
stream => this.GenerateExportFile(id, stream));
}
public void GenerateExportFile(int id, Stream stream)
{
stream.Write(/**/);
}
Note that if buffering is turned off,
请注意,如果缓冲关闭,
stream.Write(/**/);
becomes extremely slow. The solution is to use a BufferedStream. Doing so improved performance by approximately 100x in one case. See
变得极其缓慢。解决方案是使用 BufferedStream。在一种情况下,这样做将性能提高了大约 100 倍。看
回答by womp
Yes, you can write directly to the Response. After you're done, you can call CompleteRequest() and you shouldn't need to return anything.
是的,您可以直接写入响应。完成后,您可以调用 CompleteRequest() 并且不需要返回任何内容。
For example:
例如:
// GET: /Test/Edit/5
public ActionResult Edit(int id)
{
Response.Write("hi");
HttpContext.ApplicationInstance.CompleteRequest();
return View(); // does not execute!
}
回答by John Sheehan
Write your own Action Result. Here's an example of one of mine:
编写您自己的操作结果。这是我的一个例子:
public class RssResult : ActionResult
{
public RssFeed RssFeed { get; set; }
public RssResult(RssFeed feed) {
RssFeed = feed;
}
public override void ExecuteResult(ControllerContext context) {
context.HttpContext.Response.ContentType = "application/rss+xml";
SyndicationResourceSaveSettings settings = new SyndicationResourceSaveSettings();
settings.CharacterEncoding = new UTF8Encoding(false);
RssFeed.Save(context.HttpContext.Response.OutputStream, settings);
}
}
回答by G-Wiz
If you don't want to derive your own result type, you can simply write to Response.OutputStreamand return new EmptyResult().
如果您不想派生自己的结果类型,您可以简单地写入Response.OutputStream并返回new EmptyResult()。
回答by Jordan S. Jones
You can do return Content(...);where, if I remember correctly, ...would be what you want to write directly to the output stream, or nothing at all.
return Content(...);如果我没记错的话,你可以在什么地方...直接写到输出流,或者什么都不写。
Take a look at the Contentmethods on the Controller: http://aspnet.codeplex.com/SourceControl/changeset/view/22907#266451
看看上的Content方法Controller:http: //aspnet.codeplex.com/SourceControl/changeset/view/22907#266451
And the ContentResult: http://aspnet.codeplex.com/SourceControl/changeset/view/22907#266450
和ContentResult:http: //aspnet.codeplex.com/SourceControl/changeset/view/22907#266450

