This is the 5th day of my participation in the August More Text Challenge

Promise

  • The standardized feature in ES2015(ES6), Chinese name (tentative) “term contract”, is designed to provide a unified solution for asynchronous programming with more reasonable writing and stronger functions.

Synchronous and asynchronous

  • There are concepts of synchronization and asynchrony in JavaScript.
  • Common asynchronous tasks include events, timers, and Ajax
  • The synchronization task is alwayssequential, while asynchronous tasksExecution results are independent of writing order
    • For example, the end time of the timer depends on the delay time. Ajax response success time depends on the amount of data and network speed
  • Asynchronous tasks require callback functions for result processing.

conclusion

  • JavaScript has the concept of synchronous and asynchronous
  • Synchronous code sequential execution
  • Asynchronous code is sequential and needs to be handled through callback functions

Introduction of Promise

  • Question: What if there are multiple asynchronous tasks with dependencies?
  • The solution code is shown below, where the “callback hell” problem arises

Prmoise basis

  • Promise is an ES6 provided class that creates an instance object that refers to an (asynchronous) operation we need to perform.
  • Once created, the promise is in a “pending state” and the final result may be a “success state” or a “failure state.”
  • Features: The result cannot be changed after it is clear.
  • Back to the operation: then the corresponding operation is favorable for an Ajax request. When the request succeeds or fails, the corresponding “state” can be used to judge the execution result, and the corresponding operation can be carried out
  • Summary: The Promise object operates by triggering the corresponding callback function through a state change.

Use of Promise

  • The base is shown below

  • Step 1: Create an instance to store asynchronous operations
  • Step 2: Arguments are functions that are executed synchronously when the instance is created
  • Step 3: The function takes two arguments, both functions, that determine the state of the Promise object when called
    • Resolve (data) Specifies the result of successful delivery
    • Reject (Err) Error message when transmission fails
  • Note: Because the result of a Promise object cannot be changed once it is specified, only one of the two functions can be executed in logic.
const promise = new Promise(function (){
  // Pass successful, return 100
  resolve(100)})Copy the code
  • Step 4: When the state of the Promise object is determined, the corresponding callback functions are triggered for processing. These callback functions need to be specified through the methods of the Promise object
    • Handler function when then() succeeds
    • A handler for a catch() failure
  • Code demo
// Create a Promise instance
const promise = new Promise(function (){
  resolve(100)})// callback function processing
promise.then(function (value){
  console.log("It worked. The numbers are:",value)
}).catch (function (err){
  console.log("Failed. The data is:",err)
}
Copy the code

Promise exercise: Encapsulate Ajax functions

  • For a review of native Ajax, see the article Ajax Basics and Hand-wrapped Ajax functions

  • Native send Ajax step
    • 1. Create an object of type XMLHttpRequest
    • 2. Ready to send, open a link to a web address
    • 3. Perform the sending action
    • 4. Specify the XHR state change event handler
  • Concrete implementation code
function ajax (url) {
  return new Promise(function (resolve,reject) {
    Create an object of type XMLHttpRequest
    const xhr = new XMLHttpRequest()
    // Ready to send, open a link with a url
    xhr.open('GET',url)
    xhr.responseType = 'json'
    xhr.onload = function () {
      if(this.status === 200) {// Receives the response data, marks the status as success, and passes it to the callback processing in then
        resolve(this.response)
      }else {
        // Change the state on failure, passing an error message
        reject(new Error(this.statusText))
      }
    }
    // Perform the send action
    xhr.send()
  })
}

ajax(successUrl).then(function (res) {
  console.log(res)
}).catch(function (error) {
  console.log(error)
})
Copy the code
  • If only used in this way, more requests will still appear nesting problems, at this time to pay attention to the way to use, do not nest writing, but use the chain call Promise operation
// Error
ajax(url).then(function (res) {
  console.log(res)
  ajax(url).then(function (res) {
    console.log(res)
    ajax(url).then(function (res) {
      console.log(res)
  })
  })
})
Copy the code

Chain calls

  • The return value of the then() call is a new Promise object, and if an asynchronous operation is to be followed by the next asynchronous operation, this new Promise object should be used to avoid callback hell
  • Correct term
// Write it correctly
ajax(url)
  .then(function (res){
    console.log(1)
  })
  .then(function (res){
    console.log(2)
  })
  .then(function (res){
    console.log(3)})Copy the code
  • The return value of the then() call is a new Promise object, and if an asynchronous operation is to be followed by the next asynchronous operation, this new Promise object should be used to avoid callback hell
  • Correct term
// Write it correctly
ajax(url)
  .then(function (res){
    console.log(1)
  })
  .then(function (res){
    console.log(2)
  })
  .then(function (res){
    console.log(3)})Copy the code
  • Return in then() the return value that the Promise object will set to then()
ajax(url1)
  .then(function (res) {
    console.log(res,1)
    // Return the promise object to the next then()
    return ajax(url2)
  }).then(function (res) {
    console.log(res,2)
    return ajax(url3)
  }).then(function (res) {
    console.log(res,3)
    return ajax(url4)
  })
Copy the code
  • If a normal value is returned, it is wrapped in the default Promise object and passed to the THEN method, or undefined if not
ajax(url1)
  .then(function (res) {
    console.log(res,1)
    // Return the promise object to the next then()
    return ajax(url2)
  }).then(function (res) {
    console.log(res,2)
    // Returns: normal value
    return [1.2.3]
  }).then(function (res) {
    console.log(res,3) // output: [1,2,3],3
    return ajax(url4)
  })
Copy the code

conclusion

  • A Promise is essentially a callback function that defines the tasks that need to be performed when an asynchronous task ends, except that the callback is set through THEN (), which can be called chain-by-chain, avoiding layers of nested writing.

Async function

  • Promise solved the problem of asynchronous operation callback hell, but the function was written with a lot of callbacks, which, while not nested, were nowhere near as readable as synchronous code
  • In order to make asynchronous code writing more concise and readable, Async function (asynchronous function) is proposed in ES2017 to simplify the writing way of Promise and make the code format more close to synchronous code writing
  • Async is a new standard for asynchronous programming. It is a syntactic sugar used to improve asynchronous writing and is essentially a Promise object
  • Usage:
    • Set async keyword before any function to async function (async function)
    • Call the function that returns the Promise object within the async function and set await before the call
      • At this point, the return value of the call is await set to the data passed by resolve, which is the result of success
      • An error is reported with a try… Catch processing)
      • Note: await can only appear in async functions
  • Demo code
async function fn () {
  const data1 = await ajax(url)
  console.log(1,data1)
  const data2 = await ajax(url)
  console.log(2,data2)
}
fn()
Copy the code

Try… catch

  • For exception catching (error handling), when the program code is likely to error, you can try… Catch Catches exceptions
  • For robustness of the program, try… Catch to process async/await
  • Demo code
function ajax (url) {
  return new Promise(function (resolve, reject) {
    const xhr = new XMLHttpRequest()
    xhr.open('GET', url)
    xhr.responseType = 'json'
    xhr.onload = function () {
      if (this.status === 200) {
        resolve(this.response)
      } else {
        reject(new Error(this.statusText))
      } 
    }
    xhr.send()
  })
}

async function fn () {
  const data1 = await ajax(successUrl)
  console.log(1, data1)
  const data2 = await ajax(successUrl)
  console.log(2, data2)
// For example, to avoid subsequent code execution due to request 3 failure, try... Catch processing
  try {
    const data3 = await ajax(failUrl)
    console.log(3, data3)
  } catch (error) {
    console.log('Remedial treatment')}// Subsequent requests can continue even if request 3 fails.
  const data4 = await ajax(successUrl)
  console.log(4, data4)
}
fn()
Copy the code

expand

  • Promise solves the “callback hell” problem.
  • Interview question: What is Promise?
    • Asynchronous operations have a “callback hell” problem
    • When it occurs: A “callback hell” situation occurs when there are multiple asynchronous calls and dependencies between asynchronous calls
    • To solve this problem, ECMAScript2015(ES6) proposed the Promise syntax specifically for asynchronous operations.
    • I want to make asynchronous invocation more elegant with promises.
  • Async and await
  • Asynchronous processing, synchronous writing
  • I recommend reading async and await

An unpredictable try catch

  • It allows you to fix what went wrong in the program.