IIS 7 managed module cannot receive Content-Length or sent bytes

I have an ISAPI filter for IIS 6 that does some user processing using a response field with a response byte. I would like to update this for IIS 7, but I have a problem. None of the IIS 7 events seem to have access to content content, bytes sent, or any data that will allow me to calculate the length of the content or bytes sent. (I know that the content length header and the bytes sent do not match, but either will work for this purpose.)

From what I can tell, the content length header is added by HTTP.SYS after the managed modules have completed execution. Right now I have an event handler that runs on EndRequest. If I could get the output stream, I could figure out what I need, but the managed pipeline does not seem to have access to this either.

Is there a way to get the length of the content or bytes sent in a managed pipeline? Otherwise, can you somehow calculate the length of the content or bytes sent from objects available in the managed pipeline?

+7
c # module iis-7
source share
1 answer

To get sent bytes, you can use the HttpResponse.Filter property. Because MSDN documents say that this property gets or sets the wrapping filter object, which is used to modify the body of the HTTP object before passing.

You can create a new System.IO.Stream that wraps the existing HttpResponse.Filter stream and counts the bytes passed to the Write method before passing them. For example:

 public class ContentLengthModule : IHttpModule { public void Init(HttpApplication context) { context.BeginRequest += OnBeginRequest; context.EndRequest += OnEndRequest; } void OnBeginRequest(object sender, EventArgs e) { var application = (HttpApplication) sender; application.Response.Filter = new ContentLengthFilter(application.Response.Filter); } void OnEndRequest(object sender, EventArgs e) { var application = (HttpApplication) sender; var contentLengthFilter = (ContentLengthFilter) application.Response.Filter; var contentLength = contentLengthFilter.BytesWritten; } public void Dispose() { } } public class ContentLengthFilter : Stream { private readonly Stream _responseFilter; public int BytesWritten { get; set; } public ContentLengthFilter(Stream responseFilter) { _responseFilter = responseFilter; } public override void Flush() { _responseFilter.Flush(); } public override long Seek(long offset, SeekOrigin origin) { return _responseFilter.Seek(offset, origin); } public override void SetLength(long value) { _responseFilter.SetLength(value); } public override int Read(byte[] buffer, int offset, int count) { return _responseFilter.Read(buffer, offset, count); } public override void Write(byte[] buffer, int offset, int count) { BytesWritten += count; _responseFilter.Write(buffer, offset, count); } public override bool CanRead { get { return _responseFilter.CanRead; } } public override bool CanSeek { get { return _responseFilter.CanSeek; } } public override bool CanWrite { get { return _responseFilter.CanWrite; } } public override long Length { get { return _responseFilter.Length; } } public override long Position { get { return _responseFilter.Position; } set { _responseFilter.Position = value; } } } 
+7
source share

All Articles