使用StackExchange.Redis时,如何在RedisValue上维护C#基本类型

时间:2016-03-23 10:15:08

标签: c# redis stackexchange.redis

我开始使用StackExchange.Redis客户端来存储键值对。

我有一个嵌套的动态对象(JObject),我将该对象展平为键值结构,如下所示:

让我们假设JObject看起来像:

"Root":
{
   "Obj1":
    {
       "Prop":12,
       "Prop2": "StringValue"
    }
}

我将此对象展平为Dictionary<string, object>,生成如下所示的键值对:

key: "Root.Obj1.Prop" | value: 12
key: "Root.Obj1.Prop2" | value: "StringValue"

我使用object而不是string,因为我的客户知道如何处理各种原语(不总是strings)。

特定的redis客户端除了RedisValue结构外,该结构具有多种类型的隐式转换,但不包含对象。

所以我不得不将我的字典拆分成不同的原始枚举,以便创建RedisValues并维护&#34;他们的原始类型:

var strs = dic.Where(kvp => kvp.Value is string).Select(kvp => new HashEntry(kvp.Key, (string)kvp.Value));
var ints = dic.Where(kvp => kvp.Value is int).Select(kvp => new HashEntry(kvp.Key, (int)kvp.Value));

现在ints枚举中的每个值的IsInteger属性都等于true。

因此在使用这些值设置redis后,我现在从Redis中获取键值,我手中有一堆RedisValues。我拿了一个RedisValue,它的IsInteger属性等于true,看到它并没有真正保持这个状态。

我的问题:

  1. 有什么方法可以维持集合之间真正的原始类型并得到?据我所知,我有一些拳击\拆箱问题 对象,但我在这个特定的应用程序中有很多好处。使用RedisValue结构并不是我想在我的应用程序中做的事情。我希望将其保存在与Redis通信的小型特定层中。

  2. 如果没有办法做(1)那么RedisValue是否有任何理由不在集合之间保持IsInteger属性并得到?当我设置RedisValue时,我将IsInteger属性设置为true,当我获取它时,它是假的。

  3. 谢谢。

1 个答案:

答案 0 :(得分:3)

您可以使用类型信息为每个属性编写一个附加键,例如

Root:Obj1:Prop=12
Root:Obj1:Prop:type=int

Root.Obj1.Prop2=StringValue
Root.Obj1.Prop2:type=string

并始终首先检索类型键,以便您知道如何转换值键。

但我不推荐它。相反,我建议使用两种标准方法中的一种,具体取决于您打算如何通过Redis查询数据。

  1. 将强类型对象映射到Redis键

    • 假设通过Redis操作进行有效查询是一个优先事项
    • 允许您在映射类中本地化Redis特定代码
  2. 存储持久对象

    • 基本上是数据的BLOB。可能是一个完整的JSON对象(甚至可能包括每个属性的完整类型信息 - 有一个使用Json.Net启用它的选项)或使用protobuf的字节数组
    • 假设您只是将Redis用于存储;哪个好的