恩伯(Ember):观察者这样做时,为什么计算不触发?

时间:2018-11-13 12:43:44

标签: ember.js

我很难解决这个问题-我正在处理继承的遗留代码,尽管这看起来应该很简单,但仅此而已。

在此app / pods / application / route.js中,服务器抓取了一个“ welcome pack”对象,其中一部分是在welcome-pack服务上调用了setWp()方法,该方法设置了相同服务上的“ wp”值。 (是的,我知道您可能可以使用“ this.wp.set('wp',welcomePack)”直接在服务上设置值,但是正如我所说的:继承的遗留代码。)要点是,这应该触发更改价值。我的wp.wp观察者正在触发,但不是基于wp.wp的计算。有什么线索吗?

// app/pods/application/route.js
wp: inject('welcome-pack'),
model(){
  return this.store.findAll('welcome-pack').then((welcomePack) => {
  this.wp.setWp(welcomePack);
})
}



// app/pods/welcome-pack/service.js
import Service from '@ember/service';
export default Service.extend({
  wp: null,
  setWp(wp){ // <-- called when the model loads from the ajax request
    this.set('wp', wp)
  }
})

// app/pods/application/controller.js
import Controller from "@ember/controller";
import { inject } from "@ember/service";
import { computed, observer } from "@ember/object";

export default Controller.extend({
  wp: inject("welcome-pack"),
  init(){
    console.log('this.wp', this.wp) // <- logs service as class
    console.log('this.wp.wp', this.wp.wp) // <-logs null
    setTimeout(() => {
      // set for after the ajax call has been made and setWp() has been called. 
      console.log('this.wp', this.wp) //<- logs service as class
      console.log('this.wp.wp', this.wp.wp) //<- logs object as class
    }, 2000)
  },
  obsWPChanges: observer('wp', function(){
    console.log('wp changed'); // <-- never executes (don't expect it to)
  }),
  obsWPWPChanges: observer('wp.wp', function(){
    console.log('wp.wp changed') //<-- executes (as expected) when setWP() is called
  }),
  primaryColor: computed("wp.wp", function() {
    console.log("this.wp.primaryColor", this.wp.primaryColor) // <-- does not execute
    return this.wp.wp.primaryColor || "#37b3c0";
  }),
  secondaryColor: computed("wp.wp", function() {
    return this.wp.wp.secondaryColor || "#38a0d0"; // <-- does not execute
  })
});

1 个答案:

答案 0 :(得分:4)

在Ember中,对计算的属性进行延迟计算。因此,在引用它们之前,它们永远不会执行。

另一方面,观察者总是在依赖键更改时触发。假设此时尚未引用primaryColorsecondaryColor,则上面显示的行为可以完全解释。取自docs

  

计算的属性仅在消耗后才重新计算其值。   通过两种方式消耗属性:

     

通过访问,例如ironMan.fullName

     

通过引用   例如,当前正在渲染的车把模板   {{ironMan.fullName}}在这两种情况下,   即使该属性的依赖项之一,该属性也不会运行   改变了。

我记得您来自Ember subreddit的漫长咆哮,希望您过得更好。鉴于您已经积累了一些经验,因此我强烈建议您为文档提供彻底的了解。