Reputation: 573
I am working in project with backbone.js and the problem I am facing is that I have a model that doesn't need to be in sync with the server, this model its only intended to fetch user data to initialize the rest of the views, it is kind of a wrapper view for the app with a model attached to it.
This model fetch its data from multiple urls and my actual problem is that the view is rendering before all the data is assigned to the model in some cases and in other cases is rendered when all the data is already assigned to the model.
i am using $.when() to fetch the model and calling .done() to render the view but i think i don't understand the concept of the defer object. Would like to know what kind of suggestion you guys have in order to proceed with this problem. I leave you an example on how is my code.
Model
var userModel = Backbone.Model.extend({
url: "/api/vacationtypes.json",
defaults: {
userName: 'anonymous',
availableDays: 0,
vacationType: []
},
initialize: function() {
var that = this;
_.bindAll(this,'parseAvailableDays');
},
parse: function(data){
return {vacationType: data.data}
},
getAvailableDays: function() {
$.ajax({
url: "/api/staffAvailableDays/get/" + Zvacations.session.email + ".json",
success: this.parseAvailableDays
});
},
parseAvailableDays: function(response) {
this.set('availableDays', response.data[0].availableDays);
}
});
View
var Home = Backbone.View.extend({
tagName: "section",
className: "home",
el: "#request-form"
events: {
// events for the view
},
initialize: function(){
var that = this;
this.setPageTitle('Home');
this.model.on('change:availableDays', this.render, this);
// once all fetches for model are done render the view (sometime execute before the succes of getAvailableDays)
$.when( this.model.fetch(), this.model.getAvailableDays() ).done(function(){
that.render();
});
},
render: function(){
var template = _.template(homeViewTemplate, this.model.toJSON());
this.$el.html(template);
// get holydays from db
this.getHolidays();
//assign total steps after render
this.totalSteps = $(homeViewTemplate).find('fieldset').length
// initialize jQuery UI datepicker
this.dateSelectorView();
return this;
},
// here goes rest of the view methods
});
Hope you guys can help me figuring out which one is the best way to wait untill all fetch is done to render.
Upvotes: 0
Views: 87
Reputation: 1741
You need to return the jqXHR
(ajax return value) from getAvailableDays
so that it can be used with $.when
getAvailableDays: function() {
return $.ajax({
url: "/api/staffAvailableDays/get/" + Zvacations.session.email + ".json",
success: this.parseAvailableDays
});
},
Your existing code passes the return value of getAvailableDays
and fetch
to $.when
. When you don't return anything from getAvailableDays
your code is equivalent to the following:
$.when(this.model.fetch(), undefined).done(function() {
that.render();
});
Which ignores the ajax call inside of getAvailableDays
.
From the jQuery documentation:
If a single argument is passed to jQuery.when() and it is not a Deferred or a Promise, it will be treated as a resolved Deferred and any doneCallbacks attached will be executed immediately
You will find in the Backbone internals that fetch
returns the jqXHR object from the ajax call, similar to what you should be doing with getAvailableDays
Upvotes: 2