Why my super simple ASP.NET Web API (mvc4)+Entity

2019-01-20 05:41发布

问题:

I spent days to know the problems of my work, but no luck.

  1. I created new MVC4 Web API project.
  2. Add EF5 with my database (Project>Add>ADO.NET Entity Data Model>Create from database which is in Azure SQL).
  3. Add two tables to edmx as below. And two *.tt files generate entities and model classes successfully.

I can see the breakpoint(result) gives query result normally. But json gives abnormal stream without error message. (ie, http://localhost:41813/api/sheet/157 returns "157" which cannot download. in general, "157.json" is downloaded)

I copied properties in results to my handmade POCO-style class and it works.

What is my problem? I cannot use generated model classes to send data through Json. I hardly find out problem because no error message and no debug step available after the result breakpoint.

回答1:

The reason the serialization fails are yours Navigation Properties - while the serializer is trying to walk the object graph they result in circular dependencies.

For your simple sample to work you have few ways around it.

  1. Remove Navigation Property Sheet from SheetDetail
  2. Wrap your objects in ViewModel classes with Navigation Property Sheet omitted
  3. Create a metadata class with JsonIgnoreAttribute and then attach it to your entity with partial class and MetadataTypeAttribute

Here you can find sample for third solution (sample makes some assumptions as I don't know your exact data types):

public class SheetDetailSerializationMetadata
{
    [JsonIgnore]
    public Sheet Sheet { get; set; }
}

[MetadataType(typeof(SheetDetailSerializationMetadata))]
public partial class SheetDetail
{ 
}


回答2:

As @danludwig comment, http://www.asp.net/web-api/overview/formats-and-model-binding/json-and-xml-serialization gives all answers about my problem.

Add below code in Global.asax solves the problem.

var json = GlobalConfiguration.Configuration.Formatters.JsonFormatter;
json.SerializerSettings.PreserveReferencesHandling = 
Newtonsoft.Json.PreserveReferencesHandling.All;