I wanna know is it possible to make a function that make the api call then returns the response so i can call the function somewhere else and manipulate the data as i wish I’m using jQuery and it appears to be that i’m limited to what i can do with the response only inside the $.getJSON() function
I’m not really qualified to answer this as I don’t actually know the answer. Seeing as .done() / success() needs to be chained to the end of the AJAX request, I suspect probably not.
Also, getJSON() already is that function, why would you want to wrap it in another function?
You can save the URL in a variable.
Then every time you need to use the response data the only code you need to write will be…
$.getJSON(URL).done(function®{
//manipulate your response
}
It’s barely more code than calling a function. Or maybe I’ve misunderstood?
I think what your asking is could you do something like:
function makeApiCall() {
const data = $.getJSON(url);
return data;
}
// Somewhere else in code.
const data = makeApiCall(); // data immediately available.
console.log(data) // [{ ... }]
This isn’t possible, because ajax calls are asynchronous, you can’t treat them as if they’re synchronous like above.
Promises / jQuery deferred might be what you want to give you more flexibility.
@obolland’s response uses promises. You have to return the $.get
function, which returns a promise object (jQuery calls it jqXHR). Promises are chainable. As @obolland notes, you don’t save much doing this. But what if you need to do this multiple times? I think you could do something like:
function makeApiCall(url) {
var api = {
url: url,
params : {
action: 'query',
format: 'json',
prop: 'pageimages|extracts|info',
inprop: 'url',
generator: 'search',
gsrsearch: 'searchTerm',
gsrlimit: 10,
exintro: 1,
exlimit: 'max',
explaintext: 1,
grnnamespace: 0,
grnfilterredir: 'nonredirects',
origin: '*'
}
};
return $.get(api.url, api.params);
}
makeApiCall( 'http://example.com/api' )
.then(function (data) {
// do work on data
});
makeApiCall( 'http://yourwebserver.com/api' )
.then(function (otherdata) {
// do work on otherdata
});
Edited to change my example code. It makes more sense if there’s a bunch of fixed data that gets sent with each request. No need to re-type that into each .get()
request.
You could just use a simple solution like this:
let someData = null;
$.get("http://example.com/api").done(function(returnedData){ someData = returnedData; });
let functionThatUsesData = function(){
if(someData===null){ setTimeout( functionThatUsesData , 10 ); return "Loading..."; }
//else the data is avalible
}
While this is not the best solution, it will work.
What is setTimeout
doing here? Just re-calling functionThatUsesData
until the ajax response is received?
Do you have an example for us?
Looks like it’s checking every 10 milliseconds to see if the data has come in by calling itself recursively if the variable is null
.
Yeah it’s just recalling it self after a short delay until the data is received. Again this is not the best way of doing this. If you give us an example of what your trying to do, we could give you a better solution.
Instead of recursively polling ‘someData’ s/he could use promises. The callback doesn’t fire until the promise resolves, so there’s no need to check if data is available. It could look like:
var url = 'http://example.com/api';
$.get(url)
.then(handleResponse)
.then(doSomethingElse)
.then(render)
.catch(handleError);
function handleResponse(data) {
// manipulate data
return manipulatedData;
}
function doSomethingElse(manipulatedData) {
// more manipulation
return formattedData
}
function render(formattedData) {
$.('#output-div').html(formattedData);
}
function handleError(error) {
console.log(error);
}
Mate, if I understood what your are saying you are not limited to the $.getJSON(URL). The value you get from the $.getJSON can be thrown to a variable or to a place in the html document (which even can be hidden) and got thru id or class using the .html() ou .text() functions.
This is definitely the way to go if you have a set process for the data returned. However if you need to access that data inside something like a logic function, you will still need to “save” that data. In that case you would still need some logic check to ensure the data has been loaded. I usually just use a simple state boolean and if statement.