Promise not resolving before IF STATEMENT [duplicate] - javascript

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 1 year ago.
I'm trying to check the results of "checkWorkflow" but it seems to be running the "If" statement before checking, i think this because of my console output.
I feel like i'm doing something wrong with the promise, but i'm kinda at a lost at this point.
Console Output
Promise { pending } *When i console.log(doesWorkflowExists)
workflow already exists, please rename
error2
const createWorkflow = async (req, res) => {
try {
const doesWorkflowExists = checkWorkflow(req.name);
if (!doesWorkflowExists) {
console.log('do stuff')
}
else {
console.log('workflow already exists, please rename')
}
} catch (error) {
handleError(res, error);
console.log("error on create workflow");
}
};
vvvv checkWorkflow vvvv
const checkWorkflow = (name = '') => {
return new Promise((resolve, reject) => {
Workflow.findOne(
{
name,
},
(err, item) => {
if (err) {
console.log('error1')
return reject(buildErrObject(422, err.message));
}
if (item) {
console.log('error2')
return reject(buildErrObject(404, "WORKFLOW_ALREADY_EXISTS"));
}
resolve();
}
);
});
};

In your checkWorkflow function, you return a Promise. When you call checkWorkflow function like this :
const doesWorkflowExists = checkWorkflow(req.name);
doesWorkflowExists is a pending Promise. On the console, you can see that.
You need to "wait" until the Promise resolve the result or reject the error. Just add "await" keyword before the function call, like this:
const doesWorkflowExists = await checkWorkflow(req.name);
The rest seems to be fine, it should work :)

Related

JS Promise function call that returns object [duplicate]

This question already has answers here:
await setTimeout is not synchronously waiting
(2 answers)
Closed last month.
I have a async fetch function that waits 2 seconds and returns a object:
async function fetch() {
var object;
await setTimeout(() => { object = { name: 'User', data: 'API Data' } }, 2000);
return object;
}
I want to display the object when the initialization is completely done (after 2 seconds)
fetch().then((val) => {
console.log("DONE!");
console.log(val.name);
}).catch((err) => {
console.log("ERROR!");
console.log(err);
});
The code prints both DONE and ERROR Cannot read properties of undefined (reading 'name')
I have tried with Promise, no luck
let promise = new Promise((resolve, reject) => {
let request = fetch();
if (request !== undefined)
resolve(request);
else
reject(request);
}).then((val) => {
console.log(val);
});
How can I properly check that fetch() has returned a value before printing without changing the inside of the function. I can delete the async and await in it but I am unable to edit it (I.E. adding a Promise inside)
Based on requirement
I can delete the async and await in it (fetch function) but I am unable to edit it (I.E. adding a Promise inside)
The only way I see is to override window.setTimeout function to make it to return a promise. That way you will be able to await it and there will be no need to modify your fetch function.
const oldTimeout = window.setTimeout;
window.setTimeout = (fn, ms) => {
return new Promise((resolve, reject) => {
oldTimeout(() => {
fn();
resolve();
}, ms);
});
};
async function fetch() {
var object;
await setTimeout(() => {
object = { name: "User", data: "API Data" };
}, 2000);
return object;
}
fetch()
.then((val) => {
console.log("DONE!");
console.log(val.name);
})
.catch((err) => {
console.log("ERROR!");
console.log(err);
});
NOTE: For anyone without this requirement - please, use other answers to this question or check await setTimeout is not synchronously waiting for additional details/explanations. This kind of overridings are very confusing due to everyone expect common and well-known functions to behavior in a way described in the docs.
You cannot await the setTimeout function, this is because your function returns undefined. You have used the promise in the wrong way. Below code will fix your issue.
function fetch() {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve({ name: "User", data: "API Data" });
}, 2000);
});
}
fetch()
.then((val) => {
console.log("DONE!");
console.log(val.name);
})
.catch((err) => {
console.log("ERROR!");
console.log(err);
});
And remember that there is no need to change the setTimeout function.
The problem is that setTimeout does not actually return a promise, which means you cannot use await with setTimeout, that's why the var object; is returned instantly as undefined.
To solve this issue, you simply need to wrap setTimeout around a promise.
Like so:
function setTImeoutAwait(time) {
return new Promise((resolve) => {
setTimeout(resolve, time);
});
}
You can then use it like this:
async function fetch() {
var object;
await setTImeoutAwait(1000).then(() => {
object = { name: "test" };
});
return object;
}

Async method is promise but return undefined [duplicate]

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 2 years ago.
I'm working on Nuxt.js app and try to use an async method to get data from api, but the result of the async method is always undefined. It looks like my methods aren't waiting for the response. I don't know what I've missed.Here is my code in methods: {..}
async getSomething() {
console.log("getSomething");
if (condition) {
axios
.get("api_url")
.then((response) => {
console.log("getSomething success");
return "success";
})
.catch((error) => {
console.log("getSomething fail 1");
return "fail";
});
} else {
console.log("getSomething fail 2");
return "fail";
}
}
doSomething() {
console.log("do Something");
this.getSomething().then((result) => {
console.log("result", result);
if (result === "success") {
// do something on success
} else {
// do something on fail
}
});
console.log("end doSomething");
}
I already try to logging this.getSomething() and the result is Promise {<pending>}
Here, when a method has been call on created () {..}
this.doSomething()
// doSomething
// getSomething
// end doSomething
// getSomething success
// result undefined
I think part of your problem is that you're mixing async/await style of writing code with promise-chaining style. When you return 'fail' or 'success', you're usually returning from the axios.get callback, not from the getSomething method. You might want to rewrite your code a little like this:
async getSomething () {
console.log('getSomething')
if (condition) {
try {
let response = await axios.get('api_url')
console.log('getSomething success')
return 'success'
}
catch(error) {
console.log('getSomething fail 1')
return 'fail'
}
} else {
console.log('getSomething fail 2')
return 'fail'
}
}

codes still execute after promise reject [duplicate]

This question already has answers here:
Do I need to return after early resolve/reject?
(6 answers)
Closed 2 years ago.
I have the following codes:
function promise3() {
return new Promise((resolve, reject) => {
function1().then(() => {
resolve();
}).catch(err => {
reject(err);
console.log("after error");
});
})
}
promise3().catch(e => {
console.log(e);
});
function1 returns a promise. But when function1 fails and returns an error. I see the console.log("after error") before the console.log of the error. I though the codes after reject would not run. reject acts like a return. What is happening here then?
If you don't want to execute anything after resolve/reject you need to return them as follow.
function promise3() {
return new Promise((resolve, reject) => {
function1().then(() => (
resolve(); //change the brackets to () instead of {}
)).catch(err => {
return reject(err); //put a return keyword in front
console.log("after error");
});
})
}
promise3().catch(e => {
console.log(e);
});
(): mean that you are returning that is inside.
{}: mean that you need to do the following tasks and return nothing if there is no return statement.

How to return to parent function in JavaScript [duplicate]

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 3 years ago.
I have the following function at the moment, and I want to return "aaa" to the parent function (getStream), this is the code I have atm:
module.exports.getStream = (figure) => {
plotly.plot(figure, imgOpts, function(err, stream) {
if (err) {
console.log(err);
return "error";
}
return "aaa";
});
};
Right now, however, it returns undefined. What's the best solution to solve that problem?
The problem is that getStream does not return anything (therefore its return value is undefined). You have to add return before plotly or just remove curly braces. Also you'll have to return a promise, because that third argument of plotly.plot method is a callback function (I guess).
module.exports.getStream = (figure) =>
new Promise((resolve, reject) => {
plotly.plot(figure, imgOpts, function(err, stream) {
if (err) {
console.log(err);
reject("error");
}
resolve("aaa");
});
})
and then somewhere in the app:
const foo = async () => {
try {
const result = await getStream(figure)
console.log(result) // 'aaa'
} catch (err) {
console.log(err) // 'error'
}
}

Using Async inside another function [duplicate]

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 6 years ago.
I am using node.js and async with sails.js framework.
I am trying to create a function that perform some async DB operations on an array of data but I have problems figuring out a simple way to return the results of async to the parent function.
Here's my code:
convertProductfields: function (articlesFromAurelia){
async.each(articlesFromAurelia, function (post, cb) {
Categories.find({name: post.Categoria})
.then(function(category){
post.cat_id = category[0].cat_id;
cb();
})
.fail(function(error){
cb(error);
})
}, function(error){
if(error) return res.negotiate(error);
sails.log.debug('articlesFromAureliaModified ' , articlesFromAurelia);
return articlesFromAurelia;
});
sails.log.debug('articlesFromAureliaNotModified ' , articlesFromAurelia);
return articlesFromAurelia;
}
The problem of course is the execution order of the code. My function has already returned when the results of Async operations are available.... so, how to make it work? Thanks!!
Using Node 6.0, in built Promises can be used.
convertProductfields: function (articlesFromAurelia){
var allPromises = articlesFromAurelia
.map(post => new Promise((resolve, reject) => {
Categories.find({name: post.Categoria})
.then((category) => resolve(category))
.fail((error) => reject(error))
}));
return Promise.all(allPromises);
}
And to use the above function,
convertProductfields(articlesFromAurelia)
.then(() =>{
//handle success
}).catch(() => {
//handle error
})
Hope it helps you.
convertProductfields: function (articlesFromAurelia, callback){
async.each(articlesFromAurelia, function (post, cb) {
Categories.find({name: post.Categoria})
.then(function(category){
post.cat_id = category[0].cat_id;
cb();
})
.fail(function(error){
cb(error);
})
}, function(error){
if(error)
return callback(null); //incase of error, return null
sails.log.debug('articlesFromAureliaModified ' , articlesFromAurelia);
return callback(articlesFromAurelia); //return updated articles
});
}

Categories