我在MVC中有这个 Action
[OutputCache(Duration = 1200, VaryByParam = "*")]
public ActionResult FilterArea( string listType, List<int> designersID, int currPage = 1 )
{
// Code removed
}
无法使用 url 显示正确的 HTML,例如
这是 .NET 中 OutputCache 的一个已知错误,导致无法使用列表参数识别 VaryByParam 还是我遗漏了什么?
最佳答案
我在 MVC3 中也有同样的问题,我相信它在 MVC5 中仍然是同样的情况。
这是我的设置。
要求
POST,Content-Type:application/json,传入一个字符串数组作为参数
{ "options": ["option1", "option2"] }
Controller 方法
[OutputCache(Duration = 3600, Location = OutputCacheLocation.Any, VaryByParam = "options")]
public ActionResult GetOptionValues(List<string> options)
我尝试了 OutputCache 的所有可能选项,但它并没有为我缓存。绑定(bind)工作正常,使实际方法正常工作。我最大的怀疑是 OutputCache 没有创建唯一的缓存键,所以我什至从
System.Web.MVC.OutputCache
中提取了它的代码来验证。我已经验证它即使在传入 List<string>
的情况下也能正确构建唯一键。 那里的其他东西有问题,但不值得花更多的精力。OutputCacheAttribute.GetUniqueIdFromActionParameters(filterContext,
OutputCacheAttribute.SplitVaryByParam(this.VaryByParam);
解决方法
我最终在另一个 SO 帖子之后创建了我自己的 OutputCache 属性。更容易使用,我可以去享受一天的剩余时间。
Controller 方法
[MyOutputCache(Duration=3600)]
public ActionResult GetOptionValues(Options options)
自定义请求类
我是从
List<string>
继承的,所以我可以调用 MyOutputcache 类中覆盖的 .ToString()
方法来给我一个唯一的缓存键字符串。仅这种方法就为其他人解决了类似的问题,但对我没有。[DataContract(Name = "Options", Namespace = "")]
public class Options: List<string>
{
public override string ToString()
{
var optionsString= new StringBuilder();
foreach (var option in this)
{
optionsString.Append(option);
}
return optionsString.ToString();
}
}
自定义输出缓存类
public class MyOutputCache : ActionFilterAttribute
{
private string _cachedKey;
public int Duration { get; set; }
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
if (filterContext.HttpContext.Request.Url != null)
{
var path = filterContext.HttpContext.Request.Url.PathAndQuery;
var attributeNames = filterContext.ActionParameters["Options"] as AttributeNames;
if (attributeNames != null) _cachedKey = "MYOUTPUTCACHE:" + path + attributeNames;
}
if (filterContext.HttpContext.Cache[_cachedKey] != null)
{
filterContext.Result = (ActionResult) filterContext.HttpContext.Cache[_cachedKey];
}
else
{
base.OnActionExecuting(filterContext);
}
}
public override void OnActionExecuted(ActionExecutedContext filterContext)
{
filterContext.HttpContext.Cache.Add(_cachedKey, filterContext.Result, null,
DateTime.Now.AddSeconds(Duration), System.Web.Caching.Cache.NoSlidingExpiration,
System.Web.Caching.CacheItemPriority.Default, null);
base.OnActionExecuted(filterContext);
}
}
关于asp.net-mvc-5 - 如果参数是列表,则 VaryByParam 失败,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/24860685/