Gregg
Gregg

Reputation: 35864

How to get Ember to Lazy (async) Load hasMany

Possibly I'm misunderstanding how Ember wants to lazy load hasMany sides of relationships but I'll specify what I want and someone can tell me if it is possible and how to configure things.

I'm using the RESTAdapter and I have a parent object with a 1-to-many relationship with several other objects. When I view the parent, I have links for the children objects that I want to show as child outlets.

Examples might be:

// brand.js
export default Model.extend({
  name: attr('string'),
  description: attr('string'),
  dateCreated: attr('date'),
  lastUpdated: attr('date'),
  regions: hasMany('region', {async: true})
});

// region.js
export default Model.extend({
  name: attr('string'),
  dateCreated: attr('date'),
  lastUpdated: attr('date'),
  brand: belongsTo()
});

When I access /api/brands/1 I'm returning the following JSON:

{
  "brand": {
    "id": 1,
    "dateCreated": 1466456255539,
    "lastUpdated": 1466456255936,
    "name": "Some Brand",
    "description": "Voluptates odio nemo corrupti",
  }
}

I have my route defined like so:

this.route('brand', {path: '/brands/:brand_id'}, function() {
  this.route('regions');
});

So, in the brand detail screen, I have an {{outlet}} and when I click on the link for regions, I need to fetch the regions for that brand, and the URL would be /api/brands/1/regions.

Everything works if I return all the data in one big result, and my regions router looks like this:

export default Ember.Route.extend({
  model() {
    return this.modelFor('brand').get('regions');
  }
});

But I don't know what to do so that regions gets lazily fetched correctly from my API. Or if it is even possible. I read up on side loading and currently, my API won't return ID's only for children.

Upvotes: 1

Views: 715

Answers (1)

Timm
Timm

Reputation: 1015

With your example, ember.js does not know, what regions to load. Your JSON has to be either (non-embedded):

{
  "brand": {
    "id": 1,
    "dateCreated": 1466456255539,
    "lastUpdated": 1466456255936,
    "name": "Some Brand",
    "description": "Voluptates odio nemo corrupti",
    "regions": ["5", "9"]
  }
}

Which then loads regions with the id 5 and 9. Or you could embed them directly:

{
  "brand": {
    "id": 1,
    "dateCreated": 1466456255539,
    "lastUpdated": 1466456255936,
    "name": "Some Brand",
    "description": "Voluptates odio nemo corrupti",
    "regions": [{
      "id": "5",
      "name": "Hanover",
      "dateCreated": "2016-09-25 18:39:18",
      "lastUpdated": "2016-09-25 18:39:18",
    },{
      "id": "9",
      "name": "Cologne",
      "dateCreated": "2016-01-19 11:59:18",
      "lastUpdated": "2016-02-22 12:09:58",
    }]
  }
}

See here for the latter.

Upvotes: 1

Related Questions