【问题标题】:Cache ASP.NET page for anonymous users only仅为匿名用户缓存 ASP.NET 页面
【发布时间】:2011-01-06 02:26:02
【问题描述】:

是否有一种简单的方法可以仅为匿名用户缓存 ASP.NET 整个页面(使用表单身份验证)?

上下文:我正在创建一个网站,其中向匿名用户显示的页面大部分是完全静态的,但为登录用户显示的相同页面不是。

当然,我可以通过后面的代码手动执行此操作,但我认为可能有更好/更简单/更快的方法。

【问题讨论】:

  • 你有没有解决这个问题?我们有类似的需求,但 varyByCustom 不是解决方案。
  • 目前我使用代码隐藏解决方案,我可以轻松地决定是否要缓存页面。如果用户没有登录,我缓存。如果用户已登录,则整个页面的缓存将被禁用(并且只缓存“静态”部分)。在收到下面的答案后,我搜索了没有代码隐藏的解决方案,但没有发现任何帮助。毕竟,代码隐藏解决方案也非常清晰,与纯 ASP.NET 解决方案相比没有太大的缺点。
  • 您能分享一下您的代码隐藏解决方案吗?你如何控制这样的缓存?
  • 在代码中,如果您的页面默认缓存,请添加类似内容: if (User.Identity.IsAuthenticated) { Response.Cache.SetCacheability(HttpCacheability.NoCache); Response.Cache.SetExpires(DateTime.Now.AddMinutes(-1)); Response.Cache.SetNoStore();或者,如果用户未登录,您可以在代码中设置缓存,并避免在 ASP.NET 端设置任何内容。 (对不起,丑陋的没有缩进的代码。找不到如何在 cmets 中制作换行符......)
  • @MainMa 你看到这个答案了吗? stackoverflow.com/a/4951434/498892

标签: asp.net caching forms-authentication


【解决方案1】:

我使用的是 asp.net MVC,所以我在我的控制器中做了这个

if (User.Identity.IsAuthenticated) {
    Response.Cache.SetCacheability(HttpCacheability.NoCache);
    Response.Cache.SetExpires(DateTime.Now.AddMinutes(-1));
    Response.Cache.SetNoStore();
    Response.Cache.SetNoServerCaching();
}
else {
    Response.Cache.VaryByParams["id"] = true; // this is a details page
    Response.Cache.SetVaryByCustom("username"); // see global.asax.cs GetVaryByCustomString()
    Response.Cache.SetExpires(DateTime.Now.AddSeconds(60));
    Response.Cache.SetCacheability(HttpCacheability.Server);
    Response.Cache.SetValidUntilExpires(true);
}

我这样做的原因(而不是声明式)是我还需要能够通过配置打开和关闭它(此处未显示,但在 if 中对我的配置变量进行了额外的检查)。

您仍然需要根据用户名进行更改,否则当出现登录用户时您将不会执行此代码。我的 GetVaryByCustomString 函数在未通过身份验证时返回“匿名”,或者在可用时返回用户名。

【讨论】:

    【解决方案2】:

    您可以使用VaryByCustom,并使用像username 这样的密钥。

    【讨论】:

    • 这样做的问题是它也会缓存显示给登录用户的页面。就我而言,这些页面已经部分缓存,而某些部分根本无法缓存(即使对于同一用户)。当然,如果用户登录,我可以将 VaryByCustom 键设置为随机值,但这会产生巨大的性能问题。
    【解决方案3】:

    没有什么能阻止您使用所需的行为扩展现有属性,

    例如:

    public class AnonymousOutputCacheAttribute : OutputCacheAttribute
    {
        public override void OnActionExecuting(ActionExecutingContext filterContext) 
        {
           if(filterContext.HttpContext.User.Identity.IsAuthenticated)
              return;
    
            base.OnActionExecuting(filterContext);
        }  
    }  
    

    尚未对此进行测试,但我不明白为什么这不起作用。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-09-08
      • 2014-01-24
      • 1970-01-01
      • 2017-08-16
      • 1970-01-01
      • 2014-02-08
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多