@adukiorg/anza 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (349) hide show
  1. package/CHANGELOG.md +137 -0
  2. package/README.md +215 -0
  3. package/bin/anza.js +63 -0
  4. package/bin/create.js +150 -0
  5. package/importmap.json +72 -0
  6. package/package.json +100 -0
  7. package/src/core/animations/index.js +55 -0
  8. package/src/core/animations/play.js +111 -0
  9. package/src/core/animations/registry.js +54 -0
  10. package/src/core/animations/scroll.js +50 -0
  11. package/src/core/animations/tokens.js +58 -0
  12. package/src/core/animations/usage.md +301 -0
  13. package/src/core/animations/waapi.js +86 -0
  14. package/src/core/api/cache.js +120 -0
  15. package/src/core/api/caches/glob.js +24 -0
  16. package/src/core/api/caches/index.js +118 -0
  17. package/src/core/api/events/index.js +75 -0
  18. package/src/core/api/fetch.js +99 -0
  19. package/src/core/api/index.js +158 -0
  20. package/src/core/api/pipeline.js +98 -0
  21. package/src/core/api/plan.md +209 -0
  22. package/src/core/api/prefixes/index.js +66 -0
  23. package/src/core/api/retry.js +69 -0
  24. package/src/core/api/stream.js +127 -0
  25. package/src/core/api/upload.js +180 -0
  26. package/src/core/api/usage.md +206 -0
  27. package/src/core/events/bus.js +38 -0
  28. package/src/core/events/delegate.js +79 -0
  29. package/src/core/events/index.js +26 -0
  30. package/src/core/events/listen.js +50 -0
  31. package/src/core/events/missing.md +103 -0
  32. package/src/core/events/once.js +49 -0
  33. package/src/core/events/plan.md +177 -0
  34. package/src/core/events/types/index.js +34 -0
  35. package/src/core/events/usage.md +107 -0
  36. package/src/core/offline/bridge.js +51 -0
  37. package/src/core/offline/clock.js +100 -0
  38. package/src/core/offline/connectivity.js +116 -0
  39. package/src/core/offline/index.js +41 -0
  40. package/src/core/offline/missing.md +89 -0
  41. package/src/core/offline/plan.md +143 -0
  42. package/src/core/offline/queue.js +168 -0
  43. package/src/core/offline/state.js +18 -0
  44. package/src/core/offline/sync.js +106 -0
  45. package/src/core/offline/usage.md +273 -0
  46. package/src/core/platform/guard.js +104 -0
  47. package/src/core/platform/index.js +42 -0
  48. package/src/core/platform/missing.md +119 -0
  49. package/src/core/platform/platform.d.ts +88 -0
  50. package/src/core/platform/polyfills/anchor.js +79 -0
  51. package/src/core/platform/polyfills/navigation.js +142 -0
  52. package/src/core/platform/polyfills/popover.js +142 -0
  53. package/src/core/platform/polyfills/scheduler.js +194 -0
  54. package/src/core/platform/polyfills/shadow.js +35 -0
  55. package/src/core/platform/polyfills/urlpattern.js +119 -0
  56. package/src/core/platform/supports.js +186 -0
  57. package/src/core/platform/usage.md +287 -0
  58. package/src/core/router/cache.js +95 -0
  59. package/src/core/router/container.js +146 -0
  60. package/src/core/router/handler.js +52 -0
  61. package/src/core/router/history.js +120 -0
  62. package/src/core/router/index.js +158 -0
  63. package/src/core/router/intercept.js +376 -0
  64. package/src/core/router/match.js +145 -0
  65. package/src/core/router/missing.md +716 -0
  66. package/src/core/router/outlet.js +139 -0
  67. package/src/core/router/plan.md +370 -0
  68. package/src/core/router/sync/index.js +16 -0
  69. package/src/core/router/sync/tab.js +115 -0
  70. package/src/core/router/sync/transport.js +139 -0
  71. package/src/core/router/transitions.js +59 -0
  72. package/src/core/router/usage.md +773 -0
  73. package/src/core/security/crypto.js +159 -0
  74. package/src/core/security/index.js +49 -0
  75. package/src/core/security/missing.md +97 -0
  76. package/src/core/security/permissions.js +64 -0
  77. package/src/core/security/sanitize.js +100 -0
  78. package/src/core/security/usage.md +283 -0
  79. package/src/core/state/derived.js +117 -0
  80. package/src/core/state/index.js +23 -0
  81. package/src/core/state/missing.md +165 -0
  82. package/src/core/state/persist.js +284 -0
  83. package/src/core/state/store.js +308 -0
  84. package/src/core/state/sync.js +46 -0
  85. package/src/core/state/usage.md +440 -0
  86. package/src/core/storage/cache.js +83 -0
  87. package/src/core/storage/idb.js +196 -0
  88. package/src/core/storage/index.js +373 -0
  89. package/src/core/storage/lru.js +107 -0
  90. package/src/core/storage/missing.md +165 -0
  91. package/src/core/storage/opfs.js +190 -0
  92. package/src/core/storage/plan.md +69 -0
  93. package/src/core/storage/quota.js +69 -0
  94. package/src/core/storage/usage.md +226 -0
  95. package/src/core/ui/base.js +50 -0
  96. package/src/core/ui/define/container.js +82 -0
  97. package/src/core/ui/define/define.js +12 -0
  98. package/src/core/ui/define/element.js +390 -0
  99. package/src/core/ui/define/index.js +9 -0
  100. package/src/core/ui/define/orchestrator.js +105 -0
  101. package/src/core/ui/define/proxy.js +644 -0
  102. package/src/core/ui/define/state.js +6 -0
  103. package/src/core/ui/define/utils.js +134 -0
  104. package/src/core/ui/implementation.md +170 -0
  105. package/src/core/ui/index.js +41 -0
  106. package/src/core/ui/observe.js +117 -0
  107. package/src/core/ui/plan.md +510 -0
  108. package/src/core/ui/schedule.js +60 -0
  109. package/src/core/ui/template.js +37 -0
  110. package/src/core/ui/transitions.js +37 -0
  111. package/src/core/ui/ui.types.md +890 -0
  112. package/src/core/ui/usage.md +1124 -0
  113. package/src/core/ui/watch.md +346 -0
  114. package/src/core/workers/broadcast.js +138 -0
  115. package/src/core/workers/dedicated.js +153 -0
  116. package/src/core/workers/index.js +169 -0
  117. package/src/core/workers/locks.js +160 -0
  118. package/src/core/workers/offscreen.js +166 -0
  119. package/src/core/workers/plan.md +381 -0
  120. package/src/core/workers/pool.js +267 -0
  121. package/src/core/workers/shared.js +137 -0
  122. package/src/core/workers/usage.md +622 -0
  123. package/src/elements/base.js +12 -0
  124. package/src/elements/data/card/index.html +9 -0
  125. package/src/elements/data/card/index.js +19 -0
  126. package/src/elements/data/card/index.tags.json +1 -0
  127. package/src/elements/data/card/style.css +46 -0
  128. package/src/elements/data/chart/index.html +1 -0
  129. package/src/elements/data/chart/index.js +143 -0
  130. package/src/elements/data/chart/index.tags.json +1 -0
  131. package/src/elements/data/chart/style.css +13 -0
  132. package/src/elements/data/list/index.html +3 -0
  133. package/src/elements/data/list/index.js +19 -0
  134. package/src/elements/data/list/index.tags.json +1 -0
  135. package/src/elements/data/list/style.css +39 -0
  136. package/src/elements/data/stat/index.html +9 -0
  137. package/src/elements/data/stat/index.js +19 -0
  138. package/src/elements/data/stat/index.tags.json +1 -0
  139. package/src/elements/data/stat/style.css +50 -0
  140. package/src/elements/data/table/index.html +1 -0
  141. package/src/elements/data/table/index.js +16 -0
  142. package/src/elements/data/table/index.tags.json +1 -0
  143. package/src/elements/data/table/style.css +50 -0
  144. package/src/elements/feedback/alert/index.html +11 -0
  145. package/src/elements/feedback/alert/index.js +28 -0
  146. package/src/elements/feedback/alert/index.tags.json +1 -0
  147. package/src/elements/feedback/alert/style.css +75 -0
  148. package/src/elements/feedback/empty/index.html +13 -0
  149. package/src/elements/feedback/empty/index.js +34 -0
  150. package/src/elements/feedback/empty/index.tags.json +1 -0
  151. package/src/elements/feedback/empty/style.css +45 -0
  152. package/src/elements/feedback/progress/index.html +7 -0
  153. package/src/elements/feedback/progress/index.js +46 -0
  154. package/src/elements/feedback/progress/index.tags.json +1 -0
  155. package/src/elements/feedback/progress/style.css +36 -0
  156. package/src/elements/feedback/skeleton/index.html +1 -0
  157. package/src/elements/feedback/skeleton/index.js +78 -0
  158. package/src/elements/feedback/skeleton/index.tags.json +1 -0
  159. package/src/elements/feedback/skeleton/style.css +28 -0
  160. package/src/elements/feedback/toast/index.html +3 -0
  161. package/src/elements/feedback/toast/index.js +65 -0
  162. package/src/elements/feedback/toast/index.tags.json +1 -0
  163. package/src/elements/feedback/toast/style.css +36 -0
  164. package/src/elements/forms/checkbox/index.html +7 -0
  165. package/src/elements/forms/checkbox/index.js +104 -0
  166. package/src/elements/forms/checkbox/index.tags.json +1 -0
  167. package/src/elements/forms/checkbox/style.css +86 -0
  168. package/src/elements/forms/field/index.html +13 -0
  169. package/src/elements/forms/field/index.js +42 -0
  170. package/src/elements/forms/field/index.tags.json +1 -0
  171. package/src/elements/forms/field/style.css +42 -0
  172. package/src/elements/forms/form/index.html +3 -0
  173. package/src/elements/forms/form/index.js +122 -0
  174. package/src/elements/forms/form/index.tags.json +1 -0
  175. package/src/elements/forms/form/style.css +11 -0
  176. package/src/elements/forms/input/index.html +4 -0
  177. package/src/elements/forms/input/index.js +103 -0
  178. package/src/elements/forms/input/index.tags.json +1 -0
  179. package/src/elements/forms/input/style.css +39 -0
  180. package/src/elements/forms/radio/index.html +4 -0
  181. package/src/elements/forms/radio/index.js +109 -0
  182. package/src/elements/forms/radio/index.tags.json +1 -0
  183. package/src/elements/forms/radio/style.css +65 -0
  184. package/src/elements/forms/select/index.html +9 -0
  185. package/src/elements/forms/select/index.js +114 -0
  186. package/src/elements/forms/select/index.tags.json +1 -0
  187. package/src/elements/forms/select/style.css +95 -0
  188. package/src/elements/forms/textarea/index.html +4 -0
  189. package/src/elements/forms/textarea/index.js +115 -0
  190. package/src/elements/forms/textarea/index.tags.json +1 -0
  191. package/src/elements/forms/textarea/style.css +46 -0
  192. package/src/elements/forms/toggle/index.html +4 -0
  193. package/src/elements/forms/toggle/index.js +89 -0
  194. package/src/elements/forms/toggle/index.tags.json +1 -0
  195. package/src/elements/forms/toggle/style.css +63 -0
  196. package/src/elements/forms/upload/index.html +13 -0
  197. package/src/elements/forms/upload/index.js +120 -0
  198. package/src/elements/forms/upload/index.tags.json +1 -0
  199. package/src/elements/forms/upload/style.css +61 -0
  200. package/src/elements/index.js +71 -0
  201. package/src/elements/layout/app/index.html +7 -0
  202. package/src/elements/layout/app/index.js +16 -0
  203. package/src/elements/layout/app/index.tags.json +1 -0
  204. package/src/elements/layout/app/style.css +41 -0
  205. package/src/elements/layout/grid/index.html +3 -0
  206. package/src/elements/layout/grid/index.js +41 -0
  207. package/src/elements/layout/grid/index.tags.json +1 -0
  208. package/src/elements/layout/grid/style.css +12 -0
  209. package/src/elements/layout/header/index.html +8 -0
  210. package/src/elements/layout/header/index.js +16 -0
  211. package/src/elements/layout/header/index.tags.json +1 -0
  212. package/src/elements/layout/header/style.css +28 -0
  213. package/src/elements/layout/scroll/index.html +3 -0
  214. package/src/elements/layout/scroll/index.js +19 -0
  215. package/src/elements/layout/scroll/index.tags.json +1 -0
  216. package/src/elements/layout/scroll/style.css +24 -0
  217. package/src/elements/layout/sidebar/index.html +3 -0
  218. package/src/elements/layout/sidebar/index.js +24 -0
  219. package/src/elements/layout/sidebar/index.tags.json +1 -0
  220. package/src/elements/layout/sidebar/style.css +30 -0
  221. package/src/elements/layout/split/index.html +3 -0
  222. package/src/elements/layout/split/index.js +18 -0
  223. package/src/elements/layout/split/index.tags.json +1 -0
  224. package/src/elements/layout/split/style.css +28 -0
  225. package/src/elements/layout/stack/index.html +3 -0
  226. package/src/elements/layout/stack/index.js +31 -0
  227. package/src/elements/layout/stack/index.tags.json +1 -0
  228. package/src/elements/layout/stack/style.css +15 -0
  229. package/src/elements/layout/surface/index.html +3 -0
  230. package/src/elements/layout/surface/index.js +19 -0
  231. package/src/elements/layout/surface/index.tags.json +1 -0
  232. package/src/elements/layout/surface/style.css +29 -0
  233. package/src/elements/navigation/breadcrumb/index.html +5 -0
  234. package/src/elements/navigation/breadcrumb/index.js +16 -0
  235. package/src/elements/navigation/breadcrumb/index.tags.json +1 -0
  236. package/src/elements/navigation/breadcrumb/style.css +36 -0
  237. package/src/elements/navigation/nav/index.html +3 -0
  238. package/src/elements/navigation/nav/index.js +24 -0
  239. package/src/elements/navigation/nav/index.tags.json +1 -0
  240. package/src/elements/navigation/nav/style.css +38 -0
  241. package/src/elements/navigation/pagination/index.html +3 -0
  242. package/src/elements/navigation/pagination/index.js +94 -0
  243. package/src/elements/navigation/pagination/index.tags.json +1 -0
  244. package/src/elements/navigation/pagination/style.css +39 -0
  245. package/src/elements/navigation/steps/index.html +6 -0
  246. package/src/elements/navigation/steps/index.js +64 -0
  247. package/src/elements/navigation/steps/index.tags.json +1 -0
  248. package/src/elements/navigation/steps/style.css +78 -0
  249. package/src/elements/navigation/tabs/index.html +6 -0
  250. package/src/elements/navigation/tabs/index.js +132 -0
  251. package/src/elements/navigation/tabs/index.tags.json +1 -0
  252. package/src/elements/navigation/tabs/style.css +52 -0
  253. package/src/elements/overlay/dialog/index.html +5 -0
  254. package/src/elements/overlay/dialog/index.js +57 -0
  255. package/src/elements/overlay/dialog/index.tags.json +1 -0
  256. package/src/elements/overlay/dialog/style.css +31 -0
  257. package/src/elements/overlay/drawer/index.html +3 -0
  258. package/src/elements/overlay/drawer/index.js +56 -0
  259. package/src/elements/overlay/drawer/index.tags.json +1 -0
  260. package/src/elements/overlay/drawer/style.css +48 -0
  261. package/src/elements/overlay/menu/index.html +3 -0
  262. package/src/elements/overlay/menu/index.js +107 -0
  263. package/src/elements/overlay/menu/index.tags.json +1 -0
  264. package/src/elements/overlay/menu/style.css +43 -0
  265. package/src/elements/overlay/popover/index.html +3 -0
  266. package/src/elements/overlay/popover/index.js +44 -0
  267. package/src/elements/overlay/popover/index.tags.json +1 -0
  268. package/src/elements/overlay/popover/style.css +21 -0
  269. package/src/elements/overlay/sheet/index.html +8 -0
  270. package/src/elements/overlay/sheet/index.js +105 -0
  271. package/src/elements/overlay/sheet/index.tags.json +1 -0
  272. package/src/elements/overlay/sheet/style.css +64 -0
  273. package/src/elements/overlay/tooltip/index.html +6 -0
  274. package/src/elements/overlay/tooltip/index.js +16 -0
  275. package/src/elements/overlay/tooltip/index.tags.json +1 -0
  276. package/src/elements/overlay/tooltip/style.css +41 -0
  277. package/src/elements/primitives/avatar/index.html +2 -0
  278. package/src/elements/primitives/avatar/index.js +79 -0
  279. package/src/elements/primitives/avatar/index.tags.json +1 -0
  280. package/src/elements/primitives/avatar/style.css +36 -0
  281. package/src/elements/primitives/badge/index.html +3 -0
  282. package/src/elements/primitives/badge/index.js +20 -0
  283. package/src/elements/primitives/badge/index.tags.json +1 -0
  284. package/src/elements/primitives/badge/style.css +67 -0
  285. package/src/elements/primitives/button/index.html +3 -0
  286. package/src/elements/primitives/button/index.js +61 -0
  287. package/src/elements/primitives/button/index.tags.json +1 -0
  288. package/src/elements/primitives/button/style.css +66 -0
  289. package/src/elements/primitives/divider/index.html +1 -0
  290. package/src/elements/primitives/divider/index.js +43 -0
  291. package/src/elements/primitives/divider/index.tags.json +1 -0
  292. package/src/elements/primitives/divider/style.css +39 -0
  293. package/src/elements/primitives/icon/index.html +3 -0
  294. package/src/elements/primitives/icon/index.js +66 -0
  295. package/src/elements/primitives/icon/index.tags.json +1 -0
  296. package/src/elements/primitives/icon/style.css +20 -0
  297. package/src/elements/primitives/link/index.html +3 -0
  298. package/src/elements/primitives/link/index.js +129 -0
  299. package/src/elements/primitives/link/index.tags.json +1 -0
  300. package/src/elements/primitives/link/style.css +40 -0
  301. package/src/elements/primitives/spinner/index.html +1 -0
  302. package/src/elements/primitives/spinner/index.js +62 -0
  303. package/src/elements/primitives/spinner/index.tags.json +1 -0
  304. package/src/elements/primitives/spinner/style.css +20 -0
  305. package/src/elements/primitives/text/index.html +1 -0
  306. package/src/elements/primitives/text/index.js +79 -0
  307. package/src/elements/primitives/text/index.tags.json +1 -0
  308. package/src/elements/primitives/text/style.css +25 -0
  309. package/src/index.js +23 -0
  310. package/src/styles/base.css +66 -0
  311. package/src/styles/index.css +10 -0
  312. package/src/styles/layers.css +9 -0
  313. package/src/styles/reset.css +66 -0
  314. package/src/sw/activate.js +51 -0
  315. package/src/sw/expire.js +47 -0
  316. package/src/sw/index.js +28 -0
  317. package/src/sw/install.js +35 -0
  318. package/src/sw/push.js +58 -0
  319. package/src/sw/queue.js +60 -0
  320. package/src/sw/routes.js +71 -0
  321. package/src/sw/strategies.js +247 -0
  322. package/src/sw/sync.js +80 -0
  323. package/src/tokens/index.css +26 -0
  324. package/src/tokens/primitives/colors.css +54 -0
  325. package/src/tokens/primitives/motion.css +34 -0
  326. package/src/tokens/primitives/radius.css +16 -0
  327. package/src/tokens/primitives/shadow.css +34 -0
  328. package/src/tokens/primitives/spacing.css +27 -0
  329. package/src/tokens/primitives/typography.css +46 -0
  330. package/src/tokens/primitives/zindex.css +18 -0
  331. package/src/tokens/registered/colors.css +133 -0
  332. package/src/tokens/registered/dimensions.css +31 -0
  333. package/src/tokens/semantic/components.css +125 -0
  334. package/src/tokens/semantic/contrast.css +33 -0
  335. package/src/tokens/semantic/dark.css +61 -0
  336. package/src/tokens/semantic/light.css +64 -0
  337. package/types/core/animations/index.d.ts +52 -0
  338. package/types/core/api/index.d.ts +68 -0
  339. package/types/core/events/index.d.ts +50 -0
  340. package/types/core/offline/index.d.ts +68 -0
  341. package/types/core/platform/index.d.ts +60 -0
  342. package/types/core/router/index.d.ts +203 -0
  343. package/types/core/security/index.d.ts +33 -0
  344. package/types/core/state/index.d.ts +68 -0
  345. package/types/core/storage/index.d.ts +40 -0
  346. package/types/core/ui/index.d.ts +446 -0
  347. package/types/core/workers/index.d.ts +221 -0
  348. package/types/elements/index.d.ts +150 -0
  349. package/types/index.d.ts +18 -0
package/CHANGELOG.md ADDED
@@ -0,0 +1,137 @@
1
+ # Changelog
2
+
3
+ All notable changes to `@adukiorg/anza` will be documented here.
4
+
5
+ Format follows [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
6
+ Versioning follows [Semantic Versioning](https://semver.org/).
7
+
8
+ ---
9
+
10
+ ## [Unreleased]
11
+
12
+ ### Planned
13
+
14
+ - Full element library documentation (`src/elements/`)
15
+ - Integration with external bundlers/compilers
16
+
17
+ ---
18
+
19
+ ## [0.2.0] — 2026-06-07
20
+
21
+ ### Added
22
+
23
+ #### Compiler — `anza`
24
+ - **Dependency Graph Walking**: Automated dependency resolution of ESM imports/exports.
25
+ - **Tree-Shaking**: Outputs only referenced files to `dist/`, excluding unused code.
26
+ - **Automatic Inline Importmaps**: Optimal `<script type="importmap">` generated and injected inline into HTML entry points.
27
+ - **Relative Component Styles & Templates**: Parses relative template and stylesheet file paths referenced in `ui.element` relative to `import.meta.url`.
28
+ - **Concurrent File Watcher**: Recompiles output on file modifications.
29
+ - **SSE HMR Dev Server**: CSS hot-swapping and HTML/JS auto-reloading via Server-Sent Events (SSE).
30
+ - **Nested /dist Routing**: Added router nested service mapping in Axum dev server for development path parity.
31
+
32
+ #### Structure
33
+ - **Monorepo Split**: Reorganized files into `/library` (NPM package), `/sample` (demo application), and `/tools` (Rust compiler).
34
+
35
+ #### Sample
36
+ - **Cyberpunk Blog SPA**: Features reactive store, category filters, instant search, likes count persistence, details page with lightweight custom markdown renderer, post publishing, and post deletion.
37
+
38
+ ---
39
+
40
+ ## [0.1.0] — 2026-05-27
41
+
42
+ ### Added
43
+
44
+ #### Package
45
+
46
+ - Published as `@adukiorg/anza` — pure browser ESM, zero build step
47
+ - Scoped subpath exports for every core module (`/api`, `/state`, `/storage`, etc.)
48
+ - `"type": "module"` — fully native ESM, no CommonJS wrapper
49
+ - `npm test` via `@web/test-runner` (real Chromium, no jsdom)
50
+ - `npm run serve` via `@web/dev-server` on port 8080
51
+
52
+ #### Core — `@adukiorg/anza/api`
53
+
54
+ - `execute()` — fetch wrapper with AbortSignal, timeout, and `scheduler.postTask` integration
55
+ - `PlatformError` — unified error shape across all network failures
56
+ - `retry()` — exponential backoff with jitter and AbortSignal support
57
+ - `stream()` — async generator streaming over NDJSON responses
58
+ - `createNDJSONTransform()` — reusable `TransformStream` for NDJSON parsing
59
+ - `upload()` — multipart file upload with progress events
60
+ - `pipeline` — composable request/response middleware pipeline
61
+ - Cache strategies: `cache-first`, `network-first`, `stale-while-revalidate`
62
+
63
+ #### Core — `@adukiorg/anza/state`
64
+
65
+ - `ReactiveStore` — Proxy-based reactive state with microtask-batched notifications
66
+ - `setActiveSubscriber` / `getActiveSubscriber` — dependency tracking context
67
+ - `derived()` — auto-tracked computed values that re-evaluate on dependency changes
68
+ - `sync()` — BroadcastChannel cross-tab state synchronization
69
+
70
+ #### Core — `@adukiorg/anza/events`
71
+
72
+ - `EventBus` — typed pub/sub with wildcard patterns and AbortSignal cleanup
73
+ - `events` — singleton global event bus instance
74
+
75
+ #### Core — `@adukiorg/anza/router`
76
+
77
+ - `register()` / `match()` — URL pattern registration and matching
78
+ - `clear()` / `getRoutes()` — route registry management
79
+ - `addGuard()` — async navigation guard hooks
80
+ - `setNotFound()` — 404 handler
81
+ - `setup()` — bootstraps native Navigation API interception
82
+ - Full programmatic history API: `navigate`, `replace`, `back`, `forward`, `go`, `current`, `entries`
83
+ - `renderOutlet()` — declarative route outlet rendering
84
+
85
+ #### Core — `@adukiorg/anza/storage`
86
+
87
+ - `Database` — Promise-wrapped IndexedDB with sequential migrations
88
+ - `LRUCache` / `WeakLRUCache` — in-memory LRU caches with optional TTL
89
+ - `storage` — unified tiered facade: memory → IndexedDB → Cache API → OPFS
90
+ - `quota` — storage estimate and persistence request helpers
91
+
92
+ #### Core — `@adukiorg/anza/offline`
93
+
94
+ - `queue` — IndexedDB-backed offline operation queue with FIFO dequeue
95
+ - `check()` / `subscribe()` — connectivity detection and change subscriptions
96
+
97
+ #### Core — `@adukiorg/anza/animations`
98
+
99
+ - `animate()` — WAAPI wrapper with AbortSignal and easing controls
100
+ - `stagger()` — staggered multi-element animation groups with `finished` promise
101
+
102
+ #### Core — `@adukiorg/anza/workers`
103
+
104
+ - `lock()` — Web Locks API facade with timeout and AbortSignal support
105
+ - `WorkerPool` — managed pool of Web Workers with task queue and concurrency limits
106
+
107
+ #### Core — `@adukiorg/anza/security`
108
+
109
+ - `sanitize()` — XSS-safe HTML sanitizer using `DOMParser`
110
+ - `uuid()` — `crypto.randomUUID()` wrapper
111
+ - `hash()` — SHA-256/384/512 via Web Crypto API
112
+ - `generateKey()` / `deriveKey()` — AES-GCM key generation and PBKDF2 derivation
113
+ - `encrypt()` / `decrypt()` — AES-GCM symmetric encryption/decryption
114
+
115
+ #### Core — `@adukiorg/anza/platform`
116
+
117
+ - `supports` — feature detection registry for 30+ browser APIs
118
+ - `reset()` — cache reset utility (used in tests)
119
+
120
+ #### Core — `@adukiorg/anza/ui`
121
+
122
+ - `BaseElement` — Shadow DOM base class for all custom elements
123
+ - Design token cascade: primitive → semantic → component token layers
124
+
125
+ #### Tests
126
+
127
+ - 26 test suites, 70 assertions — all running in real Chromium via `@web/test-runner`
128
+ - Browser-native import maps injected per test run — no Node.js module resolution
129
+
130
+ #### Blog Demo
131
+
132
+ - `blog/` — sample SPA demonstrating state, storage, offline queue, and animations
133
+ - Import map mirrors the published `@adukiorg/anza/*` subpath exports exactly
134
+
135
+ [Unreleased]: https://github.com/aduki-org/native/compare/v0.2.0...HEAD
136
+ [0.2.0]: https://github.com/aduki-org/native/compare/v0.1.0...v0.2.0
137
+ [0.1.0]: https://github.com/aduki-org/native/releases/tag/v0.1.0
package/README.md ADDED
@@ -0,0 +1,215 @@
1
+ # @adukiorg/anza
2
+
3
+ > Anza web platform library. Pure browser ESM — no bundler, no framework lock-in. A small local Rust toolchain resolves your import graph into a minimal, browser-native `dist/`.
4
+
5
+ [![npm](https://img.shields.io/npm/v/@adukiorg/anza)](https://www.npmjs.com/package/@adukiorg/anza)
6
+ [![license](https://img.shields.io/npm/l/@adukiorg/anza)](./LICENSE)
7
+ [![tests](https://img.shields.io/badge/tests-237%20passing-brightgreen)](#testing)
8
+
9
+ ---
10
+
11
+ ## What is this?
12
+
13
+ `@adukiorg/anza` is a modular, zero-dependency platform library built entirely on top of browser-native APIs:
14
+
15
+ | Module | What it wraps |
16
+ | --- | --- |
17
+ | `/api` | `fetch`, Streams API, `scheduler.postTask` |
18
+ | `/state` | ES Proxy, `queueMicrotask`, `BroadcastChannel` |
19
+ | `/events` | Custom pub/sub with AbortSignal cleanup |
20
+ | `/router` | Navigation API, History API |
21
+ | `/storage` | IndexedDB, Cache API, OPFS, LRU memory |
22
+ | `/offline` | IDB-backed operation queue, `navigator.onLine` |
23
+ | `/animations` | WAAPI (`element.animate`), stagger groups |
24
+ | `/workers` | Web Locks API, Web Workers pool |
25
+ | `/security` | Web Crypto API, `DOMParser` XSS sanitizer |
26
+ | `/platform` | Feature detection for 30+ browser APIs |
27
+ | `/ui` | Shadow DOM base element, design token cascade |
28
+ | `/elements` | Custom element library |
29
+
30
+ No virtual DOM. No transpilation. The library is authored as plain `.js` files in `library/src/`. The bundled-in Rust toolchain (`tools/`) walks your ESM `import` graph from your entry points and emits **only the modules you actually use** into `dist/`, preserving a folder structure the browser resolves natively.
31
+
32
+ ---
33
+
34
+ ## Installation
35
+
36
+ To install `@adukiorg/anza` in your project:
37
+
38
+ ```bash
39
+ npm install @adukiorg/anza
40
+ ```
41
+
42
+ ---
43
+
44
+ ## Workspace Structure
45
+
46
+ The codebase is organized as a monorepo containing:
47
+
48
+ - **`library/`**: The core package codebase (`src/`, `tests/`, `package.json`, etc.).
49
+ - **`sample/`**: A sample application demonstrating reactive state, routing, and component separation in action.
50
+ - **`tools/`**: The Rust compiler toolchain codebase (`anza`).
51
+ - **`scripts/`**: Toolchain build and release helper scripts.
52
+
53
+ ---
54
+
55
+ ## Building the Toolchain & Running the Sample
56
+
57
+ The compiler (`anza`) is a native Rust CLI that manages the build pipeline.
58
+
59
+ ### 1. Build the compiler
60
+ From the workspace root directory:
61
+ ```bash
62
+ node scripts/build.js
63
+ ```
64
+ This builds the release binary into `tools/target/release/anza`.
65
+
66
+ ### 2. Run the Sample Application
67
+ Navigate into the sample project:
68
+ ```bash
69
+ cd sample
70
+ npm install # Links to the local library package
71
+ npm run build # Performs graph resolution and emits output to dist/
72
+ npm run dev # Starts dev server on port 8080 with HMR and routing fallbacks
73
+ ```
74
+
75
+ ---
76
+
77
+ ## What the Toolchain Does
78
+
79
+ - **Graph Walking**: Resolves the full import graph starting from your entry points (`src/index.js` by default, plus module scripts found in HTML templates).
80
+ - **Tree-Shaking**: Copies only the reached modules into `dist/`. Unreferenced files and assets are completely excluded.
81
+ - **Automatic Inline Importmap**: Analyzes import references and automatically generates/injects an optimal `<script type="importmap">` tag inline in your HTML files.
82
+ - **Static Asset Copying**: Automatically copies templates (`.html`) and stylesheets (`.css`) referenced by your components.
83
+ - **Strict Validation**: Fails the build on unresolved imports, syntax errors, or invalid component prop declarations.
84
+ - **HMR Dev Server**: Serves your files with a SSE live-reload listener. Modifying a CSS file hot-swaps it in place; HTML/JS modifications trigger a fast page reload.
85
+
86
+ ---
87
+
88
+ ## Splitting a Component Across Files
89
+
90
+ You can separate a component's logical code, templates, and styles into separate files for clean maintainability. The compiler resolves the relative template and stylesheet paths, processes them, and emits them to `dist/`:
91
+
92
+ ### `ui-button/template.html`
93
+ ```html
94
+ <button class="btn" ref="button">
95
+ <slot></slot>
96
+ </button>
97
+ ```
98
+
99
+ ### `ui-button/style.css`
100
+ ```css
101
+ :host { display: inline-block; }
102
+ .btn { background: var(--color-primary); color: white; border: none; }
103
+ ```
104
+
105
+ ### `ui-button/index.js`
106
+ ```js
107
+ import { ui } from '@adukiorg/anza/ui';
108
+
109
+ ui.element('ui-button', {
110
+ template: './template.html',
111
+ style: './style.css',
112
+ props: {
113
+ disabled: { type: Boolean, default: false }
114
+ },
115
+ mount({ el, refs, on }) {
116
+ on.click('[ref="button"]', () => {
117
+ console.log('Button clicked!');
118
+ });
119
+ }
120
+ }, import.meta.url);
121
+ ```
122
+
123
+ ---
124
+
125
+ ## Quick Examples
126
+
127
+ ### Reactive State
128
+
129
+ ```js
130
+ import { state } from '@adukiorg/anza/state';
131
+
132
+ const store = state.create({ count: 0, theme: 'dark' });
133
+
134
+ store.subscribe('count', () => {
135
+ console.log('count changed to', store.get('count'));
136
+ });
137
+
138
+ store.set('count', 1); // fires after microtask flush
139
+ store.set('count', 2); // batched — only one notification fires
140
+ ```
141
+
142
+ ### Network Requests
143
+
144
+ ```js
145
+ import { api, PlatformError } from '@adukiorg/anza/api';
146
+
147
+ try {
148
+ const data = await api.get('https://api.example.com/posts');
149
+ console.log(data);
150
+ } catch (err) {
151
+ if (err instanceof PlatformError) {
152
+ console.error(err.code, err.message); // 'NETWORK_TIMEOUT', 'HTTP_ERROR', etc.
153
+ }
154
+ }
155
+ ```
156
+
157
+ ### IndexedDB Storage
158
+
159
+ ```js
160
+ import { Database } from '@adukiorg/anza/storage';
161
+
162
+ const db = new Database('myapp', 1, [
163
+ (db) => db.createObjectStore('posts')
164
+ ]);
165
+
166
+ await db.open();
167
+ await db.set('posts', 'post-1', { title: 'Hello', content: '...' });
168
+ const post = await db.get('posts', 'post-1');
169
+ ```
170
+
171
+ ### Animations
172
+
173
+ ```js
174
+ import { animate, stagger } from '@adukiorg/anza/animations';
175
+
176
+ // Single element
177
+ animate(el, [{ opacity: 0 }, { opacity: 1 }], { duration: 300 });
178
+
179
+ // Staggered group
180
+ const cards = document.querySelectorAll('.card');
181
+ stagger(Array.from(cards), [
182
+ { transform: 'translateY(20px)', opacity: 0 },
183
+ { transform: 'translateY(0)', opacity: 1 }
184
+ ], { duration: 250, staggerDelay: 60 });
185
+ ```
186
+
187
+ ### Client-Side Router
188
+
189
+ ```js
190
+ import { register, navigate } from '@adukiorg/anza/router';
191
+
192
+ register('/posts/:id', async ({ params }) => {
193
+ const post = await fetchPost(params.id);
194
+ renderPost(post);
195
+ });
196
+
197
+ navigate('/posts/42');
198
+ ```
199
+
200
+ ---
201
+
202
+ ## Testing
203
+
204
+ Tests run in **real Chromium** via `@web/test-runner` — no jsdom or node mocks.
205
+
206
+ ```bash
207
+ cd library
208
+ npm test
209
+ ```
210
+
211
+ ---
212
+
213
+ ## License
214
+
215
+ [MIT](./LICENSE) © 2026 Aduki
package/bin/anza.js ADDED
@@ -0,0 +1,63 @@
1
+ #!/usr/bin/env node
2
+
3
+ /**
4
+ * library/bin/anza.js
5
+ *
6
+ * Node.js wrapper for the anza Rust binary.
7
+ * Detects the platform and spawns the correct pre-built binary.
8
+ *
9
+ * In development: uses tools/target/release/anza (two levels up).
10
+ * In npm install: uses pre-built platform binary from bin/.
11
+ */
12
+
13
+ import { fileURLToPath } from 'url';
14
+ import { dirname, join } from 'path';
15
+ import { existsSync } from 'fs';
16
+ import { spawn } from 'child_process';
17
+
18
+ const __filename = fileURLToPath(import.meta.url);
19
+ const __dirname = dirname(__filename);
20
+
21
+ // library/bin/ → library/ → repo root
22
+ const library = join(__dirname, '..');
23
+ const root = join(library, '..');
24
+
25
+ function binary() {
26
+ // Development: repo binary (built by `node scripts/build.js`)
27
+ const dev = join(root, 'tools', 'target', 'release', 'anza');
28
+ if (existsSync(dev)) return dev;
29
+
30
+ // npm install: pre-built platform binary alongside this script
31
+ const platform = process.platform;
32
+ const arch = process.arch;
33
+
34
+ const map = {
35
+ darwin: { x64: 'anza-macos-x64', arm64: 'anza-macos-arm64' },
36
+ linux: { x64: 'anza-linux-x64', arm64: 'anza-linux-arm64' },
37
+ win32: { x64: 'anza-windows-x64.exe', arm64: 'anza-windows-arm64.exe' },
38
+ };
39
+
40
+ const name = map[platform]?.[arch];
41
+ if (!name) {
42
+ console.error(`Unsupported platform: ${platform} ${arch}`);
43
+ process.exit(1);
44
+ }
45
+
46
+ const prebuilt = join(__dirname, name);
47
+ if (existsSync(prebuilt)) return prebuilt;
48
+
49
+ console.error(
50
+ 'anza binary not found.\n' +
51
+ 'Run: node scripts/build.js (from the repo root)'
52
+ );
53
+ process.exit(1);
54
+ }
55
+
56
+ const child = spawn(binary(), process.argv.slice(2), { stdio: 'inherit' });
57
+
58
+ child.on('error', (err) => {
59
+ console.error('Failed to spawn anza:', err.message);
60
+ process.exit(1);
61
+ });
62
+
63
+ child.on('exit', (code) => process.exit(code ?? 0));
package/bin/create.js ADDED
@@ -0,0 +1,150 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * scripts/create.js (also used as library/bin/create.js → npx anza-create)
4
+ *
5
+ * Scaffolds a new anza app project in the given directory.
6
+ * Usage:
7
+ * npx anza-create myapp
8
+ * npx anza-create . (current directory)
9
+ */
10
+
11
+ import { mkdirSync, writeFileSync, existsSync } from 'fs';
12
+ import { join, resolve, basename } from 'path';
13
+
14
+ const arg = process.argv[2];
15
+
16
+ if (!arg || arg === '--help' || arg === '-h') {
17
+ console.log('Usage: npx anza-create <name>');
18
+ console.log(' npx anza-create . (scaffold in current dir)');
19
+ process.exit(arg ? 0 : 1);
20
+ }
21
+
22
+ const target = resolve(arg);
23
+ const name = arg === '.' ? basename(process.cwd()) : basename(target);
24
+
25
+ if (existsSync(target) && arg !== '.') {
26
+ console.error(`Error: '${target}' already exists.`);
27
+ process.exit(1);
28
+ }
29
+
30
+ console.log(`Scaffolding anza app: ${name}\n`);
31
+
32
+ // Directory structure
33
+ const dirs = [
34
+ '',
35
+ 'src',
36
+ 'src/elements',
37
+ 'src/styles',
38
+ 'src/tokens',
39
+ ];
40
+
41
+ for (const dir of dirs) {
42
+ mkdirSync(join(target, dir), { recursive: true });
43
+ }
44
+
45
+ // src/index.html
46
+ writeFileSync(join(target, 'src', 'index.html'), `<!DOCTYPE html>
47
+ <html lang="en">
48
+ <head>
49
+ <meta charset="utf-8" />
50
+ <meta name="viewport" content="width=device-width, initial-scale=1" />
51
+ <title>${name}</title>
52
+
53
+ <!-- Tokens & global styles -->
54
+ <link rel="stylesheet" href="/dist/tokens/index.css" />
55
+ <link rel="stylesheet" href="/dist/styles/global.css" />
56
+
57
+ <!-- App entry -->
58
+ <script type="module" src="/dist/index.js"></script>
59
+ </head>
60
+ <body>
61
+ <!-- App root -->
62
+ </body>
63
+ </html>
64
+ `);
65
+
66
+ // src/index.js
67
+ writeFileSync(join(target, 'src', 'index.js'), `/**
68
+ * src/index.js — app entry point
69
+ */
70
+ import '@adukiorg/anza/ui';
71
+
72
+ // Import your elements
73
+ // import './elements/dashboard/index.js';
74
+ `);
75
+
76
+ // src/styles/global.css
77
+ writeFileSync(join(target, 'src', 'styles', 'global.css'), `/* global.css — global app styles */
78
+
79
+ *,
80
+ *::before,
81
+ *::after {
82
+ box-sizing: border-box;
83
+ margin: 0;
84
+ padding: 0;
85
+ }
86
+
87
+ body {
88
+ font-family: system-ui, sans-serif;
89
+ line-height: 1.5;
90
+ }
91
+ `);
92
+
93
+ // src/tokens/index.css
94
+ writeFileSync(join(target, 'src', 'tokens', 'index.css'), `/* tokens/index.css — design tokens */
95
+
96
+ :root {
97
+ /* Colors */
98
+ --color-primary: #6366f1;
99
+ --color-surface: #ffffff;
100
+ --color-text: #111827;
101
+
102
+ /* Spacing */
103
+ --space-1: 0.25rem;
104
+ --space-2: 0.5rem;
105
+ --space-4: 1rem;
106
+ --space-8: 2rem;
107
+
108
+ /* Radius */
109
+ --radius-sm: 0.25rem;
110
+ --radius-md: 0.5rem;
111
+ --radius-lg: 1rem;
112
+
113
+ /* Shadow */
114
+ --shadow-sm: 0 1px 2px rgb(0 0 0 / 0.05);
115
+ --shadow-md: 0 4px 6px rgb(0 0 0 / 0.07);
116
+ }
117
+ `);
118
+
119
+ // package.json
120
+ writeFileSync(join(target, 'package.json'), JSON.stringify({
121
+ name,
122
+ version: '0.1.0',
123
+ private: true,
124
+ type: 'module',
125
+ scripts: {
126
+ dev: 'anza dev',
127
+ build: 'anza build',
128
+ },
129
+ devDependencies: {
130
+ '@adukiorg/anza': 'latest',
131
+ }
132
+ }, null, 2));
133
+
134
+ // .gitignore
135
+ writeFileSync(join(target, '.gitignore'), `node_modules/
136
+ dist/
137
+ .anza-build-cache.json
138
+ `);
139
+
140
+ console.log('Created:');
141
+ for (const dir of dirs.filter(Boolean)) {
142
+ console.log(` ${name}/${dir}/`);
143
+ }
144
+ console.log(` ${name}/src/index.html`);
145
+ console.log(` ${name}/src/index.js`);
146
+ console.log(` ${name}/package.json`);
147
+ console.log(`\nNext steps:`);
148
+ console.log(` cd ${arg === '.' ? '.' : name}`);
149
+ console.log(` npm install`);
150
+ console.log(` npm run dev`);
package/importmap.json ADDED
@@ -0,0 +1,72 @@
1
+ {
2
+ "imports": {
3
+ "@adukiorg/anza": "/dist/index.js",
4
+
5
+ "@adukiorg/anza/api": "/dist/core/api/index.js",
6
+ "@adukiorg/anza/state": "/dist/core/state/index.js",
7
+ "@adukiorg/anza/events": "/dist/core/events/index.js",
8
+ "@adukiorg/anza/router": "/dist/core/router/index.js",
9
+ "@adukiorg/anza/storage": "/dist/core/storage/index.js",
10
+ "@adukiorg/anza/offline": "/dist/core/offline/index.js",
11
+ "@adukiorg/anza/animations": "/dist/core/animations/index.js",
12
+ "@adukiorg/anza/workers": "/dist/core/workers/index.js",
13
+ "@adukiorg/anza/security": "/dist/core/security/index.js",
14
+ "@adukiorg/anza/platform": "/dist/core/platform/index.js",
15
+ "@adukiorg/anza/ui": "/dist/core/ui/index.js",
16
+
17
+ "@adukiorg/anza/elements": "/dist/elements/index.js",
18
+
19
+ "@adukiorg/anza/elements/button": "/dist/elements/primitives/button/index.js",
20
+ "@adukiorg/anza/elements/icon": "/dist/elements/primitives/icon/index.js",
21
+ "@adukiorg/anza/elements/badge": "/dist/elements/primitives/badge/index.js",
22
+ "@adukiorg/anza/elements/avatar": "/dist/elements/primitives/avatar/index.js",
23
+ "@adukiorg/anza/elements/divider": "/dist/elements/primitives/divider/index.js",
24
+ "@adukiorg/anza/elements/text": "/dist/elements/primitives/text/index.js",
25
+ "@adukiorg/anza/elements/link": "/dist/elements/primitives/link/index.js",
26
+ "@adukiorg/anza/elements/spinner": "/dist/elements/primitives/spinner/index.js",
27
+
28
+ "@adukiorg/anza/elements/input": "/dist/elements/forms/input/index.js",
29
+ "@adukiorg/anza/elements/textarea": "/dist/elements/forms/textarea/index.js",
30
+ "@adukiorg/anza/elements/select": "/dist/elements/forms/select/index.js",
31
+ "@adukiorg/anza/elements/checkbox": "/dist/elements/forms/checkbox/index.js",
32
+ "@adukiorg/anza/elements/radio": "/dist/elements/forms/radio/index.js",
33
+ "@adukiorg/anza/elements/toggle": "/dist/elements/forms/toggle/index.js",
34
+ "@adukiorg/anza/elements/field": "/dist/elements/forms/field/index.js",
35
+ "@adukiorg/anza/elements/upload": "/dist/elements/forms/upload/index.js",
36
+ "@adukiorg/anza/elements/form": "/dist/elements/forms/form/index.js",
37
+
38
+ "@adukiorg/anza/elements/dialog": "/dist/elements/overlay/dialog/index.js",
39
+ "@adukiorg/anza/elements/popover": "/dist/elements/overlay/popover/index.js",
40
+ "@adukiorg/anza/elements/tooltip": "/dist/elements/overlay/tooltip/index.js",
41
+ "@adukiorg/anza/elements/menu": "/dist/elements/overlay/menu/index.js",
42
+ "@adukiorg/anza/elements/drawer": "/dist/elements/overlay/drawer/index.js",
43
+ "@adukiorg/anza/elements/sheet": "/dist/elements/overlay/sheet/index.js",
44
+
45
+ "@adukiorg/anza/elements/alert": "/dist/elements/feedback/alert/index.js",
46
+ "@adukiorg/anza/elements/toast": "/dist/elements/feedback/toast/index.js",
47
+ "@adukiorg/anza/elements/progress": "/dist/elements/feedback/progress/index.js",
48
+ "@adukiorg/anza/elements/skeleton": "/dist/elements/feedback/skeleton/index.js",
49
+ "@adukiorg/anza/elements/empty": "/dist/elements/feedback/empty/index.js",
50
+
51
+ "@adukiorg/anza/elements/table": "/dist/elements/data/table/index.js",
52
+ "@adukiorg/anza/elements/list": "/dist/elements/data/list/index.js",
53
+ "@adukiorg/anza/elements/card": "/dist/elements/data/card/index.js",
54
+ "@adukiorg/anza/elements/chart": "/dist/elements/data/chart/index.js",
55
+ "@adukiorg/anza/elements/stat": "/dist/elements/data/stat/index.js",
56
+
57
+ "@adukiorg/anza/elements/nav": "/dist/elements/navigation/nav/index.js",
58
+ "@adukiorg/anza/elements/tabs": "/dist/elements/navigation/tabs/index.js",
59
+ "@adukiorg/anza/elements/breadcrumb": "/dist/elements/navigation/breadcrumb/index.js",
60
+ "@adukiorg/anza/elements/pagination": "/dist/elements/navigation/pagination/index.js",
61
+ "@adukiorg/anza/elements/steps": "/dist/elements/navigation/steps/index.js",
62
+
63
+ "@adukiorg/anza/elements/app": "/dist/elements/layout/app/index.js",
64
+ "@adukiorg/anza/elements/header": "/dist/elements/layout/header/index.js",
65
+ "@adukiorg/anza/elements/sidebar": "/dist/elements/layout/sidebar/index.js",
66
+ "@adukiorg/anza/elements/stack": "/dist/elements/layout/stack/index.js",
67
+ "@adukiorg/anza/elements/grid": "/dist/elements/layout/grid/index.js",
68
+ "@adukiorg/anza/elements/split": "/dist/elements/layout/split/index.js",
69
+ "@adukiorg/anza/elements/scroll": "/dist/elements/layout/scroll/index.js",
70
+ "@adukiorg/anza/elements/surface": "/dist/elements/layout/surface/index.js"
71
+ }
72
+ }