118 lines
		
	
	
		
			3.6 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
		
		
			
		
	
	
			118 lines
		
	
	
		
			3.6 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
| 
								 | 
							
								---
							 | 
						||
| 
								 | 
							
								title: Await Promises
							 | 
						||
| 
								 | 
							
								---
							 | 
						||
| 
								 | 
							
								## Await Promises
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								The `async` / `await` <a href='https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators' target='_blank' rel='nofollow'>operators</a> make it easier to implement many async Promises. They also allow engineers to write clearer, more succinct, testable code.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								To understand this subject, you should have a solid understanding of how <a href='https://guide.freecodecamp.org/javascript/promises' target='_blank' rel='nofollow'>Promises</a> work.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								---
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								## Basic Syntax
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								``` javascript
							 | 
						||
| 
								 | 
							
								function slowlyResolvedPromiseFunc(string) { 
							 | 
						||
| 
								 | 
							
								  return new Promise(resolve => {
							 | 
						||
| 
								 | 
							
								    setTimeout(() => {
							 | 
						||
| 
								 | 
							
								      resolve(string);
							 | 
						||
| 
								 | 
							
								    }, 5000);
							 | 
						||
| 
								 | 
							
								  });
							 | 
						||
| 
								 | 
							
								}
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								async function doIt() {
							 | 
						||
| 
								 | 
							
								  const myPromise = await slowlyResolvedPromiseFunc("foo");
							 | 
						||
| 
								 | 
							
								  console.log(myPromise); // "foo"
							 | 
						||
| 
								 | 
							
								}
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								doIt();
							 | 
						||
| 
								 | 
							
								```
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								There are a few things to note:
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								* The function that encompasses the `await` declaration must include the `async` operator. This will tell the JS interpreter that it must wait until the Promise is resolved or rejected.
							 | 
						||
| 
								 | 
							
								* The `await` operator must be inline, during the const declaration.
							 | 
						||
| 
								 | 
							
								* This works for `reject` as well as `resolve`.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								---
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								## Nested Promises vs. `Async` / `Await`
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								Implementing a single Promise is pretty straightforward. In contrast, Chained Promises or the creation of a dependency pattern may produce "spaghetti code".
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								The following examples assume that the <a href='https://github.com/request/request-promise' target='_blank' rel='nofollow'>`request-promise`</a> library is available as `rp`.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								### Chained/Nested Promises
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								``` javascript
							 | 
						||
| 
								 | 
							
								// First Promise
							 | 
						||
| 
								 | 
							
								const fooPromise = rp("http://domain.com/foo");
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								fooPromise.then(resultFoo => {
							 | 
						||
| 
								 | 
							
								    // Must wait for "foo" to resolve
							 | 
						||
| 
								 | 
							
								    console.log(resultFoo);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    const barPromise = rp("http://domain.com/bar");
							 | 
						||
| 
								 | 
							
								    const bazPromise = rp("http://domain.com/baz");
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    return Promise.all([barPromise, bazPromise]);
							 | 
						||
| 
								 | 
							
								}).then(resultArr => {
							 | 
						||
| 
								 | 
							
								    // Handle "bar" and "baz" resolutions here
							 | 
						||
| 
								 | 
							
								    console.log(resultArr[0]);
							 | 
						||
| 
								 | 
							
								    console.log(resultArr[1]);
							 | 
						||
| 
								 | 
							
								});
							 | 
						||
| 
								 | 
							
								```
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								### `async` and `await` Promises
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								``` javascript
							 | 
						||
| 
								 | 
							
								// Wrap everything in an async function
							 | 
						||
| 
								 | 
							
								async function doItAll() {
							 | 
						||
| 
								 | 
							
								    // Grab data from "foo" endpoint, but wait for resolution
							 | 
						||
| 
								 | 
							
								    console.log(await rp("http://domain.com/foo"));
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    // Concurrently kick off the next two async calls,
							 | 
						||
| 
								 | 
							
								    // don't wait for "bar" to kick off "baz"
							 | 
						||
| 
								 | 
							
								    const barPromise = rp("http://domain.com/bar");
							 | 
						||
| 
								 | 
							
								    const bazPromise = rp("http://domain.com/baz");
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    // After both are concurrently kicked off, wait for both
							 | 
						||
| 
								 | 
							
								    const barResponse = await barPromise;
							 | 
						||
| 
								 | 
							
								    const bazResponse = await bazPromise;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								    console.log(barResponse);
							 | 
						||
| 
								 | 
							
								    console.log(bazResponse);
							 | 
						||
| 
								 | 
							
								}
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								// Finally, invoke the async function
							 | 
						||
| 
								 | 
							
								doItAll().then(() => console.log('Done!'));
							 | 
						||
| 
								 | 
							
								```
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								The advantages of using `async` and `await` should be clear. This code is more readable, modular, and testable.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								It's fair to note that even though there is an added sense of concurrency, the underlying computational process is the same as the previous example.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								---
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								## Handling Errors / Rejection
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								A basic try-catch block handles a rejected Promise.
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								``` javascript
							 | 
						||
| 
								 | 
							
								async function errorExample() {
							 | 
						||
| 
								 | 
							
								  try {
							 | 
						||
| 
								 | 
							
								    const rejectedPromise = await Promise.reject("Oh-oh!");
							 | 
						||
| 
								 | 
							
								  } catch (error) {
							 | 
						||
| 
								 | 
							
								    console.log(error); // "Uh-oh!"
							 | 
						||
| 
								 | 
							
								  }
							 | 
						||
| 
								 | 
							
								}
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								errorExample();
							 | 
						||
| 
								 | 
							
								```
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								---
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								#### More Information:
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								* `await` Operator <a href='https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/await' target='_blank' rel='nofollow'>MDN Docs</a>
							 | 
						||
| 
								 | 
							
								* `async` Function Operator <a href='https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/async_function' target='_blank' rel='nofollow'>MDN Docs</a>
							 |