前端手写(四)——手写promise系列

x33g5p2x  于2022-03-28 转载在 其他  
字(2.9k)|赞(0)|评价(0)|浏览(405)

一、写在前面
之前就已经手写过promise,本次手写就是为了加强记忆。
二、手写源码

  1. // 定义三个常量
  2. const PROMISE_STATUS_FULFILLED = 'fulfilled'
  3. const PROMISE_STATUS_PENDDING = 'pendding'
  4. const PROMISE_STATUS_REJECTED = 'rejected'
  5. function execFunc(func, value, resolve, reject) {
  6. try {
  7. let res = func(value)
  8. resolve(res)
  9. } catch (err) {
  10. reject(err)
  11. }
  12. }
  13. class MyPromise {
  14. constructor(exacutor) {
  15. this.status = PROMISE_STATUS_PENDDING
  16. this.reason = undefined
  17. this.value = undefined
  18. this.onFulfilledFns = []
  19. this.onRejectedFns = []
  20. const resolve = (value) => {
  21. if (this.status === PROMISE_STATUS_PENDDING) {
  22. queueMicrotask(() => {
  23. if (this.status !== PROMISE_STATUS_PENDDING) return
  24. this.value = value
  25. this.status = PROMISE_STATUS_FULFILLED
  26. this.onFulfilledFns.forEach(fn => fn(this.value))
  27. })
  28. }
  29. }
  30. const reject = (reason) => {
  31. if (this.status === PROMISE_STATUS_PENDDING) {
  32. queueMicrotask(() => {
  33. if (this.status !== PROMISE_STATUS_PENDDING) return
  34. this.reason = reason
  35. this.status = PROMISE_STATUS_REJECTED
  36. this.onRejectedFns.forEach(fn => fn(this.reason))
  37. })
  38. }
  39. }
  40. exacutor(resolve, reject)
  41. }
  42. then(onFulfilled, onRejected) {
  43. onRejected = onRejected || (err => {
  44. throw err
  45. })
  46. return new MyPromise((resolve, reject) => {
  47. if (this.status === PROMISE_STATUS_FULFILLED) {
  48. if (onFulfilled) execFunc(onFulfilled, this.value, resolve, reject)
  49. }
  50. if (this.status === PROMISE_STATUS_REJECTED) {
  51. if (onRejected) execFunc(onRejected, this.reason, resolve, reject)
  52. }
  53. if (this.status === PROMISE_STATUS_PENDDING) {
  54. if (onFulfilled) this.onFulfilledFns.push(() => {
  55. execFunc(onFulfilled, this.value, resolve, reject)
  56. })
  57. if (onRejected) this.onRejectedFns.push(() => {
  58. execFunc(onRejected, this.reason, resolve, reject)
  59. })
  60. }
  61. })
  62. }
  63. // catch方法
  64. catch (onRejected) {
  65. return this.then(undefined, onRejected)
  66. }
  67. // finally方法
  68. finnally(onFinial) {
  69. this.then(() => {
  70. onFinial()
  71. }, () => {
  72. onFinial()
  73. })
  74. }
  75. // 实现MyPromise.resolve()方法
  76. static resolve(value) {
  77. return new MyPromise((resolve, reject) => {
  78. resolve(value)
  79. })
  80. }
  81. // 实现MyPromise.reject()方法
  82. static reject(reason) {
  83. return new MyPromise((resolve, reject) => {
  84. reject(reason)
  85. })
  86. }
  87. // 实现MyPromise.all()方法
  88. static all(promises) {
  89. return new MyPromise((resolve, reject) => {
  90. let arr = []
  91. promises.forEach(item => {
  92. item.then(res => {
  93. arr.push(res)
  94. if (arr.length === promises.length) {
  95. resolve(arr)
  96. }
  97. }, err => {
  98. reject(err)
  99. })
  100. })
  101. })
  102. }
  103. // 实现MyPromise.allSettle()
  104. static allsettle(promises) {
  105. return new MyPromise((resolve, reject) => {
  106. let arr = []
  107. promises.forEach(item => {
  108. item.then(res => {
  109. arr.push({
  110. value: res,
  111. status: PROMISE_STATUS_FULFILLED
  112. })
  113. if(arr.length === promises.length) {
  114. resolve(arr)
  115. }
  116. }, err => {
  117. arr.push({
  118. value: err,
  119. status: PROMISE_STATUS_REJECTED
  120. })
  121. if(arr.length === promises.length) {
  122. resolve(arr)
  123. }
  124. })
  125. })
  126. })
  127. }
  128. // 实现MyPromise.race()方法
  129. static race(promises) {
  130. return new MyPromise((resolve, reject) => {
  131. promises.forEach(item => {
  132. item.then(res => {
  133. resolve(res)
  134. }, err => {
  135. reject(err)
  136. })
  137. })
  138. })
  139. }
  140. // 实现MyPromise.any()方法
  141. static any(promises) {
  142. return new MyPromise((resolve, reject) => {
  143. let arr = []
  144. promises.forEach(item => {
  145. item.then(res => {
  146. resolve(res)
  147. }, err => {
  148. arr.push(err)
  149. if(arr.length === promises.length) {
  150. reject(new AggregateError(arr))
  151. }
  152. })
  153. })
  154. })
  155. }
  156. }

相关文章