Ember-data:加载一对一相关模型

时间:2015-02-14 04:54:20

标签: javascript ember.js ember-data

我觉得我错过了一些非常简单的事情。我以一对一的关系创建了两个相互关联的模型,每个模型都有belongsTo('theOtherOne')

我有一条加载特定条目的路线:

条目模式

export default DS.Model.extend({
  word: DS.attr('string'),
  entry: DS.attr('number'),
  definition: DS.belongsTo('definition', {async: true}),
});

定义模型

export default DS.Model.extend({
  body: DS.attr(),
  entry: DS.belongsTo('entry')
});

路线

model: function(params){
    return this.store.find('Entry', params.entry_id);
}

那么,如何将相关记录提供给我的模板?我非常确定这种关系配置正确,因为在Ember检查员中,我可以看到"属于"属于"属性已设置,当我单击它时,将进行相应的API调用并将其加载到存储中。但是,模板仍然没有(显然)可用。

提前致谢。

1 个答案:

答案 0 :(得分:2)

一个可能的解决方案是从async: true模型的Definition属性中删除Entry属性:

definition: DS.belongsTo('definition', {async: true}) // remove async: true

当async设置为true时,Ember将不会获取相关实体,直到您实际请求它们为止。设置为false时,Ember将与请求的实体同时获取相关实体。

在您当前的Entry模型中:

word: DS.attr('string'),
entry: DS.attr('number'),
definition: DS.belongsTo('definition', {async: true}),

Ember Data希望Entry仅返回条目。响应看起来像:



{
    entries: [
        {
            id: "e1",
            word: "foo",
            entry: 1,
            definition: "d1" // id for definition belonging to this entry
        },   
        {
            id: "e2",
            word: "bar",
            entry: 2,
            definition: "d2" // id for definition belonging to this entry
        },
    ],
}




要获得实际定义,您需要再次发出请求。

但是,如果您使关系同步,那么您将在单个请求中获得两个模型,其响应类似于:



{
    entries: [
        {
            id: "e1",
            word: "foo",
            entry: 1,
            definition: "d1" // id for definition belonging to this entry
        },   
        {
            id: "e2",
            word: "bar",
            entry: 2,
            definition: "d2" // id for definition belonging to this entry
        },
    ],
    definitions: [
        {
        	id: "d1",
            body: "abc",
            entry: "e1"      // id for entry belonging to this definition
        },
        {
        	id: "d2",
            body: "def",  
            entry: "e2"      // id for entry belonging to this definition
        }
    ]
    
}




编辑(根据您的评论)

由于这两个模型位于不同的API点,因此您需要使此关系异步并发出两个请求。由于Ember(和Ember Data)大量使用承诺,你可以通过链接承诺(" thenables")来实现这一目标:

model: function() {
    var store = this.store;
    return store.find('entry').then(function() {  // success function, we got the entries so now we request definitions
        store.find('definition');
    }
}

如果此代码成功执行,则条目和定义都将加载到商店中,您的路径模型将是条目数组。

注意上面的代码没有正确的错误处理,只是展示了如何实现这一点的本质。

Here's a good read on JavaScript promises

Ember's documentation on promises