【问题标题】:OutputCache varying by a complex object property passed using ModelBinder from SessionOutputCache 因使用 Session 中的 ModelBinder 传递的复杂对象属性而异
【发布时间】:2016-12-30 17:28:45
【问题描述】:

我们将 Couchbase 用于 Session 和 OutputCache。

在这种情况下,我们如何使用从 Session 中检索值的自定义模型绑定器将传递给方法的复杂对象缓存?

这是我要使用OutputCache 属性缓存的方法的签名:

[HttpGet]
[OutputCache(CacheProfile = "MyObjectsCache", VaryByParam = "myParam")]
public ActionResult Index([ModelBinder(typeof (CustomVariableSessionModelBinder<MyClass>))] MyClass myParam)
{

注意:这里使用 ModelBinder 的原因超出了我的范围,我无法更改它。

MyClass 是一个具有 Id 的复杂对象。我想使用 Id 作为缓存标识符。

public class MyClass
{
   public int Id{get;set;}
   //Other Properties

这是从 Session 中检索对象的方式:

var sessionKey = typeof (MyNamespace.MyClass).FullName;
var httpContext = HttpContext.Current;
MyNamespace.MyClass newObject = null;

if (httpContext.Session != null)
{
    newObject = httpContext.Session[sessionKey] as MyNamespace.MyClass;
}

您可以在这种情况下使用VaryByParam,还是我必须使用VaryByCustom

【问题讨论】:

    标签: asp.net-mvc-4 asp.net-caching


    【解决方案1】:

    我没有对此进行测试,但它应该工作。不过,这几乎是您唯一的选择。

    除了内置的变化方式外,您还可以通过“自定义”进行变化。这将调用 Global.asax 中您需要覆盖的方法:GetVaryByCustomString。对于您的情况,重要的是,此方法通过HttpContext,因此您应该能够查看会话。从本质上讲,解决方案将类似于:

    public override string GetVaryByCustomString(HttpContext context, string custom)
    {
        var args = custom.ToLower().Split(';');
        var sb = new StringBuilder();
    
        foreach (var arg in args)
        {
            switch (arg)
            {
                case "session":
                    var obj = // get your object from session
                    // now create some unique string to append
                    sb.AppendFormat("Session{0}", obj.Id);
            }
        }
    
        return sb.ToString();
    }
    

    这旨在处理多种不同类型的“自定义”变化类型。例如,如果您想通过“用户”来改变,这很常见,您只需在您的开关中添加一个案例。重要的部分是此方法返回的字符串实际上是输出缓存变化的内容,因此您希望它在这种情况下是唯一的。这就是为什么我在这里为对象的 id 加上“Session”前缀。例如,如果您刚刚添加了 id,假设为 123,然后在另一种情况下,您根据用户而变化,并且该字符串仅由用户的 id 组成,恰好也是 123。这将是输出缓存的相同字符串,并且您会得到一些奇怪的结果。请注意自定义字符串的外观。

    现在,您只需更改 OutputCache 属性,例如:

    [OutputCache(CacheProfile = "MyObjectsCache", VaryByParam = "myParam", VaryByCustom = "Session")]
    

    注意:要同时改变多个自定义内容,您可以使用 ; 将它们分开(基于上面代码的工作方式)。例如:VaryByCustom = "Session;User"

    【讨论】:

    • 会话在 Global.asax.cs 中不可用
    猜你喜欢
    • 1970-01-01
    • 2013-03-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-08-26
    • 2015-02-06
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多