Last active
January 22, 2019 15:33
-
-
Save Dkowald/28ea6f6bd38562c131a76052587c6268 to your computer and use it in GitHub Desktop.
ResponseBuffering for Asp.Net core
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.IO; | |
using System.Threading.Tasks; | |
using Microsoft.AspNetCore.Http; | |
// ReSharper disable once CheckNamespace | |
namespace kwd.gist | |
{ | |
/// <summary> | |
/// Middleware to capture response stream so it can be | |
/// manipulated further. | |
/// </summary> | |
/// <remarks> | |
/// Useful to capture HTTP response for further processing, rather than immediately sending response. | |
/// </remarks> | |
public class ResponseBuffering : IMiddleware | |
{ | |
private Stream _original; | |
private MemoryStream _buffered; | |
public async Task InvokeAsync(HttpContext context, RequestDelegate next) | |
{ | |
if (context.Response.HasStarted) | |
{ | |
throw new Exception("Cannot buffer response, it has already started"); | |
} | |
_original = context.Response.Body; | |
_buffered = new MemoryStream(); | |
context.Items.Add(nameof(ResponseBuffering), _buffered); | |
context.Response.Body = _buffered; | |
await next(context); | |
if (_buffered != null) | |
{ | |
_buffered.Seek(0, SeekOrigin.Begin); | |
context.Response.Body = _original; | |
await _buffered.CopyToAsync(context.Response.Body); | |
_buffered.Dispose(); | |
_buffered = null; | |
} | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System.IO; | |
using System.Text; | |
using Microsoft.AspNetCore.Builder; | |
using Microsoft.AspNetCore.Http; | |
using Microsoft.Extensions.DependencyInjection; | |
// ReSharper disable once CheckNamespace | |
namespace kwd.gist | |
{ | |
/// <summary> | |
/// Various extensions to add and use the <see cref="ResponseBuffering"/> middleware. | |
/// </summary> | |
public static class ResponseBufferingMiddlewareExtensions | |
{ | |
/// <summary> | |
/// Add the <see cref="ResponseBuffering"/> middleware to the container. | |
/// </summary> | |
public static IServiceCollection AddResponseBuffering(this IServiceCollection services) | |
{ | |
services.AddScoped<ResponseBuffering>(); | |
return services; | |
} | |
/// <summary> | |
/// Add the <see cref="ResponseBuffering"/> middleware to the Asp.Net pipeline. | |
/// </summary> | |
public static IApplicationBuilder UseResponseBuffering(this IApplicationBuilder builder) | |
{ | |
builder.UseMiddleware<ResponseBuffering>(); | |
return builder; | |
} | |
/// <summary> | |
/// True if the HTTP response output Body stream is being buffered. | |
/// </summary> | |
public static bool IsBuffered(this HttpResponse resp) => | |
resp.Body is MemoryStream; | |
/// <summary> | |
/// True if current request context has a response that is buffered. | |
/// </summary> | |
public static bool IsResponseBuffered(this HttpContext ctx) => | |
ctx?.Response?.IsBuffered() == true; | |
/// <summary> | |
/// Read current buffered response data (if any). | |
/// </summary> | |
public static string ReadBufferedResponse(this HttpContext ctx) => | |
ReadBufferedResponse(ctx?.Response); | |
/// <summary> | |
/// Read current buffered response data (if any). | |
/// </summary> | |
public static string ReadBufferedResponse(this HttpResponse resp) | |
{ | |
string result = null; | |
if (resp?.Body is MemoryStream mem) | |
{ | |
var originalPosition = mem.Position; | |
mem.Position = 0; | |
using (var strStream = new StreamReader(mem, Encoding.UTF8, true, 1024, true)) | |
{ | |
result = strStream.ReadToEnd(); | |
} | |
mem.Position = originalPosition; | |
} | |
return result; | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment