@lwc/synthetic-shadow 2.5.11 → 2.6.3

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.
@@ -194,7 +194,7 @@ const KEY__SYNTHETIC_MODE = '$$lwc-synthetic-mode';
194
194
 
195
195
 
196
196
  const hasNativeSymbolSupport = /*@__PURE__*/(() => Symbol('x').toString() === 'Symbol(x)')();
197
- /** version: 2.5.11 */
197
+ /** version: 2.6.3 */
198
198
 
199
199
  /*
200
200
  * Copyright (c) 2018, salesforce.com, inc.
@@ -301,6 +301,7 @@ const {
301
301
  getElementsByClassName: getElementsByClassName$1
302
302
  } = HTMLElement.prototype;
303
303
  const shadowRootGetter = hasOwnProperty.call(Element.prototype, 'shadowRoot') ? getOwnPropertyDescriptor(Element.prototype, 'shadowRoot').get : () => null;
304
+ const assignedSlotGetter$1 = hasOwnProperty.call(Element.prototype, 'assignedSlot') ? getOwnPropertyDescriptor(Element.prototype, 'assignedSlot').get : () => null;
304
305
 
305
306
  /*
306
307
  * Copyright (c) 2018, salesforce.com, inc.
@@ -515,19 +516,6 @@ function arrayFromCollection(collection) {
515
516
  return cloned;
516
517
  }
517
518
 
518
- /**
519
- * Copyright (C) 2018 salesforce.com, inc.
520
- */
521
-
522
- if (!_globalThis.lwcRuntimeFlags) {
523
- Object.defineProperty(_globalThis, 'lwcRuntimeFlags', {
524
- value: create(null)
525
- });
526
- }
527
-
528
- const runtimeFlags = _globalThis.lwcRuntimeFlags;
529
- /** version: 2.5.11 */
530
-
531
519
  /*
532
520
  * Copyright (c) 2018, salesforce.com, inc.
533
521
  * All rights reserved.
@@ -587,19 +575,9 @@ function getEventListenerWrapper(fnOrObj) {
587
575
  assert.invariant(isFalse(isSyntheticShadowHost(currentTarget)), 'This routine should not be used to wrap event listeners for host elements and shadow roots.');
588
576
  }
589
577
 
590
- const {
591
- composed
592
- } = event;
593
- let shouldInvoke;
594
-
595
- if (runtimeFlags.ENABLE_NON_COMPOSED_EVENTS_LEAKAGE) {
596
- shouldInvoke = !(eventToShadowRootMap.has(event) && isFalse(composed));
597
- } else {
598
- const actualTarget = getActualTarget(event);
599
- shouldInvoke = shouldInvokeListener(event, actualTarget, currentTarget);
600
- }
578
+ const actualTarget = getActualTarget(event);
601
579
 
602
- if (!shouldInvoke) {
580
+ if (!shouldInvokeListener(event, actualTarget, currentTarget)) {
603
581
  return;
604
582
  }
605
583
 
@@ -619,25 +597,6 @@ function getEventListenerWrapper(fnOrObj) {
619
597
  * For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
620
598
  */
621
599
  const eventToContextMap = new WeakMap();
622
-
623
- function isChildNode(root, node) {
624
- return !!(compareDocumentPosition.call(root, node) & DOCUMENT_POSITION_CONTAINED_BY);
625
- }
626
-
627
- const GET_ROOT_NODE_CONFIG_FALSE = {
628
- composed: false
629
- };
630
-
631
- function getRootNodeHost(node, options) {
632
- let rootNode = node.getRootNode(options);
633
-
634
- if (isSyntheticShadowRoot(rootNode)) {
635
- rootNode = getHost(rootNode);
636
- }
637
-
638
- return rootNode;
639
- }
640
-
641
600
  const customElementToWrappedListeners = new WeakMap();
642
601
 
643
602
  function getEventMap(elm) {
@@ -681,16 +640,9 @@ function getWrappedShadowRootListener(listener) {
681
640
  currentTarget = getShadowRoot(currentTarget);
682
641
  }
683
642
 
684
- let shouldInvoke;
643
+ const actualTarget = getActualTarget(event);
685
644
 
686
- if (runtimeFlags.ENABLE_NON_COMPOSED_EVENTS_LEAKAGE) {
687
- shouldInvoke = shouldInvokeShadowRootListener(event);
688
- } else {
689
- const actualTarget = getActualTarget(event);
690
- shouldInvoke = shouldInvokeListener(event, actualTarget, currentTarget);
691
- }
692
-
693
- if (shouldInvoke) {
645
+ if (shouldInvokeListener(event, actualTarget, currentTarget)) {
694
646
  listener.call(currentTarget, event);
695
647
  }
696
648
  };
@@ -717,16 +669,9 @@ function getWrappedCustomElementListener(listener) {
717
669
  customElementWrappedListener = function (event) {
718
670
  // currentTarget is always defined inside an event listener
719
671
  const currentTarget = eventCurrentTargetGetter.call(event);
720
- let shouldInvoke;
672
+ const actualTarget = getActualTarget(event);
721
673
 
722
- if (runtimeFlags.ENABLE_NON_COMPOSED_EVENTS_LEAKAGE) {
723
- shouldInvoke = shouldInvokeCustomElementListener(event);
724
- } else {
725
- const actualTarget = getActualTarget(event);
726
- shouldInvoke = shouldInvokeListener(event, actualTarget, currentTarget);
727
- }
728
-
729
- if (shouldInvoke) {
674
+ if (shouldInvokeListener(event, actualTarget, currentTarget)) {
730
675
  listener.call(currentTarget, event);
731
676
  }
732
677
  };
@@ -847,70 +792,6 @@ function detachDOMListener(elm, type, wrappedListener) {
847
792
  }
848
793
  }
849
794
 
850
- function shouldInvokeCustomElementListener(event) {
851
- const {
852
- composed
853
- } = event;
854
-
855
- if (isTrue(composed)) {
856
- // Listeners on host elements should always be invoked for {composed: true} events.
857
- return true;
858
- } // If this {composed: false} event was dispatched on any root.
859
-
860
-
861
- if (eventToShadowRootMap.has(event)) {
862
- return false;
863
- }
864
-
865
- const target = eventTargetGetter.call(event);
866
- const currentTarget = eventCurrentTargetGetter.call(event); // If this {composed: false} event was dispatched on the current target host.
867
-
868
- if (target === currentTarget) {
869
- return true;
870
- } // At this point the event must be {bubbles: true, composed: false} and was dispatched from a
871
- // shadow-excluding descendant node. In this case, we only invoke the listener if the target
872
- // host was assigned to a slot in the composed subtree of the current target host.
873
-
874
-
875
- const targetHost = getRootNodeHost(target, GET_ROOT_NODE_CONFIG_FALSE);
876
- const currentTargetHost = currentTarget;
877
- return isChildNode(targetHost, currentTargetHost);
878
- }
879
-
880
- function shouldInvokeShadowRootListener(event) {
881
- const {
882
- composed
883
- } = event;
884
- const target = eventTargetGetter.call(event);
885
- const currentTarget = eventCurrentTargetGetter.call(event); // If the event was dispatched on the host or its root.
886
-
887
- if (target === currentTarget) {
888
- // Invoke the listener if the event was dispatched directly on the root.
889
- return eventToShadowRootMap.get(event) === getShadowRoot(target);
890
- } // At this point the event is {bubbles: true} and was dispatched from a shadow-including descendant node.
891
-
892
-
893
- if (isTrue(composed)) {
894
- // Invoke the listener if the event is {composed: true}.
895
- return true;
896
- } // At this point the event must be {bubbles: true, composed: false}.
897
-
898
-
899
- if (isTrue(eventToShadowRootMap.has(event))) {
900
- // Don't invoke the listener because the event was dispatched on a descendant root.
901
- return false;
902
- }
903
-
904
- const targetHost = getRootNodeHost(target, GET_ROOT_NODE_CONFIG_FALSE);
905
- const currentTargetHost = currentTarget;
906
- const isCurrentTargetSlotted = isChildNode(targetHost, currentTargetHost); // At this point the event must be {bubbles: true, composed: false} and was dispatched from a
907
- // shadow-excluding descendant node. In this case, we only invoke the listener if the target
908
- // host was assigned to a slot in the composed subtree of the current target host, or the
909
- // descendant node is in the shadow tree of the current root.
910
-
911
- return isCurrentTargetSlotted || targetHost === currentTargetHost;
912
- }
913
-
914
795
  function addCustomElementEventListener(type, listener, _options) {
915
796
  if (process.env.NODE_ENV !== 'production') {
916
797
  if (!isFunction(listener)) {
@@ -1019,6 +900,14 @@ function getNodeKey(node) {
1019
900
  function isNodeShadowed(node) {
1020
901
  return !isUndefined(getNodeOwnerKey(node));
1021
902
  }
903
+ /**
904
+ * Returns true if this node is a shadow host, is in a shadow host, or contains a shadow host
905
+ * anywhere in its tree.
906
+ */
907
+
908
+ function isNodeOrDescendantsShadowed(node) {
909
+ return isNodeShadowed(node) || isSyntheticShadowHost(node) || containsHost(node);
910
+ }
1022
911
 
1023
912
  /*
1024
913
  * Copyright (c) 2018, salesforce.com, inc.
@@ -1632,6 +1521,19 @@ function getOuterHTML(node) {
1632
1521
  }
1633
1522
  }
1634
1523
 
1524
+ /**
1525
+ * Copyright (C) 2018 salesforce.com, inc.
1526
+ */
1527
+
1528
+ if (!_globalThis.lwcRuntimeFlags) {
1529
+ Object.defineProperty(_globalThis, 'lwcRuntimeFlags', {
1530
+ value: create(null)
1531
+ });
1532
+ }
1533
+
1534
+ const runtimeFlags = _globalThis.lwcRuntimeFlags;
1535
+ /** version: 2.6.3 */
1536
+
1635
1537
  /*
1636
1538
  * Copyright (c) 2018, salesforce.com, inc.
1637
1539
  * All rights reserved.
@@ -1723,7 +1625,9 @@ function parentElementGetterPatched() {
1723
1625
  }
1724
1626
 
1725
1627
  function compareDocumentPositionPatched(otherNode) {
1726
- if (this.getRootNode() === otherNode) {
1628
+ if (this === otherNode) {
1629
+ return 0;
1630
+ } else if (this.getRootNode() === otherNode) {
1727
1631
  // "this" is in a shadow tree where the shadow root is the "otherNode".
1728
1632
  return 10; // Node.DOCUMENT_POSITION_CONTAINS | Node.DOCUMENT_POSITION_PRECEDING
1729
1633
  } else if (getNodeOwnerKey(this) !== getNodeOwnerKey(otherNode)) {
@@ -1769,7 +1673,7 @@ function cloneNodePatched(deep) {
1769
1673
  function childNodesGetterPatched() {
1770
1674
  if (isSyntheticShadowHost(this)) {
1771
1675
  const owner = getNodeOwner(this);
1772
- const childNodes = isNull(owner) ? [] : getAllMatches(owner, getFilteredChildNodes(this));
1676
+ const childNodes = isNull(owner) ? getFilteredChildNodes(this) : getAllMatches(owner, getFilteredChildNodes(this));
1773
1677
 
1774
1678
  if (process.env.NODE_ENV !== 'production' && isFalse(hasNativeSymbolSupport) && isExternalChildNodeAccessorFlagOn()) {
1775
1679
  // inserting a comment node as the first childNode to trick the IE11
@@ -1880,7 +1784,8 @@ defineProperties(_Node.prototype, {
1880
1784
  textContent: {
1881
1785
  get() {
1882
1786
  if (!runtimeFlags.ENABLE_NODE_PATCH) {
1883
- if (isNodeShadowed(this) || isSyntheticShadowHost(this)) {
1787
+ // See note on get innerHTML in faux-shadow/element.ts
1788
+ if (isNodeOrDescendantsShadowed(this)) {
1884
1789
  return textContentGetterPatched.call(this);
1885
1790
  }
1886
1791
 
@@ -2114,7 +2019,22 @@ function getAllRootNodes(node) {
2114
2019
  }
2115
2020
 
2116
2021
  return rootNodes;
2117
- }
2022
+ } // Keep searching up the host tree until we find an element that is within the immediate shadow root
2023
+
2024
+
2025
+ const findAncestorHostInImmediateShadowRoot = (rootNode, targetRootNode) => {
2026
+ let host;
2027
+
2028
+ while (!isUndefined(host = rootNode.host)) {
2029
+ const thisRootNode = host.getRootNode();
2030
+
2031
+ if (thisRootNode === targetRootNode) {
2032
+ return host;
2033
+ }
2034
+
2035
+ rootNode = thisRootNode;
2036
+ }
2037
+ };
2118
2038
 
2119
2039
  function fauxElementsFromPoint(context, doc, left, top) {
2120
2040
  const elements = elementsFromPoint.call(doc, left, top);
@@ -2128,8 +2048,28 @@ function fauxElementsFromPoint(context, doc, left, top) {
2128
2048
  for (let i = 0; i < elements.length; i++) {
2129
2049
  const element = elements[i];
2130
2050
 
2131
- if (rootNodes.indexOf(element.getRootNode()) !== -1 && !isSyntheticSlotElement(element)) {
2132
- result.push(element);
2051
+ if (isSyntheticSlotElement(element)) {
2052
+ continue;
2053
+ }
2054
+
2055
+ const elementRootNode = element.getRootNode();
2056
+
2057
+ if (ArrayIndexOf.call(rootNodes, elementRootNode) !== -1) {
2058
+ ArrayPush.call(result, element);
2059
+ continue;
2060
+ } // In cases where the host element is not visible but its shadow descendants are, then
2061
+ // we may get the shadow descendant instead of the host element here. (The
2062
+ // browser doesn't know the difference in synthetic shadow DOM.)
2063
+ // In native shadow DOM, however, elementsFromPoint would return the host but not
2064
+ // the child. So we need to detect if this shadow element's host is accessible from
2065
+ // the context's shadow root. Note we also need to be careful not to add the host
2066
+ // multiple times.
2067
+
2068
+
2069
+ const ancestorHost = findAncestorHostInImmediateShadowRoot(elementRootNode, rootNodes[0]);
2070
+
2071
+ if (!isUndefined(ancestorHost) && ArrayIndexOf.call(elements, ancestorHost) === -1 && ArrayIndexOf.call(result, ancestorHost) === -1) {
2072
+ ArrayPush.call(result, ancestorHost);
2133
2073
  }
2134
2074
  }
2135
2075
  }
@@ -2203,6 +2143,28 @@ function isSyntheticShadowHost(node) {
2203
2143
  function isSyntheticShadowRoot(node) {
2204
2144
  const shadowRootRecord = InternalSlot.get(node);
2205
2145
  return !isUndefined(shadowRootRecord) && node === shadowRootRecord.shadowRoot;
2146
+ } // Return true if any descendant is a host element
2147
+
2148
+ function containsHost(node) {
2149
+ // IE11 complains with "Unexpected call to method or property access." when calling walker.nextNode().
2150
+ // The fix for this is to only walk trees for nodes that are Node.ELEMENT_NODE.
2151
+ if (node.nodeType !== _Node.ELEMENT_NODE) {
2152
+ return false;
2153
+ } // IE requires all four arguments, even though the fourth is deprecated
2154
+ // https://developer.mozilla.org/en-US/docs/Web/API/Document/createTreeWalker#browser_compatibility
2155
+ // @ts-ignore
2156
+
2157
+
2158
+ const walker = document.createTreeWalker(node, NodeFilter.SHOW_ELEMENT, null, false);
2159
+ let descendant;
2160
+
2161
+ while (!isNull(descendant = walker.nextNode())) {
2162
+ if (isSyntheticShadowHost(descendant)) {
2163
+ return true;
2164
+ }
2165
+ }
2166
+
2167
+ return false;
2206
2168
  }
2207
2169
  let uid = 0;
2208
2170
  function attachShadow(elm, options) {
@@ -2250,6 +2212,12 @@ const SyntheticShadowRootDescriptors = {
2250
2212
  return `[object ShadowRoot]`;
2251
2213
  }
2252
2214
 
2215
+ },
2216
+ synthetic: {
2217
+ writable: false,
2218
+ enumerable: false,
2219
+ configurable: false,
2220
+ value: true
2253
2221
  }
2254
2222
  };
2255
2223
  const ShadowRootDescriptors = {
@@ -4078,6 +4046,14 @@ retargetRelatedTarget(FocusEvent);
4078
4046
  */
4079
4047
  retargetRelatedTarget(MouseEvent);
4080
4048
 
4049
+ /*
4050
+ * Copyright (c) 2021, salesforce.com, inc.
4051
+ * All rights reserved.
4052
+ * SPDX-License-Identifier: MIT
4053
+ * For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
4054
+ */
4055
+ const assignedSlotGetter = hasOwnProperty.call(Text.prototype, 'assignedSlot') ? getOwnPropertyDescriptor(Text.prototype, 'assignedSlot').get : () => null;
4056
+
4081
4057
  /*
4082
4058
  * Copyright (c) 2018, salesforce.com, inc.
4083
4059
  * All rights reserved.
@@ -4131,10 +4107,22 @@ function getFilteredSlotFlattenNodes(slot) {
4131
4107
  }
4132
4108
 
4133
4109
  function assignedSlotGetterPatched() {
4134
- const parentNode = parentNodeGetter.call(this);
4110
+ const parentNode = parentNodeGetter.call(this); // use original assignedSlot if parent has a native shdow root
4111
+
4112
+ if (parentNode instanceof Element) {
4113
+ const sr = shadowRootGetter.call(parentNode);
4114
+
4115
+ if (isInstanceOfNativeShadowRoot(sr)) {
4116
+ if (this instanceof Text) {
4117
+ return assignedSlotGetter.call(this);
4118
+ }
4119
+
4120
+ return assignedSlotGetter$1.call(this);
4121
+ }
4122
+ }
4135
4123
  /**
4136
4124
  * The node is assigned to a slot if:
4137
- * - it has a parent and it parent its parent is a slot element
4125
+ * - it has a parent and its parent is a slot element
4138
4126
  * - and if the slot owner key is different than the node owner key.
4139
4127
  *
4140
4128
  * When the slot and the slotted node are 2 different shadow trees, the owner keys will be
@@ -4143,6 +4131,7 @@ function assignedSlotGetterPatched() {
4143
4131
  * different than the node owner key (always `undefined`).
4144
4132
  */
4145
4133
 
4134
+
4146
4135
  if (!isNull(parentNode) && isSlotElement(parentNode) && getNodeOwnerKey(parentNode) !== getNodeOwnerKey(this)) {
4147
4136
  return parentNode;
4148
4137
  }
@@ -4359,7 +4348,10 @@ defineProperties(Element.prototype, {
4359
4348
  innerHTML: {
4360
4349
  get() {
4361
4350
  if (!runtimeFlags.ENABLE_ELEMENT_PATCH) {
4362
- if (isNodeShadowed(this) || isSyntheticShadowHost(this)) {
4351
+ // If this element is in synthetic shadow, if it's a synthetic shadow host,
4352
+ // or if any of its descendants are synthetic shadow hosts, then we can't
4353
+ // use the native innerHTML because it would expose private node internals.
4354
+ if (isNodeOrDescendantsShadowed(this)) {
4363
4355
  return innerHTMLGetterPatched.call(this);
4364
4356
  }
4365
4357
 
@@ -4384,7 +4376,8 @@ defineProperties(Element.prototype, {
4384
4376
  outerHTML: {
4385
4377
  get() {
4386
4378
  if (!runtimeFlags.ENABLE_ELEMENT_PATCH) {
4387
- if (isNodeShadowed(this) || isSyntheticShadowHost(this)) {
4379
+ // See notes above on get innerHTML
4380
+ if (isNodeOrDescendantsShadowed(this)) {
4388
4381
  return outerHTMLGetterPatched.call(this);
4389
4382
  }
4390
4383
 
@@ -5757,4 +5750,4 @@ defineProperty(Element.prototype, '$domManual$', {
5757
5750
 
5758
5751
  configurable: true
5759
5752
  });
5760
- /** version: 2.5.11 */
5753
+ /** version: 2.6.3 */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lwc/synthetic-shadow",
3
- "version": "2.5.11",
3
+ "version": "2.6.3",
4
4
  "description": "Synthetic Shadow Root for LWC",
5
5
  "homepage": "https://lwc.dev/",
6
6
  "repository": {
@@ -36,8 +36,8 @@
36
36
  "access": "public"
37
37
  },
38
38
  "devDependencies": {
39
- "@lwc/features": "2.5.11",
40
- "@lwc/shared": "2.5.11"
39
+ "@lwc/features": "2.6.3",
40
+ "@lwc/shared": "2.6.3"
41
41
  },
42
- "gitHead": "2e72bcacbf105ef92277372bb4e52f8280d7fa72"
42
+ "gitHead": "1fdd835243eed190b8ab9ca61ae7eae9f9a4073d"
43
43
  }