我正在尝试从实体框架4 edmx生成的MVC 4 web api ApiController对象返回,使用accept:json / application。
问题是json formatter还返回了导航属性,我不想返回(我只想返回Primitive Properties)。
所以我在导航属性中查看了生成的实体框架4代码,并且在我需要JsonIgnoreAttribute时只有XmlIgnoreAttribute和SoapIgnoreAttribute。
我无法更改生成的代码,因为它会在下一次更改edmx时被覆盖, 那么如何配置将使用JsonIgnoreAttribute生成模型生成?
谢谢
答案 0 :(得分:3)
虽然我不知道这是一个错误还是不受支持的功能,但我建议您定义视图模型并让API控制器操作返回视图模型而不是EF自动生成的域模型。视图模型显然只包含您要公开的属性。单个视图模型可以表示多个域模型的聚合。所以不要依赖任何XmlIgnore,SoapIgnore,JsonIgnore,...属性。依靠你的视图模型。
答案 1 :(得分:2)
好的,我发现了该怎么做。 我们需要以这种方式使用自定义DefaultContractResolver:
public class ExcludeEntityKeyContractResolver : DefaultContractResolver
{
private static Type mCollectionType = typeof(System.Data.Objects.DataClasses.RelatedEnd);
protected override IList<JsonProperty> CreateProperties(Type type, MemberSerialization memberSerialization)
{
var members = GetSerializableMembers(type);
IList<JsonProperty> properties = base.CreateProperties(type, memberSerialization);
IList<JsonProperty> serializeProperties = new List<JsonProperty>();
for (int i = 0; i < properties.Count; i++)
{
var memberInfo = members.Find(p => p.Name == properties[i].PropertyName);
if (!memberInfo.GetCustomAttributes(false).Any(a => a is SoapIgnoreAttribute) && properties[i].PropertyType != typeof(System.Data.EntityKey))
{
serializeProperties.Add(properties[i]);
}
}
return serializeProperties;
}
}
并在Global.asax中:
JsonSerializerSettings serializerSettings = new JsonSerializerSettings();
serializerSettings.ContractResolver = new ExcludeEntityKeyContractResolver();
var jsonMediaTypeFormatter = new JsonMediaTypeFormatter();
jsonMediaTypeFormatter.SerializerSettings = serializerSettings;
GlobalConfiguration.Configuration.Formatters.Insert(0, jsonMediaTypeFormatter);
并且不用担心性能,因为在整个应用程序持续时间内,每个类型只会调用一次CreateProperties:)