Ember.Data Promise-Aware Properties (Cheaters Edition)
Ember.Data Promise-Aware Properties (Cheaters Edition)
I have models like this:
Models
App.Child = DS.Model.extend({
parent: DS.belongsTo('parent', {async: true})
});
App.Parent = DS.Model.extend({
children: DS.hasMany('child', {async: true})
});
App.Nursery = DS.Model.extend({
children: DS.hasMany('child')
});
Then a controller like this:
###Controller
App.NurseryController = Ember.Controller.extend({
uniqueParents = function() {
return this.get('children').mapBy('parent').uniq();
}.property('children'),
somethingLikeReliesOnUniqueParents = function() {
....
}.property('uniqueParents')
}
The Problem
The property somethingLikeReliesOnUniqueParents was never getting unique values. I found two problems here:
- uniq() couldn’t figure out uniqueness - much like the problems with filter.
- The parents promises, once they resolved, weren’t updating properties that relied on them.
The first problem I solved the same way I solved in the filter case - filter uniqueness by id, not by object.
The second problem I found a somewhat hacky workaround. All promises in the system have a isFulfilled
flag. Setting the properties to observe that field allowed the properties to update.
The Solution
My code ended up looking like this:
###Controller
App.NurseryController = Ember.Controller.extend({
uniqueParents = function() {
return this.get('children').mapBy('parent').uniq(function(parent) { return parent.get('id'); });
}.property('children'),
somethingLikeReliesOnUniqueParents = function() {
....
}.property('uniqueParents.@each.isFulfilled')
}
This solved the issue and still allowed the async behavior I was looking for.