fix-regexp-well-known-symbol-logic.js 2.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374
  1. 'use strict';
  2. // TODO: Remove from `core-js@4` since it's moved to entry points
  3. require('../modules/es.regexp.exec');
  4. var uncurryThis = require('../internals/function-uncurry-this');
  5. var redefine = require('../internals/redefine');
  6. var regexpExec = require('../internals/regexp-exec');
  7. var fails = require('../internals/fails');
  8. var wellKnownSymbol = require('../internals/well-known-symbol');
  9. var createNonEnumerableProperty = require('../internals/create-non-enumerable-property');
  10. var SPECIES = wellKnownSymbol('species');
  11. var RegExpPrototype = RegExp.prototype;
  12. module.exports = function (KEY, exec, FORCED, SHAM) {
  13. var SYMBOL = wellKnownSymbol(KEY);
  14. var DELEGATES_TO_SYMBOL = !fails(function () {
  15. // String methods call symbol-named RegEp methods
  16. var O = {};
  17. O[SYMBOL] = function () { return 7; };
  18. return ''[KEY](O) != 7;
  19. });
  20. var DELEGATES_TO_EXEC = DELEGATES_TO_SYMBOL && !fails(function () {
  21. // Symbol-named RegExp methods call .exec
  22. var execCalled = false;
  23. var re = /a/;
  24. if (KEY === 'split') {
  25. // We can't use real regex here since it causes deoptimization
  26. // and serious performance degradation in V8
  27. // https://github.com/zloirock/core-js/issues/306
  28. re = {};
  29. // RegExp[@@split] doesn't call the regex's exec method, but first creates
  30. // a new one. We need to return the patched regex when creating the new one.
  31. re.constructor = {};
  32. re.constructor[SPECIES] = function () { return re; };
  33. re.flags = '';
  34. re[SYMBOL] = /./[SYMBOL];
  35. }
  36. re.exec = function () { execCalled = true; return null; };
  37. re[SYMBOL]('');
  38. return !execCalled;
  39. });
  40. if (
  41. !DELEGATES_TO_SYMBOL ||
  42. !DELEGATES_TO_EXEC ||
  43. FORCED
  44. ) {
  45. var uncurriedNativeRegExpMethod = uncurryThis(/./[SYMBOL]);
  46. var methods = exec(SYMBOL, ''[KEY], function (nativeMethod, regexp, str, arg2, forceStringMethod) {
  47. var uncurriedNativeMethod = uncurryThis(nativeMethod);
  48. var $exec = regexp.exec;
  49. if ($exec === regexpExec || $exec === RegExpPrototype.exec) {
  50. if (DELEGATES_TO_SYMBOL && !forceStringMethod) {
  51. // The native String method already delegates to @@method (this
  52. // polyfilled function), leasing to infinite recursion.
  53. // We avoid it by directly calling the native @@method method.
  54. return { done: true, value: uncurriedNativeRegExpMethod(regexp, str, arg2) };
  55. }
  56. return { done: true, value: uncurriedNativeMethod(str, regexp, arg2) };
  57. }
  58. return { done: false };
  59. });
  60. redefine(String.prototype, KEY, methods[0]);
  61. redefine(RegExpPrototype, SYMBOL, methods[1]);
  62. }
  63. if (SHAM) createNonEnumerableProperty(RegExpPrototype[SYMBOL], 'sham', true);
  64. };