Basic use of promise

let p = new Promise((resolve, reject) = > {
    resolve()
})
p.then(() = > {}, () = > {})
Copy the code

Manual implementation of promise (without the then chain invocation part)

// Define three constants that represent the three states of promise
const PENDING = 'pending'
const FULFILLED = 'fulfilled'
const REJECTED = 'rejected'

class myPromise {
  constructor(executer) {
    this.status = PENDING // Current contract status
    this.reasson = null   // The reason for the current contract rejection
    this.res = null     // The value of the current contract
    executer(this.resolve, this.reject)  
  }
  // The arrow function is used because of execution problems with this
  // The promise is passed in as an executor function.
  // resolve is equivalent to calling the function directly, without any decoration. This executes window or undefined
  // The arrow function holds the this execution of the function definition, pointing to the currently declared Promise instance object as expected
  resolve = (res) = > {
    if(this.status == PENDING) {
      this.status = FULFILLED
      this.res = res
    }
  }
  reject = (reason) = > {
    if(this.status = PENDING) {
      this.status = REJECTED
      this.reason = reason
    }
  }
  then(onFulfilled, onRejected) {
    if(this.status == FULFILLED) {
      onFulfilled(this.res)
    } else if(this.status == REJECTED) {
      onRejected(this.reason)
    }
  }
}


let p = new myPromise((resolve, reject) = > {
  resolve(123)
})
p.then(res= > console.log(res), reject= > console.log('reject', reject))
Copy the code

Since the above implementation is synchronous, the result of the current contract is asynchronous, and the then is executed immediately, while the promise has not given the state yet

let p = new myPromise((resolve, reject) = > {
  setTimeout(() = > {
    resolve(123)},2000);
})
p.then(res= > console.log(res), reject= > console.log('reject', reject)) // Cannot print the result
Copy the code

When executing then, save the successful or failed callback, and execute the corresponding callback after the result is given

// const PENDING = 'pending'
// const FULFILLED = 'fulfilled'
// const REJECT = 'reject'
class MyPromise {
  constructor(executer) {
    this.status = PENDING // Current contract status
    this.value = null  // The result of the current contract
    this.reason = null // The reason for the rejection
    this.successCallbacks = []
    this.errorCallbacks = []
    executer(this.resolve, this.reject)
  }
  resolve = val= > {
    // Use the arrow function so that this points to the current Promise instance and not the whole world
    if(this.status === PENDING) {
      this.status = FULFILLED
      this.value = val
      // Execute the asynchronous callback successfully by iterating through all successful callback execution
      this.successCallbacks.forEach(fn= > fn())
    }
  }
  reject = val= > {
    if(this.status === PENDING) {
      this.status = REJECTED
      this.reason = val
      this.errorCallbacks.forEach(fn= > fn())
    }
  }
  then(onFulfilled, onRejected) {
    if(this.status === FULFILLED) {
      onFulfilled(this.value)
    } else if(this.status === REJECTED) {
      onRejected(this.reason)
    } else if(this.status === PENDING) {
      // If pending indicates that no resolution is pending, save all successful and unsuccessful callbacks
      this.successCallbacks.push(() = > {
        onFulfilled(this.value)
      })
      this.errorCallbacks.push(() = > {
        onRejected(this.reason)
      })
    }
  }
}

let m = new MyPromise(function(resolve, reject) {
  setTimeout(() = > {
      resolve(123)},2000);
})
m.then(res= > console.log(res)) // Successfully printed 123
Copy the code

So far, promise is only partially implemented, so I’ll leave it there.