如何序列化EF POCO自动生成的对象以避免循环引用?

时间:2011-12-14 08:07:33

标签: .net entity-framework serialization circular-reference javascriptserializer

我正在使用ASP.NET MVC 3的库(Telerik)。

我的所有功能都存在问题,需要通过AJAX返回一些数据:

我正在使用EF4来连接我的数据库,而且我已经(并且需要)两种方式的导航属性(想象一下,有一些帖子和一个帖子的用户都有用户)。

问题是该库正在使用JavaScriptSerializer,它使用JSON对数据进行编码。

我得到的错误

  

序列化“System.Data.Entity.DynamicProxies.Employee_34048F4F6A98297F826C798A27640C7383E95E8EA8282EC8A5F738FA0C77CBC3”类型的对象时检测到循环引用。“

异常,这是正确的,因为父级引用了它的子级,并且子级引用了它的父级。

我已经找到了一些解决方法,但没有什么能完全满足我的要求:

  • 使用数据服务器绑定:不能,函数必须在ajax中工作(它是网格的寻呼机,当页面滚动到最后时加载下一个元素)
  • 使用匿名对象:不灵活,因为如果我在数据库中另外添加了一个字段,我必须将它添加到我的所有匿名对象中,此外,如果我需要一个我想要的子集合,为这个子列表的所有元素创建对象也很无聊。
  • 使用ViewModel:几乎同样的问题,如果我还有一个字段,我必须在所有viewModel上添加这些字段,并且我要为所有60个视图创建一个视图模型,其字段与我的模型完全相同, ...
  • 使用NonSerializedAttribute:我不知道如何放入生成我的POCO对象的T4模板,我不确定它是否有效:有时主要对象是子对象,有时它是父对象,空关系必须是另一个。

我和WCF几乎有同样的问题,我创建了一个知道处理循环引用的序列化,我们可以在这里做同样的事情吗?或者有办法管理这个吗?

如果没有,我认为最好的方法是使用“ViewModel”,但有没有办法加速这些创作?像一个泛型对象,它接受构造函数EF对象并删除循环引用?其他什么?

非常感谢

1 个答案:

答案 0 :(得分:5)

实际上,您需要的不是[NonSerialized],而是[ScriptIgnore]。不过,我会从两个角度中的一个角度来看待这个:

  1. 使用RegisterConverters并编写一个自定义转换器,指定父项之外的所有属性(这可能可能也是自动化的,也许正在使用在[SkipSerialize("Parent")]中添加了一个定制的类级别属性,如partial class - 这可能使事情过于复杂。“

  2. 简单地说:不要序列化EF POCO,而是使用DTO - 它声音就像你在ViewModel答案中所说的那样。就个人而言,我没有问题,有一个类的“实体”(EF / POCO)版本和一个非常相似但不同的DTO版本 - 他们的意图是不同的,在我看来它不会违反DRY。