Promise in Javascript
mathans1695
Posted on July 9, 2020
I just wanted to share what is promise in javascript?, because I struggled to understand the concept from videos and articles, so I thought of sharing a simple Promise object that I have created. I hope you guys will have better understanding after going through this article.
Prerequisite:
Before getting started, you should have basic understanding of OOJS, callback functions and prototype methods.
Callback Function:
Callback
function is a function which are being passed into another function as a reference and got executed there. Have a look at the example below to have a better understanding.
Code
function A(callback) {
//Call function B
callback();
}
function B() {
console.log('Function B got Executed');
}
//Calling the function A with function B as parameter
A(B);
Console
Function B got executed
The above code will output "Function B got executed" in console, since we are passing the reference of function B
to function A
as parameter. Function B
are called back inside the function A
. That's why it's called as callback function.
Promises:
Simply, Promises will always come back with a status, no matter what happens.
It's like give me the task, I will definitely tell you whether the task has completed or not in future period. And also it'll give the result or error along with the status.
Let's say you're fetching a resource from a website using your program,
- You will make a request to the website,
- Website may respond to your request with a success response or an error response.
- If success means - You will get the desired resource as response.
- If Error means - You will get an error as response. I have an ultra slow network connection, so I often receive
connection timed out
as response.
Code
function temp() {
//Fetch will return a promise
let promise = fetch('https://jsonplaceholder.typicode.com/users');
console.log(promise);
}
//Call temp function
temp();
(Don't worry about fetch api right now)
Fetching from Website:
I am using fetch API to make a request to the URL https://jsonplaceholder.typicode.com/users to get users data inside temp
function - let promise = fetch('https://jsonplaceholder.typicode.com/users')
.
-
If success means - fetch will return a
Promise
object withstatus
:resolved
andvalue
:Response
object.Note:
status
property ofResponse
object will bestatus
:200
. Success means - You will have the desired resource inside theResponse
object.
>Promise {<pending>}
>__proto__: Promise
[[PromiseStatus]]: "resolved"
>[[PromiseValue]]: Response
body: (...)
bodyUsed: false
>headers: Headers {}
ok: true
redirected: false
status: 200
statusText: ""
type: "cors"
url: "https://jsonplaceholder.typicode.com/users"
>__proto__: Response
-
If Error means - fetch will return a
Promise
object withstatus
:resolved
andvalue
:response
object.Note:
status
property ofResponse
object will bestatus
:404
. Error means - You will get anerror
response.Here, I used invalid URL
https://jsonplaceholder.typicode.com/use
, so I am getting404
status
>Promise {<pending>}
>__proto__: Promise
[[PromiseStatus]]: "resolved"
>[[PromiseValue]]: Response
body: (...)
bodyUsed: false
>headers: Headers {}
ok: false
redirected: false
status: 404
statusText: ""
type: "cors"
url: "https://jsonplaceholder.typicode.com/use"
>__proto__: Response
Accessing the resource:
- To access the success
Response
fromPromise
object, we have to callthen
method with thePromise
instance - "promise". - For accessing error
Response
,catch
method is used to capture the error response.
function temp() {
//Fetch will return a promise
let promise = fetch('https://jsonplaceholder.typicode.com/users');
//accessing the response using then()
promise.then(function(res) {
return res.json();
})
.then(function(json){
console.log(json);
})
}
temp();
Here, We are getting the Response
by calling then
method on Promise
instance - "promise", then
method accept an anonymous function as argument.
If you put this line inside temp
function - promise.then((res) => {console.log(res)})
, you will get the Response
object as below:
>Response {type: "cors", url: "https://jsonplaceholder.typicode.com/users", redirected: false, status: 200, ok: true, …}
In first then
method, we are returning res.json()
, json
method will return another Promise
object.
If you put this line inside temp
function- promise.then((res) => {console.log(res.json())})
, you will get a Promise
object as below:
>Promise {<pending>}
>__proto__: Promise
[[PromiseStatus]]: "resolved"
>[[PromiseValue]]: Array(10)
Second then
method is used again to capture the Response
object from Promise
object returned from res.json()
.
Now, you will get `Array` of 10 users in console as below:
10) [{…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}, {…}]
0: {id: 1, name: "Leanne Graham", username: "Bret", email: "Sincere@april.biz", address: {…}, …}
1: {id: 2, name: "Ervin Howell", username: "Antonette", email: "Shanna@melissa.tv", address: {…}, …}
2: {id: 3, name: "Clementine Bauch", username: "Samantha", email: "Nathan@yesenia.net", address: {…}, …}
3: {id: 4, name: "Patricia Lebsack", username: "Karianne", email: "Julianne.OConner@kory.org", address: {…}, …}
4: {id: 5, name: "Chelsey Dietrich", username: "Kamren", email: "Lucio_Hettinger@annie.ca", address: {…}, …}
5: {id: 6, name: "Mrs. Dennis Schulist", username: "Leopoldo_Corkery", email: "Karley_Dach@jasper.info", address: {…}, …}
6: {id: 7, name: "Kurtis Weissnat", username: "Elwyn.Skiles", email: "Telly.Hoeger@billy.biz", address: {…}, …}
7: {id: 8, name: "Nicholas Runolfsdottir V", username: "Maxime_Nienow", email: "Sherwood@rosamond.me", address: {…}, …}
8: {id: 9, name: "Glenna Reichert", username: "Delphine", email: "Chaim_McDermott@dana.io", address: {…}, …}
9: {id: 10, name: "Clementina DuBuque", username: "Moriah.Stanton", email: "Rey.Padberg@karina.biz", address: {…}, …}
length: 10
__proto__: Array(0)
Using Javascript Promise Object;
Instead of getting the Promise
object from Fetch API, we can define our own Promise
object:
const promise = new Promise(function(resolve, reject) {
const success = true;
if(success) {
resolve('Content Loaded');
} else {
reject('Some error occurred');
}
});
promise
.then(function(success){
console.log(success);
})
.catch(function(error) {
console.log(error);
})
Instantiating Promise Object:
Here, I am instantiating new Promise
object and stored it in a variable called promise
.
The
Promise
object accept an anonymous function as an argument, the anonymous itself accept two callback functions as arguments.-
Inside the anonymous function, we are calling the corresponding callback function based on the conditional inside the anonymous function.
-
Conditions:
-
if(success)
evaluates totrue
-> callresolve('Content Loaded')
- resolve callback function will be called. -
else
-> callreject('Some error occurred')
-reject
callback function will be called.
-
- Since, the
success
variable set totrue
, theif
statement will always evaluates totrue
, so theresolve
function will be called.
Now, the
promise
variable will have aPromise
object with status as "resolved" and response as "Content Loaded" as below:
-
Conditions:
>Promise {<resolved>: "Content Loaded"}
>__proto__: Promise
[[PromiseStatus]]: "resolved"
>[[PromiseValue]]: "Content Loaded"
Try - console.log(promise)
, you will get an output like above in console.
Capturing the response:
- The response can be captured by calling
then
method onPromise
instance - "promise" by passing ananoynmous
function with an argument(success
) to capture the value "Content Loaded" in variablesuccess
.(success
will have astring
-Content Loaded
). ####Output:
Content Loaded
-
Try - changing the
success
variable inside thePromise
object anonymous function tofalse
likeconst success = false
, as a result:-
else
block will be executed during instantiation, which inturn will call thereject
callback function, which can be captured usingcatch
method onPromise
instance - "promise".
-
Change success variable: const success = false
Some error occurred
Note: Calling the reject('Some error occurred')
, will give us a Promise
object - which will have status as "rejected" and value as "Some error occurred":
Reject Promise object:
Promise {<rejected>: "Some error occurred"}
__proto__: Promise
[[PromiseStatus]]: "rejected"
[[PromiseValue]]: "Some error occurred"
Summary of Promise:
-
Promise
object has three states(status):-
resolved - If the request is fullfilled, you will get a
Promise
object with status "resolved". -
rejected - If the request is not fullfilled, you will get a
Promise
object with status "rejected". -
pending - If the request is in intermediate state, you will get a
Promise
object with status "pending" and value "undefined". Try:console.log(new Promise(() => {});
, you will get apending
response.
-
resolved - If the request is fullfilled, you will get a
-
Response
capturing:-
resolved - The
Response
object can be captured usingthen
method onPromise
instance. -
rejected - The
Response
object can be captured usingcatch
method onPromise
instance. -
pending - pending response can't be captured using
then
orcatch
methods. And it's seems reasonable, because we don't need a pending response, because it will not have any data or error.
-
resolved - The
Creating Look-alike Promise Object:
Now, we know what is promise?, let's define our own Promise
object DoYouLearnProgramming
:
Defining DoYouLearnProgramming Object:
function DoYouLearnProgramming(programming) {
let self = this;
programming(function(msg) {
self.resolve = msg;
}, function(msg) {
self.reject = msg;
});
}
Here, I am declaring an object
DoYouLearnProgramming
which accept a callback functionprogramming
as an arugument.The callback function -
programming
itself accepts two anonymous function as arguments.I am setting the
this.resolve
andthis.reject
property to correspondingmsg
being passed to each anonymous functions.And the callback function will be executed during instantiation.
Defining Prototype method:
DoYouLearnProgramming.prototype.then = function(arg) {
if(this.resolve === undefined) {
return this;
} else {
this.resolve = arg(this.resolve);
return this;
}
}
DoYouLearnProgramming.prototype.catch = function(arg) {
if(this.reject === undefined) {
return this;
} else {
this.reject = arg(this.reject);
return this;
}
}
Then, I am defining two prototype functions
then
andcatch
, which also accept an anonymous function as an argument.-
Some conditionals checks were happening inside the function, which checks
this.resolve
andthis.reject
property value and perform the corresponding operations.- If the condition evaluates to
true
, it will return the object instance itself. - If the condition evaluates to
false
, it will set the corresponding property value, by executing the callback function with the corresponding property value passed as argument.
- If the condition evaluates to
Instantiating DoYouLearnProgramming Object:
let p = new DoYouLearnProgramming(function(success, fail) {
if(true) {
success('You will be a developer');
} else {
fail('Develop something for you');
}
});
Here, we are instantiating DoYouLearnProgramming
by passing an anonymous function with two callback function as arguments like "we did with Promise object above", the corresponding callback will be executed based on the conditional.
The above code snippet will execute success
callback function, which set the this.resolve
property to "You will be a developer".
Capturing response
p.then(function(msg){
console.log(msg);
}).catch(function(msg){
console.log(msg);
})
Here, we are capturing the resolve
value using then
prototype method of DoYouLearnProgramming
object, like we did above with Promise
object.
This is my first article, please provide your feedbacks guys. Thank you
Posted on July 9, 2020
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.
Related
November 28, 2024