@questpie/admin 0.0.1 → 1.0.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 (250) hide show
  1. package/README.md +439 -424
  2. package/dist/auth-layout-M8K8_q5R.mjs +181 -0
  3. package/dist/auth-layout-M8K8_q5R.mjs.map +1 -0
  4. package/dist/bulk-upload-dialog-D7w7W1Hl.mjs +273 -0
  5. package/dist/bulk-upload-dialog-D7w7W1Hl.mjs.map +1 -0
  6. package/dist/{components/ui/card.mjs → card-BKHjBQfw.mjs} +8 -8
  7. package/dist/card-BKHjBQfw.mjs.map +1 -0
  8. package/dist/client/styles/index.css +434 -0
  9. package/dist/client-DbpZKSgH.d.mts +13585 -0
  10. package/dist/client-DbpZKSgH.d.mts.map +1 -0
  11. package/dist/client-njX1rZmi.mjs +22612 -0
  12. package/dist/client-njX1rZmi.mjs.map +1 -0
  13. package/dist/client.d.mts +3 -0
  14. package/dist/client.mjs +13 -0
  15. package/dist/content-locales-provider-BXvuIgfg.mjs +1650 -0
  16. package/dist/content-locales-provider-BXvuIgfg.mjs.map +1 -0
  17. package/dist/dashboard-page-B4PGEdc2.mjs +2500 -0
  18. package/dist/dashboard-page-B4PGEdc2.mjs.map +1 -0
  19. package/dist/dashboard-page-mCY0pgZv.mjs +3 -0
  20. package/dist/dropzone-Do3awXKd.mjs +634 -0
  21. package/dist/dropzone-Do3awXKd.mjs.map +1 -0
  22. package/dist/{views/auth/forgot-password-form.mjs → forgot-password-page-Bcp-An4Y.mjs} +87 -14
  23. package/dist/forgot-password-page-Bcp-An4Y.mjs.map +1 -0
  24. package/dist/forgot-password-page-CEwsdLwn.mjs +3 -0
  25. package/dist/index-B9Xwk4hi.d.mts +2753 -0
  26. package/dist/index-B9Xwk4hi.d.mts.map +1 -0
  27. package/dist/index.d.mts +3 -0
  28. package/dist/index.mjs +13 -0
  29. package/dist/login-page-BUnpCbCa.mjs +3 -0
  30. package/dist/login-page-CP4gA-dl.mjs +298 -0
  31. package/dist/login-page-CP4gA-dl.mjs.map +1 -0
  32. package/dist/preview-utils-BKQ9-TMa.mjs +65 -0
  33. package/dist/preview-utils-BKQ9-TMa.mjs.map +1 -0
  34. package/dist/{views/auth/reset-password-form.mjs → reset-password-page-BqfDmLxA.mjs} +111 -14
  35. package/dist/reset-password-page-BqfDmLxA.mjs.map +1 -0
  36. package/dist/reset-password-page-CufHz3h3.mjs +3 -0
  37. package/dist/runtime-6VZM878K.mjs +69 -0
  38. package/dist/runtime-6VZM878K.mjs.map +1 -0
  39. package/dist/saved-views.types-BMsz5mCy.d.mts +42 -0
  40. package/dist/saved-views.types-BMsz5mCy.d.mts.map +1 -0
  41. package/dist/server.d.mts +250 -0
  42. package/dist/server.d.mts.map +1 -0
  43. package/dist/server.mjs +832 -0
  44. package/dist/server.mjs.map +1 -0
  45. package/dist/setup-page-BNNzt_Z6.mjs +3 -0
  46. package/dist/setup-page-YAP_fzqh.mjs +264 -0
  47. package/dist/setup-page-YAP_fzqh.mjs.map +1 -0
  48. package/dist/shared.d.mts +57 -0
  49. package/dist/shared.d.mts.map +1 -0
  50. package/dist/shared.mjs +3 -0
  51. package/dist/{hooks/use-auth.mjs → use-auth-BoLmWtmU.mjs} +42 -30
  52. package/dist/use-auth-BoLmWtmU.mjs.map +1 -0
  53. package/package.json +48 -198
  54. package/.turbo/turbo-build.log +0 -108
  55. package/CHANGELOG.md +0 -10
  56. package/STATUS.md +0 -917
  57. package/VALIDATION.md +0 -602
  58. package/components.json +0 -24
  59. package/dist/__tests__/setup.mjs +0 -38
  60. package/dist/__tests__/test-utils.mjs +0 -45
  61. package/dist/__tests__/vitest.d.mjs +0 -3
  62. package/dist/components/admin-app.mjs +0 -69
  63. package/dist/components/fields/array-field.mjs +0 -190
  64. package/dist/components/fields/checkbox-field.mjs +0 -34
  65. package/dist/components/fields/custom-field.mjs +0 -32
  66. package/dist/components/fields/date-field.mjs +0 -41
  67. package/dist/components/fields/datetime-field.mjs +0 -42
  68. package/dist/components/fields/email-field.mjs +0 -37
  69. package/dist/components/fields/embedded-collection.mjs +0 -253
  70. package/dist/components/fields/field-types.mjs +0 -1
  71. package/dist/components/fields/field-utils.mjs +0 -10
  72. package/dist/components/fields/field-wrapper.mjs +0 -34
  73. package/dist/components/fields/index.mjs +0 -23
  74. package/dist/components/fields/json-field.mjs +0 -243
  75. package/dist/components/fields/locale-badge.mjs +0 -16
  76. package/dist/components/fields/number-field.mjs +0 -39
  77. package/dist/components/fields/password-field.mjs +0 -37
  78. package/dist/components/fields/relation-field.mjs +0 -104
  79. package/dist/components/fields/relation-picker.mjs +0 -229
  80. package/dist/components/fields/relation-select.mjs +0 -188
  81. package/dist/components/fields/rich-text-editor/index.mjs +0 -897
  82. package/dist/components/fields/select-field.mjs +0 -41
  83. package/dist/components/fields/switch-field.mjs +0 -34
  84. package/dist/components/fields/text-field.mjs +0 -38
  85. package/dist/components/fields/textarea-field.mjs +0 -38
  86. package/dist/components/index.mjs +0 -59
  87. package/dist/components/primitives/checkbox-input.mjs +0 -127
  88. package/dist/components/primitives/date-input.mjs +0 -303
  89. package/dist/components/primitives/index.mjs +0 -12
  90. package/dist/components/primitives/number-input.mjs +0 -104
  91. package/dist/components/primitives/select-input.mjs +0 -177
  92. package/dist/components/primitives/tag-input.mjs +0 -135
  93. package/dist/components/primitives/text-input.mjs +0 -39
  94. package/dist/components/primitives/textarea-input.mjs +0 -37
  95. package/dist/components/primitives/toggle-input.mjs +0 -31
  96. package/dist/components/primitives/types.mjs +0 -12
  97. package/dist/components/ui/accordion.mjs +0 -55
  98. package/dist/components/ui/avatar.mjs +0 -54
  99. package/dist/components/ui/badge.mjs +0 -34
  100. package/dist/components/ui/button.mjs +0 -48
  101. package/dist/components/ui/checkbox.mjs +0 -21
  102. package/dist/components/ui/combobox.mjs +0 -163
  103. package/dist/components/ui/dialog.mjs +0 -95
  104. package/dist/components/ui/dropdown-menu.mjs +0 -138
  105. package/dist/components/ui/field.mjs +0 -113
  106. package/dist/components/ui/input-group.mjs +0 -82
  107. package/dist/components/ui/input.mjs +0 -17
  108. package/dist/components/ui/label.mjs +0 -15
  109. package/dist/components/ui/popover.mjs +0 -56
  110. package/dist/components/ui/scroll-area.mjs +0 -38
  111. package/dist/components/ui/select.mjs +0 -100
  112. package/dist/components/ui/separator.mjs +0 -16
  113. package/dist/components/ui/sheet.mjs +0 -90
  114. package/dist/components/ui/sidebar.mjs +0 -387
  115. package/dist/components/ui/skeleton.mjs +0 -14
  116. package/dist/components/ui/spinner.mjs +0 -16
  117. package/dist/components/ui/switch.mjs +0 -22
  118. package/dist/components/ui/table.mjs +0 -68
  119. package/dist/components/ui/tabs.mjs +0 -48
  120. package/dist/components/ui/textarea.mjs +0 -15
  121. package/dist/components/ui/tooltip.mjs +0 -44
  122. package/dist/config/component-registry.mjs +0 -38
  123. package/dist/config/index.mjs +0 -129
  124. package/dist/hooks/admin-provider.mjs +0 -70
  125. package/dist/hooks/index.mjs +0 -7
  126. package/dist/hooks/store.mjs +0 -178
  127. package/dist/hooks/use-collection-db.mjs +0 -146
  128. package/dist/hooks/use-collection.mjs +0 -112
  129. package/dist/hooks/use-global.mjs +0 -46
  130. package/dist/hooks/use-mobile.mjs +0 -20
  131. package/dist/lib/utils.mjs +0 -10
  132. package/dist/styles/index.css +0 -336
  133. package/dist/styles/index.mjs +0 -1
  134. package/dist/utils/index.mjs +0 -9
  135. package/dist/views/auth/auth-layout.mjs +0 -52
  136. package/dist/views/auth/index.mjs +0 -6
  137. package/dist/views/auth/login-form.mjs +0 -156
  138. package/dist/views/collection/auto-form-fields.mjs +0 -525
  139. package/dist/views/collection/collection-form.mjs +0 -91
  140. package/dist/views/collection/collection-list.mjs +0 -76
  141. package/dist/views/collection/form-field.mjs +0 -42
  142. package/dist/views/collection/index.mjs +0 -6
  143. package/dist/views/common/index.mjs +0 -4
  144. package/dist/views/common/locale-switcher.mjs +0 -39
  145. package/dist/views/common/version-history.mjs +0 -272
  146. package/dist/views/index.mjs +0 -9
  147. package/dist/views/layout/admin-layout.mjs +0 -40
  148. package/dist/views/layout/admin-router.mjs +0 -95
  149. package/dist/views/layout/admin-sidebar.mjs +0 -63
  150. package/dist/views/layout/index.mjs +0 -5
  151. package/src/__tests__/setup.ts +0 -44
  152. package/src/__tests__/test-utils.tsx +0 -49
  153. package/src/__tests__/vitest.d.ts +0 -9
  154. package/src/components/admin-app.tsx +0 -221
  155. package/src/components/fields/array-field.tsx +0 -237
  156. package/src/components/fields/checkbox-field.tsx +0 -47
  157. package/src/components/fields/custom-field.tsx +0 -50
  158. package/src/components/fields/date-field.tsx +0 -65
  159. package/src/components/fields/datetime-field.tsx +0 -67
  160. package/src/components/fields/email-field.tsx +0 -51
  161. package/src/components/fields/embedded-collection.tsx +0 -315
  162. package/src/components/fields/field-types.ts +0 -162
  163. package/src/components/fields/field-utils.ts +0 -6
  164. package/src/components/fields/field-wrapper.tsx +0 -52
  165. package/src/components/fields/index.ts +0 -66
  166. package/src/components/fields/json-field.tsx +0 -440
  167. package/src/components/fields/locale-badge.tsx +0 -15
  168. package/src/components/fields/number-field.tsx +0 -57
  169. package/src/components/fields/password-field.tsx +0 -51
  170. package/src/components/fields/relation-field.tsx +0 -243
  171. package/src/components/fields/relation-picker.tsx +0 -402
  172. package/src/components/fields/relation-select.tsx +0 -327
  173. package/src/components/fields/rich-text-editor/index.tsx +0 -1337
  174. package/src/components/fields/select-field.tsx +0 -61
  175. package/src/components/fields/switch-field.tsx +0 -47
  176. package/src/components/fields/text-field.tsx +0 -55
  177. package/src/components/fields/textarea-field.tsx +0 -55
  178. package/src/components/index.ts +0 -40
  179. package/src/components/primitives/checkbox-input.tsx +0 -193
  180. package/src/components/primitives/date-input.tsx +0 -401
  181. package/src/components/primitives/index.ts +0 -24
  182. package/src/components/primitives/number-input.tsx +0 -132
  183. package/src/components/primitives/select-input.tsx +0 -296
  184. package/src/components/primitives/tag-input.tsx +0 -200
  185. package/src/components/primitives/text-input.tsx +0 -49
  186. package/src/components/primitives/textarea-input.tsx +0 -46
  187. package/src/components/primitives/toggle-input.tsx +0 -36
  188. package/src/components/primitives/types.ts +0 -235
  189. package/src/components/ui/accordion.tsx +0 -72
  190. package/src/components/ui/avatar.tsx +0 -106
  191. package/src/components/ui/badge.tsx +0 -48
  192. package/src/components/ui/button.tsx +0 -53
  193. package/src/components/ui/card.tsx +0 -94
  194. package/src/components/ui/checkbox.tsx +0 -27
  195. package/src/components/ui/combobox.tsx +0 -290
  196. package/src/components/ui/dialog.tsx +0 -151
  197. package/src/components/ui/dropdown-menu.tsx +0 -254
  198. package/src/components/ui/field.tsx +0 -227
  199. package/src/components/ui/input-group.tsx +0 -149
  200. package/src/components/ui/input.tsx +0 -20
  201. package/src/components/ui/label.tsx +0 -18
  202. package/src/components/ui/popover.tsx +0 -88
  203. package/src/components/ui/scroll-area.tsx +0 -53
  204. package/src/components/ui/select.tsx +0 -192
  205. package/src/components/ui/separator.tsx +0 -23
  206. package/src/components/ui/sheet.tsx +0 -127
  207. package/src/components/ui/sidebar.tsx +0 -723
  208. package/src/components/ui/skeleton.tsx +0 -13
  209. package/src/components/ui/spinner.tsx +0 -10
  210. package/src/components/ui/switch.tsx +0 -32
  211. package/src/components/ui/table.tsx +0 -99
  212. package/src/components/ui/tabs.tsx +0 -82
  213. package/src/components/ui/textarea.tsx +0 -18
  214. package/src/components/ui/tooltip.tsx +0 -70
  215. package/src/config/component-registry.ts +0 -190
  216. package/src/config/index.ts +0 -1099
  217. package/src/hooks/README.md +0 -269
  218. package/src/hooks/admin-provider.tsx +0 -110
  219. package/src/hooks/index.ts +0 -41
  220. package/src/hooks/store.ts +0 -248
  221. package/src/hooks/use-auth.ts +0 -168
  222. package/src/hooks/use-collection-db.ts +0 -209
  223. package/src/hooks/use-collection.ts +0 -156
  224. package/src/hooks/use-global.ts +0 -69
  225. package/src/hooks/use-mobile.ts +0 -21
  226. package/src/lib/utils.ts +0 -6
  227. package/src/styles/index.css +0 -340
  228. package/src/utils/index.ts +0 -6
  229. package/src/views/auth/auth-layout.tsx +0 -77
  230. package/src/views/auth/forgot-password-form.tsx +0 -192
  231. package/src/views/auth/index.ts +0 -21
  232. package/src/views/auth/login-form.tsx +0 -229
  233. package/src/views/auth/reset-password-form.tsx +0 -232
  234. package/src/views/collection/auto-form-fields.tsx +0 -982
  235. package/src/views/collection/collection-form.tsx +0 -186
  236. package/src/views/collection/collection-list.tsx +0 -223
  237. package/src/views/collection/form-field.tsx +0 -52
  238. package/src/views/collection/index.ts +0 -15
  239. package/src/views/common/index.ts +0 -8
  240. package/src/views/common/locale-switcher.tsx +0 -45
  241. package/src/views/common/version-history.tsx +0 -406
  242. package/src/views/index.ts +0 -25
  243. package/src/views/layout/admin-layout.tsx +0 -117
  244. package/src/views/layout/admin-router.tsx +0 -206
  245. package/src/views/layout/admin-sidebar.tsx +0 -185
  246. package/src/views/layout/index.ts +0 -12
  247. package/tsconfig.json +0 -13
  248. package/tsconfig.tsbuildinfo +0 -1
  249. package/tsdown.config.ts +0 -13
  250. package/vitest.config.ts +0 -29
@@ -1,253 +0,0 @@
1
- import * as React$1 from "react";
2
- import { Fragment, jsx, jsxs } from "react/jsx-runtime";
3
- import { Button } from "../ui/button";
4
- import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle } from "../ui/dialog";
5
- import { Sheet, SheetContent, SheetDescription, SheetHeader, SheetTitle } from "../ui/sheet";
6
- import { CaretDown, CaretUp, Pencil, Plus, Trash } from "@phosphor-icons/react";
7
- import { useFieldArray, useFormContext, useWatch } from "react-hook-form";
8
- import { LocaleBadge } from "./locale-badge";
9
-
10
- //#region src/components/fields/embedded-collection.tsx
11
- /**
12
- * EmbeddedCollectionField Component
13
- *
14
- * Manages embedded collections with inline, modal, or drawer editing.
15
- */
16
- function EmbeddedCollectionField({ name, value, collection, mode = "inline", orderable = false, rowLabel, label, description, required, disabled, readOnly, error, placeholder, localized, locale, renderFields, minItems, maxItems }) {
17
- const { control } = useFormContext();
18
- const { fields, append, remove, move } = useFieldArray({
19
- control,
20
- name
21
- });
22
- const values = useWatch({
23
- control,
24
- name
25
- }) ?? value;
26
- const [activeIndex, setActiveIndex] = React$1.useState(null);
27
- const [isOpen, setIsOpen] = React$1.useState(false);
28
- const canAddMore = !maxItems || fields.length < maxItems;
29
- const canRemove = !readOnly && (!minItems || fields.length > minItems);
30
- const fallbackLabel = label || collection || "Item";
31
- const resolveRowLabel = React$1.useCallback((item, index) => {
32
- if (typeof rowLabel === "function") {
33
- const labelValue = rowLabel(item);
34
- if (labelValue) return labelValue;
35
- }
36
- if (typeof rowLabel === "string") {
37
- const labelValue = item?.[rowLabel];
38
- if (labelValue) return String(labelValue);
39
- }
40
- if (item?.title) return String(item.title);
41
- if (item?.name) return String(item.name);
42
- return `${fallbackLabel} ${index + 1}`;
43
- }, [fallbackLabel, rowLabel]);
44
- const handleAdd = () => {
45
- if (disabled || readOnly || !canAddMore) return;
46
- append({});
47
- if (mode !== "inline") {
48
- const nextIndex = fields.length;
49
- setActiveIndex(nextIndex);
50
- setIsOpen(true);
51
- }
52
- };
53
- const handleRemove = (index) => {
54
- if (!canRemove) return;
55
- remove(index);
56
- if (activeIndex === null) return;
57
- if (index === activeIndex) {
58
- setIsOpen(false);
59
- setActiveIndex(null);
60
- } else if (index < activeIndex) setActiveIndex(activeIndex - 1);
61
- };
62
- const handleMove = (from, to) => {
63
- if (to < 0 || to >= fields.length) return;
64
- move(from, to);
65
- if (activeIndex === null) return;
66
- if (activeIndex === from) setActiveIndex(to);
67
- else if (activeIndex === to) setActiveIndex(from);
68
- };
69
- const handleOpenChange = (open) => {
70
- setIsOpen(open);
71
- if (!open) setActiveIndex(null);
72
- };
73
- const renderItemFields = (index) => {
74
- if (!renderFields) return /* @__PURE__ */ jsx("div", {
75
- className: "rounded-lg border border-dashed p-4 text-center",
76
- children: /* @__PURE__ */ jsx("p", {
77
- className: "text-sm text-muted-foreground",
78
- children: "Form fields not configured."
79
- })
80
- });
81
- return renderFields(index);
82
- };
83
- const emptyState = /* @__PURE__ */ jsx("div", {
84
- className: "rounded-lg border border-dashed p-4 text-center",
85
- children: /* @__PURE__ */ jsx("p", {
86
- className: "text-sm text-muted-foreground",
87
- children: placeholder || `No ${fallbackLabel} added yet`
88
- })
89
- });
90
- const editorContent = activeIndex !== null ? renderItemFields(activeIndex) : null;
91
- const editorTitle = activeIndex !== null ? resolveRowLabel(values?.[activeIndex], activeIndex) : fallbackLabel;
92
- const showEditor = mode === "modal" || mode === "drawer";
93
- return /* @__PURE__ */ jsxs("div", {
94
- className: "space-y-2",
95
- children: [
96
- label && /* @__PURE__ */ jsxs("div", {
97
- className: "flex items-center gap-2",
98
- children: [/* @__PURE__ */ jsxs("label", {
99
- htmlFor: name,
100
- className: "text-sm font-medium",
101
- children: [
102
- label,
103
- required && /* @__PURE__ */ jsx("span", {
104
- className: "text-destructive",
105
- children: "*"
106
- }),
107
- maxItems && /* @__PURE__ */ jsxs("span", {
108
- className: "ml-2 text-xs text-muted-foreground",
109
- children: [
110
- "(",
111
- fields.length,
112
- "/",
113
- maxItems,
114
- ")"
115
- ]
116
- })
117
- ]
118
- }), localized && /* @__PURE__ */ jsx(LocaleBadge, { locale: locale || "i18n" })]
119
- }),
120
- description && /* @__PURE__ */ jsx("p", {
121
- className: "text-sm text-muted-foreground",
122
- children: description
123
- }),
124
- /* @__PURE__ */ jsx("div", {
125
- className: "space-y-3",
126
- children: fields.length === 0 ? emptyState : fields.map((field, index) => {
127
- const itemValue = values?.[index];
128
- const itemLabel = resolveRowLabel(itemValue, index);
129
- const canMoveUp = orderable && index > 0;
130
- const canMoveDown = orderable && index < fields.length - 1;
131
- return /* @__PURE__ */ jsxs("div", {
132
- className: "rounded-lg border bg-card",
133
- children: [/* @__PURE__ */ jsxs("div", {
134
- className: "flex items-center justify-between border-b px-3 py-2",
135
- children: [/* @__PURE__ */ jsxs("div", {
136
- className: "flex items-center gap-2",
137
- children: [/* @__PURE__ */ jsxs("span", {
138
- className: "text-xs text-muted-foreground",
139
- children: ["#", index + 1]
140
- }), /* @__PURE__ */ jsx("span", {
141
- className: "text-sm font-medium",
142
- children: itemLabel
143
- })]
144
- }), /* @__PURE__ */ jsxs("div", {
145
- className: "flex items-center gap-1",
146
- children: [
147
- orderable && !readOnly && /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx(Button, {
148
- type: "button",
149
- variant: "ghost",
150
- size: "icon",
151
- className: "h-6 w-6",
152
- onClick: () => handleMove(index, index - 1),
153
- disabled: !canMoveUp || disabled,
154
- title: "Move up",
155
- children: /* @__PURE__ */ jsx(CaretUp, { className: "h-3 w-3" })
156
- }), /* @__PURE__ */ jsx(Button, {
157
- type: "button",
158
- variant: "ghost",
159
- size: "icon",
160
- className: "h-6 w-6",
161
- onClick: () => handleMove(index, index + 1),
162
- disabled: !canMoveDown || disabled,
163
- title: "Move down",
164
- children: /* @__PURE__ */ jsx(CaretDown, { className: "h-3 w-3" })
165
- })] }),
166
- mode !== "inline" && /* @__PURE__ */ jsx(Button, {
167
- type: "button",
168
- variant: "ghost",
169
- size: "icon",
170
- className: "h-6 w-6",
171
- onClick: () => {
172
- setActiveIndex(index);
173
- setIsOpen(true);
174
- },
175
- disabled: disabled || !renderFields,
176
- title: readOnly ? "View" : "Edit",
177
- children: /* @__PURE__ */ jsx(Pencil, { className: "h-3 w-3" })
178
- }),
179
- !readOnly && canRemove && /* @__PURE__ */ jsx(Button, {
180
- type: "button",
181
- variant: "ghost",
182
- size: "icon",
183
- className: "h-6 w-6",
184
- onClick: () => handleRemove(index),
185
- disabled,
186
- title: "Remove",
187
- children: /* @__PURE__ */ jsx(Trash, { className: "h-3 w-3" })
188
- })
189
- ]
190
- })]
191
- }), mode === "inline" && /* @__PURE__ */ jsx("div", {
192
- className: "space-y-3 p-3",
193
- children: renderItemFields(index)
194
- })]
195
- }, field.id);
196
- })
197
- }),
198
- !readOnly && canAddMore && /* @__PURE__ */ jsxs(Button, {
199
- type: "button",
200
- variant: "outline",
201
- onClick: handleAdd,
202
- disabled,
203
- children: [
204
- /* @__PURE__ */ jsx(Plus, { className: "h-4 w-4" }),
205
- "Add ",
206
- fallbackLabel
207
- ]
208
- }),
209
- error && /* @__PURE__ */ jsx("p", {
210
- className: "text-sm text-destructive",
211
- children: error
212
- }),
213
- showEditor && mode === "modal" && /* @__PURE__ */ jsx(Dialog, {
214
- open: isOpen,
215
- onOpenChange: handleOpenChange,
216
- children: /* @__PURE__ */ jsxs(DialogContent, {
217
- className: "sm:max-w-2xl",
218
- children: [/* @__PURE__ */ jsxs(DialogHeader, { children: [/* @__PURE__ */ jsx(DialogTitle, { children: editorTitle }), description && /* @__PURE__ */ jsx(DialogDescription, { children: description })] }), /* @__PURE__ */ jsx("div", {
219
- className: "space-y-4",
220
- children: editorContent
221
- })]
222
- })
223
- }),
224
- showEditor && mode === "drawer" && /* @__PURE__ */ jsx(Sheet, {
225
- open: isOpen,
226
- onOpenChange: handleOpenChange,
227
- children: /* @__PURE__ */ jsxs(SheetContent, {
228
- side: "right",
229
- className: "sm:max-w-lg",
230
- children: [
231
- /* @__PURE__ */ jsxs(SheetHeader, { children: [/* @__PURE__ */ jsx(SheetTitle, { children: editorTitle }), description && /* @__PURE__ */ jsx(SheetDescription, { children: description })] }),
232
- /* @__PURE__ */ jsx("div", {
233
- className: "px-4 pb-4",
234
- children: editorContent
235
- }),
236
- /* @__PURE__ */ jsx("div", {
237
- className: "px-4 pb-4",
238
- children: /* @__PURE__ */ jsx(Button, {
239
- type: "button",
240
- variant: "outline",
241
- onClick: () => handleOpenChange(false),
242
- children: "Close"
243
- })
244
- })
245
- ]
246
- })
247
- })
248
- ]
249
- });
250
- }
251
-
252
- //#endregion
253
- export { EmbeddedCollectionField };
@@ -1 +0,0 @@
1
- export { };
@@ -1,10 +0,0 @@
1
- import { useFormContext } from "react-hook-form";
2
-
3
- //#region src/components/fields/field-utils.ts
4
- function useResolvedControl(control) {
5
- const form = useFormContext();
6
- return control ?? form.control;
7
- }
8
-
9
- //#endregion
10
- export { useResolvedControl };
@@ -1,34 +0,0 @@
1
- import "react";
2
- import { jsx, jsxs } from "react/jsx-runtime";
3
- import { Field, FieldContent, FieldDescription, FieldError, FieldLabel } from "../ui/field";
4
- import { LocaleBadge } from "./locale-badge";
5
-
6
- //#region src/components/fields/field-wrapper.tsx
7
- function FieldWrapper({ name, label, description, required, disabled, error, localized, locale, children }) {
8
- return /* @__PURE__ */ jsx(Field, {
9
- "data-disabled": disabled,
10
- "data-invalid": !!error,
11
- children: /* @__PURE__ */ jsxs("div", {
12
- className: "space-y-2",
13
- children: [
14
- label && /* @__PURE__ */ jsxs(FieldLabel, {
15
- htmlFor: name,
16
- className: "flex items-center gap-2",
17
- children: [/* @__PURE__ */ jsxs("span", {
18
- className: "flex items-center gap-1",
19
- children: [label, required && /* @__PURE__ */ jsx("span", {
20
- className: "text-destructive",
21
- children: "*"
22
- })]
23
- }), localized && /* @__PURE__ */ jsx(LocaleBadge, { locale: locale || "i18n" })]
24
- }),
25
- /* @__PURE__ */ jsx(FieldContent, { children }),
26
- description && /* @__PURE__ */ jsx(FieldDescription, { children: description }),
27
- error && /* @__PURE__ */ jsx(FieldError, { errors: [{ message: error }] })
28
- ]
29
- })
30
- });
31
- }
32
-
33
- //#endregion
34
- export { FieldWrapper };
@@ -1,23 +0,0 @@
1
- import { LocaleBadge } from "./locale-badge";
2
- import { FieldWrapper } from "./field-wrapper";
3
- import { useResolvedControl } from "./field-utils";
4
- import { RelationSelect } from "./relation-select";
5
- import { RelationPicker } from "./relation-picker";
6
- import { RelationField } from "./relation-field";
7
- import { JsonField } from "./json-field";
8
- import { EmbeddedCollectionField } from "./embedded-collection";
9
- import { ArrayField } from "./array-field";
10
- import { RichTextEditor } from "./rich-text-editor";
11
- import { TextField } from "./text-field";
12
- import { EmailField } from "./email-field";
13
- import { PasswordField } from "./password-field";
14
- import { TextareaField } from "./textarea-field";
15
- import { NumberField } from "./number-field";
16
- import { CheckboxField } from "./checkbox-field";
17
- import { SwitchField } from "./switch-field";
18
- import { SelectField } from "./select-field";
19
- import { DateField } from "./date-field";
20
- import { DatetimeField } from "./datetime-field";
21
- import { CustomField } from "./custom-field";
22
-
23
- export { ArrayField, CheckboxField, CustomField, DateField, DatetimeField, EmailField, EmbeddedCollectionField, FieldWrapper, JsonField, LocaleBadge, NumberField, PasswordField, RelationField, RelationPicker, RelationSelect, RichTextEditor, SelectField, SwitchField, TextField, TextareaField, useResolvedControl };
@@ -1,243 +0,0 @@
1
- import * as React$1 from "react";
2
- import { jsx, jsxs } from "react/jsx-runtime";
3
- import { Button } from "../ui/button";
4
- import { Field, FieldContent, FieldDescription, FieldError, FieldLabel } from "../ui/field";
5
- import { Textarea } from "../ui/textarea";
6
- import { cn } from "../../lib/utils";
7
- import { Code, ListBullets, WarningCircle } from "@phosphor-icons/react";
8
- import { Controller, useFormContext } from "react-hook-form";
9
-
10
- //#region src/components/fields/json-field.tsx
11
- /**
12
- * JsonField Component
13
- *
14
- * JSON field with two editing modes:
15
- * - "code" - Raw JSON editing with syntax highlighting
16
- * - "form" - Structured form editing (if schema provided)
17
- *
18
- * Integrates with react-hook-form via Controller.
19
- */
20
- /**
21
- * JSON field with code editor and optional form mode.
22
- *
23
- * @example
24
- * ```tsx
25
- * // Basic JSON editor
26
- * <JsonField
27
- * name="metadata"
28
- * label="Metadata"
29
- * description="Additional metadata as JSON"
30
- * />
31
- *
32
- * // With custom form mode
33
- * <JsonField
34
- * name="settings"
35
- * label="Settings"
36
- * renderForm={({ value, onChange }) => (
37
- * <SettingsForm value={value} onChange={onChange} />
38
- * )}
39
- * />
40
- * ```
41
- */
42
- function JsonField({ name, label, description, required, disabled, readOnly, placeholder = "{\n \"key\": \"value\"\n}", defaultMode = "code", allowModeSwitch = true, minHeight = 200, maxHeight = 400, renderForm, control: controlProp, className }) {
43
- const formContext = useFormContext();
44
- const control = controlProp ?? formContext?.control;
45
- const [mode, setMode] = React$1.useState(defaultMode);
46
- if (!control) {
47
- console.warn("JsonField: No form control found. Make sure to use within FormProvider or pass control prop.");
48
- return null;
49
- }
50
- const showModeSwitch = allowModeSwitch && renderForm;
51
- return /* @__PURE__ */ jsx(Controller, {
52
- name,
53
- control,
54
- rules: {
55
- required: required ? `${label || name} is required` : void 0,
56
- validate: (value) => {
57
- if (!value) return true;
58
- if (mode === "code" && typeof value === "string") try {
59
- JSON.parse(value);
60
- return true;
61
- } catch {
62
- return "Invalid JSON format";
63
- }
64
- return true;
65
- }
66
- },
67
- render: ({ field, fieldState }) => {
68
- const error = fieldState.error?.message;
69
- return /* @__PURE__ */ jsxs(Field, {
70
- "data-invalid": !!error,
71
- className,
72
- children: [/* @__PURE__ */ jsxs("div", {
73
- className: "flex items-center justify-between",
74
- children: [label && /* @__PURE__ */ jsxs(FieldLabel, {
75
- htmlFor: name,
76
- children: [label, required && /* @__PURE__ */ jsx("span", {
77
- className: "text-destructive ml-1",
78
- children: "*"
79
- })]
80
- }), showModeSwitch && /* @__PURE__ */ jsxs("div", {
81
- className: "flex gap-1",
82
- children: [/* @__PURE__ */ jsx(Button, {
83
- type: "button",
84
- variant: mode === "code" ? "secondary" : "ghost",
85
- size: "icon-xs",
86
- onClick: () => setMode("code"),
87
- disabled,
88
- title: "Code editor",
89
- children: /* @__PURE__ */ jsx(Code, { weight: "bold" })
90
- }), /* @__PURE__ */ jsx(Button, {
91
- type: "button",
92
- variant: mode === "form" ? "secondary" : "ghost",
93
- size: "icon-xs",
94
- onClick: () => setMode("form"),
95
- disabled,
96
- title: "Form editor",
97
- children: /* @__PURE__ */ jsx(ListBullets, { weight: "bold" })
98
- })]
99
- })]
100
- }), /* @__PURE__ */ jsxs(FieldContent, { children: [
101
- mode === "code" ? /* @__PURE__ */ jsx(JsonCodeEditor, {
102
- value: field.value,
103
- onChange: field.onChange,
104
- disabled,
105
- readOnly,
106
- placeholder,
107
- minHeight,
108
- maxHeight,
109
- error: !!error
110
- }) : renderForm ? /* @__PURE__ */ jsx(JsonFormEditor, {
111
- value: field.value,
112
- onChange: field.onChange,
113
- disabled,
114
- readOnly,
115
- renderForm
116
- }) : /* @__PURE__ */ jsx(JsonCodeEditor, {
117
- value: field.value,
118
- onChange: field.onChange,
119
- disabled,
120
- readOnly,
121
- placeholder,
122
- minHeight,
123
- maxHeight,
124
- error: !!error
125
- }),
126
- description && !error && /* @__PURE__ */ jsx(FieldDescription, { children: description }),
127
- /* @__PURE__ */ jsx(FieldError, { children: error })
128
- ] })]
129
- });
130
- }
131
- });
132
- }
133
- /**
134
- * Code editor for JSON (using Textarea for simplicity)
135
- * Can be replaced with Monaco/CodeMirror in the future
136
- */
137
- function JsonCodeEditor({ value, onChange, disabled, readOnly, placeholder, minHeight, maxHeight, error }) {
138
- const [localValue, setLocalValue] = React$1.useState(() => {
139
- if (typeof value === "string") return value;
140
- if (value === null || value === void 0) return "";
141
- try {
142
- return JSON.stringify(value, null, 2);
143
- } catch {
144
- return "";
145
- }
146
- });
147
- const [parseError, setParseError] = React$1.useState(null);
148
- React$1.useEffect(() => {
149
- if (typeof value === "string") setLocalValue(value);
150
- else if (value !== null && value !== void 0) try {
151
- setLocalValue(JSON.stringify(value, null, 2));
152
- } catch {}
153
- else setLocalValue("");
154
- }, [value]);
155
- const handleChange = (e) => {
156
- const newValue = e.target.value;
157
- setLocalValue(newValue);
158
- if (!newValue.trim()) {
159
- setParseError(null);
160
- onChange(null);
161
- return;
162
- }
163
- try {
164
- const parsed = JSON.parse(newValue);
165
- setParseError(null);
166
- onChange(parsed);
167
- } catch (err) {
168
- setParseError("Invalid JSON");
169
- onChange(newValue);
170
- }
171
- };
172
- const handleFormat = () => {
173
- try {
174
- const parsed = JSON.parse(localValue);
175
- setLocalValue(JSON.stringify(parsed, null, 2));
176
- setParseError(null);
177
- onChange(parsed);
178
- } catch {}
179
- };
180
- return /* @__PURE__ */ jsxs("div", {
181
- className: "space-y-2",
182
- children: [/* @__PURE__ */ jsxs("div", {
183
- className: "relative",
184
- children: [/* @__PURE__ */ jsx(Textarea, {
185
- value: localValue,
186
- onChange: handleChange,
187
- disabled,
188
- readOnly,
189
- placeholder,
190
- className: cn("font-mono text-xs", error || parseError ? "border-destructive" : ""),
191
- style: {
192
- minHeight: `${minHeight}px`,
193
- maxHeight: maxHeight ? `${maxHeight}px` : void 0,
194
- resize: maxHeight ? "none" : "vertical"
195
- },
196
- "aria-invalid": !!error || !!parseError
197
- }), parseError && /* @__PURE__ */ jsxs("div", {
198
- className: "text-destructive absolute right-2 top-2 flex items-center gap-1 text-xs",
199
- children: [/* @__PURE__ */ jsx(WarningCircle, {
200
- weight: "fill",
201
- className: "size-3"
202
- }), parseError]
203
- })]
204
- }), !readOnly && !disabled && localValue && /* @__PURE__ */ jsx("div", {
205
- className: "flex justify-end",
206
- children: /* @__PURE__ */ jsx(Button, {
207
- type: "button",
208
- variant: "ghost",
209
- size: "xs",
210
- onClick: handleFormat,
211
- disabled: !!parseError,
212
- children: "Format JSON"
213
- })
214
- })]
215
- });
216
- }
217
- /**
218
- * Form-based editor wrapper
219
- */
220
- function JsonFormEditor({ value, onChange, disabled, readOnly, renderForm }) {
221
- const safeValue = React$1.useMemo(() => {
222
- if (typeof value === "object" && value !== null) return value;
223
- if (typeof value === "string") try {
224
- return JSON.parse(value);
225
- } catch {
226
- return {};
227
- }
228
- return {};
229
- }, [value]);
230
- if (!renderForm) return null;
231
- return /* @__PURE__ */ jsx("div", {
232
- className: "rounded-lg border p-4",
233
- children: renderForm({
234
- value: safeValue,
235
- onChange,
236
- disabled,
237
- readOnly
238
- })
239
- });
240
- }
241
-
242
- //#endregion
243
- export { JsonField };
@@ -1,16 +0,0 @@
1
- import "react";
2
- import { jsx } from "react/jsx-runtime";
3
- import { Badge } from "../ui/badge";
4
-
5
- //#region src/components/fields/locale-badge.tsx
6
- function LocaleBadge({ locale }) {
7
- if (!locale) return null;
8
- return /* @__PURE__ */ jsx(Badge, {
9
- variant: "secondary",
10
- className: "uppercase text-[10px] tracking-wide",
11
- children: locale
12
- });
13
- }
14
-
15
- //#endregion
16
- export { LocaleBadge };
@@ -1,39 +0,0 @@
1
- import { jsx } from "react/jsx-runtime";
2
- import { NumberInput } from "../primitives/number-input";
3
- import { Controller } from "react-hook-form";
4
- import { FieldWrapper } from "./field-wrapper";
5
- import { useResolvedControl } from "./field-utils";
6
-
7
- //#region src/components/fields/number-field.tsx
8
- function NumberField({ name, label, description, placeholder, required, disabled, localized, locale, control, className, min, max, step, showButtons }) {
9
- return /* @__PURE__ */ jsx(Controller, {
10
- name,
11
- control: useResolvedControl(control),
12
- render: ({ field, fieldState }) => /* @__PURE__ */ jsx(FieldWrapper, {
13
- name,
14
- label,
15
- description,
16
- required,
17
- disabled,
18
- localized,
19
- locale,
20
- error: fieldState.error?.message,
21
- children: /* @__PURE__ */ jsx(NumberInput, {
22
- id: name,
23
- value: field.value ?? null,
24
- onChange: field.onChange,
25
- placeholder,
26
- disabled,
27
- min,
28
- max,
29
- step,
30
- showButtons,
31
- "aria-invalid": !!fieldState.error,
32
- className
33
- })
34
- })
35
- });
36
- }
37
-
38
- //#endregion
39
- export { NumberField };
@@ -1,37 +0,0 @@
1
- import { jsx } from "react/jsx-runtime";
2
- import { TextInput } from "../primitives/text-input";
3
- import { Controller } from "react-hook-form";
4
- import { FieldWrapper } from "./field-wrapper";
5
- import { useResolvedControl } from "./field-utils";
6
-
7
- //#region src/components/fields/password-field.tsx
8
- function PasswordField({ name, label, description, placeholder, required, disabled, localized, locale, control, className }) {
9
- return /* @__PURE__ */ jsx(Controller, {
10
- name,
11
- control: useResolvedControl(control),
12
- render: ({ field, fieldState }) => /* @__PURE__ */ jsx(FieldWrapper, {
13
- name,
14
- label,
15
- description,
16
- required,
17
- disabled,
18
- localized,
19
- locale,
20
- error: fieldState.error?.message,
21
- children: /* @__PURE__ */ jsx(TextInput, {
22
- id: name,
23
- value: field.value ?? "",
24
- onChange: field.onChange,
25
- type: "password",
26
- placeholder,
27
- disabled,
28
- autoComplete: "current-password",
29
- "aria-invalid": !!fieldState.error,
30
- className
31
- })
32
- })
33
- });
34
- }
35
-
36
- //#endregion
37
- export { PasswordField };