3

只是想弄清楚 servicestack.text 支持将 expando 对象序列化到 json 和从 json 序列化的能力。我知道expando 对象实现了一个IDictionary。当我序列化到 json 和从 json 序列化时,我无法在反序列化的 IDictionary 中获取正确的类型。由于 Json 本身不支持类型并且 servicestack 有一个名为 JsConfig.IncludeTypeInfo 的设置,我希望它在序列化的 json 中包含类型信息,以使服务堆栈能够反序列化为另一端的正确类型(例如,没有小数位的小数被反序列化为 uint64)。

是否有强制 servicestack 使用 expando 对象正确反序列化与源相同的类型?

Ps:我不想使用 poco 对象来实现这一点,因为直到运行时我才知道对象的属性。

下面是一个快速测试,显示我的意思。

谢谢

/// <summary>
/// Test servicestack serialisation
/// I was expecting that IncludeTypeInfo=true would always add the type info
/// so when you deserialise into a IDictionary<string,object> servicerstack
/// would have enough information to convert to the expected type
/// </summary>
[Test]
public void TestDynamicSerialization()
{
    JsConfig.Reset();
    JsConfig.IncludeNullValues = true;
    JsConfig.IncludeTypeInfo = true;
    JsConfig.EmitCamelCaseNames = false;
    JsConfig.ConvertObjectTypesIntoStringDictionary = true;
    JsConfig.PropertyConvention = JsonPropertyConvention.Lenient;
    JsConfig.TryToParsePrimitiveTypeValues = true;

    // create an expando object
    dynamic obj = new ExpandoObject();

    // cast as a idictionary and set two decimals, one with decimnal places and one without
    var objDict = (IDictionary<string, object>)obj;
    objDict["decimal1"] = 12345.222M;
    objDict["decimal2"] = 12345M;

    Assert.AreEqual(typeof(decimal), objDict["decimal1"].GetType());
    Assert.AreEqual(typeof(decimal), objDict["decimal2"].GetType());

    // serialise to json
    var json = JsonSerializer.SerializeToString(obj);

    //deserialise to a a IDictionary<string,object>
    var deserialisedDict = JsonSerializer.DeserializeFromString<IDictionary<string, object>>(json);

    // make sure we got the expected types
    Assert.AreEqual(typeof(decimal), deserialisedDict["decimal1"].GetType());
    Assert.AreEqual(typeof(decimal), deserialisedDict["decimal2"].GetType(), "Fails because type is UInt64 expected decimal");


}
4

2 回答 2

1

NuGet 上的 ServiceStack.Text 是一个 .NET 3.5 dll,没有对 Dynamic/Expando 的隐式支持。您仍然可以使用JsonObject动态解析 JSON。

在 ServiceStack.Text 的 .NET 4.0 构建中,您可以使用DynamicJson它将对动态类中的 JSON 对象的访问包装。

于 2012-12-05T06:03:14.703 回答
1

应该从https://github.com/ServiceStack/ServiceStack.Text/pull/347开始修复,除非您指定 TryToParseNumericType,否则默认情况下会返回小数,在这种情况下,您将获得最合适的数字类型。

于 2013-06-30T13:40:11.633 回答