@microsoft/fast-element 2.10.3 → 3.0.0-rc.1

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 (351) hide show
  1. package/ARCHITECTURE_HTML_TAGGED_TEMPLATE_LITERAL.md +1 -1
  2. package/ARCHITECTURE_OVERVIEW.md +2 -2
  3. package/CHANGELOG.json +31 -1
  4. package/CHANGELOG.md +10 -2
  5. package/DECLARATIVE_DESIGN.md +806 -0
  6. package/DECLARATIVE_HTML.md +470 -0
  7. package/DECLARATIVE_MIGRATION.md +215 -0
  8. package/DECLARATIVE_RENDERING.md +530 -0
  9. package/DECLARATIVE_RENDERING_LIFECYCLE.md +288 -0
  10. package/DECLARATIVE_SCHEMA_OBSERVER_MAP.md +489 -0
  11. package/DESIGN.md +143 -34
  12. package/MIGRATION.md +387 -0
  13. package/README.md +208 -1
  14. package/SIZES.md +25 -0
  15. package/api-extractor.arrays.json +15 -0
  16. package/api-extractor.context.json +1 -0
  17. package/api-extractor.declarative.json +15 -0
  18. package/api-extractor.di.json +1 -0
  19. package/api-extractor.hydration.json +15 -0
  20. package/api-extractor.styles.json +15 -0
  21. package/dist/arrays/arrays.api.json +2621 -0
  22. package/dist/context/context.api.json +1 -1
  23. package/dist/declarative/declarative.api.json +7844 -0
  24. package/dist/di/di.api.json +2 -2
  25. package/dist/dts/array-observer.d.ts +2 -0
  26. package/dist/dts/arrays.d.ts +2 -0
  27. package/dist/dts/attr.d.ts +1 -0
  28. package/dist/dts/binding/signal.d.ts +6 -6
  29. package/dist/dts/binding/two-way.d.ts +1 -0
  30. package/dist/dts/binding.d.ts +7 -0
  31. package/dist/dts/components/attributes.d.ts +2 -5
  32. package/dist/dts/components/definition-schema-transforms.d.ts +9 -0
  33. package/dist/dts/components/element-controller.d.ts +80 -114
  34. package/dist/dts/components/element-hydration.d.ts +1 -1
  35. package/dist/dts/components/enable-hydration.d.ts +34 -0
  36. package/dist/dts/components/fast-definitions.d.ts +91 -42
  37. package/dist/dts/components/fast-element.d.ts +5 -8
  38. package/dist/dts/components/hydration-tracker.d.ts +40 -0
  39. package/dist/dts/components/hydration.d.ts +18 -53
  40. package/dist/dts/components/schema.d.ts +205 -0
  41. package/dist/dts/context.d.ts +6 -6
  42. package/dist/dts/css.d.ts +3 -0
  43. package/dist/dts/debug.d.ts +5 -1
  44. package/dist/dts/declarative/attribute-map.d.ts +58 -0
  45. package/dist/dts/declarative/debug.d.ts +5 -0
  46. package/dist/dts/declarative/index.d.ts +13 -0
  47. package/dist/dts/declarative/interfaces.d.ts +9 -0
  48. package/dist/dts/declarative/observer-map-utilities.d.ts +58 -0
  49. package/dist/dts/declarative/observer-map.d.ts +89 -0
  50. package/dist/dts/declarative/runtime.d.ts +5 -0
  51. package/dist/dts/declarative/syntax.d.ts +21 -0
  52. package/dist/dts/declarative/template-bridge.d.ts +33 -0
  53. package/dist/dts/declarative/template-parser.d.ts +98 -0
  54. package/dist/dts/declarative/template.d.ts +9 -0
  55. package/dist/dts/declarative/utilities.d.ts +312 -0
  56. package/dist/dts/di/di.d.ts +1 -1
  57. package/dist/dts/directives/children.d.ts +2 -0
  58. package/dist/dts/directives/node-observation.d.ts +2 -0
  59. package/dist/dts/directives/ref.d.ts +2 -0
  60. package/dist/dts/directives/repeat.d.ts +4 -0
  61. package/dist/dts/directives/slotted.d.ts +2 -0
  62. package/dist/dts/directives/when.d.ts +3 -0
  63. package/dist/dts/dom-policy.d.ts +1 -1
  64. package/dist/dts/html.d.ts +5 -0
  65. package/dist/dts/hydration/runtime.d.ts +7 -0
  66. package/dist/dts/hydration/target-builder.d.ts +15 -12
  67. package/dist/dts/hydration.d.ts +14 -0
  68. package/dist/dts/index.d.ts +38 -42
  69. package/dist/dts/index.debug.d.ts +0 -1
  70. package/dist/dts/index.rollup.debug.d.ts +0 -1
  71. package/dist/dts/interfaces.d.ts +1 -49
  72. package/dist/dts/observable.d.ts +3 -6
  73. package/dist/dts/observation/arrays.d.ts +1 -1
  74. package/dist/dts/observation/update-queue.d.ts +1 -1
  75. package/dist/dts/platform.d.ts +25 -4
  76. package/dist/dts/render.d.ts +7 -0
  77. package/dist/dts/schema.d.ts +1 -0
  78. package/dist/dts/state/exports.d.ts +1 -1
  79. package/dist/dts/state/state.d.ts +2 -2
  80. package/dist/dts/styles/css-directive.d.ts +5 -12
  81. package/dist/dts/styles/css.d.ts +5 -7
  82. package/dist/dts/styles/element-styles.d.ts +0 -10
  83. package/dist/dts/styles.d.ts +6 -0
  84. package/dist/dts/templating/children.d.ts +1 -1
  85. package/dist/dts/templating/html-binding-directive.d.ts +10 -0
  86. package/dist/dts/templating/html-directive.d.ts +17 -0
  87. package/dist/dts/templating/hydration-view.d.ts +109 -0
  88. package/dist/dts/templating/ref.d.ts +1 -1
  89. package/dist/dts/templating/render.d.ts +8 -2
  90. package/dist/dts/templating/repeat.d.ts +2 -2
  91. package/dist/dts/templating/slotted.d.ts +1 -1
  92. package/dist/dts/templating/template.d.ts +17 -9
  93. package/dist/dts/templating/view.d.ts +25 -102
  94. package/dist/dts/templating/when.d.ts +1 -1
  95. package/dist/dts/templating.d.ts +10 -0
  96. package/dist/dts/testing/exports.d.ts +2 -2
  97. package/dist/dts/tsdoc-metadata.json +1 -1
  98. package/dist/dts/updates.d.ts +1 -0
  99. package/dist/dts/volatile.d.ts +2 -0
  100. package/dist/esm/array-observer.js +1 -0
  101. package/dist/esm/arrays.js +1 -0
  102. package/dist/esm/attr.js +1 -0
  103. package/dist/esm/binding/normalize.js +1 -1
  104. package/dist/esm/binding/signal.js +4 -4
  105. package/dist/esm/binding/two-way.js +2 -1
  106. package/dist/esm/binding.js +4 -0
  107. package/dist/esm/components/attributes.js +8 -5
  108. package/dist/esm/components/definition-schema-transforms.js +23 -0
  109. package/dist/esm/components/element-controller.js +200 -269
  110. package/dist/esm/components/element-hydration.js +1 -1
  111. package/dist/esm/components/enable-hydration.js +100 -0
  112. package/dist/esm/components/fast-definitions.js +211 -49
  113. package/dist/esm/components/fast-element.js +18 -27
  114. package/dist/esm/components/hydration-tracker.js +93 -0
  115. package/dist/esm/components/hydration.js +62 -144
  116. package/dist/esm/components/schema.js +253 -0
  117. package/dist/esm/context.js +6 -6
  118. package/dist/esm/css.js +3 -0
  119. package/dist/esm/debug.js +26 -26
  120. package/dist/esm/declarative/attribute-map.js +121 -0
  121. package/dist/esm/declarative/debug.js +5 -0
  122. package/dist/esm/declarative/index.js +3 -0
  123. package/dist/esm/declarative/interfaces.js +10 -0
  124. package/dist/esm/declarative/observer-map-utilities.js +562 -0
  125. package/dist/esm/declarative/observer-map.js +216 -0
  126. package/dist/esm/declarative/runtime.js +14 -0
  127. package/dist/esm/declarative/syntax.js +36 -0
  128. package/dist/esm/declarative/template-bridge.js +170 -0
  129. package/dist/esm/declarative/template-parser.js +306 -0
  130. package/dist/esm/declarative/template.js +142 -0
  131. package/dist/esm/declarative/utilities.js +834 -0
  132. package/dist/esm/di/di.js +6 -8
  133. package/dist/esm/directives/children.js +1 -0
  134. package/dist/esm/directives/node-observation.js +1 -0
  135. package/dist/esm/directives/ref.js +1 -0
  136. package/dist/esm/directives/repeat.js +1 -0
  137. package/dist/esm/directives/slotted.js +1 -0
  138. package/dist/esm/directives/when.js +1 -0
  139. package/dist/esm/dom-policy.js +2 -2
  140. package/dist/esm/dom.js +1 -1
  141. package/dist/esm/html.js +2 -0
  142. package/dist/esm/hydration/runtime.js +33 -0
  143. package/dist/esm/hydration/target-builder.js +97 -90
  144. package/dist/esm/hydration.js +4 -0
  145. package/dist/esm/index.debug.js +2 -1
  146. package/dist/esm/index.js +34 -29
  147. package/dist/esm/index.rollup.debug.js +3 -2
  148. package/dist/esm/index.rollup.js +1 -1
  149. package/dist/esm/interfaces.js +1 -45
  150. package/dist/esm/observable.js +1 -4
  151. package/dist/esm/observation/arrays.js +1 -1
  152. package/dist/esm/observation/observable.js +5 -5
  153. package/dist/esm/observation/update-queue.js +47 -58
  154. package/dist/esm/platform.js +31 -30
  155. package/dist/esm/render.js +1 -0
  156. package/dist/esm/schema.js +1 -0
  157. package/dist/esm/state/exports.js +1 -1
  158. package/dist/esm/styles/css-directive.js +1 -2
  159. package/dist/esm/styles/css.js +15 -56
  160. package/dist/esm/styles/element-styles.js +69 -15
  161. package/dist/esm/styles.js +2 -0
  162. package/dist/esm/templating/html-binding-directive.js +24 -10
  163. package/dist/esm/templating/hydration-view.js +235 -0
  164. package/dist/esm/templating/render.js +13 -2
  165. package/dist/esm/templating/repeat.js +36 -34
  166. package/dist/esm/templating/template.js +7 -7
  167. package/dist/esm/templating/view.js +24 -233
  168. package/dist/esm/templating.js +7 -0
  169. package/dist/esm/testing/exports.js +2 -2
  170. package/dist/esm/updates.js +1 -0
  171. package/dist/esm/volatile.js +1 -0
  172. package/dist/fast-element.api.json +9017 -6996
  173. package/dist/fast-element.d.ts +3557 -796
  174. package/dist/fast-element.debug.js +5093 -4419
  175. package/dist/fast-element.debug.min.js +2 -2
  176. package/dist/fast-element.js +5398 -4655
  177. package/dist/fast-element.min.js +2 -2
  178. package/dist/fast-element.untrimmed.d.ts +881 -481
  179. package/dist/hydration/hydration.api.json +5237 -0
  180. package/dist/styles/styles.api.json +2672 -0
  181. package/docs/api-report.api.md +344 -167
  182. package/docs/arrays/api-report.api.md +114 -0
  183. package/docs/declarative/api-report.api.md +397 -0
  184. package/docs/hydration/api-report.api.md +285 -0
  185. package/docs/styles/api-report.api.md +135 -0
  186. package/package.json +149 -40
  187. package/playwright.declarative.config.ts +26 -0
  188. package/playwright.declarative.webui.config.ts +20 -0
  189. package/scripts/declarative/build-fixtures-with-webui.js +135 -0
  190. package/scripts/declarative/build-fixtures.js +49 -0
  191. package/scripts/declarative/build-fixtures.utilities.js +101 -0
  192. package/scripts/measure-sizes.js +219 -0
  193. package/scripts/run-api-extractor.js +39 -20
  194. package/test/declarative/fixtures/README.md +72 -0
  195. package/test/declarative/fixtures/WRITING_FIXTURES.md +330 -0
  196. package/test/declarative/fixtures/bindings/README.md +12 -0
  197. package/test/declarative/fixtures/bindings/attribute/entry.html +13 -0
  198. package/test/declarative/fixtures/bindings/attribute/fast-build.config.json +6 -0
  199. package/test/declarative/fixtures/bindings/attribute/index.html +25 -0
  200. package/test/declarative/fixtures/bindings/attribute/main.ts +41 -0
  201. package/test/declarative/fixtures/bindings/attribute/state.json +8 -0
  202. package/test/declarative/fixtures/bindings/attribute/templates.html +11 -0
  203. package/test/declarative/fixtures/bindings/content/entry.html +12 -0
  204. package/test/declarative/fixtures/bindings/content/fast-build.config.json +6 -0
  205. package/test/declarative/fixtures/bindings/content/index.html +19 -0
  206. package/test/declarative/fixtures/bindings/content/main.ts +27 -0
  207. package/test/declarative/fixtures/bindings/content/state.json +4 -0
  208. package/test/declarative/fixtures/bindings/content/templates.html +6 -0
  209. package/test/declarative/fixtures/bindings/dot-syntax/entry.html +11 -0
  210. package/test/declarative/fixtures/bindings/dot-syntax/fast-build.config.json +6 -0
  211. package/test/declarative/fixtures/bindings/dot-syntax/index.html +47 -0
  212. package/test/declarative/fixtures/bindings/dot-syntax/main.ts +59 -0
  213. package/test/declarative/fixtures/bindings/dot-syntax/state.json +16 -0
  214. package/test/declarative/fixtures/bindings/dot-syntax/templates.html +17 -0
  215. package/test/declarative/fixtures/bindings/event/entry.html +11 -0
  216. package/test/declarative/fixtures/bindings/event/fast-build.config.json +6 -0
  217. package/test/declarative/fixtures/bindings/event/index.html +43 -0
  218. package/test/declarative/fixtures/bindings/event/main.ts +43 -0
  219. package/test/declarative/fixtures/bindings/event/state.json +3 -0
  220. package/test/declarative/fixtures/bindings/event/templates.html +18 -0
  221. package/test/declarative/fixtures/bindings/host/entry.html +40 -0
  222. package/test/declarative/fixtures/bindings/host/fast-build.config.json +6 -0
  223. package/test/declarative/fixtures/bindings/host/index.html +96 -0
  224. package/test/declarative/fixtures/bindings/host/main.ts +222 -0
  225. package/test/declarative/fixtures/bindings/host/state.json +9 -0
  226. package/test/declarative/fixtures/bindings/host/templates.html +55 -0
  227. package/test/declarative/fixtures/directives/README.md +12 -0
  228. package/test/declarative/fixtures/directives/children/entry.html +11 -0
  229. package/test/declarative/fixtures/directives/children/fast-build.config.json +6 -0
  230. package/test/declarative/fixtures/directives/children/index.html +15 -0
  231. package/test/declarative/fixtures/directives/children/main.ts +22 -0
  232. package/test/declarative/fixtures/directives/children/state.json +3 -0
  233. package/test/declarative/fixtures/directives/children/templates.html +3 -0
  234. package/test/declarative/fixtures/directives/ref/entry.html +11 -0
  235. package/test/declarative/fixtures/directives/ref/fast-build.config.json +6 -0
  236. package/test/declarative/fixtures/directives/ref/index.html +15 -0
  237. package/test/declarative/fixtures/directives/ref/main.ts +17 -0
  238. package/test/declarative/fixtures/directives/ref/state.json +1 -0
  239. package/test/declarative/fixtures/directives/ref/templates.html +3 -0
  240. package/test/declarative/fixtures/directives/repeat/entry.html +21 -0
  241. package/test/declarative/fixtures/directives/repeat/fast-build.config.json +6 -0
  242. package/test/declarative/fixtures/directives/repeat/index.html +133 -0
  243. package/test/declarative/fixtures/directives/repeat/main.ts +110 -0
  244. package/test/declarative/fixtures/directives/repeat/sprites.svg +8 -0
  245. package/test/declarative/fixtures/directives/repeat/state.json +10 -0
  246. package/test/declarative/fixtures/directives/repeat/templates.html +75 -0
  247. package/test/declarative/fixtures/directives/slotted/entry.html +17 -0
  248. package/test/declarative/fixtures/directives/slotted/fast-build.config.json +6 -0
  249. package/test/declarative/fixtures/directives/slotted/index.html +27 -0
  250. package/test/declarative/fixtures/directives/slotted/main.ts +29 -0
  251. package/test/declarative/fixtures/directives/slotted/state.json +1 -0
  252. package/test/declarative/fixtures/directives/slotted/templates.html +7 -0
  253. package/test/declarative/fixtures/directives/when/entry.html +51 -0
  254. package/test/declarative/fixtures/directives/when/fast-build.config.json +6 -0
  255. package/test/declarative/fixtures/directives/when/index.html +136 -0
  256. package/test/declarative/fixtures/directives/when/main.ts +172 -0
  257. package/test/declarative/fixtures/directives/when/state.json +12 -0
  258. package/test/declarative/fixtures/directives/when/templates.html +75 -0
  259. package/test/declarative/fixtures/ecosystem/README.md +11 -0
  260. package/test/declarative/fixtures/ecosystem/declarative-no-hydration/entry.html +12 -0
  261. package/test/declarative/fixtures/ecosystem/declarative-no-hydration/fast-build.config.json +6 -0
  262. package/test/declarative/fixtures/ecosystem/declarative-no-hydration/index.html +20 -0
  263. package/test/declarative/fixtures/ecosystem/declarative-no-hydration/main.ts +68 -0
  264. package/test/declarative/fixtures/ecosystem/declarative-no-hydration/state.json +4 -0
  265. package/test/declarative/fixtures/ecosystem/declarative-no-hydration/templates.html +7 -0
  266. package/test/declarative/fixtures/ecosystem/errors/entry.html +12 -0
  267. package/test/declarative/fixtures/ecosystem/errors/fast-build.config.json +6 -0
  268. package/test/declarative/fixtures/ecosystem/errors/index.html +20 -0
  269. package/test/declarative/fixtures/ecosystem/errors/main.ts +17 -0
  270. package/test/declarative/fixtures/ecosystem/errors/state.json +1 -0
  271. package/test/declarative/fixtures/ecosystem/errors/templates.html +7 -0
  272. package/test/declarative/fixtures/ecosystem/lifecycle-callbacks/entry.html +17 -0
  273. package/test/declarative/fixtures/ecosystem/lifecycle-callbacks/fast-build.config.json +6 -0
  274. package/test/declarative/fixtures/ecosystem/lifecycle-callbacks/index.html +56 -0
  275. package/test/declarative/fixtures/ecosystem/lifecycle-callbacks/main.ts +134 -0
  276. package/test/declarative/fixtures/ecosystem/lifecycle-callbacks/state.json +12 -0
  277. package/test/declarative/fixtures/ecosystem/lifecycle-callbacks/templates.html +34 -0
  278. package/test/declarative/fixtures/ecosystem/performance-metrics/entry.html +25 -0
  279. package/test/declarative/fixtures/ecosystem/performance-metrics/fast-build.config.json +6 -0
  280. package/test/declarative/fixtures/ecosystem/performance-metrics/fast-card.css +10 -0
  281. package/test/declarative/fixtures/ecosystem/performance-metrics/index.html +181 -0
  282. package/test/declarative/fixtures/ecosystem/performance-metrics/main.ts +58 -0
  283. package/test/declarative/fixtures/ecosystem/performance-metrics/state.json +6 -0
  284. package/test/declarative/fixtures/ecosystem/performance-metrics/templates.html +15 -0
  285. package/test/declarative/fixtures/extensions/README.md +15 -0
  286. package/test/declarative/fixtures/extensions/attribute-map/entry.html +14 -0
  287. package/test/declarative/fixtures/extensions/attribute-map/fast-build.config.json +6 -0
  288. package/test/declarative/fixtures/extensions/attribute-map/index.html +31 -0
  289. package/test/declarative/fixtures/extensions/attribute-map/main.ts +40 -0
  290. package/test/declarative/fixtures/extensions/attribute-map/state.json +4 -0
  291. package/test/declarative/fixtures/extensions/attribute-map/templates.html +14 -0
  292. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy/entry.html +12 -0
  293. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy/fast-build.config.json +7 -0
  294. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy/index.html +25 -0
  295. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy/main.ts +31 -0
  296. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy/state.json +5 -0
  297. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy/templates.html +11 -0
  298. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy-camel-case/entry.html +13 -0
  299. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy-camel-case/fast-build.config.json +7 -0
  300. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy-camel-case/index.html +23 -0
  301. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy-camel-case/main.ts +37 -0
  302. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy-camel-case/state.json +1 -0
  303. package/test/declarative/fixtures/extensions/attribute-map-naming-strategy-camel-case/templates.html +9 -0
  304. package/test/declarative/fixtures/extensions/observer-map/entry.html +15 -0
  305. package/test/declarative/fixtures/extensions/observer-map/fast-build.config.json +6 -0
  306. package/test/declarative/fixtures/extensions/observer-map/index.html +442 -0
  307. package/test/declarative/fixtures/extensions/observer-map/main.ts +482 -0
  308. package/test/declarative/fixtures/extensions/observer-map/state.json +158 -0
  309. package/test/declarative/fixtures/extensions/observer-map/templates.html +172 -0
  310. package/test/declarative/fixtures/extensions/observer-map-config-object/entry.html +16 -0
  311. package/test/declarative/fixtures/extensions/observer-map-config-object/fast-build.config.json +6 -0
  312. package/test/declarative/fixtures/extensions/observer-map-config-object/index.html +27 -0
  313. package/test/declarative/fixtures/extensions/observer-map-config-object/main.ts +53 -0
  314. package/test/declarative/fixtures/extensions/observer-map-config-object/state.json +9 -0
  315. package/test/declarative/fixtures/extensions/observer-map-config-object/templates.html +12 -0
  316. package/test/declarative/fixtures/extensions/observer-map-deep-merge/README.md +98 -0
  317. package/test/declarative/fixtures/extensions/observer-map-deep-merge/entry.html +156 -0
  318. package/test/declarative/fixtures/extensions/observer-map-deep-merge/fast-build.config.json +6 -0
  319. package/test/declarative/fixtures/extensions/observer-map-deep-merge/index.html +376 -0
  320. package/test/declarative/fixtures/extensions/observer-map-deep-merge/main.ts +366 -0
  321. package/test/declarative/fixtures/extensions/observer-map-deep-merge/state.json +69 -0
  322. package/test/declarative/fixtures/extensions/observer-map-deep-merge/templates.html +91 -0
  323. package/test/declarative/fixtures/extensions/observer-map-properties/entry.html +14 -0
  324. package/test/declarative/fixtures/extensions/observer-map-properties/fast-build.config.json +6 -0
  325. package/test/declarative/fixtures/extensions/observer-map-properties/index.html +110 -0
  326. package/test/declarative/fixtures/extensions/observer-map-properties/main.ts +175 -0
  327. package/test/declarative/fixtures/extensions/observer-map-properties/state.json +29 -0
  328. package/test/declarative/fixtures/extensions/observer-map-properties/templates.html +55 -0
  329. package/test/declarative/fixtures/scenarios/README.md +7 -0
  330. package/test/declarative/fixtures/scenarios/nested-elements/entry.html +16 -0
  331. package/test/declarative/fixtures/scenarios/nested-elements/fast-build.config.json +6 -0
  332. package/test/declarative/fixtures/scenarios/nested-elements/index.html +126 -0
  333. package/test/declarative/fixtures/scenarios/nested-elements/main.ts +214 -0
  334. package/test/declarative/fixtures/scenarios/nested-elements/state.json +10 -0
  335. package/test/declarative/fixtures/scenarios/nested-elements/templates.html +54 -0
  336. package/test/declarative/index.html +12 -0
  337. package/test/declarative/vite.config.ts +55 -0
  338. package/test/declarative-main.ts +6 -0
  339. package/test/extension-subpaths-main.ts +9 -0
  340. package/test/main.ts +38 -33
  341. package/test/pure-declarative-main.ts +1 -0
  342. package/dist/dts/components/install-hydration.d.ts +0 -1
  343. package/dist/dts/pending-task.d.ts +0 -32
  344. package/dist/dts/polyfills.d.ts +0 -0
  345. package/dist/dts/styles/css-binding-directive.d.ts +0 -60
  346. package/dist/dts/templating/install-hydratable-view-templates.d.ts +0 -1
  347. package/dist/esm/components/install-hydration.js +0 -3
  348. package/dist/esm/pending-task.js +0 -28
  349. package/dist/esm/polyfills.js +0 -60
  350. package/dist/esm/styles/css-binding-directive.js +0 -76
  351. package/dist/esm/templating/install-hydratable-view-templates.js +0 -23
@@ -0,0 +1,366 @@
1
+ import { declarativeTemplate } from "@microsoft/fast-element/declarative.js";
2
+ import { deepMerge } from "@microsoft/fast-element/declarative-utilities.js";
3
+ import { FASTElement } from "@microsoft/fast-element/fast-element.js";
4
+ import { enableHydration } from "@microsoft/fast-element/hydration.js";
5
+ import { observable } from "@microsoft/fast-element/observable.js";
6
+ import { observerMap } from "@microsoft/fast-element/observer-map.js";
7
+
8
+ interface Product {
9
+ id: number;
10
+ name: string;
11
+ price: number;
12
+ inStock: boolean;
13
+ tags: string[];
14
+ metadata: {
15
+ views: number;
16
+ rating: number;
17
+ };
18
+ }
19
+
20
+ interface User {
21
+ id: number;
22
+ name: string;
23
+ email: string;
24
+ profile: {
25
+ age: number;
26
+ location: {
27
+ city: string;
28
+ country: string;
29
+ };
30
+ preferences: {
31
+ theme: "light" | "dark";
32
+ notifications: boolean;
33
+ };
34
+ };
35
+ orders: Array<{
36
+ id: number;
37
+ date: string;
38
+ total: number;
39
+ items: Product[];
40
+ }>;
41
+ }
42
+
43
+ class DeepMergeTestElement extends FASTElement {
44
+ users: User[] = [
45
+ {
46
+ id: 1,
47
+ name: "Alice Johnson",
48
+ email: "alice@example.com",
49
+ profile: {
50
+ age: 28,
51
+ location: {
52
+ city: "New York",
53
+ country: "USA",
54
+ },
55
+ preferences: {
56
+ theme: "dark",
57
+ notifications: true,
58
+ },
59
+ },
60
+ orders: [
61
+ {
62
+ id: 101,
63
+ date: "2024-01-15",
64
+ total: 150.5,
65
+ items: [
66
+ {
67
+ id: 1001,
68
+ name: "Laptop",
69
+ price: 100.0,
70
+ inStock: true,
71
+ tags: ["electronics", "computers"],
72
+ metadata: {
73
+ views: 250,
74
+ rating: 4.5,
75
+ },
76
+ },
77
+ {
78
+ id: 1002,
79
+ name: "Mouse",
80
+ price: 50.5,
81
+ inStock: true,
82
+ tags: ["electronics", "accessories"],
83
+ metadata: {
84
+ views: 180,
85
+ rating: 4.0,
86
+ },
87
+ },
88
+ ],
89
+ },
90
+ {
91
+ id: 102,
92
+ date: "2024-02-20",
93
+ total: 75.0,
94
+ items: [
95
+ {
96
+ id: 1003,
97
+ name: "Keyboard",
98
+ price: 75.0,
99
+ inStock: true,
100
+ tags: ["electronics", "accessories"],
101
+ metadata: {
102
+ views: 120,
103
+ rating: 4.8,
104
+ },
105
+ },
106
+ ],
107
+ },
108
+ ],
109
+ },
110
+ {
111
+ id: 2,
112
+ name: "Bob Smith",
113
+ email: "bob@example.com",
114
+ profile: {
115
+ age: 35,
116
+ location: {
117
+ city: "London",
118
+ country: "UK",
119
+ },
120
+ preferences: {
121
+ theme: "light",
122
+ notifications: false,
123
+ },
124
+ },
125
+ orders: [
126
+ {
127
+ id: 201,
128
+ date: "2024-03-10",
129
+ total: 200.0,
130
+ items: [
131
+ {
132
+ id: 2001,
133
+ name: "Headphones",
134
+ price: 200.0,
135
+ inStock: false,
136
+ tags: ["electronics", "audio"],
137
+ metadata: {
138
+ views: 350,
139
+ rating: 4.7,
140
+ },
141
+ },
142
+ ],
143
+ },
144
+ ],
145
+ },
146
+ ];
147
+
148
+ @observable
149
+ showDetails: boolean = true;
150
+
151
+ @observable
152
+ stats: {
153
+ totalOrders: number;
154
+ totalRevenue: number;
155
+ activeUsers: number;
156
+ } = {
157
+ totalOrders: 3,
158
+ totalRevenue: 425.5,
159
+ activeUsers: 2,
160
+ };
161
+
162
+ // Test: Deep merge with nested object changes
163
+ public updateUserProfile() {
164
+ const updates = {
165
+ profile: {
166
+ age: 29,
167
+ location: {
168
+ city: "San Francisco", // Changed
169
+ // country stays "USA"
170
+ },
171
+ preferences: {
172
+ theme: "light" as const, // Changed
173
+ // notifications stays true
174
+ },
175
+ },
176
+ };
177
+
178
+ deepMerge(this.users[0], updates);
179
+ }
180
+
181
+ // Test: Array replacement via deep merge
182
+ public updateUserOrders() {
183
+ const updates = {
184
+ orders: [
185
+ {
186
+ id: 103,
187
+ date: "2024-04-01",
188
+ total: 99.99,
189
+ items: [
190
+ {
191
+ id: 1004,
192
+ name: "Monitor",
193
+ price: 99.99,
194
+ inStock: true,
195
+ tags: ["electronics", "displays"],
196
+ metadata: {
197
+ views: 400,
198
+ rating: 4.9,
199
+ },
200
+ },
201
+ ],
202
+ },
203
+ ],
204
+ };
205
+
206
+ deepMerge(this.users[0], updates);
207
+ }
208
+
209
+ // Test: Array item removal (shorter array)
210
+ public removeOrderItems() {
211
+ const updates = {
212
+ orders: [
213
+ {
214
+ id: 101,
215
+ date: "2024-01-15",
216
+ total: 100.0,
217
+ items: [
218
+ // Only one item now, second item removed
219
+ {
220
+ id: 1001,
221
+ name: "Laptop",
222
+ price: 100.0,
223
+ inStock: true,
224
+ tags: ["electronics", "computers"],
225
+ metadata: {
226
+ views: 250,
227
+ rating: 4.5,
228
+ },
229
+ },
230
+ ],
231
+ },
232
+ ],
233
+ };
234
+
235
+ deepMerge(this.users[0], updates);
236
+ }
237
+
238
+ // Test: Nested array tag changes
239
+ public updateProductTags() {
240
+ const updates = {
241
+ orders: [
242
+ {
243
+ id: 101,
244
+ date: "2024-01-15",
245
+ total: 150.5,
246
+ items: [
247
+ {
248
+ id: 1001,
249
+ name: "Laptop",
250
+ price: 100.0,
251
+ inStock: true,
252
+ tags: ["tech", "premium", "sale"], // Changed tags
253
+ metadata: {
254
+ views: 300, // Updated
255
+ rating: 4.5,
256
+ },
257
+ },
258
+ {
259
+ id: 1002,
260
+ name: "Mouse",
261
+ price: 50.5,
262
+ inStock: false, // Changed
263
+ tags: ["accessories"], // Reduced tags
264
+ metadata: {
265
+ views: 180,
266
+ rating: 4.0,
267
+ },
268
+ },
269
+ ],
270
+ },
271
+ {
272
+ id: 102,
273
+ date: "2024-02-20",
274
+ total: 75.0,
275
+ items: [
276
+ {
277
+ id: 1003,
278
+ name: "Keyboard",
279
+ price: 75.0,
280
+ inStock: true,
281
+ tags: ["electronics", "accessories"],
282
+ metadata: {
283
+ views: 120,
284
+ rating: 4.8,
285
+ },
286
+ },
287
+ ],
288
+ },
289
+ ],
290
+ };
291
+
292
+ deepMerge(this.users[0], updates);
293
+ }
294
+
295
+ // Test: Complete user replacement
296
+ public addNewUser() {
297
+ const newUser: User = {
298
+ id: 3,
299
+ name: "Charlie Davis",
300
+ email: "charlie@example.com",
301
+ profile: {
302
+ age: 42,
303
+ location: {
304
+ city: "Tokyo",
305
+ country: "Japan",
306
+ },
307
+ preferences: {
308
+ theme: "dark",
309
+ notifications: true,
310
+ },
311
+ },
312
+ orders: [],
313
+ };
314
+
315
+ this.users = [...this.users, newUser];
316
+ }
317
+
318
+ // Test: Toggle for conditional rendering
319
+ public toggleDetails() {
320
+ this.showDetails = !this.showDetails;
321
+ }
322
+
323
+ // Test: Stats update via deep merge
324
+ public updateStats() {
325
+ const updates = {
326
+ totalOrders: 4,
327
+ totalRevenue: 525.49,
328
+ // activeUsers stays 2
329
+ };
330
+
331
+ deepMerge(this.stats, updates);
332
+ }
333
+
334
+ // Test: Direct property update
335
+ public incrementAge() {
336
+ this.users[0].profile.age++;
337
+ }
338
+
339
+ // Test: Undefined value handling
340
+ public testUndefinedMerge() {
341
+ const updates = {
342
+ profile: {
343
+ age: undefined, // Should be skipped
344
+ location: {
345
+ city: "Boston",
346
+ },
347
+ },
348
+ };
349
+
350
+ deepMerge(this.users[0], updates);
351
+ }
352
+ }
353
+
354
+ enableHydration({
355
+ hydrationComplete() {
356
+ (window as any).hydrationCompleted = true;
357
+ },
358
+ });
359
+
360
+ DeepMergeTestElement.define(
361
+ {
362
+ name: "deep-merge-test-element",
363
+ template: declarativeTemplate(),
364
+ },
365
+ [observerMap()],
366
+ );
@@ -0,0 +1,69 @@
1
+ {
2
+ "show-details": true,
3
+ "showDetails": true,
4
+ "stats": {
5
+ "totalOrders": 3,
6
+ "totalRevenue": 425.5,
7
+ "activeUsers": 2
8
+ },
9
+ "users": [
10
+ {
11
+ "id": 1,
12
+ "name": "Alice Johnson",
13
+ "email": "alice@example.com",
14
+ "profile": {
15
+ "age": 28,
16
+ "location": {
17
+ "city": "New York",
18
+ "country": "USA"
19
+ },
20
+ "preferences": {
21
+ "theme": "dark",
22
+ "notifications": true
23
+ }
24
+ },
25
+ "orders": [
26
+ {
27
+ "id": 101,
28
+ "date": "2024-01-15",
29
+ "total": 150.5,
30
+ "items": [
31
+ {
32
+ "id": 1001,
33
+ "name": "Laptop",
34
+ "price": 100.0,
35
+ "inStock": true,
36
+ "tags": ["electronics", "computers"],
37
+ "metadata": { "views": 250, "rating": 4.5 }
38
+ },
39
+ {
40
+ "id": 1002,
41
+ "name": "Mouse",
42
+ "price": 50.5,
43
+ "inStock": true,
44
+ "tags": ["electronics", "accessories"],
45
+ "metadata": { "views": 180, "rating": 4.0 }
46
+ }
47
+ ]
48
+ }
49
+ ]
50
+ },
51
+ {
52
+ "id": 2,
53
+ "name": "Bob Smith",
54
+ "email": "bob@example.com",
55
+ "profile": {
56
+ "age": 35,
57
+ "location": {
58
+ "city": "London",
59
+ "country": "UK"
60
+ },
61
+ "preferences": {
62
+ "theme": "light",
63
+ "notifications": false
64
+ }
65
+ },
66
+ "orders": []
67
+ }
68
+ ]
69
+ }
@@ -0,0 +1,91 @@
1
+ <f-template name="deep-merge-test-element">
2
+ <template>
3
+ <div class="container">
4
+ <h1>Deep Merge Test Fixture</h1>
5
+
6
+ <!-- Stats Section with Deep Property Access -->
7
+ <div class="stats">
8
+ <h2>Statistics</h2>
9
+ <p>Total Orders: <strong>{{stats.totalOrders}}</strong></p>
10
+ <p>Total Revenue: <strong>${{stats.totalRevenue}}</strong></p>
11
+ <p>Active Users: <strong>{{stats.activeUsers}}</strong></p>
12
+ <button @click="{updateStats()}">Update Stats</button>
13
+ </div>
14
+
15
+ <!-- Control Buttons -->
16
+ <div class="controls">
17
+ <h2>Test Actions</h2>
18
+ <button @click="{updateUserProfile()}">Update User Profile</button>
19
+ <button @click="{updateUserOrders()}">Replace Orders</button>
20
+ <button @click="{removeOrderItems()}">Remove Order Items</button>
21
+ <button @click="{updateProductTags()}">Update Product Tags</button>
22
+ <button @click="{addNewUser()}">Add New User</button>
23
+ <button @click="{toggleDetails()}">Toggle Details</button>
24
+ <button @click="{incrementAge()}">Increment Age</button>
25
+ <button @click="{testUndefinedMerge()}">Test Undefined Merge</button>
26
+ </div>
27
+
28
+ <!-- Users List with Conditional Rendering -->
29
+ <div class="users">
30
+ <h2>Users ({{users.length}} total)</h2>
31
+
32
+ <f-repeat value="{{user in users}}">
33
+ <div class="user-card">
34
+ <h3>{{user.name}} (ID: {{user.id}})</h3>
35
+ <p>Email: {{user.email}}</p>
36
+
37
+ <!-- Conditional Details Section -->
38
+ <f-when value="{{showDetails}}">
39
+ <div class="profile">
40
+ <h4>Profile</h4>
41
+ <p>Age: {{user.profile.age}}</p>
42
+ <p>Location: {{user.profile.location.city}}, {{user.profile.location.country}}</p>
43
+ <p>Theme: {{user.profile.preferences.theme}}</p>
44
+ <p>Notifications: <f-when value="{{user.profile.preferences.notifications}}">Enabled</f-when><f-when value="{{!user.profile.preferences.notifications}}">Disabled</f-when></p>
45
+ </div>
46
+ </f-when>
47
+
48
+ <!-- Orders Section with Nested Repeats -->
49
+ <div class="orders">
50
+ <h4>Orders ({{user.orders.length}})</h4>
51
+
52
+ <f-when value="{{user.orders.length > 0}}">
53
+ <f-repeat value="{{order in user.orders}}">
54
+ <div class="order">
55
+ <p><strong>Order #{{order.id}}</strong> - {{order.date}} - Total: ${{order.total}}</p>
56
+
57
+ <!-- Items with Nested Array -->
58
+ <ul class="items">
59
+ <f-repeat value="{{item in order.items}}">
60
+ <li class="item">
61
+ <strong>{{item.name}}</strong> - ${{item.price}}
62
+ <span class="stock"><f-when value="{{item.inStock}}">✓ In Stock</f-when><f-when value="{{!item.inStock}}">✗ Out of Stock</f-when></span>
63
+
64
+ <!-- Tags Array -->
65
+ <div class="tags">
66
+ Tags: <f-repeat value="{{tag in item.tags}}"><span class="tag">{{tag}}</span></f-repeat>
67
+ </div>
68
+
69
+ <!-- Metadata -->
70
+ <f-when value="{{showDetails}}">
71
+ <div class="metadata">
72
+ <small>Views: {{item.metadata.views}} | Rating: {{item.metadata.rating}}</small>
73
+ </div>
74
+ </f-when>
75
+ </li>
76
+ </f-repeat>
77
+ </ul>
78
+ </div>
79
+ </f-repeat>
80
+ </f-when>
81
+
82
+ <f-when value="{{user.orders.length == 0}}">
83
+ <p><em>No orders yet</em></p>
84
+ </f-when>
85
+ </div>
86
+ </div>
87
+ </f-repeat>
88
+ </div>
89
+ </div>
90
+ </template>
91
+ </f-template>
@@ -0,0 +1,14 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en-US">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title></title>
6
+ </head>
7
+ <body>
8
+ <selective-obs-element></selective-obs-element>
9
+ <all-obs-element></all-obs-element>
10
+ <empty-props-element></empty-props-element>
11
+ <array-selective-element></array-selective-element>
12
+ <script type="module" src="./main.ts"></script>
13
+ </body>
14
+ </html>
@@ -0,0 +1,6 @@
1
+ {
2
+ "entry": "entry.html",
3
+ "state": "state.json",
4
+ "output": "index.html",
5
+ "templates": "templates.html"
6
+ }
@@ -0,0 +1,110 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en-US">
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title></title>
6
+ </head>
7
+ <body>
8
+ <selective-obs-element><template shadowrootmode="open" shadowroot="open"><div class="user-section">
9
+ <span class="user-name"><!--fe:b-->Alice<!--fe:/b--></span>
10
+ <span class="user-age"><!--fe:b-->28<!--fe:/b--></span>
11
+ <span class="user-history-joined"><!--fe:b-->2020-01-01<!--fe:/b--></span>
12
+ <span class="user-history-visits"><!--fe:b-->100<!--fe:/b--></span>
13
+ <span class="user-location-city"><!--fe:b-->New York<!--fe:/b--></span>
14
+ </div>
15
+ <div class="settings-section">
16
+ <span class="settings-theme"><!--fe:b-->dark<!--fe:/b--></span>
17
+ </div>
18
+ <div class="analytics-section">
19
+ <span class="active-chart"><!--fe:b-->line<!--fe:/b--></span>
20
+ <span class="cached-data"><!--fe:b-->heavy-data<!--fe:/b--></span>
21
+ <span class="analytics-summary"><!--fe:b-->good<!--fe:/b--></span>
22
+ </div>
23
+ <button data-fe="1">Update Name</button>
24
+ <button data-fe="1">Update Age</button>
25
+ <button data-fe="1">Update History</button>
26
+ <button data-fe="1">Update Location</button>
27
+ <button data-fe="1">Update Settings</button>
28
+ <button data-fe="1">Update Active Chart</button>
29
+ <button data-fe="1">Update Cached Data</button>
30
+ <button data-fe="1">Update Summary</button></template></selective-obs-element>
31
+ <all-obs-element><template shadowrootmode="open" shadowroot="open"><span class="user-name"><!--fe:b-->Alice<!--fe:/b--></span>
32
+ <span class="settings-theme"><!--fe:b-->dark<!--fe:/b--></span>
33
+ <button data-fe="1">Update Name</button>
34
+ <button data-fe="1">Update Settings</button></template></all-obs-element>
35
+ <empty-props-element><template shadowrootmode="open" shadowroot="open"><span class="user-name"><!--fe:b-->Alice<!--fe:/b--></span>
36
+ <span class="settings-theme"><!--fe:b-->dark<!--fe:/b--></span>
37
+ <button data-fe="1">Update Name</button>
38
+ <button data-fe="1">Update Settings</button></template></empty-props-element>
39
+ <array-selective-element><template shadowrootmode="open" shadowroot="open"><!--fe:b--><!--fe:r-->
40
+ <div class="item-row">
41
+ <span class="item-text"><!--fe:b-->item-1<!--fe:/b--></span>
42
+ <span class="item-count"><!--fe:b-->1<!--fe:/b--></span>
43
+ </div>
44
+ <!--fe:/r--><!--fe:r-->
45
+ <div class="item-row">
46
+ <span class="item-text"><!--fe:b-->item-2<!--fe:/b--></span>
47
+ <span class="item-count"><!--fe:b-->2<!--fe:/b--></span>
48
+ </div>
49
+ <!--fe:/r--><!--fe:/b-->
50
+ <button data-fe="1">Update Item Text</button>
51
+ <button data-fe="1">Add Item</button></template></array-selective-element>
52
+ <f-template name="selective-obs-element">
53
+ <template>
54
+ <div class="user-section">
55
+ <span class="user-name">{{user.name}}</span>
56
+ <span class="user-age">{{user.age}}</span>
57
+ <span class="user-history-joined">{{user.history.joined}}</span>
58
+ <span class="user-history-visits">{{user.history.visits}}</span>
59
+ <span class="user-location-city">{{user.location.city}}</span>
60
+ </div>
61
+ <div class="settings-section">
62
+ <span class="settings-theme">{{settings.theme}}</span>
63
+ </div>
64
+ <div class="analytics-section">
65
+ <span class="active-chart">{{analytics.charts.activeChart}}</span>
66
+ <span class="cached-data">{{analytics.charts.cachedData}}</span>
67
+ <span class="analytics-summary">{{analytics.summary}}</span>
68
+ </div>
69
+ <button @click="{updateUserName()}">Update Name</button>
70
+ <button @click="{updateUserAge()}">Update Age</button>
71
+ <button @click="{updateHistory()}">Update History</button>
72
+ <button @click="{updateLocation()}">Update Location</button>
73
+ <button @click="{updateSettings()}">Update Settings</button>
74
+ <button @click="{updateActiveChart()}">Update Active Chart</button>
75
+ <button @click="{updateCachedData()}">Update Cached Data</button>
76
+ <button @click="{updateSummary()}">Update Summary</button>
77
+ </template>
78
+ </f-template>
79
+ <f-template name="all-obs-element">
80
+ <template>
81
+ <span class="user-name">{{user.name}}</span>
82
+ <span class="settings-theme">{{settings.theme}}</span>
83
+ <button @click="{updateUserName()}">Update Name</button>
84
+ <button @click="{updateSettings()}">Update Settings</button>
85
+ </template>
86
+ </f-template>
87
+ <f-template name="empty-props-element">
88
+ <template>
89
+ <span class="user-name">{{user.name}}</span>
90
+ <span class="settings-theme">{{settings.theme}}</span>
91
+ <button @click="{updateUserName()}">Update Name</button>
92
+ <button @click="{updateSettings()}">Update Settings</button>
93
+ </template>
94
+ </f-template>
95
+ <f-template name="array-selective-element">
96
+ <template>
97
+ <f-repeat value="{{item in items}}">
98
+ <div class="item-row">
99
+ <span class="item-text">{{item.text}}</span>
100
+ <span class="item-count">{{item.meta.count}}</span>
101
+ </div>
102
+ </f-repeat>
103
+ <button @click="{updateItemText()}">Update Item Text</button>
104
+ <button @click="{addItem()}">Add Item</button>
105
+ </template>
106
+ </f-template>
107
+
108
+ <script type="module" src="./main.ts"></script>
109
+ </body>
110
+ </html>