Following on from the promiseA+ rip-off implementation, promise has a few syntactic sugar implementations outside of the spec
catch finally resolve reject race all
The implementation code
catch
MyPromise.prototype.catch = function (onRejected) {
return this.then(null, onRejected)
}
Copy the code
The test code
new MyPromise((resolve, reject) = > {
reject('err')
}).catch((reason) = > {
console.log(reason) // err
return 'data'
}).then((value) = > {
console.log(value) // data
})
Copy the code
resolve
MyPromise.resolve = (data) = > {
// If data is a promise, return it directly
if (data instanceof MyPromise) {
return data
} else {
return new MyPromise(resolve= > {
resolve(data)
})
}
}
Copy the code
The test code
MyPromise.resolve(2).then((data) = > {
console.log(data) / / 2
})
MyPromise.resolve(
new MyPromise((resolve, reject) = > {
reject(5)
})
).catch((data) = > {
console.log(data) / / 5
})
Copy the code
reject
// As opposed to promise. resolve, reject directly
MyPromise.reject = (reason) = > {
return new MyPromise((resolve, reject) = > {
reject(reason)
})
}
Copy the code
The test code
MyPromise.reject(2).catch((reason) = > {
console.log(reason) / / 2
})
Copy the code
finally
MyPromise.prototype.finally = function (callback) {
return this.then((value) = > {
// callback has no arguments.
// If the callback returns a PROMISE, it waits for the promise to execute
return MyPromise.resolve(callback()).then((a)= > {
// Finally keeps the promise state and value
return value
})
}, (reason) => {
return MyPromise.resolve(callback()).then((a)= > {
// Finally keeps the promise state and value
throw reason
})
})
}
Copy the code
The test code
MyPromise.resolve(2).finally((value) = > {
console.log(value) // undefined
}).then((value) = > {
console.log(value) / / 2
})
MyPromise.reject(2).finally((reason) = > {
console.log(reason) // undefined
}).catch((reason) = > {
console.log(reason) / / 2
})
MyPromise.resolve(2).finally((value) = > {
return new MyPromise((resolve) = > {
setTimeout((a)= > {
resolve(100)},1000)
})
}).then((value) = > {
console.log(value) / / 100
})
Copy the code
all
MyPromise.all = (paramList) = > {
const len = paramList.length
const result = []
let count = 0
return new MyPromise((resolve, reject) = > {
// The length of the argument is 0
if (len === 0) resolve(result)
paramList.forEach((param, index) = > {
// If the array element is not a promise, it is wrapped as a promise
MyPromise.resolve(param).then((value) = > {
count++
result[index] = value
if (count === len) {
resolve(result)
}
}, (reason) => {
reject(reason)
})
})
})
}
Copy the code
The test code
const p1 = new MyPromise((resolve) = > {
setTimeout((a)= > {
resolve(3)},2000)})const p2 = new MyPromise((resolve) = > {
setTimeout((a)= > {
resolve(4)},1000)})const p3 = new MyPromise((resolve, reject) = > {
setTimeout((a)= > {
reject(5)},1000)
})
MyPromise.all([
1.2, p1, p2
]).then((value) = > {
console.log(value) // [1, 2, 3, 4]
})
MyPromise.all([
1.2, p1, p2, p3
]).catch((reason) = > {
console.log(reason) / / 5
})
MyPromise.all([]).then((value) = > {
console.log(value) / / []
})
Copy the code
race
MyPromise.race = (paramList) = > {
return new MyPromise((resolve, reject) = > {
// An empty array is kept in wait state
if (paramList.length === 0) return
paramList.forEach((param) = > {
Promise.resolve(param).then((value) = > {
resolve(value)
}, (reason) => {
reject(reason)
})
})
})
}
Copy the code
The test code
const p1 = new MyPromise((resolve) = > {
setTimeout((a)= > {
resolve(1)},1000)})const p2 = new MyPromise((resolve) = > {
setTimeout((a)= > {
resolve(2)},2000)})const p3 = new MyPromise((resolve, reject) = > {
setTimeout((a)= > {
reject(3)},500)
})
MyPromise.race([]).then(value= > {
console.log(value)
}, reason => {
console.log(reason)
})
MyPromise.race([1.2]).then(value= > {
console.log(value) / / 1
}, reason => {
console.log(reason)
})
MyPromise.race([p1, 4]).then(value= > {
console.log(value) / / 4
}, reason => {
console.log(reason)
})
MyPromise.race([p1, p2]).then(value= > {
console.log(value) / / 1
}, reason => {
console.log(reason)
})
MyPromise.race([p1, p3]).then(value= > {
console.log(value)
}, reason => {
console.log(reason) / / 3
})
Copy the code
reference
-
proposal-promise-finally
-
Source code implementation of Promise (perfect compliance with the Promise/A+ specification)
-
Hand-write A Promise/A+ that passes the official 872 test cases flawlessly
Welcome to the front end learning punch group learning ~ 516913974