@remote-dom/polyfill 1.5.0 → 1.6.0

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.
Files changed (304) hide show
  1. package/CHANGELOG.md +94 -0
  2. package/README.md +51 -3
  3. package/build/cjs/Attr.cjs +33 -4
  4. package/build/cjs/CharacterData.cjs +10 -0
  5. package/build/cjs/ChildNode.cjs +79 -13
  6. package/build/cjs/Comment.cjs +1 -1
  7. package/build/cjs/CustomElementRegistry.cjs +27 -2
  8. package/build/cjs/CustomEvent.cjs +2 -2
  9. package/build/cjs/Document.cjs +56 -32
  10. package/build/cjs/DocumentFragment.cjs +6 -2
  11. package/build/cjs/Element.cjs +68 -8
  12. package/build/cjs/Event.cjs +29 -27
  13. package/build/cjs/EventTarget.cjs +128 -58
  14. package/build/cjs/HTMLTemplateElement.cjs +1 -0
  15. package/build/cjs/MutationObserver.cjs +167 -1
  16. package/build/cjs/NamedNodeMap.cjs +82 -45
  17. package/build/cjs/Node.cjs +47 -11
  18. package/build/cjs/NodeList.cjs +9 -1
  19. package/build/cjs/ParentNode.cjs +319 -77
  20. package/build/cjs/SVGElement.cjs +1 -1
  21. package/build/cjs/Text.cjs +1 -1
  22. package/build/cjs/Window.cjs +131 -38
  23. package/build/cjs/attribute-reactions.cjs +20 -0
  24. package/build/cjs/constants.cjs +48 -24
  25. package/build/cjs/custom-element-reactions.cjs +52 -0
  26. package/build/cjs/dom-exception.cjs +15 -0
  27. package/build/cjs/hook-effects.cjs +51 -0
  28. package/build/cjs/names.cjs +61 -0
  29. package/build/cjs/selectors.cjs +213 -122
  30. package/build/cjs/serialization.cjs +168 -65
  31. package/build/cjs/shared.cjs +177 -28
  32. package/build/esm/Attr.mjs +34 -5
  33. package/build/esm/CharacterData.mjs +10 -0
  34. package/build/esm/ChildNode.mjs +76 -15
  35. package/build/esm/Comment.mjs +2 -2
  36. package/build/esm/CustomElementRegistry.mjs +27 -2
  37. package/build/esm/CustomEvent.mjs +2 -2
  38. package/build/esm/Document.mjs +60 -35
  39. package/build/esm/DocumentFragment.mjs +7 -3
  40. package/build/esm/Element.mjs +69 -9
  41. package/build/esm/Event.mjs +27 -27
  42. package/build/esm/EventTarget.mjs +130 -60
  43. package/build/esm/HTMLTemplateElement.mjs +2 -1
  44. package/build/esm/MutationObserver.mjs +166 -2
  45. package/build/esm/NamedNodeMap.mjs +83 -46
  46. package/build/esm/Node.mjs +48 -12
  47. package/build/esm/NodeList.mjs +9 -1
  48. package/build/esm/ParentNode.mjs +322 -81
  49. package/build/esm/SVGElement.mjs +2 -2
  50. package/build/esm/Text.mjs +2 -2
  51. package/build/esm/Window.mjs +132 -39
  52. package/build/esm/attribute-reactions.mjs +16 -0
  53. package/build/esm/constants.mjs +28 -23
  54. package/build/esm/custom-element-reactions.mjs +47 -0
  55. package/build/esm/dom-exception.mjs +11 -0
  56. package/build/esm/hook-effects.mjs +46 -0
  57. package/build/esm/names.mjs +54 -0
  58. package/build/esm/selectors.mjs +202 -124
  59. package/build/esm/serialization.mjs +169 -66
  60. package/build/esm/shared.mjs +173 -30
  61. package/build/esnext/Attr.esnext +45 -5
  62. package/build/esnext/CharacterData.esnext +10 -0
  63. package/build/esnext/ChildNode.esnext +84 -15
  64. package/build/esnext/Comment.esnext +2 -2
  65. package/build/esnext/CustomElementRegistry.esnext +42 -0
  66. package/build/esnext/CustomEvent.esnext +2 -2
  67. package/build/esnext/Document.esnext +69 -32
  68. package/build/esnext/DocumentFragment.esnext +7 -3
  69. package/build/esnext/Element.esnext +78 -9
  70. package/build/esnext/Event.esnext +36 -37
  71. package/build/esnext/EventTarget.esnext +133 -61
  72. package/build/esnext/HTMLTemplateElement.esnext +3 -1
  73. package/build/esnext/MutationObserver.esnext +163 -2
  74. package/build/esnext/NamedNodeMap.esnext +110 -42
  75. package/build/esnext/Node.esnext +50 -12
  76. package/build/esnext/NodeList.esnext +1 -1
  77. package/build/esnext/ParentNode.esnext +352 -79
  78. package/build/esnext/SVGElement.esnext +2 -2
  79. package/build/esnext/Text.esnext +2 -2
  80. package/build/esnext/Window.esnext +120 -16
  81. package/build/esnext/attribute-reactions.esnext +21 -0
  82. package/build/esnext/constants.esnext +34 -21
  83. package/build/esnext/custom-element-reactions.esnext +49 -0
  84. package/build/esnext/dom-exception.esnext +11 -0
  85. package/build/esnext/hook-effects.esnext +46 -0
  86. package/build/esnext/names.esnext +61 -0
  87. package/build/esnext/selectors.esnext +202 -100
  88. package/build/esnext/serialization.esnext +171 -48
  89. package/build/esnext/shared.esnext +181 -34
  90. package/build/tsconfig.tsbuildinfo +1 -1
  91. package/build/typescript/Attr.d.ts +6 -4
  92. package/build/typescript/Attr.d.ts.map +1 -1
  93. package/build/typescript/CharacterData.d.ts.map +1 -1
  94. package/build/typescript/ChildNode.d.ts +5 -0
  95. package/build/typescript/ChildNode.d.ts.map +1 -1
  96. package/build/typescript/ClipboardEvent.d.ts.map +1 -1
  97. package/build/typescript/Comment.d.ts +2 -2
  98. package/build/typescript/Comment.d.ts.map +1 -1
  99. package/build/typescript/CustomElementRegistry.d.ts +1 -0
  100. package/build/typescript/CustomElementRegistry.d.ts.map +1 -1
  101. package/build/typescript/CustomEvent.d.ts.map +1 -1
  102. package/build/typescript/Document.d.ts +10 -5
  103. package/build/typescript/Document.d.ts.map +1 -1
  104. package/build/typescript/DocumentFragment.d.ts +2 -1
  105. package/build/typescript/DocumentFragment.d.ts.map +1 -1
  106. package/build/typescript/Element.d.ts +16 -7
  107. package/build/typescript/Element.d.ts.map +1 -1
  108. package/build/typescript/ErrorEvent.d.ts.map +1 -1
  109. package/build/typescript/Event.d.ts +9 -10
  110. package/build/typescript/Event.d.ts.map +1 -1
  111. package/build/typescript/EventTarget.d.ts +20 -3
  112. package/build/typescript/EventTarget.d.ts.map +1 -1
  113. package/build/typescript/FocusEvent.d.ts.map +1 -1
  114. package/build/typescript/HTMLTemplateElement.d.ts.map +1 -1
  115. package/build/typescript/MutationObserver.d.ts +42 -0
  116. package/build/typescript/MutationObserver.d.ts.map +1 -1
  117. package/build/typescript/NamedNodeMap.d.ts +5 -3
  118. package/build/typescript/NamedNodeMap.d.ts.map +1 -1
  119. package/build/typescript/Node.d.ts +4 -3
  120. package/build/typescript/Node.d.ts.map +1 -1
  121. package/build/typescript/NodeList.d.ts +3 -2
  122. package/build/typescript/NodeList.d.ts.map +1 -1
  123. package/build/typescript/ParentNode.d.ts +29 -10
  124. package/build/typescript/ParentNode.d.ts.map +1 -1
  125. package/build/typescript/PromiseRejectionEvent.d.ts.map +1 -1
  126. package/build/typescript/SVGElement.d.ts +1 -1
  127. package/build/typescript/SVGElement.d.ts.map +1 -1
  128. package/build/typescript/Text.d.ts +1 -1
  129. package/build/typescript/Text.d.ts.map +1 -1
  130. package/build/typescript/ToggleEvent.d.ts.map +1 -1
  131. package/build/typescript/Window.d.ts +5 -1
  132. package/build/typescript/Window.d.ts.map +1 -1
  133. package/build/typescript/attribute-reactions.d.ts +4 -0
  134. package/build/typescript/attribute-reactions.d.ts.map +1 -0
  135. package/build/typescript/constants.d.ts +27 -18
  136. package/build/typescript/constants.d.ts.map +1 -1
  137. package/build/typescript/custom-element-reactions.d.ts +6 -0
  138. package/build/typescript/custom-element-reactions.d.ts.map +1 -0
  139. package/build/typescript/dom-exception.d.ts +2 -0
  140. package/build/typescript/dom-exception.d.ts.map +1 -0
  141. package/build/typescript/extensions.d.ts +4 -0
  142. package/build/typescript/extensions.d.ts.map +1 -0
  143. package/build/typescript/hook-effects.d.ts +6 -0
  144. package/build/typescript/hook-effects.d.ts.map +1 -0
  145. package/build/typescript/hooks.d.ts +3 -3
  146. package/build/typescript/hooks.d.ts.map +1 -1
  147. package/build/typescript/index.d.ts +1 -0
  148. package/build/typescript/index.d.ts.map +1 -1
  149. package/build/typescript/names.d.ts +11 -0
  150. package/build/typescript/names.d.ts.map +1 -0
  151. package/build/typescript/selectors.d.ts +21 -22
  152. package/build/typescript/selectors.d.ts.map +1 -1
  153. package/build/typescript/serialization.d.ts.map +1 -1
  154. package/build/typescript/shared.d.ts +10 -0
  155. package/build/typescript/shared.d.ts.map +1 -1
  156. package/build/typescript/tests/ChildNode.test.d.ts +2 -0
  157. package/build/typescript/tests/ChildNode.test.d.ts.map +1 -0
  158. package/build/typescript/tests/MutationObserver.test.d.ts +2 -0
  159. package/build/typescript/tests/MutationObserver.test.d.ts.map +1 -0
  160. package/build/typescript/tests/adopt-inserted-subtrees.test.d.ts +2 -0
  161. package/build/typescript/tests/adopt-inserted-subtrees.test.d.ts.map +1 -0
  162. package/build/typescript/tests/attr-mutation.test.d.ts +2 -0
  163. package/build/typescript/tests/attr-mutation.test.d.ts.map +1 -0
  164. package/build/typescript/tests/child-node-before-after.test.d.ts +2 -0
  165. package/build/typescript/tests/child-node-before-after.test.d.ts.map +1 -0
  166. package/build/typescript/tests/child-node-replace-with.test.d.ts +2 -0
  167. package/build/typescript/tests/child-node-replace-with.test.d.ts.map +1 -0
  168. package/build/typescript/tests/clone-import-namespaces.test.d.ts +2 -0
  169. package/build/typescript/tests/clone-import-namespaces.test.d.ts.map +1 -0
  170. package/build/typescript/tests/constants.test.d.ts +2 -0
  171. package/build/typescript/tests/constants.test.d.ts.map +1 -0
  172. package/build/typescript/tests/create-element-namespaces.test.d.ts +2 -0
  173. package/build/typescript/tests/create-element-namespaces.test.d.ts.map +1 -0
  174. package/build/typescript/tests/create-text-node.test.d.ts +2 -0
  175. package/build/typescript/tests/create-text-node.test.d.ts.map +1 -0
  176. package/build/typescript/tests/custom-element-reactions.test.d.ts +2 -0
  177. package/build/typescript/tests/custom-element-reactions.test.d.ts.map +1 -0
  178. package/build/typescript/tests/custom-element-registry.test.d.ts +2 -0
  179. package/build/typescript/tests/custom-element-registry.test.d.ts.map +1 -0
  180. package/build/typescript/tests/custom-event.test.d.ts +2 -0
  181. package/build/typescript/tests/custom-event.test.d.ts.map +1 -0
  182. package/build/typescript/tests/document-clone-import-contract.test.d.ts +2 -0
  183. package/build/typescript/tests/document-clone-import-contract.test.d.ts.map +1 -0
  184. package/build/typescript/tests/document.test.d.ts +2 -0
  185. package/build/typescript/tests/document.test.d.ts.map +1 -0
  186. package/build/typescript/tests/dom-mutation-selector-errors.test.d.ts +2 -0
  187. package/build/typescript/tests/dom-mutation-selector-errors.test.d.ts.map +1 -0
  188. package/build/typescript/tests/event-dispatch.test.d.ts +2 -0
  189. package/build/typescript/tests/event-dispatch.test.d.ts.map +1 -0
  190. package/build/typescript/tests/event-target.test.d.ts +2 -0
  191. package/build/typescript/tests/event-target.test.d.ts.map +1 -0
  192. package/build/typescript/tests/event.test.d.ts +2 -0
  193. package/build/typescript/tests/event.test.d.ts.map +1 -0
  194. package/build/typescript/tests/extensions.test.d.ts +2 -0
  195. package/build/typescript/tests/extensions.test.d.ts.map +1 -0
  196. package/build/typescript/tests/get-elements-by-tag-name.test.d.ts +2 -0
  197. package/build/typescript/tests/get-elements-by-tag-name.test.d.ts.map +1 -0
  198. package/build/typescript/tests/getElementsByClassName.test.d.ts +2 -0
  199. package/build/typescript/tests/getElementsByClassName.test.d.ts.map +1 -0
  200. package/build/typescript/tests/hooks.test.d.ts +2 -0
  201. package/build/typescript/tests/hooks.test.d.ts.map +1 -0
  202. package/build/typescript/tests/inner-html-parsing.test.d.ts +2 -0
  203. package/build/typescript/tests/inner-html-parsing.test.d.ts.map +1 -0
  204. package/build/typescript/tests/is-default-namespace.test.d.ts +2 -0
  205. package/build/typescript/tests/is-default-namespace.test.d.ts.map +1 -0
  206. package/build/typescript/tests/name-and-namespace-normalization.test.d.ts +2 -0
  207. package/build/typescript/tests/name-and-namespace-normalization.test.d.ts.map +1 -0
  208. package/build/typescript/tests/named-node-map.test.d.ts +2 -0
  209. package/build/typescript/tests/named-node-map.test.d.ts.map +1 -0
  210. package/build/typescript/tests/namespaced-attribute-reactions.test.d.ts +2 -0
  211. package/build/typescript/tests/namespaced-attribute-reactions.test.d.ts.map +1 -0
  212. package/build/typescript/tests/node.test.d.ts +2 -0
  213. package/build/typescript/tests/node.test.d.ts.map +1 -0
  214. package/build/typescript/tests/parent-node-mutation-return-values.test.d.ts +2 -0
  215. package/build/typescript/tests/parent-node-mutation-return-values.test.d.ts.map +1 -0
  216. package/build/typescript/tests/parent-node-mutation-validation.test.d.ts +2 -0
  217. package/build/typescript/tests/parent-node-mutation-validation.test.d.ts.map +1 -0
  218. package/build/typescript/tests/parent-node.test.d.ts +2 -0
  219. package/build/typescript/tests/parent-node.test.d.ts.map +1 -0
  220. package/build/typescript/tests/serialization-template.test.d.ts +2 -0
  221. package/build/typescript/tests/serialization-template.test.d.ts.map +1 -0
  222. package/build/typescript/tests/slot-attribute.test.d.ts +2 -0
  223. package/build/typescript/tests/slot-attribute.test.d.ts.map +1 -0
  224. package/build/typescript/tests/text-content.test.d.ts +2 -0
  225. package/build/typescript/tests/text-content.test.d.ts.map +1 -0
  226. package/build/typescript/tests/toggle-attribute.test.d.ts +2 -0
  227. package/build/typescript/tests/toggle-attribute.test.d.ts.map +1 -0
  228. package/build/typescript/tests/wide-tree-traversal.test.d.ts +2 -0
  229. package/build/typescript/tests/wide-tree-traversal.test.d.ts.map +1 -0
  230. package/build/typescript/tests/window-set-global.test.d.ts +2 -0
  231. package/build/typescript/tests/window-set-global.test.d.ts.map +1 -0
  232. package/package.json +1 -1
  233. package/source/Attr.ts +60 -8
  234. package/source/CharacterData.ts +13 -0
  235. package/source/ChildNode.ts +107 -14
  236. package/source/Comment.ts +2 -2
  237. package/source/CustomElementRegistry.ts +56 -0
  238. package/source/CustomEvent.ts +2 -2
  239. package/source/Document.ts +104 -38
  240. package/source/DocumentFragment.ts +15 -3
  241. package/source/Element.ts +129 -14
  242. package/source/Event.ts +34 -32
  243. package/source/EventTarget.ts +203 -79
  244. package/source/HTMLTemplateElement.ts +2 -1
  245. package/source/MutationObserver.ts +279 -1
  246. package/source/NamedNodeMap.ts +141 -60
  247. package/source/Node.ts +70 -14
  248. package/source/NodeList.ts +13 -3
  249. package/source/ParentNode.ts +500 -88
  250. package/source/SVGElement.ts +2 -2
  251. package/source/Text.ts +2 -2
  252. package/source/Window.ts +156 -17
  253. package/source/attribute-reactions.ts +32 -0
  254. package/source/constants.ts +40 -17
  255. package/source/custom-element-reactions.ts +64 -0
  256. package/source/dom-exception.ts +14 -0
  257. package/source/extensions.ts +4 -0
  258. package/source/hook-effects.ts +56 -0
  259. package/source/hooks.ts +11 -3
  260. package/source/index.ts +1 -0
  261. package/source/names.ts +94 -0
  262. package/source/selectors.ts +301 -138
  263. package/source/serialization.ts +224 -66
  264. package/source/shared.ts +269 -40
  265. package/source/tests/ChildNode.test.ts +178 -0
  266. package/source/tests/MutationObserver.test.ts +303 -0
  267. package/source/tests/adopt-inserted-subtrees.test.ts +584 -0
  268. package/source/tests/attr-mutation.test.ts +112 -0
  269. package/source/tests/child-node-before-after.test.ts +421 -0
  270. package/source/tests/child-node-replace-with.test.ts +251 -0
  271. package/source/tests/clone-import-namespaces.test.ts +365 -0
  272. package/source/tests/constants.test.ts +46 -0
  273. package/source/tests/create-element-namespaces.test.ts +142 -0
  274. package/source/tests/create-text-node.test.ts +38 -0
  275. package/source/tests/custom-element-reactions.test.ts +600 -0
  276. package/source/tests/custom-element-registry.test.ts +137 -0
  277. package/source/tests/custom-event.test.ts +26 -0
  278. package/source/tests/document-clone-import-contract.test.ts +77 -0
  279. package/source/tests/document.test.ts +122 -0
  280. package/source/tests/dom-mutation-selector-errors.test.ts +484 -0
  281. package/source/tests/event-dispatch.test.ts +270 -0
  282. package/source/tests/event-target.test.ts +208 -0
  283. package/source/tests/event.test.ts +98 -0
  284. package/source/tests/extensions.test.ts +159 -0
  285. package/source/tests/get-elements-by-tag-name.test.ts +79 -0
  286. package/source/tests/getElementsByClassName.test.ts +109 -0
  287. package/source/tests/hooks.test.ts +43 -0
  288. package/source/tests/inner-html-parsing.test.ts +461 -0
  289. package/source/tests/is-default-namespace.test.ts +111 -0
  290. package/source/tests/name-and-namespace-normalization.test.ts +319 -0
  291. package/source/tests/named-node-map.test.ts +122 -0
  292. package/source/tests/namespaced-attribute-reactions.test.ts +141 -0
  293. package/source/tests/node.test.ts +56 -0
  294. package/source/tests/parent-node-mutation-return-values.test.ts +63 -0
  295. package/source/tests/parent-node-mutation-validation.test.ts +362 -0
  296. package/source/tests/parent-node.test.ts +169 -0
  297. package/source/tests/selectors.test.ts +533 -22
  298. package/source/tests/serialization-template.test.ts +232 -0
  299. package/source/tests/slot-attribute.test.ts +133 -0
  300. package/source/tests/text-content.test.ts +440 -0
  301. package/source/tests/toggle-attribute.test.ts +113 -0
  302. package/source/tests/wide-tree-traversal.test.ts +699 -0
  303. package/source/tests/window-set-global.test.ts +321 -0
  304. package/tsconfig.json +1 -1
@@ -4,28 +4,54 @@ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
4
4
 
5
5
  const constants = require('./constants.cjs');
6
6
  const shared = require('./shared.cjs');
7
+ const NodeList = require('./NodeList.cjs');
8
+ const domException = require('./dom-exception.cjs');
7
9
 
8
- var Combinator = /*#__PURE__*/function (Combinator) {
9
- Combinator[Combinator["Descendant"] = 0] = "Descendant";
10
- Combinator[Combinator["Child"] = 1] = "Child";
11
- Combinator[Combinator["Sibling"] = 2] = "Sibling";
12
- Combinator[Combinator["Adjacent"] = 3] = "Adjacent";
13
- Combinator[Combinator["Inner"] = 4] = "Inner";
14
- return Combinator;
15
- }(Combinator || {});
16
- var MatcherType = /*#__PURE__*/function (MatcherType) {
17
- MatcherType[MatcherType["Unknown"] = 0] = "Unknown";
18
- MatcherType[MatcherType["Element"] = 1] = "Element";
19
- MatcherType[MatcherType["Id"] = 2] = "Id";
20
- MatcherType[MatcherType["Class"] = 3] = "Class";
21
- MatcherType[MatcherType["Attribute"] = 4] = "Attribute";
22
- MatcherType[MatcherType["Pseudo"] = 5] = "Pseudo";
23
- MatcherType[MatcherType["Function"] = 6] = "Function";
24
- return MatcherType;
25
- }(MatcherType || {});
26
- const ELEMENT_SELECTOR_TEST = /[a-z]/;
10
+ const COMBINATOR_DESCENDANT = 0;
11
+ const COMBINATOR_CHILD = 1;
12
+ const COMBINATOR_SIBLING = 2;
13
+ const COMBINATOR_ADJACENT = 3;
14
+ const COMBINATOR_INNER = 4;
15
+ const MATCHER_UNKNOWN = 0;
16
+ const MATCHER_ELEMENT = 1;
17
+ const MATCHER_ID = 2;
18
+ const MATCHER_CLASS = 3;
19
+ const MATCHER_ATTRIBUTE = 4;
20
+ const MATCHER_PSEUDO = 5;
21
+ const MATCHER_FUNCTION = 6;
22
+ const MATCHER_SCOPE = 7;
23
+ const SUPPORTED_IDENTIFIER_TEST = /^(?:--|-?[A-Za-z_\u0080-\u{10FFFF}])[A-Za-z0-9_\u0080-\u{10FFFF}-]*$/u;
24
+ function readFunctionArgument(selector, start) {
25
+ let depth = 1;
26
+ let quote = null;
27
+ for (let index = start; index < selector.length; index++) {
28
+ const character = selector[index];
29
+ if (quote) {
30
+ if (character === '\\') {
31
+ index++;
32
+ } else if (character === quote) {
33
+ quote = null;
34
+ }
35
+ continue;
36
+ }
37
+ if (character === '"' || character === "'") {
38
+ quote = character;
39
+ } else if (character === '(') {
40
+ depth++;
41
+ } else if (character === ')' && --depth === 0) {
42
+ return [selector.slice(start, index), index + 1];
43
+ }
44
+ }
45
+ return [selector.slice(start), selector.length];
46
+ }
47
+ function throwSelectorSyntaxError(selector) {
48
+ throw domException.createDOMException(`Invalid or unsupported selector: "${selector}"`, 'SyntaxError');
49
+ }
27
50
  function querySelector(within, selector) {
28
- const parts = parseSelector(selector);
51
+ const parts = typeof selector === 'string' ? parseSelector(selector) : [{
52
+ combinator: COMBINATOR_INNER,
53
+ matchers: selector
54
+ }];
29
55
  let result = null;
30
56
  const child = within[constants.CHILD];
31
57
  if (child && parts[0].matchers.length) {
@@ -37,8 +63,11 @@ function querySelector(within, selector) {
37
63
  return result;
38
64
  }
39
65
  function querySelectorAll(within, selector) {
40
- const parts = parseSelector(selector);
41
- const results = [];
66
+ const parts = typeof selector === 'string' ? parseSelector(selector) : [{
67
+ combinator: COMBINATOR_INNER,
68
+ matchers: selector
69
+ }];
70
+ const results = new NodeList.NodeList();
42
71
  const child = within[constants.CHILD];
43
72
  if (child && parts[0].matchers.length) {
44
73
  walkNodesForSelector(child, parts, node => {
@@ -47,98 +76,170 @@ function querySelectorAll(within, selector) {
47
76
  }
48
77
  return results;
49
78
  }
50
- function parseSelector(selector) {
79
+ function parseSelector(selector, insideHas = false, allowLeadingCombinator = false) {
51
80
  let part = {
52
- combinator: Combinator.Inner,
81
+ combinator: COMBINATOR_INNER,
53
82
  matchers: []
54
83
  };
55
84
  const parts = [part];
56
- const tokenizer = /\s*?([>\s+~]?)\s*?(?:(?:\[\s*([^\]=]+)(?:=(['"])(.*?)\3)?\s*\])|([#.]?)([^\s#.[>:+~]+)|:(\w+)(?:\((.*?)\))?)/gi;
85
+ const tokenizer = /[\t\n\f\r ]*?([>\t\n\f\r +~]?)[\t\n\f\r ]*?(?:(?:\[[\t\n\f\r ]*([^\]=\t\n\f\r ]+)[\t\n\f\r ]*(?:=[\t\n\f\r ]*(?:(['"])(.*?)\3|([^\]\t\n\f\r ]+)))?[\t\n\f\r ]*(?:\]|$))|([#.]?)([^\t\n\f\r #.[>:+~()]+)|:(\w+)(\()?)/gi;
86
+ const normalizedSelector = selector.replace(/^[\t\n\f\r ]+|[\t\n\f\r ]+$/g, '');
87
+ if (normalizedSelector === '') throwSelectorSyntaxError(selector);
88
+ let consumed = 0;
57
89
  let token;
58
- while (token = tokenizer.exec(selector)) {
59
- // [1]: ancestor/parent/sibling/adjacent
90
+ while (token = tokenizer.exec(normalizedSelector)) {
91
+ if (token.index !== consumed) throwSelectorSyntaxError(selector);
92
+
93
+ // [1]: ancestor/ parent/ sibling/ adjacent
60
94
  // [2]: attribute name
61
- // [4]: attribute value
62
- // [5]: id/class sigil
63
- // [6]: id/class name
64
- // [7]: :pseudo/:function() name
65
- // [8]: :function(argument) value
95
+ // [3]/[4]: quoted attribute value
96
+ // [5]: unquoted attribute value
97
+ // [6]: id/class sigil
98
+ // [7]: id/class/type name
99
+ // [8]: :pseudo/:function() name
100
+ // [9]: :function opening parenthesis
66
101
  if (token[1]) {
67
- // Update the combinator on the (now parent) Part:
68
- if (token[1] === '>') part.combinator = Combinator.Child;else if (token[1] === '+') part.combinator = Combinator.Adjacent;else if (token[1] === '~') part.combinator = Combinator.Sibling;else part.combinator = Combinator.Descendant;
69
- // Add a new Part for the next selector parts:
102
+ if (part.matchers.length === 0 && !(allowLeadingCombinator && parts.length === 1)) {
103
+ throwSelectorSyntaxError(selector);
104
+ }
105
+ if (token[1] === '>') part.combinator = COMBINATOR_CHILD;else if (token[1] === '+') part.combinator = COMBINATOR_ADJACENT;else if (token[1] === '~') part.combinator = COMBINATOR_SIBLING;else part.combinator = COMBINATOR_DESCENDANT;
70
106
  part = {
71
- combinator: Combinator.Inner,
107
+ combinator: COMBINATOR_INNER,
72
108
  matchers: []
73
109
  };
74
110
  parts.push(part);
75
111
  }
76
- let type = MatcherType.Unknown;
112
+ const name = token[8] ? constants.asciiLowercase(token[8]) : token[2] || token[7];
113
+ const isTypeSelector = token[7] != null && !token[6];
114
+ if (isTypeSelector && part.matchers.length > 0) {
115
+ throwSelectorSyntaxError(selector);
116
+ }
117
+ let type;
118
+ let value = token[4] ?? token[5] ?? token[7];
77
119
  if (token[2]) {
78
- type = MatcherType.Attribute;
79
- } else if (token[5]) {
80
- type = token[5] === '#' ? MatcherType.Id : MatcherType.Class;
81
- } else if (token[7]) {
82
- type = token[8] == null ? MatcherType.Pseudo : MatcherType.Function;
120
+ if (!SUPPORTED_IDENTIFIER_TEST.test(name)) {
121
+ throwSelectorSyntaxError(selector);
122
+ }
123
+ const unquotedValue = token[5];
124
+ const openingQuote = unquotedValue?.[0];
125
+ if (token[3] == null && (openingQuote === '"' || openingQuote === "'")) {
126
+ const valueOffset = token[0].lastIndexOf(unquotedValue);
127
+ value = normalizedSelector.slice(token.index + valueOffset + 1);
128
+ tokenizer.lastIndex = normalizedSelector.length;
129
+ } else if (unquotedValue != null && !SUPPORTED_IDENTIFIER_TEST.test(unquotedValue)) {
130
+ throwSelectorSyntaxError(selector);
131
+ }
132
+ type = MATCHER_ATTRIBUTE;
83
133
  } else if (token[6]) {
84
- if (token[6] === '*') {
85
- type = MatcherType.Unknown; // Universal selector matches all
86
- } else if (ELEMENT_SELECTOR_TEST.test(token[6])) {
87
- type = MatcherType.Element;
134
+ if (!SUPPORTED_IDENTIFIER_TEST.test(name)) {
135
+ throwSelectorSyntaxError(selector);
88
136
  }
137
+ type = token[6] === '#' ? MATCHER_ID : MATCHER_CLASS;
138
+ } else if (token[8]) {
139
+ type = token[9] == null ? MATCHER_PSEUDO : MATCHER_FUNCTION;
140
+ } else if (token[7] === '*') {
141
+ type = MATCHER_UNKNOWN;
142
+ } else if (token[7] && SUPPORTED_IDENTIFIER_TEST.test(token[7])) {
143
+ type = MATCHER_ELEMENT;
144
+ } else {
145
+ throwSelectorSyntaxError(selector);
146
+ }
147
+ if (token[9]) {
148
+ [value, tokenizer.lastIndex] = readFunctionArgument(normalizedSelector, tokenizer.lastIndex);
149
+ if (name !== 'has' && name !== 'not') {
150
+ throwSelectorSyntaxError(selector);
151
+ }
152
+ if (name === 'has' && insideHas) throwSelectorSyntaxError(selector);
153
+ parseSelector(value, insideHas || name === 'has', name === 'has');
154
+ } else if (type === MATCHER_PSEUDO) {
155
+ throwSelectorSyntaxError(selector);
89
156
  }
90
157
  part.matchers.push({
91
158
  type,
92
- name: token[2] || token[6] || token[7],
93
- value: token[4] ?? token[6] ?? token[8]
159
+ name,
160
+ value
94
161
  });
162
+ consumed = tokenizer.lastIndex;
163
+ }
164
+ if (consumed !== normalizedSelector.length || part.matchers.length === 0) {
165
+ throwSelectorSyntaxError(selector);
95
166
  }
96
167
  return parts;
97
168
  }
98
169
  function matchesSelector(element, selector) {
99
170
  const parsed = parseSelector(selector);
100
- let part;
101
- while (part = parsed.pop()) {
102
- if (!matchesSelectorPart(element, part)) return false;
103
- }
104
- return true;
171
+ return parsed[0]?.matchers.length ? matchesSelectorRecursive(element, parsed) : false;
105
172
  }
106
- function walkNodesForSelector(node, parts, callback) {
107
- if (shared.isElementNode(node)) {
108
- if (matchesSelectorRecursive(node, parts)) {
109
- if (callback(node) === false) return false;
110
- }
111
- const child = node[constants.CHILD];
112
- if (child && walkNodesForSelector(child, parts, callback) === false) {
113
- return false;
114
- }
173
+ function matchesRelativeSelector(scope, selector) {
174
+ const parts = parseSelector(selector, true, true);
175
+ const first = parts[0];
176
+ if (parts.length === 1 && first.matchers.length === 0) return false;
177
+ let leadingCombinator = COMBINATOR_DESCENDANT;
178
+ const scopeMatcher = {
179
+ type: MATCHER_SCOPE,
180
+ name: ':scope'
181
+ };
182
+ if (first.matchers.length === 0) {
183
+ leadingCombinator = first.combinator;
184
+ first.matchers.push(scopeMatcher);
185
+ } else {
186
+ parts.unshift({
187
+ combinator: COMBINATOR_DESCENDANT,
188
+ matchers: [scopeMatcher]
189
+ });
115
190
  }
116
- const next = node[constants.NEXT];
117
- if (next && walkNodesForSelector(next, parts, callback) === false) {
191
+ if (parts.some(({
192
+ matchers
193
+ }) => matchers.length === 0)) return false;
194
+ const root = leadingCombinator === COMBINATOR_ADJACENT || leadingCombinator === COMBINATOR_SIBLING ? scope[constants.NEXT] : scope[constants.CHILD];
195
+ if (!root) return false;
196
+ let matched = false;
197
+ walkNodesForSelector(root, parts, () => {
198
+ matched = true;
118
199
  return false;
200
+ }, scope);
201
+ return matched;
202
+ }
203
+ function walkNodesForSelector(node, parts, callback, scope) {
204
+ const pendingSiblings = [];
205
+ let current = node;
206
+ while (current) {
207
+ if (shared.isElementNode(current)) {
208
+ if (matchesSelectorRecursive(current, parts, scope)) {
209
+ if (callback(current) === false) return false;
210
+ }
211
+ const child = current[constants.CHILD];
212
+ if (child) {
213
+ const sibling = current[constants.NEXT];
214
+ if (sibling) pendingSiblings.push(sibling);
215
+ current = child;
216
+ continue;
217
+ }
218
+ }
219
+ current = current[constants.NEXT] ?? pendingSiblings.pop() ?? null;
119
220
  }
120
221
  return true;
121
222
  }
122
- function matchesSelectorRecursive(element, parts) {
223
+ function matchesSelectorRecursive(element, parts, scope) {
123
224
  const {
124
225
  combinator,
125
226
  matchers
126
227
  } = parts[parts.length - 1];
127
- if (combinator === Combinator.Inner) {
128
- if (!matchesSelectorMatcher(element, matchers)) return false;
228
+ if (combinator === COMBINATOR_INNER) {
229
+ if (!matchesSelectorMatcher(element, matchers, scope)) return false;
129
230
  const pp = parts.slice(0, -1);
130
- return pp.length === 0 || matchesSelectorRecursive(element, pp);
231
+ return pp.length === 0 || matchesSelectorRecursive(element, pp, scope);
131
232
  }
132
- const link = combinator === Combinator.Child || combinator === Combinator.Descendant ? constants.PARENT : constants.PREV;
233
+ const link = combinator === COMBINATOR_CHILD || combinator === COMBINATOR_DESCENDANT ? constants.PARENT : constants.PREV;
133
234
  let ref = element[link];
134
235
  if (!ref) return false;
135
- if (combinator === Combinator.Descendant || combinator === Combinator.Sibling) {
236
+ if (combinator === COMBINATOR_DESCENDANT || combinator === COMBINATOR_SIBLING) {
136
237
  // For descendant/sibling combinators, search through all ancestors/siblings
137
238
  while (ref) {
138
- if (shared.isElementNode(ref) && matchesSelectorMatcher(ref, matchers)) {
239
+ if (shared.isElementNode(ref) && matchesSelectorMatcher(ref, matchers, scope)) {
139
240
  const pp = parts.slice(0, -1);
140
241
  if (pp.length === 0) return true;
141
- if (matchesSelectorRecursive(element, pp)) return true;
242
+ if (matchesSelectorRecursive(ref, pp, scope)) return true;
142
243
  }
143
244
  ref = ref[link];
144
245
  }
@@ -146,53 +247,30 @@ function matchesSelectorRecursive(element, parts) {
146
247
  } else {
147
248
  // For child/adjacent combinators, check only the immediate parent/sibling
148
249
  // For sibling combinators, skip non-element siblings
149
- if (combinator === Combinator.Adjacent && !shared.isElementNode(ref)) {
250
+ if (combinator === COMBINATOR_ADJACENT && !shared.isElementNode(ref)) {
150
251
  // Skip to next element sibling
151
252
  while (ref && !shared.isElementNode(ref)) {
152
253
  ref = ref[link];
153
254
  }
154
255
  if (!ref) return false;
155
256
  }
156
- if (!shared.isElementNode(ref) || !matchesSelectorMatcher(ref, matchers)) {
257
+ if (!shared.isElementNode(ref) || !matchesSelectorMatcher(ref, matchers, scope)) {
157
258
  return false;
158
259
  }
159
260
  const pp = parts.slice(0, -1);
160
- return pp.length === 0 || matchesSelectorRecursive(element, pp);
261
+ return pp.length === 0 || matchesSelectorRecursive(ref, pp, scope);
161
262
  }
162
263
  }
163
- function matchesSelectorPart(element, {
164
- combinator,
165
- matchers
166
- }) {
167
- if (combinator === Combinator.Inner) {
168
- return matchesSelectorMatcher(element, matchers);
169
- }
170
- const link = combinator === Combinator.Child || combinator === Combinator.Descendant ? constants.PARENT : constants.PREV;
171
- let ref = element[link];
172
- if (!ref) return false;
173
-
174
- // For sibling combinators, skip non-element siblings
175
- if (combinator === Combinator.Adjacent && !shared.isElementNode(ref)) {
176
- while (ref && !shared.isElementNode(ref)) {
177
- ref = ref[link];
178
- }
179
- if (!ref) return false;
180
- }
181
- if (!shared.isElementNode(ref) || !matchesSelectorMatcher(ref, matchers)) {
182
- return false;
183
- }
184
- if (combinator === Combinator.Descendant || combinator === Combinator.Sibling) {
185
- while (ref = ref[link]) {
186
- if (shared.isElementNode(ref) && matchesSelectorMatcher(ref, matchers)) return true;
187
- }
188
- }
189
- return true;
264
+ function getSelectorAttribute(element, name) {
265
+ return element.getAttributeNS(null, element.namespaceURI === constants.HTML_NAMESPACE ? constants.asciiLowercase(name) : name);
190
266
  }
191
- function matchesSelectorMatcher(element, matcher) {
267
+ function matchesSelectorMatcher(element, matcher, scope) {
192
268
  if (!element) return false;
193
269
  if (Array.isArray(matcher)) {
194
270
  for (const single of matcher) {
195
- if (matchesSelectorMatcher(element, single) === false) return false;
271
+ if (matchesSelectorMatcher(element, single, scope) === false) {
272
+ return false;
273
+ }
196
274
  }
197
275
  return true;
198
276
  }
@@ -202,37 +280,50 @@ function matchesSelectorMatcher(element, matcher) {
202
280
  value
203
281
  } = matcher;
204
282
  switch (type) {
205
- case MatcherType.Unknown:
283
+ case MATCHER_UNKNOWN:
206
284
  return name === '*';
207
285
  // Universal selector
208
- case MatcherType.Element:
209
- return element.localName === name;
210
- case MatcherType.Id:
211
- return element.getAttribute('id') === name;
212
- case MatcherType.Class:
213
- const classAttr = element.getAttribute('class');
286
+ case MATCHER_ELEMENT:
287
+ return element.namespaceURI === constants.HTML_NAMESPACE ? element.localName === constants.asciiLowercase(name) : element.localName === name;
288
+ case MATCHER_ID:
289
+ return getSelectorAttribute(element, 'id') === name;
290
+ case MATCHER_CLASS:
291
+ const classAttr = getSelectorAttribute(element, 'class');
214
292
  if (!classAttr) return false;
215
- return classAttr.split(/\s+/).includes(name);
216
- case MatcherType.Attribute:
217
- return value == null ? element.hasAttribute(name) : element.getAttribute(name) === value;
218
- case MatcherType.Pseudo:
219
- switch (name) {
220
- default:
221
- throw Error(`Pseudo :${name} not implemented`);
222
- }
223
- case MatcherType.Function:
293
+ return constants.splitOnASCIIWhitespace(classAttr).includes(name);
294
+ case MATCHER_ATTRIBUTE:
295
+ const attribute = getSelectorAttribute(element, name);
296
+ return value == null ? attribute != null : attribute === value;
297
+ case MATCHER_SCOPE:
298
+ return element === scope;
299
+ case MATCHER_PSEUDO:
300
+ throwSelectorSyntaxError(`:${name}`);
301
+ case MATCHER_FUNCTION:
224
302
  switch (name) {
225
303
  case 'has':
226
- return matchesSelector(element, value || '');
304
+ return matchesRelativeSelector(element, value || '');
227
305
  case 'not':
228
306
  return !matchesSelector(element, value || '');
229
307
  default:
230
- throw Error(`Function :${name}(${value}) not implemented`);
308
+ throwSelectorSyntaxError(`:${name}(${value})`);
231
309
  }
232
310
  }
233
311
  return false;
234
312
  }
235
313
 
314
+ exports.COMBINATOR_ADJACENT = COMBINATOR_ADJACENT;
315
+ exports.COMBINATOR_CHILD = COMBINATOR_CHILD;
316
+ exports.COMBINATOR_DESCENDANT = COMBINATOR_DESCENDANT;
317
+ exports.COMBINATOR_INNER = COMBINATOR_INNER;
318
+ exports.COMBINATOR_SIBLING = COMBINATOR_SIBLING;
319
+ exports.MATCHER_ATTRIBUTE = MATCHER_ATTRIBUTE;
320
+ exports.MATCHER_CLASS = MATCHER_CLASS;
321
+ exports.MATCHER_ELEMENT = MATCHER_ELEMENT;
322
+ exports.MATCHER_FUNCTION = MATCHER_FUNCTION;
323
+ exports.MATCHER_ID = MATCHER_ID;
324
+ exports.MATCHER_PSEUDO = MATCHER_PSEUDO;
325
+ exports.MATCHER_SCOPE = MATCHER_SCOPE;
326
+ exports.MATCHER_UNKNOWN = MATCHER_UNKNOWN;
236
327
  exports.parseSelector = parseSelector;
237
328
  exports.querySelector = querySelector;
238
329
  exports.querySelectorAll = querySelectorAll;