Ember.js:将控制器计算的属性从多个模型移至新模型

时间:2018-07-11 14:08:03

标签: ember.js service model controller json-api

给出一个包含属性substances的模型measurements,该属性是一个包含对象的数组。每个对象都是具有诸如(int) value之类的某些属性的度量。 第二个模型elements是一个集合,其中包含所有特定元素(例如平均值)的全局数据。

我希望每个度量都将各自的元素包含为属性,因此可以将其传递给组件。例如:

{{#each contents as |m|}}
    {{some-graph m}}
    {{some-chart m}}
    {{some-data m}}
{{/each}}

我只做一次findAll(elements, {limit: 300, reload: false}),所以每种物质都不会向jsonapi服务器发送数十个请求。因此,route:substance的模型为:

model(params) {
    return {
        substance   : this.store.findRecord('substance', params.substance_id),
        elements    : this.store.findAll('element', {limit: 300, reload: false}})
    }
},

我尝试在model:substance中将两者合并,但是model:elements在那儿不可用(出于明显的原因)。所以我在controller:substance中这样做,就像这样:

export default Controller.extend({
    substance       : computed.alias('model.substance'),
    measurements    : computed.alias('substance.measurements'),
    elements        : computed.alias('model.elements'),
    contents        : computed('{elements,measurements}.[]', function() {
        if (!this.get('elements')) return null
        if (!this.get('measurements')) return null
        return this.get('measurements').map(m => {
            const element = this.get('elements').find(detail => detail.id == m.id)
            if (element) set(m, 'element', element)
            return m
        })
    }),

    // More calculations w/ `utils` here based on `contents`

这可行,但是存在一些问题。首先(1),contents:computed发射3次。

  1. 引用模板时是模板;
  2. 加载model.substance时;
  3. 加载model.elements时。

这不是一个大问题(开销),因为前两次会return null

第二(2),对模板中特定测量的所有引用(例如:{{contents.oxigen.value}})将按字面显示undefined,直到在第三次computed迭代中计算出所有内容为止。我希望它在加载之前不显示任何内容('')。

但是,我的最终目标是能够将substance(结合了measurementelement s)传递到类似购物车的service您可以编写自己的物质清单,然后进行计算并显示摘要,而与当前的路线/控制器无关。

鉴于我无法在{内执行此操作,因此如何将这些controller:substance计算移动到可传递给服务的自包含项(模型?)中?(3) {1}}?

我无法从model:substance引用此controller:substance,因为控制器是singeltons。

1 个答案:

答案 0 :(得分:1)

如果在显示任何数据之前需要先解决所有数据,则可以使用RSVP.hash,它仅在两个诺言都已解决时才能解决。

import { hash } from 'rsvp';
model(params) {
    return hash({
        substance   : this.store.findRecord('substance', params.substance_id),
        elements    : this.store.findAll('element', {limit: 300, reload: false}})
    });
}

现在,内容将只计算一次,因为控制器必须等到两个问题都解决后才能加载。 不能取消定义测量,因为数据已经加载。