我在尝试通过Web API返回由Entity Framework 6生成的递归序列化对象时遇到了问题。这是我的问题的一个小例子:
[Serializable]
[DataContract]
public partial class Thing
{
public Thing()
{
this.OtherThings = new HashSet<OtherThings>();
}
[DataMember]
public int ThingId { get; set; }
[DataMember]
public string ThingName { get; set; }
//Not included in serialization
public virtual ICollection<OtherThing> OtherThings { get; set; }
}
[Serializable]
[DataContract]
public partial class OtherThing
{
public OtherThing()
{
this.Things = new HashSet<Things>();
}
//I want these
[DataMember]
public int OtherThingId { get; set; }
[DataMember]
public string OtherThingName { get; set; }
//Do NOT want this from GetAllThings() to avoid circular references
public virtual ICollection<Things> Things { get; set; }
}
装饰器是从Context.tt文件生成的,在我的真实对象中有一些 lot 更多的属性,手动编辑每一个都是不可能的 - 更不用说文件是自动的 - 生成。
我使用这个简单的方法从我的数据库中检索Things
的集合:
public static class Repo {
internal static IQueryable<Thing> GetAllThings()
{
//Context is an initialized database context
return Context.Things;
}
}
返回包含Things
的整个OtherThings
集合,其中每个集合包含更多Things
。当我尝试将其序列化为Web API响应时,问题就变得很明显了:
public class API {
//This response is serialized to JSON
public List<Thing> GetAllThings()
{
var things = Repo.GetAllThings();
//Do something here to exclude
return things.ToList();
}
}
当然,序列化程序会失败(或溢出),因为存在循环引用。通常情况下,我会将[DataIgnore]
添加到有问题的属性中,完全忘记DataContracts,但如果我请求Things
的集合,我只想要每个连接OtherThing
,反之亦然。< / p>
可以这样做吗?
答案 0 :(得分:2)
假设Context.Things的类型为DbSet,您可以使用
return Context.Things.Select(s => s).Include(s => s.OtherThings);