Suponiendo que tenemos una API tipo RESTful que administra la información de unos patrocinadores y que esa información debe ser listada y agregada a través de la web:
Vista agregar patrocinador:
Vista listar patrocinadores:
Para esto, tenemos el siguiente modelo (no es PHP es JS xD):
Código PHP:
var ejemplo = ejemplo || {};
ejemplo.Patrocinador = Backbone.Model.extend({
url: '/api/patrocinadores',
defaults: {
nombrepatrocinador : '',
logopatrocinador: '',
bannerpatrocinador: ''
}
});
Código PHP:
ejemplo.Patrocinadores = Backbone.Collection.extend({
url: '/api/patrocinadores',
model: ejemplo.Patrocinador
});
Código PHP:
ejemplo.AppRouter = Backbone.Router.extend({
routes:{
"patrocinadores/add" : "addPatrocinador",
"patrocinadores" : "listarPatrocinadores"
},
addPatrocinador: function(){
this.addpatrocinadorview = new ejemplo.AddPatrocinadorView();
$('#content').html(this.addpatrocinadorview.render().el);
},
listarPatrocinadores: function(){
this.listarpatrocinadorview = new ejemplo.ListarPatrocinadoresView();
$('#content').html(this.listarpatrocinadorview.render().el);
}
});
La vista de agregar patrocinador captura los datos del formulario y por medio de model.save() se guardan en el servidor. Al guardar, la aplicación se dirige a la vista de listar patrocinadores.
Código PHP:
ejemplo.AddPatrocinadorView = Backbone.View.extend({
template: _.template($('#tpl_addpatrocinador').html()),
events: {
'click #addpatrocinador': 'addPatrocinador'
},
initialize: function(){
this.model = new ejemplo.Patrocinador();
},
render: function(){
this.$el.html(this.template());
Backbone.Validation.bind(this);
return this;
},
getPatrocinadorData: function(){
//devuelve la data del formulario en json
},
addPatrocinador: function(e){
e.preventDefault();
this.model.save(this.getPatrocinadorData(),{
success: function(){
window.location = '#patrocinadores';
},
error: function(){
//muestra un popup con los errores de validaciones
}
});
}
});
Código PHP:
ejemplo.ListarPatrocinadoresView = Backbone.View.extend({
template: _.template($('#tpl_listarpatrocinadores').html()),
events: {
},
initialize: function(){
this.collection = new ejemplo.Patrocinadores();
_.bindAll(this, 'addOne', 'addAll', 'render');
this.collection.on('reset', this.render);
this.collection.fetch();
},
render: function(){
this.$el.empty();
this.$el.html(this.template());
this.addAll();
return this;
},
addOne: function(patrocinador){
var patrocinadorview = new ejemplo.PatrocinadorItemView({
model: patrocinador
});
//para acceder a la tabla tuve que navegar a través del elemento :/
$(this.$el.children().get(2)).append(patrocinadorview.render().el);
},
addAll: function(){
this.collection.each(this.addOne);
}
});
Esto se debe (hipótesis) a que tanto model.save() como collection.fetch() ejecutan peticiones asíncronas lo cual sugiere que el fetch se ejecuta antes de que haya terminado de guardar el nuevo patrocinador y por eso no aparece.
Hay un problema de comunicación entre las dos vistas ya que cada quien hace lo suyo por separado pero no interactúan entre sí.
En este orden de ideas, que debería hacer para que la aplicación maneje las vistas de una forma mas coherente con la idea de single page application?