我在大型Ember-CLI应用程序中遇到非常严重的内存泄漏。我可以轻松地复制应用程序,使其减慢然后完全崩溃。
在花了很多时间研究性能瓶颈等(这导致了改进)后,我确定我有内存泄漏。
在通常的事情精神中,我试图尽可能简单地制作一段示例代码。我的结论是:当条件包含时,Ember Components会泄漏内存。
然而,我无法看到其他人抱怨,所以想知道我是否忽视了一些明显的东西?
我的测试应用程序产生完全相同的输出,但有两种不同的方式。在这两种情况下,应用程序初始化,它创建了一个包含1000个简单对象的数据数组,其中一个属性是 vis ,最初设置为false。在初始延迟之后,这1000个对象将 vis 属性以50ms的间隔更改为true。
export default Ember.Controller.extend({
data : [],
scrollTimer : null,
init : function()
{
var data = this.get("data");
for (var x=0;x<500;x++)
{
var obj = {id:x,label:"o".repeat(10) + "_" + x,vis:false};
data.push(obj);
obj = null;
}
Ember.run.later(this,this.make_visible,0,5000);
},
make_visible : function(idx)
{
var data = this.get("data");
Ember.set(data[idx++],"vis",true);
if (idx < data.length)
{
Ember.run.later(this,this.make_visible,idx,10);
}
},
});
在TEST 1中,我的应用程序模板如下所示:
{{#each data as |item index|}}
{{data-item item=item}}
{{/each}}
和data-item看起来像这样:
模板:
{{component itemComponent item=item}}
JS:
export default Ember.Component.extend({
itemComponent : function()
{
var item = this.get("item");
return item.vis ? "item-visible" : "item-hidden";
}.property("item.vis"),
});
item-visible和item-hidden只是HBS文件,其中包含静态文本 隐藏 和 可见 。< / p>
因此,当它运行时,我得到1000行说隐藏,慢慢变为可见。在这种情况下,数据项交换中的逻辑哪个组件正在输出文本,最初是项目隐藏的,然后是项目可见的。
Timeline snapshot from Chrome dev tools
在这里,您可以看到消耗的内存不断增加。
这里有一个小问题:http://ember-twiddle.com/c9c3e6c5a9908bd2c438
在TEST 2中,我省略了item-visible / item-hidden组件,数据项现在使用内联条件逻辑直接输出隐藏/可见文本。
{{#if item.vis}}
<div>visible</div>
{{else}}
<div>hidden</div>
{{/if}}
Timeline snapshot from Chrome dev tools
这段时间记忆正在我不时发布。
这里有一个小问题:http://ember-twiddle.com/01b1abe7badea3ce3a16
所以我的问题是,为什么有条件地包含这样的组件会导致内存泄漏?我可以做些什么来避免它?
在我的实际应用程序中,我有这样的逻辑:
{{#if XXXXX}}
{{component-x}}
{{else}}
{{component-y}}
{{/if}}
这有相同的内存泄漏问题。
我使用Ember 1.3.8(使用最新的Ember-CLI),Twiddle似乎正在使用1.3.10
答案 0 :(得分:0)
事实证明存在内存泄漏。但是Ember团队已经解决了它,只是没有发布修复。 V2.2.0-beta.1包含修复,显然是v.1.3.10。因此,如果您遇到类似的问题,请抓住新的代码。
非常感谢Ember团队关注并提供解决方案。