在任何具有导航属性的Breeze实体上调用ko.toJS(entity)
或者是大对象图的一部分时,IE7-8会抱怨长时间运行的脚本错误,甚至chrome也会陷入困境超过1秒。
答案 0 :(得分:2)
我以前曾经遇到过这样的困扰,并且看到了各种论坛或Github问题,这成为了开发者的问题。我想分享一些知识,希望它能帮助别人。
问题
Breeze.js为您的客户端库或框架提供了一个对象图。在实体上调用JSON.stringify()将导致可怕的堆栈溢出,因为某些属性相互引用。示例 -
Person -> Company -> Persons
由于某人的公司导航属性也具有人员的导航属性,因此他们会继续相互找到。
ko.toJS()通过检测重复项并在此时停止序列化来解决这个问题。
为什么会慢?
序列化需要更长时间,具体取决于对象图中的实体数量。别相信我?加载你的应用程序并调用ko.toJS()然后在同一对象图中加载更多实体。这需要更长的时间,保证。问题是,即使你在一个人身上调用ko.toJS(),Knockout也没有找到重复项,直到它序列化原始人公司中的每个人。这不是Knockout和Breeze的问题 - 它是由一切都相互关联的原因引起的。
我该怎么做才能解决问题?
如果可以,使用投影查询是最佳解决方案。问题通常是我们需要更深层次的嵌套实体,而不仅仅是当前实体。如果您的实体具有包含许多相关实体的导航属性,则没有简单的方法来执行投影查询,因此我们需要以两种方式之一进一步 -
编写自定义序列化程序
Vote for IdeaBlade (the company behind Breeze.js) to support unwrapping more efficiently
我的观点 - 在实体经理上公开一种方法来解开'接受以下参数 -
entityManager.unwrap(entity || [entities], [addtlTypesToUnwrap])
其中addtlTypesToUnwrap是一个字符串数组或逗号分隔的字符串,用于定义要解包的相关实体类型。
使用示例 -
var thisEntity = manager.fetchEntityByKey('Person', 1, true);
var relatedProps = ['Company', 'Address']
entityManager.unwrap(thisEntity, relatedProps);
哪会打开人员,他们的地址,公司和公司地址(如果存在)