I have a Web Application that currently uses JQGrid but I'm trying to introduce Backbone.js to improve code organization. What I'm trying to do is get data from the server using a Collection, and then add the JSON information to my defined JQGrid but I can't get it to work. My JQGrid is defined like this:
var tareasHumanasTable = $("#grillaTH").jqGrid({
datatype: 'local',
height: 'auto',
colNames:[ colNames...],
colModel:[ colModel...]
}
And my Model and Collection are defined like this:
window.TareaHumana = Backbone.Model.extend();
window.TareaHumanaCollection = Backbone.Collection.extend({
model: TareaHumana,
url: "bandejaTareas/buscarTH"
});
I have a button that when clicked starts server communication. Now is doing this:
$(function(){
$("#botonBuscar").bind('click',function(){
var tareaHumanaList = new TareaHumanaCollection();
tareaHumanaList.fetch({data: $("#formBandejaTareas").serializeObject()});
//alert("tareaHumanaList.toJSON(): " + tareaHumanaList.toJSON());
tareaHumanaList.each(function(tareaHumana, i){
//alert("tareaHumana.toJSON(): " + tareaHumana.toJSON());
tareasHumanasTable.jqGrid('addRowData', (i + 1), tareaHumana.toJSON());
});
That code doesn't work at all. With Firebug I verified that the server sends the data in the correct format but the code isn't working. The weirdest thing is that when I uncomment the "alert(...)" lines everything starts to work.
The key is that fetch is asynchronous. So if you immediately call each after fetch it's probably your collection won't be populated. You should use success callback. For example take a look at this answer.
Try to use datatype:jsonstring and create a format function on the collection to provide corect data format to jqgrid.
Related
In general I'm working on a little webapp that just shows me search entries from wikipedia on the page after I enter a search term into the textfield.
I’m working on this problem a long time now.
I have setup an ajax get request to the wikipedia api.
It’s working fine as far as the title goes. But I looked at the json I get in return via console.log and see that there is no summary or first paragraph in this response.
So I googled and found a very nice article which points me to that link:
(can't post it due to under 10 reputation, sad story)
Just google for "wikipedia extracts api"
It says that the query also needs this prop=“extracts” and the exintro: true
But if I add this to my query I do not get the "exintro" in return.
Here is how I set up my ajax call:
function callback(){ // gets called when sliding up the div is completed
$.ajax({
url: 'http://en.wikipedia.org/w/api.php',
//TODO: Fix this line of code (extracts)
data: { action: 'query', list: 'search', prop: 'extracts', exintro: true, srsearch: $("input[name=search]").val(), format: 'json' },
dataType: 'jsonp',
success: processResult
});
$(".container").remove();
}
So if it’s successfull it runs the processResultmethod:
function processResult(apiResult){
console.log(apiResult);
for (var i = 0; i < apiResult.query.search.length; i++){
$('#display-result').append('<div class="' + i + '">' + '<p>'+apiResult.query.search[i].title+'</p>' + '<p>'+ apiResult.query.search[i].snippet +'</p>' + '</div>');
}
}
But the json it returns looks something like that:
Picture of the returned json
Nothing I’m interested in. I need the summary or exintro how wiki api calls this.
Here is the link to the github: https://github.com/dhuber666/wikipediaJS
Any ideas? Do I set it up wrong in the ajax call object “data” ? Pleae help!
The snippetin the json is useless since it cuts off the sentence after a few words
Your "data" object is fine. Seems like "snippet" is just what Wikimedia API returns for this request. You can then send request to get extracts of returned pages (using "title" or "pageid" you get for each article). For example: https://en.wikipedia.org/w/api.php?format=json&action=query&prop=extracts&exintro=true&explaintext=true&titles=Title|Hello for titles "Title" and "Hello".
Maybe this other API call will suit your needs:
https://en.wikipedia.org/w/api.php?action=opensearch&search=hello&format=json It returns one full sentence, doesn't cut anything.
I'm trying to setup my datatable to POST to the contents of it's rows into my PHP script so that I can store it in a database.
I have a working HTML page, which when I click "+ Add Mapping" a BS modal appears and I can add a row to the datatable.
<script>
$(document).ready(function() {
var t = $('#parameters_config').DataTable();
$('#add_new_mapping').on('click', function() {
$('#add_field_mapping').modal('hide');
var wb_field = $("#add_field_mapping #wb_field").val();
var adobe_field = $("#add_field_mapping #adobe_field").val();
t.row.add([
adobe_field,
wb_field,
]).draw();
$('#add_new_field_mapping').trigger("reset");
});
});
</script>
This all works perfectly. I now would like to retrieve all data rows and POST them to my script so that I can process the submitted data and store. So far, I've come up with this based on information provided:
<script>
$(document).ready(function() {
$('#parameters').submit(function(event) {
var table = $('#parameters_config').DataTable();
var dataToSend = table
.rows()
.data();
console.log( 'Data', dataToSend);
alert( 'There are '+dataToSend.length+' row(s) of data in this table');
$.ajax({
type: 'POST',
url: '{$this->homeURL}',
data: dataToSend,
dataType: 'json',
});
});
});
</script>
In my console window I see the following returned for "dataToSend" but no actual data!
[Array[2], context: Array[1], selector: Object, ajax: Object]
Where am I going wrong?
Where the examples went wrong
The two examples you linked in your post aren't really related to what you're trying to do (from what I can gather about your goal).
The first example is about how to obtain data from the server with a POST instead of the default GET, and has nothing to do with sending data to the server for some purpose.
The second example is about serverside processing, which is where you have pagination, ordering, sorting, filtering, and all other DataTables features handled in your own server code where you then send the results to the client (which is pretty complicated and unless you have a huge number of rows, unnecessary).
Therefore, remove serverSide: true!
Your Goal
What you actually want to do (I think) is send your data to a php script so that you can do something with it. This is not handled by any DataTables API call, but is a fairly simple feature to implement. All you really need is a function that will make an AJAX call that will send the data to the script.
Solution
The way you can do this is by obtaining the data with the t.data() API call, and then sending it with an ajax request. It might look like this:
function sendData(){
var dataToSend = t.data();
$.ajax({
type: 'POST',
url: 'URL OF SCRIPT HERE',
data: dataToSend
});
}
Then you simply have to call sendData() whenever it is that you want to send the data. Of course, you'll have to ensure that your controller handles the data correctly, but that's a different matter entirely.
I am creating a basic piece of functionality to allow users to send their location to a server which then queries a database and returns locations near to them. I am using the below jQuery .ajax wrapper to POST data to the server. This takes the form of a latlon point which is then used as the basis for a geosearch in MongoDB using nodejs and express on the backend. The results of the search are then intended to be returned to the client and rendered by the createMapListings function.
The /find page is initially rendered through a GET request to the database via mongodb separate from the below code. However subsequent to initial rendering, I then want to return results dependent on the location provided.
The POST method works fine and the location is posted to the server, with the search results being returned as I can print contents out through the console log.
However, I then want to render the results on the client-side. As mentioned, the results of the search render in the console, but when I attempt to pass through to the client, I can render the data itself (in the form of an array of objects) in the #output div, but the createMapListings function does not seem to catch the data.
In fact, the below function appears to be called but prints out over a thousand rows with the data that should be caught described as 'undefined'. I have tried to use res.render and res.redirect, but in the first case, the view renders in the div (which I suppose is expected) and the redirect fails.
The createMapListings function works fine when a simple GET request is made to the server, for example, for all objects in a collection, using ejs template. However, I think the issue here may be a combination of a POST request and then wanting to pass the results back to the AJAX request using the complete callback.
I apologise if the below code is somewhat obtuse. I’m definitely what you would call a beginner. I appreciate the above functionality may not possible so if there is a better way, I would of course be open to it (res.direct perhaps).
Here is the relevant client side script:
$(document).ready(function(){
$("#geolocate").click(function(){
navigator.geolocation.getCurrentPosition(geolocate, function(){
});
});
});
function geolocate(pos){
var latlonpt = [];
var x = pos.coords.latitude;
var y = pos.coords.longitude;
latlonpt.push(x);
latlonpt.push(y);
var obj = {
userlocation: latitudelongitudept
};
$.ajax({
url: "/find",
type: "POST",
contentType: "application/json",
processData: false,
data: JSON.stringify(obj),
complete: function (data) {
$('#output').html(data.responseText);
$('#infooutput').children().remove();
createMapListings(data.responseText);
}
});
};
function createMapListings(maps) {
for (var i = 0; i < maps.length; i++) {
var url = maps[i]._id;
var fullurl = "<a href='/show?id=" + url + "'>Route</a></div>";
var title = "<div>" + maps[i].title + " - " + fullurl +"";
$('#infooutput').append(title);
};
};
</script>
Here is the relevant route used in a basic express app to handle the post request made by the above .ajax wrapper.
exports.findbylocation = function(req, res) {
console.log(req.body.userlocation);
var userlocation = req.body.userlocation;
Map.ensureIndexes;
Map.find({loc :{ $near : userlocation }}, function(err, maps) {
if (err) {
console.log(err)
}
else {
var jmaps = JSON.stringify(maps);
console.log(jmaps);
res.send(jmaps);
}
});
};
By convention, the data variable name in an $.ajax callback signature refers to the parsed HTTP response body. Since your callback is on complete, we're actually passed the XMLHttpRequest used, by convention called xhr. You rightly grab the responseText property, but this needs parsing to be useful. So long as we take care over our Content-Type's and don't explicitly disable processData, jQuery will do the encoding/unencoding for us - we just deal with objects. This is a good thing, since the transport format isn't usually of any particular importance to the application logic. If we use res.json(maps) in place of res.send(jmaps), we can write our call more simply:
$.ajax({
url: '/find',
type: 'POST',
data: obj,
success: function(data) {},
error: function(xhr, text, err) {}
});
Here data is a Javascript object already parsed and ready to use. We also use a default application/x-www-form-urlencoded request rather than explicitly setting a contentType. This is the same as far as express is concerned: it will just be parsed by urlencoded instead of json.
Assuming you solved your client-sie problem.
As you are using express there is no need for JSON.stringfy,
you can use res.json(maps).
I am using backbone for the first time and I am really struggling to get it to function correctly with a JSON data file.
I have a model Like so:
window.Test = Backbone.Model.extend({
defaults: {
id: null,
name: null,
},
url: function() {
return 'json/test.json/this.id';
},
initialize: function(){
}
});
When a test item is clicked I then try to bring up the details of the pacific model that was clicked by doing
testDetails: function (id) {
var test = new Test();
test.id = id;
test.fetch({ success: function(data) { alert(JSON.stringify(data))}});
},
However this does not work, I am unable to correctly say "get the JSON element with the passed ID"
Can anyone please show me how to correctly structure the models URL to pull the element with the ID.
Thanks
The problem here is that you're treating your JSON data file like a call to a server. That won't work and it's the reason you're getting a 404. If you're accessing a file locally, you have to load the file first. You can do this with jQuery using the .getJSON() method, or if the file's static, just load it into memory with a script block (though you'll probably need to assign a var in the file). Most likely, you'll use jQuery. An example of this can be found here:
Using Jquery to get JSON objects from local file.
If this is an array of JSON, you can load the array into a collection, and use the "at" method to access the particular element by id. If it's entirely JSON, you'll have to create a custom parser.
your url is incorrect for one. you are returning the literal string 'this.id'. you probably want to do something more along the lines of
url: function () {
return 'json/test.json/' + this.id;
}
I would start by fixing your url function:
url: function() {
return 'json/test.json/' + this.get('id');
}
The way you have it now, every fetch request, regardless of the model's id, is going to /json/test.json/test.id
my requirement is to get the result in gridview based on the treeview node selection using javascript i.e. client scripting. Currently the same can be achieved using server side scripting, but i want to do this without postback and without using selectednodeindexchanged event. Pls. help me to solve this problem.
The solution is quite involved but goes something like this:
Use the Page.GetCallbackEventReference method to make an XmlHttpRequest back to the server and retrieve a json object that will be used to populated the grid.
See the System.Web.Script.Serialization namespace for pointers on how to convert your objects to JSON.
Create a JavaScript closure to encapsulate your grid update logic. Something like:
var vm = {
someField: 'test',
init: function() {
},
update: function(data) {
var grid = document.getElementById('yourGrid');
// loop through the data and set the innerHTML on the cells to whatever your data is.
}
}
setTimeout(function() {
vm.init();
}, 100);
// In the aspx/ascx
//when the callback completes convert the json to an object like this
var d = eval('(' + data + ')');
//call update on your object
vm.update(data)