@thangnqdev/ui 0.1.2 → 0.2.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 (233) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +54 -206
  3. package/bin/cli.js +125 -0
  4. package/dist/bento/index.cjs.map +1 -1
  5. package/dist/bento/index.js +2 -2
  6. package/dist/bento/styles.css +2 -46
  7. package/dist/buttons/index.cjs +111 -18
  8. package/dist/buttons/index.cjs.map +1 -1
  9. package/dist/buttons/index.d.cts +1 -1
  10. package/dist/buttons/index.d.ts +1 -1
  11. package/dist/buttons/index.js +3 -3
  12. package/dist/buttons/styles.css +2 -6
  13. package/dist/{chunk-4S6L5V7X.js → chunk-2YJBW4E2.js} +2 -2
  14. package/dist/chunk-2YJBW4E2.js.map +1 -0
  15. package/dist/{chunk-F5Q7BTMH.js → chunk-4CRFNALF.js} +1011 -556
  16. package/dist/chunk-4CRFNALF.js.map +1 -0
  17. package/dist/{chunk-LWFRUJRU.js → chunk-4MS6ZHFQ.js} +225 -41
  18. package/dist/chunk-4MS6ZHFQ.js.map +1 -0
  19. package/dist/{chunk-2OXZK6IP.js → chunk-77KTYOMQ.js} +3 -3
  20. package/dist/chunk-77KTYOMQ.js.map +1 -0
  21. package/dist/{chunk-IABPUCAQ.js → chunk-ADO3SVUA.js} +2 -2
  22. package/dist/chunk-ADO3SVUA.js.map +1 -0
  23. package/dist/{chunk-GXI2H5XA.js → chunk-D7FB3TCA.js} +3 -3
  24. package/dist/chunk-D7FB3TCA.js.map +1 -0
  25. package/dist/chunk-DSEL7ELZ.js +314 -0
  26. package/dist/chunk-DSEL7ELZ.js.map +1 -0
  27. package/dist/{chunk-KJRBRTQE.js → chunk-EXFR2BFJ.js} +37 -28
  28. package/dist/chunk-EXFR2BFJ.js.map +1 -0
  29. package/dist/{chunk-PF4ZHGVW.js → chunk-GXWB6BSY.js} +116 -23
  30. package/dist/chunk-GXWB6BSY.js.map +1 -0
  31. package/dist/{chunk-66VWUJEI.js → chunk-I2FQBMVW.js} +3 -3
  32. package/dist/chunk-I2FQBMVW.js.map +1 -0
  33. package/dist/{chunk-EU2LPUYP.js → chunk-I5O2WCGF.js} +3 -3
  34. package/dist/chunk-I5O2WCGF.js.map +1 -0
  35. package/dist/{chunk-ATYGDTMK.js → chunk-ME4XILG5.js} +5 -5
  36. package/dist/chunk-ME4XILG5.js.map +1 -0
  37. package/dist/{chunk-5FZ6ZFII.js → chunk-PC5SZFZC.js} +373 -150
  38. package/dist/chunk-PC5SZFZC.js.map +1 -0
  39. package/dist/{chunk-C4SUXMI3.js → chunk-S6XJMYME.js} +3 -3
  40. package/dist/chunk-S6XJMYME.js.map +1 -0
  41. package/dist/{chunk-A7P3O5Z5.js → chunk-V52JOSDF.js} +3 -3
  42. package/dist/chunk-V52JOSDF.js.map +1 -0
  43. package/dist/{chunk-NFVONJUK.js → chunk-W5WNWTQC.js} +455 -211
  44. package/dist/chunk-W5WNWTQC.js.map +1 -0
  45. package/dist/{chunk-WAFHC4DQ.js → chunk-YJ64RI7J.js} +3 -3
  46. package/dist/chunk-YJ64RI7J.js.map +1 -0
  47. package/dist/chunk-YOCGBORV.js +155 -0
  48. package/dist/chunk-YOCGBORV.js.map +1 -0
  49. package/dist/chunk-ZEDXARXW.js +96 -0
  50. package/dist/chunk-ZEDXARXW.js.map +1 -0
  51. package/dist/components.css +2 -0
  52. package/dist/core/index.cjs +33 -24
  53. package/dist/core/index.cjs.map +1 -1
  54. package/dist/core/index.js +2 -2
  55. package/dist/core/styles.css +2 -134
  56. package/dist/data-display/index.cjs +770 -247
  57. package/dist/data-display/index.cjs.map +1 -1
  58. package/dist/data-display/index.d.cts +1 -1
  59. package/dist/data-display/index.d.ts +1 -1
  60. package/dist/data-display/index.js +5 -4
  61. package/dist/data-display/styles.css +2 -4
  62. package/dist/feedback/index.cjs.map +1 -1
  63. package/dist/feedback/index.js +2 -2
  64. package/dist/feedback/styles.css +2 -4
  65. package/dist/forms/index.cjs +1211 -459
  66. package/dist/forms/index.cjs.map +1 -1
  67. package/dist/forms/index.d.cts +1 -1
  68. package/dist/forms/index.d.ts +1 -1
  69. package/dist/forms/index.js +8 -8
  70. package/dist/forms/styles.css +2 -6
  71. package/dist/glass/index.cjs.map +1 -1
  72. package/dist/glass/index.js +2 -2
  73. package/dist/glass/styles.css +2 -81
  74. package/dist/{index-D6fE7w-b.d.cts → index-BGt_hecO.d.cts} +1 -0
  75. package/dist/{index-D6fE7w-b.d.ts → index-BGt_hecO.d.ts} +1 -0
  76. package/dist/{index-DzcWh1Hs.d.cts → index-BtDvpZCf.d.cts} +7 -0
  77. package/dist/{index-DzcWh1Hs.d.ts → index-BtDvpZCf.d.ts} +7 -0
  78. package/dist/{index-Cle6QzQl.d.ts → index-COX1sBUN.d.ts} +27 -3
  79. package/dist/{index-BkRqGNG1.d.ts → index-Cg8MuP7u.d.cts} +40 -13
  80. package/dist/{index-BkRqGNG1.d.cts → index-Cg8MuP7u.d.ts} +40 -13
  81. package/dist/{index-CenuF_P2.d.ts → index-DHkPRTvE.d.cts} +39 -8
  82. package/dist/{index-CenuF_P2.d.cts → index-DHkPRTvE.d.ts} +39 -8
  83. package/dist/{index-TyK-Ldpy.d.cts → index-Du_oht9k.d.cts} +27 -3
  84. package/dist/index.cjs +2481 -917
  85. package/dist/index.cjs.map +1 -1
  86. package/dist/index.d.cts +5 -5
  87. package/dist/index.d.ts +5 -5
  88. package/dist/index.js +19 -19
  89. package/dist/layout/index.cjs.map +1 -1
  90. package/dist/layout/index.js +2 -2
  91. package/dist/layout/styles.css +2 -8
  92. package/dist/navigation/index.cjs +288 -48
  93. package/dist/navigation/index.cjs.map +1 -1
  94. package/dist/navigation/index.d.cts +1 -1
  95. package/dist/navigation/index.d.ts +1 -1
  96. package/dist/navigation/index.js +6 -6
  97. package/dist/navigation/styles.css +2 -4
  98. package/dist/overlays/index.cjs +566 -229
  99. package/dist/overlays/index.cjs.map +1 -1
  100. package/dist/overlays/index.d.cts +1 -1
  101. package/dist/overlays/index.d.ts +1 -1
  102. package/dist/overlays/index.js +7 -7
  103. package/dist/overlays/styles.css +2 -8
  104. package/dist/reset.css +45 -0
  105. package/dist/styles.css +1 -1
  106. package/dist/tokens.css +11 -0
  107. package/dist/typography/index.cjs.map +1 -1
  108. package/dist/typography/index.js +4 -4
  109. package/dist/typography/styles.css +2 -5
  110. package/llms.txt +211 -113
  111. package/package.json +167 -116
  112. package/scripts/postinstall.js +125 -0
  113. package/src/bento/BentoCard.tsx +140 -140
  114. package/src/bento/BentoGrid.tsx +50 -50
  115. package/src/bento/index.ts +2 -2
  116. package/src/bento/tokens.css +46 -46
  117. package/src/buttons/Button.tsx +104 -104
  118. package/src/buttons/ButtonGroup.tsx +43 -43
  119. package/src/buttons/IconButton.tsx +79 -79
  120. package/src/buttons/SplitButton.tsx +186 -86
  121. package/src/buttons/ToggleButton.tsx +157 -157
  122. package/src/buttons/index.ts +5 -5
  123. package/src/buttons/tokens.css +6 -6
  124. package/src/core/ThemeProvider.tsx +135 -123
  125. package/src/core/index.ts +2 -2
  126. package/src/core/tokens.css +134 -134
  127. package/src/data-display/Accordion.tsx +147 -147
  128. package/src/data-display/Avatar.tsx +134 -134
  129. package/src/data-display/Card.tsx +112 -112
  130. package/src/data-display/Chip.tsx +74 -74
  131. package/src/data-display/DataTablePro.tsx +299 -121
  132. package/src/data-display/StatCard.tsx +60 -60
  133. package/src/data-display/Table.tsx +74 -74
  134. package/src/data-display/Timeline.tsx +62 -62
  135. package/src/data-display/TreeView.tsx +243 -104
  136. package/src/data-display/tokens.css +4 -4
  137. package/src/feedback/Alert.tsx +80 -80
  138. package/src/feedback/EmptyState.tsx +45 -45
  139. package/src/feedback/Skeleton.tsx +66 -66
  140. package/src/feedback/Spinner.tsx +65 -65
  141. package/src/feedback/index.ts +5 -5
  142. package/src/feedback/tokens.css +4 -4
  143. package/src/forms/Checkbox.tsx +149 -69
  144. package/src/forms/CheckboxGroup.tsx +76 -29
  145. package/src/forms/Combobox.tsx +172 -28
  146. package/src/forms/DatePicker.tsx +385 -81
  147. package/src/forms/FileUpload.tsx +51 -7
  148. package/src/forms/FormField.tsx +115 -115
  149. package/src/forms/Input.tsx +151 -151
  150. package/src/forms/NumberInput.tsx +34 -20
  151. package/src/forms/PasswordInput.tsx +35 -35
  152. package/src/forms/PinInput.tsx +139 -125
  153. package/src/forms/Radio.tsx +142 -142
  154. package/src/forms/RangeSlider.tsx +237 -111
  155. package/src/forms/SearchInput.tsx +34 -34
  156. package/src/forms/Select.tsx +103 -103
  157. package/src/forms/Slider.tsx +85 -85
  158. package/src/forms/Textarea.tsx +114 -114
  159. package/src/forms/tokens.css +6 -6
  160. package/src/glass/GlassButton.tsx +59 -59
  161. package/src/glass/GlassCard.tsx +71 -71
  162. package/src/glass/index.ts +3 -3
  163. package/src/glass/tokens.css +81 -81
  164. package/src/index.ts +26 -26
  165. package/src/layout/AspectRatio.tsx +39 -39
  166. package/src/layout/Container.tsx +53 -53
  167. package/src/layout/Divider.tsx +61 -61
  168. package/src/layout/Flex.tsx +79 -79
  169. package/src/layout/Grid.tsx +124 -124
  170. package/src/layout/PageLayout.tsx +59 -59
  171. package/src/layout/Section.tsx +47 -47
  172. package/src/layout/Spacer.tsx +30 -30
  173. package/src/layout/Stack.tsx +88 -88
  174. package/src/layout/tokens.css +8 -8
  175. package/src/navigation/Breadcrumb.tsx +73 -73
  176. package/src/navigation/CommandPalette.tsx +142 -142
  177. package/src/navigation/DropdownMenu.tsx +244 -160
  178. package/src/navigation/Pagination.tsx +114 -114
  179. package/src/navigation/Stepper.tsx +93 -93
  180. package/src/navigation/Tabs.tsx +265 -133
  181. package/src/navigation/index.ts +6 -6
  182. package/src/navigation/tokens.css +4 -4
  183. package/src/overlays/AlertDialog.tsx +63 -54
  184. package/src/overlays/BottomSheet.tsx +30 -10
  185. package/src/overlays/ContextMenu.tsx +51 -9
  186. package/src/overlays/Drawer.tsx +160 -145
  187. package/src/overlays/FocusTrap.tsx +122 -49
  188. package/src/overlays/Modal.tsx +296 -219
  189. package/src/overlays/Popover.tsx +55 -25
  190. package/src/overlays/Portal.tsx +23 -23
  191. package/src/overlays/Toast.tsx +175 -137
  192. package/src/overlays/Tooltip.tsx +125 -100
  193. package/src/overlays/tokens.css +8 -8
  194. package/src/registry/components.ts +1368 -0
  195. package/src/styles/components.css +39 -0
  196. package/src/styles/index.css +2 -93
  197. package/src/styles/reset.css +45 -0
  198. package/src/styles/tokens.css +11 -2
  199. package/src/typography/Blockquote.tsx +32 -32
  200. package/src/typography/Code.tsx +89 -89
  201. package/src/typography/Heading.tsx +56 -56
  202. package/src/typography/Kbd.tsx +25 -25
  203. package/src/typography/Label.tsx +47 -47
  204. package/src/typography/Link.tsx +56 -56
  205. package/src/typography/Text.tsx +62 -62
  206. package/src/typography/index.ts +7 -7
  207. package/src/typography/tokens.css +5 -5
  208. package/src/utils/cn.ts +6 -6
  209. package/src/utils/scroll-lock.ts +19 -0
  210. package/src/utils/useControllableState.ts +54 -0
  211. package/ui-contract.json +192 -35
  212. package/dist/chunk-2OXZK6IP.js.map +0 -1
  213. package/dist/chunk-4S6L5V7X.js.map +0 -1
  214. package/dist/chunk-5FZ6ZFII.js.map +0 -1
  215. package/dist/chunk-66VWUJEI.js.map +0 -1
  216. package/dist/chunk-A7P3O5Z5.js.map +0 -1
  217. package/dist/chunk-ATYGDTMK.js.map +0 -1
  218. package/dist/chunk-C4SUXMI3.js.map +0 -1
  219. package/dist/chunk-EU2LPUYP.js.map +0 -1
  220. package/dist/chunk-F5Q7BTMH.js.map +0 -1
  221. package/dist/chunk-GXI2H5XA.js.map +0 -1
  222. package/dist/chunk-H3LCNPMC.js +0 -101
  223. package/dist/chunk-H3LCNPMC.js.map +0 -1
  224. package/dist/chunk-IABPUCAQ.js.map +0 -1
  225. package/dist/chunk-KJRBRTQE.js.map +0 -1
  226. package/dist/chunk-LBUBXUYQ.js +0 -40
  227. package/dist/chunk-LBUBXUYQ.js.map +0 -1
  228. package/dist/chunk-LWFRUJRU.js.map +0 -1
  229. package/dist/chunk-NFVONJUK.js.map +0 -1
  230. package/dist/chunk-PF4ZHGVW.js.map +0 -1
  231. package/dist/chunk-WAFHC4DQ.js.map +0 -1
  232. package/dist/chunk-X76KBH4Y.js +0 -71
  233. package/dist/chunk-X76KBH4Y.js.map +0 -1
package/package.json CHANGED
@@ -1,116 +1,167 @@
1
- {
2
- "name": "@thangnqdev/ui",
3
- "version": "0.1.2",
4
- "type": "module",
5
- "description": "Spatial Optics & Editorial Bento UI System",
6
- "main": "./dist/index.cjs",
7
- "module": "./dist/index.js",
8
- "types": "./dist/index.d.ts",
9
- "exports": {
10
- ".": {
11
- "types": "./dist/index.d.ts",
12
- "import": "./dist/index.js",
13
- "require": "./dist/index.cjs"
14
- },
15
- "./core": {
16
- "types": "./dist/core/index.d.ts",
17
- "import": "./dist/core/index.js",
18
- "require": "./dist/core/index.cjs"
19
- },
20
- "./layout": {
21
- "types": "./dist/layout/index.d.ts",
22
- "import": "./dist/layout/index.js",
23
- "require": "./dist/layout/index.cjs"
24
- },
25
- "./typography": {
26
- "types": "./dist/typography/index.d.ts",
27
- "import": "./dist/typography/index.js",
28
- "require": "./dist/typography/index.cjs"
29
- },
30
- "./buttons": {
31
- "types": "./dist/buttons/index.d.ts",
32
- "import": "./dist/buttons/index.js",
33
- "require": "./dist/buttons/index.cjs"
34
- },
35
- "./forms": {
36
- "types": "./dist/forms/index.d.ts",
37
- "import": "./dist/forms/index.js",
38
- "require": "./dist/forms/index.cjs"
39
- },
40
- "./overlays": {
41
- "types": "./dist/overlays/index.d.ts",
42
- "import": "./dist/overlays/index.js",
43
- "require": "./dist/overlays/index.cjs"
44
- },
45
- "./navigation": {
46
- "types": "./dist/navigation/index.d.ts",
47
- "import": "./dist/navigation/index.js",
48
- "require": "./dist/navigation/index.cjs"
49
- },
50
- "./data-display": {
51
- "types": "./dist/data-display/index.d.ts",
52
- "import": "./dist/data-display/index.js",
53
- "require": "./dist/data-display/index.cjs"
54
- },
55
- "./feedback": {
56
- "types": "./dist/feedback/index.d.ts",
57
- "import": "./dist/feedback/index.js",
58
- "require": "./dist/feedback/index.cjs"
59
- },
60
- "./glass": {
61
- "types": "./dist/glass/index.d.ts",
62
- "import": "./dist/glass/index.js",
63
- "require": "./dist/glass/index.cjs"
64
- },
65
- "./bento": {
66
- "types": "./dist/bento/index.d.ts",
67
- "import": "./dist/bento/index.js",
68
- "require": "./dist/bento/index.cjs"
69
- },
70
- "./styles.css": "./dist/styles.css",
71
- "./glass/styles.css": "./dist/glass/styles.css",
72
- "./bento/styles.css": "./dist/bento/styles.css"
73
- },
74
- "files": [
75
- "dist",
76
- "src",
77
- "llms.txt",
78
- "ui-contract.json"
79
- ],
80
- "scripts": {
81
- "dev": "vite",
82
- "build": "tsup && node scripts/build-css.js",
83
- "build:lib": "tsup && node scripts/build-css.js",
84
- "watch:lib": "tsup --watch",
85
- "typecheck": "tsc --noEmit",
86
- "test": "vitest run",
87
- "preview": "vite preview"
88
- },
89
- "peerDependencies": {
90
- "react": "^18.0.0 || ^19.0.0",
91
- "react-dom": "^18.0.0 || ^19.0.0"
92
- },
93
- "dependencies": {
94
- "class-variance-authority": "^0.7.1",
95
- "clsx": "^2.1.1",
96
- "lucide-react": "^1.16.0",
97
- "tailwind-merge": "^3.0.2"
98
- },
99
- "devDependencies": {
100
- "@tailwindcss/vite": "^4.3.3",
101
- "@testing-library/dom": "^10.4.1",
102
- "@testing-library/jest-dom": "^7.0.1",
103
- "@testing-library/react": "^16.3.2",
104
- "@types/react": "^19.0.0",
105
- "@types/react-dom": "^19.0.0",
106
- "@vitejs/plugin-react": "^6.0.5",
107
- "jsdom": "^30.0.1",
108
- "react": "^19.0.0",
109
- "react-dom": "^19.0.0",
110
- "tailwindcss": "^4.3.3",
111
- "tsup": "^8.3.6",
112
- "typescript": "^5.7.3",
113
- "vite": "^8.2.1",
114
- "vitest": "^3.0.7"
115
- }
116
- }
1
+ {
2
+ "name": "@thangnqdev/ui",
3
+ "version": "0.2.1",
4
+ "type": "module",
5
+ "description": "Spatial Optics & Editorial Bento UI System with Machine-Readable AI Contracts",
6
+ "license": "MIT",
7
+ "author": "thangnqdev",
8
+ "keywords": [
9
+ "react",
10
+ "ui",
11
+ "design-system",
12
+ "tailwind",
13
+ "spatial-optics",
14
+ "bento",
15
+ "accessibility",
16
+ "wcag",
17
+ "ssot",
18
+ "enterprise"
19
+ ],
20
+ "engines": {
21
+ "node": ">=20.0.0"
22
+ },
23
+ "sideEffects": [
24
+ "*.css",
25
+ "**/*.css"
26
+ ],
27
+ "main": "./dist/index.cjs",
28
+ "module": "./dist/index.js",
29
+ "types": "./dist/index.d.ts",
30
+ "exports": {
31
+ ".": {
32
+ "types": "./dist/index.d.ts",
33
+ "import": "./dist/index.js",
34
+ "require": "./dist/index.cjs"
35
+ },
36
+ "./core": {
37
+ "types": "./dist/core/index.d.ts",
38
+ "import": "./dist/core/index.js",
39
+ "require": "./dist/core/index.cjs"
40
+ },
41
+ "./layout": {
42
+ "types": "./dist/layout/index.d.ts",
43
+ "import": "./dist/layout/index.js",
44
+ "require": "./dist/layout/index.cjs"
45
+ },
46
+ "./typography": {
47
+ "types": "./dist/typography/index.d.ts",
48
+ "import": "./dist/typography/index.js",
49
+ "require": "./dist/typography/index.cjs"
50
+ },
51
+ "./buttons": {
52
+ "types": "./dist/buttons/index.d.ts",
53
+ "import": "./dist/buttons/index.js",
54
+ "require": "./dist/buttons/index.cjs"
55
+ },
56
+ "./forms": {
57
+ "types": "./dist/forms/index.d.ts",
58
+ "import": "./dist/forms/index.js",
59
+ "require": "./dist/forms/index.cjs"
60
+ },
61
+ "./overlays": {
62
+ "types": "./dist/overlays/index.d.ts",
63
+ "import": "./dist/overlays/index.js",
64
+ "require": "./dist/overlays/index.cjs"
65
+ },
66
+ "./navigation": {
67
+ "types": "./dist/navigation/index.d.ts",
68
+ "import": "./dist/navigation/index.js",
69
+ "require": "./dist/navigation/index.cjs"
70
+ },
71
+ "./data-display": {
72
+ "types": "./dist/data-display/index.d.ts",
73
+ "import": "./dist/data-display/index.js",
74
+ "require": "./dist/data-display/index.cjs"
75
+ },
76
+ "./feedback": {
77
+ "types": "./dist/feedback/index.d.ts",
78
+ "import": "./dist/feedback/index.js",
79
+ "require": "./dist/feedback/index.cjs"
80
+ },
81
+ "./glass": {
82
+ "types": "./dist/glass/index.d.ts",
83
+ "import": "./dist/glass/index.js",
84
+ "require": "./dist/glass/index.cjs"
85
+ },
86
+ "./bento": {
87
+ "types": "./dist/bento/index.d.ts",
88
+ "import": "./dist/bento/index.js",
89
+ "require": "./dist/bento/index.cjs"
90
+ },
91
+ "./styles.css": "./dist/styles.css",
92
+ "./tokens.css": "./dist/tokens.css",
93
+ "./components.css": "./dist/components.css",
94
+ "./reset.css": "./dist/reset.css",
95
+ "./core/styles.css": "./dist/core/styles.css",
96
+ "./layout/styles.css": "./dist/layout/styles.css",
97
+ "./typography/styles.css": "./dist/typography/styles.css",
98
+ "./buttons/styles.css": "./dist/buttons/styles.css",
99
+ "./forms/styles.css": "./dist/forms/styles.css",
100
+ "./overlays/styles.css": "./dist/overlays/styles.css",
101
+ "./navigation/styles.css": "./dist/navigation/styles.css",
102
+ "./data-display/styles.css": "./dist/data-display/styles.css",
103
+ "./feedback/styles.css": "./dist/feedback/styles.css",
104
+ "./glass/styles.css": "./dist/glass/styles.css",
105
+ "./bento/styles.css": "./dist/bento/styles.css"
106
+ },
107
+ "bin": {
108
+ "@thangnqdev/ui": "./bin/cli.js",
109
+ "aether-ui": "./bin/cli.js"
110
+ },
111
+ "files": [
112
+ "dist",
113
+ "src",
114
+ "bin",
115
+ "scripts/postinstall.js",
116
+ "llms.txt",
117
+ "ui-contract.json",
118
+ "LICENSE"
119
+ ],
120
+ "scripts": {
121
+ "dev": "vite",
122
+ "postinstall": "node scripts/postinstall.js",
123
+ "build:manifests": "node scripts/generate-manifests.js",
124
+ "build:css": "node scripts/build-css.js",
125
+ "build:ts": "tsup",
126
+ "build": "node scripts/generate-manifests.js && tsup && node scripts/build-css.js",
127
+ "build:lib": "node scripts/generate-manifests.js && tsup && node scripts/build-css.js",
128
+ "watch:lib": "tsup --watch",
129
+ "typecheck": "tsc --noEmit",
130
+ "test": "vitest run",
131
+ "test:ssot": "vitest run tests/ssot-invariant.test.ts",
132
+ "test:a11y": "vitest run tests/a11y-enhanced.test.tsx tests/axe-automated.test.tsx tests/navigation-a11y.test.tsx",
133
+ "test:ssr": "vitest run tests/ssr.test.tsx",
134
+ "prepack": "npm run typecheck && npm test && npm run build",
135
+ "preview": "vite preview"
136
+ },
137
+ "peerDependencies": {
138
+ "react": "^18.0.0 || ^19.0.0",
139
+ "react-dom": "^18.0.0 || ^19.0.0"
140
+ },
141
+ "dependencies": {
142
+ "class-variance-authority": "^0.7.1",
143
+ "clsx": "^2.1.1",
144
+ "lucide-react": "^1.16.0",
145
+ "tailwind-merge": "^3.0.2"
146
+ },
147
+ "devDependencies": {
148
+ "@tailwindcss/cli": "^4.3.3",
149
+ "@tailwindcss/vite": "^4.3.3",
150
+ "@testing-library/dom": "^10.4.1",
151
+ "@testing-library/jest-dom": "^7.0.1",
152
+ "@testing-library/react": "^16.3.2",
153
+ "@types/node": "^26.2.0",
154
+ "@types/react": "^19.0.0",
155
+ "@types/react-dom": "^19.0.0",
156
+ "@vitejs/plugin-react": "^6.0.5",
157
+ "axe-core": "^4.13.0",
158
+ "jsdom": "^30.0.1",
159
+ "react": "^19.0.0",
160
+ "react-dom": "^19.0.0",
161
+ "tailwindcss": "^4.3.3",
162
+ "tsup": "^8.3.6",
163
+ "typescript": "^5.7.3",
164
+ "vite": "^8.2.1",
165
+ "vitest": "^3.0.7"
166
+ }
167
+ }
@@ -0,0 +1,125 @@
1
+ #!/usr/bin/env node
2
+
3
+ import fs from 'node:fs';
4
+ import path from 'node:path';
5
+ import os from 'node:os';
6
+ import readline from 'node:readline';
7
+ import { execSync } from 'node:child_process';
8
+
9
+ const CONFIG_DIR = path.join(os.homedir(), '.thangnqdev-ui');
10
+ const CONFIG_FILE = path.join(CONFIG_DIR, 'telemetry.json');
11
+
12
+ // 1. Silent bailouts for CI, non-interactive environments, and opt-out flags
13
+ if (
14
+ process.env.CI ||
15
+ process.env.CONTINUOUS_INTEGRATION ||
16
+ process.env.DO_NOT_TRACK === '1' ||
17
+ process.env.AETHER_TELEMETRY_DISABLED === '1' ||
18
+ !process.stdout.isTTY ||
19
+ !process.stdin.isTTY
20
+ ) {
21
+ process.exit(0);
22
+ }
23
+
24
+ // 2. Check if user has already configured preference
25
+ if (fs.existsSync(CONFIG_FILE)) {
26
+ try {
27
+ const config = JSON.parse(fs.readFileSync(CONFIG_FILE, 'utf-8'));
28
+ if (config.prompted) {
29
+ process.exit(0);
30
+ }
31
+ } catch {
32
+ // Ignore corrupted config
33
+ }
34
+ }
35
+
36
+ function getGitRemote() {
37
+ try {
38
+ const remote = execSync('git remote get-url origin', {
39
+ stdio: ['pipe', 'pipe', 'ignore'],
40
+ timeout: 1000,
41
+ })
42
+ .toString()
43
+ .trim();
44
+ return remote;
45
+ } catch {
46
+ return null;
47
+ }
48
+ }
49
+
50
+ function saveConfig(data) {
51
+ try {
52
+ if (!fs.existsSync(CONFIG_DIR)) {
53
+ fs.mkdirSync(CONFIG_DIR, { recursive: true });
54
+ }
55
+ fs.writeFileSync(
56
+ CONFIG_FILE,
57
+ JSON.stringify(
58
+ {
59
+ ...data,
60
+ updatedAt: new Date().toISOString(),
61
+ prompted: true,
62
+ },
63
+ null,
64
+ 2
65
+ )
66
+ );
67
+ } catch {
68
+ // Ignore filesystem permissions error on read-only environments
69
+ }
70
+ }
71
+
72
+ async function promptUser() {
73
+ const detectedRepo = getGitRemote();
74
+
75
+ console.log('\n\x1b[36m╭────────────────────────────────────────────────────────────────────────╮\x1b[0m');
76
+ console.log('\x1b[36m│\x1b[0m \x1b[1m✦ Thanks for installing @thangnqdev/ui (AETHER Spatial UI)\x1b[0m \x1b[36m│\x1b[0m');
77
+ console.log('\x1b[36m│\x1b[0m \x1b[36m│\x1b[0m');
78
+ console.log('\x1b[36m│\x1b[0m Would you like to share your public repository info to be featured \x1b[36m│\x1b[0m');
79
+ console.log('\x1b[36m│\x1b[0m in the AETHER Community Showcase & project ecosystem? \x1b[36m│\x1b[0m');
80
+ if (detectedRepo) {
81
+ console.log(`\x1b[36m│\x1b[0m \x1b[90mDetected repo:\x1b[0m \x1b[32m${detectedRepo.slice(0, 52)}\x1b[0m \x1b[36m│\x1b[0m`);
82
+ }
83
+ console.log('\x1b[36m│\x1b[0m \x1b[36m│\x1b[0m');
84
+ console.log('\x1b[36m│\x1b[0m \x1b[1m[y]\x1b[0m Yes, share repo info \x1b[1m[n]\x1b[0m No, keep anonymous (Default: n) \x1b[36m│\x1b[0m');
85
+ console.log('\x1b[36m╰────────────────────────────────────────────────────────────────────────╯\x1b[0m');
86
+
87
+ const rl = readline.createInterface({
88
+ input: process.stdin,
89
+ output: process.stdout,
90
+ });
91
+
92
+ return new Promise((resolve) => {
93
+ // Timeout prompt after 15 seconds so installation never hangs
94
+ const timer = setTimeout(() => {
95
+ saveConfig({ enabled: false, repo: null });
96
+ rl.close();
97
+ resolve();
98
+ }, 15000);
99
+
100
+ rl.question(' \x1b[33mShare repository info? (y/N):\x1b[0m ', (answer) => {
101
+ clearTimeout(timer);
102
+ const isYes = answer.trim().toLowerCase() === 'y' || answer.trim().toLowerCase() === 'yes';
103
+
104
+ if (isYes) {
105
+ saveConfig({
106
+ enabled: true,
107
+ repo: detectedRepo || 'manual-opt-in',
108
+ optedInAt: new Date().toISOString(),
109
+ });
110
+ console.log(' \x1b[32m✔ Thank you! Repository info shared with AETHER Community Showcase.\x1b[0m\n');
111
+ } else {
112
+ saveConfig({
113
+ enabled: false,
114
+ repo: null,
115
+ });
116
+ console.log(' \x1b[90m✔ Understood. Anonymous mode active. (Manage anytime via npx @thangnqdev/ui showcase)\x1b[0m\n');
117
+ }
118
+
119
+ rl.close();
120
+ resolve();
121
+ });
122
+ });
123
+ }
124
+
125
+ promptUser().catch(() => process.exit(0));