简体   繁体   中英

Asp.Net Server-side Output Cache gets hit every request (HttpHandler)

I have this pretty straight forward piece of code below.

There are several things I've tried and I can't understand why the server-side output cache is not working at http://localhost . Below is the last try of 'cache settings' in order to not see a HIT on the Debug output pane.

It's driving me nuts! How do I prevent the HIT...?! When I open the Developer tools and check Disable cache I'm expecting a cached server-side copy and not see a HIT in the Debug output pane.

I'm on Windows 8, but even on another Windows version (/IIS Version), I can't imagine the eventual code would be different.

using System;
using System.Diagnostics;
using System.Net.Http;
using System.Web;

namespace WebApplication1
{
    /// <summary>
    /// Summary description for MyHandler
    /// </summary>
    public class MyHandler : IHttpHandler
    {
        public void ProcessRequest(HttpContext context)
        {
            Debug.WriteLine("HIT"+DateTime.Now.ToLongTimeString());

            context.Response.Cache.SetExpires(DateTime.Now.AddMinutes(5));
            context.Response.Cache.SetCacheability(HttpCacheability.Server);
            context.Response.Cache.SetValidUntilExpires(true);
            context.Response.Cache.SetOmitVaryStar(true);
            context.Response.Cache.VaryByParams["none"] = true;
            context.Response.Cache.SetMaxAge(new TimeSpan(0, 5, 0));

            // Just here for testing purposes
            const string url = "http://otherserver/image.png";
            using (var client = new HttpClient())
            {
                var task = client.GetStreamAsync(url);
                task.Wait();
                task.Result.CopyTo(context.Response.OutputStream);
                context.ApplicationInstance.CompleteRequest();
            }
        }

        public bool IsReusable
        {
            get { return true; }
        }
    }
}

It turns out that ApplicationInstance.CompleteRequest() is causing the pain in my situation. According to MSDN it:

Causes ASP.NET to bypass all events and filtering in the HTTP pipeline chain of execution and directly execute the EndRequest event.

This is the Asp.Net pipeline flow

Asp.Net管道流量

The Handler is being executed somewhere in the middle as you can see and after calling ApplicationInstance.CompleteRequest() it skips everything and goes directly to Send request (or CompleteRequest() internally).

When this happens it also skips the "Update cache" events. This is where the Request Cache gets updated; where the Server-side output cache items will be added...

So, be aware of what ApplicationInstance.CompleteRequest() does when you think you're done in your HttpHandler !

Another interesting read: https://weblog.west-wind.com/posts/2009/May/21/Dont-use-ResponseEnd-with-OutputCache

Happy caching!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM