I was called function inside setinterval. But i don't take return value from function.
My code:
function getApiData() {
request({
url : 'http://testest.com',
json : true
}, (error, response , body) => {
if(!error && response.statusCode == 200){
return JSON.stringify(body);
}
else{
return undefined;
}
});
}
Call:
setInterval(() => {
var data = getApiData();
console.log(data);
}, 2000);
Output : Undefined
Please help me. (I am learning new)
As #Aravindan Ve pointed out, there is no way to get retrieve the value returned by that function.So, define a different function
functionPrintResponse(res){
console.log(res)
}
and instead of returning there, invoke functionPrintResponse(JSON.stringify(body))
Related
I am calling network requests in a forEach loop, each request returns a new object which I would like to push to an array that is outside the forEach. When it is called after awaiting for the network requests to complete, it returns as empty "[]".
return this.get(urlOne, function (error, response) {
if (response.statusCode === 200) {
let array = [];
stores.forEach((store) => {
this.get(urlTwo, function (error, response) {
if (response.statusCode === 200) {
array.push(response.body);
}
});
});
console.log(array);
}
});
This is just a guess but, stores.forEach contents are async thus console.log(array) is called right after stores.forEach() is calle d(not completed) meaning array is blank.
console.log(array); probably needs to be called when the requests are actually done not right after they are made.
Simplest way to test if this is true is to see the array for every push if you see the array growing with your data there is the problem.
return this.get(urlOne, function (error, response) {
if (response.statusCode === 200) {
let array = [];
stores.forEach((store) => {
this.get(urlTwo, function (error, response) {
if (response.statusCode === 200) {
array.push(response.body);
console.log(array);
}
});
});
}
});
(EDIT)
if (response.statusCode === 200)
array.push(response.body);
else if(response.statusCode === 204)
console.log(array);
Status code 204 means No Content, if this isn't being sent automatically or an equivalent, you may need to send it manual some how.
I see the below code in my application. I am not able to understand the logic implemented.
Can someone explain me how the below works. Is this a different implementation of 'if' condition.
Also, Can I put 'await' ahead of 'request' in the below code since I need to wait till I get response for this request made. If not, how else can I use await below.
newstatus != undefined &&
request(params, (error, response, body) => {
error && console.info("error");
console.info("response received:", body);
});
In javascript this && operator named as AND
&& means if a condition returns true then move to the next step otherwise not go for the next inner step.
newstatus != undefined &&
request(params, (error, response, body) => {
error && console.info("error");
console.info("response received:", body);
});
the above example demonstrates that if(newstatus != undefined) condition true then call request API call.
To answer your second question how can we use async in it.
await use for promises only or before functions that return promise after completing some tasks like API call.
you have to make a function for request API that return Promise
here we have created the doRequest() function that will return a promise.
solution:
function doRequest(url) {
return new Promise(function (resolve, reject) {
request(params, (error, response, body) => {
if (!error && res.statusCode == 200) {
resolve(body);
} else {
reject(error);
}
});
});
}
// Usage:
async function main() {
let res = await doRequest(url);
console.log(res);
}
OR
newstatus != undefined && await doRequest(url);
I have a method in my routes and I want to invoke the API mentioned in the uri. I am able to invoke the method successfully.But now I have created a method sample in my restful API in which I need to pass a value from node.js and print the concatenated value.
I have the sample method which accepts a String argument.I have created a variable named paramater = Hi and send this as an request.But it is not concatinating it.
Can anyone tell me the way to pass values in restful API in node.js
Here's mine code
router.post('/restful', function (req, res) {
var options = {
uri: 'http://192.168.1.6:8080/sampleRest/RequestxARC/sample',
method: 'post'
};
var parameters = "Hi";
var responseFromClient = '';
request(options, function (error, response, body, parameters) {
if (!error && response.statusCode == 200) {
responseFromClient = body;
}
else {
responseFromClient = 'Not Found';
}
console.log(responseFromClient);
//res.json(resss);
req.flash('response_msg', responseFromClient);
if (responseFromClient != 'Not Found') {
res.redirect('/users/restful');
}
else {
res.redirect('/users/restful');
}
});
});
If we want to use any value which is being passed from UI. We can use it by this way:
router.post('/restful', function(req, res){
var platformname=req.body.platform;//This is the way to attach variables from UI.
var options = {
uri : 'http://192.168.1.6:8080/sampleRest/RequestxARC/sample',
body : platformname,
method : 'post'
};
console.log(options.body +" value attached from UI");
var responseFromClient = '';
request(options,function (error, response, body ,form ,callback) {
if (!error && response.statusCode == 200) {
responseFromClient = body;
}
else {
responseFromClient = 'Not Found';
}
console.log(responseFromClient);
//res.json(resss);
req.flash('response_msg', responseFromClient);
if(responseFromClient !='Not Found'){
res.redirect('/users/restful');
}
else{
res.redirect('/users/restful');
}
});
});
This question already has answers here:
NodeJS get async return value (callback) [duplicate]
(2 answers)
Closed 5 years ago.
I'm working on a module that returns a the data retrieved from an http request using the request module. However, I'm having a problem when I want to pass the data out of the function. Take this, for example.
function getData(term) {
var parsedData
request.post(url, term, (err, response, body) => {
if (!err && response.statusCode == 200) {
parsedData = doSomethingTo(body);
}
});
return parsedData;
}
This method doesn't work, since the function getData() performs asynchronously and the value is returned before the request can actually return the proper data.
function getData(term) {
var parsedData
request.post(url, term, (err, response, body) => {
if (!err && response.statusCode == 200) {
parsedData = doSomethingTo(body);
return parsedData;
}
});
}
This method doesn't work either, as it will merely make the request function return the parsed data, and not the getData function.
How could I make the parent function return the data parsed from the request function?
use Promise like this :
function getData(term) {
return new Promise(function(resolve){
request.post(url, term, (err, response, body) => {
if (!err && response.statusCode == 200) {
var parsedData = doSomethingTo(body);
resolve(parsedData);
}
});
});
}
and you can call your function like this :
getData(term).then(function(data){
//console.log(data);
})
use the bluebird promise module very fast.
var Promise = require('bluebird');
function getData(term) {
return new Promise(function(resolve,reject){
if (!err && response.statusCode == 200) {
var parsedData = doSomethingTo(body);
resolve(parsedData);
}else{
reject(err);
}
});
};
then the place you are calling the function do this;
var promise = getData(term);
promise.then(function(data){console.log(data)}).catch(function(err){console.error(err)});
Can somebody see in my code why the variable oauthToken is defined on the server but not defined when returned to the client in the result of Meteor.call
I make a call to initiate a post request on the server
The body is parsed and I store a value into the variable oauthToken
This prints out on the server but does not print out on the client in my 'result'
Is this because the client is running a simulation? Can we do a 'return' in an asynchronous function?
Server.js
Meteor.methods({
getGoodreads: function () {
request.post('http://www.goodreads.com/oauth/request_token', {oauth:{
consumer_key: '89hdg8pEoMzRdg',
consumer_secret: 'dfgdfgHthtdtjtt' }}, function (error, response, body) {
if (!error && response.statusCode == 200) {
var a = querystring.parse(body)
oauthToken = a.oauth_token
console.log(oauthToken); //prints value i need
return oauthToken
}else{
console.log('there is an error ' + error);
}
});
}
});
client.js
Template.profile.events({
'click #goodreads': function (event) {
event.preventDefault();
Meteor.call('getGoodreads', function(error, result) {
if (error) {
console.log('this is an error ');
} else {
console.log(result); //THIS IS UNDEFINED...possibilities?
}
});
}
});
Use futures to return values from async functions:
var Future = Npm.require("fibers/future")
Meteor.methods({
getGoodreads: function () {
var f = new Future();
request.post('http://www.goodreads.com/oauth/request_token', {oauth:{
consumer_key: '89hdg8pEoMzRdg',
consumer_secret: 'dfgdfgHthtdtjtt' }}, function (error, response, body) {
if (!error && response.statusCode == 200) {
var a = querystring.parse(body)
oauthToken = a.oauth_token
console.log(oauthToken); //prints value i need
return f.return(oauthToken)
}else{
f.throw(error);
console.log('there is an error ' + error);
}
});
return f.wait()
}
});
It's because you are starting an asynchronous request in the method body. The method returns immediately, and the callback from the request doesn't really have anywhere to return the result.
I don't really know how to do this with methods, but you could do it with publish/subscribe. Something like this:
Server.js
var result = "";
Meteor.setInterval(function() {
request.post('http://www.goodreads.com/oauth/request_token', {oauth:{
consumer_key: '89hdg8pEoMzRdg',
consumer_secret: 'dfgdfgHthtdtjtt' }},
function(error, response, body) {
if (!error && response.statusCode == 200) {
var a = querystring.parse(body);
oauthToken = a.oauth_token;
result = oauthtoken;
}
});
});
}, 10*1000);
Meteor.publish("goodReads", function() {
this.added("goodReads", 1, {reads: result});
Meteor.setInterval(function() {
this.changed("goodReads", 1, {reads: result});
}, 10*1000);
this.ready();
});
Client.js
goodReads = new Meteor.Collection("goodReads");
Meteor.subscribe("goodReads"); // May be done in waitOn in the router
This was taken off the top of my head, and is not tested. It may or may not work, but is at least a pointer to how you could do it