@gyral/core 0.2.0 → 0.3.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 (517) hide show
  1. package/CHANGELOG.md +129 -0
  2. package/NOTICE +19 -0
  3. package/README.md +35 -8
  4. package/dist/call.d.ts +32 -0
  5. package/dist/call.js +63 -0
  6. package/dist/call.js.map +1 -0
  7. package/dist/children.d.ts +30 -5
  8. package/dist/children.js +26 -4
  9. package/dist/children.js.map +1 -1
  10. package/dist/cli/gyral-types.d.ts +2 -0
  11. package/dist/cli/gyral-types.js +23 -0
  12. package/dist/cli/gyral-types.js.map +1 -0
  13. package/dist/command.d.ts +54 -12
  14. package/dist/command.js +31 -11
  15. package/dist/command.js.map +1 -1
  16. package/dist/compiler/ast.d.ts +23 -0
  17. package/dist/compiler/ast.js +149 -0
  18. package/dist/compiler/ast.js.map +1 -0
  19. package/dist/compiler/compile.d.ts +41 -0
  20. package/dist/compiler/compile.js +148 -0
  21. package/dist/compiler/compile.js.map +1 -0
  22. package/dist/compiler/component-entries.d.ts +7 -0
  23. package/dist/compiler/component-entries.js +42 -0
  24. package/dist/compiler/component-entries.js.map +1 -0
  25. package/dist/compiler/components.d.ts +4 -0
  26. package/dist/compiler/components.js +182 -0
  27. package/dist/compiler/components.js.map +1 -0
  28. package/dist/compiler/facts.d.ts +31 -0
  29. package/dist/compiler/facts.js +285 -0
  30. package/dist/compiler/facts.js.map +1 -0
  31. package/dist/compiler/features.d.ts +34 -0
  32. package/dist/compiler/features.js +158 -0
  33. package/dist/compiler/features.js.map +1 -0
  34. package/dist/compiler/hooks.d.ts +22 -0
  35. package/dist/compiler/hooks.js +241 -0
  36. package/dist/compiler/hooks.js.map +1 -0
  37. package/dist/compiler/loader-source.d.ts +14 -0
  38. package/dist/compiler/loader-source.js +86 -0
  39. package/dist/compiler/loader-source.js.map +1 -0
  40. package/dist/compiler/locate.d.ts +14 -0
  41. package/dist/compiler/locate.js +78 -0
  42. package/dist/compiler/locate.js.map +1 -0
  43. package/dist/compiler/parse5-check.d.ts +21 -0
  44. package/dist/compiler/parse5-check.js +60 -0
  45. package/dist/compiler/parse5-check.js.map +1 -0
  46. package/dist/compiler/prop-schemas.d.ts +4 -0
  47. package/dist/compiler/prop-schemas.js +108 -0
  48. package/dist/compiler/prop-schemas.js.map +1 -0
  49. package/dist/compiler/scan.d.ts +41 -0
  50. package/dist/compiler/scan.js +160 -0
  51. package/dist/compiler/scan.js.map +1 -0
  52. package/dist/compiler/scope.d.ts +8 -0
  53. package/dist/compiler/scope.js +116 -0
  54. package/dist/compiler/scope.js.map +1 -0
  55. package/dist/compiler/source.d.ts +34 -0
  56. package/dist/compiler/source.js +114 -0
  57. package/dist/compiler/source.js.map +1 -0
  58. package/dist/compiler/tag-map.d.ts +41 -0
  59. package/dist/compiler/tag-map.js +126 -0
  60. package/dist/compiler/tag-map.js.map +1 -0
  61. package/dist/components-ready.d.ts +7 -0
  62. package/dist/components-ready.js +19 -0
  63. package/dist/components-ready.js.map +1 -0
  64. package/dist/define.d.ts +13 -4
  65. package/dist/define.js +35 -331
  66. package/dist/define.js.map +1 -1
  67. package/dist/devtools-events.d.ts +13 -0
  68. package/dist/devtools-events.js.map +1 -1
  69. package/dist/devtools-off.d.ts +2 -0
  70. package/dist/devtools-off.js +2 -0
  71. package/dist/devtools-off.js.map +1 -1
  72. package/dist/devtools.d.ts +4 -0
  73. package/dist/devtools.js +17 -2
  74. package/dist/devtools.js.map +1 -1
  75. package/dist/drivers-scope.d.ts +1 -1
  76. package/dist/drivers-scope.js +1 -8
  77. package/dist/drivers-scope.js.map +1 -1
  78. package/dist/element-internals.d.ts +1 -0
  79. package/dist/element-internals.js +11 -0
  80. package/dist/element-internals.js.map +1 -0
  81. package/dist/element-types.d.ts +11 -5
  82. package/dist/element-types.js.map +1 -1
  83. package/dist/element.d.ts +3 -0
  84. package/dist/element.js +322 -0
  85. package/dist/element.js.map +1 -0
  86. package/dist/error-view.d.ts +10 -0
  87. package/dist/error-view.js +30 -0
  88. package/dist/error-view.js.map +1 -0
  89. package/dist/errors.d.ts +21 -0
  90. package/dist/errors.js +47 -0
  91. package/dist/errors.js.map +1 -0
  92. package/dist/errors.json +289 -0
  93. package/dist/eslint/imports.d.ts +26 -0
  94. package/dist/eslint/imports.js +78 -0
  95. package/dist/eslint/imports.js.map +1 -0
  96. package/dist/eslint/index.d.ts +16 -0
  97. package/dist/eslint/index.js +23 -0
  98. package/dist/eslint/index.js.map +1 -0
  99. package/dist/eslint/locate.d.ts +33 -0
  100. package/dist/eslint/locate.js +132 -0
  101. package/dist/eslint/locate.js.map +1 -0
  102. package/dist/eslint/row-purity-rule.d.ts +2 -0
  103. package/dist/eslint/row-purity-rule.js +103 -0
  104. package/dist/eslint/row-purity-rule.js.map +1 -0
  105. package/dist/eslint/template-rule.d.ts +6 -0
  106. package/dist/eslint/template-rule.js +76 -0
  107. package/dist/eslint/template-rule.js.map +1 -0
  108. package/dist/eslint/unused-intent-rule.d.ts +2 -0
  109. package/dist/eslint/unused-intent-rule.js +186 -0
  110. package/dist/eslint/unused-intent-rule.js.map +1 -0
  111. package/dist/features.d.ts +39 -0
  112. package/dist/features.js +2 -0
  113. package/dist/features.js.map +1 -0
  114. package/dist/focus.d.ts +13 -12
  115. package/dist/focus.js +44 -11
  116. package/dist/focus.js.map +1 -1
  117. package/dist/form-associated.d.ts +46 -0
  118. package/dist/form-associated.js +77 -0
  119. package/dist/form-associated.js.map +1 -0
  120. package/dist/forms.d.ts +42 -30
  121. package/dist/forms.js +85 -41
  122. package/dist/forms.js.map +1 -1
  123. package/dist/frame-lane.d.ts +11 -0
  124. package/dist/frame-lane.js +28 -0
  125. package/dist/frame-lane.js.map +1 -0
  126. package/dist/head.d.ts +61 -0
  127. package/dist/head.js +85 -0
  128. package/dist/head.js.map +1 -0
  129. package/dist/hooks/invalid.d.ts +14 -0
  130. package/dist/hooks/invalid.js +72 -0
  131. package/dist/hooks/invalid.js.map +1 -0
  132. package/dist/host-model.d.ts +77 -0
  133. package/dist/host-model.js +278 -0
  134. package/dist/host-model.js.map +1 -0
  135. package/dist/hydration-client.d.ts +9 -0
  136. package/dist/hydration-client.js +35 -0
  137. package/dist/hydration-client.js.map +1 -0
  138. package/dist/hydration-loader.d.ts +13 -0
  139. package/dist/hydration-loader.js +58 -0
  140. package/dist/hydration-loader.js.map +1 -0
  141. package/dist/hydration-off.d.ts +8 -0
  142. package/dist/hydration-off.js +25 -0
  143. package/dist/hydration-off.js.map +1 -0
  144. package/dist/hydration.d.ts +3 -21
  145. package/dist/hydration.js +14 -63
  146. package/dist/hydration.js.map +1 -1
  147. package/dist/index.d.ts +24 -36
  148. package/dist/index.js +14 -32
  149. package/dist/index.js.map +1 -1
  150. package/dist/indexeddb-types.d.ts +97 -0
  151. package/dist/indexeddb-types.js +2 -0
  152. package/dist/indexeddb-types.js.map +1 -0
  153. package/dist/indexeddb.d.ts +5 -0
  154. package/dist/indexeddb.js +118 -0
  155. package/dist/indexeddb.js.map +1 -0
  156. package/dist/intent.d.ts +62 -17
  157. package/dist/intent.js +193 -100
  158. package/dist/intent.js.map +1 -1
  159. package/dist/internal/indexeddb-open.d.ts +8 -0
  160. package/dist/internal/indexeddb-open.js +96 -0
  161. package/dist/internal/indexeddb-open.js.map +1 -0
  162. package/dist/internal/indexeddb-transaction.d.ts +4 -0
  163. package/dist/internal/indexeddb-transaction.js +134 -0
  164. package/dist/internal/indexeddb-transaction.js.map +1 -0
  165. package/dist/internal/interpreter.d.ts +15 -1
  166. package/dist/internal/interpreter.js +42 -47
  167. package/dist/internal/interpreter.js.map +1 -1
  168. package/dist/internal/token.d.ts +1 -0
  169. package/dist/internal/token.js +7 -0
  170. package/dist/internal/token.js.map +1 -0
  171. package/dist/internal.d.ts +20 -0
  172. package/dist/internal.js +22 -0
  173. package/dist/internal.js.map +1 -0
  174. package/dist/invoker-fallback-used.d.ts +4 -0
  175. package/dist/invoker-fallback-used.js +10 -0
  176. package/dist/invoker-fallback-used.js.map +1 -0
  177. package/dist/invoker-fallback.d.ts +4 -0
  178. package/dist/invoker-fallback.js +15 -0
  179. package/dist/invoker-fallback.js.map +1 -0
  180. package/dist/invokers-shim.d.ts +6 -0
  181. package/dist/invokers-shim.js +32 -0
  182. package/dist/invokers-shim.js.map +1 -0
  183. package/dist/invokers.d.ts +3 -5
  184. package/dist/invokers.js +11 -51
  185. package/dist/invokers.js.map +1 -1
  186. package/dist/islands.d.ts +0 -2
  187. package/dist/islands.js +4 -11
  188. package/dist/islands.js.map +1 -1
  189. package/dist/light-dom.d.ts +4 -53
  190. package/dist/light-dom.js +5 -100
  191. package/dist/light-dom.js.map +1 -1
  192. package/dist/prop.d.ts +89 -0
  193. package/dist/prop.js +41 -0
  194. package/dist/prop.js.map +1 -0
  195. package/dist/props.d.ts +57 -21
  196. package/dist/props.js +157 -34
  197. package/dist/props.js.map +1 -1
  198. package/dist/retry.d.ts +15 -0
  199. package/dist/retry.js +48 -0
  200. package/dist/retry.js.map +1 -0
  201. package/dist/scheduler.d.ts +43 -0
  202. package/dist/scheduler.js +212 -0
  203. package/dist/scheduler.js.map +1 -0
  204. package/dist/script-json.d.ts +2 -0
  205. package/dist/script-json.js +13 -0
  206. package/dist/script-json.js.map +1 -0
  207. package/dist/server-component.d.ts +10 -0
  208. package/dist/server-component.js +133 -0
  209. package/dist/server-component.js.map +1 -0
  210. package/dist/server-specs.d.ts +6 -0
  211. package/dist/server-specs.js +13 -0
  212. package/dist/server-specs.js.map +1 -0
  213. package/dist/server.d.ts +34 -0
  214. package/dist/server.js +59 -0
  215. package/dist/server.js.map +1 -0
  216. package/dist/settled.d.ts +11 -0
  217. package/dist/settled.js +62 -0
  218. package/dist/settled.js.map +1 -0
  219. package/dist/spec-features-used.d.ts +21 -0
  220. package/dist/spec-features-used.js +50 -0
  221. package/dist/spec-features-used.js.map +1 -0
  222. package/dist/spec-features.d.ts +28 -0
  223. package/dist/spec-features.js +42 -0
  224. package/dist/spec-features.js.map +1 -0
  225. package/dist/states.d.ts +3 -5
  226. package/dist/states.js +22 -11
  227. package/dist/states.js.map +1 -1
  228. package/dist/storage.d.ts +69 -0
  229. package/dist/storage.js +158 -0
  230. package/dist/storage.js.map +1 -0
  231. package/dist/store-binding.d.ts +6 -3
  232. package/dist/store-binding.js +7 -8
  233. package/dist/store-binding.js.map +1 -1
  234. package/dist/store-scope.d.ts +8 -11
  235. package/dist/store-scope.js +15 -40
  236. package/dist/store-scope.js.map +1 -1
  237. package/dist/store.d.ts +3 -0
  238. package/dist/store.js +45 -10
  239. package/dist/store.js.map +1 -1
  240. package/dist/stores-provider.d.ts +2 -6
  241. package/dist/stores-provider.js +21 -55
  242. package/dist/stores-provider.js.map +1 -1
  243. package/dist/subscription.d.ts +35 -0
  244. package/dist/subscription.js +74 -0
  245. package/dist/subscription.js.map +1 -0
  246. package/dist/subscriptions.d.ts +26 -0
  247. package/dist/subscriptions.js +98 -0
  248. package/dist/subscriptions.js.map +1 -0
  249. package/dist/transitions.d.ts +5 -7
  250. package/dist/transitions.js +17 -20
  251. package/dist/transitions.js.map +1 -1
  252. package/dist/types.d.ts +142 -49
  253. package/dist/types.js.map +1 -1
  254. package/dist/use-dialogs.d.ts +2 -0
  255. package/dist/use-dialogs.js +9 -0
  256. package/dist/use-dialogs.js.map +1 -0
  257. package/dist/use-disposal.d.ts +2 -0
  258. package/dist/use-disposal.js +9 -0
  259. package/dist/use-disposal.js.map +1 -0
  260. package/dist/use-error-view.d.ts +2 -0
  261. package/dist/use-error-view.js +9 -0
  262. package/dist/use-error-view.js.map +1 -0
  263. package/dist/use-errored.d.ts +2 -0
  264. package/dist/use-errored.js +9 -0
  265. package/dist/use-errored.js.map +1 -0
  266. package/dist/use-form-associated.d.ts +2 -0
  267. package/dist/use-form-associated.js +7 -0
  268. package/dist/use-form-associated.js.map +1 -0
  269. package/dist/use-frame-lane.d.ts +2 -0
  270. package/dist/use-frame-lane.js +10 -0
  271. package/dist/use-frame-lane.js.map +1 -0
  272. package/dist/use-invokers.d.ts +2 -0
  273. package/dist/use-invokers.js +10 -0
  274. package/dist/use-invokers.js.map +1 -0
  275. package/dist/use-states.d.ts +2 -0
  276. package/dist/use-states.js +10 -0
  277. package/dist/use-states.js.map +1 -0
  278. package/dist/use-subscriptions.d.ts +2 -0
  279. package/dist/use-subscriptions.js +10 -0
  280. package/dist/use-subscriptions.js.map +1 -0
  281. package/dist/use-transitions.d.ts +2 -0
  282. package/dist/use-transitions.js +10 -0
  283. package/dist/use-transitions.js.map +1 -0
  284. package/dist/view/attributes.d.ts +11 -0
  285. package/dist/view/attributes.js +15 -0
  286. package/dist/view/attributes.js.map +1 -0
  287. package/dist/view/compiled.d.ts +1 -0
  288. package/dist/view/compiled.js +6 -0
  289. package/dist/view/compiled.js.map +1 -0
  290. package/dist/view/dev-off.d.ts +1 -0
  291. package/dist/view/dev-off.js +4 -0
  292. package/dist/view/dev-off.js.map +1 -0
  293. package/dist/view/dev.d.ts +1 -0
  294. package/dist/view/dev.js +5 -0
  295. package/dist/view/dev.js.map +1 -0
  296. package/dist/view/flags.d.ts +1 -0
  297. package/dist/view/flags.js +4 -0
  298. package/dist/view/flags.js.map +1 -0
  299. package/dist/view/index.d.ts +26 -0
  300. package/dist/view/index.js +27 -0
  301. package/dist/view/index.js.map +1 -0
  302. package/dist/view/loc.d.ts +9 -0
  303. package/dist/view/loc.js +50 -0
  304. package/dist/view/loc.js.map +1 -0
  305. package/dist/view/message.d.ts +17 -0
  306. package/dist/view/message.js +40 -0
  307. package/dist/view/message.js.map +1 -0
  308. package/dist/view/messages.d.ts +43 -0
  309. package/dist/view/messages.js +84 -0
  310. package/dist/view/messages.js.map +1 -0
  311. package/dist/view/normalize/check.d.ts +23 -0
  312. package/dist/view/normalize/check.js +81 -0
  313. package/dist/view/normalize/check.js.map +1 -0
  314. package/dist/view/normalize/emit.d.ts +15 -0
  315. package/dist/view/normalize/emit.js +165 -0
  316. package/dist/view/normalize/emit.js.map +1 -0
  317. package/dist/view/normalize/entities.d.ts +4 -0
  318. package/dist/view/normalize/entities.js +38 -0
  319. package/dist/view/normalize/entities.js.map +1 -0
  320. package/dist/view/normalize/errors.d.ts +9 -0
  321. package/dist/view/normalize/errors.js +19 -0
  322. package/dist/view/normalize/errors.js.map +1 -0
  323. package/dist/view/normalize/id.d.ts +10 -0
  324. package/dist/view/normalize/id.js +55 -0
  325. package/dist/view/normalize/id.js.map +1 -0
  326. package/dist/view/normalize/normalize.d.ts +18 -0
  327. package/dist/view/normalize/normalize.js +42 -0
  328. package/dist/view/normalize/normalize.js.map +1 -0
  329. package/dist/view/normalize/repairs.d.ts +24 -0
  330. package/dist/view/normalize/repairs.js +166 -0
  331. package/dist/view/normalize/repairs.js.map +1 -0
  332. package/dist/view/normalize/rules.d.ts +39 -0
  333. package/dist/view/normalize/rules.js +120 -0
  334. package/dist/view/normalize/rules.js.map +1 -0
  335. package/dist/view/normalize/shape.d.ts +5 -0
  336. package/dist/view/normalize/shape.js +38 -0
  337. package/dist/view/normalize/shape.js.map +1 -0
  338. package/dist/view/normalize/source.d.ts +13 -0
  339. package/dist/view/normalize/source.js +34 -0
  340. package/dist/view/normalize/source.js.map +1 -0
  341. package/dist/view/normalize/svg.d.ts +14 -0
  342. package/dist/view/normalize/svg.js +40 -0
  343. package/dist/view/normalize/svg.js.map +1 -0
  344. package/dist/view/normalize/tag-states.d.ts +23 -0
  345. package/dist/view/normalize/tag-states.js +192 -0
  346. package/dist/view/normalize/tag-states.js.map +1 -0
  347. package/dist/view/normalize/tokenizer.d.ts +5 -0
  348. package/dist/view/normalize/tokenizer.js +233 -0
  349. package/dist/view/normalize/tokenizer.js.map +1 -0
  350. package/dist/view/normalize/tokens.d.ts +55 -0
  351. package/dist/view/normalize/tokens.js +24 -0
  352. package/dist/view/normalize/tokens.js.map +1 -0
  353. package/dist/view/normalize/tree.d.ts +65 -0
  354. package/dist/view/normalize/tree.js +235 -0
  355. package/dist/view/normalize/tree.js.map +1 -0
  356. package/dist/view/normalize/types.d.ts +146 -0
  357. package/dist/view/normalize/types.js +29 -0
  358. package/dist/view/normalize/types.js.map +1 -0
  359. package/dist/view/normalize/whitespace.d.ts +2 -0
  360. package/dist/{template-whitespace.js → view/normalize/whitespace.js} +27 -36
  361. package/dist/view/normalize/whitespace.js.map +1 -0
  362. package/dist/view/prepare-stub.d.ts +3 -0
  363. package/dist/view/prepare-stub.js +7 -0
  364. package/dist/view/prepare-stub.js.map +1 -0
  365. package/dist/view/prepare.d.ts +11 -0
  366. package/dist/view/prepare.js +63 -0
  367. package/dist/view/prepare.js.map +1 -0
  368. package/dist/view/registry.d.ts +78 -0
  369. package/dist/view/registry.js +27 -0
  370. package/dist/view/registry.js.map +1 -0
  371. package/dist/view/render/adopt-attr.d.ts +14 -0
  372. package/dist/view/render/adopt-attr.js +83 -0
  373. package/dist/view/render/adopt-attr.js.map +1 -0
  374. package/dist/view/render/adopt-plan.d.ts +10 -0
  375. package/dist/view/render/adopt-plan.js +26 -0
  376. package/dist/view/render/adopt-plan.js.map +1 -0
  377. package/dist/view/render/adopt.d.ts +3 -0
  378. package/dist/view/render/adopt.js +286 -0
  379. package/dist/view/render/adopt.js.map +1 -0
  380. package/dist/view/render/attr-parts.d.ts +72 -0
  381. package/dist/view/render/attr-parts.js +262 -0
  382. package/dist/view/render/attr-parts.js.map +1 -0
  383. package/dist/view/render/child-part.d.ts +51 -0
  384. package/dist/view/render/child-part.js +173 -0
  385. package/dist/view/render/child-part.js.map +1 -0
  386. package/dist/view/render/dev-check.d.ts +12 -0
  387. package/dist/view/render/dev-check.js +122 -0
  388. package/dist/view/render/dev-check.js.map +1 -0
  389. package/dist/view/render/dispose.d.ts +3 -0
  390. package/dist/view/render/dispose.js +76 -0
  391. package/dist/view/render/dispose.js.map +1 -0
  392. package/dist/view/render/hook-part.d.ts +5 -0
  393. package/dist/view/render/hook-part.js +36 -0
  394. package/dist/view/render/hook-part.js.map +1 -0
  395. package/dist/view/render/hook-run.d.ts +2 -0
  396. package/dist/view/render/hook-run.js +72 -0
  397. package/dist/view/render/hook-run.js.map +1 -0
  398. package/dist/view/render/hooks.d.ts +108 -0
  399. package/dist/view/render/hooks.js +108 -0
  400. package/dist/view/render/hooks.js.map +1 -0
  401. package/dist/view/render/hydrate.d.ts +10 -0
  402. package/dist/view/render/hydrate.js +33 -0
  403. package/dist/view/render/hydrate.js.map +1 -0
  404. package/dist/view/render/instance.d.ts +33 -0
  405. package/dist/view/render/instance.js +107 -0
  406. package/dist/view/render/instance.js.map +1 -0
  407. package/dist/view/render/keyed.d.ts +6 -0
  408. package/dist/view/render/keyed.js +15 -0
  409. package/dist/view/render/keyed.js.map +1 -0
  410. package/dist/view/render/list.d.ts +20 -0
  411. package/dist/view/render/list.js +156 -0
  412. package/dist/view/render/list.js.map +1 -0
  413. package/dist/view/render/mismatch.d.ts +10 -0
  414. package/dist/view/render/mismatch.js +55 -0
  415. package/dist/view/render/mismatch.js.map +1 -0
  416. package/dist/view/render/modal.d.ts +3 -0
  417. package/dist/view/render/modal.js +39 -0
  418. package/dist/view/render/modal.js.map +1 -0
  419. package/dist/view/render/nodes.d.ts +10 -0
  420. package/dist/view/render/nodes.js +37 -0
  421. package/dist/view/render/nodes.js.map +1 -0
  422. package/dist/view/render/place.d.ts +18 -0
  423. package/dist/view/render/place.js +69 -0
  424. package/dist/view/render/place.js.map +1 -0
  425. package/dist/view/render/plan.d.ts +26 -0
  426. package/dist/view/render/plan.js +124 -0
  427. package/dist/view/render/plan.js.map +1 -0
  428. package/dist/view/render/raw.d.ts +21 -0
  429. package/dist/view/render/raw.js +72 -0
  430. package/dist/view/render/raw.js.map +1 -0
  431. package/dist/view/render/render.d.ts +15 -0
  432. package/dist/view/render/render.js +65 -0
  433. package/dist/view/render/render.js.map +1 -0
  434. package/dist/view/render/reorder.d.ts +4 -0
  435. package/dist/view/render/reorder.js +101 -0
  436. package/dist/view/render/reorder.js.map +1 -0
  437. package/dist/view/render/rows.d.ts +23 -0
  438. package/dist/view/render/rows.js +95 -0
  439. package/dist/view/render/rows.js.map +1 -0
  440. package/dist/view/render/seen.d.ts +11 -0
  441. package/dist/view/render/seen.js +17 -0
  442. package/dist/view/render/seen.js.map +1 -0
  443. package/dist/view/render/toggles.d.ts +6 -0
  444. package/dist/view/render/toggles.js +6 -0
  445. package/dist/view/render/toggles.js.map +1 -0
  446. package/dist/view/render/values.d.ts +29 -0
  447. package/dist/view/render/values.js +13 -0
  448. package/dist/view/render/values.js.map +1 -0
  449. package/dist/view/render/warn.d.ts +28 -0
  450. package/dist/view/render/warn.js +114 -0
  451. package/dist/view/render/warn.js.map +1 -0
  452. package/dist/view/server/component.d.ts +12 -0
  453. package/dist/view/server/component.js +64 -0
  454. package/dist/view/server/component.js.map +1 -0
  455. package/dist/view/server/escape.d.ts +10 -0
  456. package/dist/view/server/escape.js +34 -0
  457. package/dist/view/server/escape.js.map +1 -0
  458. package/dist/view/server/index.d.ts +48 -0
  459. package/dist/view/server/index.js +80 -0
  460. package/dist/view/server/index.js.map +1 -0
  461. package/dist/view/server/sha256.d.ts +2 -0
  462. package/dist/view/server/sha256.js +75 -0
  463. package/dist/view/server/sha256.js.map +1 -0
  464. package/dist/view/server/tags.d.ts +68 -0
  465. package/dist/view/server/tags.js +132 -0
  466. package/dist/view/server/tags.js.map +1 -0
  467. package/dist/view/server/values.d.ts +18 -0
  468. package/dist/view/server/values.js +94 -0
  469. package/dist/view/server/values.js.map +1 -0
  470. package/dist/view/server/writer.d.ts +21 -0
  471. package/dist/view/server/writer.js +170 -0
  472. package/dist/view/server/writer.js.map +1 -0
  473. package/dist/view/styles.d.ts +25 -0
  474. package/dist/view/styles.js +58 -0
  475. package/dist/view/styles.js.map +1 -0
  476. package/dist/view/template-element.d.ts +10 -0
  477. package/dist/view/template-element.js +45 -0
  478. package/dist/view/template-element.js.map +1 -0
  479. package/dist/view/template.d.ts +29 -0
  480. package/dist/view/template.js +84 -0
  481. package/dist/view/template.js.map +1 -0
  482. package/dist/view/trusted-html.d.ts +6 -0
  483. package/dist/view/trusted-html.js +34 -0
  484. package/dist/view/trusted-html.js.map +1 -0
  485. package/dist/vite.d.ts +57 -11
  486. package/dist/vite.js +319 -27
  487. package/dist/vite.js.map +1 -1
  488. package/package.json +70 -4
  489. package/dist/accessible-name.d.ts +0 -19
  490. package/dist/accessible-name.js +0 -56
  491. package/dist/accessible-name.js.map +0 -1
  492. package/dist/element-directive.d.ts +0 -20
  493. package/dist/element-directive.js +0 -31
  494. package/dist/element-directive.js.map +0 -1
  495. package/dist/invalid.d.ts +0 -21
  496. package/dist/invalid.js +0 -70
  497. package/dist/invalid.js.map +0 -1
  498. package/dist/lit-html-check.d.ts +0 -6
  499. package/dist/lit-html-check.js +0 -48
  500. package/dist/lit-html-check.js.map +0 -1
  501. package/dist/live-boolean.d.ts +0 -22
  502. package/dist/live-boolean.js +0 -34
  503. package/dist/live-boolean.js.map +0 -1
  504. package/dist/random.d.ts +0 -13
  505. package/dist/random.js +0 -19
  506. package/dist/random.js.map +0 -1
  507. package/dist/styles.d.ts +0 -12
  508. package/dist/styles.js +0 -11
  509. package/dist/styles.js.map +0 -1
  510. package/dist/template-whitespace.d.ts +0 -7
  511. package/dist/template-whitespace.js.map +0 -1
  512. package/dist/templates.d.ts +0 -5
  513. package/dist/templates.js +0 -15
  514. package/dist/templates.js.map +0 -1
  515. package/dist/textarea.d.ts +0 -26
  516. package/dist/textarea.js +0 -85
  517. package/dist/textarea.js.map +0 -1
package/dist/command.d.ts CHANGED
@@ -1,12 +1,20 @@
1
1
  import type { IntentRejected } from './types.js';
2
2
  /** How commands in the same lane interact. See ADR 0006 for the table. */
3
3
  export type Concurrency = 'merge' | 'switch' | 'exhaust' | 'queue';
4
- export interface RetryPolicy {
4
+ /** How `retry(driver, policy)` retries a rejected run (retry.ts). `E`: the driver's error. */
5
+ export interface RetryPolicy<E = unknown> {
5
6
  /** Retries after the first failure. */
6
7
  readonly times: number;
7
8
  /** Delay before each retry (the base delay for exponential backoff). Default 0. */
8
9
  readonly delayMs?: number;
9
10
  readonly backoff?: 'fixed' | 'exponential';
11
+ /** Full jitter: wait a random time between 0 and the computed delay, so clients spread out. */
12
+ readonly jitter?: boolean;
13
+ /**
14
+ * Which failures to retry, given the driver's typed error (its `toError`, else the thrown
15
+ * value). Default: every failure. For `@gyral/http`, `retryableHttpError`.
16
+ */
17
+ readonly retryIf?: (error: E) => boolean;
10
18
  }
11
19
  export interface DriverContext<O = unknown> {
12
20
  /** Aborts when the command is switched away or its component disconnects. */
@@ -24,15 +32,35 @@ export interface Driver<I, O, E = unknown> {
24
32
  readonly run: (input: I, ctx: DriverContext<O>) => O | Promise<O>;
25
33
  /** Default policy for this driver's commands. Default `'merge'`. */
26
34
  readonly concurrency?: Concurrency;
27
- readonly retry?: RetryPolicy;
28
35
  /** Turns a thrown or rejected value into this driver's typed error. */
29
36
  readonly toError?: (cause: unknown) => E;
30
37
  }
31
- /** Any driver, with its input type erased. */
38
+ /**
39
+ * Any driver, with its input type erased. Every `Driver<I, O, E>` (from `defineDriver`,
40
+ * `subscription`, a test fake) is assignable to it as is: no cast.
41
+ */
32
42
  export type AnyDriver = Driver<never, unknown>;
33
- /** Drivers substituted by name (test fakes, configured instances). */
43
+ /**
44
+ * A driver with no implementation of its own (`defineDriver<I, O, E>('session')`): commands built
45
+ * from it are typed by `I`, `O` and `E`, and it runs only when `provideDrivers` or `el.drivers`
46
+ * supplies a driver of that name (ADR 0006 addendum "Driver tokens").
47
+ */
48
+ export interface DriverToken<E = unknown> {
49
+ readonly name: string;
50
+ readonly concurrency?: Concurrency;
51
+ readonly toError?: (cause: unknown) => E;
52
+ }
53
+ /**
54
+ * Drivers substituted by name (test fakes, configured instances): `el.drivers`,
55
+ * `provideDrivers`. Annotate a driver map with this type (or `Record<string, AnyDriver>`), not
56
+ * `Record<string, Driver<unknown, unknown>>`, which rejects drivers with a typed input.
57
+ */
34
58
  export type DriverOverrides = Readonly<Record<string, AnyDriver>>;
35
- /** A side effect described as data, plus pure mappers from its outcome to messages. */
59
+ /**
60
+ * A side effect described as data, plus pure mappers from its outcome to messages. Commands
61
+ * that answer with no message (`focus()`, `call()`, `navigate()`) are `Command<never>`,
62
+ * which fits wherever a `Command<Msg>` is expected: no type argument needed.
63
+ */
36
64
  export interface Command<M> {
37
65
  readonly driver: AnyDriver;
38
66
  readonly input: unknown;
@@ -40,24 +68,38 @@ export interface Command<M> {
40
68
  readonly key?: string;
41
69
  readonly concurrency?: Concurrency;
42
70
  readonly onSuccess: (output: unknown) => M | undefined;
43
- /** If omitted, failures are logged and dropped. */
71
+ /** If omitted, a failure is reported to the error channel (ADR 0024, G0041). */
44
72
  readonly onFailure?: (error: unknown) => M | undefined;
45
73
  }
74
+ /**
75
+ * How a command's outcome becomes a message. Every field is optional: without `onSuccess` the
76
+ * command answers with nothing (`Command<never>`); without `onFailure` a failure is reported to
77
+ * the error channel (ADR 0024).
78
+ */
46
79
  export interface CommandHandlers<O, E, MS, MF = MS> {
47
- readonly onSuccess: (output: O) => MS | undefined;
80
+ readonly onSuccess?: (output: O) => MS | undefined;
48
81
  readonly onFailure?: (error: E) => MF | undefined;
49
82
  readonly key?: string;
50
83
  readonly concurrency?: Concurrency;
51
84
  }
52
85
  /**
53
86
  * What a reducer (or `init`) returns: new state, optionally with commands to run. Commands may
54
- * also answer with the framework message `IntentRejected` (e.g. `submitForm` in @gyral/http
87
+ * also answer with the framework message `IntentRejected` (e.g. `submitForm` in `@gyral/http`
55
88
  * when the server rejects a form), which goes to the optional `IntentRejected` reducer.
56
89
  */
57
90
  export type Next<S, M> = S | readonly [S, ReadonlyArray<Command<M | IntentRejected>>];
58
- /** Identity helper so driver literals infer `I`, `O` and `E`. */
59
- export declare function defineDriver<I, O, E = unknown>(driver: Driver<I, O, E>): Driver<I, O, E>;
60
- /** Builds a command whose mappers are typed by the driver's input, output and error. */
61
- export declare function command<I, O, E, MS, MF = MS>(driver: Driver<I, O, E>, input: I, handlers: CommandHandlers<O, E, MS, MF>): Command<MS | MF>;
91
+ /**
92
+ * Defines a driver. Given an implementation (`run`), it returns it as is, so literals infer
93
+ * `I`, `O` and `E`. Given only a name, it returns a typed **token**: commands built from it are
94
+ * typed, and it runs only when a provider (`provideDrivers`) or `el.drivers` supplies a driver of
95
+ * that name. A command whose token nothing provides fails with G0043, naming the driver.
96
+ */
97
+ export declare function defineDriver<I, O, E = unknown>(spec: Driver<I, O, E> | DriverToken<E> | string): Driver<I, O, E>;
98
+ /**
99
+ * Builds a command whose mappers are typed by the driver's input, output and error. Without
100
+ * handlers (or without `onSuccess`) it answers with no message: `command(log, line)` is a
101
+ * `Command<never>`, which fits any `Command<Msg>`.
102
+ */
103
+ export declare function command<I, O, E, const MS = never, const MF = MS>(driver: Driver<I, O, E>, input: I, handlers?: CommandHandlers<O, E, MS, MF>): Command<MS | MF>;
62
104
  /** Splits a reducer result into state and commands. State is never an array (ADR 0006). */
63
105
  export declare function splitNext<S, M>(next: Next<S, M>): readonly [S, ReadonlyArray<Command<M | IntentRejected>>];
package/dist/command.js CHANGED
@@ -1,17 +1,37 @@
1
- /** Identity helper so driver literals infer `I`, `O` and `E`. */
2
- export function defineDriver(driver) {
3
- return driver;
1
+ // Effects as data (docs/design-docs/0006-effects-and-drivers.md). Plain TypeScript only: the
2
+ // interpreter lives in ./internal/ (ADR 0015); `command()` registers it (features.ts), so apps
3
+ // that build no commands don't bundle it.
4
+ import { features } from './features.js';
5
+ import { hostInterpreter } from './internal/interpreter.js';
6
+ import { unprovided } from './internal/token.js';
7
+ /**
8
+ * Defines a driver. Given an implementation (`run`), it returns it as is, so literals infer
9
+ * `I`, `O` and `E`. Given only a name, it returns a typed **token**: commands built from it are
10
+ * typed, and it runs only when a provider (`provideDrivers`) or `el.drivers` supplies a driver of
11
+ * that name. A command whose token nothing provides fails with G0043, naming the driver.
12
+ */
13
+ export function defineDriver(spec) {
14
+ if (typeof spec === 'string')
15
+ return { name: spec, run: unprovided };
16
+ return 'run' in spec ? spec : { ...spec, run: unprovided };
4
17
  }
5
- /** Builds a command whose mappers are typed by the driver's input, output and error. */
6
- // Two message parameters so success and failure may produce different variants.
7
- export function command(driver, input, handlers) {
8
- const { onFailure, key, concurrency } = handlers;
18
+ const none = () => undefined;
19
+ /**
20
+ * Builds a command whose mappers are typed by the driver's input, output and error. Without
21
+ * handlers (or without `onSuccess`) it answers with no message: `command(log, line)` is a
22
+ * `Command<never>`, which fits any `Command<Msg>`.
23
+ */
24
+ // Two message parameters so success and failure may produce different variants; `const` keeps
25
+ // a mapper's `{ _tag: 'Loaded' }` literal, so no type arguments are needed.
26
+ export function command(driver, input, handlers = {}) {
27
+ features.commands = hostInterpreter;
28
+ const { onSuccess = none, onFailure, key, concurrency } = handlers;
29
+ // Sound: the interpreter only passes this driver's output and toError() result.
9
30
  return {
10
- driver: driver,
31
+ driver,
11
32
  input,
12
- // Sound: the interpreter only passes this driver's output and toError() result.
13
- onSuccess: (output) => handlers.onSuccess(output),
14
- ...(onFailure === undefined ? {} : { onFailure: (error) => onFailure(error) }),
33
+ onSuccess,
34
+ ...(onFailure && { onFailure }),
15
35
  ...(key === undefined ? {} : { key }),
16
36
  ...(concurrency === undefined ? {} : { concurrency }),
17
37
  };
@@ -1 +1 @@
1
- {"version":3,"file":"command.js","sourceRoot":"","sources":["../src/command.ts"],"names":[],"mappings":"AAqEA,iEAAiE;AACjE,MAAM,UAAU,YAAY,CAAoB,MAAuB;IACrE,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,wFAAwF;AACxF,gFAAgF;AAChF,MAAM,UAAU,OAAO,CACrB,MAAuB,EACvB,KAAQ,EACR,QAAuC;IAEvC,MAAM,EAAE,SAAS,EAAE,GAAG,EAAE,WAAW,EAAE,GAAG,QAAQ,CAAC;IACjD,OAAO;QACL,MAAM,EAAE,MAAM;QACd,KAAK;QACL,gFAAgF;QAChF,SAAS,EAAE,CAAC,MAAM,EAAE,EAAE,CAAC,QAAQ,CAAC,SAAS,CAAC,MAAW,CAAC;QACtD,GAAG,CAAC,SAAS,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,SAAS,EAAE,CAAC,KAAc,EAAE,EAAE,CAAC,SAAS,CAAC,KAAU,CAAC,EAAE,CAAC;QAC5F,GAAG,CAAC,GAAG,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,GAAG,EAAE,CAAC;QACrC,GAAG,CAAC,WAAW,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,WAAW,EAAE,CAAC;KACtD,CAAC;AACJ,CAAC;AAED,2FAA2F;AAC3F,MAAM,UAAU,SAAS,CACvB,IAAgB;IAEhB,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;QACvE,OAAO,IAAgE,CAAC;IAC1E,CAAC;IACD,OAAO,CAAC,IAAS,EAAE,EAAE,CAAC,CAAC;AACzB,CAAC","sourcesContent":["// Effects as data (docs/design-docs/0006-effects-and-drivers.md). Plain TypeScript only:\nimport type { IntentRejected } from './types.js';\n// the interpreter lives in ./internal/ (ADR 0015).\n\n/** How commands in the same lane interact. See ADR 0006 for the table. */\nexport type Concurrency = 'merge' | 'switch' | 'exhaust' | 'queue';\n\nexport interface RetryPolicy {\n /** Retries after the first failure. */\n readonly times: number;\n /** Delay before each retry (the base delay for exponential backoff). Default 0. */\n readonly delayMs?: number;\n readonly backoff?: 'fixed' | 'exponential';\n}\n\nexport interface DriverContext<O = unknown> {\n /** Aborts when the command is switched away or its component disconnects. */\n readonly signal: AbortSignal;\n /**\n * Delivers an extra result while the command runs (streaming drivers: routers, timers,\n * sockets). Each value goes through the command's `onSuccess`. Ignored once the command\n * has settled or been aborted. A streaming `run` usually never resolves; abort ends it.\n */\n readonly emit: (output: O) => void;\n}\n\n/** Performs one kind of side effect. A plain object: easy to fake in tests. */\nexport interface Driver<I, O, E = unknown> {\n readonly name: string;\n readonly run: (input: I, ctx: DriverContext<O>) => O | Promise<O>;\n /** Default policy for this driver's commands. Default `'merge'`. */\n readonly concurrency?: Concurrency;\n readonly retry?: RetryPolicy;\n /** Turns a thrown or rejected value into this driver's typed error. */\n readonly toError?: (cause: unknown) => E;\n}\n\n/** Any driver, with its input type erased. */\nexport type AnyDriver = Driver<never, unknown>;\n\n/** Drivers substituted by name (test fakes, configured instances). */\nexport type DriverOverrides = Readonly<Record<string, AnyDriver>>;\n\n/** A side effect described as data, plus pure mappers from its outcome to messages. */\nexport interface Command<M> {\n readonly driver: AnyDriver;\n readonly input: unknown;\n /** Concurrency lane. Default: the driver's name. */\n readonly key?: string;\n readonly concurrency?: Concurrency;\n readonly onSuccess: (output: unknown) => M | undefined;\n /** If omitted, failures are logged and dropped. */\n readonly onFailure?: (error: unknown) => M | undefined;\n}\n\nexport interface CommandHandlers<O, E, MS, MF = MS> {\n readonly onSuccess: (output: O) => MS | undefined;\n readonly onFailure?: (error: E) => MF | undefined;\n readonly key?: string;\n readonly concurrency?: Concurrency;\n}\n\n/**\n * What a reducer (or `init`) returns: new state, optionally with commands to run. Commands may\n * also answer with the framework message `IntentRejected` (e.g. `submitForm` in @gyral/http\n * when the server rejects a form), which goes to the optional `IntentRejected` reducer.\n */\nexport type Next<S, M> = S | readonly [S, ReadonlyArray<Command<M | IntentRejected>>];\n\n/** Identity helper so driver literals infer `I`, `O` and `E`. */\nexport function defineDriver<I, O, E = unknown>(driver: Driver<I, O, E>): Driver<I, O, E> {\n return driver;\n}\n\n/** Builds a command whose mappers are typed by the driver's input, output and error. */\n// Two message parameters so success and failure may produce different variants.\nexport function command<I, O, E, MS, MF = MS>(\n driver: Driver<I, O, E>,\n input: I,\n handlers: CommandHandlers<O, E, MS, MF>,\n): Command<MS | MF> {\n const { onFailure, key, concurrency } = handlers;\n return {\n driver: driver,\n input,\n // Sound: the interpreter only passes this driver's output and toError() result.\n onSuccess: (output) => handlers.onSuccess(output as O),\n ...(onFailure === undefined ? {} : { onFailure: (error: unknown) => onFailure(error as E) }),\n ...(key === undefined ? {} : { key }),\n ...(concurrency === undefined ? {} : { concurrency }),\n };\n}\n\n/** Splits a reducer result into state and commands. State is never an array (ADR 0006). */\nexport function splitNext<S, M>(\n next: Next<S, M>,\n): readonly [S, ReadonlyArray<Command<M | IntentRejected>>] {\n if (Array.isArray(next) && next.length === 2 && Array.isArray(next[1])) {\n return next as readonly [S, ReadonlyArray<Command<M | IntentRejected>>];\n }\n return [next as S, []];\n}\n"]}
1
+ {"version":3,"file":"command.js","sourceRoot":"","sources":["../src/command.ts"],"names":[],"mappings":"AAAA,6FAA6F;AAC7F,+FAA+F;AAC/F,0CAA0C;AAC1C,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAsGjD;;;;;GAKG;AACH,MAAM,UAAU,YAAY,CAC1B,IAA+C;IAE/C,IAAI,OAAO,IAAI,KAAK,QAAQ;QAAE,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,UAAU,EAAE,CAAC;IACrE,OAAO,KAAK,IAAI,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,GAAG,IAAI,EAAE,GAAG,EAAE,UAAU,EAAE,CAAC;AAC7D,CAAC;AAED,MAAM,IAAI,GAAG,GAAc,EAAE,CAAC,SAAS,CAAC;AAExC;;;;GAIG;AACH,8FAA8F;AAC9F,4EAA4E;AAC5E,MAAM,UAAU,OAAO,CACrB,MAAuB,EACvB,KAAQ,EACR,WAA0C,EAAE;IAE5C,QAAQ,CAAC,QAAQ,GAAG,eAAe,CAAC;IACpC,MAAM,EAAE,SAAS,GAAG,IAAI,EAAE,SAAS,EAAE,GAAG,EAAE,WAAW,EAAE,GAAG,QAAQ,CAAC;IACnE,gFAAgF;IAChF,OAAO;QACL,MAAM;QACN,KAAK;QACL,SAAS;QACT,GAAG,CAAC,SAAS,IAAI,EAAE,SAAS,EAAE,CAAC;QAC/B,GAAG,CAAC,GAAG,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,GAAG,EAAE,CAAC;QACrC,GAAG,CAAC,WAAW,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,WAAW,EAAE,CAAC;KAClC,CAAC;AACxB,CAAC;AAED,2FAA2F;AAC3F,MAAM,UAAU,SAAS,CACvB,IAAgB;IAEhB,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;QACvE,OAAO,IAAgE,CAAC;IAC1E,CAAC;IACD,OAAO,CAAC,IAAS,EAAE,EAAE,CAAC,CAAC;AACzB,CAAC","sourcesContent":["// Effects as data (docs/design-docs/0006-effects-and-drivers.md). Plain TypeScript only: the\n// interpreter lives in ./internal/ (ADR 0015); `command()` registers it (features.ts), so apps\n// that build no commands don't bundle it.\nimport { features } from './features.js';\nimport { hostInterpreter } from './internal/interpreter.js';\nimport { unprovided } from './internal/token.js';\nimport type { IntentRejected } from './types.js';\n\n/** How commands in the same lane interact. See ADR 0006 for the table. */\nexport type Concurrency = 'merge' | 'switch' | 'exhaust' | 'queue';\n\n/** How `retry(driver, policy)` retries a rejected run (retry.ts). `E`: the driver's error. */\nexport interface RetryPolicy<E = unknown> {\n /** Retries after the first failure. */\n readonly times: number;\n /** Delay before each retry (the base delay for exponential backoff). Default 0. */\n readonly delayMs?: number;\n readonly backoff?: 'fixed' | 'exponential';\n /** Full jitter: wait a random time between 0 and the computed delay, so clients spread out. */\n readonly jitter?: boolean;\n /**\n * Which failures to retry, given the driver's typed error (its `toError`, else the thrown\n * value). Default: every failure. For `@gyral/http`, `retryableHttpError`.\n */\n readonly retryIf?: (error: E) => boolean;\n}\n\nexport interface DriverContext<O = unknown> {\n /** Aborts when the command is switched away or its component disconnects. */\n readonly signal: AbortSignal;\n /**\n * Delivers an extra result while the command runs (streaming drivers: routers, timers,\n * sockets). Each value goes through the command's `onSuccess`. Ignored once the command\n * has settled or been aborted. A streaming `run` usually never resolves; abort ends it.\n */\n readonly emit: (output: O) => void;\n}\n\n/** Performs one kind of side effect. A plain object: easy to fake in tests. */\nexport interface Driver<I, O, E = unknown> {\n readonly name: string;\n readonly run: (input: I, ctx: DriverContext<O>) => O | Promise<O>;\n /** Default policy for this driver's commands. Default `'merge'`. */\n readonly concurrency?: Concurrency;\n /** Turns a thrown or rejected value into this driver's typed error. */\n readonly toError?: (cause: unknown) => E;\n}\n\n/**\n * Any driver, with its input type erased. Every `Driver<I, O, E>` (from `defineDriver`,\n * `subscription`, a test fake) is assignable to it as is: no cast.\n */\nexport type AnyDriver = Driver<never, unknown>;\n\n/**\n * A driver with no implementation of its own (`defineDriver<I, O, E>('session')`): commands built\n * from it are typed by `I`, `O` and `E`, and it runs only when `provideDrivers` or `el.drivers`\n * supplies a driver of that name (ADR 0006 addendum \"Driver tokens\").\n */\nexport interface DriverToken<E = unknown> {\n readonly name: string;\n readonly concurrency?: Concurrency;\n readonly toError?: (cause: unknown) => E;\n}\n\n/**\n * Drivers substituted by name (test fakes, configured instances): `el.drivers`,\n * `provideDrivers`. Annotate a driver map with this type (or `Record<string, AnyDriver>`), not\n * `Record<string, Driver<unknown, unknown>>`, which rejects drivers with a typed input.\n */\nexport type DriverOverrides = Readonly<Record<string, AnyDriver>>;\n\n/**\n * A side effect described as data, plus pure mappers from its outcome to messages. Commands\n * that answer with no message (`focus()`, `call()`, `navigate()`) are `Command<never>`,\n * which fits wherever a `Command<Msg>` is expected: no type argument needed.\n */\nexport interface Command<M> {\n readonly driver: AnyDriver;\n readonly input: unknown;\n /** Concurrency lane. Default: the driver's name. */\n readonly key?: string;\n readonly concurrency?: Concurrency;\n readonly onSuccess: (output: unknown) => M | undefined;\n /** If omitted, a failure is reported to the error channel (ADR 0024, G0041). */\n readonly onFailure?: (error: unknown) => M | undefined;\n}\n\n/**\n * How a command's outcome becomes a message. Every field is optional: without `onSuccess` the\n * command answers with nothing (`Command<never>`); without `onFailure` a failure is reported to\n * the error channel (ADR 0024).\n */\nexport interface CommandHandlers<O, E, MS, MF = MS> {\n readonly onSuccess?: (output: O) => MS | undefined;\n readonly onFailure?: (error: E) => MF | undefined;\n readonly key?: string;\n readonly concurrency?: Concurrency;\n}\n\n/**\n * What a reducer (or `init`) returns: new state, optionally with commands to run. Commands may\n * also answer with the framework message `IntentRejected` (e.g. `submitForm` in `@gyral/http`\n * when the server rejects a form), which goes to the optional `IntentRejected` reducer.\n */\nexport type Next<S, M> = S | readonly [S, ReadonlyArray<Command<M | IntentRejected>>];\n\n/**\n * Defines a driver. Given an implementation (`run`), it returns it as is, so literals infer\n * `I`, `O` and `E`. Given only a name, it returns a typed **token**: commands built from it are\n * typed, and it runs only when a provider (`provideDrivers`) or `el.drivers` supplies a driver of\n * that name. A command whose token nothing provides fails with G0043, naming the driver.\n */\nexport function defineDriver<I, O, E = unknown>(\n spec: Driver<I, O, E> | DriverToken<E> | string,\n): Driver<I, O, E> {\n if (typeof spec === 'string') return { name: spec, run: unprovided };\n return 'run' in spec ? spec : { ...spec, run: unprovided };\n}\n\nconst none = (): undefined => undefined;\n\n/**\n * Builds a command whose mappers are typed by the driver's input, output and error. Without\n * handlers (or without `onSuccess`) it answers with no message: `command(log, line)` is a\n * `Command<never>`, which fits any `Command<Msg>`.\n */\n// Two message parameters so success and failure may produce different variants; `const` keeps\n// a mapper's `{ _tag: 'Loaded' }` literal, so no type arguments are needed.\nexport function command<I, O, E, const MS = never, const MF = MS>(\n driver: Driver<I, O, E>,\n input: I,\n handlers: CommandHandlers<O, E, MS, MF> = {},\n): Command<MS | MF> {\n features.commands = hostInterpreter;\n const { onSuccess = none, onFailure, key, concurrency } = handlers;\n // Sound: the interpreter only passes this driver's output and toError() result.\n return {\n driver,\n input,\n onSuccess,\n ...(onFailure && { onFailure }),\n ...(key === undefined ? {} : { key }),\n ...(concurrency === undefined ? {} : { concurrency }),\n } as Command<MS | MF>;\n}\n\n/** Splits a reducer result into state and commands. State is never an array (ADR 0006). */\nexport function splitNext<S, M>(\n next: Next<S, M>,\n): readonly [S, ReadonlyArray<Command<M | IntentRejected>>] {\n if (Array.isArray(next) && next.length === 2 && Array.isArray(next[1])) {\n return next as readonly [S, ReadonlyArray<Command<M | IntentRejected>>];\n }\n return [next as S, []];\n}\n"]}
@@ -0,0 +1,23 @@
1
+ /** The `lang` to parse a module with, from its id (`this.parse(code, { lang })`). */
2
+ export declare const langOf: (id: string) => "js" | "jsx" | "ts" | "tsx";
3
+ /** An ESTree node: `start`/`end` are UTF-16 offsets into the module's code. */
4
+ export interface Node {
5
+ readonly type: string;
6
+ readonly start: number;
7
+ readonly end: number;
8
+ readonly [key: string]: unknown;
9
+ }
10
+ export declare const isNode: (value: unknown) => value is Node;
11
+ export declare const nodeAt: (node: Node, key: string) => Node | undefined;
12
+ /** The node or nodes at `key` (an array, or a single node). */
13
+ export declare const nodesAt: (node: Node, key: string) => Node[];
14
+ /** The child nodes of `node` that can contain runtime code, in source order. */
15
+ export declare function children(node: Node): Node[];
16
+ /** The names a binding pattern declares (`a`, `{ a, b: [c] }`, `...d`, `e = 1`). */
17
+ export declare function patternNames(pattern: Node | undefined): string[];
18
+ export declare const isFunction: (node: Node) => boolean;
19
+ /**
20
+ * The names `node` declares for its own scope, or undefined when it opens no scope. The
21
+ * Program scope is left out: the imported binding lives there.
22
+ */
23
+ export declare function scopeNames(node: Node): string[] | undefined;
@@ -0,0 +1,149 @@
1
+ // A minimal view of the ESTree AST that Rolldown's `this.parse` returns (oxc, TypeScript
2
+ // included), for the template compiler's scanner (scan.ts): generic child iteration, the
3
+ // names a binding pattern declares, and the names each scope declares, so a local variable
4
+ // that shadows the imported `html` is never mistaken for it.
5
+ /** The `lang` to parse a module with, from its id (`this.parse(code, { lang })`). */
6
+ export const langOf = (id) => /\.[cm]?tsx$/.test(id) ? 'tsx' : /\.[cm]?ts$/.test(id) ? 'ts' : id.endsWith('x') ? 'jsx' : 'js';
7
+ export const isNode = (value) => typeof value === 'object' &&
8
+ value !== null &&
9
+ typeof value.type === 'string';
10
+ export const nodeAt = (node, key) => {
11
+ const value = node[key];
12
+ return isNode(value) ? value : undefined;
13
+ };
14
+ /** The node or nodes at `key` (an array, or a single node). */
15
+ export const nodesAt = (node, key) => {
16
+ const value = node[key];
17
+ return Array.isArray(value) ? value.filter(isNode) : isNode(value) ? [value] : [];
18
+ };
19
+ /** TypeScript-only keys: type annotations never reference a value. */
20
+ const TYPE_KEYS = new Set([
21
+ 'typeAnnotation',
22
+ 'typeArguments',
23
+ 'typeParameters',
24
+ 'returnType',
25
+ 'superTypeArguments',
26
+ 'implements',
27
+ ]);
28
+ /** TS nodes that wrap a runtime expression; every other `TS*` node is type-only. */
29
+ const TS_VALUE = new Set([
30
+ 'TSAsExpression',
31
+ 'TSSatisfiesExpression',
32
+ 'TSNonNullExpression',
33
+ 'TSTypeAssertion',
34
+ 'TSInstantiationExpression',
35
+ 'TSExportAssignment',
36
+ ]);
37
+ /** TS declarations whose members are runtime values (`enum E { A = 'a' }`). */
38
+ const TS_RUNTIME = new Set(['TSEnumDeclaration', 'TSEnumBody', 'TSEnumMember']);
39
+ /** The child nodes of `node` that can contain runtime code, in source order. */
40
+ export function children(node) {
41
+ if (node.type.startsWith('TS') && !TS_RUNTIME.has(node.type)) {
42
+ if (TS_VALUE.has(node.type))
43
+ return nodesAt(node, 'expression');
44
+ if (node.type === 'TSParameterProperty')
45
+ return nodesAt(node, 'parameter');
46
+ if (node.type === 'TSModuleDeclaration')
47
+ return nodesAt(node, 'body');
48
+ if (node.type === 'TSModuleBlock')
49
+ return nodesAt(node, 'body');
50
+ return [];
51
+ }
52
+ const out = [];
53
+ for (const key in node) {
54
+ if (key === 'type' || key === 'start' || key === 'end' || TYPE_KEYS.has(key))
55
+ continue;
56
+ const value = node[key];
57
+ if (Array.isArray(value))
58
+ out.push(...value.filter(isNode));
59
+ else if (isNode(value))
60
+ out.push(value);
61
+ }
62
+ return out.sort((a, b) => a.start - b.start);
63
+ }
64
+ /** The names a binding pattern declares (`a`, `{ a, b: [c] }`, `...d`, `e = 1`). */
65
+ export function patternNames(pattern) {
66
+ if (pattern === undefined)
67
+ return [];
68
+ switch (pattern.type) {
69
+ case 'Identifier':
70
+ return [pattern['name']];
71
+ case 'ObjectPattern':
72
+ return nodesAt(pattern, 'properties').flatMap((p) => p.type === 'RestElement'
73
+ ? patternNames(nodeAt(p, 'argument'))
74
+ : patternNames(nodeAt(p, 'value')));
75
+ case 'ArrayPattern':
76
+ return nodesAt(pattern, 'elements').flatMap(patternNames);
77
+ case 'RestElement':
78
+ return patternNames(nodeAt(pattern, 'argument'));
79
+ case 'AssignmentPattern':
80
+ return patternNames(nodeAt(pattern, 'left'));
81
+ case 'TSParameterProperty':
82
+ return patternNames(nodeAt(pattern, 'parameter'));
83
+ default:
84
+ return [];
85
+ }
86
+ }
87
+ const FUNCTIONS = new Set(['FunctionDeclaration', 'FunctionExpression', 'ArrowFunctionExpression']);
88
+ export const isFunction = (node) => FUNCTIONS.has(node.type);
89
+ /** `var` names declared anywhere in a function body (hoisted), not crossing nested functions. */
90
+ function varNames(node, out) {
91
+ if (node.type === 'VariableDeclaration' && node['kind'] === 'var') {
92
+ for (const d of nodesAt(node, 'declarations'))
93
+ out.push(...patternNames(nodeAt(d, 'id')));
94
+ }
95
+ for (const child of children(node))
96
+ if (!isFunction(child))
97
+ varNames(child, out);
98
+ }
99
+ /** Block-scoped names declared directly in a list of statements. */
100
+ function lexicalNames(statements) {
101
+ return statements.flatMap((s) => {
102
+ if (s.type === 'VariableDeclaration' && s['kind'] !== 'var') {
103
+ return nodesAt(s, 'declarations').flatMap((d) => patternNames(nodeAt(d, 'id')));
104
+ }
105
+ if (s.type === 'FunctionDeclaration' || s.type === 'ClassDeclaration') {
106
+ return patternNames(nodeAt(s, 'id'));
107
+ }
108
+ return [];
109
+ });
110
+ }
111
+ /**
112
+ * The names `node` declares for its own scope, or undefined when it opens no scope. The
113
+ * Program scope is left out: the imported binding lives there.
114
+ */
115
+ export function scopeNames(node) {
116
+ switch (node.type) {
117
+ case 'FunctionDeclaration':
118
+ case 'FunctionExpression':
119
+ case 'ArrowFunctionExpression': {
120
+ const names = nodesAt(node, 'params').flatMap(patternNames);
121
+ if (node.type === 'FunctionExpression')
122
+ names.push(...patternNames(nodeAt(node, 'id')));
123
+ const body = nodeAt(node, 'body');
124
+ if (body?.type === 'BlockStatement') {
125
+ varNames(body, names);
126
+ names.push(...lexicalNames(nodesAt(body, 'body')));
127
+ }
128
+ return names;
129
+ }
130
+ case 'BlockStatement':
131
+ case 'StaticBlock':
132
+ return lexicalNames(nodesAt(node, 'body'));
133
+ case 'SwitchStatement':
134
+ return lexicalNames(nodesAt(node, 'cases').flatMap((c) => nodesAt(c, 'consequent')));
135
+ case 'ForStatement':
136
+ case 'ForInStatement':
137
+ case 'ForOfStatement': {
138
+ const head = nodeAt(node, node.type === 'ForStatement' ? 'init' : 'left');
139
+ return head === undefined ? [] : lexicalNames([head]);
140
+ }
141
+ case 'CatchClause':
142
+ return patternNames(nodeAt(node, 'param'));
143
+ case 'ClassExpression':
144
+ return patternNames(nodeAt(node, 'id'));
145
+ default:
146
+ return undefined;
147
+ }
148
+ }
149
+ //# sourceMappingURL=ast.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ast.js","sourceRoot":"","sources":["../../src/compiler/ast.ts"],"names":[],"mappings":"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","sourcesContent":["// A minimal view of the ESTree AST that Rolldown's `this.parse` returns (oxc, TypeScript\n// included), for the template compiler's scanner (scan.ts): generic child iteration, the\n// names a binding pattern declares, and the names each scope declares, so a local variable\n// that shadows the imported `html` is never mistaken for it.\n\n/** The `lang` to parse a module with, from its id (`this.parse(code, { lang })`). */\nexport const langOf = (id: string): 'js' | 'jsx' | 'ts' | 'tsx' =>\n /\\.[cm]?tsx$/.test(id) ? 'tsx' : /\\.[cm]?ts$/.test(id) ? 'ts' : id.endsWith('x') ? 'jsx' : 'js';\n\n/** An ESTree node: `start`/`end` are UTF-16 offsets into the module's code. */\nexport interface Node {\n readonly type: string;\n readonly start: number;\n readonly end: number;\n readonly [key: string]: unknown;\n}\n\nexport const isNode = (value: unknown): value is Node =>\n typeof value === 'object' &&\n value !== null &&\n typeof (value as { type?: unknown }).type === 'string';\n\nexport const nodeAt = (node: Node, key: string): Node | undefined => {\n const value = node[key];\n return isNode(value) ? value : undefined;\n};\n\n/** The node or nodes at `key` (an array, or a single node). */\nexport const nodesAt = (node: Node, key: string): Node[] => {\n const value = node[key];\n return Array.isArray(value) ? value.filter(isNode) : isNode(value) ? [value] : [];\n};\n\n/** TypeScript-only keys: type annotations never reference a value. */\nconst TYPE_KEYS = new Set([\n 'typeAnnotation',\n 'typeArguments',\n 'typeParameters',\n 'returnType',\n 'superTypeArguments',\n 'implements',\n]);\n\n/** TS nodes that wrap a runtime expression; every other `TS*` node is type-only. */\nconst TS_VALUE = new Set([\n 'TSAsExpression',\n 'TSSatisfiesExpression',\n 'TSNonNullExpression',\n 'TSTypeAssertion',\n 'TSInstantiationExpression',\n 'TSExportAssignment',\n]);\n\n/** TS declarations whose members are runtime values (`enum E { A = 'a' }`). */\nconst TS_RUNTIME = new Set(['TSEnumDeclaration', 'TSEnumBody', 'TSEnumMember']);\n\n/** The child nodes of `node` that can contain runtime code, in source order. */\nexport function children(node: Node): Node[] {\n if (node.type.startsWith('TS') && !TS_RUNTIME.has(node.type)) {\n if (TS_VALUE.has(node.type)) return nodesAt(node, 'expression');\n if (node.type === 'TSParameterProperty') return nodesAt(node, 'parameter');\n if (node.type === 'TSModuleDeclaration') return nodesAt(node, 'body');\n if (node.type === 'TSModuleBlock') return nodesAt(node, 'body');\n return [];\n }\n const out: Node[] = [];\n for (const key in node) {\n if (key === 'type' || key === 'start' || key === 'end' || TYPE_KEYS.has(key)) continue;\n const value = node[key];\n if (Array.isArray(value)) out.push(...value.filter(isNode));\n else if (isNode(value)) out.push(value);\n }\n return out.sort((a, b) => a.start - b.start);\n}\n\n/** The names a binding pattern declares (`a`, `{ a, b: [c] }`, `...d`, `e = 1`). */\nexport function patternNames(pattern: Node | undefined): string[] {\n if (pattern === undefined) return [];\n switch (pattern.type) {\n case 'Identifier':\n return [pattern['name'] as string];\n case 'ObjectPattern':\n return nodesAt(pattern, 'properties').flatMap((p) =>\n p.type === 'RestElement'\n ? patternNames(nodeAt(p, 'argument'))\n : patternNames(nodeAt(p, 'value')),\n );\n case 'ArrayPattern':\n return nodesAt(pattern, 'elements').flatMap(patternNames);\n case 'RestElement':\n return patternNames(nodeAt(pattern, 'argument'));\n case 'AssignmentPattern':\n return patternNames(nodeAt(pattern, 'left'));\n case 'TSParameterProperty':\n return patternNames(nodeAt(pattern, 'parameter'));\n default:\n return [];\n }\n}\n\nconst FUNCTIONS = new Set(['FunctionDeclaration', 'FunctionExpression', 'ArrowFunctionExpression']);\n\nexport const isFunction = (node: Node): boolean => FUNCTIONS.has(node.type);\n\n/** `var` names declared anywhere in a function body (hoisted), not crossing nested functions. */\nfunction varNames(node: Node, out: string[]): void {\n if (node.type === 'VariableDeclaration' && node['kind'] === 'var') {\n for (const d of nodesAt(node, 'declarations')) out.push(...patternNames(nodeAt(d, 'id')));\n }\n for (const child of children(node)) if (!isFunction(child)) varNames(child, out);\n}\n\n/** Block-scoped names declared directly in a list of statements. */\nfunction lexicalNames(statements: readonly Node[]): string[] {\n return statements.flatMap((s) => {\n if (s.type === 'VariableDeclaration' && s['kind'] !== 'var') {\n return nodesAt(s, 'declarations').flatMap((d) => patternNames(nodeAt(d, 'id')));\n }\n if (s.type === 'FunctionDeclaration' || s.type === 'ClassDeclaration') {\n return patternNames(nodeAt(s, 'id'));\n }\n return [];\n });\n}\n\n/**\n * The names `node` declares for its own scope, or undefined when it opens no scope. The\n * Program scope is left out: the imported binding lives there.\n */\nexport function scopeNames(node: Node): string[] | undefined {\n switch (node.type) {\n case 'FunctionDeclaration':\n case 'FunctionExpression':\n case 'ArrowFunctionExpression': {\n const names = nodesAt(node, 'params').flatMap(patternNames);\n if (node.type === 'FunctionExpression') names.push(...patternNames(nodeAt(node, 'id')));\n const body = nodeAt(node, 'body');\n if (body?.type === 'BlockStatement') {\n varNames(body, names);\n names.push(...lexicalNames(nodesAt(body, 'body')));\n }\n return names;\n }\n case 'BlockStatement':\n case 'StaticBlock':\n return lexicalNames(nodesAt(node, 'body'));\n case 'SwitchStatement':\n return lexicalNames(nodesAt(node, 'cases').flatMap((c) => nodesAt(c, 'consequent')));\n case 'ForStatement':\n case 'ForInStatement':\n case 'ForOfStatement': {\n const head = nodeAt(node, node.type === 'ForStatement' ? 'init' : 'left');\n return head === undefined ? [] : lexicalNames([head]);\n }\n case 'CatchClause':\n return patternNames(nodeAt(node, 'param'));\n case 'ClassExpression':\n return patternNames(nodeAt(node, 'id'));\n default:\n return undefined;\n }\n}\n"]}
@@ -0,0 +1,41 @@
1
+ import type { Node } from './ast.js';
2
+ import { type Parse5 } from './parse5-check.js';
3
+ import type { HtmlImport, Tag } from './scan.js';
4
+ import { type Edit, type Lines, type SourceMap } from './source.js';
5
+ /** A build error at `start`–`end` of the module (the plugin adds the code frame). */
6
+ export declare class CompileError extends Error {
7
+ readonly start: number;
8
+ readonly end: number;
9
+ constructor(start: number, end: number, message: string);
10
+ }
11
+ export interface CompileInput {
12
+ readonly lines: Lines;
13
+ /** Module id, and its path relative to the root (for messages). */
14
+ readonly id: string;
15
+ readonly file: string;
16
+ readonly sites: readonly {
17
+ readonly node: Node;
18
+ readonly binding: HtmlImport;
19
+ readonly tag: Tag;
20
+ }[];
21
+ /** Server build: keep the server segments. */
22
+ readonly ssr: boolean;
23
+ /**
24
+ * Keep template ids: SSR and development builds (development markers, the hydration id
25
+ * check). A production client compares templates by identity, so its objects go without.
26
+ */
27
+ readonly ids: boolean;
28
+ readonly parse5: Parse5 | undefined;
29
+ /** Other edits to apply in the same pass (prop-schemas.ts); dropped inside a call site. */
30
+ readonly extra?: readonly Edit[];
31
+ /** Template id → normalized strings and call site, for the whole build (collisions). */
32
+ readonly seen: Map<string, {
33
+ readonly strings: string;
34
+ readonly loc: string;
35
+ }>;
36
+ }
37
+ /** Rewrites every call site in the module; nested templates inside values are included. */
38
+ export declare function compileModule(input: CompileInput): {
39
+ code: string;
40
+ map: SourceMap;
41
+ };
@@ -0,0 +1,148 @@
1
+ // Compiles one module's `html` and `svg` call sites (view/01-templates.md "Compiled"): each
2
+ // call site's cooked strings go through the same normalizer as the runtime path (so ids match),
3
+ // parse5 double-checks rule 7, one module-level constant is hoisted per template object
4
+ // (without its id in production client builds: the renderer compares those by identity), and
5
+ // the call becomes `compiled(<const>, [values…])`, or `compiledSvg(…)` for an svg template.
6
+ // Line breaks inside a rewritten template are kept, so every following line keeps its number;
7
+ // the source map covers columns.
8
+ import { analyze, TemplateError } from '../view/index.js';
9
+ import { nodeAt, nodesAt } from './ast.js';
10
+ import { checkWithParse5 } from './parse5-check.js';
11
+ import { splice } from './source.js';
12
+ /** Where a source's `compiled` lives when its `html` module isn't the one to import it from. */
13
+ const COMPILED_ENTRIES = {
14
+ '@gyral/core': '@gyral/core/compiled',
15
+ };
16
+ /** A build error at `start`–`end` of the module (the plugin adds the code frame). */
17
+ export class CompileError extends Error {
18
+ constructor(start, end, message) {
19
+ super(message);
20
+ this.start = start;
21
+ this.end = end;
22
+ }
23
+ }
24
+ /**
25
+ * The template object as emitted: no `loc` (production), no `segments` in client builds, no
26
+ * `id` unless `ids` (01 "Template ids": random base-36 text that gzip can't shrink). Its fields
27
+ * are already compact (numeric part kinds, tuples, `server` only when true; 01), so the code
28
+ * needs no decoding.
29
+ */
30
+ function emitted(template, ssr, ids) {
31
+ const { id, html, parts, server, svg, segments, staticStyles } = template;
32
+ const client = {
33
+ ...(ids ? { id } : {}),
34
+ html,
35
+ parts,
36
+ ...(server === true ? { server } : {}),
37
+ ...(svg === true ? { svg } : {}),
38
+ };
39
+ if (!ssr)
40
+ return client;
41
+ return staticStyles === undefined
42
+ ? { ...client, segments }
43
+ : { ...client, segments, staticStyles };
44
+ }
45
+ const newlines = (text) => '\n'.repeat(text.split('\n').length - 1);
46
+ /** Edits turning html`a${x}b${y}c` into `callee(name, [x, y])`, keeping line breaks. */
47
+ function siteEdits(code, node, callee, name) {
48
+ const values = nodesAt(nodeAt(node, 'quasi') ?? node, 'expressions');
49
+ const first = values[0];
50
+ const last = values.at(-1);
51
+ if (first === undefined || last === undefined) {
52
+ const nl = newlines(code.slice(node.start, node.end));
53
+ return [{ start: node.start, end: node.end, text: `${callee}(${name}, [${nl}])` }];
54
+ }
55
+ const edit = (start, end, text) => ({
56
+ start,
57
+ end,
58
+ text: text + newlines(code.slice(start, end)),
59
+ });
60
+ const edits = [edit(node.start, first.start, `${callee}(${name}, [`)];
61
+ for (let k = 1; k < values.length; k++) {
62
+ const prev = values[k - 1];
63
+ const next = values[k];
64
+ if (prev !== undefined && next !== undefined)
65
+ edits.push(edit(prev.end, next.start, ', '));
66
+ }
67
+ edits.push({
68
+ start: last.end,
69
+ end: node.end,
70
+ text: `${newlines(code.slice(last.end, node.end))}])`,
71
+ });
72
+ return edits;
73
+ }
74
+ /** The cooked strings of a tagged template (what the tag receives at runtime). */
75
+ function cookedStrings(node, tag) {
76
+ return nodesAt(nodeAt(node, 'quasi') ?? node, 'quasis').map((q) => {
77
+ const cooked = q['value']?.cooked;
78
+ if (typeof cooked !== 'string') {
79
+ throw new CompileError(q.start, q.end, `This ${tag} template has an invalid escape sequence, so it has no string value at ` +
80
+ 'runtime. Fix the escape (write \\\\ for a backslash).');
81
+ }
82
+ return cooked;
83
+ });
84
+ }
85
+ /** Rewrites every call site in the module; nested templates inside values are included. */
86
+ export function compileModule(input) {
87
+ const { lines, sites, seen } = input;
88
+ const { code } = lines;
89
+ let prefix = '_gyral$';
90
+ for (let n = 1; code.includes(prefix); n++)
91
+ prefix = `_gyral${String(n)}$`;
92
+ /** `compiled from "entry"` → the import's local name, per tag function and entry. */
93
+ const callees = new Map();
94
+ const imports = [];
95
+ const consts = new Map();
96
+ const decls = [];
97
+ const edits = [];
98
+ for (const { node, binding, tag } of sites) {
99
+ const { line, column } = lines.position(node.start);
100
+ const loc = `${input.file}:${String(line)}:${String(column + 1)}`;
101
+ let analysis;
102
+ try {
103
+ analysis = analyze(cookedStrings(node, tag), loc, tag === 'svg');
104
+ }
105
+ catch (error) {
106
+ if (error instanceof TemplateError)
107
+ throw new CompileError(node.start, node.end, error.message);
108
+ throw error;
109
+ }
110
+ const { template, shape } = analysis;
111
+ const strings = JSON.stringify(analysis.strings);
112
+ const known = seen.get(template.id);
113
+ if (known !== undefined && known.strings !== strings) {
114
+ throw new CompileError(node.start, node.end, `Two different templates share the id ${template.id} (this one and ${known.loc}), so ` +
115
+ `server output and hydration could confuse them. Change one slightly (for example add ` +
116
+ `a class) and report the collision (view/01-templates.md "Template ids").`);
117
+ }
118
+ seen.set(template.id, { strings, loc });
119
+ const repaired = input.parse5 && checkWithParse5(input.parse5, template, shape);
120
+ if (repaired)
121
+ throw new CompileError(node.start, node.end, repaired.message);
122
+ let name = consts.get(template.id);
123
+ if (name === undefined) {
124
+ name = `${prefix}t${String(consts.size)}`;
125
+ consts.set(template.id, name);
126
+ decls.push(`const ${name} = ${JSON.stringify(emitted(template, input.ssr, input.ids))};`);
127
+ }
128
+ const entry = COMPILED_ENTRIES[binding.specifier] ?? binding.specifier;
129
+ const exported = tag === 'svg' ? 'compiledSvg' : 'compiled';
130
+ const from = `${exported} from ${JSON.stringify(entry)}`;
131
+ let callee = callees.get(from);
132
+ if (callee === undefined) {
133
+ callee = `${prefix}${exported}${callees.size === 0 ? '' : String(callees.size)}`;
134
+ callees.set(from, callee);
135
+ imports.push(`import { ${exported} as ${callee} } from ${JSON.stringify(entry)};`);
136
+ }
137
+ edits.push(...siteEdits(code, node, callee, name));
138
+ }
139
+ for (const e of input.extra ?? []) {
140
+ if (!sites.some(({ node }) => e.start < node.end && e.end > node.start))
141
+ edits.push(e);
142
+ }
143
+ // Prepended to the first line (after a hashbang), so no line moves.
144
+ const at = code.startsWith('#!') ? code.indexOf('\n') + 1 : 0;
145
+ edits.unshift({ start: at, end: at, text: [...imports, ...decls].join('') });
146
+ return splice(lines, edits, input.id);
147
+ }
148
+ //# sourceMappingURL=compile.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compile.js","sourceRoot":"","sources":["../../src/compiler/compile.ts"],"names":[],"mappings":"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","sourcesContent":["// Compiles one module's `html` and `svg` call sites (view/01-templates.md \"Compiled\"): each\n// call site's cooked strings go through the same normalizer as the runtime path (so ids match),\n// parse5 double-checks rule 7, one module-level constant is hoisted per template object\n// (without its id in production client builds: the renderer compares those by identity), and\n// the call becomes `compiled(<const>, [values…])`, or `compiledSvg(…)` for an svg template.\n// Line breaks inside a rewritten template are kept, so every following line keeps its number;\n// the source map covers columns.\nimport { analyze, TemplateError, type TemplateObject } from '../view/index.js';\nimport type { Node } from './ast.js';\nimport { nodeAt, nodesAt } from './ast.js';\nimport { checkWithParse5, type Parse5 } from './parse5-check.js';\nimport type { HtmlImport, Tag } from './scan.js';\nimport { splice, type Edit, type Lines, type SourceMap } from './source.js';\n\n/** Where a source's `compiled` lives when its `html` module isn't the one to import it from. */\nconst COMPILED_ENTRIES: Readonly<Record<string, string>> = {\n '@gyral/core': '@gyral/core/compiled',\n};\n\n/** A build error at `start`–`end` of the module (the plugin adds the code frame). */\nexport class CompileError extends Error {\n constructor(\n readonly start: number,\n readonly end: number,\n message: string,\n ) {\n super(message);\n }\n}\n\nexport interface CompileInput {\n readonly lines: Lines;\n /** Module id, and its path relative to the root (for messages). */\n readonly id: string;\n readonly file: string;\n readonly sites: readonly {\n readonly node: Node;\n readonly binding: HtmlImport;\n readonly tag: Tag;\n }[];\n /** Server build: keep the server segments. */\n readonly ssr: boolean;\n /**\n * Keep template ids: SSR and development builds (development markers, the hydration id\n * check). A production client compares templates by identity, so its objects go without.\n */\n readonly ids: boolean;\n readonly parse5: Parse5 | undefined;\n /** Other edits to apply in the same pass (prop-schemas.ts); dropped inside a call site. */\n readonly extra?: readonly Edit[];\n /** Template id → normalized strings and call site, for the whole build (collisions). */\n readonly seen: Map<string, { readonly strings: string; readonly loc: string }>;\n}\n\n/**\n * The template object as emitted: no `loc` (production), no `segments` in client builds, no\n * `id` unless `ids` (01 \"Template ids\": random base-36 text that gzip can't shrink). Its fields\n * are already compact (numeric part kinds, tuples, `server` only when true; 01), so the code\n * needs no decoding.\n */\nfunction emitted(template: TemplateObject, ssr: boolean, ids: boolean): object {\n const { id, html, parts, server, svg, segments, staticStyles } = template;\n const client = {\n ...(ids ? { id } : {}),\n html,\n parts,\n ...(server === true ? { server } : {}),\n ...(svg === true ? { svg } : {}),\n };\n if (!ssr) return client;\n return staticStyles === undefined\n ? { ...client, segments }\n : { ...client, segments, staticStyles };\n}\n\nconst newlines = (text: string): string => '\\n'.repeat(text.split('\\n').length - 1);\n\n/** Edits turning html`a${x}b${y}c` into `callee(name, [x, y])`, keeping line breaks. */\nfunction siteEdits(code: string, node: Node, callee: string, name: string): Edit[] {\n const values = nodesAt(nodeAt(node, 'quasi') ?? node, 'expressions');\n const first = values[0];\n const last = values.at(-1);\n if (first === undefined || last === undefined) {\n const nl = newlines(code.slice(node.start, node.end));\n return [{ start: node.start, end: node.end, text: `${callee}(${name}, [${nl}])` }];\n }\n const edit = (start: number, end: number, text: string): Edit => ({\n start,\n end,\n text: text + newlines(code.slice(start, end)),\n });\n const edits = [edit(node.start, first.start, `${callee}(${name}, [`)];\n for (let k = 1; k < values.length; k++) {\n const prev = values[k - 1];\n const next = values[k];\n if (prev !== undefined && next !== undefined) edits.push(edit(prev.end, next.start, ', '));\n }\n edits.push({\n start: last.end,\n end: node.end,\n text: `${newlines(code.slice(last.end, node.end))}])`,\n });\n return edits;\n}\n\n/** The cooked strings of a tagged template (what the tag receives at runtime). */\nfunction cookedStrings(node: Node, tag: Tag): string[] {\n return nodesAt(nodeAt(node, 'quasi') ?? node, 'quasis').map((q) => {\n const cooked = (q['value'] as { cooked?: unknown } | undefined)?.cooked;\n if (typeof cooked !== 'string') {\n throw new CompileError(\n q.start,\n q.end,\n `This ${tag} template has an invalid escape sequence, so it has no string value at ` +\n 'runtime. Fix the escape (write \\\\\\\\ for a backslash).',\n );\n }\n return cooked;\n });\n}\n\n/** Rewrites every call site in the module; nested templates inside values are included. */\nexport function compileModule(input: CompileInput): { code: string; map: SourceMap } {\n const { lines, sites, seen } = input;\n const { code } = lines;\n let prefix = '_gyral$';\n for (let n = 1; code.includes(prefix); n++) prefix = `_gyral${String(n)}$`;\n /** `compiled from \"entry\"` → the import's local name, per tag function and entry. */\n const callees = new Map<string, string>();\n const imports: string[] = [];\n const consts = new Map<string, string>();\n const decls: string[] = [];\n const edits: Edit[] = [];\n for (const { node, binding, tag } of sites) {\n const { line, column } = lines.position(node.start);\n const loc = `${input.file}:${String(line)}:${String(column + 1)}`;\n let analysis;\n try {\n analysis = analyze(cookedStrings(node, tag), loc, tag === 'svg');\n } catch (error) {\n if (error instanceof TemplateError)\n throw new CompileError(node.start, node.end, error.message);\n throw error;\n }\n const { template, shape } = analysis;\n const strings = JSON.stringify(analysis.strings);\n const known = seen.get(template.id);\n if (known !== undefined && known.strings !== strings) {\n throw new CompileError(\n node.start,\n node.end,\n `Two different templates share the id ${template.id} (this one and ${known.loc}), so ` +\n `server output and hydration could confuse them. Change one slightly (for example add ` +\n `a class) and report the collision (view/01-templates.md \"Template ids\").`,\n );\n }\n seen.set(template.id, { strings, loc });\n const repaired = input.parse5 && checkWithParse5(input.parse5, template, shape);\n if (repaired) throw new CompileError(node.start, node.end, repaired.message);\n let name = consts.get(template.id);\n if (name === undefined) {\n name = `${prefix}t${String(consts.size)}`;\n consts.set(template.id, name);\n decls.push(`const ${name} = ${JSON.stringify(emitted(template, input.ssr, input.ids))};`);\n }\n const entry = COMPILED_ENTRIES[binding.specifier] ?? binding.specifier;\n const exported = tag === 'svg' ? 'compiledSvg' : 'compiled';\n const from = `${exported} from ${JSON.stringify(entry)}`;\n let callee = callees.get(from);\n if (callee === undefined) {\n callee = `${prefix}${exported}${callees.size === 0 ? '' : String(callees.size)}`;\n callees.set(from, callee);\n imports.push(`import { ${exported} as ${callee} } from ${JSON.stringify(entry)};`);\n }\n edits.push(...siteEdits(code, node, callee, name));\n }\n for (const e of input.extra ?? []) {\n if (!sites.some(({ node }) => e.start < node.end && e.end > node.start)) edits.push(e);\n }\n // Prepended to the first line (after a hashbang), so no line moves.\n const at = code.startsWith('#!') ? code.indexOf('\\n') + 1 : 0;\n edits.unshift({ start: at, end: at, text: [...imports, ...decls].join('') });\n return splice(lines, edits, input.id);\n}\n"]}
@@ -0,0 +1,7 @@
1
+ import type { Rollup } from 'vite';
2
+ /**
3
+ * Modules statically retained by the app's inputs (transitively). A component among them is
4
+ * defined at startup by the app's own entry; giving it to the loader as well would make the
5
+ * bundler split it out of the entry into a chunk of its own.
6
+ */
7
+ export declare function staticallyReachable(ctx: Rollup.PluginContext, inputs: readonly string[]): Promise<Set<string>>;