@byline/admin 2.5.2 → 2.6.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 (260) hide show
  1. package/dist/fields/array/array-field.d.ts +14 -0
  2. package/dist/fields/array/array-field.js +177 -0
  3. package/dist/fields/array/array-field.module.js +11 -0
  4. package/dist/fields/array/array-field_module.css +32 -0
  5. package/dist/fields/blocks/blocks-field.d.ts +13 -0
  6. package/dist/fields/blocks/blocks-field.js +245 -0
  7. package/dist/fields/blocks/blocks-field.module.js +26 -0
  8. package/dist/fields/blocks/blocks-field_module.css +107 -0
  9. package/dist/fields/checkbox/checkbox-field.d.ts +16 -0
  10. package/dist/fields/checkbox/checkbox-field.js +28 -0
  11. package/dist/fields/checkbox/checkbox-field.module.js +6 -0
  12. package/dist/fields/checkbox/checkbox-field_module.css +4 -0
  13. package/dist/fields/column-formatter.d.ts +20 -0
  14. package/dist/fields/column-formatter.js +15 -0
  15. package/dist/fields/date-time-formatter.d.ts +16 -0
  16. package/dist/fields/date-time-formatter.js +8 -0
  17. package/dist/fields/datetime/datetime-field.d.ts +16 -0
  18. package/dist/fields/datetime/datetime-field.js +37 -0
  19. package/dist/fields/datetime/datetime-field.module.js +5 -0
  20. package/dist/fields/datetime/datetime-field_module.css +4 -0
  21. package/dist/fields/draggable-context-menu.d.ts +6 -0
  22. package/dist/fields/draggable-context-menu.js +85 -0
  23. package/dist/fields/draggable-context-menu.module.js +15 -0
  24. package/dist/fields/draggable-context-menu_module.css +91 -0
  25. package/dist/fields/field-helpers.d.ts +26 -0
  26. package/dist/fields/field-helpers.js +50 -0
  27. package/dist/fields/field-renderer.d.ts +37 -0
  28. package/dist/fields/field-renderer.js +206 -0
  29. package/dist/fields/field-renderer.module.js +8 -0
  30. package/dist/fields/field-renderer_module.css +11 -0
  31. package/dist/fields/field-services-context.d.ts +16 -0
  32. package/dist/fields/field-services-context.js +13 -0
  33. package/dist/fields/field-services-types.d.ts +63 -0
  34. package/dist/fields/field-services-types.js +1 -0
  35. package/dist/fields/file/file-field.d.ts +19 -0
  36. package/dist/fields/file/file-field.js +225 -0
  37. package/dist/fields/file/file-field.module.js +18 -0
  38. package/dist/fields/file/file-field_module.css +131 -0
  39. package/dist/fields/file/file-upload-field.d.ts +21 -0
  40. package/dist/fields/file/file-upload-field.js +130 -0
  41. package/dist/fields/file/file-upload-field.module.js +15 -0
  42. package/dist/fields/file/file-upload-field_module.css +74 -0
  43. package/dist/fields/group/group-field.d.ts +15 -0
  44. package/dist/fields/group/group-field.js +59 -0
  45. package/dist/fields/group/group-field.module.js +9 -0
  46. package/dist/fields/group/group-field_module.css +27 -0
  47. package/dist/fields/image/image-field.d.ts +19 -0
  48. package/dist/fields/image/image-field.js +241 -0
  49. package/dist/fields/image/image-field.module.js +22 -0
  50. package/dist/fields/image/image-field_module.css +121 -0
  51. package/dist/fields/image/image-upload-field.d.ts +21 -0
  52. package/dist/fields/image/image-upload-field.js +190 -0
  53. package/dist/fields/image/image-upload-field.module.js +19 -0
  54. package/dist/fields/image/image-upload-field_module.css +92 -0
  55. package/dist/fields/local-date-time.d.ts +27 -0
  56. package/dist/fields/local-date-time.js +49 -0
  57. package/dist/fields/locale-badge.d.ts +18 -0
  58. package/dist/fields/locale-badge.js +10 -0
  59. package/dist/fields/locale-badge.module.js +5 -0
  60. package/dist/fields/locale-badge_module.css +27 -0
  61. package/dist/fields/numerical/numerical-field.d.ts +18 -0
  62. package/dist/fields/numerical/numerical-field.js +74 -0
  63. package/dist/fields/relation/relation-display.d.ts +40 -0
  64. package/dist/fields/relation/relation-display.js +58 -0
  65. package/dist/fields/relation/relation-display.module.js +9 -0
  66. package/dist/fields/relation/relation-display_module.css +21 -0
  67. package/dist/fields/relation/relation-field.d.ts +18 -0
  68. package/dist/fields/relation/relation-field.js +138 -0
  69. package/dist/fields/relation/relation-field.module.js +13 -0
  70. package/dist/fields/relation/relation-field_module.css +62 -0
  71. package/dist/fields/relation/relation-picker.d.ts +49 -0
  72. package/dist/fields/relation/relation-picker.js +236 -0
  73. package/dist/fields/relation/relation-picker.module.js +26 -0
  74. package/dist/fields/relation/relation-picker_module.css +124 -0
  75. package/dist/fields/relation/relation-summary.d.ts +31 -0
  76. package/dist/fields/relation/relation-summary.js +50 -0
  77. package/dist/fields/relation/relation-summary.module.js +11 -0
  78. package/dist/fields/relation/relation-summary_module.css +37 -0
  79. package/dist/fields/select/select-field.d.ts +16 -0
  80. package/dist/fields/select/select-field.js +50 -0
  81. package/dist/fields/select/select-field.module.js +5 -0
  82. package/dist/fields/select/select-field_module.css +4 -0
  83. package/dist/fields/sortable-item.d.ts +15 -0
  84. package/dist/fields/sortable-item.js +81 -0
  85. package/dist/fields/sortable-item.module.js +22 -0
  86. package/dist/fields/sortable-item_module.css +124 -0
  87. package/dist/fields/text/text-field.d.ts +20 -0
  88. package/dist/fields/text/text-field.js +104 -0
  89. package/dist/fields/text/text-field.module.js +6 -0
  90. package/dist/fields/text/text-field_module.css +5 -0
  91. package/dist/fields/text-area/text-area-field.d.ts +20 -0
  92. package/dist/fields/text-area/text-area-field.js +105 -0
  93. package/dist/fields/text-area/text-area-field.module.js +6 -0
  94. package/dist/fields/text-area/text-area-field_module.css +5 -0
  95. package/dist/fields/use-field-change-handler.d.ts +23 -0
  96. package/dist/fields/use-field-change-handler.js +52 -0
  97. package/dist/forms/document-actions.d.ts +48 -0
  98. package/dist/forms/document-actions.js +475 -0
  99. package/dist/forms/document-actions.module.js +34 -0
  100. package/dist/forms/document-actions_module.css +118 -0
  101. package/dist/forms/form-context.d.ts +89 -0
  102. package/dist/forms/form-context.js +466 -0
  103. package/dist/forms/form-renderer.d.ts +98 -0
  104. package/dist/forms/form-renderer.js +597 -0
  105. package/dist/forms/form-renderer.module.js +46 -0
  106. package/dist/forms/form-renderer_module.css +245 -0
  107. package/dist/forms/navigation-guard.d.ts +54 -0
  108. package/dist/forms/navigation-guard.js +22 -0
  109. package/dist/forms/path-widget.d.ts +36 -0
  110. package/dist/forms/path-widget.js +116 -0
  111. package/dist/forms/path-widget.module.js +8 -0
  112. package/dist/forms/path-widget_module.css +29 -0
  113. package/dist/forms/upload-executor.d.ts +57 -0
  114. package/dist/forms/upload-executor.js +94 -0
  115. package/dist/lib/translate-validation-error.d.ts +36 -0
  116. package/dist/lib/translate-validation-error.js +11 -0
  117. package/dist/modules/admin-account/commands.d.ts +2 -1
  118. package/dist/modules/admin-account/commands.js +13 -2
  119. package/dist/modules/admin-account/components/change-password.js +45 -36
  120. package/dist/modules/admin-account/components/container.js +185 -134
  121. package/dist/modules/admin-account/components/preferences.d.ts +8 -0
  122. package/dist/modules/admin-account/components/preferences.js +152 -0
  123. package/dist/modules/admin-account/components/preferences.module.js +11 -0
  124. package/dist/modules/admin-account/components/preferences_module.css +41 -0
  125. package/dist/modules/admin-account/components/update.js +50 -31
  126. package/dist/modules/admin-account/index.d.ts +3 -3
  127. package/dist/modules/admin-account/index.js +2 -2
  128. package/dist/modules/admin-account/schemas.d.ts +4 -0
  129. package/dist/modules/admin-account/schemas.js +4 -1
  130. package/dist/modules/admin-account/service.d.ts +1 -0
  131. package/dist/modules/admin-account/service.js +8 -0
  132. package/dist/modules/admin-permissions/components/inspector.js +31 -41
  133. package/dist/modules/admin-roles/components/create.js +43 -26
  134. package/dist/modules/admin-roles/components/permissions.js +26 -35
  135. package/dist/modules/admin-roles/components/update.js +26 -16
  136. package/dist/modules/admin-users/components/create.js +60 -40
  137. package/dist/modules/admin-users/components/roles.js +9 -15
  138. package/dist/modules/admin-users/components/set-password.js +30 -31
  139. package/dist/modules/admin-users/components/update.js +58 -39
  140. package/dist/modules/admin-users/dto.js +1 -0
  141. package/dist/modules/admin-users/repository.d.ts +17 -0
  142. package/dist/modules/admin-users/schemas.d.ts +4 -0
  143. package/dist/modules/admin-users/schemas.js +6 -2
  144. package/dist/modules/auth/components/sign-in-form.js +10 -8
  145. package/dist/presentation/group.d.ts +27 -0
  146. package/dist/presentation/group.js +14 -0
  147. package/dist/presentation/group.module.js +6 -0
  148. package/dist/presentation/group_module.css +19 -0
  149. package/dist/presentation/row.d.ts +25 -0
  150. package/dist/presentation/row.js +8 -0
  151. package/dist/presentation/row.module.js +5 -0
  152. package/dist/presentation/row_module.css +18 -0
  153. package/dist/presentation/tabs.d.ts +25 -0
  154. package/dist/presentation/tabs.js +39 -0
  155. package/dist/presentation/tabs.module.js +10 -0
  156. package/dist/presentation/tabs_module.css +68 -0
  157. package/dist/react.d.ts +66 -0
  158. package/dist/react.js +36 -0
  159. package/dist/services/admin-services-types.d.ts +16 -0
  160. package/dist/widgets/diff-viewer/diff-modal.d.ts +22 -0
  161. package/dist/widgets/diff-viewer/diff-modal.js +149 -0
  162. package/dist/widgets/diff-viewer/diff-modal.module.js +14 -0
  163. package/dist/widgets/diff-viewer/diff-modal_module.css +56 -0
  164. package/dist/widgets/status-badge/status-badge.d.ts +25 -0
  165. package/dist/widgets/status-badge/status-badge.js +37 -0
  166. package/dist/widgets/status-badge/status-badge.module.js +7 -0
  167. package/dist/widgets/status-badge/status-badge_module.css +20 -0
  168. package/package.json +14 -4
  169. package/src/fields/array/array-field.module.css +48 -0
  170. package/src/fields/array/array-field.tsx +267 -0
  171. package/src/fields/blocks/blocks-field.module.css +148 -0
  172. package/src/fields/blocks/blocks-field.tsx +323 -0
  173. package/src/fields/checkbox/checkbox-field.module.css +4 -0
  174. package/src/fields/checkbox/checkbox-field.tsx +54 -0
  175. package/src/fields/column-formatter.tsx +31 -0
  176. package/src/fields/date-time-formatter.tsx +22 -0
  177. package/src/fields/datetime/datetime-field.module.css +13 -0
  178. package/src/fields/datetime/datetime-field.tsx +54 -0
  179. package/src/fields/draggable-context-menu.module.css +127 -0
  180. package/src/fields/draggable-context-menu.tsx +87 -0
  181. package/src/fields/field-helpers.ts +69 -0
  182. package/src/fields/field-renderer.module.css +22 -0
  183. package/src/fields/field-renderer.tsx +288 -0
  184. package/src/fields/field-services-context.tsx +35 -0
  185. package/src/fields/field-services-types.ts +68 -0
  186. package/src/fields/file/file-field.module.css +153 -0
  187. package/src/fields/file/file-field.tsx +286 -0
  188. package/src/fields/file/file-upload-field.module.css +101 -0
  189. package/src/fields/file/file-upload-field.tsx +187 -0
  190. package/src/fields/group/group-field.module.css +43 -0
  191. package/src/fields/group/group-field.tsx +84 -0
  192. package/src/fields/image/image-field.module.css +155 -0
  193. package/src/fields/image/image-field.tsx +306 -0
  194. package/src/fields/image/image-upload-field.module.css +123 -0
  195. package/src/fields/image/image-upload-field.tsx +276 -0
  196. package/src/fields/local-date-time.tsx +88 -0
  197. package/src/fields/locale-badge.module.css +37 -0
  198. package/src/fields/locale-badge.tsx +32 -0
  199. package/src/fields/numerical/numerical-field.tsx +114 -0
  200. package/src/fields/relation/relation-display.module.css +36 -0
  201. package/src/fields/relation/relation-display.tsx +130 -0
  202. package/src/fields/relation/relation-field.module.css +83 -0
  203. package/src/fields/relation/relation-field.tsx +211 -0
  204. package/src/fields/relation/relation-picker.module.css +168 -0
  205. package/src/fields/relation/relation-picker.tsx +326 -0
  206. package/src/fields/relation/relation-summary.module.css +55 -0
  207. package/src/fields/relation/relation-summary.tsx +123 -0
  208. package/src/fields/select/select-field.module.css +13 -0
  209. package/src/fields/select/select-field.tsx +61 -0
  210. package/src/fields/sortable-item.module.css +167 -0
  211. package/src/fields/sortable-item.tsx +106 -0
  212. package/src/fields/text/text-field.module.css +13 -0
  213. package/src/fields/text/text-field.tsx +146 -0
  214. package/src/fields/text-area/text-area-field.module.css +13 -0
  215. package/src/fields/text-area/text-area-field.tsx +147 -0
  216. package/src/fields/use-field-change-handler.ts +112 -0
  217. package/src/forms/document-actions.module.css +160 -0
  218. package/src/forms/document-actions.tsx +482 -0
  219. package/src/forms/form-context.tsx +704 -0
  220. package/src/forms/form-renderer.module.css +321 -0
  221. package/src/forms/form-renderer.tsx +891 -0
  222. package/src/forms/navigation-guard.tsx +98 -0
  223. package/src/forms/path-widget.module.css +41 -0
  224. package/src/forms/path-widget.test.tsx +217 -0
  225. package/src/forms/path-widget.tsx +183 -0
  226. package/src/forms/upload-executor.ts +192 -0
  227. package/src/lib/translate-validation-error.ts +56 -0
  228. package/src/modules/admin-account/commands.ts +13 -0
  229. package/src/modules/admin-account/components/change-password.tsx +46 -31
  230. package/src/modules/admin-account/components/container.tsx +83 -38
  231. package/src/modules/admin-account/components/preferences.module.css +60 -0
  232. package/src/modules/admin-account/components/preferences.tsx +203 -0
  233. package/src/modules/admin-account/components/update.tsx +53 -27
  234. package/src/modules/admin-account/index.ts +3 -0
  235. package/src/modules/admin-account/schemas.ts +13 -0
  236. package/src/modules/admin-account/service.ts +12 -0
  237. package/src/modules/admin-permissions/components/inspector.tsx +22 -14
  238. package/src/modules/admin-roles/components/create.tsx +51 -23
  239. package/src/modules/admin-roles/components/permissions.tsx +25 -21
  240. package/src/modules/admin-roles/components/update.tsx +37 -19
  241. package/src/modules/admin-users/components/create.tsx +63 -34
  242. package/src/modules/admin-users/components/roles.tsx +9 -8
  243. package/src/modules/admin-users/components/set-password.tsx +34 -28
  244. package/src/modules/admin-users/components/update.tsx +58 -36
  245. package/src/modules/admin-users/dto.ts +1 -0
  246. package/src/modules/admin-users/repository.ts +17 -0
  247. package/src/modules/admin-users/schemas.ts +12 -0
  248. package/src/modules/auth/components/sign-in-form.tsx +14 -8
  249. package/src/presentation/group.module.css +41 -0
  250. package/src/presentation/group.tsx +40 -0
  251. package/src/presentation/row.module.css +32 -0
  252. package/src/presentation/row.tsx +33 -0
  253. package/src/presentation/tabs.module.css +107 -0
  254. package/src/presentation/tabs.tsx +84 -0
  255. package/src/react.ts +84 -0
  256. package/src/services/admin-services-types.ts +18 -0
  257. package/src/widgets/diff-viewer/diff-modal.module.css +79 -0
  258. package/src/widgets/diff-viewer/diff-modal.tsx +186 -0
  259. package/src/widgets/status-badge/status-badge.module.css +31 -0
  260. package/src/widgets/status-badge/status-badge.tsx +71 -0
@@ -0,0 +1,245 @@
1
+ :is(.form-MVxxVb, .byline-form) {
2
+ flex-direction: column;
3
+ width: 100%;
4
+ display: flex;
5
+ }
6
+
7
+ :is(.heading-row-qw_UYh, .byline-form-heading-row) {
8
+ align-items: start;
9
+ gap: .25rem var(--spacing-16);
10
+ margin-bottom: var(--spacing-8);
11
+ grid-template-columns: 1fr;
12
+ display: grid;
13
+ }
14
+
15
+ @media (min-width: 40rem) {
16
+ :is(.heading-row-qw_UYh, .byline-form-heading-row) {
17
+ grid-template-columns: 1fr auto;
18
+ }
19
+ }
20
+
21
+ :is(.heading-wnLlb_, .byline-form-heading) {
22
+ margin-bottom: 0;
23
+ font-size: 1.75rem;
24
+ }
25
+
26
+ :is(.status-bar-kQCXLT, .byline-form-status-bar) {
27
+ z-index: 20;
28
+ align-items: start;
29
+ gap: .25rem var(--spacing-16);
30
+ padding: var(--spacing-8);
31
+ border: var(--border-width-thin) var(--border-style-solid) var(--gray-100);
32
+ border-radius: var(--border-radius-sm);
33
+ background-color: var(--canvas-25);
34
+ grid-template-columns: 1fr;
35
+ margin-bottom: .25rem;
36
+ display: grid;
37
+ position: sticky;
38
+ top: 45px;
39
+ }
40
+
41
+ @media (min-width: 40rem) {
42
+ :is(.status-bar-kQCXLT, .byline-form-status-bar) {
43
+ grid-template-columns: 1fr auto;
44
+ }
45
+ }
46
+
47
+ @media (min-width: 66rem) {
48
+ :is(.status-bar-kQCXLT, .byline-form-status-bar) {
49
+ margin-bottom: 0;
50
+ }
51
+ }
52
+
53
+ :is(.status-XbhkJR, .byline-form-status) {
54
+ flex-direction: column;
55
+ justify-content: center;
56
+ height: 100%;
57
+ display: flex;
58
+ }
59
+
60
+ :is(.status-meta-gppNXX, .byline-form-status-meta) {
61
+ flex-direction: column;
62
+ font-size: .8rem;
63
+ line-height: 1.25;
64
+ display: flex;
65
+ }
66
+
67
+ @media (min-width: 48rem) {
68
+ :is(.status-meta-gppNXX, .byline-form-status-meta) {
69
+ margin-bottom: .25rem;
70
+ line-height: .75rem;
71
+ }
72
+ }
73
+
74
+ @media (min-width: 66rem) {
75
+ :is(.status-meta-gppNXX, .byline-form-status-meta) {
76
+ flex-direction: row;
77
+ align-items: center;
78
+ }
79
+ }
80
+
81
+ @media (min-width: 40rem) {
82
+ :is(.status-meta-gppNXX, .byline-form-status-meta) {
83
+ gap: var(--spacing-8);
84
+ }
85
+ }
86
+
87
+ :is(.status-cell-Tr3QHl, .byline-form-status-cell) {
88
+ align-items: center;
89
+ gap: .25rem;
90
+ min-width: 0;
91
+ display: flex;
92
+ }
93
+
94
+ :is(.status-muted-vHn34O, .byline-form-status-muted) {
95
+ color: var(--gray-500);
96
+ flex-shrink: 0;
97
+ }
98
+
99
+ :is(.status-trunc-jGiHWf, .byline-form-status-trunc) {
100
+ text-overflow: ellipsis;
101
+ white-space: nowrap;
102
+ overflow: hidden;
103
+ }
104
+
105
+ :is(.status-published-hqosWb, .byline-form-status-published) {
106
+ font-size: .8rem;
107
+ line-height: 1rem;
108
+ display: inline;
109
+ }
110
+
111
+ @media (min-width: 48rem) {
112
+ :is(.status-published-hqosWb, .byline-form-status-published) {
113
+ line-height: .875rem;
114
+ }
115
+ }
116
+
117
+ :is(.status-unpublish-DiCNI0, .byline-form-status-unpublish) {
118
+ color: inherit;
119
+ cursor: pointer;
120
+ background: none;
121
+ border: none;
122
+ padding: 0;
123
+ font-size: .8rem;
124
+ text-decoration: underline;
125
+ }
126
+
127
+ :is(.actions-AZBIdR, .byline-form-actions) {
128
+ align-items: center;
129
+ gap: var(--spacing-8);
130
+ display: flex;
131
+ }
132
+
133
+ :is(.actions-button-VIwbST, .byline-form-actions-button) {
134
+ min-width: 70px;
135
+ min-height: 28px;
136
+ }
137
+
138
+ :is(.actions-status-wrap-hSvlps, .byline-form-actions-status-wrap) {
139
+ z-index: 10;
140
+ position: relative;
141
+ }
142
+
143
+ :is(.actions-combo-button-XvqHCC, .byline-form-actions-combo-button) {
144
+ min-width: 100px;
145
+ min-height: 28px;
146
+ }
147
+
148
+ :is(.actions-combo-trigger-bmXUzc, .byline-form-actions-combo-trigger) {
149
+ min-height: 28px;
150
+ }
151
+
152
+ :is(.layout-WTbLYr, .byline-form-layout) {
153
+ gap: var(--spacing-12);
154
+ padding-top: var(--spacing-32);
155
+ flex-direction: column;
156
+ display: flex;
157
+ }
158
+
159
+ @media (min-width: 60rem) {
160
+ :is(.layout-WTbLYr, .byline-form-layout) {
161
+ gap: var(--spacing-32);
162
+ grid-column-gap: 36px;
163
+ grid-template-columns: minmax(0, 1fr) .4fr;
164
+ align-items: start;
165
+ display: grid;
166
+ }
167
+ }
168
+
169
+ :is(.content-_P5cdJ, .byline-form-content) {
170
+ gap: var(--spacing-20);
171
+ flex-direction: column;
172
+ max-width: 100%;
173
+ margin-bottom: 2.75rem;
174
+ display: flex;
175
+ }
176
+
177
+ @media (min-width: 60rem) {
178
+ :is(.content-_P5cdJ, .byline-form-content) {
179
+ margin-bottom: 3.75rem;
180
+ }
181
+ }
182
+
183
+ :is(.sidebar-WsxX88, .byline-form-sidebar) {
184
+ gap: var(--spacing-20);
185
+ background-color: oklch(from var(--canvas-50) l c h / .2);
186
+ flex-direction: column;
187
+ max-width: 100%;
188
+ margin-top: 0;
189
+ margin-bottom: 4rem;
190
+ display: flex;
191
+ }
192
+
193
+ @media (min-width: 60rem) {
194
+ :is(.sidebar-WsxX88, .byline-form-sidebar) {
195
+ padding-top: .25rem;
196
+ padding-right: 12px;
197
+ padding-left: var(--spacing-16);
198
+ border-left: var(--border-width-thin) var(--border-style-solid) var(--gray-100);
199
+ margin-bottom: 0;
200
+ position: sticky;
201
+ top: 95px;
202
+ }
203
+ }
204
+
205
+ :is(.tabset-xfaMkP, .byline-form-tabset) {
206
+ gap: var(--spacing-20);
207
+ flex-direction: column;
208
+ display: flex;
209
+ }
210
+
211
+ :is(.tabset-tabs-jZpqd_, .byline-form-tabset-tabs) {
212
+ margin-top: -1rem;
213
+ margin-bottom: 0;
214
+ }
215
+
216
+ :is(.tabset-fields-JJefdw, .byline-form-tabset-fields) {
217
+ gap: var(--spacing-20);
218
+ flex-direction: column;
219
+ display: flex;
220
+ }
221
+
222
+ :is(.guard-modal-head-r2TApi, .byline-form-guard-modal-head) {
223
+ margin-bottom: var(--spacing-8);
224
+ padding-top: 1rem;
225
+ }
226
+
227
+ :is(.guard-modal-title-p9dFJ9, .byline-form-guard-modal-title) {
228
+ margin: 0 0 var(--spacing-8) 0;
229
+ font-size: var(--font-size-2xl);
230
+ }
231
+
232
+ :is(.guard-modal-text-uW56HS, .byline-form-guard-modal-text) {
233
+ font-size: var(--font-size-sm);
234
+ }
235
+
236
+ :is(:is([data-theme="dark"], .dark) .status-bar-kQCXLT, :is([data-theme="dark"], .dark) .byline-form-status-bar) {
237
+ background-color: var(--canvas-800);
238
+ border: var(--border-width-thin) var(--border-style-solid) var(--gray-700);
239
+ }
240
+
241
+ :is(:is([data-theme="dark"], .dark) .sidebar-WsxX88, :is([data-theme="dark"], .dark) .byline-form-sidebar) {
242
+ border-left-color: var(--gray-800);
243
+ background-color: var(--canvas-900);
244
+ }
245
+
@@ -0,0 +1,54 @@
1
+ /**
2
+ * This Source Code is subject to the terms of the Mozilla Public
3
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
4
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
5
+ *
6
+ * Copyright (c) Infonomic Company Limited
7
+ */
8
+ /** The result returned by a `UseNavigationGuard` hook. */
9
+ export interface NavigationGuardResult {
10
+ /** Whether a navigation attempt is currently being blocked (show confirmation UI). */
11
+ isBlocked: boolean;
12
+ /** Cancel the pending navigation — stay on the current page. */
13
+ stay: () => void;
14
+ /** Confirm the pending navigation — leave the page. */
15
+ proceed: () => void;
16
+ }
17
+ /**
18
+ * A hook that blocks in-app navigation and (optionally) browser unload when
19
+ * `shouldBlock` is `true`.
20
+ *
21
+ * Each framework adapter implements this signature.
22
+ */
23
+ export type UseNavigationGuard = (shouldBlock: boolean) => NavigationGuardResult;
24
+ /**
25
+ * Fallback navigation guard that only handles the browser's native
26
+ * `beforeunload` event. In-app (client-side) route changes are **not**
27
+ * intercepted — `isBlocked` will never become `true`.
28
+ *
29
+ * This is used when no framework-specific adapter has been provided.
30
+ */
31
+ export declare const useBeforeUnloadGuard: UseNavigationGuard;
32
+ /**
33
+ * Provide a framework-specific `UseNavigationGuard` hook to all descendant
34
+ * `FormRenderer` instances.
35
+ *
36
+ * ```tsx
37
+ * import { NavigationGuardProvider } from './navigation-guard'
38
+ * import { useTanStackNavigationGuard } from './tanstack-navigation-guard'
39
+ *
40
+ * function App() {
41
+ * return (
42
+ * <NavigationGuardProvider value={useTanStackNavigationGuard}>
43
+ * <Outlet />
44
+ * </NavigationGuardProvider>
45
+ * )
46
+ * }
47
+ * ```
48
+ */
49
+ export declare const NavigationGuardProvider: import("react").Provider<UseNavigationGuard>;
50
+ /**
51
+ * Consume the current `UseNavigationGuard` hook from context.
52
+ * Falls back to `useBeforeUnloadGuard` when no provider is present.
53
+ */
54
+ export declare const useNavigationGuardAdapter: () => UseNavigationGuard;
@@ -0,0 +1,22 @@
1
+ import { createContext, useContext, useEffect } from "react";
2
+ const useBeforeUnloadGuard = (shouldBlock)=>{
3
+ useEffect(()=>{
4
+ if (!shouldBlock) return;
5
+ const handler = (e)=>{
6
+ e.preventDefault();
7
+ };
8
+ window.addEventListener('beforeunload', handler);
9
+ return ()=>window.removeEventListener('beforeunload', handler);
10
+ }, [
11
+ shouldBlock
12
+ ]);
13
+ return {
14
+ isBlocked: false,
15
+ stay: ()=>{},
16
+ proceed: ()=>{}
17
+ };
18
+ };
19
+ const NavigationGuardContext = /*#__PURE__*/ createContext(useBeforeUnloadGuard);
20
+ const NavigationGuardProvider = NavigationGuardContext.Provider;
21
+ const useNavigationGuardAdapter = ()=>useContext(NavigationGuardContext);
22
+ export { NavigationGuardProvider, useBeforeUnloadGuard, useNavigationGuardAdapter };
@@ -0,0 +1,36 @@
1
+ export interface PathWidgetProps {
2
+ /** The collection's `useAsPath` source field name, when configured. */
3
+ useAsPath: string | undefined;
4
+ /** Collection path, forwarded to the slugifier as context. */
5
+ collectionPath: string;
6
+ /** Default content locale, forwarded to the slugifier as context. */
7
+ defaultLocale: string;
8
+ /**
9
+ * The locale currently being edited in the form. When this differs
10
+ * from `defaultLocale` (i.e. the editor is editing a translation),
11
+ * the widget renders read-only — phase 1 paths are default-locale
12
+ * territory, and the lifecycle drops translation-locale path changes
13
+ * with a warn. Locking the input prevents the warn path being hit
14
+ * through the admin form and gives editors a clear cue.
15
+ */
16
+ activeLocale: string;
17
+ /** `'create'` shows the live derived preview as placeholder text. */
18
+ mode: 'create' | 'edit';
19
+ }
20
+ /**
21
+ * System-managed `path` widget.
22
+ *
23
+ * Edits the path stored in `byline_document_paths` for the current
24
+ * (document, locale) row. Displays the current persisted/overridden
25
+ * value as an editable input.
26
+ * In create mode, when the user hasn't supplied an override, the input
27
+ * shows the live-derived preview (slugified `useAsPath` source field) as
28
+ * a placeholder so the user sees what will be saved. The "Regenerate"
29
+ * action explicitly writes the current live preview into the override
30
+ * slot so the user can re-anchor a path against the source field after
31
+ * editing the title.
32
+ *
33
+ * Stable override handles: `.byline-form-path`, `.byline-form-path-header`,
34
+ * `.byline-form-path-regenerate`.
35
+ */
36
+ export declare const PathWidget: ({ useAsPath, collectionPath, defaultLocale, activeLocale, mode, }: PathWidgetProps) => import("react").JSX.Element;
@@ -0,0 +1,116 @@
1
+ "use client";
2
+ import { jsx, jsxs } from "react/jsx-runtime";
3
+ import { useCallback, useMemo } from "react";
4
+ import { slugify } from "@byline/core";
5
+ import { useTranslation } from "@byline/i18n/react";
6
+ import { Input, Label } from "@byline/ui/react";
7
+ import classnames from "classnames";
8
+ import { useFieldValue, useFormContext, useSystemPath } from "./form-context.js";
9
+ import path_widget_module from "./path-widget.module.js";
10
+ function coerceToString(value) {
11
+ if (null == value) return '';
12
+ if (value instanceof Date) return value.toISOString();
13
+ return String(value);
14
+ }
15
+ const PathWidget = ({ useAsPath, collectionPath, defaultLocale, activeLocale, mode })=>{
16
+ const { setSystemPath } = useFormContext();
17
+ const { t } = useTranslation('byline-admin');
18
+ const systemPath = useSystemPath();
19
+ const sourceValue = useFieldValue(useAsPath ?? '');
20
+ const isReadOnly = activeLocale !== defaultLocale;
21
+ const livePreview = useMemo(()=>{
22
+ if (!useAsPath) return '';
23
+ const asString = coerceToString(sourceValue);
24
+ if (0 === asString.length) return '';
25
+ return slugify(asString, {
26
+ locale: defaultLocale,
27
+ collectionPath
28
+ });
29
+ }, [
30
+ useAsPath,
31
+ sourceValue,
32
+ defaultLocale,
33
+ collectionPath
34
+ ]);
35
+ const inputValue = systemPath ?? '';
36
+ const handleChange = useCallback((next)=>{
37
+ setSystemPath(0 === next.length ? null : next);
38
+ }, [
39
+ setSystemPath
40
+ ]);
41
+ const handleRegenerate = useCallback(()=>{
42
+ if (livePreview.length > 0) setSystemPath(livePreview);
43
+ }, [
44
+ livePreview,
45
+ setSystemPath
46
+ ]);
47
+ const formatted = useMemo(()=>{
48
+ if (0 === inputValue.length) return '';
49
+ return slugify(inputValue, {
50
+ locale: defaultLocale,
51
+ collectionPath
52
+ });
53
+ }, [
54
+ inputValue,
55
+ defaultLocale,
56
+ collectionPath
57
+ ]);
58
+ const validationHint = inputValue.length > 0 && formatted !== inputValue ? t('pathWidget.suggestedHint', {
59
+ formatted
60
+ }) : void 0;
61
+ const readOnlyHint = isReadOnly ? t('pathWidget.readOnlyHint', {
62
+ locale: defaultLocale
63
+ }) : void 0;
64
+ const hint = readOnlyHint ?? validationHint;
65
+ const placeholder = !isReadOnly && 'create' === mode && livePreview.length > 0 ? t('pathWidget.willBeSavedAs', {
66
+ preview: livePreview
67
+ }) : void 0;
68
+ const srDescription = [
69
+ t("pathWidget.srDescription"),
70
+ placeholder,
71
+ hint
72
+ ].filter(Boolean).join(' ');
73
+ const showRegenerate = !isReadOnly && useAsPath && livePreview.length > 0 && livePreview !== systemPath;
74
+ return /*#__PURE__*/ jsxs("div", {
75
+ className: "byline-form-path",
76
+ children: [
77
+ /*#__PURE__*/ jsxs("div", {
78
+ className: classnames('byline-form-path-header', path_widget_module.header),
79
+ children: [
80
+ /*#__PURE__*/ jsx(Label, {
81
+ id: "system-path-label",
82
+ htmlFor: "system-path",
83
+ label: t('pathWidget.label')
84
+ }),
85
+ showRegenerate && /*#__PURE__*/ jsx("button", {
86
+ type: "button",
87
+ onClick: handleRegenerate,
88
+ className: classnames('byline-form-path-regenerate', path_widget_module.regenerate),
89
+ "aria-label": t('pathWidget.regenerateAriaLabel', {
90
+ field: useAsPath
91
+ }),
92
+ children: t('pathWidget.regenerateButton', {
93
+ field: useAsPath
94
+ })
95
+ })
96
+ ]
97
+ }),
98
+ /*#__PURE__*/ jsx(Input, {
99
+ id: "system-path",
100
+ name: "__systemPath__",
101
+ value: inputValue,
102
+ placeholder: placeholder,
103
+ onChange: (e)=>handleChange(e.target.value),
104
+ helpText: hint,
105
+ readOnly: isReadOnly,
106
+ "aria-describedby": "system-path-description"
107
+ }),
108
+ /*#__PURE__*/ jsx("span", {
109
+ id: "system-path-description",
110
+ className: classnames('byline-form-path-sr-only', path_widget_module["sr-only"]),
111
+ children: srDescription
112
+ })
113
+ ]
114
+ });
115
+ };
116
+ export { PathWidget };
@@ -0,0 +1,8 @@
1
+ import "./path-widget_module.css";
2
+ const path_widget_module = {
3
+ header: "header-mJ5Fde",
4
+ regenerate: "regenerate-P5Mdye",
5
+ "sr-only": "sr-only-feJgAM",
6
+ srOnly: "sr-only-feJgAM"
7
+ };
8
+ export default path_widget_module;
@@ -0,0 +1,29 @@
1
+ :is(.header-mJ5Fde, .byline-form-path-header) {
2
+ justify-content: space-between;
3
+ align-items: center;
4
+ gap: var(--spacing-8);
5
+ display: flex;
6
+ }
7
+
8
+ :is(.regenerate-P5Mdye, .byline-form-path-regenerate) {
9
+ color: inherit;
10
+ cursor: pointer;
11
+ background: none;
12
+ border: none;
13
+ padding: 0;
14
+ font-size: .8rem;
15
+ text-decoration: underline;
16
+ }
17
+
18
+ :is(.sr-only-feJgAM, .byline-form-path-sr-only) {
19
+ clip: rect(0, 0, 0, 0);
20
+ white-space: nowrap;
21
+ border: 0;
22
+ width: 1px;
23
+ height: 1px;
24
+ margin: -1px;
25
+ padding: 0;
26
+ position: absolute;
27
+ overflow: hidden;
28
+ }
29
+
@@ -0,0 +1,57 @@
1
+ /**
2
+ * This Source Code is subject to the terms of the Mozilla Public
3
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
4
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
5
+ *
6
+ * Copyright (c) Infonomic Company Limited
7
+ */
8
+ /**
9
+ * Upload Executor
10
+ *
11
+ * Handles batch execution of pending file uploads at form submission time.
12
+ * This enables "deferred uploads" — files are selected/previewed immediately
13
+ * but only uploaded when the user clicks Save.
14
+ */
15
+ import type { StoredFileValue } from '@byline/core';
16
+ import type { UploadFieldFn } from '../fields/field-services-types';
17
+ import type { PendingUpload } from './form-context';
18
+ export interface UploadResult {
19
+ fieldPath: string;
20
+ success: boolean;
21
+ storedFile?: StoredFileValue;
22
+ error?: string;
23
+ }
24
+ export interface ExecuteUploadsResult {
25
+ /** All upload results (both successful and failed) */
26
+ results: UploadResult[];
27
+ /** Map of field path to StoredFileValue for successful uploads */
28
+ successful: Map<string, StoredFileValue>;
29
+ /** Map of field path to error message for failed uploads */
30
+ errors: Map<string, string>;
31
+ /** Whether all uploads succeeded */
32
+ allSucceeded: boolean;
33
+ }
34
+ /**
35
+ * Execute all pending uploads sequentially.
36
+ * Returns a result object with successful uploads and any errors.
37
+ *
38
+ * @param pendingUploads - Map of field path to PendingUpload
39
+ * @param uploadField - Host-provided upload transport (resolved via
40
+ * `useBylineFieldServices()` in the calling React tree)
41
+ * @returns Promise resolving to ExecuteUploadsResult
42
+ */
43
+ export declare function executeUploads(pendingUploads: Map<string, PendingUpload>, uploadField: UploadFieldFn): Promise<ExecuteUploadsResult>;
44
+ /**
45
+ * Progress callback type for upload execution with progress tracking.
46
+ */
47
+ export type UploadProgressCallback = (info: {
48
+ current: number;
49
+ total: number;
50
+ fieldPath: string;
51
+ status: 'uploading' | 'done' | 'error';
52
+ }) => void;
53
+ /**
54
+ * Execute uploads with progress callbacks.
55
+ * Useful for showing upload progress in the UI.
56
+ */
57
+ export declare function executeUploadsWithProgress(pendingUploads: Map<string, PendingUpload>, uploadField: UploadFieldFn, onProgress?: UploadProgressCallback): Promise<ExecuteUploadsResult>;
@@ -0,0 +1,94 @@
1
+ async function executeUploads(pendingUploads, uploadField) {
2
+ const results = [];
3
+ const successful = new Map();
4
+ const errors = new Map();
5
+ for (const [fieldPath, upload] of pendingUploads.entries()){
6
+ const formData = new FormData();
7
+ formData.append('file', upload.file);
8
+ formData.append('field', uploadFieldName(fieldPath));
9
+ try {
10
+ const result = await uploadField(upload.collectionPath, formData, false);
11
+ results.push({
12
+ fieldPath,
13
+ success: true,
14
+ storedFile: result.storedFile
15
+ });
16
+ successful.set(fieldPath, result.storedFile);
17
+ } catch (err) {
18
+ const message = err instanceof Error ? err.message : 'Upload failed';
19
+ results.push({
20
+ fieldPath,
21
+ success: false,
22
+ error: message
23
+ });
24
+ errors.set(fieldPath, message);
25
+ }
26
+ }
27
+ return {
28
+ results,
29
+ successful,
30
+ errors,
31
+ allSucceeded: 0 === errors.size
32
+ };
33
+ }
34
+ function uploadFieldName(fieldPath) {
35
+ const dot = fieldPath.lastIndexOf('.');
36
+ return -1 === dot ? fieldPath : fieldPath.slice(dot + 1);
37
+ }
38
+ async function executeUploadsWithProgress(pendingUploads, uploadField, onProgress) {
39
+ const results = [];
40
+ const successful = new Map();
41
+ const errors = new Map();
42
+ const entries = Array.from(pendingUploads.entries());
43
+ const total = entries.length;
44
+ for(let i = 0; i < entries.length; i++){
45
+ const entry = entries[i];
46
+ if (!entry) continue;
47
+ const [fieldPath, upload] = entry;
48
+ onProgress?.({
49
+ current: i + 1,
50
+ total,
51
+ fieldPath,
52
+ status: 'uploading'
53
+ });
54
+ const formData = new FormData();
55
+ formData.append('file', upload.file);
56
+ formData.append('field', uploadFieldName(fieldPath));
57
+ try {
58
+ const result = await uploadField(upload.collectionPath, formData, false);
59
+ results.push({
60
+ fieldPath,
61
+ success: true,
62
+ storedFile: result.storedFile
63
+ });
64
+ successful.set(fieldPath, result.storedFile);
65
+ onProgress?.({
66
+ current: i + 1,
67
+ total,
68
+ fieldPath,
69
+ status: 'done'
70
+ });
71
+ } catch (err) {
72
+ const message = err instanceof Error ? err.message : 'Upload failed';
73
+ results.push({
74
+ fieldPath,
75
+ success: false,
76
+ error: message
77
+ });
78
+ errors.set(fieldPath, message);
79
+ onProgress?.({
80
+ current: i + 1,
81
+ total,
82
+ fieldPath,
83
+ status: 'error'
84
+ });
85
+ }
86
+ }
87
+ return {
88
+ results,
89
+ successful,
90
+ errors,
91
+ allSucceeded: 0 === errors.size
92
+ };
93
+ }
94
+ export { executeUploads, executeUploadsWithProgress };