diff --git a/CHANGELOG.md b/CHANGELOG.md index b2669a962603..9bad25a3e271 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,7 @@ ## Changelog ##### Unreleased - Added a workaround of V8 deoptimization which causes serious performance degradation (~4x in my tests) of `Array#concat`, [#679](https://github.com/zloirock/core-js/issues/679) +- Added a workaround of V8 deoptimization which causes slightly performance degradation of `Promise`, [#679](https://github.com/zloirock/core-js/issues/679) - Added compat data for Chromium-based Edge ##### 3.3.4 - 2019.10.25 diff --git a/packages/core-js/modules/es.promise.js b/packages/core-js/modules/es.promise.js index 31d08ea14890..6505105e7b1a 100644 --- a/packages/core-js/modules/es.promise.js +++ b/packages/core-js/modules/es.promise.js @@ -50,20 +50,27 @@ var UNHANDLED = 2; var Internal, OwnPromiseCapability, PromiseWrapper, nativeThen; var FORCED = isForced(PROMISE, function () { - // correct subclassing with @@species support + if (typeof PromiseConstructor != 'function') return true; + // V8 6.6 (Node 10 and Chrome 66) have a bug with resolving custom thenables + // https://bugs.chromium.org/p/chromium/issues/detail?id=830565 + // We can't detect it synchronously, so just check versions + if (V8_VERSION === 66) return true; + // Unhandled rejections tracking support, NodeJS Promise without it fails @@species test + if (!IS_NODE && typeof PromiseRejectionEvent != 'function') return true; + // We need Promise#finally in the pure version for preventing prototype pollution + if (IS_PURE && !PromiseConstructor.prototype['finally']) return true; + // We can't use @@species feature detection in V8 since it causes + // deoptimization and performance degradation + // https://github.com/zloirock/core-js/issues/679 + if (V8_VERSION >= 51) return false; + // Detect correctness of subclassing with @@species support var promise = PromiseConstructor.resolve(1); - var empty = function () { /* empty */ }; - var FakePromise = (promise.constructor = {})[SPECIES] = function (exec) { - exec(empty, empty); + var FakePromise = function (exec) { + exec(function () { /* empty */ }, function () { /* empty */ }); }; - // unhandled rejections tracking support, NodeJS Promise without it fails @@species test - return !((IS_NODE || typeof PromiseRejectionEvent == 'function') - && (!IS_PURE || promise['finally']) - && promise.then(empty) instanceof FakePromise - // v8 6.6 (Node 10 and Chrome 66) have a bug with resolving custom thenables - // https://bugs.chromium.org/p/chromium/issues/detail?id=830565 - // we can't detect it synchronously, so just check versions - && V8_VERSION !== 66); + promise.constructor = {}; + promise.constructor[SPECIES] = FakePromise; + return !(promise.then(function () { /* empty */ }) instanceof FakePromise); }); var INCORRECT_ITERATION = FORCED || !checkCorrectnessOfIteration(function (iterable) {