NoR*_*Ryb 3 .net json.net sqlgeography deserialization breeze
我在SinglePageApplication中使用DbGeography-Type(带微风和角度).现在使用带有DbGeography-Type的数据(readOnly)时没有问题.
只要我保存了一个具有DbGeography-Type属性的实体,就会出现以下错误:
Error getting value from 'WellKnownValue' on 'System.Data.Entity.Spatial.DbGeography'
Run Code Online (Sandbox Code Playgroud)
当数据被序列化为JSON(使用newtonsoft JSON.NET或ODATA/WebAPI?)时,DbGeography会被正确序列化,但属性"WellKownValue"被称为"Geography".这也反映在MSDN文档中:
[DataMemberAttribute(Name = "Geography")]
public DbGeographyWellKnownValue WellKnownValue { get; set; }
Run Code Online (Sandbox Code Playgroud)
我的实体看起来像这样(通过电线):
{
..
"Name" : "Test",
"Coordinate" : {
"$id" : "3",
"$type" : "System.Data.Entity.Spatial.DbGeography, EntityFramework",
"Geography" : {
"$id" : "4",
"$type" : "System.Data.Entity.Spatial.DbGeographyWellKnownValue, EntityFramework",
"CoordinateSystemId" : 4326,
"WellKnownText" : "POINT (8.73275400148029 47.5006958431132)"
}
}
}
Run Code Online (Sandbox Code Playgroud)
我想当它稍后被反序列化时,JSON.NET不知道我的对象的Geography -Property实际上被称为WellKnownValue.
我使用的是Newtonsoft.Json-Package版本7.0.1和Microsoft.Data.OData版本5.6.4.
怎样才能解决这个问题?
我发现(使用.NET Reflector)DbGeography-Type可以通过默认构造函数实例化(没有参数)但是这个默认构造函数没有设置一些重要的私有成员(如_spatialProvider).
这导致NullReferenceException异常时WellKnownValue -Getter反序列化过程中调用.所以我所做的就是许多人以前必须做的事情(我希望不必这样做) - 我创建了一个自定义的JsonConverter.
一个特点是,我必须在BreezeWebApiConfig中注册它而不是普通的WebApiConfig:
public class MyBreezeConfig : Breeze.ContextProvider.BreezeConfig
{
protected override JsonSerializerSettings CreateJsonSerializerSettings()
{
JsonSerializerSettings result = base.CreateJsonSerializerSettings();
result.Converters.Add(new WebDbGeographyJsonConverter());
return result;
}
}
Run Code Online (Sandbox Code Playgroud)
和转换器:
public class WebDbGeographyJsonConverter : JsonConverter {
public override bool CanConvert(Type objectType) {
return typeof(DbGeography).IsAssignableFrom(objectType);
}
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) {
var jObj = JObject.Load(reader);
if (jObj != null) {
var geography = jObj["Geography"];
if (geography != null) {
var wktText = geography["WellKnownText"].Value<string>();
if (!string.IsNullOrEmpty(wktText)) {
var coordSysId = geography["CoordinateSystemId"].Value<int?>() ?? DbGeography.DefaultCoordinateSystemId;
return DbGeography.FromText(wktText, coordSysId);
}
}
}
return null;
}
public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) {
throw new NotImplementedException();
}
public override bool CanWrite {
get {
// use default implementation of Serialization
return false;
}
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1613 次 |
| 最近记录: |