Modern JS/Promise newbie here. I'm having trouble finding the answer to a simple question, despite the overwhelming amount of content on this subject.
I believe I have a decent understanding of JS Promises (thanks to various sources, including mdn and /)
I have consumed and produced Promises regularly in their simplest form, however I keep stumbling on methods in my inherited projects with the following pattern:
const doAsyncOp = () =>
$http.get(uri)
.then(
value => value,
reject => //...
);
My big question is: What happens when you simply return a value from your success handler? I need to consume this method, and need access to 'value' in the client code. Is this technically unhandled? Should I rewrite the implementation?
Modern JS/Promise newbie here. I'm having trouble finding the answer to a simple question, despite the overwhelming amount of content on this subject.
I believe I have a decent understanding of JS Promises (thanks to various sources, including mdn and https://spin.atomicobject./2016/02/16/how-javascript-promises-work/)
I have consumed and produced Promises regularly in their simplest form, however I keep stumbling on methods in my inherited projects with the following pattern:
const doAsyncOp = () =>
$http.get(uri)
.then(
value => value,
reject => //...
);
My big question is: What happens when you simply return a value from your success handler? I need to consume this method, and need access to 'value' in the client code. Is this technically unhandled? Should I rewrite the implementation?
Share Improve this question edited Apr 2, 2018 at 19:27 pvgdev asked Apr 2, 2018 at 19:20 pvgdevpvgdev 1572 silver badges8 bronze badges 5-
Drop the pointless
.then(value => value)
. You can just passnull
, or usecatch
if you only want to handle rejections. – Bergi Commented Apr 2, 2018 at 19:26 - I'm sorry if the snippet wasn't clear. The rejection is arbitrary here; I need access to value in the client code. Is this possible with this code? – pvgdev Commented Apr 2, 2018 at 19:28
-
If by "client" you mean caller, you are returning the promise from your function, so you can just use
doAsyncOp().then(value => /* do whatever you need */)
. – Bergi Commented Apr 2, 2018 at 21:25 - Client code, meaning the scope of the consumer script. The caller is part of the client code. And, yes, but what if the implementation already includes a .then(value => value)? I'd like to consume this method without modifying it, because this type of method implementation is repeated many times in the project. I think someone clarified this for me. Thanks though! – pvgdev Commented Apr 2, 2018 at 22:18
- Bergi, I've realized that you've answered my question; I just needed more elaboration. jfriend00 helped clear it out for me. Cheers! – pvgdev Commented Apr 2, 2018 at 22:24
3 Answers
Reset to default 4My big question is: What happens when you simply return a value from your success handler?
When you return a value from a .then()
handler, that value bees the resolved value of the parent promise chain: So, in this code:
// utility function that returns a promise that resolves after a delay
function delay(t, v) {
return new Promise(resolve => {
setTimeout(resolve.bind(null, v), t);
});
}
function test() {
return delay(100, 5).then(val => {
// this return value bees the resolved value of the promise chain
// that is returned from this function
return 10;
});
}
test().then(result => {
// logs 10
console.log(result);
});
When you run it, it will log 10
because of the return 10
in the .then()
handler.
There are four possibilities from a .then()
handler:
Return a regular value such as
return 10
orreturn val
. That value bees the resolved value of the promise chain. If no value is returned (which in Javascript means the return value isundefined
), then the resolved value of the promise chain isundefined
.Return a promise that ultimately resolves or is already resolved. This promise is added to the chain and the promise chain takes on the resolved value of that promise.
Return a promise that ultimately rejects or is already rejected. This promise is added to the chain and the promise chain takes on the rejected reason of the returned promise.
Throw an exception. If an exception is thrown inside the
.then()
handler, then the.then()
infrastructure will catch it and turn the promise chain into a rejected state with the reject reason set to the value that is thrown. So, if you dothrow new Error("User not found")
inside a.then()
handler, then that promise chain will be rejected with that error object as the reject reason.
In your specific code:
const doAsyncOp = () =>
$http.get(uri)
.then(
value => value,
reject => //...
);
There is no reason for the value => value
. value
is already the resolved value of the promise, you do not need to set it again.
And since the fat arrow function automatically returns any single statement, you're already returning the promise from $http.get().then()
in your doAsyncOp()
function. So, you can just do:
const doAsyncOp = () => $http.get(uri);
doAsyncOp().then(result => {
// handle the result here
}).catch(err => {
// handle error here
});
To get this to the client code, just return the promise from your function:
const doAsyncOp = () => $http.get(uri)
then in your client you can use:
doAsyncOp()
.then(value => {
// use value
}
.catch(err => { /* error */ }
I think you can use async and await for the resolved values.
function delay(t, v) {
return new Promise(resolve => {
setTimeout(resolve.bind(null, v), t);
});
}
async function(){
await myData = delay(1000, 1000);
console.log(myData);
}