2015-02-18 7 views
3

Я пытаюсь реализовать кэширование вывода для результатов моих действий.Условный кэш с использованием OutputCacheAttribute в Asp.net MVC 4

В моих действиях в зависимости от ответа некоторых бизнес-правил возвращается ответ. В своем ответе я отправляю код ошибки. Я не хочу кэшировать ответ, если есть какая-либо ошибка.

После в Действие Результат

class Response 
    { 
    public int ErrorCode { get; set; } 
    public string Message { get; set; } 

} 


    [OutputCache(CacheProfile = "Test")] 
    public ActionResult Sample() 
    { 
     Response response = new Response(); 
     return new JsonResult { Data = response, JsonRequestBehavior = JsonRequestBehavior.AllowGet }; 
    } 

Я хочу кэшировать результат только если ErrorCode == 0.

Я попытался перекрывая OutputCache, но он не работает

public class CustomOutputCacheAttribute : OutputCacheAttribute 
    { 
     public override void OnActionExecuted(ActionExecutedContext filterContext) 
     { 

      if (filterContext.Result is JsonResult) 
      { 
       var result = (JsonResult)filterContext.Result; 
       BaseReponse response = result.Data as BaseReponse; 
       if (!response.IsSuccess) 
       { 
        filterContext.HttpContext.Response.Cache.SetNoStore(); 
       } 
       base.OnActionExecuted(filterContext); 
      } 
     } 


    } 

Есть ли другой способ или подход к достижению этой цели.

Благодаря

+0

Переопределение 'OutputCacheAttribute' правильный способ сделать это. Вы также можете кэшировать объект ответа вручную в своем методе действий. –

+0

Обновлено вопрос –

+0

Почему вы реализуете свои собственные объекты ответа на ошибки? OutputCache имеет встроенную поддержку обычных HTTP-ошибок ... – Moeri

ответ

2

Вы можете создать свой собственный пользовательский атрибут, который будет игнорировать [OutputCache] на основе результирующего кода ошибки, что-то вроде этого:

[OutputCache(Duration=60, VaryByParam="none")] 
[OutputCacheValidation] 
public ActionResult Sample() 
{ 
    var r = new Response(); 
    r.ErrorCode = 0; 
    return Json(r, JsonRequestBehavior.AllowGet); 
} 

public class OutputCacheValidationAttribute : ActionFilterAttribute 
{ 
    public override void OnResultExecuting(ResultExecutingContext filterContext) 
    { 
     base.OnResultExecuting(filterContext); 
     filterContext.HttpContext.Response.Cache.AddValidationCallback(ValidatioCallback, filterContext.Result); 
    } 

    private static void ValidatioCallback(HttpContext context, object data, ref HttpValidationStatus validationStatus) 
    { 
     var jsonResult = data as JsonResult; 
     if (jsonResult == null) return; 

     var response = jsonResult.Data as Response; 
     if (response == null) return; 

     if (response.ErrorCode != 0) 
     { 
      //ignore [OutputCache] for this request 
      validationStatus = HttpValidationStatus.IgnoreThisRequest; 
      context.Response.Cache.SetNoServerCaching(); 
      context.Response.Cache.SetNoStore(); 
     } 
    } 
} 
+0

Спасибо, однако он все еще сохраняет данные в кеш, но во время обслуживания он выполняет проверку. Я хотел не хранить данные вообще в кеше, если возникает ошибка –

+0

У меня появилась идея из вашего кода и http://juristr.com/blog/2012/10/output-caching-in-aspnet-mvc/. Теперь он работает. благодаря –