1

返回 Json 的操作的 OutputCache 属性不起作用 - 当我在浏览器中多次点击操作 URL 时,每次我在 VS2012 中激活断点(看起来 OutputCache 属性被忽略)。这是我的代码:

public class ApiController : GenericControllerBase
{

    [OutputCache(Duration = 300, VaryByParam = "type;showEmpty;sort;platform")]
    public JsonResult GetCategories(string type, bool? showEmpty, string sort, string platform)
    {
        ///... creating categoryResults object
        return Json(new ApiResult() { Result = categoryResults }, JsonRequestBehavior.AllowGet);
    }

}   

GenericControllerBase 继承自 Controller。在从 GenericControllerBase OutputCache 继承的其他控制器中,它们按预期工作,但它们返回 View() 而不是 Json。作为一个实验,我添加了 VaryByCustom 参数并检查了 global.asax 文件中的 GetVaryByCustomString 方法也没有被命中,所以缓存功能被完全忽略了。我使用 MVC3 和 autofac 进行服务注入(但其他使用 autofac 注入的控制器可以与 OutputCache 一起正常工作)。

可能是什么问题呢?什么会阻止 OutputCache 功能?是否可能与缓存整个响应有关?在我的项目中使用 OutputCache 的所有其他操作都是在视图中嵌入 @Html.Action(...) 的部分操作。

在 MVC3 中对 GET 操作缓存整个 Json 响应的最佳方法是什么?

更新

经过一些测试后发现,对于返回完整页面(不仅是 json)的操作,OutputCache 会被忽略。缓存仅适用于我项目中的子操作。可能是什么原因?

4

1 回答 1

5

最终,我使用了 MVC3 忽略 OutputCache 属性的解决方法。我使用自定义动作过滤器进行缓存:

public class ManualActionCacheAttribute : ActionFilterAttribute
{
    public ManualActionCacheAttribute()
    {
    }

    public int Duration { get; set; }

    private string cachedKey = null;

    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        string key = filterContext.HttpContext.Request.Url.PathAndQuery;
        this.cachedKey = "CustomResultCache-" + key;
        if (filterContext.HttpContext.Cache[this.cachedKey] != null)
        {
            filterContext.Result = (ActionResult)filterContext.HttpContext.Cache[this.cachedKey];
        }
        else
        {
            base.OnActionExecuting(filterContext);
        }
    }

    public override void OnActionExecuted(ActionExecutedContext filterContext)
    {
        filterContext.HttpContext.Cache.Add(this.cachedKey, filterContext.Result, null, DateTime.Now.AddSeconds(Duration), System.Web.Caching.Cache.NoSlidingExpiration, System.Web.Caching.CacheItemPriority.Default, null);
        base.OnActionExecuted(filterContext);
    }
}

以上属性根据给定时间的确切 URL 路径和查询缓存请求,并按预期工作。

于 2013-01-17T11:34:10.150 回答