I'm not the first person to ask this... the answers basically say "Well you're doing REST wrong." Fair enough, but development is filled with tradeoffs and I often find myself not in a position to rewrite the API.
Moving on to the problem at hand, what's the most elegant way to add a method for some resource to a model?
var Issue = can.Model.extend({
findAll: 'GET Issues',
findOne: 'GET Issues/{id}',
findRelated: can.Model.makeFindAll(function(params) {
return can.ajax({
type: 'GET',
url: 'Issues/'+params.id+'/'
});
})
},{});
If I understand the question correctly, you want to get an Issue.List
from findRelated.
var Issue = can.Model.extend({
findAll: 'GET Issues',
findOne: 'GET Issues/{id}',
findRelated: function(params) {
var deferred = new can.Deferred();
can.ajax({
type: 'GET',
url: 'Issue/'+params.id+'/Related'
}).then(function(response) {
// success
deferred.resolve(Issue.models(response || []));
}, function(xhr, textStatus, err) {
// failure
deferred.reject(err);
});
return deferred;
}
},{});
Another option, similar to the accepted answer, is to return can.ajax
instead of creating a new deferred. It's a bit less verbose.
Also, as of v2.1, passing the response directly to .models
is deprecated and converting it first with .parseModels
is preferred.
var Issue = can.Model.extend({ findAll: 'GET Issues', findOne: 'GET Issues/{id}', findRelated: function(issue) { return can.ajax({ type: 'GET', url: 'Issue/'+issue.id+'/Related' }).then(function(response) { return this.models(this.parseModels(response)); }.bind(this)); } },{ findRelated: function() { return this.constructor.findRelated(this); } }); // usage examples // 1. Issue.findRelated({id: 1}); // 2. new Issue({id: 1}).findRelated();
©2020 All rights reserved.