rollup 2.75.3 → 2.75.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,7 +1,7 @@
1
1
  /*
2
2
  @license
3
- Rollup.js v2.75.3
4
- Sun, 29 May 2022 14:46:24 GMT - commit 279581594d642307218126f20092aaf822084d6a
3
+ Rollup.js v2.75.6
4
+ Tue, 07 Jun 2022 14:42:22 GMT - commit 0ab16cc04b7d6dfe5bd14340ba7448085a379e25
5
5
 
6
6
  https://github.com/rollup/rollup
7
7
 
@@ -27,7 +27,7 @@ function _interopNamespaceDefault(e) {
27
27
  return n;
28
28
  }
29
29
 
30
- var version$1 = "2.75.3";
30
+ var version$1 = "2.75.6";
31
31
 
32
32
  function ensureArray$1(items) {
33
33
  if (Array.isArray(items)) {
@@ -2228,8 +2228,8 @@ class ExpressionEntity {
2228
2228
  this.included = false;
2229
2229
  }
2230
2230
  deoptimizePath(_path) { }
2231
- deoptimizeThisOnEventAtPath(_event, _path, thisParameter, _recursionTracker) {
2232
- thisParameter.deoptimizePath(UNKNOWN_PATH);
2231
+ deoptimizeThisOnInteractionAtPath({ thisArg }, _path, _recursionTracker) {
2232
+ thisArg.deoptimizePath(UNKNOWN_PATH);
2233
2233
  }
2234
2234
  /**
2235
2235
  * If possible it returns a stringifyable literal value for this node that can be used
@@ -2239,16 +2239,10 @@ class ExpressionEntity {
2239
2239
  getLiteralValueAtPath(_path, _recursionTracker, _origin) {
2240
2240
  return UnknownValue;
2241
2241
  }
2242
- getReturnExpressionWhenCalledAtPath(_path, _callOptions, _recursionTracker, _origin) {
2242
+ getReturnExpressionWhenCalledAtPath(_path, _interaction, _recursionTracker, _origin) {
2243
2243
  return UNKNOWN_EXPRESSION;
2244
2244
  }
2245
- hasEffectsWhenAccessedAtPath(_path, _context) {
2246
- return true;
2247
- }
2248
- hasEffectsWhenAssignedAtPath(_path, _context) {
2249
- return true;
2250
- }
2251
- hasEffectsWhenCalledAtPath(_path, _callOptions, _context) {
2245
+ hasEffectsOnInteractionAtPath(_path, _interaction, _context) {
2252
2246
  return true;
2253
2247
  }
2254
2248
  include(_context, _includeChildrenRecursively, _options) {
@@ -2266,6 +2260,30 @@ class ExpressionEntity {
2266
2260
  const UNKNOWN_EXPRESSION = new (class UnknownExpression extends ExpressionEntity {
2267
2261
  })();
2268
2262
 
2263
+ const INTERACTION_ACCESSED = 0;
2264
+ const INTERACTION_ASSIGNED = 1;
2265
+ const INTERACTION_CALLED = 2;
2266
+ const NODE_INTERACTION_UNKNOWN_ACCESS = {
2267
+ thisArg: null,
2268
+ type: INTERACTION_ACCESSED
2269
+ };
2270
+ const UNKNOWN_ARG = [UNKNOWN_EXPRESSION];
2271
+ const NODE_INTERACTION_UNKNOWN_ASSIGNMENT = {
2272
+ args: UNKNOWN_ARG,
2273
+ thisArg: null,
2274
+ type: INTERACTION_ASSIGNED
2275
+ };
2276
+ const NO_ARGS = [];
2277
+ // While this is technically a call without arguments, we can compare against
2278
+ // this reference in places where precise values or thisArg would make a
2279
+ // difference
2280
+ const NODE_INTERACTION_UNKNOWN_CALL = {
2281
+ args: NO_ARGS,
2282
+ thisArg: null,
2283
+ type: INTERACTION_CALLED,
2284
+ withNew: false
2285
+ };
2286
+
2269
2287
  class Variable extends ExpressionEntity {
2270
2288
  constructor(name) {
2271
2289
  super();
@@ -2290,8 +2308,8 @@ class Variable extends ExpressionEntity {
2290
2308
  const name = this.renderName || this.name;
2291
2309
  return this.renderBaseName ? `${this.renderBaseName}${getPropertyAccess(name)}` : name;
2292
2310
  }
2293
- hasEffectsWhenAccessedAtPath(path, _context) {
2294
- return path.length > 0;
2311
+ hasEffectsOnInteractionAtPath(path, { type }, _context) {
2312
+ return type !== INTERACTION_ACCESSED || path.length > 0;
2295
2313
  }
2296
2314
  /**
2297
2315
  * Marks this variable as being part of the bundle, which is usually the case when one of
@@ -2322,8 +2340,8 @@ class ExternalVariable extends Variable {
2322
2340
  this.module.suggestName(identifier.name);
2323
2341
  }
2324
2342
  }
2325
- hasEffectsWhenAccessedAtPath(path) {
2326
- return path.length > (this.isNamespace ? 1 : 0);
2343
+ hasEffectsOnInteractionAtPath(path, { type }) {
2344
+ return type !== INTERACTION_ACCESSED || path.length > (this.isNamespace ? 1 : 0);
2327
2345
  }
2328
2346
  include() {
2329
2347
  if (!this.included) {
@@ -4710,8 +4728,6 @@ function createHasEffectsContext() {
4710
4728
  };
4711
4729
  }
4712
4730
 
4713
- const NO_ARGS = [];
4714
-
4715
4731
  function assembleMemberDescriptions(memberDescriptions, inheritedDescriptions = null) {
4716
4732
  return Object.create(inheritedDescriptions, memberDescriptions);
4717
4733
  }
@@ -4733,12 +4749,12 @@ const UNKNOWN_LITERAL_BOOLEAN = new (class UnknownBoolean extends ExpressionEnti
4733
4749
  }
4734
4750
  return UNKNOWN_EXPRESSION;
4735
4751
  }
4736
- hasEffectsWhenAccessedAtPath(path) {
4737
- return path.length > 1;
4738
- }
4739
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
4740
- if (path.length === 1) {
4741
- return hasMemberEffectWhenCalled(literalBooleanMembers, path[0], callOptions, context);
4752
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
4753
+ if (interaction.type === INTERACTION_ACCESSED) {
4754
+ return path.length > 1;
4755
+ }
4756
+ if (interaction.type === INTERACTION_CALLED && path.length === 1) {
4757
+ return hasMemberEffectWhenCalled(literalBooleanMembers, path[0], interaction, context);
4742
4758
  }
4743
4759
  return true;
4744
4760
  }
@@ -4756,12 +4772,12 @@ const UNKNOWN_LITERAL_NUMBER = new (class UnknownNumber extends ExpressionEntity
4756
4772
  }
4757
4773
  return UNKNOWN_EXPRESSION;
4758
4774
  }
4759
- hasEffectsWhenAccessedAtPath(path) {
4760
- return path.length > 1;
4761
- }
4762
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
4763
- if (path.length === 1) {
4764
- return hasMemberEffectWhenCalled(literalNumberMembers, path[0], callOptions, context);
4775
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
4776
+ if (interaction.type === INTERACTION_ACCESSED) {
4777
+ return path.length > 1;
4778
+ }
4779
+ if (interaction.type === INTERACTION_CALLED && path.length === 1) {
4780
+ return hasMemberEffectWhenCalled(literalNumberMembers, path[0], interaction, context);
4765
4781
  }
4766
4782
  return true;
4767
4783
  }
@@ -4779,12 +4795,12 @@ const UNKNOWN_LITERAL_STRING = new (class UnknownString extends ExpressionEntity
4779
4795
  }
4780
4796
  return UNKNOWN_EXPRESSION;
4781
4797
  }
4782
- hasEffectsWhenAccessedAtPath(path) {
4783
- return path.length > 1;
4784
- }
4785
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
4786
- if (path.length === 1) {
4787
- return hasMemberEffectWhenCalled(literalStringMembers, path[0], callOptions, context);
4798
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
4799
+ if (interaction.type === INTERACTION_ACCESSED) {
4800
+ return path.length > 1;
4801
+ }
4802
+ if (interaction.type === INTERACTION_CALLED && path.length === 1) {
4803
+ return hasMemberEffectWhenCalled(literalStringMembers, path[0], interaction, context);
4788
4804
  }
4789
4805
  return true;
4790
4806
  }
@@ -4797,17 +4813,13 @@ const returnsString = {
4797
4813
  };
4798
4814
  const stringReplace = {
4799
4815
  value: {
4800
- hasEffectsWhenCalled(callOptions, context) {
4801
- const arg1 = callOptions.args[1];
4802
- return (callOptions.args.length < 2 ||
4816
+ hasEffectsWhenCalled({ args }, context) {
4817
+ const arg1 = args[1];
4818
+ return (args.length < 2 ||
4803
4819
  (typeof arg1.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, {
4804
4820
  deoptimizeCache() { }
4805
4821
  }) === 'symbol' &&
4806
- arg1.hasEffectsWhenCalledAtPath(EMPTY_PATH, {
4807
- args: NO_ARGS,
4808
- thisParam: null,
4809
- withNew: false
4810
- }, context)));
4822
+ arg1.hasEffectsOnInteractionAtPath(EMPTY_PATH, NODE_INTERACTION_UNKNOWN_CALL, context)));
4811
4823
  },
4812
4824
  returns: UNKNOWN_LITERAL_STRING
4813
4825
  }
@@ -4891,12 +4903,12 @@ function getLiteralMembersForValue(value) {
4891
4903
  }
4892
4904
  return Object.create(null);
4893
4905
  }
4894
- function hasMemberEffectWhenCalled(members, memberName, callOptions, context) {
4906
+ function hasMemberEffectWhenCalled(members, memberName, interaction, context) {
4895
4907
  var _a, _b;
4896
4908
  if (typeof memberName !== 'string' || !members[memberName]) {
4897
4909
  return true;
4898
4910
  }
4899
- return ((_b = (_a = members[memberName]).hasEffectsWhenCalled) === null || _b === void 0 ? void 0 : _b.call(_a, callOptions, context)) || false;
4911
+ return ((_b = (_a = members[memberName]).hasEffectsWhenCalled) === null || _b === void 0 ? void 0 : _b.call(_a, interaction, context)) || false;
4900
4912
  }
4901
4913
  function getMemberReturnExpressionWhenCalled(members, memberName) {
4902
4914
  if (typeof memberName !== 'string' || !members[memberName])
@@ -5335,6 +5347,13 @@ const INCLUDE_PARAMETERS = 'variables';
5335
5347
  class NodeBase extends ExpressionEntity {
5336
5348
  constructor(esTreeNode, parent, parentScope) {
5337
5349
  super();
5350
+ /**
5351
+ * Nodes can apply custom deoptimizations once they become part of the
5352
+ * executed code. To do this, they must initialize this as false, implement
5353
+ * applyDeoptimizations and call this from include and hasEffects if they have
5354
+ * custom handlers
5355
+ */
5356
+ this.deoptimized = false;
5338
5357
  this.esTreeNode = esTreeNode;
5339
5358
  this.keys = keys[esTreeNode.type] || getAndCreateKeys(esTreeNode);
5340
5359
  this.parent = parent;
@@ -5372,7 +5391,7 @@ class NodeBase extends ExpressionEntity {
5372
5391
  this.scope = parentScope;
5373
5392
  }
5374
5393
  hasEffects(context) {
5375
- if (this.deoptimized === false)
5394
+ if (!this.deoptimized)
5376
5395
  this.applyDeoptimizations();
5377
5396
  for (const key of this.keys) {
5378
5397
  const value = this[key];
@@ -5389,8 +5408,12 @@ class NodeBase extends ExpressionEntity {
5389
5408
  }
5390
5409
  return false;
5391
5410
  }
5411
+ hasEffectsAsAssignmentTarget(context, _checkAccess) {
5412
+ return (this.hasEffects(context) ||
5413
+ this.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.assignmentInteraction, context));
5414
+ }
5392
5415
  include(context, includeChildrenRecursively, _options) {
5393
- if (this.deoptimized === false)
5416
+ if (!this.deoptimized)
5394
5417
  this.applyDeoptimizations();
5395
5418
  this.included = true;
5396
5419
  for (const key of this.keys) {
@@ -5407,6 +5430,9 @@ class NodeBase extends ExpressionEntity {
5407
5430
  }
5408
5431
  }
5409
5432
  }
5433
+ includeAsAssignmentTarget(context, includeChildrenRecursively, _deoptimizeAccess) {
5434
+ this.include(context, includeChildrenRecursively);
5435
+ }
5410
5436
  /**
5411
5437
  * Override to perform special initialisation steps after the scope is initialised
5412
5438
  */
@@ -5461,6 +5487,9 @@ class NodeBase extends ExpressionEntity {
5461
5487
  }
5462
5488
  }
5463
5489
  }
5490
+ setAssignedValue(value) {
5491
+ this.assignmentInteraction = { args: [value], thisArg: null, type: INTERACTION_ASSIGNED };
5492
+ }
5464
5493
  shouldBeIncluded(context) {
5465
5494
  return this.included || (!context.brokenFlow && this.hasEffects(createHasEffectsContext()));
5466
5495
  }
@@ -5489,13 +5518,9 @@ class NodeBase extends ExpressionEntity {
5489
5518
  }
5490
5519
 
5491
5520
  class SpreadElement extends NodeBase {
5492
- constructor() {
5493
- super(...arguments);
5494
- this.deoptimized = false;
5495
- }
5496
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
5521
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
5497
5522
  if (path.length > 0) {
5498
- this.argument.deoptimizeThisOnEventAtPath(event, [UnknownKey, ...path], thisParameter, recursionTracker);
5523
+ this.argument.deoptimizeThisOnInteractionAtPath(interaction, [UnknownKey, ...path], recursionTracker);
5499
5524
  }
5500
5525
  }
5501
5526
  hasEffects(context) {
@@ -5506,7 +5531,7 @@ class SpreadElement extends NodeBase {
5506
5531
  return (this.argument.hasEffects(context) ||
5507
5532
  (propertyReadSideEffects &&
5508
5533
  (propertyReadSideEffects === 'always' ||
5509
- this.argument.hasEffectsWhenAccessedAtPath(UNKNOWN_PATH, context))));
5534
+ this.argument.hasEffectsOnInteractionAtPath(UNKNOWN_PATH, NODE_INTERACTION_UNKNOWN_ACCESS, context))));
5510
5535
  }
5511
5536
  applyDeoptimizations() {
5512
5537
  this.deoptimized = true;
@@ -5517,53 +5542,43 @@ class SpreadElement extends NodeBase {
5517
5542
  }
5518
5543
  }
5519
5544
 
5520
- const EVENT_ACCESSED = 0;
5521
- const EVENT_ASSIGNED = 1;
5522
- const EVENT_CALLED = 2;
5523
-
5524
5545
  class Method extends ExpressionEntity {
5525
5546
  constructor(description) {
5526
5547
  super();
5527
5548
  this.description = description;
5528
5549
  }
5529
- deoptimizeThisOnEventAtPath(event, path, thisParameter) {
5530
- if (event === EVENT_CALLED && path.length === 0 && this.description.mutatesSelfAsArray) {
5531
- thisParameter.deoptimizePath(UNKNOWN_INTEGER_PATH);
5550
+ deoptimizeThisOnInteractionAtPath({ type, thisArg }, path) {
5551
+ if (type === INTERACTION_CALLED && path.length === 0 && this.description.mutatesSelfAsArray) {
5552
+ thisArg.deoptimizePath(UNKNOWN_INTEGER_PATH);
5532
5553
  }
5533
5554
  }
5534
- getReturnExpressionWhenCalledAtPath(path, callOptions) {
5555
+ getReturnExpressionWhenCalledAtPath(path, { thisArg }) {
5535
5556
  if (path.length > 0) {
5536
5557
  return UNKNOWN_EXPRESSION;
5537
5558
  }
5538
5559
  return (this.description.returnsPrimitive ||
5539
5560
  (this.description.returns === 'self'
5540
- ? callOptions.thisParam || UNKNOWN_EXPRESSION
5561
+ ? thisArg || UNKNOWN_EXPRESSION
5541
5562
  : this.description.returns()));
5542
5563
  }
5543
- hasEffectsWhenAccessedAtPath(path) {
5544
- return path.length > 1;
5545
- }
5546
- hasEffectsWhenAssignedAtPath(path) {
5547
- return path.length > 0;
5548
- }
5549
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
5564
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
5550
5565
  var _a, _b;
5551
- if (path.length > 0 ||
5552
- (this.description.mutatesSelfAsArray === true &&
5553
- ((_a = callOptions.thisParam) === null || _a === void 0 ? void 0 : _a.hasEffectsWhenAssignedAtPath(UNKNOWN_INTEGER_PATH, context)))) {
5566
+ const { type } = interaction;
5567
+ if (path.length > (type === INTERACTION_ACCESSED ? 1 : 0)) {
5554
5568
  return true;
5555
5569
  }
5556
- if (!this.description.callsArgs) {
5557
- return false;
5558
- }
5559
- for (const argIndex of this.description.callsArgs) {
5560
- if ((_b = callOptions.args[argIndex]) === null || _b === void 0 ? void 0 : _b.hasEffectsWhenCalledAtPath(EMPTY_PATH, {
5561
- args: NO_ARGS,
5562
- thisParam: null,
5563
- withNew: false
5564
- }, context)) {
5570
+ if (type === INTERACTION_CALLED) {
5571
+ if (this.description.mutatesSelfAsArray === true &&
5572
+ ((_a = interaction.thisArg) === null || _a === void 0 ? void 0 : _a.hasEffectsOnInteractionAtPath(UNKNOWN_INTEGER_PATH, NODE_INTERACTION_UNKNOWN_ASSIGNMENT, context))) {
5565
5573
  return true;
5566
5574
  }
5575
+ if (this.description.callsArgs) {
5576
+ for (const argIndex of this.description.callsArgs) {
5577
+ if ((_b = interaction.args[argIndex]) === null || _b === void 0 ? void 0 : _b.hasEffectsOnInteractionAtPath(EMPTY_PATH, NODE_INTERACTION_UNKNOWN_CALL, context)) {
5578
+ return true;
5579
+ }
5580
+ }
5581
+ }
5567
5582
  }
5568
5583
  return false;
5569
5584
  }
@@ -5705,24 +5720,24 @@ class ObjectEntity extends ExpressionEntity {
5705
5720
  }
5706
5721
  (_a = this.prototypeExpression) === null || _a === void 0 ? void 0 : _a.deoptimizePath(path.length === 1 ? [...path, UnknownKey] : path);
5707
5722
  }
5708
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
5723
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
5709
5724
  var _a;
5710
5725
  const [key, ...subPath] = path;
5711
5726
  if (this.hasLostTrack ||
5712
5727
  // single paths that are deoptimized will not become getters or setters
5713
- ((event === EVENT_CALLED || path.length > 1) &&
5728
+ ((interaction.type === INTERACTION_CALLED || path.length > 1) &&
5714
5729
  (this.hasUnknownDeoptimizedProperty ||
5715
5730
  (typeof key === 'string' && this.deoptimizedPaths[key])))) {
5716
- thisParameter.deoptimizePath(UNKNOWN_PATH);
5731
+ interaction.thisArg.deoptimizePath(UNKNOWN_PATH);
5717
5732
  return;
5718
5733
  }
5719
- const [propertiesForExactMatchByKey, relevantPropertiesByKey, relevantUnmatchableProperties] = event === EVENT_CALLED || path.length > 1
5734
+ const [propertiesForExactMatchByKey, relevantPropertiesByKey, relevantUnmatchableProperties] = interaction.type === INTERACTION_CALLED || path.length > 1
5720
5735
  ? [
5721
5736
  this.propertiesAndGettersByKey,
5722
5737
  this.propertiesAndGettersByKey,
5723
5738
  this.unmatchablePropertiesAndGetters
5724
5739
  ]
5725
- : event === EVENT_ACCESSED
5740
+ : interaction.type === INTERACTION_ACCESSED
5726
5741
  ? [this.propertiesAndGettersByKey, this.gettersByKey, this.unmatchableGetters]
5727
5742
  : [this.propertiesAndSettersByKey, this.settersByKey, this.unmatchableSetters];
5728
5743
  if (typeof key === 'string') {
@@ -5730,20 +5745,20 @@ class ObjectEntity extends ExpressionEntity {
5730
5745
  const properties = relevantPropertiesByKey[key];
5731
5746
  if (properties) {
5732
5747
  for (const property of properties) {
5733
- property.deoptimizeThisOnEventAtPath(event, subPath, thisParameter, recursionTracker);
5748
+ property.deoptimizeThisOnInteractionAtPath(interaction, subPath, recursionTracker);
5734
5749
  }
5735
5750
  }
5736
5751
  if (!this.immutable) {
5737
- this.thisParametersToBeDeoptimized.add(thisParameter);
5752
+ this.thisParametersToBeDeoptimized.add(interaction.thisArg);
5738
5753
  }
5739
5754
  return;
5740
5755
  }
5741
5756
  for (const property of relevantUnmatchableProperties) {
5742
- property.deoptimizeThisOnEventAtPath(event, subPath, thisParameter, recursionTracker);
5757
+ property.deoptimizeThisOnInteractionAtPath(interaction, subPath, recursionTracker);
5743
5758
  }
5744
5759
  if (INTEGER_REG_EXP.test(key)) {
5745
5760
  for (const property of this.unknownIntegerProps) {
5746
- property.deoptimizeThisOnEventAtPath(event, subPath, thisParameter, recursionTracker);
5761
+ property.deoptimizeThisOnInteractionAtPath(interaction, subPath, recursionTracker);
5747
5762
  }
5748
5763
  }
5749
5764
  }
@@ -5752,17 +5767,17 @@ class ObjectEntity extends ExpressionEntity {
5752
5767
  relevantUnmatchableProperties
5753
5768
  ])) {
5754
5769
  for (const property of properties) {
5755
- property.deoptimizeThisOnEventAtPath(event, subPath, thisParameter, recursionTracker);
5770
+ property.deoptimizeThisOnInteractionAtPath(interaction, subPath, recursionTracker);
5756
5771
  }
5757
5772
  }
5758
5773
  for (const property of this.unknownIntegerProps) {
5759
- property.deoptimizeThisOnEventAtPath(event, subPath, thisParameter, recursionTracker);
5774
+ property.deoptimizeThisOnInteractionAtPath(interaction, subPath, recursionTracker);
5760
5775
  }
5761
5776
  }
5762
5777
  if (!this.immutable) {
5763
- this.thisParametersToBeDeoptimized.add(thisParameter);
5778
+ this.thisParametersToBeDeoptimized.add(interaction.thisArg);
5764
5779
  }
5765
- (_a = this.prototypeExpression) === null || _a === void 0 ? void 0 : _a.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
5780
+ (_a = this.prototypeExpression) === null || _a === void 0 ? void 0 : _a.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
5766
5781
  }
5767
5782
  getLiteralValueAtPath(path, recursionTracker, origin) {
5768
5783
  if (path.length === 0) {
@@ -5781,79 +5796,29 @@ class ObjectEntity extends ExpressionEntity {
5781
5796
  }
5782
5797
  return UnknownValue;
5783
5798
  }
5784
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
5799
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
5785
5800
  if (path.length === 0) {
5786
5801
  return UNKNOWN_EXPRESSION;
5787
5802
  }
5788
- const key = path[0];
5803
+ const [key, ...subPath] = path;
5789
5804
  const expressionAtPath = this.getMemberExpressionAndTrackDeopt(key, origin);
5790
5805
  if (expressionAtPath) {
5791
- return expressionAtPath.getReturnExpressionWhenCalledAtPath(path.slice(1), callOptions, recursionTracker, origin);
5806
+ return expressionAtPath.getReturnExpressionWhenCalledAtPath(subPath, interaction, recursionTracker, origin);
5792
5807
  }
5793
5808
  if (this.prototypeExpression) {
5794
- return this.prototypeExpression.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
5809
+ return this.prototypeExpression.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
5795
5810
  }
5796
5811
  return UNKNOWN_EXPRESSION;
5797
5812
  }
5798
- hasEffectsWhenAccessedAtPath(path, context) {
5799
- const [key, ...subPath] = path;
5800
- if (path.length > 1) {
5801
- if (typeof key !== 'string') {
5802
- return true;
5803
- }
5804
- const expressionAtPath = this.getMemberExpression(key);
5805
- if (expressionAtPath) {
5806
- return expressionAtPath.hasEffectsWhenAccessedAtPath(subPath, context);
5807
- }
5808
- if (this.prototypeExpression) {
5809
- return this.prototypeExpression.hasEffectsWhenAccessedAtPath(path, context);
5810
- }
5811
- return true;
5812
- }
5813
- if (this.hasLostTrack)
5814
- return true;
5815
- if (typeof key === 'string') {
5816
- if (this.propertiesAndGettersByKey[key]) {
5817
- const getters = this.gettersByKey[key];
5818
- if (getters) {
5819
- for (const getter of getters) {
5820
- if (getter.hasEffectsWhenAccessedAtPath(subPath, context))
5821
- return true;
5822
- }
5823
- }
5824
- return false;
5825
- }
5826
- for (const getter of this.unmatchableGetters) {
5827
- if (getter.hasEffectsWhenAccessedAtPath(subPath, context)) {
5828
- return true;
5829
- }
5830
- }
5831
- }
5832
- else {
5833
- for (const getters of Object.values(this.gettersByKey).concat([this.unmatchableGetters])) {
5834
- for (const getter of getters) {
5835
- if (getter.hasEffectsWhenAccessedAtPath(subPath, context))
5836
- return true;
5837
- }
5838
- }
5839
- }
5840
- if (this.prototypeExpression) {
5841
- return this.prototypeExpression.hasEffectsWhenAccessedAtPath(path, context);
5842
- }
5843
- return false;
5844
- }
5845
- hasEffectsWhenAssignedAtPath(path, context) {
5813
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
5846
5814
  const [key, ...subPath] = path;
5847
- if (path.length > 1) {
5848
- if (typeof key !== 'string') {
5849
- return true;
5850
- }
5815
+ if (subPath.length || interaction.type === INTERACTION_CALLED) {
5851
5816
  const expressionAtPath = this.getMemberExpression(key);
5852
5817
  if (expressionAtPath) {
5853
- return expressionAtPath.hasEffectsWhenAssignedAtPath(subPath, context);
5818
+ return expressionAtPath.hasEffectsOnInteractionAtPath(subPath, interaction, context);
5854
5819
  }
5855
5820
  if (this.prototypeExpression) {
5856
- return this.prototypeExpression.hasEffectsWhenAssignedAtPath(path, context);
5821
+ return this.prototypeExpression.hasEffectsOnInteractionAtPath(path, interaction, context);
5857
5822
  }
5858
5823
  return true;
5859
5824
  }
@@ -5861,47 +5826,39 @@ class ObjectEntity extends ExpressionEntity {
5861
5826
  return false;
5862
5827
  if (this.hasLostTrack)
5863
5828
  return true;
5829
+ const [propertiesAndAccessorsByKey, accessorsByKey, unmatchableAccessors] = interaction.type === INTERACTION_ACCESSED
5830
+ ? [this.propertiesAndGettersByKey, this.gettersByKey, this.unmatchableGetters]
5831
+ : [this.propertiesAndSettersByKey, this.settersByKey, this.unmatchableSetters];
5864
5832
  if (typeof key === 'string') {
5865
- if (this.propertiesAndSettersByKey[key]) {
5866
- const setters = this.settersByKey[key];
5867
- if (setters) {
5868
- for (const setter of setters) {
5869
- if (setter.hasEffectsWhenAssignedAtPath(subPath, context))
5833
+ if (propertiesAndAccessorsByKey[key]) {
5834
+ const accessors = accessorsByKey[key];
5835
+ if (accessors) {
5836
+ for (const accessor of accessors) {
5837
+ if (accessor.hasEffectsOnInteractionAtPath(subPath, interaction, context))
5870
5838
  return true;
5871
5839
  }
5872
5840
  }
5873
5841
  return false;
5874
5842
  }
5875
- for (const property of this.unmatchableSetters) {
5876
- if (property.hasEffectsWhenAssignedAtPath(subPath, context)) {
5843
+ for (const accessor of unmatchableAccessors) {
5844
+ if (accessor.hasEffectsOnInteractionAtPath(subPath, interaction, context)) {
5877
5845
  return true;
5878
5846
  }
5879
5847
  }
5880
5848
  }
5881
5849
  else {
5882
- for (const setters of Object.values(this.settersByKey).concat([this.unmatchableSetters])) {
5883
- for (const setter of setters) {
5884
- if (setter.hasEffectsWhenAssignedAtPath(subPath, context))
5850
+ for (const accessors of Object.values(accessorsByKey).concat([unmatchableAccessors])) {
5851
+ for (const accessor of accessors) {
5852
+ if (accessor.hasEffectsOnInteractionAtPath(subPath, interaction, context))
5885
5853
  return true;
5886
5854
  }
5887
5855
  }
5888
5856
  }
5889
5857
  if (this.prototypeExpression) {
5890
- return this.prototypeExpression.hasEffectsWhenAssignedAtPath(path, context);
5858
+ return this.prototypeExpression.hasEffectsOnInteractionAtPath(path, interaction, context);
5891
5859
  }
5892
5860
  return false;
5893
5861
  }
5894
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
5895
- const key = path[0];
5896
- const expressionAtPath = this.getMemberExpression(key);
5897
- if (expressionAtPath) {
5898
- return expressionAtPath.hasEffectsWhenCalledAtPath(path.slice(1), callOptions, context);
5899
- }
5900
- if (this.prototypeExpression) {
5901
- return this.prototypeExpression.hasEffectsWhenCalledAtPath(path, callOptions, context);
5902
- }
5903
- return true;
5904
- }
5905
5862
  buildPropertyMaps(properties) {
5906
5863
  const { allProperties, propertiesAndGettersByKey, propertiesAndSettersByKey, settersByKey, gettersByKey, unknownIntegerProps, unmatchablePropertiesAndGetters, unmatchableGetters, unmatchableSetters } = this;
5907
5864
  const unmatchablePropertiesAndSetters = [];
@@ -6007,9 +5964,9 @@ const isInteger = (prop) => typeof prop === 'string' && /^\d+$/.test(prop);
6007
5964
  // properties as we do not expect new builtin properties to be numbers, this
6008
5965
  // will improve tree-shaking for out-of-bounds array properties
6009
5966
  const OBJECT_PROTOTYPE_FALLBACK = new (class ObjectPrototypeFallbackExpression extends ExpressionEntity {
6010
- deoptimizeThisOnEventAtPath(event, path, thisParameter) {
6011
- if (event === EVENT_CALLED && path.length === 1 && !isInteger(path[0])) {
6012
- thisParameter.deoptimizePath(UNKNOWN_PATH);
5967
+ deoptimizeThisOnInteractionAtPath({ type, thisArg }, path) {
5968
+ if (type === INTERACTION_CALLED && path.length === 1 && !isInteger(path[0])) {
5969
+ thisArg.deoptimizePath(UNKNOWN_PATH);
6013
5970
  }
6014
5971
  }
6015
5972
  getLiteralValueAtPath(path) {
@@ -6018,11 +5975,8 @@ const OBJECT_PROTOTYPE_FALLBACK = new (class ObjectPrototypeFallbackExpression e
6018
5975
  // "undefined"
6019
5976
  return path.length === 1 && isInteger(path[0]) ? undefined : UnknownValue;
6020
5977
  }
6021
- hasEffectsWhenAccessedAtPath(path) {
6022
- return path.length > 1;
6023
- }
6024
- hasEffectsWhenAssignedAtPath(path) {
6025
- return path.length > 1;
5978
+ hasEffectsOnInteractionAtPath(path, { type }) {
5979
+ return path.length > 1 || type === INTERACTION_CALLED;
6026
5980
  }
6027
5981
  })();
6028
5982
  const OBJECT_PROTOTYPE = new ObjectEntity({
@@ -6171,37 +6125,30 @@ const ARRAY_PROTOTYPE = new ObjectEntity({
6171
6125
  class ArrayExpression extends NodeBase {
6172
6126
  constructor() {
6173
6127
  super(...arguments);
6174
- this.deoptimized = false;
6175
6128
  this.objectEntity = null;
6176
6129
  }
6177
6130
  deoptimizePath(path) {
6178
6131
  this.getObjectEntity().deoptimizePath(path);
6179
6132
  }
6180
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
6181
- this.getObjectEntity().deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
6133
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
6134
+ this.getObjectEntity().deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
6182
6135
  }
6183
6136
  getLiteralValueAtPath(path, recursionTracker, origin) {
6184
6137
  return this.getObjectEntity().getLiteralValueAtPath(path, recursionTracker, origin);
6185
6138
  }
6186
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
6187
- return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
6139
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
6140
+ return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
6188
6141
  }
6189
- hasEffectsWhenAccessedAtPath(path, context) {
6190
- return this.getObjectEntity().hasEffectsWhenAccessedAtPath(path, context);
6191
- }
6192
- hasEffectsWhenAssignedAtPath(path, context) {
6193
- return this.getObjectEntity().hasEffectsWhenAssignedAtPath(path, context);
6194
- }
6195
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
6196
- return this.getObjectEntity().hasEffectsWhenCalledAtPath(path, callOptions, context);
6142
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
6143
+ return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
6197
6144
  }
6198
6145
  applyDeoptimizations() {
6199
6146
  this.deoptimized = true;
6200
6147
  let hasSpread = false;
6201
6148
  for (let index = 0; index < this.elements.length; index++) {
6202
6149
  const element = this.elements[index];
6203
- if (hasSpread || element instanceof SpreadElement) {
6204
- if (element) {
6150
+ if (element) {
6151
+ if (hasSpread || element instanceof SpreadElement) {
6205
6152
  hasSpread = true;
6206
6153
  element.deoptimizePath(UNKNOWN_PATH);
6207
6154
  }
@@ -6258,9 +6205,9 @@ class ArrayPattern extends NodeBase {
6258
6205
  }
6259
6206
  }
6260
6207
  // Patterns are only checked at the emtpy path at the moment
6261
- hasEffectsWhenAssignedAtPath(_path, context) {
6208
+ hasEffectsOnInteractionAtPath(_path, interaction, context) {
6262
6209
  for (const element of this.elements) {
6263
- if (element === null || element === void 0 ? void 0 : element.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context))
6210
+ if (element === null || element === void 0 ? void 0 : element.hasEffectsOnInteractionAtPath(EMPTY_PATH, interaction, context))
6264
6211
  return true;
6265
6212
  }
6266
6213
  return false;
@@ -6319,11 +6266,11 @@ class LocalVariable extends Variable {
6319
6266
  (_b = this.init) === null || _b === void 0 ? void 0 : _b.deoptimizePath(path);
6320
6267
  }
6321
6268
  }
6322
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
6269
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
6323
6270
  if (this.isReassigned || !this.init) {
6324
- return thisParameter.deoptimizePath(UNKNOWN_PATH);
6271
+ return interaction.thisArg.deoptimizePath(UNKNOWN_PATH);
6325
6272
  }
6326
- recursionTracker.withTrackedEntityAtPath(path, this.init, () => this.init.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker), undefined);
6273
+ recursionTracker.withTrackedEntityAtPath(path, this.init, () => this.init.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker), undefined);
6327
6274
  }
6328
6275
  getLiteralValueAtPath(path, recursionTracker, origin) {
6329
6276
  if (this.isReassigned || !this.init) {
@@ -6334,39 +6281,40 @@ class LocalVariable extends Variable {
6334
6281
  return this.init.getLiteralValueAtPath(path, recursionTracker, origin);
6335
6282
  }, UnknownValue);
6336
6283
  }
6337
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
6284
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
6338
6285
  if (this.isReassigned || !this.init) {
6339
6286
  return UNKNOWN_EXPRESSION;
6340
6287
  }
6341
6288
  return recursionTracker.withTrackedEntityAtPath(path, this.init, () => {
6342
6289
  this.expressionsToBeDeoptimized.push(origin);
6343
- return this.init.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
6290
+ return this.init.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
6344
6291
  }, UNKNOWN_EXPRESSION);
6345
6292
  }
6346
- hasEffectsWhenAccessedAtPath(path, context) {
6347
- if (this.isReassigned)
6348
- return true;
6349
- return (this.init &&
6350
- !context.accessed.trackEntityAtPathAndGetIfTracked(path, this) &&
6351
- this.init.hasEffectsWhenAccessedAtPath(path, context));
6352
- }
6353
- hasEffectsWhenAssignedAtPath(path, context) {
6354
- if (this.included)
6355
- return true;
6356
- if (path.length === 0)
6357
- return false;
6358
- if (this.isReassigned)
6359
- return true;
6360
- return (this.init &&
6361
- !context.assigned.trackEntityAtPathAndGetIfTracked(path, this) &&
6362
- this.init.hasEffectsWhenAssignedAtPath(path, context));
6363
- }
6364
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
6365
- if (this.isReassigned)
6366
- return true;
6367
- return (this.init &&
6368
- !(callOptions.withNew ? context.instantiated : context.called).trackEntityAtPathAndGetIfTracked(path, callOptions, this) &&
6369
- this.init.hasEffectsWhenCalledAtPath(path, callOptions, context));
6293
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
6294
+ switch (interaction.type) {
6295
+ case INTERACTION_ACCESSED:
6296
+ if (this.isReassigned)
6297
+ return true;
6298
+ return (this.init &&
6299
+ !context.accessed.trackEntityAtPathAndGetIfTracked(path, this) &&
6300
+ this.init.hasEffectsOnInteractionAtPath(path, interaction, context));
6301
+ case INTERACTION_ASSIGNED:
6302
+ if (this.included)
6303
+ return true;
6304
+ if (path.length === 0)
6305
+ return false;
6306
+ if (this.isReassigned)
6307
+ return true;
6308
+ return (this.init &&
6309
+ !context.assigned.trackEntityAtPathAndGetIfTracked(path, this) &&
6310
+ this.init.hasEffectsOnInteractionAtPath(path, interaction, context));
6311
+ case INTERACTION_CALLED:
6312
+ if (this.isReassigned)
6313
+ return true;
6314
+ return (this.init &&
6315
+ !(interaction.withNew ? context.instantiated : context.called).trackEntityAtPathAndGetIfTracked(path, interaction.args, this) &&
6316
+ this.init.hasEffectsOnInteractionAtPath(path, interaction, context));
6317
+ }
6370
6318
  }
6371
6319
  include() {
6372
6320
  if (!this.included) {
@@ -6643,642 +6591,87 @@ class ReturnValueScope extends ParameterScope {
6643
6591
  }
6644
6592
  }
6645
6593
 
6646
- class AssignmentPattern extends NodeBase {
6647
- constructor() {
6648
- super(...arguments);
6649
- this.deoptimized = false;
6650
- }
6651
- addExportedVariables(variables, exportNamesByVariable) {
6652
- this.left.addExportedVariables(variables, exportNamesByVariable);
6653
- }
6654
- declare(kind, init) {
6655
- return this.left.declare(kind, init);
6656
- }
6657
- deoptimizePath(path) {
6658
- path.length === 0 && this.left.deoptimizePath(path);
6659
- }
6660
- hasEffectsWhenAssignedAtPath(path, context) {
6661
- return path.length > 0 || this.left.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context);
6662
- }
6663
- // Note that FunctionBase may directly include .left and .right without
6664
- // including the pattern itself. This is how default parameter tree-shaking
6665
- // works at the moment.
6666
- include(context, includeChildrenRecursively) {
6667
- this.included = true;
6668
- this.left.include(context, includeChildrenRecursively);
6669
- this.right.include(context, includeChildrenRecursively);
6670
- }
6671
- markDeclarationReached() {
6672
- this.left.markDeclarationReached();
6673
- }
6674
- render(code, options, { isShorthandProperty } = BLANK) {
6675
- this.left.render(code, options, { isShorthandProperty });
6676
- if (this.right.included) {
6677
- this.right.render(code, options);
6678
- }
6679
- else {
6680
- code.remove(this.left.end, this.end);
6681
- }
6682
- }
6683
- applyDeoptimizations() {
6684
- this.deoptimized = true;
6685
- this.left.deoptimizePath(EMPTY_PATH);
6686
- this.right.deoptimizePath(UNKNOWN_PATH);
6687
- this.context.requestTreeshakingPass();
6688
- }
6689
- }
6594
+ //@ts-check
6595
+ /** @typedef { import('estree').Node} Node */
6596
+ /** @typedef {Node | {
6597
+ * type: 'PropertyDefinition';
6598
+ * computed: boolean;
6599
+ * value: Node
6600
+ * }} NodeWithPropertyDefinition */
6690
6601
 
6691
- function treeshakeNode(node, code, start, end) {
6692
- code.remove(start, end);
6693
- if (node.annotations) {
6694
- for (const annotation of node.annotations) {
6695
- if (annotation.start < start) {
6696
- code.remove(annotation.start, annotation.end);
6697
- }
6698
- else {
6699
- return;
6700
- }
6701
- }
6702
- }
6602
+ /**
6603
+ *
6604
+ * @param {NodeWithPropertyDefinition} node
6605
+ * @param {NodeWithPropertyDefinition} parent
6606
+ * @returns boolean
6607
+ */
6608
+ function is_reference (node, parent) {
6609
+ if (node.type === 'MemberExpression') {
6610
+ return !node.computed && is_reference(node.object, node);
6611
+ }
6612
+
6613
+ if (node.type === 'Identifier') {
6614
+ if (!parent) return true;
6615
+
6616
+ switch (parent.type) {
6617
+ // disregard `bar` in `foo.bar`
6618
+ case 'MemberExpression': return parent.computed || node === parent.object;
6619
+
6620
+ // disregard the `foo` in `class {foo(){}}` but keep it in `class {[foo](){}}`
6621
+ case 'MethodDefinition': return parent.computed;
6622
+
6623
+ // disregard the `foo` in `class {foo=bar}` but keep it in `class {[foo]=bar}` and `class {bar=foo}`
6624
+ case 'PropertyDefinition': return parent.computed || node === parent.value;
6625
+
6626
+ // disregard the `bar` in `{ bar: foo }`, but keep it in `{ [bar]: foo }`
6627
+ case 'Property': return parent.computed || node === parent.value;
6628
+
6629
+ // disregard the `bar` in `export { foo as bar }` or
6630
+ // the foo in `import { foo as bar }`
6631
+ case 'ExportSpecifier':
6632
+ case 'ImportSpecifier': return node === parent.local;
6633
+
6634
+ // disregard the `foo` in `foo: while (...) { ... break foo; ... continue foo;}`
6635
+ case 'LabeledStatement':
6636
+ case 'BreakStatement':
6637
+ case 'ContinueStatement': return false;
6638
+ default: return true;
6639
+ }
6640
+ }
6641
+
6642
+ return false;
6703
6643
  }
6704
- function removeAnnotations(node, code) {
6705
- if (!node.annotations && node.parent.type === ExpressionStatement$1) {
6706
- node = node.parent;
6644
+
6645
+ /* eslint sort-keys: "off" */
6646
+ const ValueProperties = Symbol('Value Properties');
6647
+ const PURE = {
6648
+ hasEffectsWhenCalled() {
6649
+ return false;
6707
6650
  }
6708
- if (node.annotations) {
6709
- for (const annotation of node.annotations) {
6710
- code.remove(annotation.start, annotation.end);
6711
- }
6651
+ };
6652
+ const IMPURE = {
6653
+ hasEffectsWhenCalled() {
6654
+ return true;
6712
6655
  }
6713
- }
6714
-
6715
- const NO_SEMICOLON = { isNoStatement: true };
6716
- // This assumes there are only white-space and comments between start and the string we are looking for
6717
- function findFirstOccurrenceOutsideComment(code, searchString, start = 0) {
6718
- let searchPos, charCodeAfterSlash;
6719
- searchPos = code.indexOf(searchString, start);
6720
- while (true) {
6721
- start = code.indexOf('/', start);
6722
- if (start === -1 || start >= searchPos)
6723
- return searchPos;
6724
- charCodeAfterSlash = code.charCodeAt(++start);
6725
- ++start;
6726
- // With our assumption, '/' always starts a comment. Determine comment type:
6727
- start =
6728
- charCodeAfterSlash === 47 /*"/"*/
6729
- ? code.indexOf('\n', start) + 1
6730
- : code.indexOf('*/', start) + 2;
6731
- if (start > searchPos) {
6732
- searchPos = code.indexOf(searchString, start);
6733
- }
6734
- }
6735
- }
6736
- const NON_WHITESPACE = /\S/g;
6737
- function findNonWhiteSpace(code, index) {
6738
- NON_WHITESPACE.lastIndex = index;
6739
- const result = NON_WHITESPACE.exec(code);
6740
- return result.index;
6741
- }
6742
- // This assumes "code" only contains white-space and comments
6743
- // Returns position of line-comment if applicable
6744
- function findFirstLineBreakOutsideComment(code) {
6745
- let lineBreakPos, charCodeAfterSlash, start = 0;
6746
- lineBreakPos = code.indexOf('\n', start);
6747
- while (true) {
6748
- start = code.indexOf('/', start);
6749
- if (start === -1 || start > lineBreakPos)
6750
- return [lineBreakPos, lineBreakPos + 1];
6751
- // With our assumption, '/' always starts a comment. Determine comment type:
6752
- charCodeAfterSlash = code.charCodeAt(start + 1);
6753
- if (charCodeAfterSlash === 47 /*"/"*/)
6754
- return [start, lineBreakPos + 1];
6755
- start = code.indexOf('*/', start + 3) + 2;
6756
- if (start > lineBreakPos) {
6757
- lineBreakPos = code.indexOf('\n', start);
6758
- }
6759
- }
6760
- }
6761
- function renderStatementList(statements, code, start, end, options) {
6762
- let currentNode, currentNodeStart, currentNodeNeedsBoundaries, nextNodeStart;
6763
- let nextNode = statements[0];
6764
- let nextNodeNeedsBoundaries = !nextNode.included || nextNode.needsBoundaries;
6765
- if (nextNodeNeedsBoundaries) {
6766
- nextNodeStart =
6767
- start + findFirstLineBreakOutsideComment(code.original.slice(start, nextNode.start))[1];
6768
- }
6769
- for (let nextIndex = 1; nextIndex <= statements.length; nextIndex++) {
6770
- currentNode = nextNode;
6771
- currentNodeStart = nextNodeStart;
6772
- currentNodeNeedsBoundaries = nextNodeNeedsBoundaries;
6773
- nextNode = statements[nextIndex];
6774
- nextNodeNeedsBoundaries =
6775
- nextNode === undefined ? false : !nextNode.included || nextNode.needsBoundaries;
6776
- if (currentNodeNeedsBoundaries || nextNodeNeedsBoundaries) {
6777
- nextNodeStart =
6778
- currentNode.end +
6779
- findFirstLineBreakOutsideComment(code.original.slice(currentNode.end, nextNode === undefined ? end : nextNode.start))[1];
6780
- if (currentNode.included) {
6781
- currentNodeNeedsBoundaries
6782
- ? currentNode.render(code, options, {
6783
- end: nextNodeStart,
6784
- start: currentNodeStart
6785
- })
6786
- : currentNode.render(code, options);
6787
- }
6788
- else {
6789
- treeshakeNode(currentNode, code, currentNodeStart, nextNodeStart);
6790
- }
6791
- }
6792
- else {
6793
- currentNode.render(code, options);
6794
- }
6795
- }
6796
- }
6797
- // This assumes that the first character is not part of the first node
6798
- function getCommaSeparatedNodesWithBoundaries(nodes, code, start, end) {
6799
- const splitUpNodes = [];
6800
- let node, nextNode, nextNodeStart, contentEnd, char;
6801
- let separator = start - 1;
6802
- for (let nextIndex = 0; nextIndex < nodes.length; nextIndex++) {
6803
- nextNode = nodes[nextIndex];
6804
- if (node !== undefined) {
6805
- separator =
6806
- node.end +
6807
- findFirstOccurrenceOutsideComment(code.original.slice(node.end, nextNode.start), ',');
6808
- }
6809
- nextNodeStart = contentEnd =
6810
- separator +
6811
- 1 +
6812
- findFirstLineBreakOutsideComment(code.original.slice(separator + 1, nextNode.start))[1];
6813
- while (((char = code.original.charCodeAt(nextNodeStart)),
6814
- char === 32 /*" "*/ || char === 9 /*"\t"*/ || char === 10 /*"\n"*/ || char === 13) /*"\r"*/)
6815
- nextNodeStart++;
6816
- if (node !== undefined) {
6817
- splitUpNodes.push({
6818
- contentEnd,
6819
- end: nextNodeStart,
6820
- node,
6821
- separator,
6822
- start
6823
- });
6824
- }
6825
- node = nextNode;
6826
- start = nextNodeStart;
6827
- }
6828
- splitUpNodes.push({
6829
- contentEnd: end,
6830
- end,
6831
- node: node,
6832
- separator: null,
6833
- start
6834
- });
6835
- return splitUpNodes;
6836
- }
6837
- // This assumes there are only white-space and comments between start and end
6838
- function removeLineBreaks(code, start, end) {
6839
- while (true) {
6840
- const [removeStart, removeEnd] = findFirstLineBreakOutsideComment(code.original.slice(start, end));
6841
- if (removeStart === -1) {
6842
- break;
6843
- }
6844
- code.remove(start + removeStart, (start += removeEnd));
6845
- }
6846
- }
6847
-
6848
- class BlockScope extends ChildScope {
6849
- addDeclaration(identifier, context, init, isHoisted) {
6850
- if (isHoisted) {
6851
- const variable = this.parent.addDeclaration(identifier, context, init, isHoisted);
6852
- // Necessary to make sure the init is deoptimized for conditional declarations.
6853
- // We cannot call deoptimizePath here.
6854
- variable.markInitializersForDeoptimization();
6855
- return variable;
6856
- }
6857
- else {
6858
- return super.addDeclaration(identifier, context, init, false);
6859
- }
6860
- }
6861
- }
6862
-
6863
- class ExpressionStatement extends NodeBase {
6864
- initialise() {
6865
- if (this.directive &&
6866
- this.directive !== 'use strict' &&
6867
- this.parent.type === Program$1) {
6868
- this.context.warn(
6869
- // This is necessary, because either way (deleting or not) can lead to errors.
6870
- {
6871
- code: 'MODULE_LEVEL_DIRECTIVE',
6872
- message: `Module level directives cause errors when bundled, '${this.directive}' was ignored.`
6873
- }, this.start);
6874
- }
6875
- }
6876
- render(code, options) {
6877
- super.render(code, options);
6878
- if (this.included)
6879
- this.insertSemicolon(code);
6880
- }
6881
- shouldBeIncluded(context) {
6882
- if (this.directive && this.directive !== 'use strict')
6883
- return this.parent.type !== Program$1;
6884
- return super.shouldBeIncluded(context);
6885
- }
6886
- }
6887
-
6888
- class BlockStatement extends NodeBase {
6889
- constructor() {
6890
- super(...arguments);
6891
- this.directlyIncluded = false;
6892
- }
6893
- addImplicitReturnExpressionToScope() {
6894
- const lastStatement = this.body[this.body.length - 1];
6895
- if (!lastStatement || lastStatement.type !== ReturnStatement$1) {
6896
- this.scope.addReturnExpression(UNKNOWN_EXPRESSION);
6897
- }
6898
- }
6899
- createScope(parentScope) {
6900
- this.scope = this.parent.preventChildBlockScope
6901
- ? parentScope
6902
- : new BlockScope(parentScope);
6903
- }
6904
- hasEffects(context) {
6905
- if (this.deoptimizeBody)
6906
- return true;
6907
- for (const node of this.body) {
6908
- if (context.brokenFlow)
6909
- break;
6910
- if (node.hasEffects(context))
6911
- return true;
6912
- }
6913
- return false;
6914
- }
6915
- include(context, includeChildrenRecursively) {
6916
- if (!(this.deoptimizeBody && this.directlyIncluded)) {
6917
- this.included = true;
6918
- this.directlyIncluded = true;
6919
- if (this.deoptimizeBody)
6920
- includeChildrenRecursively = true;
6921
- for (const node of this.body) {
6922
- if (includeChildrenRecursively || node.shouldBeIncluded(context))
6923
- node.include(context, includeChildrenRecursively);
6924
- }
6925
- }
6926
- }
6927
- initialise() {
6928
- const firstBodyStatement = this.body[0];
6929
- this.deoptimizeBody =
6930
- firstBodyStatement instanceof ExpressionStatement &&
6931
- firstBodyStatement.directive === 'use asm';
6932
- }
6933
- render(code, options) {
6934
- if (this.body.length) {
6935
- renderStatementList(this.body, code, this.start + 1, this.end - 1, options);
6936
- }
6937
- else {
6938
- super.render(code, options);
6939
- }
6940
- }
6941
- }
6942
-
6943
- class RestElement extends NodeBase {
6944
- constructor() {
6945
- super(...arguments);
6946
- this.deoptimized = false;
6947
- this.declarationInit = null;
6948
- }
6949
- addExportedVariables(variables, exportNamesByVariable) {
6950
- this.argument.addExportedVariables(variables, exportNamesByVariable);
6951
- }
6952
- declare(kind, init) {
6953
- this.declarationInit = init;
6954
- return this.argument.declare(kind, UNKNOWN_EXPRESSION);
6955
- }
6956
- deoptimizePath(path) {
6957
- path.length === 0 && this.argument.deoptimizePath(EMPTY_PATH);
6958
- }
6959
- hasEffectsWhenAssignedAtPath(path, context) {
6960
- return path.length > 0 || this.argument.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context);
6961
- }
6962
- markDeclarationReached() {
6963
- this.argument.markDeclarationReached();
6964
- }
6965
- applyDeoptimizations() {
6966
- this.deoptimized = true;
6967
- if (this.declarationInit !== null) {
6968
- this.declarationInit.deoptimizePath([UnknownKey, UnknownKey]);
6969
- this.context.requestTreeshakingPass();
6970
- }
6971
- }
6972
- }
6973
-
6974
- class FunctionBase extends NodeBase {
6975
- constructor() {
6976
- super(...arguments);
6977
- this.objectEntity = null;
6978
- this.deoptimizedReturn = false;
6979
- this.forceIncludeParameters = false;
6980
- }
6981
- deoptimizeCache() {
6982
- this.forceIncludeParameters = true;
6983
- }
6984
- deoptimizePath(path) {
6985
- this.getObjectEntity().deoptimizePath(path);
6986
- if (path.length === 1 && path[0] === UnknownKey) {
6987
- // A reassignment of UNKNOWN_PATH is considered equivalent to having lost track
6988
- // which means the return expression needs to be reassigned
6989
- this.forceIncludeParameters = true;
6990
- this.scope.getReturnExpression().deoptimizePath(UNKNOWN_PATH);
6991
- }
6992
- }
6993
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
6994
- if (path.length > 0) {
6995
- this.getObjectEntity().deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
6996
- }
6997
- }
6998
- getLiteralValueAtPath(path, recursionTracker, origin) {
6999
- return this.getObjectEntity().getLiteralValueAtPath(path, recursionTracker, origin);
7000
- }
7001
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
7002
- if (path.length > 0) {
7003
- return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
7004
- }
7005
- if (this.async) {
7006
- if (!this.deoptimizedReturn) {
7007
- this.deoptimizedReturn = true;
7008
- this.scope.getReturnExpression().deoptimizePath(UNKNOWN_PATH);
7009
- this.context.requestTreeshakingPass();
7010
- }
7011
- return UNKNOWN_EXPRESSION;
7012
- }
7013
- return this.scope.getReturnExpression();
7014
- }
7015
- hasEffectsWhenAccessedAtPath(path, context) {
7016
- return this.getObjectEntity().hasEffectsWhenAccessedAtPath(path, context);
7017
- }
7018
- hasEffectsWhenAssignedAtPath(path, context) {
7019
- return this.getObjectEntity().hasEffectsWhenAssignedAtPath(path, context);
7020
- }
7021
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
7022
- var _a;
7023
- if (path.length > 0) {
7024
- return this.getObjectEntity().hasEffectsWhenCalledAtPath(path, callOptions, context);
7025
- }
7026
- if (this.async) {
7027
- const { propertyReadSideEffects } = this.context.options
7028
- .treeshake;
7029
- const returnExpression = this.scope.getReturnExpression();
7030
- if (returnExpression.hasEffectsWhenCalledAtPath(['then'], { args: NO_ARGS, thisParam: null, withNew: false }, context) ||
7031
- (propertyReadSideEffects &&
7032
- (propertyReadSideEffects === 'always' ||
7033
- returnExpression.hasEffectsWhenAccessedAtPath(['then'], context)))) {
7034
- return true;
7035
- }
7036
- }
7037
- for (let position = 0; position < this.params.length; position++) {
7038
- const parameter = this.params[position];
7039
- if (parameter instanceof AssignmentPattern) {
7040
- if (parameter.left.hasEffects(context)) {
7041
- return true;
7042
- }
7043
- const argumentValue = (_a = callOptions.args[position]) === null || _a === void 0 ? void 0 : _a.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this);
7044
- if ((argumentValue === undefined || argumentValue === UnknownValue) &&
7045
- parameter.right.hasEffects(context)) {
7046
- return true;
7047
- }
7048
- }
7049
- else if (parameter.hasEffects(context)) {
7050
- return true;
7051
- }
7052
- }
7053
- return false;
7054
- }
7055
- include(context, includeChildrenRecursively, { includeWithoutParameterDefaults } = BLANK) {
7056
- if (!this.deoptimized)
7057
- this.applyDeoptimizations();
7058
- this.included = true;
7059
- const { brokenFlow } = context;
7060
- context.brokenFlow = BROKEN_FLOW_NONE;
7061
- this.body.include(context, includeChildrenRecursively);
7062
- context.brokenFlow = brokenFlow;
7063
- if (!includeWithoutParameterDefaults ||
7064
- includeChildrenRecursively ||
7065
- this.forceIncludeParameters) {
7066
- for (const param of this.params) {
7067
- param.include(context, includeChildrenRecursively);
7068
- }
7069
- }
7070
- }
7071
- includeCallArguments(context, args) {
7072
- var _a;
7073
- for (let position = 0; position < this.params.length; position++) {
7074
- const parameter = this.params[position];
7075
- if (parameter instanceof AssignmentPattern) {
7076
- if (parameter.left.shouldBeIncluded(context)) {
7077
- parameter.left.include(context, false);
7078
- }
7079
- const argumentValue = (_a = args[position]) === null || _a === void 0 ? void 0 : _a.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this);
7080
- // If argumentValue === UnknownTruthyValue, then we do not need to
7081
- // include the default
7082
- if ((argumentValue === undefined || argumentValue === UnknownValue) &&
7083
- (this.parameterVariables[position].some(variable => variable.included) ||
7084
- parameter.right.shouldBeIncluded(context))) {
7085
- parameter.right.include(context, false);
7086
- }
7087
- }
7088
- else if (parameter.shouldBeIncluded(context)) {
7089
- parameter.include(context, false);
7090
- }
7091
- }
7092
- this.scope.includeCallArguments(context, args);
7093
- }
7094
- initialise() {
7095
- this.parameterVariables = this.params.map(param => param.declare('parameter', UNKNOWN_EXPRESSION));
7096
- this.scope.addParameterVariables(this.parameterVariables, this.params[this.params.length - 1] instanceof RestElement);
7097
- if (this.body instanceof BlockStatement) {
7098
- this.body.addImplicitReturnExpressionToScope();
7099
- }
7100
- else {
7101
- this.scope.addReturnExpression(this.body);
7102
- }
7103
- }
7104
- parseNode(esTreeNode) {
7105
- if (esTreeNode.body.type === BlockStatement$1) {
7106
- this.body = new BlockStatement(esTreeNode.body, this, this.scope.hoistedBodyVarScope);
7107
- }
7108
- super.parseNode(esTreeNode);
7109
- }
7110
- applyDeoptimizations() {
7111
- // We currently do not track deoptimizations of default values, deoptimize them
7112
- // just as we deoptimize call arguments
7113
- for (const param of this.params) {
7114
- if (param instanceof AssignmentPattern) {
7115
- param.right.deoptimizePath(UNKNOWN_PATH);
7116
- }
7117
- }
7118
- }
7119
- }
7120
- FunctionBase.prototype.preventChildBlockScope = true;
7121
-
7122
- class ArrowFunctionExpression extends FunctionBase {
7123
- constructor() {
7124
- super(...arguments);
7125
- this.objectEntity = null;
7126
- }
7127
- createScope(parentScope) {
7128
- this.scope = new ReturnValueScope(parentScope, this.context);
7129
- }
7130
- hasEffects() {
7131
- if (!this.deoptimized)
7132
- this.applyDeoptimizations();
7133
- return false;
7134
- }
7135
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
7136
- if (super.hasEffectsWhenCalledAtPath(path, callOptions, context))
7137
- return true;
7138
- const { ignore, brokenFlow } = context;
7139
- context.ignore = {
7140
- breaks: false,
7141
- continues: false,
7142
- labels: new Set(),
7143
- returnYield: true
7144
- };
7145
- if (this.body.hasEffects(context))
7146
- return true;
7147
- context.ignore = ignore;
7148
- context.brokenFlow = brokenFlow;
7149
- return false;
7150
- }
7151
- getObjectEntity() {
7152
- if (this.objectEntity !== null) {
7153
- return this.objectEntity;
7154
- }
7155
- return (this.objectEntity = new ObjectEntity([], OBJECT_PROTOTYPE));
7156
- }
7157
- }
7158
-
7159
- function getSystemExportStatement(exportedVariables, { exportNamesByVariable, snippets: { _, getObject, getPropertyAccess } }, modifier = '') {
7160
- if (exportedVariables.length === 1 &&
7161
- exportNamesByVariable.get(exportedVariables[0]).length === 1) {
7162
- const variable = exportedVariables[0];
7163
- return `exports('${exportNamesByVariable.get(variable)}',${_}${variable.getName(getPropertyAccess)}${modifier})`;
7164
- }
7165
- else {
7166
- const fields = [];
7167
- for (const variable of exportedVariables) {
7168
- for (const exportName of exportNamesByVariable.get(variable)) {
7169
- fields.push([exportName, variable.getName(getPropertyAccess) + modifier]);
7170
- }
7171
- }
7172
- return `exports(${getObject(fields, { lineBreakIndent: null })})`;
7173
- }
7174
- }
7175
- function renderSystemExportExpression(exportedVariable, expressionStart, expressionEnd, code, { exportNamesByVariable, snippets: { _ } }) {
7176
- code.prependRight(expressionStart, `exports('${exportNamesByVariable.get(exportedVariable)}',${_}`);
7177
- code.appendLeft(expressionEnd, ')');
7178
- }
7179
- function renderSystemExportFunction(exportedVariables, expressionStart, expressionEnd, needsParens, code, options) {
7180
- const { _, getDirectReturnIifeLeft } = options.snippets;
7181
- code.prependRight(expressionStart, getDirectReturnIifeLeft(['v'], `${getSystemExportStatement(exportedVariables, options)},${_}v`, { needsArrowReturnParens: true, needsWrappedFunction: needsParens }));
7182
- code.appendLeft(expressionEnd, ')');
7183
- }
7184
- function renderSystemExportSequenceAfterExpression(exportedVariable, expressionStart, expressionEnd, needsParens, code, options) {
7185
- const { _, getPropertyAccess } = options.snippets;
7186
- code.appendLeft(expressionEnd, `,${_}${getSystemExportStatement([exportedVariable], options)},${_}${exportedVariable.getName(getPropertyAccess)}`);
7187
- if (needsParens) {
7188
- code.prependRight(expressionStart, '(');
7189
- code.appendLeft(expressionEnd, ')');
7190
- }
7191
- }
7192
- function renderSystemExportSequenceBeforeExpression(exportedVariable, expressionStart, expressionEnd, needsParens, code, options, modifier) {
7193
- const { _ } = options.snippets;
7194
- code.prependRight(expressionStart, `${getSystemExportStatement([exportedVariable], options, modifier)},${_}`);
7195
- if (needsParens) {
7196
- code.prependRight(expressionStart, '(');
7197
- code.appendLeft(expressionEnd, ')');
7198
- }
7199
- }
7200
-
7201
- //@ts-check
7202
- /** @typedef { import('estree').Node} Node */
7203
- /** @typedef {Node | {
7204
- * type: 'PropertyDefinition';
7205
- * computed: boolean;
7206
- * value: Node
7207
- * }} NodeWithPropertyDefinition */
7208
-
7209
- /**
7210
- *
7211
- * @param {NodeWithPropertyDefinition} node
7212
- * @param {NodeWithPropertyDefinition} parent
7213
- * @returns boolean
7214
- */
7215
- function is_reference (node, parent) {
7216
- if (node.type === 'MemberExpression') {
7217
- return !node.computed && is_reference(node.object, node);
7218
- }
7219
-
7220
- if (node.type === 'Identifier') {
7221
- if (!parent) return true;
7222
-
7223
- switch (parent.type) {
7224
- // disregard `bar` in `foo.bar`
7225
- case 'MemberExpression': return parent.computed || node === parent.object;
7226
-
7227
- // disregard the `foo` in `class {foo(){}}` but keep it in `class {[foo](){}}`
7228
- case 'MethodDefinition': return parent.computed;
7229
-
7230
- // disregard the `foo` in `class {foo=bar}` but keep it in `class {[foo]=bar}` and `class {bar=foo}`
7231
- case 'PropertyDefinition': return parent.computed || node === parent.value;
7232
-
7233
- // disregard the `bar` in `{ bar: foo }`, but keep it in `{ [bar]: foo }`
7234
- case 'Property': return parent.computed || node === parent.value;
7235
-
7236
- // disregard the `bar` in `export { foo as bar }` or
7237
- // the foo in `import { foo as bar }`
7238
- case 'ExportSpecifier':
7239
- case 'ImportSpecifier': return node === parent.local;
7240
-
7241
- // disregard the `foo` in `foo: while (...) { ... break foo; ... continue foo;}`
7242
- case 'LabeledStatement':
7243
- case 'BreakStatement':
7244
- case 'ContinueStatement': return false;
7245
- default: return true;
7246
- }
7247
- }
7248
-
7249
- return false;
7250
- }
7251
-
7252
- /* eslint sort-keys: "off" */
7253
- const ValueProperties = Symbol('Value Properties');
7254
- const PURE = {
7255
- hasEffectsWhenCalled() {
7256
- return false;
7257
- }
7258
- };
7259
- const IMPURE = {
7260
- hasEffectsWhenCalled() {
7261
- return true;
7262
- }
7263
- };
7264
- // We use shortened variables to reduce file size here
7265
- /* OBJECT */
7266
- const O = {
7267
- __proto__: null,
7268
- [ValueProperties]: IMPURE
7269
- };
7270
- /* PURE FUNCTION */
7271
- const PF = {
7272
- __proto__: null,
7273
- [ValueProperties]: PURE
7274
- };
7275
- /* FUNCTION THAT MUTATES FIRST ARG WITHOUT TRIGGERING ACCESSORS */
7276
- const MUTATES_ARG_WITHOUT_ACCESSOR = {
7277
- __proto__: null,
7278
- [ValueProperties]: {
7279
- hasEffectsWhenCalled(callOptions, context) {
7280
- return (!callOptions.args.length ||
7281
- callOptions.args[0].hasEffectsWhenAssignedAtPath(UNKNOWN_NON_ACCESSOR_PATH, context));
6656
+ };
6657
+ // We use shortened variables to reduce file size here
6658
+ /* OBJECT */
6659
+ const O = {
6660
+ __proto__: null,
6661
+ [ValueProperties]: IMPURE
6662
+ };
6663
+ /* PURE FUNCTION */
6664
+ const PF = {
6665
+ __proto__: null,
6666
+ [ValueProperties]: PURE
6667
+ };
6668
+ /* FUNCTION THAT MUTATES FIRST ARG WITHOUT TRIGGERING ACCESSORS */
6669
+ const MUTATES_ARG_WITHOUT_ACCESSOR = {
6670
+ __proto__: null,
6671
+ [ValueProperties]: {
6672
+ hasEffectsWhenCalled({ args }, context) {
6673
+ return (!args.length ||
6674
+ args[0].hasEffectsOnInteractionAtPath(UNKNOWN_NON_ACCESSOR_PATH, NODE_INTERACTION_UNKNOWN_ASSIGNMENT, context));
7282
6675
  }
7283
6676
  }
7284
6677
  };
@@ -8095,222 +7488,691 @@ const knownGlobals = {
8095
7488
  for (const global of ['window', 'global', 'self', 'globalThis']) {
8096
7489
  knownGlobals[global] = knownGlobals;
8097
7490
  }
8098
- function getGlobalAtPath(path) {
8099
- let currentGlobal = knownGlobals;
8100
- for (const pathSegment of path) {
8101
- if (typeof pathSegment !== 'string') {
8102
- return null;
7491
+ function getGlobalAtPath(path) {
7492
+ let currentGlobal = knownGlobals;
7493
+ for (const pathSegment of path) {
7494
+ if (typeof pathSegment !== 'string') {
7495
+ return null;
7496
+ }
7497
+ currentGlobal = currentGlobal[pathSegment];
7498
+ if (!currentGlobal) {
7499
+ return null;
7500
+ }
7501
+ }
7502
+ return currentGlobal[ValueProperties];
7503
+ }
7504
+
7505
+ class GlobalVariable extends Variable {
7506
+ constructor() {
7507
+ super(...arguments);
7508
+ // Ensure we use live-bindings for globals as we do not know if they have
7509
+ // been reassigned
7510
+ this.isReassigned = true;
7511
+ }
7512
+ getLiteralValueAtPath(path, _recursionTracker, _origin) {
7513
+ return getGlobalAtPath([this.name, ...path]) ? UnknownTruthyValue : UnknownValue;
7514
+ }
7515
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
7516
+ switch (interaction.type) {
7517
+ case INTERACTION_ACCESSED:
7518
+ if (path.length === 0) {
7519
+ // Technically, "undefined" is a global variable of sorts
7520
+ return this.name !== 'undefined' && !getGlobalAtPath([this.name]);
7521
+ }
7522
+ return !getGlobalAtPath([this.name, ...path].slice(0, -1));
7523
+ case INTERACTION_ASSIGNED:
7524
+ return true;
7525
+ case INTERACTION_CALLED: {
7526
+ const globalAtPath = getGlobalAtPath([this.name, ...path]);
7527
+ return !globalAtPath || globalAtPath.hasEffectsWhenCalled(interaction, context);
7528
+ }
7529
+ }
7530
+ }
7531
+ }
7532
+
7533
+ const tdzVariableKinds = {
7534
+ __proto__: null,
7535
+ class: true,
7536
+ const: true,
7537
+ let: true,
7538
+ var: true
7539
+ };
7540
+ class Identifier extends NodeBase {
7541
+ constructor() {
7542
+ super(...arguments);
7543
+ this.variable = null;
7544
+ this.isTDZAccess = null;
7545
+ }
7546
+ addExportedVariables(variables, exportNamesByVariable) {
7547
+ if (exportNamesByVariable.has(this.variable)) {
7548
+ variables.push(this.variable);
7549
+ }
7550
+ }
7551
+ bind() {
7552
+ if (!this.variable && is_reference(this, this.parent)) {
7553
+ this.variable = this.scope.findVariable(this.name);
7554
+ this.variable.addReference(this);
7555
+ }
7556
+ }
7557
+ declare(kind, init) {
7558
+ let variable;
7559
+ const { treeshake } = this.context.options;
7560
+ switch (kind) {
7561
+ case 'var':
7562
+ variable = this.scope.addDeclaration(this, this.context, init, true);
7563
+ if (treeshake && treeshake.correctVarValueBeforeDeclaration) {
7564
+ // Necessary to make sure the init is deoptimized. We cannot call deoptimizePath here.
7565
+ variable.markInitializersForDeoptimization();
7566
+ }
7567
+ break;
7568
+ case 'function':
7569
+ // in strict mode, functions are only hoisted within a scope but not across block scopes
7570
+ variable = this.scope.addDeclaration(this, this.context, init, false);
7571
+ break;
7572
+ case 'let':
7573
+ case 'const':
7574
+ case 'class':
7575
+ variable = this.scope.addDeclaration(this, this.context, init, false);
7576
+ break;
7577
+ case 'parameter':
7578
+ variable = this.scope.addParameterDeclaration(this);
7579
+ break;
7580
+ /* istanbul ignore next */
7581
+ default:
7582
+ /* istanbul ignore next */
7583
+ throw new Error(`Internal Error: Unexpected identifier kind ${kind}.`);
7584
+ }
7585
+ variable.kind = kind;
7586
+ return [(this.variable = variable)];
7587
+ }
7588
+ deoptimizePath(path) {
7589
+ var _a;
7590
+ if (path.length === 0 && !this.scope.contains(this.name)) {
7591
+ this.disallowImportReassignment();
7592
+ }
7593
+ // We keep conditional chaining because an unknown Node could have an
7594
+ // Identifier as property that might be deoptimized by default
7595
+ (_a = this.variable) === null || _a === void 0 ? void 0 : _a.deoptimizePath(path);
7596
+ }
7597
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
7598
+ this.variable.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
7599
+ }
7600
+ getLiteralValueAtPath(path, recursionTracker, origin) {
7601
+ return this.getVariableRespectingTDZ().getLiteralValueAtPath(path, recursionTracker, origin);
7602
+ }
7603
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
7604
+ return this.getVariableRespectingTDZ().getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
7605
+ }
7606
+ hasEffects(context) {
7607
+ if (!this.deoptimized)
7608
+ this.applyDeoptimizations();
7609
+ if (this.isPossibleTDZ() && this.variable.kind !== 'var') {
7610
+ return true;
7611
+ }
7612
+ return (this.context.options.treeshake.unknownGlobalSideEffects &&
7613
+ this.variable instanceof GlobalVariable &&
7614
+ this.variable.hasEffectsOnInteractionAtPath(EMPTY_PATH, NODE_INTERACTION_UNKNOWN_ACCESS, context));
7615
+ }
7616
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
7617
+ switch (interaction.type) {
7618
+ case INTERACTION_ACCESSED:
7619
+ return (this.variable !== null &&
7620
+ this.getVariableRespectingTDZ().hasEffectsOnInteractionAtPath(path, interaction, context));
7621
+ case INTERACTION_ASSIGNED:
7622
+ return (path.length > 0 ? this.getVariableRespectingTDZ() : this.variable).hasEffectsOnInteractionAtPath(path, interaction, context);
7623
+ case INTERACTION_CALLED:
7624
+ return this.getVariableRespectingTDZ().hasEffectsOnInteractionAtPath(path, interaction, context);
7625
+ }
7626
+ }
7627
+ include() {
7628
+ if (!this.deoptimized)
7629
+ this.applyDeoptimizations();
7630
+ if (!this.included) {
7631
+ this.included = true;
7632
+ if (this.variable !== null) {
7633
+ this.context.includeVariableInModule(this.variable);
7634
+ }
7635
+ }
7636
+ }
7637
+ includeCallArguments(context, args) {
7638
+ this.variable.includeCallArguments(context, args);
7639
+ }
7640
+ isPossibleTDZ() {
7641
+ // return cached value to avoid issues with the next tree-shaking pass
7642
+ if (this.isTDZAccess !== null)
7643
+ return this.isTDZAccess;
7644
+ if (!(this.variable instanceof LocalVariable) ||
7645
+ !this.variable.kind ||
7646
+ !(this.variable.kind in tdzVariableKinds)) {
7647
+ return (this.isTDZAccess = false);
7648
+ }
7649
+ let decl_id;
7650
+ if (this.variable.declarations &&
7651
+ this.variable.declarations.length === 1 &&
7652
+ (decl_id = this.variable.declarations[0]) &&
7653
+ this.start < decl_id.start &&
7654
+ closestParentFunctionOrProgram(this) === closestParentFunctionOrProgram(decl_id)) {
7655
+ // a variable accessed before its declaration
7656
+ // in the same function or at top level of module
7657
+ return (this.isTDZAccess = true);
7658
+ }
7659
+ if (!this.variable.initReached) {
7660
+ // Either a const/let TDZ violation or
7661
+ // var use before declaration was encountered.
7662
+ return (this.isTDZAccess = true);
7663
+ }
7664
+ return (this.isTDZAccess = false);
7665
+ }
7666
+ markDeclarationReached() {
7667
+ this.variable.initReached = true;
7668
+ }
7669
+ render(code, { snippets: { getPropertyAccess } }, { renderedParentType, isCalleeOfRenderedParent, isShorthandProperty } = BLANK) {
7670
+ if (this.variable) {
7671
+ const name = this.variable.getName(getPropertyAccess);
7672
+ if (name !== this.name) {
7673
+ code.overwrite(this.start, this.end, name, {
7674
+ contentOnly: true,
7675
+ storeName: true
7676
+ });
7677
+ if (isShorthandProperty) {
7678
+ code.prependRight(this.start, `${this.name}: `);
7679
+ }
7680
+ }
7681
+ // In strict mode, any variable named "eval" must be the actual "eval" function
7682
+ if (name === 'eval' &&
7683
+ renderedParentType === CallExpression$1 &&
7684
+ isCalleeOfRenderedParent) {
7685
+ code.appendRight(this.start, '0, ');
7686
+ }
7687
+ }
7688
+ }
7689
+ applyDeoptimizations() {
7690
+ this.deoptimized = true;
7691
+ if (this.variable instanceof LocalVariable) {
7692
+ this.variable.consolidateInitializers();
7693
+ this.context.requestTreeshakingPass();
7694
+ }
7695
+ }
7696
+ disallowImportReassignment() {
7697
+ return this.context.error({
7698
+ code: 'ILLEGAL_REASSIGNMENT',
7699
+ message: `Illegal reassignment to import '${this.name}'`
7700
+ }, this.start);
7701
+ }
7702
+ getVariableRespectingTDZ() {
7703
+ if (this.isPossibleTDZ()) {
7704
+ return UNKNOWN_EXPRESSION;
7705
+ }
7706
+ return this.variable;
7707
+ }
7708
+ }
7709
+ function closestParentFunctionOrProgram(node) {
7710
+ while (node && !/^Program|Function/.test(node.type)) {
7711
+ node = node.parent;
7712
+ }
7713
+ // one of: ArrowFunctionExpression, FunctionDeclaration, FunctionExpression or Program
7714
+ return node;
7715
+ }
7716
+
7717
+ function treeshakeNode(node, code, start, end) {
7718
+ code.remove(start, end);
7719
+ if (node.annotations) {
7720
+ for (const annotation of node.annotations) {
7721
+ if (annotation.start < start) {
7722
+ code.remove(annotation.start, annotation.end);
7723
+ }
7724
+ else {
7725
+ return;
7726
+ }
7727
+ }
7728
+ }
7729
+ }
7730
+ function removeAnnotations(node, code) {
7731
+ if (!node.annotations && node.parent.type === ExpressionStatement$1) {
7732
+ node = node.parent;
7733
+ }
7734
+ if (node.annotations) {
7735
+ for (const annotation of node.annotations) {
7736
+ code.remove(annotation.start, annotation.end);
7737
+ }
7738
+ }
7739
+ }
7740
+
7741
+ const NO_SEMICOLON = { isNoStatement: true };
7742
+ // This assumes there are only white-space and comments between start and the string we are looking for
7743
+ function findFirstOccurrenceOutsideComment(code, searchString, start = 0) {
7744
+ let searchPos, charCodeAfterSlash;
7745
+ searchPos = code.indexOf(searchString, start);
7746
+ while (true) {
7747
+ start = code.indexOf('/', start);
7748
+ if (start === -1 || start >= searchPos)
7749
+ return searchPos;
7750
+ charCodeAfterSlash = code.charCodeAt(++start);
7751
+ ++start;
7752
+ // With our assumption, '/' always starts a comment. Determine comment type:
7753
+ start =
7754
+ charCodeAfterSlash === 47 /*"/"*/
7755
+ ? code.indexOf('\n', start) + 1
7756
+ : code.indexOf('*/', start) + 2;
7757
+ if (start > searchPos) {
7758
+ searchPos = code.indexOf(searchString, start);
7759
+ }
7760
+ }
7761
+ }
7762
+ const NON_WHITESPACE = /\S/g;
7763
+ function findNonWhiteSpace(code, index) {
7764
+ NON_WHITESPACE.lastIndex = index;
7765
+ const result = NON_WHITESPACE.exec(code);
7766
+ return result.index;
7767
+ }
7768
+ // This assumes "code" only contains white-space and comments
7769
+ // Returns position of line-comment if applicable
7770
+ function findFirstLineBreakOutsideComment(code) {
7771
+ let lineBreakPos, charCodeAfterSlash, start = 0;
7772
+ lineBreakPos = code.indexOf('\n', start);
7773
+ while (true) {
7774
+ start = code.indexOf('/', start);
7775
+ if (start === -1 || start > lineBreakPos)
7776
+ return [lineBreakPos, lineBreakPos + 1];
7777
+ // With our assumption, '/' always starts a comment. Determine comment type:
7778
+ charCodeAfterSlash = code.charCodeAt(start + 1);
7779
+ if (charCodeAfterSlash === 47 /*"/"*/)
7780
+ return [start, lineBreakPos + 1];
7781
+ start = code.indexOf('*/', start + 3) + 2;
7782
+ if (start > lineBreakPos) {
7783
+ lineBreakPos = code.indexOf('\n', start);
8103
7784
  }
8104
- currentGlobal = currentGlobal[pathSegment];
8105
- if (!currentGlobal) {
8106
- return null;
7785
+ }
7786
+ }
7787
+ function renderStatementList(statements, code, start, end, options) {
7788
+ let currentNode, currentNodeStart, currentNodeNeedsBoundaries, nextNodeStart;
7789
+ let nextNode = statements[0];
7790
+ let nextNodeNeedsBoundaries = !nextNode.included || nextNode.needsBoundaries;
7791
+ if (nextNodeNeedsBoundaries) {
7792
+ nextNodeStart =
7793
+ start + findFirstLineBreakOutsideComment(code.original.slice(start, nextNode.start))[1];
7794
+ }
7795
+ for (let nextIndex = 1; nextIndex <= statements.length; nextIndex++) {
7796
+ currentNode = nextNode;
7797
+ currentNodeStart = nextNodeStart;
7798
+ currentNodeNeedsBoundaries = nextNodeNeedsBoundaries;
7799
+ nextNode = statements[nextIndex];
7800
+ nextNodeNeedsBoundaries =
7801
+ nextNode === undefined ? false : !nextNode.included || nextNode.needsBoundaries;
7802
+ if (currentNodeNeedsBoundaries || nextNodeNeedsBoundaries) {
7803
+ nextNodeStart =
7804
+ currentNode.end +
7805
+ findFirstLineBreakOutsideComment(code.original.slice(currentNode.end, nextNode === undefined ? end : nextNode.start))[1];
7806
+ if (currentNode.included) {
7807
+ currentNodeNeedsBoundaries
7808
+ ? currentNode.render(code, options, {
7809
+ end: nextNodeStart,
7810
+ start: currentNodeStart
7811
+ })
7812
+ : currentNode.render(code, options);
7813
+ }
7814
+ else {
7815
+ treeshakeNode(currentNode, code, currentNodeStart, nextNodeStart);
7816
+ }
7817
+ }
7818
+ else {
7819
+ currentNode.render(code, options);
8107
7820
  }
8108
7821
  }
8109
- return currentGlobal[ValueProperties];
8110
7822
  }
8111
-
8112
- class GlobalVariable extends Variable {
8113
- constructor() {
8114
- super(...arguments);
8115
- // Ensure we use live-bindings for globals as we do not know if they have
8116
- // been reassigned
8117
- this.isReassigned = true;
7823
+ // This assumes that the first character is not part of the first node
7824
+ function getCommaSeparatedNodesWithBoundaries(nodes, code, start, end) {
7825
+ const splitUpNodes = [];
7826
+ let node, nextNode, nextNodeStart, contentEnd, char;
7827
+ let separator = start - 1;
7828
+ for (let nextIndex = 0; nextIndex < nodes.length; nextIndex++) {
7829
+ nextNode = nodes[nextIndex];
7830
+ if (node !== undefined) {
7831
+ separator =
7832
+ node.end +
7833
+ findFirstOccurrenceOutsideComment(code.original.slice(node.end, nextNode.start), ',');
7834
+ }
7835
+ nextNodeStart = contentEnd =
7836
+ separator +
7837
+ 1 +
7838
+ findFirstLineBreakOutsideComment(code.original.slice(separator + 1, nextNode.start))[1];
7839
+ while (((char = code.original.charCodeAt(nextNodeStart)),
7840
+ char === 32 /*" "*/ || char === 9 /*"\t"*/ || char === 10 /*"\n"*/ || char === 13) /*"\r"*/)
7841
+ nextNodeStart++;
7842
+ if (node !== undefined) {
7843
+ splitUpNodes.push({
7844
+ contentEnd,
7845
+ end: nextNodeStart,
7846
+ node,
7847
+ separator,
7848
+ start
7849
+ });
7850
+ }
7851
+ node = nextNode;
7852
+ start = nextNodeStart;
8118
7853
  }
8119
- getLiteralValueAtPath(path, _recursionTracker, _origin) {
8120
- return getGlobalAtPath([this.name, ...path]) ? UnknownTruthyValue : UnknownValue;
7854
+ splitUpNodes.push({
7855
+ contentEnd: end,
7856
+ end,
7857
+ node: node,
7858
+ separator: null,
7859
+ start
7860
+ });
7861
+ return splitUpNodes;
7862
+ }
7863
+ // This assumes there are only white-space and comments between start and end
7864
+ function removeLineBreaks(code, start, end) {
7865
+ while (true) {
7866
+ const [removeStart, removeEnd] = findFirstLineBreakOutsideComment(code.original.slice(start, end));
7867
+ if (removeStart === -1) {
7868
+ break;
7869
+ }
7870
+ code.remove(start + removeStart, (start += removeEnd));
8121
7871
  }
8122
- hasEffectsWhenAccessedAtPath(path) {
8123
- if (path.length === 0) {
8124
- // Technically, "undefined" is a global variable of sorts
8125
- return this.name !== 'undefined' && !getGlobalAtPath([this.name]);
7872
+ }
7873
+
7874
+ class BlockScope extends ChildScope {
7875
+ addDeclaration(identifier, context, init, isHoisted) {
7876
+ if (isHoisted) {
7877
+ const variable = this.parent.addDeclaration(identifier, context, init, isHoisted);
7878
+ // Necessary to make sure the init is deoptimized for conditional declarations.
7879
+ // We cannot call deoptimizePath here.
7880
+ variable.markInitializersForDeoptimization();
7881
+ return variable;
7882
+ }
7883
+ else {
7884
+ return super.addDeclaration(identifier, context, init, false);
7885
+ }
7886
+ }
7887
+ }
7888
+
7889
+ class ExpressionStatement extends NodeBase {
7890
+ initialise() {
7891
+ if (this.directive &&
7892
+ this.directive !== 'use strict' &&
7893
+ this.parent.type === Program$1) {
7894
+ this.context.warn(
7895
+ // This is necessary, because either way (deleting or not) can lead to errors.
7896
+ {
7897
+ code: 'MODULE_LEVEL_DIRECTIVE',
7898
+ message: `Module level directives cause errors when bundled, '${this.directive}' was ignored.`
7899
+ }, this.start);
8126
7900
  }
8127
- return !getGlobalAtPath([this.name, ...path].slice(0, -1));
8128
7901
  }
8129
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
8130
- const globalAtPath = getGlobalAtPath([this.name, ...path]);
8131
- return !globalAtPath || globalAtPath.hasEffectsWhenCalled(callOptions, context);
7902
+ render(code, options) {
7903
+ super.render(code, options);
7904
+ if (this.included)
7905
+ this.insertSemicolon(code);
7906
+ }
7907
+ shouldBeIncluded(context) {
7908
+ if (this.directive && this.directive !== 'use strict')
7909
+ return this.parent.type !== Program$1;
7910
+ return super.shouldBeIncluded(context);
8132
7911
  }
7912
+ applyDeoptimizations() { }
8133
7913
  }
8134
7914
 
8135
- const tdzVariableKinds = {
8136
- __proto__: null,
8137
- class: true,
8138
- const: true,
8139
- let: true,
8140
- var: true
8141
- };
8142
- class Identifier extends NodeBase {
7915
+ class BlockStatement extends NodeBase {
8143
7916
  constructor() {
8144
7917
  super(...arguments);
8145
- this.variable = null;
8146
- this.deoptimized = false;
8147
- this.isTDZAccess = null;
7918
+ this.directlyIncluded = false;
8148
7919
  }
8149
- addExportedVariables(variables, exportNamesByVariable) {
8150
- if (exportNamesByVariable.has(this.variable)) {
8151
- variables.push(this.variable);
7920
+ addImplicitReturnExpressionToScope() {
7921
+ const lastStatement = this.body[this.body.length - 1];
7922
+ if (!lastStatement || lastStatement.type !== ReturnStatement$1) {
7923
+ this.scope.addReturnExpression(UNKNOWN_EXPRESSION);
8152
7924
  }
8153
7925
  }
8154
- bind() {
8155
- if (!this.variable && is_reference(this, this.parent)) {
8156
- this.variable = this.scope.findVariable(this.name);
8157
- this.variable.addReference(this);
8158
- }
7926
+ createScope(parentScope) {
7927
+ this.scope = this.parent.preventChildBlockScope
7928
+ ? parentScope
7929
+ : new BlockScope(parentScope);
8159
7930
  }
8160
- declare(kind, init) {
8161
- let variable;
8162
- const { treeshake } = this.context.options;
8163
- switch (kind) {
8164
- case 'var':
8165
- variable = this.scope.addDeclaration(this, this.context, init, true);
8166
- if (treeshake && treeshake.correctVarValueBeforeDeclaration) {
8167
- // Necessary to make sure the init is deoptimized. We cannot call deoptimizePath here.
8168
- variable.markInitializersForDeoptimization();
8169
- }
8170
- break;
8171
- case 'function':
8172
- // in strict mode, functions are only hoisted within a scope but not across block scopes
8173
- variable = this.scope.addDeclaration(this, this.context, init, false);
8174
- break;
8175
- case 'let':
8176
- case 'const':
8177
- case 'class':
8178
- variable = this.scope.addDeclaration(this, this.context, init, false);
8179
- break;
8180
- case 'parameter':
8181
- variable = this.scope.addParameterDeclaration(this);
7931
+ hasEffects(context) {
7932
+ if (this.deoptimizeBody)
7933
+ return true;
7934
+ for (const node of this.body) {
7935
+ if (context.brokenFlow)
8182
7936
  break;
8183
- /* istanbul ignore next */
8184
- default:
8185
- /* istanbul ignore next */
8186
- throw new Error(`Internal Error: Unexpected identifier kind ${kind}.`);
7937
+ if (node.hasEffects(context))
7938
+ return true;
8187
7939
  }
8188
- variable.kind = kind;
8189
- return [(this.variable = variable)];
7940
+ return false;
7941
+ }
7942
+ include(context, includeChildrenRecursively) {
7943
+ if (!(this.deoptimizeBody && this.directlyIncluded)) {
7944
+ this.included = true;
7945
+ this.directlyIncluded = true;
7946
+ if (this.deoptimizeBody)
7947
+ includeChildrenRecursively = true;
7948
+ for (const node of this.body) {
7949
+ if (includeChildrenRecursively || node.shouldBeIncluded(context))
7950
+ node.include(context, includeChildrenRecursively);
7951
+ }
7952
+ }
7953
+ }
7954
+ initialise() {
7955
+ const firstBodyStatement = this.body[0];
7956
+ this.deoptimizeBody =
7957
+ firstBodyStatement instanceof ExpressionStatement &&
7958
+ firstBodyStatement.directive === 'use asm';
7959
+ }
7960
+ render(code, options) {
7961
+ if (this.body.length) {
7962
+ renderStatementList(this.body, code, this.start + 1, this.end - 1, options);
7963
+ }
7964
+ else {
7965
+ super.render(code, options);
7966
+ }
7967
+ }
7968
+ }
7969
+
7970
+ class RestElement extends NodeBase {
7971
+ constructor() {
7972
+ super(...arguments);
7973
+ this.declarationInit = null;
7974
+ }
7975
+ addExportedVariables(variables, exportNamesByVariable) {
7976
+ this.argument.addExportedVariables(variables, exportNamesByVariable);
7977
+ }
7978
+ declare(kind, init) {
7979
+ this.declarationInit = init;
7980
+ return this.argument.declare(kind, UNKNOWN_EXPRESSION);
8190
7981
  }
8191
7982
  deoptimizePath(path) {
8192
- if (path.length === 0 && !this.scope.contains(this.name)) {
8193
- this.disallowImportReassignment();
8194
- }
8195
- this.variable.deoptimizePath(path);
7983
+ path.length === 0 && this.argument.deoptimizePath(EMPTY_PATH);
8196
7984
  }
8197
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
8198
- this.variable.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
7985
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
7986
+ return (path.length > 0 ||
7987
+ this.argument.hasEffectsOnInteractionAtPath(EMPTY_PATH, interaction, context));
8199
7988
  }
8200
- getLiteralValueAtPath(path, recursionTracker, origin) {
8201
- return this.getVariableRespectingTDZ().getLiteralValueAtPath(path, recursionTracker, origin);
7989
+ markDeclarationReached() {
7990
+ this.argument.markDeclarationReached();
8202
7991
  }
8203
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
8204
- return this.getVariableRespectingTDZ().getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
7992
+ applyDeoptimizations() {
7993
+ this.deoptimized = true;
7994
+ if (this.declarationInit !== null) {
7995
+ this.declarationInit.deoptimizePath([UnknownKey, UnknownKey]);
7996
+ this.context.requestTreeshakingPass();
7997
+ }
8205
7998
  }
8206
- hasEffects() {
8207
- if (!this.deoptimized)
8208
- this.applyDeoptimizations();
8209
- if (this.isPossibleTDZ() && this.variable.kind !== 'var') {
8210
- return true;
7999
+ }
8000
+
8001
+ class FunctionBase extends NodeBase {
8002
+ constructor() {
8003
+ super(...arguments);
8004
+ this.objectEntity = null;
8005
+ this.deoptimizedReturn = false;
8006
+ }
8007
+ deoptimizePath(path) {
8008
+ this.getObjectEntity().deoptimizePath(path);
8009
+ if (path.length === 1 && path[0] === UnknownKey) {
8010
+ // A reassignment of UNKNOWN_PATH is considered equivalent to having lost track
8011
+ // which means the return expression needs to be reassigned
8012
+ this.scope.getReturnExpression().deoptimizePath(UNKNOWN_PATH);
8211
8013
  }
8212
- return (this.context.options.treeshake.unknownGlobalSideEffects &&
8213
- this.variable instanceof GlobalVariable &&
8214
- this.variable.hasEffectsWhenAccessedAtPath(EMPTY_PATH));
8215
8014
  }
8216
- hasEffectsWhenAccessedAtPath(path, context) {
8217
- return (this.variable !== null &&
8218
- this.getVariableRespectingTDZ().hasEffectsWhenAccessedAtPath(path, context));
8015
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
8016
+ if (path.length > 0) {
8017
+ this.getObjectEntity().deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
8018
+ }
8219
8019
  }
8220
- hasEffectsWhenAssignedAtPath(path, context) {
8221
- return (path.length > 0 ? this.getVariableRespectingTDZ() : this.variable).hasEffectsWhenAssignedAtPath(path, context);
8020
+ getLiteralValueAtPath(path, recursionTracker, origin) {
8021
+ return this.getObjectEntity().getLiteralValueAtPath(path, recursionTracker, origin);
8222
8022
  }
8223
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
8224
- return this.getVariableRespectingTDZ().hasEffectsWhenCalledAtPath(path, callOptions, context);
8023
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
8024
+ if (path.length > 0) {
8025
+ return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
8026
+ }
8027
+ if (this.async) {
8028
+ if (!this.deoptimizedReturn) {
8029
+ this.deoptimizedReturn = true;
8030
+ this.scope.getReturnExpression().deoptimizePath(UNKNOWN_PATH);
8031
+ this.context.requestTreeshakingPass();
8032
+ }
8033
+ return UNKNOWN_EXPRESSION;
8034
+ }
8035
+ return this.scope.getReturnExpression();
8225
8036
  }
8226
- include() {
8227
- if (!this.deoptimized)
8228
- this.applyDeoptimizations();
8229
- if (!this.included) {
8230
- this.included = true;
8231
- if (this.variable !== null) {
8232
- this.context.includeVariableInModule(this.variable);
8037
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8038
+ if (path.length > 0 || interaction.type !== INTERACTION_CALLED) {
8039
+ return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
8040
+ }
8041
+ if (this.async) {
8042
+ const { propertyReadSideEffects } = this.context.options
8043
+ .treeshake;
8044
+ const returnExpression = this.scope.getReturnExpression();
8045
+ if (returnExpression.hasEffectsOnInteractionAtPath(['then'], NODE_INTERACTION_UNKNOWN_CALL, context) ||
8046
+ (propertyReadSideEffects &&
8047
+ (propertyReadSideEffects === 'always' ||
8048
+ returnExpression.hasEffectsOnInteractionAtPath(['then'], NODE_INTERACTION_UNKNOWN_ACCESS, context)))) {
8049
+ return true;
8233
8050
  }
8234
8051
  }
8052
+ for (const param of this.params) {
8053
+ if (param.hasEffects(context))
8054
+ return true;
8055
+ }
8056
+ return false;
8057
+ }
8058
+ include(context, includeChildrenRecursively) {
8059
+ if (!this.deoptimized)
8060
+ this.applyDeoptimizations();
8061
+ this.included = true;
8062
+ const { brokenFlow } = context;
8063
+ context.brokenFlow = BROKEN_FLOW_NONE;
8064
+ this.body.include(context, includeChildrenRecursively);
8065
+ context.brokenFlow = brokenFlow;
8235
8066
  }
8236
8067
  includeCallArguments(context, args) {
8237
- this.variable.includeCallArguments(context, args);
8068
+ this.scope.includeCallArguments(context, args);
8238
8069
  }
8239
- isPossibleTDZ() {
8240
- // return cached value to avoid issues with the next tree-shaking pass
8241
- if (this.isTDZAccess !== null)
8242
- return this.isTDZAccess;
8243
- if (!(this.variable instanceof LocalVariable) ||
8244
- !this.variable.kind ||
8245
- !(this.variable.kind in tdzVariableKinds)) {
8246
- return (this.isTDZAccess = false);
8070
+ initialise() {
8071
+ this.scope.addParameterVariables(this.params.map(param => param.declare('parameter', UNKNOWN_EXPRESSION)), this.params[this.params.length - 1] instanceof RestElement);
8072
+ if (this.body instanceof BlockStatement) {
8073
+ this.body.addImplicitReturnExpressionToScope();
8247
8074
  }
8248
- let decl_id;
8249
- if (this.variable.declarations &&
8250
- this.variable.declarations.length === 1 &&
8251
- (decl_id = this.variable.declarations[0]) &&
8252
- this.start < decl_id.start &&
8253
- closestParentFunctionOrProgram(this) === closestParentFunctionOrProgram(decl_id)) {
8254
- // a variable accessed before its declaration
8255
- // in the same function or at top level of module
8256
- return (this.isTDZAccess = true);
8075
+ else {
8076
+ this.scope.addReturnExpression(this.body);
8257
8077
  }
8258
- if (!this.variable.initReached) {
8259
- // Either a const/let TDZ violation or
8260
- // var use before declaration was encountered.
8261
- return (this.isTDZAccess = true);
8078
+ }
8079
+ parseNode(esTreeNode) {
8080
+ if (esTreeNode.body.type === BlockStatement$1) {
8081
+ this.body = new BlockStatement(esTreeNode.body, this, this.scope.hoistedBodyVarScope);
8262
8082
  }
8263
- return (this.isTDZAccess = false);
8083
+ super.parseNode(esTreeNode);
8264
8084
  }
8265
- markDeclarationReached() {
8266
- this.variable.initReached = true;
8085
+ applyDeoptimizations() { }
8086
+ }
8087
+ FunctionBase.prototype.preventChildBlockScope = true;
8088
+
8089
+ class ArrowFunctionExpression extends FunctionBase {
8090
+ constructor() {
8091
+ super(...arguments);
8092
+ this.objectEntity = null;
8267
8093
  }
8268
- render(code, { snippets: { getPropertyAccess } }, { renderedParentType, isCalleeOfRenderedParent, isShorthandProperty } = BLANK) {
8269
- if (this.variable) {
8270
- const name = this.variable.getName(getPropertyAccess);
8271
- if (name !== this.name) {
8272
- code.overwrite(this.start, this.end, name, {
8273
- contentOnly: true,
8274
- storeName: true
8275
- });
8276
- if (isShorthandProperty) {
8277
- code.prependRight(this.start, `${this.name}: `);
8278
- }
8279
- }
8280
- // In strict mode, any variable named "eval" must be the actual "eval" function
8281
- if (name === 'eval' &&
8282
- renderedParentType === CallExpression$1 &&
8283
- isCalleeOfRenderedParent) {
8284
- code.appendRight(this.start, '0, ');
8094
+ createScope(parentScope) {
8095
+ this.scope = new ReturnValueScope(parentScope, this.context);
8096
+ }
8097
+ hasEffects() {
8098
+ if (!this.deoptimized)
8099
+ this.applyDeoptimizations();
8100
+ return false;
8101
+ }
8102
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8103
+ if (super.hasEffectsOnInteractionAtPath(path, interaction, context))
8104
+ return true;
8105
+ if (interaction.type === INTERACTION_CALLED) {
8106
+ const { ignore, brokenFlow } = context;
8107
+ context.ignore = {
8108
+ breaks: false,
8109
+ continues: false,
8110
+ labels: new Set(),
8111
+ returnYield: true
8112
+ };
8113
+ if (this.body.hasEffects(context))
8114
+ return true;
8115
+ context.ignore = ignore;
8116
+ context.brokenFlow = brokenFlow;
8117
+ }
8118
+ return false;
8119
+ }
8120
+ include(context, includeChildrenRecursively) {
8121
+ super.include(context, includeChildrenRecursively);
8122
+ for (const param of this.params) {
8123
+ if (!(param instanceof Identifier)) {
8124
+ param.include(context, includeChildrenRecursively);
8285
8125
  }
8286
8126
  }
8287
8127
  }
8288
- applyDeoptimizations() {
8289
- this.deoptimized = true;
8290
- if (this.variable instanceof LocalVariable) {
8291
- this.variable.consolidateInitializers();
8292
- this.context.requestTreeshakingPass();
8128
+ getObjectEntity() {
8129
+ if (this.objectEntity !== null) {
8130
+ return this.objectEntity;
8293
8131
  }
8132
+ return (this.objectEntity = new ObjectEntity([], OBJECT_PROTOTYPE));
8294
8133
  }
8295
- disallowImportReassignment() {
8296
- return this.context.error({
8297
- code: 'ILLEGAL_REASSIGNMENT',
8298
- message: `Illegal reassignment to import '${this.name}'`
8299
- }, this.start);
8134
+ }
8135
+
8136
+ function getSystemExportStatement(exportedVariables, { exportNamesByVariable, snippets: { _, getObject, getPropertyAccess } }, modifier = '') {
8137
+ if (exportedVariables.length === 1 &&
8138
+ exportNamesByVariable.get(exportedVariables[0]).length === 1) {
8139
+ const variable = exportedVariables[0];
8140
+ return `exports('${exportNamesByVariable.get(variable)}',${_}${variable.getName(getPropertyAccess)}${modifier})`;
8300
8141
  }
8301
- getVariableRespectingTDZ() {
8302
- if (this.isPossibleTDZ()) {
8303
- return UNKNOWN_EXPRESSION;
8142
+ else {
8143
+ const fields = [];
8144
+ for (const variable of exportedVariables) {
8145
+ for (const exportName of exportNamesByVariable.get(variable)) {
8146
+ fields.push([exportName, variable.getName(getPropertyAccess) + modifier]);
8147
+ }
8304
8148
  }
8305
- return this.variable;
8149
+ return `exports(${getObject(fields, { lineBreakIndent: null })})`;
8306
8150
  }
8307
8151
  }
8308
- function closestParentFunctionOrProgram(node) {
8309
- while (node && !/^Program|Function/.test(node.type)) {
8310
- node = node.parent;
8152
+ function renderSystemExportExpression(exportedVariable, expressionStart, expressionEnd, code, { exportNamesByVariable, snippets: { _ } }) {
8153
+ code.prependRight(expressionStart, `exports('${exportNamesByVariable.get(exportedVariable)}',${_}`);
8154
+ code.appendLeft(expressionEnd, ')');
8155
+ }
8156
+ function renderSystemExportFunction(exportedVariables, expressionStart, expressionEnd, needsParens, code, options) {
8157
+ const { _, getDirectReturnIifeLeft } = options.snippets;
8158
+ code.prependRight(expressionStart, getDirectReturnIifeLeft(['v'], `${getSystemExportStatement(exportedVariables, options)},${_}v`, { needsArrowReturnParens: true, needsWrappedFunction: needsParens }));
8159
+ code.appendLeft(expressionEnd, ')');
8160
+ }
8161
+ function renderSystemExportSequenceAfterExpression(exportedVariable, expressionStart, expressionEnd, needsParens, code, options) {
8162
+ const { _, getPropertyAccess } = options.snippets;
8163
+ code.appendLeft(expressionEnd, `,${_}${getSystemExportStatement([exportedVariable], options)},${_}${exportedVariable.getName(getPropertyAccess)}`);
8164
+ if (needsParens) {
8165
+ code.prependRight(expressionStart, '(');
8166
+ code.appendLeft(expressionEnd, ')');
8167
+ }
8168
+ }
8169
+ function renderSystemExportSequenceBeforeExpression(exportedVariable, expressionStart, expressionEnd, needsParens, code, options, modifier) {
8170
+ const { _ } = options.snippets;
8171
+ code.prependRight(expressionStart, `${getSystemExportStatement([exportedVariable], options, modifier)},${_}`);
8172
+ if (needsParens) {
8173
+ code.prependRight(expressionStart, '(');
8174
+ code.appendLeft(expressionEnd, ')');
8311
8175
  }
8312
- // one of: ArrowFunctionExpression, FunctionDeclaration, FunctionExpression or Program
8313
- return node;
8314
8176
  }
8315
8177
 
8316
8178
  class ObjectPattern extends NodeBase {
@@ -8338,11 +8200,12 @@ class ObjectPattern extends NodeBase {
8338
8200
  }
8339
8201
  }
8340
8202
  }
8341
- hasEffectsWhenAssignedAtPath(path, context) {
8342
- if (path.length > 0)
8343
- return true;
8203
+ hasEffectsOnInteractionAtPath(
8204
+ // At the moment, this is only triggered for assignment left-hand sides,
8205
+ // where the path is empty
8206
+ _path, interaction, context) {
8344
8207
  for (const property of this.properties) {
8345
- if (property.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context))
8208
+ if (property.hasEffectsOnInteractionAtPath(EMPTY_PATH, interaction, context))
8346
8209
  return true;
8347
8210
  }
8348
8211
  return false;
@@ -8355,80 +8218,79 @@ class ObjectPattern extends NodeBase {
8355
8218
  }
8356
8219
 
8357
8220
  class AssignmentExpression extends NodeBase {
8358
- constructor() {
8359
- super(...arguments);
8360
- this.deoptimized = false;
8361
- }
8362
8221
  hasEffects(context) {
8363
- if (!this.deoptimized)
8222
+ const { deoptimized, left, right } = this;
8223
+ if (!deoptimized)
8364
8224
  this.applyDeoptimizations();
8365
- return (this.right.hasEffects(context) ||
8366
- this.left.hasEffects(context) ||
8367
- this.left.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context));
8225
+ // MemberExpressions do not access the property before assignments if the
8226
+ // operator is '='.
8227
+ return (right.hasEffects(context) || left.hasEffectsAsAssignmentTarget(context, this.operator !== '='));
8368
8228
  }
8369
- hasEffectsWhenAccessedAtPath(path, context) {
8370
- return path.length > 0 && this.right.hasEffectsWhenAccessedAtPath(path, context);
8229
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8230
+ return this.right.hasEffectsOnInteractionAtPath(path, interaction, context);
8371
8231
  }
8372
8232
  include(context, includeChildrenRecursively) {
8373
- if (!this.deoptimized)
8233
+ const { deoptimized, left, right, operator } = this;
8234
+ if (!deoptimized)
8374
8235
  this.applyDeoptimizations();
8375
8236
  this.included = true;
8376
- let hasEffectsContext;
8377
8237
  if (includeChildrenRecursively ||
8378
- this.operator !== '=' ||
8379
- this.left.included ||
8380
- ((hasEffectsContext = createHasEffectsContext()),
8381
- this.left.hasEffects(hasEffectsContext) ||
8382
- this.left.hasEffectsWhenAssignedAtPath(EMPTY_PATH, hasEffectsContext))) {
8383
- this.left.include(context, includeChildrenRecursively);
8238
+ operator !== '=' ||
8239
+ left.included ||
8240
+ left.hasEffectsAsAssignmentTarget(createHasEffectsContext(), false)) {
8241
+ left.includeAsAssignmentTarget(context, includeChildrenRecursively, operator !== '=');
8384
8242
  }
8385
- this.right.include(context, includeChildrenRecursively);
8243
+ right.include(context, includeChildrenRecursively);
8244
+ }
8245
+ initialise() {
8246
+ this.left.setAssignedValue(this.right);
8386
8247
  }
8387
8248
  render(code, options, { preventASI, renderedParentType, renderedSurroundingElement } = BLANK) {
8388
- if (this.left.included) {
8389
- this.left.render(code, options);
8390
- this.right.render(code, options);
8249
+ const { left, right, start, end, parent } = this;
8250
+ if (left.included) {
8251
+ left.render(code, options);
8252
+ right.render(code, options);
8391
8253
  }
8392
8254
  else {
8393
- const inclusionStart = findNonWhiteSpace(code.original, findFirstOccurrenceOutsideComment(code.original, '=', this.left.end) + 1);
8394
- code.remove(this.start, inclusionStart);
8255
+ const inclusionStart = findNonWhiteSpace(code.original, findFirstOccurrenceOutsideComment(code.original, '=', left.end) + 1);
8256
+ code.remove(start, inclusionStart);
8395
8257
  if (preventASI) {
8396
- removeLineBreaks(code, inclusionStart, this.right.start);
8258
+ removeLineBreaks(code, inclusionStart, right.start);
8397
8259
  }
8398
- this.right.render(code, options, {
8399
- renderedParentType: renderedParentType || this.parent.type,
8400
- renderedSurroundingElement: renderedSurroundingElement || this.parent.type
8260
+ right.render(code, options, {
8261
+ renderedParentType: renderedParentType || parent.type,
8262
+ renderedSurroundingElement: renderedSurroundingElement || parent.type
8401
8263
  });
8402
8264
  }
8403
8265
  if (options.format === 'system') {
8404
- if (this.left instanceof Identifier) {
8405
- const variable = this.left.variable;
8266
+ if (left instanceof Identifier) {
8267
+ const variable = left.variable;
8406
8268
  const exportNames = options.exportNamesByVariable.get(variable);
8407
8269
  if (exportNames) {
8408
8270
  if (exportNames.length === 1) {
8409
- renderSystemExportExpression(variable, this.start, this.end, code, options);
8271
+ renderSystemExportExpression(variable, start, end, code, options);
8410
8272
  }
8411
8273
  else {
8412
- renderSystemExportSequenceAfterExpression(variable, this.start, this.end, this.parent.type !== ExpressionStatement$1, code, options);
8274
+ renderSystemExportSequenceAfterExpression(variable, start, end, parent.type !== ExpressionStatement$1, code, options);
8413
8275
  }
8414
8276
  return;
8415
8277
  }
8416
8278
  }
8417
8279
  else {
8418
8280
  const systemPatternExports = [];
8419
- this.left.addExportedVariables(systemPatternExports, options.exportNamesByVariable);
8281
+ left.addExportedVariables(systemPatternExports, options.exportNamesByVariable);
8420
8282
  if (systemPatternExports.length > 0) {
8421
- renderSystemExportFunction(systemPatternExports, this.start, this.end, renderedSurroundingElement === ExpressionStatement$1, code, options);
8283
+ renderSystemExportFunction(systemPatternExports, start, end, renderedSurroundingElement === ExpressionStatement$1, code, options);
8422
8284
  return;
8423
8285
  }
8424
8286
  }
8425
8287
  }
8426
- if (this.left.included &&
8427
- this.left instanceof ObjectPattern &&
8288
+ if (left.included &&
8289
+ left instanceof ObjectPattern &&
8428
8290
  (renderedSurroundingElement === ExpressionStatement$1 ||
8429
8291
  renderedSurroundingElement === ArrowFunctionExpression$1)) {
8430
- code.appendRight(this.start, '(');
8431
- code.prependLeft(this.end, ')');
8292
+ code.appendRight(start, '(');
8293
+ code.prependLeft(end, ')');
8432
8294
  }
8433
8295
  }
8434
8296
  applyDeoptimizations() {
@@ -8439,18 +8301,40 @@ class AssignmentExpression extends NodeBase {
8439
8301
  }
8440
8302
  }
8441
8303
 
8304
+ class AssignmentPattern extends NodeBase {
8305
+ addExportedVariables(variables, exportNamesByVariable) {
8306
+ this.left.addExportedVariables(variables, exportNamesByVariable);
8307
+ }
8308
+ declare(kind, init) {
8309
+ return this.left.declare(kind, init);
8310
+ }
8311
+ deoptimizePath(path) {
8312
+ path.length === 0 && this.left.deoptimizePath(path);
8313
+ }
8314
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8315
+ return (path.length > 0 || this.left.hasEffectsOnInteractionAtPath(EMPTY_PATH, interaction, context));
8316
+ }
8317
+ markDeclarationReached() {
8318
+ this.left.markDeclarationReached();
8319
+ }
8320
+ render(code, options, { isShorthandProperty } = BLANK) {
8321
+ this.left.render(code, options, { isShorthandProperty });
8322
+ this.right.render(code, options);
8323
+ }
8324
+ applyDeoptimizations() {
8325
+ this.deoptimized = true;
8326
+ this.left.deoptimizePath(EMPTY_PATH);
8327
+ this.right.deoptimizePath(UNKNOWN_PATH);
8328
+ this.context.requestTreeshakingPass();
8329
+ }
8330
+ }
8331
+
8442
8332
  class ArgumentsVariable extends LocalVariable {
8443
8333
  constructor(context) {
8444
8334
  super('arguments', null, UNKNOWN_EXPRESSION, context);
8445
8335
  }
8446
- hasEffectsWhenAccessedAtPath(path) {
8447
- return path.length > 1;
8448
- }
8449
- hasEffectsWhenAssignedAtPath() {
8450
- return true;
8451
- }
8452
- hasEffectsWhenCalledAtPath() {
8453
- return true;
8336
+ hasEffectsOnInteractionAtPath(path, { type }) {
8337
+ return type !== INTERACTION_ACCESSED || path.length > 1;
8454
8338
  }
8455
8339
  }
8456
8340
 
@@ -8466,8 +8350,8 @@ class ThisVariable extends LocalVariable {
8466
8350
  for (const path of this.deoptimizedPaths) {
8467
8351
  entity.deoptimizePath(path);
8468
8352
  }
8469
- for (const thisDeoptimization of this.thisDeoptimizationList) {
8470
- this.applyThisDeoptimizationEvent(entity, thisDeoptimization);
8353
+ for (const { interaction, path } of this.thisDeoptimizationList) {
8354
+ entity.deoptimizeThisOnInteractionAtPath(interaction, path, SHARED_RECURSION_TRACKER);
8471
8355
  }
8472
8356
  this.entitiesToBeDeoptimized.add(entity);
8473
8357
  }
@@ -8481,29 +8365,21 @@ class ThisVariable extends LocalVariable {
8481
8365
  entity.deoptimizePath(path);
8482
8366
  }
8483
8367
  }
8484
- deoptimizeThisOnEventAtPath(event, path, thisParameter) {
8368
+ deoptimizeThisOnInteractionAtPath(interaction, path) {
8485
8369
  const thisDeoptimization = {
8486
- event,
8487
- path,
8488
- thisParameter
8370
+ interaction,
8371
+ path
8489
8372
  };
8490
- if (!this.thisDeoptimizations.trackEntityAtPathAndGetIfTracked(path, event, thisParameter)) {
8373
+ if (!this.thisDeoptimizations.trackEntityAtPathAndGetIfTracked(path, interaction.type, interaction.thisArg)) {
8491
8374
  for (const entity of this.entitiesToBeDeoptimized) {
8492
- this.applyThisDeoptimizationEvent(entity, thisDeoptimization);
8375
+ entity.deoptimizeThisOnInteractionAtPath(interaction, path, SHARED_RECURSION_TRACKER);
8493
8376
  }
8494
8377
  this.thisDeoptimizationList.push(thisDeoptimization);
8495
8378
  }
8496
8379
  }
8497
- hasEffectsWhenAccessedAtPath(path, context) {
8498
- return (this.getInit(context).hasEffectsWhenAccessedAtPath(path, context) ||
8499
- super.hasEffectsWhenAccessedAtPath(path, context));
8500
- }
8501
- hasEffectsWhenAssignedAtPath(path, context) {
8502
- return (this.getInit(context).hasEffectsWhenAssignedAtPath(path, context) ||
8503
- super.hasEffectsWhenAssignedAtPath(path, context));
8504
- }
8505
- applyThisDeoptimizationEvent(entity, { event, path, thisParameter }) {
8506
- entity.deoptimizeThisOnEventAtPath(event, path, thisParameter === this ? entity : thisParameter, SHARED_RECURSION_TRACKER);
8380
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8381
+ return (this.getInit(context).hasEffectsOnInteractionAtPath(path, interaction, context) ||
8382
+ super.hasEffectsOnInteractionAtPath(path, interaction, context));
8507
8383
  }
8508
8384
  getInit(context) {
8509
8385
  return context.replacedVariableInits.get(this) || UNKNOWN_EXPRESSION;
@@ -8539,50 +8415,56 @@ class FunctionNode extends FunctionBase {
8539
8415
  createScope(parentScope) {
8540
8416
  this.scope = new FunctionScope(parentScope, this.context);
8541
8417
  }
8542
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
8543
- super.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
8544
- if (event === EVENT_CALLED && path.length === 0) {
8545
- this.scope.thisVariable.addEntityToBeDeoptimized(thisParameter);
8418
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
8419
+ super.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
8420
+ if (interaction.type === INTERACTION_CALLED && path.length === 0) {
8421
+ this.scope.thisVariable.addEntityToBeDeoptimized(interaction.thisArg);
8546
8422
  }
8547
8423
  }
8548
- hasEffects() {
8424
+ hasEffects(context) {
8549
8425
  var _a;
8550
8426
  if (!this.deoptimized)
8551
8427
  this.applyDeoptimizations();
8552
- return !!((_a = this.id) === null || _a === void 0 ? void 0 : _a.hasEffects());
8428
+ return !!((_a = this.id) === null || _a === void 0 ? void 0 : _a.hasEffects(context));
8553
8429
  }
8554
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
8555
- if (super.hasEffectsWhenCalledAtPath(path, callOptions, context))
8556
- return true;
8557
- const thisInit = context.replacedVariableInits.get(this.scope.thisVariable);
8558
- context.replacedVariableInits.set(this.scope.thisVariable, callOptions.withNew
8559
- ? new ObjectEntity(Object.create(null), OBJECT_PROTOTYPE)
8560
- : UNKNOWN_EXPRESSION);
8561
- const { brokenFlow, ignore } = context;
8562
- context.ignore = {
8563
- breaks: false,
8564
- continues: false,
8565
- labels: new Set(),
8566
- returnYield: true
8567
- };
8568
- if (this.body.hasEffects(context))
8430
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8431
+ if (super.hasEffectsOnInteractionAtPath(path, interaction, context))
8569
8432
  return true;
8570
- context.brokenFlow = brokenFlow;
8571
- if (thisInit) {
8572
- context.replacedVariableInits.set(this.scope.thisVariable, thisInit);
8573
- }
8574
- else {
8575
- context.replacedVariableInits.delete(this.scope.thisVariable);
8433
+ if (interaction.type === INTERACTION_CALLED) {
8434
+ const thisInit = context.replacedVariableInits.get(this.scope.thisVariable);
8435
+ context.replacedVariableInits.set(this.scope.thisVariable, interaction.withNew
8436
+ ? new ObjectEntity(Object.create(null), OBJECT_PROTOTYPE)
8437
+ : UNKNOWN_EXPRESSION);
8438
+ const { brokenFlow, ignore } = context;
8439
+ context.ignore = {
8440
+ breaks: false,
8441
+ continues: false,
8442
+ labels: new Set(),
8443
+ returnYield: true
8444
+ };
8445
+ if (this.body.hasEffects(context))
8446
+ return true;
8447
+ context.brokenFlow = brokenFlow;
8448
+ if (thisInit) {
8449
+ context.replacedVariableInits.set(this.scope.thisVariable, thisInit);
8450
+ }
8451
+ else {
8452
+ context.replacedVariableInits.delete(this.scope.thisVariable);
8453
+ }
8454
+ context.ignore = ignore;
8576
8455
  }
8577
- context.ignore = ignore;
8578
8456
  return false;
8579
8457
  }
8580
- include(context, includeChildrenRecursively, { includeWithoutParameterDefaults } = BLANK) {
8458
+ include(context, includeChildrenRecursively) {
8581
8459
  var _a;
8460
+ super.include(context, includeChildrenRecursively);
8582
8461
  (_a = this.id) === null || _a === void 0 ? void 0 : _a.include();
8583
- super.include(context, includeChildrenRecursively, {
8584
- includeWithoutParameterDefaults: includeWithoutParameterDefaults && !this.scope.argumentsVariable.included
8585
- });
8462
+ const hasArguments = this.scope.argumentsVariable.included;
8463
+ for (const param of this.params) {
8464
+ if (!(param instanceof Identifier) || hasArguments) {
8465
+ param.include(context, includeChildrenRecursively);
8466
+ }
8467
+ }
8586
8468
  }
8587
8469
  initialise() {
8588
8470
  var _a;
@@ -8604,10 +8486,6 @@ class FunctionNode extends FunctionBase {
8604
8486
  }
8605
8487
 
8606
8488
  class AwaitExpression extends NodeBase {
8607
- constructor() {
8608
- super(...arguments);
8609
- this.deoptimized = false;
8610
- }
8611
8489
  hasEffects() {
8612
8490
  if (!this.deoptimized)
8613
8491
  this.applyDeoptimizations();
@@ -8681,8 +8559,8 @@ class BinaryExpression extends NodeBase {
8681
8559
  return true;
8682
8560
  return super.hasEffects(context);
8683
8561
  }
8684
- hasEffectsWhenAccessedAtPath(path) {
8685
- return path.length > 1;
8562
+ hasEffectsOnInteractionAtPath(path, { type }) {
8563
+ return type !== INTERACTION_ACCESSED || path.length > 1;
8686
8564
  }
8687
8565
  render(code, options, { renderedSurroundingElement } = BLANK) {
8688
8566
  this.left.render(code, options, { renderedSurroundingElement });
@@ -8715,8 +8593,33 @@ class BreakStatement extends NodeBase {
8715
8593
  }
8716
8594
  }
8717
8595
 
8596
+ function renderCallArguments(code, options, node) {
8597
+ if (node.arguments.length > 0) {
8598
+ if (node.arguments[node.arguments.length - 1].included) {
8599
+ for (const arg of node.arguments) {
8600
+ arg.render(code, options);
8601
+ }
8602
+ }
8603
+ else {
8604
+ let lastIncludedIndex = node.arguments.length - 2;
8605
+ while (lastIncludedIndex >= 0 && !node.arguments[lastIncludedIndex].included) {
8606
+ lastIncludedIndex--;
8607
+ }
8608
+ if (lastIncludedIndex >= 0) {
8609
+ for (let index = 0; index <= lastIncludedIndex; index++) {
8610
+ node.arguments[index].render(code, options);
8611
+ }
8612
+ code.remove(findFirstOccurrenceOutsideComment(code.original, ',', node.arguments[lastIncludedIndex].end), node.end - 1);
8613
+ }
8614
+ else {
8615
+ code.remove(findFirstOccurrenceOutsideComment(code.original, '(', node.callee.end) + 1, node.end - 1);
8616
+ }
8617
+ }
8618
+ }
8619
+ }
8620
+
8718
8621
  class Literal extends NodeBase {
8719
- deoptimizeThisOnEventAtPath() { }
8622
+ deoptimizeThisOnInteractionAtPath() { }
8720
8623
  getLiteralValueAtPath(path) {
8721
8624
  if (path.length > 0 ||
8722
8625
  // unknown literals can also be null but do not start with an "n"
@@ -8733,17 +8636,16 @@ class Literal extends NodeBase {
8733
8636
  return UNKNOWN_EXPRESSION;
8734
8637
  return getMemberReturnExpressionWhenCalled(this.members, path[0]);
8735
8638
  }
8736
- hasEffectsWhenAccessedAtPath(path) {
8737
- if (this.value === null) {
8738
- return path.length > 0;
8739
- }
8740
- return path.length > 1;
8741
- }
8742
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
8743
- if (path.length === 1) {
8744
- return hasMemberEffectWhenCalled(this.members, path[0], callOptions, context);
8639
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8640
+ switch (interaction.type) {
8641
+ case INTERACTION_ACCESSED:
8642
+ return path.length > (this.value === null ? 0 : 1);
8643
+ case INTERACTION_ASSIGNED:
8644
+ return true;
8645
+ case INTERACTION_CALLED:
8646
+ return (path.length !== 1 ||
8647
+ hasMemberEffectWhenCalled(this.members, path[0], interaction, context));
8745
8648
  }
8746
- return true;
8747
8649
  }
8748
8650
  initialise() {
8749
8651
  this.members = getLiteralMembersForValue(this.value);
@@ -8801,7 +8703,7 @@ class MemberExpression extends NodeBase {
8801
8703
  constructor() {
8802
8704
  super(...arguments);
8803
8705
  this.variable = null;
8804
- this.deoptimized = false;
8706
+ this.assignmentDeoptimized = false;
8805
8707
  this.bound = false;
8806
8708
  this.expressionsToBeDeoptimized = [];
8807
8709
  this.replacement = null;
@@ -8811,7 +8713,7 @@ class MemberExpression extends NodeBase {
8811
8713
  const path = getPathIfNotComputed(this);
8812
8714
  const baseVariable = path && this.scope.findVariable(path[0].key);
8813
8715
  if (baseVariable && baseVariable.isNamespace) {
8814
- const resolvedVariable = this.resolveNamespaceVariables(baseVariable, path.slice(1));
8716
+ const resolvedVariable = resolveNamespaceVariables(baseVariable, path.slice(1), this.context);
8815
8717
  if (!resolvedVariable) {
8816
8718
  super.bind();
8817
8719
  }
@@ -8852,21 +8754,21 @@ class MemberExpression extends NodeBase {
8852
8754
  }
8853
8755
  }
8854
8756
  }
8855
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
8757
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
8856
8758
  if (this.variable) {
8857
- this.variable.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
8759
+ this.variable.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
8858
8760
  }
8859
8761
  else if (!this.replacement) {
8860
8762
  if (path.length < MAX_PATH_DEPTH) {
8861
- this.object.deoptimizeThisOnEventAtPath(event, [this.getPropertyKey(), ...path], thisParameter, recursionTracker);
8763
+ this.object.deoptimizeThisOnInteractionAtPath(interaction, [this.getPropertyKey(), ...path], recursionTracker);
8862
8764
  }
8863
8765
  else {
8864
- thisParameter.deoptimizePath(UNKNOWN_PATH);
8766
+ interaction.thisArg.deoptimizePath(UNKNOWN_PATH);
8865
8767
  }
8866
8768
  }
8867
8769
  }
8868
8770
  getLiteralValueAtPath(path, recursionTracker, origin) {
8869
- if (this.variable !== null) {
8771
+ if (this.variable) {
8870
8772
  return this.variable.getLiteralValueAtPath(path, recursionTracker, origin);
8871
8773
  }
8872
8774
  if (this.replacement) {
@@ -8878,81 +8780,62 @@ class MemberExpression extends NodeBase {
8878
8780
  }
8879
8781
  return UnknownValue;
8880
8782
  }
8881
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
8882
- if (this.variable !== null) {
8883
- return this.variable.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
8783
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
8784
+ if (this.variable) {
8785
+ return this.variable.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
8884
8786
  }
8885
8787
  if (this.replacement) {
8886
8788
  return UNKNOWN_EXPRESSION;
8887
8789
  }
8888
8790
  this.expressionsToBeDeoptimized.push(origin);
8889
8791
  if (path.length < MAX_PATH_DEPTH) {
8890
- return this.object.getReturnExpressionWhenCalledAtPath([this.getPropertyKey(), ...path], callOptions, recursionTracker, origin);
8792
+ return this.object.getReturnExpressionWhenCalledAtPath([this.getPropertyKey(), ...path], interaction, recursionTracker, origin);
8891
8793
  }
8892
8794
  return UNKNOWN_EXPRESSION;
8893
8795
  }
8894
8796
  hasEffects(context) {
8895
8797
  if (!this.deoptimized)
8896
8798
  this.applyDeoptimizations();
8897
- const { propertyReadSideEffects } = this.context.options
8898
- .treeshake;
8899
8799
  return (this.property.hasEffects(context) ||
8900
8800
  this.object.hasEffects(context) ||
8901
- // Assignments do not access the property before assigning
8902
- (!(this.variable ||
8903
- this.replacement ||
8904
- (this.parent instanceof AssignmentExpression && this.parent.operator === '=')) &&
8905
- propertyReadSideEffects &&
8906
- (propertyReadSideEffects === 'always' ||
8907
- this.object.hasEffectsWhenAccessedAtPath([this.getPropertyKey()], context))));
8908
- }
8909
- hasEffectsWhenAccessedAtPath(path, context) {
8910
- if (this.variable !== null) {
8911
- return this.variable.hasEffectsWhenAccessedAtPath(path, context);
8912
- }
8913
- if (this.replacement) {
8914
- return true;
8915
- }
8916
- if (path.length < MAX_PATH_DEPTH) {
8917
- return this.object.hasEffectsWhenAccessedAtPath([this.getPropertyKey(), ...path], context);
8918
- }
8919
- return true;
8801
+ this.hasAccessEffect(context));
8920
8802
  }
8921
- hasEffectsWhenAssignedAtPath(path, context) {
8922
- if (this.variable !== null) {
8923
- return this.variable.hasEffectsWhenAssignedAtPath(path, context);
8924
- }
8925
- if (this.replacement) {
8926
- return true;
8927
- }
8928
- if (path.length < MAX_PATH_DEPTH) {
8929
- return this.object.hasEffectsWhenAssignedAtPath([this.getPropertyKey(), ...path], context);
8930
- }
8931
- return true;
8803
+ hasEffectsAsAssignmentTarget(context, checkAccess) {
8804
+ if (checkAccess && !this.deoptimized)
8805
+ this.applyDeoptimizations();
8806
+ if (!this.assignmentDeoptimized)
8807
+ this.applyAssignmentDeoptimization();
8808
+ return (this.property.hasEffects(context) ||
8809
+ this.object.hasEffects(context) ||
8810
+ (checkAccess && this.hasAccessEffect(context)) ||
8811
+ this.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.assignmentInteraction, context));
8932
8812
  }
8933
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
8934
- if (this.variable !== null) {
8935
- return this.variable.hasEffectsWhenCalledAtPath(path, callOptions, context);
8813
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
8814
+ if (this.variable) {
8815
+ return this.variable.hasEffectsOnInteractionAtPath(path, interaction, context);
8936
8816
  }
8937
8817
  if (this.replacement) {
8938
8818
  return true;
8939
8819
  }
8940
8820
  if (path.length < MAX_PATH_DEPTH) {
8941
- return this.object.hasEffectsWhenCalledAtPath([this.getPropertyKey(), ...path], callOptions, context);
8821
+ return this.object.hasEffectsOnInteractionAtPath([this.getPropertyKey(), ...path], interaction, context);
8942
8822
  }
8943
8823
  return true;
8944
8824
  }
8945
8825
  include(context, includeChildrenRecursively) {
8946
8826
  if (!this.deoptimized)
8947
8827
  this.applyDeoptimizations();
8948
- if (!this.included) {
8949
- this.included = true;
8950
- if (this.variable !== null) {
8951
- this.context.includeVariableInModule(this.variable);
8952
- }
8828
+ this.includeProperties(context, includeChildrenRecursively);
8829
+ }
8830
+ includeAsAssignmentTarget(context, includeChildrenRecursively, deoptimizeAccess) {
8831
+ if (!this.assignmentDeoptimized)
8832
+ this.applyAssignmentDeoptimization();
8833
+ if (deoptimizeAccess) {
8834
+ this.include(context, includeChildrenRecursively);
8835
+ }
8836
+ else {
8837
+ this.includeProperties(context, includeChildrenRecursively);
8953
8838
  }
8954
- this.object.include(context, includeChildrenRecursively);
8955
- this.property.include(context, includeChildrenRecursively);
8956
8839
  }
8957
8840
  includeCallArguments(context, args) {
8958
8841
  if (this.variable) {
@@ -8964,6 +8847,7 @@ class MemberExpression extends NodeBase {
8964
8847
  }
8965
8848
  initialise() {
8966
8849
  this.propertyKey = getResolvablePropertyKey(this);
8850
+ this.accessInteraction = { thisArg: this.object, type: INTERACTION_ACCESSED };
8967
8851
  }
8968
8852
  render(code, options, { renderedParentType, isCalleeOfRenderedParent, renderedSurroundingElement } = BLANK) {
8969
8853
  if (this.variable || this.replacement) {
@@ -8984,6 +8868,13 @@ class MemberExpression extends NodeBase {
8984
8868
  this.property.render(code, options);
8985
8869
  }
8986
8870
  }
8871
+ setAssignedValue(value) {
8872
+ this.assignmentInteraction = {
8873
+ args: [value],
8874
+ thisArg: this.object,
8875
+ type: INTERACTION_ASSIGNED
8876
+ };
8877
+ }
8987
8878
  applyDeoptimizations() {
8988
8879
  this.deoptimized = true;
8989
8880
  const { propertyReadSideEffects } = this.context.options
@@ -8993,13 +8884,21 @@ class MemberExpression extends NodeBase {
8993
8884
  this.bound &&
8994
8885
  propertyReadSideEffects &&
8995
8886
  !(this.variable || this.replacement)) {
8996
- // Regular Assignments do not access the property before assigning
8997
- if (!(this.parent instanceof AssignmentExpression && this.parent.operator === '=')) {
8998
- this.object.deoptimizeThisOnEventAtPath(EVENT_ACCESSED, [this.propertyKey], this.object, SHARED_RECURSION_TRACKER);
8999
- }
9000
- if (this.parent instanceof AssignmentExpression) {
9001
- this.object.deoptimizeThisOnEventAtPath(EVENT_ASSIGNED, [this.propertyKey], this.object, SHARED_RECURSION_TRACKER);
9002
- }
8887
+ const propertyKey = this.getPropertyKey();
8888
+ this.object.deoptimizeThisOnInteractionAtPath(this.accessInteraction, [propertyKey], SHARED_RECURSION_TRACKER);
8889
+ this.context.requestTreeshakingPass();
8890
+ }
8891
+ }
8892
+ applyAssignmentDeoptimization() {
8893
+ this.assignmentDeoptimized = true;
8894
+ const { propertyReadSideEffects } = this.context.options
8895
+ .treeshake;
8896
+ if (
8897
+ // Namespaces are not bound and should not be deoptimized
8898
+ this.bound &&
8899
+ propertyReadSideEffects &&
8900
+ !(this.variable || this.replacement)) {
8901
+ this.object.deoptimizeThisOnInteractionAtPath(this.assignmentInteraction, [this.getPropertyKey()], SHARED_RECURSION_TRACKER);
9003
8902
  this.context.requestTreeshakingPass();
9004
8903
  }
9005
8904
  }
@@ -9025,33 +8924,50 @@ class MemberExpression extends NodeBase {
9025
8924
  }
9026
8925
  return this.propertyKey;
9027
8926
  }
9028
- resolveNamespaceVariables(baseVariable, path) {
9029
- if (path.length === 0)
9030
- return baseVariable;
9031
- if (!baseVariable.isNamespace || baseVariable instanceof ExternalVariable)
9032
- return null;
9033
- const exportName = path[0].key;
9034
- const variable = baseVariable.context.traceExport(exportName);
9035
- if (!variable) {
9036
- const fileName = baseVariable.context.fileName;
9037
- this.context.warn({
9038
- code: 'MISSING_EXPORT',
9039
- exporter: relativeId(fileName),
9040
- importer: relativeId(this.context.fileName),
9041
- message: `'${exportName}' is not exported by '${relativeId(fileName)}'`,
9042
- missing: exportName,
9043
- url: `https://rollupjs.org/guide/en/#error-name-is-not-exported-by-module`
9044
- }, path[0].pos);
9045
- return 'undefined';
8927
+ hasAccessEffect(context) {
8928
+ const { propertyReadSideEffects } = this.context.options
8929
+ .treeshake;
8930
+ return (!(this.variable || this.replacement) &&
8931
+ propertyReadSideEffects &&
8932
+ (propertyReadSideEffects === 'always' ||
8933
+ this.object.hasEffectsOnInteractionAtPath([this.getPropertyKey()], this.accessInteraction, context)));
8934
+ }
8935
+ includeProperties(context, includeChildrenRecursively) {
8936
+ if (!this.included) {
8937
+ this.included = true;
8938
+ if (this.variable) {
8939
+ this.context.includeVariableInModule(this.variable);
8940
+ }
9046
8941
  }
9047
- return this.resolveNamespaceVariables(variable, path.slice(1));
8942
+ this.object.include(context, includeChildrenRecursively);
8943
+ this.property.include(context, includeChildrenRecursively);
9048
8944
  }
9049
8945
  }
8946
+ function resolveNamespaceVariables(baseVariable, path, astContext) {
8947
+ if (path.length === 0)
8948
+ return baseVariable;
8949
+ if (!baseVariable.isNamespace || baseVariable instanceof ExternalVariable)
8950
+ return null;
8951
+ const exportName = path[0].key;
8952
+ const variable = baseVariable.context.traceExport(exportName);
8953
+ if (!variable) {
8954
+ const fileName = baseVariable.context.fileName;
8955
+ astContext.warn({
8956
+ code: 'MISSING_EXPORT',
8957
+ exporter: relativeId(fileName),
8958
+ importer: relativeId(astContext.fileName),
8959
+ message: `'${exportName}' is not exported by '${relativeId(fileName)}'`,
8960
+ missing: exportName,
8961
+ url: `https://rollupjs.org/guide/en/#error-name-is-not-exported-by-module`
8962
+ }, path[0].pos);
8963
+ return 'undefined';
8964
+ }
8965
+ return resolveNamespaceVariables(variable, path.slice(1), astContext);
8966
+ }
9050
8967
 
9051
8968
  class CallExpressionBase extends NodeBase {
9052
8969
  constructor() {
9053
8970
  super(...arguments);
9054
- this.deoptimized = false;
9055
8971
  this.returnExpression = null;
9056
8972
  this.deoptimizableDependentExpressions = [];
9057
8973
  this.expressionsToBeDeoptimized = new Set();
@@ -9077,15 +8993,15 @@ class CallExpressionBase extends NodeBase {
9077
8993
  returnExpression.deoptimizePath(path);
9078
8994
  }
9079
8995
  }
9080
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
8996
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
9081
8997
  const returnExpression = this.getReturnExpression(recursionTracker);
9082
8998
  if (returnExpression === UNKNOWN_EXPRESSION) {
9083
- thisParameter.deoptimizePath(UNKNOWN_PATH);
8999
+ interaction.thisArg.deoptimizePath(UNKNOWN_PATH);
9084
9000
  }
9085
9001
  else {
9086
9002
  recursionTracker.withTrackedEntityAtPath(path, returnExpression, () => {
9087
- this.expressionsToBeDeoptimized.add(thisParameter);
9088
- returnExpression.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
9003
+ this.expressionsToBeDeoptimized.add(interaction.thisArg);
9004
+ returnExpression.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
9089
9005
  }, undefined);
9090
9006
  }
9091
9007
  }
@@ -9099,27 +9015,31 @@ class CallExpressionBase extends NodeBase {
9099
9015
  return returnExpression.getLiteralValueAtPath(path, recursionTracker, origin);
9100
9016
  }, UnknownValue);
9101
9017
  }
9102
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
9018
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
9103
9019
  const returnExpression = this.getReturnExpression(recursionTracker);
9104
9020
  if (this.returnExpression === UNKNOWN_EXPRESSION) {
9105
9021
  return UNKNOWN_EXPRESSION;
9106
9022
  }
9107
9023
  return recursionTracker.withTrackedEntityAtPath(path, returnExpression, () => {
9108
9024
  this.deoptimizableDependentExpressions.push(origin);
9109
- return returnExpression.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
9025
+ return returnExpression.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
9110
9026
  }, UNKNOWN_EXPRESSION);
9111
9027
  }
9112
- hasEffectsWhenAccessedAtPath(path, context) {
9113
- return (!context.accessed.trackEntityAtPathAndGetIfTracked(path, this) &&
9114
- this.getReturnExpression().hasEffectsWhenAccessedAtPath(path, context));
9115
- }
9116
- hasEffectsWhenAssignedAtPath(path, context) {
9117
- return (!context.assigned.trackEntityAtPathAndGetIfTracked(path, this) &&
9118
- this.getReturnExpression().hasEffectsWhenAssignedAtPath(path, context));
9119
- }
9120
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
9121
- return (!(callOptions.withNew ? context.instantiated : context.called).trackEntityAtPathAndGetIfTracked(path, callOptions, this) &&
9122
- this.getReturnExpression().hasEffectsWhenCalledAtPath(path, callOptions, context));
9028
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
9029
+ const { type } = interaction;
9030
+ if (type === INTERACTION_CALLED) {
9031
+ if ((interaction.withNew
9032
+ ? context.instantiated
9033
+ : context.called).trackEntityAtPathAndGetIfTracked(path, interaction.args, this)) {
9034
+ return false;
9035
+ }
9036
+ }
9037
+ else if ((type === INTERACTION_ASSIGNED
9038
+ ? context.assigned
9039
+ : context.accessed).trackEntityAtPathAndGetIfTracked(path, this)) {
9040
+ return false;
9041
+ }
9042
+ return this.getReturnExpression().hasEffectsOnInteractionAtPath(path, interaction, context);
9123
9043
  }
9124
9044
  }
9125
9045
 
@@ -9142,11 +9062,12 @@ class CallExpression extends CallExpressionBase {
9142
9062
  }, this.start);
9143
9063
  }
9144
9064
  }
9145
- this.callOptions = {
9065
+ this.interaction = {
9146
9066
  args: this.arguments,
9147
- thisParam: this.callee instanceof MemberExpression && !this.callee.variable
9067
+ thisArg: this.callee instanceof MemberExpression && !this.callee.variable
9148
9068
  ? this.callee.object
9149
9069
  : null,
9070
+ type: INTERACTION_CALLED,
9150
9071
  withNew: false
9151
9072
  };
9152
9073
  }
@@ -9160,7 +9081,7 @@ class CallExpression extends CallExpressionBase {
9160
9081
  this.annotations)
9161
9082
  return false;
9162
9083
  return (this.callee.hasEffects(context) ||
9163
- this.callee.hasEffectsWhenCalledAtPath(EMPTY_PATH, this.callOptions, context));
9084
+ this.callee.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.interaction, context));
9164
9085
  }
9165
9086
  finally {
9166
9087
  if (!this.deoptimized)
@@ -9180,7 +9101,7 @@ class CallExpression extends CallExpressionBase {
9180
9101
  }
9181
9102
  else {
9182
9103
  this.included = true;
9183
- this.callee.include(context, false, { includeWithoutParameterDefaults: true });
9104
+ this.callee.include(context, false);
9184
9105
  }
9185
9106
  this.callee.includeCallArguments(context, this.arguments);
9186
9107
  const returnExpression = this.getReturnExpression();
@@ -9193,34 +9114,12 @@ class CallExpression extends CallExpressionBase {
9193
9114
  isCalleeOfRenderedParent: true,
9194
9115
  renderedSurroundingElement
9195
9116
  });
9196
- if (this.arguments.length > 0) {
9197
- if (this.arguments[this.arguments.length - 1].included) {
9198
- for (const arg of this.arguments) {
9199
- arg.render(code, options);
9200
- }
9201
- }
9202
- else {
9203
- let lastIncludedIndex = this.arguments.length - 2;
9204
- while (lastIncludedIndex >= 0 && !this.arguments[lastIncludedIndex].included) {
9205
- lastIncludedIndex--;
9206
- }
9207
- if (lastIncludedIndex >= 0) {
9208
- for (let index = 0; index <= lastIncludedIndex; index++) {
9209
- this.arguments[index].render(code, options);
9210
- }
9211
- code.remove(findFirstOccurrenceOutsideComment(code.original, ',', this.arguments[lastIncludedIndex].end), this.end - 1);
9212
- }
9213
- else {
9214
- code.remove(findFirstOccurrenceOutsideComment(code.original, '(', this.callee.end) + 1, this.end - 1);
9215
- }
9216
- }
9217
- }
9117
+ renderCallArguments(code, options, this);
9218
9118
  }
9219
9119
  applyDeoptimizations() {
9220
9120
  this.deoptimized = true;
9221
- const { thisParam } = this.callOptions;
9222
- if (thisParam) {
9223
- this.callee.deoptimizeThisOnEventAtPath(EVENT_CALLED, EMPTY_PATH, thisParam, SHARED_RECURSION_TRACKER);
9121
+ if (this.interaction.thisArg) {
9122
+ this.callee.deoptimizeThisOnInteractionAtPath(this.interaction, EMPTY_PATH, SHARED_RECURSION_TRACKER);
9224
9123
  }
9225
9124
  for (const argument of this.arguments) {
9226
9125
  // This will make sure all properties of parameters behave as "unknown"
@@ -9231,7 +9130,7 @@ class CallExpression extends CallExpressionBase {
9231
9130
  getReturnExpression(recursionTracker = SHARED_RECURSION_TRACKER) {
9232
9131
  if (this.returnExpression === null) {
9233
9132
  this.returnExpression = UNKNOWN_EXPRESSION;
9234
- return (this.returnExpression = this.callee.getReturnExpressionWhenCalledAtPath(EMPTY_PATH, this.callOptions, recursionTracker, this));
9133
+ return (this.returnExpression = this.callee.getReturnExpressionWhenCalledAtPath(EMPTY_PATH, this.interaction, recursionTracker, this));
9235
9134
  }
9236
9135
  return this.returnExpression;
9237
9136
  }
@@ -9302,17 +9201,13 @@ class ClassBody extends NodeBase {
9302
9201
  }
9303
9202
  super.parseNode(esTreeNode);
9304
9203
  }
9204
+ applyDeoptimizations() { }
9305
9205
  }
9306
9206
 
9307
9207
  class MethodBase extends NodeBase {
9308
9208
  constructor() {
9309
9209
  super(...arguments);
9310
9210
  this.accessedValue = null;
9311
- this.accessorCallOptions = {
9312
- args: NO_ARGS,
9313
- thisParam: null,
9314
- withNew: false
9315
- };
9316
9211
  }
9317
9212
  // As getter properties directly receive their values from fixed function
9318
9213
  // expressions, there is no known situation where a getter is deoptimized.
@@ -9320,44 +9215,60 @@ class MethodBase extends NodeBase {
9320
9215
  deoptimizePath(path) {
9321
9216
  this.getAccessedValue().deoptimizePath(path);
9322
9217
  }
9323
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
9324
- if (event === EVENT_ACCESSED && this.kind === 'get' && path.length === 0) {
9325
- return this.value.deoptimizeThisOnEventAtPath(EVENT_CALLED, EMPTY_PATH, thisParameter, recursionTracker);
9218
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
9219
+ if (interaction.type === INTERACTION_ACCESSED && this.kind === 'get' && path.length === 0) {
9220
+ return this.value.deoptimizeThisOnInteractionAtPath({
9221
+ args: NO_ARGS,
9222
+ thisArg: interaction.thisArg,
9223
+ type: INTERACTION_CALLED,
9224
+ withNew: false
9225
+ }, EMPTY_PATH, recursionTracker);
9326
9226
  }
9327
- if (event === EVENT_ASSIGNED && this.kind === 'set' && path.length === 0) {
9328
- return this.value.deoptimizeThisOnEventAtPath(EVENT_CALLED, EMPTY_PATH, thisParameter, recursionTracker);
9227
+ if (interaction.type === INTERACTION_ASSIGNED && this.kind === 'set' && path.length === 0) {
9228
+ return this.value.deoptimizeThisOnInteractionAtPath({
9229
+ args: interaction.args,
9230
+ thisArg: interaction.thisArg,
9231
+ type: INTERACTION_CALLED,
9232
+ withNew: false
9233
+ }, EMPTY_PATH, recursionTracker);
9329
9234
  }
9330
- this.getAccessedValue().deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
9235
+ this.getAccessedValue().deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
9331
9236
  }
9332
9237
  getLiteralValueAtPath(path, recursionTracker, origin) {
9333
9238
  return this.getAccessedValue().getLiteralValueAtPath(path, recursionTracker, origin);
9334
9239
  }
9335
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
9336
- return this.getAccessedValue().getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
9240
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
9241
+ return this.getAccessedValue().getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
9337
9242
  }
9338
9243
  hasEffects(context) {
9339
9244
  return this.key.hasEffects(context);
9340
9245
  }
9341
- hasEffectsWhenAccessedAtPath(path, context) {
9342
- if (this.kind === 'get' && path.length === 0) {
9343
- return this.value.hasEffectsWhenCalledAtPath(EMPTY_PATH, this.accessorCallOptions, context);
9344
- }
9345
- return this.getAccessedValue().hasEffectsWhenAccessedAtPath(path, context);
9346
- }
9347
- hasEffectsWhenAssignedAtPath(path, context) {
9348
- if (this.kind === 'set') {
9349
- return this.value.hasEffectsWhenCalledAtPath(EMPTY_PATH, this.accessorCallOptions, context);
9246
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
9247
+ if (this.kind === 'get' && interaction.type === INTERACTION_ACCESSED && path.length === 0) {
9248
+ return this.value.hasEffectsOnInteractionAtPath(EMPTY_PATH, {
9249
+ args: NO_ARGS,
9250
+ thisArg: interaction.thisArg,
9251
+ type: INTERACTION_CALLED,
9252
+ withNew: false
9253
+ }, context);
9254
+ }
9255
+ // setters are only called for empty paths
9256
+ if (this.kind === 'set' && interaction.type === INTERACTION_ASSIGNED) {
9257
+ return this.value.hasEffectsOnInteractionAtPath(EMPTY_PATH, {
9258
+ args: interaction.args,
9259
+ thisArg: interaction.thisArg,
9260
+ type: INTERACTION_CALLED,
9261
+ withNew: false
9262
+ }, context);
9350
9263
  }
9351
- return this.getAccessedValue().hasEffectsWhenAssignedAtPath(path, context);
9352
- }
9353
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
9354
- return this.getAccessedValue().hasEffectsWhenCalledAtPath(path, callOptions, context);
9264
+ return this.getAccessedValue().hasEffectsOnInteractionAtPath(path, interaction, context);
9355
9265
  }
9266
+ applyDeoptimizations() { }
9356
9267
  getAccessedValue() {
9357
9268
  if (this.accessedValue === null) {
9358
9269
  if (this.kind === 'get') {
9359
9270
  this.accessedValue = UNKNOWN_EXPRESSION;
9360
- return (this.accessedValue = this.value.getReturnExpressionWhenCalledAtPath(EMPTY_PATH, this.accessorCallOptions, SHARED_RECURSION_TRACKER, this));
9271
+ return (this.accessedValue = this.value.getReturnExpressionWhenCalledAtPath(EMPTY_PATH, NODE_INTERACTION_UNKNOWN_CALL, SHARED_RECURSION_TRACKER, this));
9361
9272
  }
9362
9273
  else {
9363
9274
  return (this.accessedValue = this.value);
@@ -9368,6 +9279,7 @@ class MethodBase extends NodeBase {
9368
9279
  }
9369
9280
 
9370
9281
  class MethodDefinition extends MethodBase {
9282
+ applyDeoptimizations() { }
9371
9283
  }
9372
9284
 
9373
9285
  class ObjectMember extends ExpressionEntity {
@@ -9379,30 +9291,23 @@ class ObjectMember extends ExpressionEntity {
9379
9291
  deoptimizePath(path) {
9380
9292
  this.object.deoptimizePath([this.key, ...path]);
9381
9293
  }
9382
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
9383
- this.object.deoptimizeThisOnEventAtPath(event, [this.key, ...path], thisParameter, recursionTracker);
9294
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
9295
+ this.object.deoptimizeThisOnInteractionAtPath(interaction, [this.key, ...path], recursionTracker);
9384
9296
  }
9385
9297
  getLiteralValueAtPath(path, recursionTracker, origin) {
9386
9298
  return this.object.getLiteralValueAtPath([this.key, ...path], recursionTracker, origin);
9387
9299
  }
9388
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
9389
- return this.object.getReturnExpressionWhenCalledAtPath([this.key, ...path], callOptions, recursionTracker, origin);
9390
- }
9391
- hasEffectsWhenAccessedAtPath(path, context) {
9392
- return this.object.hasEffectsWhenAccessedAtPath([this.key, ...path], context);
9393
- }
9394
- hasEffectsWhenAssignedAtPath(path, context) {
9395
- return this.object.hasEffectsWhenAssignedAtPath([this.key, ...path], context);
9300
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
9301
+ return this.object.getReturnExpressionWhenCalledAtPath([this.key, ...path], interaction, recursionTracker, origin);
9396
9302
  }
9397
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
9398
- return this.object.hasEffectsWhenCalledAtPath([this.key, ...path], callOptions, context);
9303
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
9304
+ return this.object.hasEffectsOnInteractionAtPath([this.key, ...path], interaction, context);
9399
9305
  }
9400
9306
  }
9401
9307
 
9402
9308
  class ClassNode extends NodeBase {
9403
9309
  constructor() {
9404
9310
  super(...arguments);
9405
- this.deoptimized = false;
9406
9311
  this.objectEntity = null;
9407
9312
  }
9408
9313
  createScope(parentScope) {
@@ -9412,23 +9317,16 @@ class ClassNode extends NodeBase {
9412
9317
  this.getObjectEntity().deoptimizeAllProperties();
9413
9318
  }
9414
9319
  deoptimizePath(path) {
9415
- var _a, _b;
9416
9320
  this.getObjectEntity().deoptimizePath(path);
9417
- if (path.length === 1 && path[0] === UnknownKey) {
9418
- // A reassignment of UNKNOWN_PATH is considered equivalent to having lost track
9419
- // which means the constructor needs to be reassigned
9420
- (_a = this.classConstructor) === null || _a === void 0 ? void 0 : _a.deoptimizePath(UNKNOWN_PATH);
9421
- (_b = this.superClass) === null || _b === void 0 ? void 0 : _b.deoptimizePath(UNKNOWN_PATH);
9422
- }
9423
9321
  }
9424
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
9425
- this.getObjectEntity().deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
9322
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
9323
+ this.getObjectEntity().deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
9426
9324
  }
9427
9325
  getLiteralValueAtPath(path, recursionTracker, origin) {
9428
9326
  return this.getObjectEntity().getLiteralValueAtPath(path, recursionTracker, origin);
9429
9327
  }
9430
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
9431
- return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
9328
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
9329
+ return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
9432
9330
  }
9433
9331
  hasEffects(context) {
9434
9332
  var _a, _b;
@@ -9438,23 +9336,17 @@ class ClassNode extends NodeBase {
9438
9336
  (_b = this.id) === null || _b === void 0 ? void 0 : _b.markDeclarationReached();
9439
9337
  return initEffect || super.hasEffects(context);
9440
9338
  }
9441
- hasEffectsWhenAccessedAtPath(path, context) {
9442
- return this.getObjectEntity().hasEffectsWhenAccessedAtPath(path, context);
9443
- }
9444
- hasEffectsWhenAssignedAtPath(path, context) {
9445
- return this.getObjectEntity().hasEffectsWhenAssignedAtPath(path, context);
9446
- }
9447
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
9339
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
9448
9340
  var _a;
9449
- if (path.length === 0) {
9450
- return (!callOptions.withNew ||
9341
+ if (interaction.type === INTERACTION_CALLED && path.length === 0) {
9342
+ return (!interaction.withNew ||
9451
9343
  (this.classConstructor !== null
9452
- ? this.classConstructor.hasEffectsWhenCalledAtPath(EMPTY_PATH, callOptions, context)
9453
- : (_a = this.superClass) === null || _a === void 0 ? void 0 : _a.hasEffectsWhenCalledAtPath(path, callOptions, context)) ||
9344
+ ? this.classConstructor.hasEffectsOnInteractionAtPath(path, interaction, context)
9345
+ : (_a = this.superClass) === null || _a === void 0 ? void 0 : _a.hasEffectsOnInteractionAtPath(path, interaction, context)) ||
9454
9346
  false);
9455
9347
  }
9456
9348
  else {
9457
- return this.getObjectEntity().hasEffectsWhenCalledAtPath(path, callOptions, context);
9349
+ return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
9458
9350
  }
9459
9351
  }
9460
9352
  include(context, includeChildrenRecursively) {
@@ -9575,26 +9467,12 @@ class MultiExpression extends ExpressionEntity {
9575
9467
  expression.deoptimizePath(path);
9576
9468
  }
9577
9469
  }
9578
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
9579
- return new MultiExpression(this.expressions.map(expression => expression.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin)));
9580
- }
9581
- hasEffectsWhenAccessedAtPath(path, context) {
9582
- for (const expression of this.expressions) {
9583
- if (expression.hasEffectsWhenAccessedAtPath(path, context))
9584
- return true;
9585
- }
9586
- return false;
9587
- }
9588
- hasEffectsWhenAssignedAtPath(path, context) {
9589
- for (const expression of this.expressions) {
9590
- if (expression.hasEffectsWhenAssignedAtPath(path, context))
9591
- return true;
9592
- }
9593
- return false;
9470
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
9471
+ return new MultiExpression(this.expressions.map(expression => expression.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)));
9594
9472
  }
9595
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
9473
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
9596
9474
  for (const expression of this.expressions) {
9597
- if (expression.hasEffectsWhenCalledAtPath(path, callOptions, context))
9475
+ if (expression.hasEffectsOnInteractionAtPath(path, interaction, context))
9598
9476
  return true;
9599
9477
  }
9600
9478
  return false;
@@ -9637,9 +9515,9 @@ class ConditionalExpression extends NodeBase {
9637
9515
  usedBranch.deoptimizePath(path);
9638
9516
  }
9639
9517
  }
9640
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
9641
- this.consequent.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
9642
- this.alternate.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
9518
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
9519
+ this.consequent.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
9520
+ this.alternate.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
9643
9521
  }
9644
9522
  getLiteralValueAtPath(path, recursionTracker, origin) {
9645
9523
  const usedBranch = this.getUsedBranch();
@@ -9648,15 +9526,15 @@ class ConditionalExpression extends NodeBase {
9648
9526
  this.expressionsToBeDeoptimized.push(origin);
9649
9527
  return usedBranch.getLiteralValueAtPath(path, recursionTracker, origin);
9650
9528
  }
9651
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
9529
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
9652
9530
  const usedBranch = this.getUsedBranch();
9653
9531
  if (!usedBranch)
9654
9532
  return new MultiExpression([
9655
- this.consequent.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin),
9656
- this.alternate.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin)
9533
+ this.consequent.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin),
9534
+ this.alternate.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)
9657
9535
  ]);
9658
9536
  this.expressionsToBeDeoptimized.push(origin);
9659
- return usedBranch.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
9537
+ return usedBranch.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
9660
9538
  }
9661
9539
  hasEffects(context) {
9662
9540
  if (this.test.hasEffects(context))
@@ -9667,29 +9545,13 @@ class ConditionalExpression extends NodeBase {
9667
9545
  }
9668
9546
  return usedBranch.hasEffects(context);
9669
9547
  }
9670
- hasEffectsWhenAccessedAtPath(path, context) {
9671
- const usedBranch = this.getUsedBranch();
9672
- if (!usedBranch) {
9673
- return (this.consequent.hasEffectsWhenAccessedAtPath(path, context) ||
9674
- this.alternate.hasEffectsWhenAccessedAtPath(path, context));
9675
- }
9676
- return usedBranch.hasEffectsWhenAccessedAtPath(path, context);
9677
- }
9678
- hasEffectsWhenAssignedAtPath(path, context) {
9679
- const usedBranch = this.getUsedBranch();
9680
- if (!usedBranch) {
9681
- return (this.consequent.hasEffectsWhenAssignedAtPath(path, context) ||
9682
- this.alternate.hasEffectsWhenAssignedAtPath(path, context));
9683
- }
9684
- return usedBranch.hasEffectsWhenAssignedAtPath(path, context);
9685
- }
9686
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
9548
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
9687
9549
  const usedBranch = this.getUsedBranch();
9688
9550
  if (!usedBranch) {
9689
- return (this.consequent.hasEffectsWhenCalledAtPath(path, callOptions, context) ||
9690
- this.alternate.hasEffectsWhenCalledAtPath(path, callOptions, context));
9551
+ return (this.consequent.hasEffectsOnInteractionAtPath(path, interaction, context) ||
9552
+ this.alternate.hasEffectsOnInteractionAtPath(path, interaction, context));
9691
9553
  }
9692
- return usedBranch.hasEffectsWhenCalledAtPath(path, callOptions, context);
9554
+ return usedBranch.hasEffectsOnInteractionAtPath(path, interaction, context);
9693
9555
  }
9694
9556
  include(context, includeChildrenRecursively) {
9695
9557
  this.included = true;
@@ -9817,13 +9679,11 @@ class ExportAllDeclaration extends NodeBase {
9817
9679
  render(code, _options, nodeRenderOptions) {
9818
9680
  code.remove(nodeRenderOptions.start, nodeRenderOptions.end);
9819
9681
  }
9682
+ applyDeoptimizations() { }
9820
9683
  }
9821
9684
  ExportAllDeclaration.prototype.needsBoundaries = true;
9822
9685
 
9823
9686
  class FunctionDeclaration extends FunctionNode {
9824
- include(context, includeChildrenRecursively) {
9825
- super.include(context, includeChildrenRecursively, { includeWithoutParameterDefaults: true });
9826
- }
9827
9687
  initialise() {
9828
9688
  super.initialise();
9829
9689
  if (this.id !== null) {
@@ -9894,6 +9754,7 @@ class ExportDefaultDeclaration extends NodeBase {
9894
9754
  }
9895
9755
  this.declaration.render(code, options);
9896
9756
  }
9757
+ applyDeoptimizations() { }
9897
9758
  renderNamedDeclaration(code, declarationStart, declarationKeyword, endMarker, needsId, options) {
9898
9759
  const { exportNamesByVariable, format, snippets: { getPropertyAccess } } = options;
9899
9760
  const name = this.variable.getName(getPropertyAccess);
@@ -9948,27 +9809,23 @@ class ExportNamedDeclaration extends NodeBase {
9948
9809
  this.declaration.render(code, options, { end, start });
9949
9810
  }
9950
9811
  }
9812
+ applyDeoptimizations() { }
9951
9813
  }
9952
9814
  ExportNamedDeclaration.prototype.needsBoundaries = true;
9953
9815
 
9954
9816
  class ExportSpecifier extends NodeBase {
9817
+ applyDeoptimizations() { }
9955
9818
  }
9956
9819
 
9957
9820
  class ForInStatement extends NodeBase {
9958
- constructor() {
9959
- super(...arguments);
9960
- this.deoptimized = false;
9961
- }
9962
9821
  createScope(parentScope) {
9963
9822
  this.scope = new BlockScope(parentScope);
9964
9823
  }
9965
9824
  hasEffects(context) {
9966
- if (!this.deoptimized)
9825
+ const { deoptimized, left, right } = this;
9826
+ if (!deoptimized)
9967
9827
  this.applyDeoptimizations();
9968
- if ((this.left &&
9969
- (this.left.hasEffects(context) ||
9970
- this.left.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context))) ||
9971
- (this.right && this.right.hasEffects(context)))
9828
+ if (left.hasEffectsAsAssignmentTarget(context, false) || right.hasEffects(context))
9972
9829
  return true;
9973
9830
  const { brokenFlow, ignore: { breaks, continues } } = context;
9974
9831
  context.ignore.breaks = true;
@@ -9981,15 +9838,19 @@ class ForInStatement extends NodeBase {
9981
9838
  return false;
9982
9839
  }
9983
9840
  include(context, includeChildrenRecursively) {
9984
- if (!this.deoptimized)
9841
+ const { body, deoptimized, left, right } = this;
9842
+ if (!deoptimized)
9985
9843
  this.applyDeoptimizations();
9986
9844
  this.included = true;
9987
- this.left.include(context, includeChildrenRecursively || true);
9988
- this.right.include(context, includeChildrenRecursively);
9845
+ left.includeAsAssignmentTarget(context, includeChildrenRecursively || true, false);
9846
+ right.include(context, includeChildrenRecursively);
9989
9847
  const { brokenFlow } = context;
9990
- this.body.include(context, includeChildrenRecursively, { asSingleStatement: true });
9848
+ body.include(context, includeChildrenRecursively, { asSingleStatement: true });
9991
9849
  context.brokenFlow = brokenFlow;
9992
9850
  }
9851
+ initialise() {
9852
+ this.left.setAssignedValue(UNKNOWN_EXPRESSION);
9853
+ }
9993
9854
  render(code, options) {
9994
9855
  this.left.render(code, options, NO_SEMICOLON);
9995
9856
  this.right.render(code, options, NO_SEMICOLON);
@@ -10007,10 +9868,6 @@ class ForInStatement extends NodeBase {
10007
9868
  }
10008
9869
 
10009
9870
  class ForOfStatement extends NodeBase {
10010
- constructor() {
10011
- super(...arguments);
10012
- this.deoptimized = false;
10013
- }
10014
9871
  createScope(parentScope) {
10015
9872
  this.scope = new BlockScope(parentScope);
10016
9873
  }
@@ -10021,15 +9878,19 @@ class ForOfStatement extends NodeBase {
10021
9878
  return true;
10022
9879
  }
10023
9880
  include(context, includeChildrenRecursively) {
10024
- if (!this.deoptimized)
9881
+ const { body, deoptimized, left, right } = this;
9882
+ if (!deoptimized)
10025
9883
  this.applyDeoptimizations();
10026
9884
  this.included = true;
10027
- this.left.include(context, includeChildrenRecursively || true);
10028
- this.right.include(context, includeChildrenRecursively);
9885
+ left.includeAsAssignmentTarget(context, includeChildrenRecursively || true, false);
9886
+ right.include(context, includeChildrenRecursively);
10029
9887
  const { brokenFlow } = context;
10030
- this.body.include(context, includeChildrenRecursively, { asSingleStatement: true });
9888
+ body.include(context, includeChildrenRecursively, { asSingleStatement: true });
10031
9889
  context.brokenFlow = brokenFlow;
10032
9890
  }
9891
+ initialise() {
9892
+ this.left.setAssignedValue(UNKNOWN_EXPRESSION);
9893
+ }
10033
9894
  render(code, options) {
10034
9895
  this.left.render(code, options, NO_SEMICOLON);
10035
9896
  this.right.render(code, options, NO_SEMICOLON);
@@ -10205,6 +10066,7 @@ class IfStatement extends NodeBase {
10205
10066
  }
10206
10067
  this.renderHoistedDeclarations(hoistedDeclarations, code, getPropertyAccess);
10207
10068
  }
10069
+ applyDeoptimizations() { }
10208
10070
  getTestValue() {
10209
10071
  if (this.testValue === unset) {
10210
10072
  return (this.testValue = this.test.getLiteralValueAtPath(EMPTY_PATH, SHARED_RECURSION_TRACKER, this));
@@ -10290,10 +10152,12 @@ class ImportDeclaration extends NodeBase {
10290
10152
  render(code, _options, nodeRenderOptions) {
10291
10153
  code.remove(nodeRenderOptions.start, nodeRenderOptions.end);
10292
10154
  }
10155
+ applyDeoptimizations() { }
10293
10156
  }
10294
10157
  ImportDeclaration.prototype.needsBoundaries = true;
10295
10158
 
10296
10159
  class ImportDefaultSpecifier extends NodeBase {
10160
+ applyDeoptimizations() { }
10297
10161
  }
10298
10162
 
10299
10163
  const INTEROP_DEFAULT_VARIABLE = '_interopDefault';
@@ -10552,6 +10416,7 @@ class ImportExpression extends NodeBase {
10552
10416
  setInternalResolution(inlineNamespace) {
10553
10417
  this.inlineNamespace = inlineNamespace;
10554
10418
  }
10419
+ applyDeoptimizations() { }
10555
10420
  getDynamicImportMechanismAndHelper(resolution, exportMode, { compact, dynamicImportFunction, format, generatedCode: { arrowFunctions }, interop }, { _, getDirectReturnFunction, getDirectReturnIifeLeft }, pluginDriver) {
10556
10421
  const mechanism = pluginDriver.hookFirstSync('renderDynamicImport', [
10557
10422
  {
@@ -10660,9 +10525,11 @@ const accessedImportGlobals = {
10660
10525
  };
10661
10526
 
10662
10527
  class ImportNamespaceSpecifier extends NodeBase {
10528
+ applyDeoptimizations() { }
10663
10529
  }
10664
10530
 
10665
10531
  class ImportSpecifier extends NodeBase {
10532
+ applyDeoptimizations() { }
10666
10533
  }
10667
10534
 
10668
10535
  class LabeledStatement extends NodeBase {
@@ -10708,13 +10575,16 @@ class LogicalExpression extends NodeBase {
10708
10575
  this.usedBranch = null;
10709
10576
  }
10710
10577
  deoptimizeCache() {
10711
- if (this.usedBranch !== null) {
10578
+ if (this.usedBranch) {
10712
10579
  const unusedBranch = this.usedBranch === this.left ? this.right : this.left;
10713
10580
  this.usedBranch = null;
10714
10581
  unusedBranch.deoptimizePath(UNKNOWN_PATH);
10715
10582
  for (const expression of this.expressionsToBeDeoptimized) {
10716
10583
  expression.deoptimizeCache();
10717
10584
  }
10585
+ // Request another pass because we need to ensure "include" runs again if
10586
+ // it is rendered
10587
+ this.context.requestTreeshakingPass();
10718
10588
  }
10719
10589
  }
10720
10590
  deoptimizePath(path) {
@@ -10727,9 +10597,9 @@ class LogicalExpression extends NodeBase {
10727
10597
  usedBranch.deoptimizePath(path);
10728
10598
  }
10729
10599
  }
10730
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
10731
- this.left.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
10732
- this.right.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
10600
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
10601
+ this.left.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
10602
+ this.right.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
10733
10603
  }
10734
10604
  getLiteralValueAtPath(path, recursionTracker, origin) {
10735
10605
  const usedBranch = this.getUsedBranch();
@@ -10738,15 +10608,15 @@ class LogicalExpression extends NodeBase {
10738
10608
  this.expressionsToBeDeoptimized.push(origin);
10739
10609
  return usedBranch.getLiteralValueAtPath(path, recursionTracker, origin);
10740
10610
  }
10741
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
10611
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
10742
10612
  const usedBranch = this.getUsedBranch();
10743
10613
  if (!usedBranch)
10744
10614
  return new MultiExpression([
10745
- this.left.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin),
10746
- this.right.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin)
10615
+ this.left.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin),
10616
+ this.right.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)
10747
10617
  ]);
10748
10618
  this.expressionsToBeDeoptimized.push(origin);
10749
- return usedBranch.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
10619
+ return usedBranch.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
10750
10620
  }
10751
10621
  hasEffects(context) {
10752
10622
  if (this.left.hasEffects(context)) {
@@ -10757,29 +10627,13 @@ class LogicalExpression extends NodeBase {
10757
10627
  }
10758
10628
  return false;
10759
10629
  }
10760
- hasEffectsWhenAccessedAtPath(path, context) {
10761
- const usedBranch = this.getUsedBranch();
10762
- if (!usedBranch) {
10763
- return (this.left.hasEffectsWhenAccessedAtPath(path, context) ||
10764
- this.right.hasEffectsWhenAccessedAtPath(path, context));
10765
- }
10766
- return usedBranch.hasEffectsWhenAccessedAtPath(path, context);
10767
- }
10768
- hasEffectsWhenAssignedAtPath(path, context) {
10769
- const usedBranch = this.getUsedBranch();
10770
- if (!usedBranch) {
10771
- return (this.left.hasEffectsWhenAssignedAtPath(path, context) ||
10772
- this.right.hasEffectsWhenAssignedAtPath(path, context));
10773
- }
10774
- return usedBranch.hasEffectsWhenAssignedAtPath(path, context);
10775
- }
10776
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
10630
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
10777
10631
  const usedBranch = this.getUsedBranch();
10778
10632
  if (!usedBranch) {
10779
- return (this.left.hasEffectsWhenCalledAtPath(path, callOptions, context) ||
10780
- this.right.hasEffectsWhenCalledAtPath(path, callOptions, context));
10633
+ return (this.left.hasEffectsOnInteractionAtPath(path, interaction, context) ||
10634
+ this.right.hasEffectsOnInteractionAtPath(path, interaction, context));
10781
10635
  }
10782
- return usedBranch.hasEffectsWhenCalledAtPath(path, callOptions, context);
10636
+ return usedBranch.hasEffectsOnInteractionAtPath(path, interaction, context);
10783
10637
  }
10784
10638
  include(context, includeChildrenRecursively) {
10785
10639
  this.included = true;
@@ -10869,8 +10723,8 @@ class MetaProperty extends NodeBase {
10869
10723
  hasEffects() {
10870
10724
  return false;
10871
10725
  }
10872
- hasEffectsWhenAccessedAtPath(path) {
10873
- return path.length > 1;
10726
+ hasEffectsOnInteractionAtPath(path, { type }) {
10727
+ return path.length > 1 || type !== INTERACTION_ACCESSED;
10874
10728
  }
10875
10729
  include() {
10876
10730
  if (!this.included) {
@@ -11008,10 +10862,6 @@ const importMetaMechanisms = {
11008
10862
  };
11009
10863
 
11010
10864
  class NewExpression extends NodeBase {
11011
- constructor() {
11012
- super(...arguments);
11013
- this.deoptimized = false;
11014
- }
11015
10865
  hasEffects(context) {
11016
10866
  try {
11017
10867
  for (const argument of this.arguments) {
@@ -11022,15 +10872,15 @@ class NewExpression extends NodeBase {
11022
10872
  this.annotations)
11023
10873
  return false;
11024
10874
  return (this.callee.hasEffects(context) ||
11025
- this.callee.hasEffectsWhenCalledAtPath(EMPTY_PATH, this.callOptions, context));
10875
+ this.callee.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.interaction, context));
11026
10876
  }
11027
10877
  finally {
11028
10878
  if (!this.deoptimized)
11029
10879
  this.applyDeoptimizations();
11030
10880
  }
11031
10881
  }
11032
- hasEffectsWhenAccessedAtPath(path) {
11033
- return path.length > 0;
10882
+ hasEffectsOnInteractionAtPath(path, { type }) {
10883
+ return path.length > 0 || type !== INTERACTION_ACCESSED;
11034
10884
  }
11035
10885
  include(context, includeChildrenRecursively) {
11036
10886
  if (!this.deoptimized)
@@ -11045,12 +10895,17 @@ class NewExpression extends NodeBase {
11045
10895
  this.callee.includeCallArguments(context, this.arguments);
11046
10896
  }
11047
10897
  initialise() {
11048
- this.callOptions = {
10898
+ this.interaction = {
11049
10899
  args: this.arguments,
11050
- thisParam: null,
10900
+ thisArg: null,
10901
+ type: INTERACTION_CALLED,
11051
10902
  withNew: true
11052
10903
  };
11053
10904
  }
10905
+ render(code, options) {
10906
+ this.callee.render(code, options);
10907
+ renderCallArguments(code, options, this);
10908
+ }
11054
10909
  applyDeoptimizations() {
11055
10910
  this.deoptimized = true;
11056
10911
  for (const argument of this.arguments) {
@@ -11072,23 +10927,17 @@ class ObjectExpression extends NodeBase {
11072
10927
  deoptimizePath(path) {
11073
10928
  this.getObjectEntity().deoptimizePath(path);
11074
10929
  }
11075
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
11076
- this.getObjectEntity().deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
10930
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
10931
+ this.getObjectEntity().deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
11077
10932
  }
11078
10933
  getLiteralValueAtPath(path, recursionTracker, origin) {
11079
10934
  return this.getObjectEntity().getLiteralValueAtPath(path, recursionTracker, origin);
11080
10935
  }
11081
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
11082
- return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin);
11083
- }
11084
- hasEffectsWhenAccessedAtPath(path, context) {
11085
- return this.getObjectEntity().hasEffectsWhenAccessedAtPath(path, context);
10936
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
10937
+ return this.getObjectEntity().getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin);
11086
10938
  }
11087
- hasEffectsWhenAssignedAtPath(path, context) {
11088
- return this.getObjectEntity().hasEffectsWhenAssignedAtPath(path, context);
11089
- }
11090
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
11091
- return this.getObjectEntity().hasEffectsWhenCalledAtPath(path, callOptions, context);
10939
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
10940
+ return this.getObjectEntity().hasEffectsOnInteractionAtPath(path, interaction, context);
11092
10941
  }
11093
10942
  render(code, options, { renderedSurroundingElement } = BLANK) {
11094
10943
  super.render(code, options);
@@ -11098,6 +10947,7 @@ class ObjectExpression extends NodeBase {
11098
10947
  code.prependLeft(this.end, ')');
11099
10948
  }
11100
10949
  }
10950
+ applyDeoptimizations() { }
11101
10951
  getObjectEntity() {
11102
10952
  if (this.objectEntity !== null) {
11103
10953
  return this.objectEntity;
@@ -11174,12 +11024,12 @@ class Program extends NodeBase {
11174
11024
  super.render(code, options);
11175
11025
  }
11176
11026
  }
11027
+ applyDeoptimizations() { }
11177
11028
  }
11178
11029
 
11179
11030
  class Property extends MethodBase {
11180
11031
  constructor() {
11181
11032
  super(...arguments);
11182
- this.deoptimized = false;
11183
11033
  this.declarationInit = null;
11184
11034
  }
11185
11035
  declare(kind, init) {
@@ -11218,33 +11068,28 @@ class PropertyDefinition extends NodeBase {
11218
11068
  var _a;
11219
11069
  (_a = this.value) === null || _a === void 0 ? void 0 : _a.deoptimizePath(path);
11220
11070
  }
11221
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
11071
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
11222
11072
  var _a;
11223
- (_a = this.value) === null || _a === void 0 ? void 0 : _a.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
11073
+ (_a = this.value) === null || _a === void 0 ? void 0 : _a.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
11224
11074
  }
11225
11075
  getLiteralValueAtPath(path, recursionTracker, origin) {
11226
11076
  return this.value
11227
11077
  ? this.value.getLiteralValueAtPath(path, recursionTracker, origin)
11228
11078
  : UnknownValue;
11229
11079
  }
11230
- getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin) {
11080
+ getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin) {
11231
11081
  return this.value
11232
- ? this.value.getReturnExpressionWhenCalledAtPath(path, callOptions, recursionTracker, origin)
11082
+ ? this.value.getReturnExpressionWhenCalledAtPath(path, interaction, recursionTracker, origin)
11233
11083
  : UNKNOWN_EXPRESSION;
11234
11084
  }
11235
11085
  hasEffects(context) {
11236
11086
  var _a;
11237
11087
  return this.key.hasEffects(context) || (this.static && !!((_a = this.value) === null || _a === void 0 ? void 0 : _a.hasEffects(context)));
11238
11088
  }
11239
- hasEffectsWhenAccessedAtPath(path, context) {
11240
- return !this.value || this.value.hasEffectsWhenAccessedAtPath(path, context);
11241
- }
11242
- hasEffectsWhenAssignedAtPath(path, context) {
11243
- return !this.value || this.value.hasEffectsWhenAssignedAtPath(path, context);
11244
- }
11245
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
11246
- return !this.value || this.value.hasEffectsWhenCalledAtPath(path, callOptions, context);
11089
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
11090
+ return !this.value || this.value.hasEffectsOnInteractionAtPath(path, interaction, context);
11247
11091
  }
11092
+ applyDeoptimizations() { }
11248
11093
  }
11249
11094
 
11250
11095
  class ReturnStatement extends NodeBase {
@@ -11278,8 +11123,8 @@ class SequenceExpression extends NodeBase {
11278
11123
  deoptimizePath(path) {
11279
11124
  this.expressions[this.expressions.length - 1].deoptimizePath(path);
11280
11125
  }
11281
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
11282
- this.expressions[this.expressions.length - 1].deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
11126
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
11127
+ this.expressions[this.expressions.length - 1].deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
11283
11128
  }
11284
11129
  getLiteralValueAtPath(path, recursionTracker, origin) {
11285
11130
  return this.expressions[this.expressions.length - 1].getLiteralValueAtPath(path, recursionTracker, origin);
@@ -11291,15 +11136,8 @@ class SequenceExpression extends NodeBase {
11291
11136
  }
11292
11137
  return false;
11293
11138
  }
11294
- hasEffectsWhenAccessedAtPath(path, context) {
11295
- return (path.length > 0 &&
11296
- this.expressions[this.expressions.length - 1].hasEffectsWhenAccessedAtPath(path, context));
11297
- }
11298
- hasEffectsWhenAssignedAtPath(path, context) {
11299
- return this.expressions[this.expressions.length - 1].hasEffectsWhenAssignedAtPath(path, context);
11300
- }
11301
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
11302
- return this.expressions[this.expressions.length - 1].hasEffectsWhenCalledAtPath(path, callOptions, context);
11139
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
11140
+ return this.expressions[this.expressions.length - 1].hasEffectsOnInteractionAtPath(path, interaction, context);
11303
11141
  }
11304
11142
  include(context, includeChildrenRecursively) {
11305
11143
  this.included = true;
@@ -11378,8 +11216,8 @@ class Super extends NodeBase {
11378
11216
  deoptimizePath(path) {
11379
11217
  this.variable.deoptimizePath(path);
11380
11218
  }
11381
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
11382
- this.variable.deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker);
11219
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
11220
+ this.variable.deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker);
11383
11221
  }
11384
11222
  include() {
11385
11223
  if (!this.included) {
@@ -11519,7 +11357,7 @@ class TaggedTemplateExpression extends CallExpressionBase {
11519
11357
  return true;
11520
11358
  }
11521
11359
  return (this.tag.hasEffects(context) ||
11522
- this.tag.hasEffectsWhenCalledAtPath(EMPTY_PATH, this.callOptions, context));
11360
+ this.tag.hasEffectsOnInteractionAtPath(EMPTY_PATH, this.interaction, context));
11523
11361
  }
11524
11362
  finally {
11525
11363
  if (!this.deoptimized)
@@ -11537,16 +11375,17 @@ class TaggedTemplateExpression extends CallExpressionBase {
11537
11375
  this.tag.include(context, includeChildrenRecursively);
11538
11376
  this.quasi.include(context, includeChildrenRecursively);
11539
11377
  }
11540
- this.tag.includeCallArguments(context, this.callOptions.args);
11378
+ this.tag.includeCallArguments(context, this.interaction.args);
11541
11379
  const returnExpression = this.getReturnExpression();
11542
11380
  if (!returnExpression.included) {
11543
11381
  returnExpression.include(context, false);
11544
11382
  }
11545
11383
  }
11546
11384
  initialise() {
11547
- this.callOptions = {
11385
+ this.interaction = {
11548
11386
  args: [UNKNOWN_EXPRESSION, ...this.quasi.expressions],
11549
- thisParam: this.tag instanceof MemberExpression && !this.tag.variable ? this.tag.object : null,
11387
+ thisArg: this.tag instanceof MemberExpression && !this.tag.variable ? this.tag.object : null,
11388
+ type: INTERACTION_CALLED,
11550
11389
  withNew: false
11551
11390
  };
11552
11391
  }
@@ -11556,9 +11395,8 @@ class TaggedTemplateExpression extends CallExpressionBase {
11556
11395
  }
11557
11396
  applyDeoptimizations() {
11558
11397
  this.deoptimized = true;
11559
- const { thisParam } = this.callOptions;
11560
- if (thisParam) {
11561
- this.tag.deoptimizeThisOnEventAtPath(EVENT_CALLED, EMPTY_PATH, thisParam, SHARED_RECURSION_TRACKER);
11398
+ if (this.interaction.thisArg) {
11399
+ this.tag.deoptimizeThisOnInteractionAtPath(this.interaction, EMPTY_PATH, SHARED_RECURSION_TRACKER);
11562
11400
  }
11563
11401
  for (const argument of this.quasi.expressions) {
11564
11402
  // This will make sure all properties of parameters behave as "unknown"
@@ -11569,7 +11407,7 @@ class TaggedTemplateExpression extends CallExpressionBase {
11569
11407
  getReturnExpression(recursionTracker = SHARED_RECURSION_TRACKER) {
11570
11408
  if (this.returnExpression === null) {
11571
11409
  this.returnExpression = UNKNOWN_EXPRESSION;
11572
- return (this.returnExpression = this.tag.getReturnExpressionWhenCalledAtPath(EMPTY_PATH, this.callOptions, recursionTracker, this));
11410
+ return (this.returnExpression = this.tag.getReturnExpressionWhenCalledAtPath(EMPTY_PATH, this.interaction, recursionTracker, this));
11573
11411
  }
11574
11412
  return this.returnExpression;
11575
11413
  }
@@ -11592,7 +11430,7 @@ class TemplateElement extends NodeBase {
11592
11430
  }
11593
11431
 
11594
11432
  class TemplateLiteral extends NodeBase {
11595
- deoptimizeThisOnEventAtPath() { }
11433
+ deoptimizeThisOnInteractionAtPath() { }
11596
11434
  getLiteralValueAtPath(path) {
11597
11435
  if (path.length > 0 || this.quasis.length !== 1) {
11598
11436
  return UnknownValue;
@@ -11605,12 +11443,12 @@ class TemplateLiteral extends NodeBase {
11605
11443
  }
11606
11444
  return getMemberReturnExpressionWhenCalled(literalStringMembers, path[0]);
11607
11445
  }
11608
- hasEffectsWhenAccessedAtPath(path) {
11609
- return path.length > 1;
11610
- }
11611
- hasEffectsWhenCalledAtPath(path, callOptions, context) {
11612
- if (path.length === 1) {
11613
- return hasMemberEffectWhenCalled(literalStringMembers, path[0], callOptions, context);
11446
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
11447
+ if (interaction.type === INTERACTION_ACCESSED) {
11448
+ return path.length > 1;
11449
+ }
11450
+ if (interaction.type === INTERACTION_CALLED && path.length === 1) {
11451
+ return hasMemberEffectWhenCalled(literalStringMembers, path[0], interaction, context);
11614
11452
  }
11615
11453
  return true;
11616
11454
  }
@@ -11738,16 +11576,15 @@ class ThisExpression extends NodeBase {
11738
11576
  deoptimizePath(path) {
11739
11577
  this.variable.deoptimizePath(path);
11740
11578
  }
11741
- deoptimizeThisOnEventAtPath(event, path, thisParameter, recursionTracker) {
11742
- this.variable.deoptimizeThisOnEventAtPath(event, path,
11579
+ deoptimizeThisOnInteractionAtPath(interaction, path, recursionTracker) {
11743
11580
  // We rewrite the parameter so that a ThisVariable can detect self-mutations
11744
- thisParameter === this ? this.variable : thisParameter, recursionTracker);
11745
- }
11746
- hasEffectsWhenAccessedAtPath(path, context) {
11747
- return path.length > 0 && this.variable.hasEffectsWhenAccessedAtPath(path, context);
11581
+ this.variable.deoptimizeThisOnInteractionAtPath(interaction.thisArg === this ? { ...interaction, thisArg: this.variable } : interaction, path, recursionTracker);
11748
11582
  }
11749
- hasEffectsWhenAssignedAtPath(path, context) {
11750
- return this.variable.hasEffectsWhenAssignedAtPath(path, context);
11583
+ hasEffectsOnInteractionAtPath(path, interaction, context) {
11584
+ if (path.length === 0) {
11585
+ return interaction.type !== INTERACTION_ACCESSED;
11586
+ }
11587
+ return this.variable.hasEffectsOnInteractionAtPath(path, interaction, context);
11751
11588
  }
11752
11589
  include() {
11753
11590
  if (!this.included) {
@@ -11841,10 +11678,6 @@ const unaryOperators = {
11841
11678
  '~': value => ~value
11842
11679
  };
11843
11680
  class UnaryExpression extends NodeBase {
11844
- constructor() {
11845
- super(...arguments);
11846
- this.deoptimized = false;
11847
- }
11848
11681
  getLiteralValueAtPath(path, recursionTracker, origin) {
11849
11682
  if (path.length > 0)
11850
11683
  return UnknownValue;
@@ -11860,13 +11693,10 @@ class UnaryExpression extends NodeBase {
11860
11693
  return false;
11861
11694
  return (this.argument.hasEffects(context) ||
11862
11695
  (this.operator === 'delete' &&
11863
- this.argument.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context)));
11696
+ this.argument.hasEffectsOnInteractionAtPath(EMPTY_PATH, NODE_INTERACTION_UNKNOWN_ASSIGNMENT, context)));
11864
11697
  }
11865
- hasEffectsWhenAccessedAtPath(path) {
11866
- if (this.operator === 'void') {
11867
- return path.length > 0;
11868
- }
11869
- return path.length > 1;
11698
+ hasEffectsOnInteractionAtPath(path, { type }) {
11699
+ return type !== INTERACTION_ACCESSED || path.length > (this.operator === 'void' ? 0 : 1);
11870
11700
  }
11871
11701
  applyDeoptimizations() {
11872
11702
  this.deoptimized = true;
@@ -11887,18 +11717,22 @@ class UnknownNode extends NodeBase {
11887
11717
  }
11888
11718
 
11889
11719
  class UpdateExpression extends NodeBase {
11890
- constructor() {
11891
- super(...arguments);
11892
- this.deoptimized = false;
11893
- }
11894
11720
  hasEffects(context) {
11895
11721
  if (!this.deoptimized)
11896
11722
  this.applyDeoptimizations();
11897
- return (this.argument.hasEffects(context) ||
11898
- this.argument.hasEffectsWhenAssignedAtPath(EMPTY_PATH, context));
11723
+ return this.argument.hasEffectsAsAssignmentTarget(context, true);
11724
+ }
11725
+ hasEffectsOnInteractionAtPath(path, { type }) {
11726
+ return path.length > 1 || type !== INTERACTION_ACCESSED;
11727
+ }
11728
+ include(context, includeChildrenRecursively) {
11729
+ if (!this.deoptimized)
11730
+ this.applyDeoptimizations();
11731
+ this.included = true;
11732
+ this.argument.includeAsAssignmentTarget(context, includeChildrenRecursively, true);
11899
11733
  }
11900
- hasEffectsWhenAccessedAtPath(path) {
11901
- return path.length > 1;
11734
+ initialise() {
11735
+ this.argument.setAssignedValue(UNKNOWN_EXPRESSION);
11902
11736
  }
11903
11737
  render(code, options) {
11904
11738
  const { exportNamesByVariable, format, snippets: { _ } } = options;
@@ -11960,7 +11794,7 @@ class VariableDeclaration extends NodeBase {
11960
11794
  declarator.deoptimizePath(EMPTY_PATH);
11961
11795
  }
11962
11796
  }
11963
- hasEffectsWhenAssignedAtPath() {
11797
+ hasEffectsOnInteractionAtPath() {
11964
11798
  return false;
11965
11799
  }
11966
11800
  include(context, includeChildrenRecursively, { asSingleStatement } = BLANK) {
@@ -11992,6 +11826,7 @@ class VariableDeclaration extends NodeBase {
11992
11826
  this.renderReplacedDeclarations(code, options);
11993
11827
  }
11994
11828
  }
11829
+ applyDeoptimizations() { }
11995
11830
  renderDeclarationEnd(code, separatorString, lastSeparatorPos, actualContentEnd, renderedContentEnd, systemPatternExports, options) {
11996
11831
  if (code.original.charCodeAt(this.end - 1) === 59 /*";"*/) {
11997
11832
  code.remove(this.end - 1, this.end);
@@ -12122,9 +11957,7 @@ class VariableDeclarator extends NodeBase {
12122
11957
  include(context, includeChildrenRecursively) {
12123
11958
  var _a;
12124
11959
  this.included = true;
12125
- (_a = this.init) === null || _a === void 0 ? void 0 : _a.include(context, includeChildrenRecursively, {
12126
- includeWithoutParameterDefaults: true
12127
- });
11960
+ (_a = this.init) === null || _a === void 0 ? void 0 : _a.include(context, includeChildrenRecursively);
12128
11961
  this.id.markDeclarationReached();
12129
11962
  if (includeChildrenRecursively || this.id.shouldBeIncluded(context)) {
12130
11963
  this.id.include(context, includeChildrenRecursively);
@@ -12148,6 +11981,7 @@ class VariableDeclarator extends NodeBase {
12148
11981
  code.appendLeft(this.end, `${_}=${_}void 0`);
12149
11982
  }
12150
11983
  }
11984
+ applyDeoptimizations() { }
12151
11985
  }
12152
11986
 
12153
11987
  class WhileStatement extends NodeBase {
@@ -12174,15 +12008,11 @@ class WhileStatement extends NodeBase {
12174
12008
  }
12175
12009
 
12176
12010
  class YieldExpression extends NodeBase {
12177
- constructor() {
12178
- super(...arguments);
12179
- this.deoptimized = false;
12180
- }
12181
12011
  hasEffects(context) {
12182
12012
  var _a;
12183
12013
  if (!this.deoptimized)
12184
12014
  this.applyDeoptimizations();
12185
- return !context.ignore.returnYield || !!((_a = this.argument) === null || _a === void 0 ? void 0 : _a.hasEffects(context));
12015
+ return !(context.ignore.returnYield && !((_a = this.argument) === null || _a === void 0 ? void 0 : _a.hasEffects(context)));
12186
12016
  }
12187
12017
  render(code, options) {
12188
12018
  if (this.argument) {