2017-07-13 8 views
1

asp.net mvcコントローラでGeoPointsのリストを返そうとしています。Newtonsoft.Json.JsonWriterException with GeoJson

ポイント&フィーチャクラスは、Geojson.netライブラリの一部です。空List<Point>を含むMultiPointをシリアル化しようとすると、原因のためであると表示されたとき、あなたが例外を取得

Token PropertyName in state Property would result in an invalid JSON object. Path 'geometry'. 
+0

あなたは 'Feature'クラスのソースコードが含まれることができますか? – mjwills

+1

空の 'List 'を含む 'MultiPoint'を直列化しようとすると例外が発生しますか? 'MultiPoint'クラスと' Point'クラスのコードを投稿できますか? –

+0

@BrianRogersあなたは私のエラーを発見しました。 'points'を参照しているはずです。そのメモで、なぜ空のリストがそのエラーを投げるのでしょうか? – Zapnologica

答えて

1

理由:それはデータをシリアル化しようとしたとき

public async Task<ActionResult> GetGeoData() 
{  
    var query = _db.Data_Raw 
     .Where(x => x.Geography != null);  
    var dbResults = await query.Take(100).ToListAsync(); 

    var points = new List<Feature>(); 
    foreach (var item in dbResults) 
    { 
     var point = new Point(new Position(item.Geography.Longitude.Value, item.Geography.Latitude.Value, item.Altitude)); 
     var featureProperties = new Dictionary<string, object> { { "Speed", item.Speed }, { "Bearing", item.Course } }; 
     points.Add(new Feature(point, featureProperties)); 
    } 

    var model = new MultiPoint(new List<Point>()); 

    var serializedData = JsonConvert.SerializeObject(model, Formatting.Indented, 
     new JsonSerializerSettings 
     { 
      ContractResolver = new CamelCasePropertyNamesContractResolver(), 
      NullValueHandling = NullValueHandling.Ignore 
     }); 

    return Content(serializedData, "application/json"); 
} 

は、しかし、私は次の例外を取得しますMultiPointConverterのバグで、ポイントのリストをシリアライズするために使用されます。ここでWriteJsonメソッドのコードは次のとおりです。

public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) 
{ 
    var points = (List<Point>)value; 
    if (points.Any()) 
    { 
     var converter = new PointConverter(); 

     writer.WriteStartArray(); 

     foreach (var point in points) 
     { 
      converter.WriteJson(writer, point.Coordinates, serializer); 
     } 

     writer.WriteEndArray(); 
    } 
} 

ポイントのリストが空の場合、コンバータは何も書き込まれないことをあなたが見ることができます!この場合、空の配列を書き込む必要があります。問題は、シリアライザがコンバータのWriteJsonメソッドを呼び出すまでにプロパティ名coordinatesが既に出力に書き込まれていることです。コンバーターが値を書き込まない場合、次のプロパティー名が書き込まれるとすぐに無効なJSONが作成されます。シリアライザはこの状況を検出し、例外をスローします。

この不具合を回避するには、MultiPointに少なくとも1つのPoint(理想的にはそれが必要です)が含まれていることを確認してください。

修正コンバータのコードは次のようになります。

public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) 
{ 
    writer.WriteStartArray(); 

    var points = (List<Point>)value; 
    if (points.Any()) 
    { 
     var converter = new PointConverter(); 

     foreach (var point in points) 
     { 
      converter.WriteJson(writer, point.Coordinates, serializer); 
     } 
    } 

    writer.WriteEndArray(); 
}