Challenge 04: Promises
For this challenge, you'll update both the client and the server to use promises.
On the client, you will change the API methods to return promises instead accepting callbacks. Then update the api.METHOD()
calls to use promises.
On the server, you will update simDb
to use promises, we'll provide the code. Then update the queries to use promises instead of callbacks.
Update the server-side code
simDb.js
file with "promisified" versionUpdate the client-side code
api.js
methods to return a promise from $.ajax
To get started, you need to update the simDB
to use promises. Copy the Promisified simDB code to your /db/simDB.js
. The new version uses Node's promisify
utility to use promises instead of callbacks. Don't worry about the details, yet. We'll cover creating promises in a future challenge
notes.METHOD()
to use promisesYour first challenge to is to convert the notes.METHOD
queries from callbacks to promises. We'll help you get started by stepping thru the notes.find
so you can update the others on your own. Below is an example of the callback-style function followed by the promise-style equivalent.
Callback Style
notes.find(id, (err, item) => {
if (err) {
return next(err);
}
if (item) {
res.json(item);
} else {
next();
}
});
Promise Style
notes.find(id)
.then(item => {
if (item) {
res.json(item);
} else {
next();
}
})
.catch(err => {
next(err)
});
});
Notice, the callback is moved to the .then()
and the error check condition has been extracted and moved to the .catch()
.
Your challenge is to update the other queries (filter, update, create and delete) to use promises. As you work thru the challenge, verify your changes using Postman.
Currently, all the api.METHOD()
functions in api.js
on the client use callbacks. Your bonus challenge is to update api.js
and all the functions that call the API. Thankfully, as of jQuery 3.0, the $.ajax
returns a promise-like object which is fully Promises/A+ spec compliant - meaning they work the same as native Javascript Promises.
api.js
methods to return a promiseTo help you get started, we've provided a before and after example of the .search
method, see below.
Before: Callback Style
...
search: function (query, callback) {
$.ajax({
type: 'GET',
url: '/api/notes/',
dataType: 'json',
data: query,
success: callback
});
},
...
After: Promise Style
callback
parametersuccess
property from the $.AJAX
options objectreturn $.ajax({...
. ...
search: function (query) {
return $.ajax({
type: 'GET',
url: '/api/notes/',
dataType: 'json',
data: query
});
},
...
Before updating the other methods, you should verify your changes in a clean, standalone environment. Continually verifying your changes before proceeeding will help you become an efficient developer. It is the developer's equivalent to the carpenter's old adage "measure twice, cut once".
In the /public
folder, create a temporary HTML file named scratch.html
that loads jQuery and the /scripts/api.js
file Then, in <script>
tags, add the following function which test the api.search
method.
<script>
// test get all
api.search({})
.then(response => {
console.log(response)
});
// test get all with search term
api.search({searchTerm: 'cats'})
.then(response => {
console.log(response)
});
</script>
Alternatively, you could create a separate .js
file with the code and load in scratch.html
.
Start your server and load scratch.html
in your browser and check the console in Dev Tools. You should see the results from the API calls.
Your challenge is to update the other methods (details
, update
, create
and remove
) and verify them in the scratch.html
.
The extra bonus challenge is to update the api.METHOD
calls throughout the client-side app. The api.METHOD
calls use the callback style which you need to update to use promises. We'll help you with the first one.
Hint. To find all the occurrences, search for
api.
. That's "a-p-i DOT". Below is a list based on the code in the recent solution branch.
index.js
file, you should find api.search()
. Update the call to use promisesBefore: Callback style
api.search({}, response => {
store.notes = response;
noteful.render();
});
After: Promise style
api.search({})
.then(response => {
store.notes = response;
noteful.render();
});
Your turn!
In the noteful.js
file you will find the following methods. Update each to use promises. Remember to check your changes in Dev Tools
handleNoteItemClick()
method, update the api.details()
callhandleNoteSearchSubmit()
method, update the api.search()
callhandleNoteFormSubmit()
method, update the nested callbacks of api.update()
, api.create()
and api.search()
to use chained .then()
calls.handleNoteDeleteClick()
method, update the nested callbacks of api.remove()
and api.search()
to use chained .then()
calls.If you run into issues with converting the nested callbacks to promise chains, simplify! Go back to your scratch.html
file above and implement the solution in a clean, standalone environment. Once it is working, integrate it into the larger application. Below is a sample.
You can view an example solution and compare the differences between branches
Good Luck!