cakephp backbone save not working - javascript

I have a site developed in cakephp where I'm using a simple app in backbone.
Now I would like to save data from backbone but doesn't work, return always inside callback error, and it doens't take the right value to save inside table.
This is my simple app:
TaskModel = Backbone.Model.extend({
url: function(){
return "/step_task/ajax_save";
}
});
TaskCollection = Backbone.Collection.extend({
model: TaskModel,
initData: function(data){
return data;
}
});
var TaskView = Backbone.View.extend({
template: _.template($("#task-template").html()),
initialize: function(){
this.task = new TaskCollection(<?php echo json_encode($step['StepTask']); ?>);
this.render();
},
render: function(){
taskModel = new TaskModel({
'id': '1',
'user_id': '1'
});
//--------------------------- here I would like to save inside my table ----------------
taskModel.save(null, {
success: function(model, response) {
console.log('success');
console.log(model);
console.log(response);
},
error: function(model, response) {
console.log('error');
console.log(model);
console.log(response);
},
wait: true // Add this
});
$(this.el).html(this.template({tasks: this.task.models}));
}
});
and this is my funciton inside StepTaskController.php
public function ajax_save(){
$this->autoRender = false;
$this->StepTask->save($this->request->data);
}
How can I solve it?

Try to change the url in your model to urlRoot :
TaskModel = Backbone.Model.extend({
urlRoot: '/step_task/ajax_save'
});

Related

Can't Fetch Data from REST call in BackBone after switching model

I use backbone to fetch restful api.
Switch collection and fetch data is not work.
I have a view with two collections(as below), while View detect the change change trigger switchModel.
I use console.log display. that.collection.fetch don't run successfully or error. My server show 500 Internet Server error. I don't know how to fix it... can anyone help me thx.
view
var view = Backbone.View.extend({
initialize: function() {
this.A_info = ACollection;
this.B_info = BCollection;
*//I do not bind any collection in thi function.*
},
events: {
"change #some_name": "switchModel"
},
switchModel: function(ev) {
var that = this;
var data = {};
if(that.VENDOR_TYPE==that.A_TYPE){
that.collection = that.A_info;
}
else{
that.collection = that.B_info;
}
that.collection.reset();
that.collection.fetch({
type: 'GET',
dataType: "json",
data: data,
success: function() {
var _parent = that;
_parent.filter();
//console.log("successfully!!");
}
error{
//console.log("error!!");
}
return view;
});
ACollection
var collection = Backbone.Collection.extend({
url: function() {
return "/api/a_info"
},
},
model: AInfoModel
});
return new collection();
});
BCollection
var collection = Backbone.Collection.extend({
url: function() {
return "/api/b_info"
},
},
model: BInfoModel
});
return new collection();
});

Backbone Collection from URL json

[{"uniqueId":61,"content":"test","createTextDate":"time"}]
this is /data/commentList.json
var Comment = Backbone.Model.extend({
defaults: {
uniqueId: null,
createTextDate: null,
content: null
}
});
Model for Backbone Collection
var List = Backbone.Collection.extend({
model: Comment,
url: function() {
return '/data/commentList.json';
},
parse: function(response) {
return response.results;
},
sync: function(method, model, options) {
var that = this;
var params = _.extend({
type: 'GET',
dataType: 'jsonp',
url: that.url(),
processData: false
}, options);
return $.ajax(params);
}
});
Backbone Collection
var ListView = Backbone.View.extend({
el: $('#test'),
initialize: function() {
_.bindAll(this, 'render');
this.collection = new List();
this.render();
},
render: function() {
var self = this;
this.collection.fetch({
success: function() {
console.log("SUCESS");
console.log(that.collection.toJSON());
},
error: function() {
console.log('Failed to fetch!');
}
});
}
});
Console log
Failed to fetch!
How to make Backbone Collection using jSON url?
parse: function(response) {
return response.results;
},
Above code assumes your server returns
{"results": [comment1, comment2]}
You rarely need to override sync method.

backbone.js model not updating on fetch after success

I'm trying to use backbone.js in a project and having trouble when trying to update a model with the fetch method.
my model is as follows (singleton object as I only ever want one instance)
define([
'underscore',
'backbone'
], function (_, Backbone) {
var UserModel = Backbone.Model.extend({
defaults: {
name: "",
loggedIn: false,
user: "null",
pass: "null"
},
prepare: function (options) {
this.loggedIn = false;
this.user = options.user;
this.pass = options.pass;
},
url: function () {
return _SERVER_ + "/WebServices/TTMobileAppService.svc/getUserLogin?user=" + this.user+"&pass="+this.pass;
},
parse: function (res) {
// because of jsonp
return res.data;
}
});
return new UserModel();
});
my view is as below, when a successful fetch occurs the method updateLogin is called where the model and response are logged.
define([
'jquery',
'underscore',
'backbone',
'models/user/UserModel',
'text!templates/login/loginTemplate.html'
], function ($, _, Backbone, UserModel, loginTemplate){//}, footerTemplate) {
var LoginView = Backbone.View.extend({
el: $("#loginArea"),
events: {
'mouseup #loginButton': 'expandLogin',
'click #login': 'loginUser'
},
initialize: function () {
this.options = { user: '', pass: "" };
var that = this;
this.model = UserModel;
this.model.on('change', this.render, this);
this.render();
},
render: function () {
var data = {
user: this.model.toJSON(),
_: _
};
var compiledTemplate = _.template(loginTemplate, data);
this.$el.html(compiledTemplate);
},
updateLogin: function(model, response, options) {
console.log(model);
console.log(response);
console.log(options);
},
expandLogin: function () {
var button = this.$el.children("div").first().children('#loginButton')[0];
var box = this.$el.children("div").first().children('#loginBox')[0];
$(box).fadeToggle(400);
$(button).toggleClass('active');
},
loginUser: function () {
var that = this;
var username = $('#username_field', this.el).val();
var password = $('#password_field', this.el).val();
this.options = { user: username, pass: password };
this.model.prepare(this.options);
this.model.fetch({
type: "GET",
error: function (collection, response, options) {
alert('error');
alert(response.responseText);
},
success: that.updateLogin,
complete: function () {
alert('complete');
},
dataType: 'jsonp'
});
}
});
return LoginView;
});
currently my model isn't updated
but the response object is correct and successful
Any help would be greatly appreciated
parse: function (res) {
// because of jsonp
return res.data;
}
needed to be removed, it was copied from an example although the query in the example had an object inside an object unlike my configuration. resolved now =]

Fetching Youtube videos with Backbone

I need to find a way to fetch a Youtube JSON url and print the titles and descriptions. The code I have here succeeds when I try to fetch, but the array it receives is empty when I try to see it in console.
Do you know why this may happen?
You can find the code here:
http://jsfiddle.net/BHrmC/73/
var Item = Backbone.Model.extend();
var List = Backbone.Collection.extend({
model: Item,
url: "https://gdata.youtube.com/feeds/api/playlists/67DEB98D8D9CF0F7?v=2&alt=json-in-script&max-results=6",
parse: function(response) {
return response.results;
},
sync: function(method, model, options) {
var that = this;
var params = _.extend({
type: 'GET',
dataType: 'jsonp',
url: that.url,
processData: false
}, options);
return $.ajax(params);
}
});
var ListView = Backbone.View.extend({
el: $('#test'),
events: {
'click button#add': 'getPost'
},
initialize: function() {
_.bindAll(this, 'render', 'getPost');
this.collection = new List();
this.render();
},
render: function() {
var self = this;
$(this.el).append("<button id='add'>get</button>");
},
getPost: function() {
var that = this;
this.collection.fetch({
success: function(response) {
console.log(that.collection.toJSON());
console.log("working");
},
error: function() {
console.log('Failed to fetch!');
}
});
}
});
// **listView instance**: Instantiate main app view.
var listView = new ListView();
Make up your mind on the data representation you want to use. The code shown here uses an XML to JSON conversion (alt=json-in-script) while the URL in you Fiddle points to a much simpler representation, a JSON-C feed (alt=jsonc). See https://developers.google.com/youtube/2.0/developers_guide_jsonc#Comparing_JSON_and_JSONC for more info.
Assuming you meant to use a JSON-C representation, the items definitions are under data.items
parse: function(response) {
return response.data.items;
}
The video data for each object is under a video attribute. Assuming you want your Item instances to directly reflect the videos, you will have to unwrap them with _.pluck for example:
parse: function(response) {
var items = response.data.items;
return _.pluck(items, 'video');
}
And an updated Fiddle http://jsfiddle.net/BHrmC/80/

BackboneJS with XML ajax

this is a two part question from a JS newbie.
So, I was trying to create a backbone application using requireJS by following Thomas Davis's tutorial.
How do I go create Backbone collections out of an ajax call to a server that provides data in XML? collections.fetch() seem to be expecting a JSON backend.
while trying some things, I ended up with the following code, in which the page doesn't refresh upon populating the collection "bookStore" from within Ajax success-callback.
Here is how far I have gotten so far.
var bookListView = Backbone.View.extend({
el: $("#books"),
initialize: function () {
thisView = this;
$.ajax({
type: "GET",
url: "books.xml",
dataType: "xml",
success: function (data) {
console.log(data);
$(data).find('book').each(function (index) {
var bookTitle = $(this).find('name').text();
bookStore.add({ title: bookTitle });
console.log(seid);
});
thisView.collection = bookStore;
thisView.collection.bind('add', thisView.tryBind);
}
}).done(function (msg) {
alert("Data retrieved: " + msg);
});
this.collection = bookStore;
this.collection.bind("add", this.exampleBind);
this.collection.bind("refresh", function () { thisView.render(); });
/*
// This one works!
bookStore.add({ name: "book1" });
bookStore.add({ name: "book2" });
bookStore.add({ name: "book3" });
*/
},
tryBind: function (model) {
console.log(model);
},
render: function () {
var data = {
books: this.collection.models,
};
var compiledTemplate = _.template(bookListTemplate, data);
$("#books").html(compiledTemplate);
}
});
Here, the success call-back in the "initialize" function seems to be processing the data properly and adding to the collection. However, the page doesn't refreshed.
While I was stepping through the Firebug console, the page gets refreshed however. How do I solve this problem?
You can override the default parse function to provide XML support. It should return the data transformed into JSON http://backbonejs.org/#Collection-parse
Bind the render to a reset event instead of refresh for Backbone<1.0 or to a sync event for Backbone>=1.0
It could look like this
var Book = Backbone.Model.extend();
var Books = Backbone.Collection.extend({
model: Book,
url: "books.xml",
parse: function (data) {
var $xml = $(data);
return $xml.find('book').map(function () {
var bookTitle = $(this).find('name').text();
return {title: bookTitle};
}).get();
},
fetch: function (options) {
options = options || {};
options.dataType = "xml";
return Backbone.Collection.prototype.fetch.call(this, options);
}
});
var bookListView = Backbone.View.extend({
initialize: function () {
this.listenTo(this.collection, "sync", this.render);
},
render: function () {
console.log(this.collection.toJSON());
}
});
var bks = new Books();
new bookListView({collection: bks});
bks.fetch();
And a demo http://jsfiddle.net/ULK7q/73/

Categories