@open-mercato/core 0.6.6-develop.6094.1.28b081ea16 → 0.6.6-develop.6126.1.0b9392fdae

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 (317) hide show
  1. package/.turbo/turbo-build.log +1 -1
  2. package/dist/generated/entities/catalog_product/index.js +52 -0
  3. package/dist/generated/entities/catalog_product/index.js.map +2 -2
  4. package/dist/generated/entities/catalog_product_variant/index.js +4 -0
  5. package/dist/generated/entities/catalog_product_variant/index.js.map +2 -2
  6. package/dist/generated/entity-fields-registry.js +28 -0
  7. package/dist/generated/entity-fields-registry.js.map +2 -2
  8. package/dist/modules/catalog/api/products/route.js +103 -33
  9. package/dist/modules/catalog/api/products/route.js.map +2 -2
  10. package/dist/modules/catalog/api/variants/route.js +4 -0
  11. package/dist/modules/catalog/api/variants/route.js.map +2 -2
  12. package/dist/modules/catalog/backend/catalog/products/[id]/page.js +46 -2
  13. package/dist/modules/catalog/backend/catalog/products/[id]/page.js.map +2 -2
  14. package/dist/modules/catalog/backend/catalog/products/[productId]/variants/[variantId]/page.js +4 -0
  15. package/dist/modules/catalog/backend/catalog/products/[productId]/variants/[variantId]/page.js.map +2 -2
  16. package/dist/modules/catalog/backend/catalog/products/[productId]/variants/create/page.js +2 -0
  17. package/dist/modules/catalog/backend/catalog/products/[productId]/variants/create/page.js.map +2 -2
  18. package/dist/modules/catalog/backend/catalog/products/create/page.js +42 -2
  19. package/dist/modules/catalog/backend/catalog/products/create/page.js.map +2 -2
  20. package/dist/modules/catalog/commands/products.js +251 -14
  21. package/dist/modules/catalog/commands/products.js.map +2 -2
  22. package/dist/modules/catalog/commands/variants.js +72 -1
  23. package/dist/modules/catalog/commands/variants.js.map +2 -2
  24. package/dist/modules/catalog/components/products/ProductComplianceSection.js +500 -0
  25. package/dist/modules/catalog/components/products/ProductComplianceSection.js.map +7 -0
  26. package/dist/modules/catalog/components/products/VariantBuilder.js +39 -1
  27. package/dist/modules/catalog/components/products/VariantBuilder.js.map +2 -2
  28. package/dist/modules/catalog/components/products/productForm.js +164 -2
  29. package/dist/modules/catalog/components/products/productForm.js.map +2 -2
  30. package/dist/modules/catalog/components/products/variantForm.js +2 -0
  31. package/dist/modules/catalog/components/products/variantForm.js.map +2 -2
  32. package/dist/modules/catalog/data/entities.js +93 -0
  33. package/dist/modules/catalog/data/entities.js.map +2 -2
  34. package/dist/modules/catalog/data/types.js +28 -0
  35. package/dist/modules/catalog/data/types.js.map +2 -2
  36. package/dist/modules/catalog/data/validators.js +100 -5
  37. package/dist/modules/catalog/data/validators.js.map +2 -2
  38. package/dist/modules/catalog/lib/gtin.js +61 -0
  39. package/dist/modules/catalog/lib/gtin.js.map +7 -0
  40. package/dist/modules/catalog/migrations/Migration20260611090000.js +17 -0
  41. package/dist/modules/catalog/migrations/Migration20260611090000.js.map +7 -0
  42. package/dist/modules/catalog/translations.js +1 -1
  43. package/dist/modules/catalog/translations.js.map +2 -2
  44. package/dist/modules/configs/api/cache/route.js +60 -10
  45. package/dist/modules/configs/api/cache/route.js.map +3 -3
  46. package/dist/modules/configs/components/CachePanel.js +52 -29
  47. package/dist/modules/configs/components/CachePanel.js.map +2 -2
  48. package/dist/modules/currencies/api/currencies/options/route.js +18 -4
  49. package/dist/modules/currencies/api/currencies/options/route.js.map +2 -2
  50. package/dist/modules/currencies/services/rateFetchingService.js +35 -18
  51. package/dist/modules/currencies/services/rateFetchingService.js.map +2 -2
  52. package/dist/modules/customer_accounts/backend/customer_accounts/users/[id]/page.js +16 -16
  53. package/dist/modules/customer_accounts/backend/customer_accounts/users/[id]/page.js.map +2 -2
  54. package/dist/modules/customer_accounts/backend/customer_accounts/users/page.js +1 -1
  55. package/dist/modules/customer_accounts/backend/customer_accounts/users/page.js.map +2 -2
  56. package/dist/modules/customers/backend/calendar/page.js +10 -0
  57. package/dist/modules/customers/backend/calendar/page.js.map +7 -0
  58. package/dist/modules/customers/backend/calendar/page.meta.js +25 -0
  59. package/dist/modules/customers/backend/calendar/page.meta.js.map +7 -0
  60. package/dist/modules/customers/cli.js +1 -0
  61. package/dist/modules/customers/cli.js.map +2 -2
  62. package/dist/modules/customers/components/calendar/AgendaList.js +182 -0
  63. package/dist/modules/customers/components/calendar/AgendaList.js.map +7 -0
  64. package/dist/modules/customers/components/calendar/CalendarEventEditor.js +331 -0
  65. package/dist/modules/customers/components/calendar/CalendarEventEditor.js.map +7 -0
  66. package/dist/modules/customers/components/calendar/CalendarFooter.js +48 -0
  67. package/dist/modules/customers/components/calendar/CalendarFooter.js.map +7 -0
  68. package/dist/modules/customers/components/calendar/CalendarHeader.js +36 -0
  69. package/dist/modules/customers/components/calendar/CalendarHeader.js.map +7 -0
  70. package/dist/modules/customers/components/calendar/CalendarScreen.js +516 -0
  71. package/dist/modules/customers/components/calendar/CalendarScreen.js.map +7 -0
  72. package/dist/modules/customers/components/calendar/CalendarSettingsModal.js +163 -0
  73. package/dist/modules/customers/components/calendar/CalendarSettingsModal.js.map +7 -0
  74. package/dist/modules/customers/components/calendar/CalendarTabs.js +60 -0
  75. package/dist/modules/customers/components/calendar/CalendarTabs.js.map +7 -0
  76. package/dist/modules/customers/components/calendar/CalendarToolbar.js +262 -0
  77. package/dist/modules/customers/components/calendar/CalendarToolbar.js.map +7 -0
  78. package/dist/modules/customers/components/calendar/EventBlock.js +149 -0
  79. package/dist/modules/customers/components/calendar/EventBlock.js.map +7 -0
  80. package/dist/modules/customers/components/calendar/EventPeekPopover.js +72 -0
  81. package/dist/modules/customers/components/calendar/EventPeekPopover.js.map +7 -0
  82. package/dist/modules/customers/components/calendar/MonthGrid.js +214 -0
  83. package/dist/modules/customers/components/calendar/MonthGrid.js.map +7 -0
  84. package/dist/modules/customers/components/calendar/ShortcutsDialog.js +44 -0
  85. package/dist/modules/customers/components/calendar/ShortcutsDialog.js.map +7 -0
  86. package/dist/modules/customers/components/calendar/TimeGrid.js +410 -0
  87. package/dist/modules/customers/components/calendar/TimeGrid.js.map +7 -0
  88. package/dist/modules/customers/components/calendar/UpcomingCards.js +175 -0
  89. package/dist/modules/customers/components/calendar/UpcomingCards.js.map +7 -0
  90. package/dist/modules/customers/components/calendar/editor/CategoryField.js +75 -0
  91. package/dist/modules/customers/components/calendar/editor/CategoryField.js.map +7 -0
  92. package/dist/modules/customers/components/calendar/editor/LocationField.js +30 -0
  93. package/dist/modules/customers/components/calendar/editor/LocationField.js.map +7 -0
  94. package/dist/modules/customers/components/calendar/editor/PeopleField.js +135 -0
  95. package/dist/modules/customers/components/calendar/editor/PeopleField.js.map +7 -0
  96. package/dist/modules/customers/components/calendar/editor/RelatedToField.js +218 -0
  97. package/dist/modules/customers/components/calendar/editor/RelatedToField.js.map +7 -0
  98. package/dist/modules/customers/components/calendar/editor/RepeatField.js +119 -0
  99. package/dist/modules/customers/components/calendar/editor/RepeatField.js.map +7 -0
  100. package/dist/modules/customers/components/calendar/editor/ScheduleSection.js +83 -0
  101. package/dist/modules/customers/components/calendar/editor/ScheduleSection.js.map +7 -0
  102. package/dist/modules/customers/components/calendar/editor/SegmentGroup.js +44 -0
  103. package/dist/modules/customers/components/calendar/editor/SegmentGroup.js.map +7 -0
  104. package/dist/modules/customers/components/calendar/editor/hooks.js +132 -0
  105. package/dist/modules/customers/components/calendar/editor/hooks.js.map +7 -0
  106. package/dist/modules/customers/components/calendar/editor/inputs.js +160 -0
  107. package/dist/modules/customers/components/calendar/editor/inputs.js.map +7 -0
  108. package/dist/modules/customers/components/calendar/editor/lookups.js +107 -0
  109. package/dist/modules/customers/components/calendar/editor/lookups.js.map +7 -0
  110. package/dist/modules/customers/components/calendar/types.js +30 -0
  111. package/dist/modules/customers/components/calendar/types.js.map +7 -0
  112. package/dist/modules/customers/components/calendar/useCalendarItems.js +131 -0
  113. package/dist/modules/customers/components/calendar/useCalendarItems.js.map +7 -0
  114. package/dist/modules/customers/components/calendar/useCalendarPreferences.js +41 -0
  115. package/dist/modules/customers/components/calendar/useCalendarPreferences.js.map +7 -0
  116. package/dist/modules/customers/lib/calendar/categories.js +28 -0
  117. package/dist/modules/customers/lib/calendar/categories.js.map +7 -0
  118. package/dist/modules/customers/lib/calendar/conflicts.js +72 -0
  119. package/dist/modules/customers/lib/calendar/conflicts.js.map +7 -0
  120. package/dist/modules/customers/lib/calendar/editorPayload.js +271 -0
  121. package/dist/modules/customers/lib/calendar/editorPayload.js.map +7 -0
  122. package/dist/modules/customers/lib/calendar/grid.js +48 -0
  123. package/dist/modules/customers/lib/calendar/grid.js.map +7 -0
  124. package/dist/modules/customers/lib/calendar/layout.js +39 -0
  125. package/dist/modules/customers/lib/calendar/layout.js.map +7 -0
  126. package/dist/modules/customers/lib/calendar/mapItem.js +79 -0
  127. package/dist/modules/customers/lib/calendar/mapItem.js.map +7 -0
  128. package/dist/modules/customers/lib/calendar/preferences.js +71 -0
  129. package/dist/modules/customers/lib/calendar/preferences.js.map +7 -0
  130. package/dist/modules/customers/lib/calendar/range.js +46 -0
  131. package/dist/modules/customers/lib/calendar/range.js.map +7 -0
  132. package/dist/modules/customers/lib/calendar/recurrence.js +113 -0
  133. package/dist/modules/customers/lib/calendar/recurrence.js.map +7 -0
  134. package/dist/modules/dashboards/services/widgetDataService.js +5 -5
  135. package/dist/modules/dashboards/services/widgetDataService.js.map +2 -2
  136. package/dist/modules/dictionaries/api/[dictionaryId]/entries/[entryId]/route.js +61 -1
  137. package/dist/modules/dictionaries/api/[dictionaryId]/entries/[entryId]/route.js.map +2 -2
  138. package/dist/modules/dictionaries/api/[dictionaryId]/entries/route.js +33 -1
  139. package/dist/modules/dictionaries/api/[dictionaryId]/entries/route.js.map +2 -2
  140. package/dist/modules/dictionaries/api/[dictionaryId]/route.js +61 -1
  141. package/dist/modules/dictionaries/api/[dictionaryId]/route.js.map +2 -2
  142. package/dist/modules/dictionaries/api/route.js +33 -1
  143. package/dist/modules/dictionaries/api/route.js.map +2 -2
  144. package/dist/modules/feature_toggles/lib/queries.js +36 -52
  145. package/dist/modules/feature_toggles/lib/queries.js.map +2 -2
  146. package/dist/modules/perspectives/api/[tableId]/[perspectiveId]/route.js +32 -1
  147. package/dist/modules/perspectives/api/[tableId]/[perspectiveId]/route.js.map +2 -2
  148. package/dist/modules/perspectives/api/[tableId]/roles/[roleId]/route.js +32 -1
  149. package/dist/modules/perspectives/api/[tableId]/roles/[roleId]/route.js.map +2 -2
  150. package/dist/modules/perspectives/api/[tableId]/route.js +73 -2
  151. package/dist/modules/perspectives/api/[tableId]/route.js.map +2 -2
  152. package/dist/modules/perspectives/services/perspectiveService.js +5 -3
  153. package/dist/modules/perspectives/services/perspectiveService.js.map +2 -2
  154. package/dist/modules/planner/api/access.js +9 -0
  155. package/dist/modules/planner/api/access.js.map +2 -2
  156. package/dist/modules/planner/api/availability-date-specific.js +22 -1
  157. package/dist/modules/planner/api/availability-date-specific.js.map +2 -2
  158. package/dist/modules/planner/api/availability-weekly.js +22 -1
  159. package/dist/modules/planner/api/availability-weekly.js.map +2 -2
  160. package/dist/modules/resources/api/resources/tags/assign/route.js +39 -0
  161. package/dist/modules/resources/api/resources/tags/assign/route.js.map +2 -2
  162. package/dist/modules/resources/api/resources/tags/unassign/route.js +39 -0
  163. package/dist/modules/resources/api/resources/tags/unassign/route.js.map +2 -2
  164. package/dist/modules/sales/api/settings/document-numbers/route.js +33 -1
  165. package/dist/modules/sales/api/settings/document-numbers/route.js.map +2 -2
  166. package/dist/modules/sales/api/settings/order-editing/route.js +35 -3
  167. package/dist/modules/sales/api/settings/order-editing/route.js.map +2 -2
  168. package/dist/modules/staff/api/leave-requests/accept/route.js +41 -0
  169. package/dist/modules/staff/api/leave-requests/accept/route.js.map +2 -2
  170. package/dist/modules/staff/api/leave-requests/reject/route.js +41 -0
  171. package/dist/modules/staff/api/leave-requests/reject/route.js.map +2 -2
  172. package/dist/modules/staff/api/team-members/self/route.js +40 -0
  173. package/dist/modules/staff/api/team-members/self/route.js.map +2 -2
  174. package/dist/modules/staff/api/team-members/tags/assign/route.js +41 -0
  175. package/dist/modules/staff/api/team-members/tags/assign/route.js.map +2 -2
  176. package/dist/modules/staff/api/team-members/tags/unassign/route.js +41 -0
  177. package/dist/modules/staff/api/team-members/tags/unassign/route.js.map +2 -2
  178. package/dist/modules/translations/api/[entityType]/[entityId]/route.js +61 -1
  179. package/dist/modules/translations/api/[entityType]/[entityId]/route.js.map +2 -2
  180. package/dist/modules/translations/api/context.js +7 -0
  181. package/dist/modules/translations/api/context.js.map +2 -2
  182. package/dist/modules/translations/api/put/locales.js +33 -1
  183. package/dist/modules/translations/api/put/locales.js.map +2 -2
  184. package/dist/modules/workflows/backend/definitions/visual-editor/page.js +6 -7
  185. package/dist/modules/workflows/backend/definitions/visual-editor/page.js.map +2 -2
  186. package/dist/modules/workflows/backend/instances/[id]/page.js.map +1 -1
  187. package/dist/modules/workflows/components/EdgeEditDialog.js.map +1 -1
  188. package/dist/modules/workflows/components/EdgeEditDialogCrudForm.js.map +1 -1
  189. package/dist/modules/workflows/components/NodeEditDialog.js.map +1 -1
  190. package/dist/modules/workflows/components/NodeEditDialogCrudForm.js.map +1 -1
  191. package/dist/modules/workflows/components/WorkflowGraph.js.map +1 -1
  192. package/dist/modules/workflows/components/WorkflowGraphImpl.js +17 -9
  193. package/dist/modules/workflows/components/WorkflowGraphImpl.js.map +2 -2
  194. package/dist/modules/workflows/components/mobile/MobileVisualEditor.js.map +1 -1
  195. package/dist/modules/workflows/frontend/checkout-demo/deriveCurrentStep.js +8 -0
  196. package/dist/modules/workflows/frontend/checkout-demo/deriveCurrentStep.js.map +7 -0
  197. package/dist/modules/workflows/frontend/checkout-demo/page.js +2 -20
  198. package/dist/modules/workflows/frontend/checkout-demo/page.js.map +2 -2
  199. package/dist/modules/workflows/lib/graph-utils.js +8 -0
  200. package/dist/modules/workflows/lib/graph-utils.js.map +2 -2
  201. package/generated/entities/catalog_product/index.ts +26 -0
  202. package/generated/entities/catalog_product_variant/index.ts +2 -0
  203. package/generated/entity-fields-registry.ts +28 -0
  204. package/package.json +7 -7
  205. package/src/modules/catalog/api/products/route.ts +123 -39
  206. package/src/modules/catalog/api/variants/route.ts +4 -0
  207. package/src/modules/catalog/backend/catalog/products/[id]/page.tsx +43 -0
  208. package/src/modules/catalog/backend/catalog/products/[productId]/variants/[variantId]/page.tsx +14 -0
  209. package/src/modules/catalog/backend/catalog/products/[productId]/variants/create/page.tsx +2 -0
  210. package/src/modules/catalog/backend/catalog/products/create/page.tsx +41 -0
  211. package/src/modules/catalog/commands/products.ts +307 -2
  212. package/src/modules/catalog/commands/variants.ts +90 -1
  213. package/src/modules/catalog/components/products/ProductComplianceSection.tsx +497 -0
  214. package/src/modules/catalog/components/products/VariantBuilder.tsx +43 -0
  215. package/src/modules/catalog/components/products/productForm.ts +262 -0
  216. package/src/modules/catalog/components/products/variantForm.ts +4 -0
  217. package/src/modules/catalog/data/entities.ts +97 -0
  218. package/src/modules/catalog/data/types.ts +36 -0
  219. package/src/modules/catalog/data/validators.ts +159 -3
  220. package/src/modules/catalog/i18n/de.json +64 -0
  221. package/src/modules/catalog/i18n/en.json +64 -0
  222. package/src/modules/catalog/i18n/es.json +64 -0
  223. package/src/modules/catalog/i18n/pl.json +64 -0
  224. package/src/modules/catalog/lib/gtin.ts +66 -0
  225. package/src/modules/catalog/migrations/.snapshot-open-mercato.json +457 -0
  226. package/src/modules/catalog/migrations/Migration20260611090000.ts +17 -0
  227. package/src/modules/catalog/translations.ts +1 -1
  228. package/src/modules/configs/api/cache/route.ts +72 -10
  229. package/src/modules/configs/components/CachePanel.tsx +59 -29
  230. package/src/modules/currencies/api/currencies/options/route.ts +22 -4
  231. package/src/modules/currencies/services/rateFetchingService.ts +63 -26
  232. package/src/modules/customer_accounts/backend/customer_accounts/users/[id]/page.tsx +18 -18
  233. package/src/modules/customer_accounts/backend/customer_accounts/users/page.tsx +1 -1
  234. package/src/modules/customer_accounts/i18n/de.json +1 -1
  235. package/src/modules/customer_accounts/i18n/en.json +1 -1
  236. package/src/modules/customer_accounts/i18n/es.json +1 -1
  237. package/src/modules/customer_accounts/i18n/pl.json +1 -1
  238. package/src/modules/customers/backend/calendar/page.meta.ts +23 -0
  239. package/src/modules/customers/backend/calendar/page.tsx +12 -0
  240. package/src/modules/customers/cli.ts +1 -0
  241. package/src/modules/customers/components/calendar/AgendaList.tsx +219 -0
  242. package/src/modules/customers/components/calendar/CalendarEventEditor.tsx +386 -0
  243. package/src/modules/customers/components/calendar/CalendarFooter.tsx +61 -0
  244. package/src/modules/customers/components/calendar/CalendarHeader.tsx +40 -0
  245. package/src/modules/customers/components/calendar/CalendarScreen.tsx +590 -0
  246. package/src/modules/customers/components/calendar/CalendarSettingsModal.tsx +207 -0
  247. package/src/modules/customers/components/calendar/CalendarTabs.tsx +63 -0
  248. package/src/modules/customers/components/calendar/CalendarToolbar.tsx +295 -0
  249. package/src/modules/customers/components/calendar/EventBlock.tsx +205 -0
  250. package/src/modules/customers/components/calendar/EventPeekPopover.tsx +100 -0
  251. package/src/modules/customers/components/calendar/MonthGrid.tsx +236 -0
  252. package/src/modules/customers/components/calendar/ShortcutsDialog.tsx +57 -0
  253. package/src/modules/customers/components/calendar/TimeGrid.tsx +510 -0
  254. package/src/modules/customers/components/calendar/UpcomingCards.tsx +220 -0
  255. package/src/modules/customers/components/calendar/editor/CategoryField.tsx +79 -0
  256. package/src/modules/customers/components/calendar/editor/LocationField.tsx +37 -0
  257. package/src/modules/customers/components/calendar/editor/PeopleField.tsx +148 -0
  258. package/src/modules/customers/components/calendar/editor/RelatedToField.tsx +242 -0
  259. package/src/modules/customers/components/calendar/editor/RepeatField.tsx +132 -0
  260. package/src/modules/customers/components/calendar/editor/ScheduleSection.tsx +110 -0
  261. package/src/modules/customers/components/calendar/editor/SegmentGroup.tsx +50 -0
  262. package/src/modules/customers/components/calendar/editor/hooks.ts +162 -0
  263. package/src/modules/customers/components/calendar/editor/inputs.tsx +158 -0
  264. package/src/modules/customers/components/calendar/editor/lookups.ts +160 -0
  265. package/src/modules/customers/components/calendar/types.ts +163 -0
  266. package/src/modules/customers/components/calendar/useCalendarItems.ts +162 -0
  267. package/src/modules/customers/components/calendar/useCalendarPreferences.ts +52 -0
  268. package/src/modules/customers/i18n/de.json +195 -0
  269. package/src/modules/customers/i18n/en.json +195 -0
  270. package/src/modules/customers/i18n/es.json +195 -0
  271. package/src/modules/customers/i18n/pl.json +195 -0
  272. package/src/modules/customers/lib/calendar/categories.ts +26 -0
  273. package/src/modules/customers/lib/calendar/conflicts.ts +117 -0
  274. package/src/modules/customers/lib/calendar/editorPayload.ts +388 -0
  275. package/src/modules/customers/lib/calendar/grid.ts +50 -0
  276. package/src/modules/customers/lib/calendar/layout.ts +47 -0
  277. package/src/modules/customers/lib/calendar/mapItem.ts +94 -0
  278. package/src/modules/customers/lib/calendar/preferences.ts +95 -0
  279. package/src/modules/customers/lib/calendar/range.ts +45 -0
  280. package/src/modules/customers/lib/calendar/recurrence.ts +137 -0
  281. package/src/modules/dashboards/services/widgetDataService.ts +8 -6
  282. package/src/modules/dictionaries/api/[dictionaryId]/entries/[entryId]/route.ts +61 -1
  283. package/src/modules/dictionaries/api/[dictionaryId]/entries/route.ts +33 -1
  284. package/src/modules/dictionaries/api/[dictionaryId]/route.ts +65 -1
  285. package/src/modules/dictionaries/api/route.ts +36 -1
  286. package/src/modules/feature_toggles/lib/queries.ts +41 -60
  287. package/src/modules/perspectives/api/[tableId]/[perspectiveId]/route.ts +34 -1
  288. package/src/modules/perspectives/api/[tableId]/roles/[roleId]/route.ts +34 -1
  289. package/src/modules/perspectives/api/[tableId]/route.ts +107 -32
  290. package/src/modules/perspectives/services/perspectiveService.ts +9 -5
  291. package/src/modules/planner/api/access.ts +9 -0
  292. package/src/modules/planner/api/availability-date-specific.ts +22 -1
  293. package/src/modules/planner/api/availability-weekly.ts +22 -1
  294. package/src/modules/resources/api/resources/tags/assign/route.ts +42 -0
  295. package/src/modules/resources/api/resources/tags/unassign/route.ts +42 -0
  296. package/src/modules/sales/api/settings/document-numbers/route.ts +35 -1
  297. package/src/modules/sales/api/settings/order-editing/route.ts +37 -3
  298. package/src/modules/staff/api/leave-requests/accept/route.ts +45 -0
  299. package/src/modules/staff/api/leave-requests/reject/route.ts +45 -0
  300. package/src/modules/staff/api/team-members/self/route.ts +43 -0
  301. package/src/modules/staff/api/team-members/tags/assign/route.ts +45 -0
  302. package/src/modules/staff/api/team-members/tags/unassign/route.ts +45 -0
  303. package/src/modules/translations/api/[entityType]/[entityId]/route.ts +65 -1
  304. package/src/modules/translations/api/context.ts +7 -0
  305. package/src/modules/translations/api/put/locales.ts +35 -1
  306. package/src/modules/workflows/backend/definitions/visual-editor/page.tsx +11 -9
  307. package/src/modules/workflows/backend/instances/[id]/page.tsx +1 -1
  308. package/src/modules/workflows/components/EdgeEditDialog.tsx +1 -1
  309. package/src/modules/workflows/components/EdgeEditDialogCrudForm.tsx +1 -1
  310. package/src/modules/workflows/components/NodeEditDialog.tsx +1 -1
  311. package/src/modules/workflows/components/NodeEditDialogCrudForm.tsx +1 -1
  312. package/src/modules/workflows/components/WorkflowGraph.tsx +2 -2
  313. package/src/modules/workflows/components/WorkflowGraphImpl.tsx +27 -13
  314. package/src/modules/workflows/components/mobile/MobileVisualEditor.tsx +3 -3
  315. package/src/modules/workflows/frontend/checkout-demo/deriveCurrentStep.ts +12 -0
  316. package/src/modules/workflows/frontend/checkout-demo/page.tsx +3 -23
  317. package/src/modules/workflows/lib/graph-utils.ts +21 -1
@@ -0,0 +1,497 @@
1
+ "use client";
2
+
3
+ import * as React from "react";
4
+ import { useT } from "@open-mercato/shared/lib/i18n/context";
5
+ import { Checkbox } from "@open-mercato/ui/primitives/checkbox";
6
+ import { Input } from "@open-mercato/ui/primitives/input";
7
+ import { Label } from "@open-mercato/ui/primitives/label";
8
+ import {
9
+ Select,
10
+ SelectContent,
11
+ SelectItem,
12
+ SelectTrigger,
13
+ SelectValue,
14
+ } from "@open-mercato/ui/primitives/select";
15
+ import { Textarea } from "@open-mercato/ui/primitives/textarea";
16
+ import {
17
+ CATALOG_EXCISE_CATEGORIES,
18
+ CATALOG_GTU_CODES,
19
+ CATALOG_HAZMAT_PACKING_GROUPS,
20
+ } from "../../data/types";
21
+ import type { ProductFormValues } from "./productForm";
22
+
23
+ const NONE_OPTION = "none";
24
+
25
+ type ProductComplianceSectionProps = {
26
+ values: ProductFormValues;
27
+ errors: Record<string, string>;
28
+ setValue: (id: string, value: unknown) => void;
29
+ embedded?: boolean;
30
+ };
31
+
32
+ function FieldError({ message }: { message?: string }) {
33
+ if (!message) return null;
34
+ return <p className="text-xs text-destructive">{message}</p>;
35
+ }
36
+
37
+ export function ProductComplianceSection({
38
+ values,
39
+ errors,
40
+ setValue,
41
+ embedded = false,
42
+ }: ProductComplianceSectionProps) {
43
+ const t = useT();
44
+ const gtuCodes = Array.isArray(values.gtuCodes) ? values.gtuCodes : [];
45
+
46
+ const toggleGtuCode = React.useCallback(
47
+ (code: string, checked: boolean) => {
48
+ const current = Array.isArray(values.gtuCodes) ? values.gtuCodes : [];
49
+ const next = checked
50
+ ? Array.from(new Set([...current, code])).sort()
51
+ : current.filter((entry) => entry !== code);
52
+ setValue("gtuCodes", next);
53
+ },
54
+ [setValue, values.gtuCodes],
55
+ );
56
+
57
+ return (
58
+ <div
59
+ className={
60
+ embedded ? "space-y-6" : "space-y-6 rounded-lg border bg-card p-4"
61
+ }
62
+ >
63
+ <div className="space-y-4">
64
+ <div className="space-y-1">
65
+ <h3 className="text-sm font-semibold">
66
+ {t("catalog.products.compliance.codes.title", "Compliance codes (PL/EU)")}
67
+ </h3>
68
+ <p className="text-xs text-muted-foreground">
69
+ {t(
70
+ "catalog.products.compliance.codes.description",
71
+ "Classification codes used by KSeF/JPK invoices, customs declarations, and marketplace feeds.",
72
+ )}
73
+ </p>
74
+ </div>
75
+ <div className="grid gap-4 md:grid-cols-2">
76
+ <div className="space-y-2">
77
+ <Label htmlFor="catalog-product-compliance-country">
78
+ {t("catalog.products.compliance.fields.countryOfOrigin", "Country of origin (ISO code)")}
79
+ </Label>
80
+ <Input
81
+ id="catalog-product-compliance-country"
82
+ value={values.countryOfOriginCode ?? ""}
83
+ maxLength={2}
84
+ placeholder={t("catalog.products.compliance.placeholders.countryOfOrigin", "PL")}
85
+ onChange={(event) =>
86
+ setValue("countryOfOriginCode", event.target.value.toUpperCase())
87
+ }
88
+ />
89
+ <FieldError message={errors.countryOfOriginCode} />
90
+ </div>
91
+ <div className="space-y-2">
92
+ <Label htmlFor="catalog-product-compliance-tax-classification">
93
+ {t("catalog.products.compliance.fields.taxClassification", "Tax classification code")}
94
+ </Label>
95
+ <Input
96
+ id="catalog-product-compliance-tax-classification"
97
+ value={values.taxClassificationCode ?? ""}
98
+ onChange={(event) => setValue("taxClassificationCode", event.target.value)}
99
+ />
100
+ <FieldError message={errors.taxClassificationCode} />
101
+ </div>
102
+ <div className="space-y-2">
103
+ <Label htmlFor="catalog-product-compliance-pkwiu">
104
+ {t("catalog.products.compliance.fields.pkwiu", "PKWiU code")}
105
+ </Label>
106
+ <Input
107
+ id="catalog-product-compliance-pkwiu"
108
+ value={values.pkwiuCode ?? ""}
109
+ onChange={(event) => setValue("pkwiuCode", event.target.value)}
110
+ />
111
+ <FieldError message={errors.pkwiuCode} />
112
+ </div>
113
+ <div className="space-y-2">
114
+ <Label htmlFor="catalog-product-compliance-cn">
115
+ {t("catalog.products.compliance.fields.cn", "CN code (Combined Nomenclature)")}
116
+ </Label>
117
+ <Input
118
+ id="catalog-product-compliance-cn"
119
+ value={values.cnCode ?? ""}
120
+ onChange={(event) => setValue("cnCode", event.target.value)}
121
+ />
122
+ <FieldError message={errors.cnCode} />
123
+ </div>
124
+ <div className="space-y-2 md:col-span-2">
125
+ <Label htmlFor="catalog-product-compliance-hs">
126
+ {t("catalog.products.compliance.fields.hs", "HS code (customs tariff)")}
127
+ </Label>
128
+ <Input
129
+ id="catalog-product-compliance-hs"
130
+ value={values.hsCode ?? ""}
131
+ onChange={(event) => setValue("hsCode", event.target.value)}
132
+ />
133
+ <FieldError message={errors.hsCode} />
134
+ </div>
135
+ </div>
136
+ <div className="space-y-2">
137
+ <Label>{t("catalog.products.compliance.fields.gtuCodes", "GTU codes (JPK_V7)")}</Label>
138
+ <div className="grid gap-2 sm:grid-cols-3 md:grid-cols-4">
139
+ {CATALOG_GTU_CODES.map((code) => (
140
+ <label
141
+ key={code}
142
+ className="flex items-center gap-2 text-sm"
143
+ htmlFor={`catalog-product-compliance-gtu-${code}`}
144
+ >
145
+ <Checkbox
146
+ id={`catalog-product-compliance-gtu-${code}`}
147
+ checked={gtuCodes.includes(code)}
148
+ onCheckedChange={(checked) => toggleGtuCode(code, checked === true)}
149
+ />
150
+ {code.replace("_", " ")}
151
+ </label>
152
+ ))}
153
+ </div>
154
+ <FieldError message={errors.gtuCodes} />
155
+ </div>
156
+ </div>
157
+
158
+ <div className="space-y-4">
159
+ <div className="space-y-1">
160
+ <h3 className="text-sm font-semibold">
161
+ {t("catalog.products.compliance.safety.title", "Restrictions & safety")}
162
+ </h3>
163
+ <p className="text-xs text-muted-foreground">
164
+ {t(
165
+ "catalog.products.compliance.safety.description",
166
+ "Age, excise, and dangerous-goods attributes enforced by storefront, POS, and carriers.",
167
+ )}
168
+ </p>
169
+ </div>
170
+ <div className="grid gap-4 md:grid-cols-2">
171
+ <div className="space-y-2">
172
+ <Label htmlFor="catalog-product-compliance-age-min">
173
+ {t("catalog.products.compliance.fields.ageMin", "Minimum buyer age")}
174
+ </Label>
175
+ <Input
176
+ id="catalog-product-compliance-age-min"
177
+ type="number"
178
+ min={0}
179
+ max={120}
180
+ value={values.ageMin ?? ""}
181
+ onChange={(event) => setValue("ageMin", event.target.value)}
182
+ />
183
+ <FieldError message={errors.ageMin} />
184
+ </div>
185
+ <div className="space-y-2">
186
+ <Label htmlFor="catalog-product-compliance-excise-category">
187
+ {t("catalog.products.compliance.fields.exciseCategory", "Excise category")}
188
+ </Label>
189
+ <Select
190
+ value={values.exciseCategory ?? NONE_OPTION}
191
+ onValueChange={(value) =>
192
+ setValue("exciseCategory", value === NONE_OPTION ? null : value)
193
+ }
194
+ >
195
+ <SelectTrigger id="catalog-product-compliance-excise-category">
196
+ <SelectValue />
197
+ </SelectTrigger>
198
+ <SelectContent>
199
+ <SelectItem value={NONE_OPTION}>
200
+ {t("catalog.products.compliance.options.none", "None")}
201
+ </SelectItem>
202
+ {CATALOG_EXCISE_CATEGORIES.map((category) => (
203
+ <SelectItem key={category} value={category}>
204
+ {t(`catalog.products.compliance.exciseCategories.${category}`, category)}
205
+ </SelectItem>
206
+ ))}
207
+ </SelectContent>
208
+ </Select>
209
+ <FieldError message={errors.exciseCategory} />
210
+ </div>
211
+ </div>
212
+ <div className="grid gap-2 sm:grid-cols-2">
213
+ <label
214
+ className="flex items-center gap-2 text-sm"
215
+ htmlFor="catalog-product-compliance-excise"
216
+ >
217
+ <Checkbox
218
+ id="catalog-product-compliance-excise"
219
+ checked={values.isExciseGood === true}
220
+ onCheckedChange={(checked) => setValue("isExciseGood", checked === true)}
221
+ />
222
+ {t("catalog.products.compliance.fields.isExciseGood", "Excise good")}
223
+ </label>
224
+ <label
225
+ className="flex items-center gap-2 text-sm"
226
+ htmlFor="catalog-product-compliance-prescription"
227
+ >
228
+ <Checkbox
229
+ id="catalog-product-compliance-prescription"
230
+ checked={values.requiresPrescription === true}
231
+ onCheckedChange={(checked) => setValue("requiresPrescription", checked === true)}
232
+ />
233
+ {t("catalog.products.compliance.fields.requiresPrescription", "Requires prescription")}
234
+ </label>
235
+ <label
236
+ className="flex items-center gap-2 text-sm"
237
+ htmlFor="catalog-product-compliance-lithium"
238
+ >
239
+ <Checkbox
240
+ id="catalog-product-compliance-lithium"
241
+ checked={values.containsLithiumBattery === true}
242
+ onCheckedChange={(checked) => setValue("containsLithiumBattery", checked === true)}
243
+ />
244
+ {t("catalog.products.compliance.fields.containsLithiumBattery", "Contains lithium battery")}
245
+ </label>
246
+ </div>
247
+ <div className="grid gap-4 md:grid-cols-3">
248
+ <div className="space-y-2">
249
+ <Label htmlFor="catalog-product-compliance-hazmat-class">
250
+ {t("catalog.products.compliance.fields.hazmatClass", "Hazmat class (ADR)")}
251
+ </Label>
252
+ <Input
253
+ id="catalog-product-compliance-hazmat-class"
254
+ value={values.hazmatClass ?? ""}
255
+ onChange={(event) => setValue("hazmatClass", event.target.value)}
256
+ />
257
+ <FieldError message={errors.hazmatClass} />
258
+ </div>
259
+ <div className="space-y-2">
260
+ <Label htmlFor="catalog-product-compliance-un-number">
261
+ {t("catalog.products.compliance.fields.unNumber", "UN number")}
262
+ </Label>
263
+ <Input
264
+ id="catalog-product-compliance-un-number"
265
+ placeholder={t("catalog.products.compliance.placeholders.unNumber", "UN1234")}
266
+ value={values.unNumber ?? ""}
267
+ onChange={(event) => setValue("unNumber", event.target.value)}
268
+ />
269
+ <FieldError message={errors.unNumber} />
270
+ </div>
271
+ <div className="space-y-2">
272
+ <Label htmlFor="catalog-product-compliance-packing-group">
273
+ {t("catalog.products.compliance.fields.hazmatPackingGroup", "Packing group")}
274
+ </Label>
275
+ <Select
276
+ value={values.hazmatPackingGroup ?? NONE_OPTION}
277
+ onValueChange={(value) =>
278
+ setValue("hazmatPackingGroup", value === NONE_OPTION ? null : value)
279
+ }
280
+ >
281
+ <SelectTrigger id="catalog-product-compliance-packing-group">
282
+ <SelectValue />
283
+ </SelectTrigger>
284
+ <SelectContent>
285
+ <SelectItem value={NONE_OPTION}>
286
+ {t("catalog.products.compliance.options.none", "None")}
287
+ </SelectItem>
288
+ {CATALOG_HAZMAT_PACKING_GROUPS.map((group) => (
289
+ <SelectItem key={group} value={group}>
290
+ {group}
291
+ </SelectItem>
292
+ ))}
293
+ </SelectContent>
294
+ </Select>
295
+ <FieldError message={errors.hazmatPackingGroup} />
296
+ </div>
297
+ </div>
298
+ </div>
299
+
300
+ <div className="space-y-4">
301
+ <div className="space-y-1">
302
+ <h3 className="text-sm font-semibold">
303
+ {t("catalog.products.compliance.logistics.title", "Availability & lifecycle")}
304
+ </h3>
305
+ <p className="text-xs text-muted-foreground">
306
+ {t(
307
+ "catalog.products.compliance.logistics.description",
308
+ "Launch, end-of-life, and selling windows plus shipping requirements.",
309
+ )}
310
+ </p>
311
+ </div>
312
+ <div className="grid gap-4 md:grid-cols-2">
313
+ <div className="space-y-2">
314
+ <Label htmlFor="catalog-product-compliance-launch-at">
315
+ {t("catalog.products.compliance.fields.launchAt", "Launch date")}
316
+ </Label>
317
+ <Input
318
+ id="catalog-product-compliance-launch-at"
319
+ type="date"
320
+ value={values.launchAt ?? ""}
321
+ onChange={(event) => setValue("launchAt", event.target.value)}
322
+ />
323
+ <FieldError message={errors.launchAt} />
324
+ </div>
325
+ <div className="space-y-2">
326
+ <Label htmlFor="catalog-product-compliance-eol-at">
327
+ {t("catalog.products.compliance.fields.endOfLifeAt", "End of life")}
328
+ </Label>
329
+ <Input
330
+ id="catalog-product-compliance-eol-at"
331
+ type="date"
332
+ value={values.endOfLifeAt ?? ""}
333
+ onChange={(event) => setValue("endOfLifeAt", event.target.value)}
334
+ />
335
+ <FieldError message={errors.endOfLifeAt} />
336
+ </div>
337
+ <div className="space-y-2">
338
+ <Label htmlFor="catalog-product-compliance-available-from">
339
+ {t("catalog.products.compliance.fields.availableFrom", "Available from")}
340
+ </Label>
341
+ <Input
342
+ id="catalog-product-compliance-available-from"
343
+ type="date"
344
+ value={values.availableFrom ?? ""}
345
+ onChange={(event) => setValue("availableFrom", event.target.value)}
346
+ />
347
+ <FieldError message={errors.availableFrom} />
348
+ </div>
349
+ <div className="space-y-2">
350
+ <Label htmlFor="catalog-product-compliance-available-until">
351
+ {t("catalog.products.compliance.fields.availableUntil", "Available until")}
352
+ </Label>
353
+ <Input
354
+ id="catalog-product-compliance-available-until"
355
+ type="date"
356
+ value={values.availableUntil ?? ""}
357
+ onChange={(event) => setValue("availableUntil", event.target.value)}
358
+ />
359
+ <FieldError message={errors.availableUntil} />
360
+ </div>
361
+ </div>
362
+ <label
363
+ className="flex items-center gap-2 text-sm"
364
+ htmlFor="catalog-product-compliance-requires-shipping"
365
+ >
366
+ <Checkbox
367
+ id="catalog-product-compliance-requires-shipping"
368
+ checked={values.requiresShipping !== false}
369
+ onCheckedChange={(checked) => setValue("requiresShipping", checked === true)}
370
+ />
371
+ {t("catalog.products.compliance.fields.requiresShipping", "Requires shipping")}
372
+ </label>
373
+ </div>
374
+
375
+ <div className="space-y-4">
376
+ <div className="space-y-1">
377
+ <h3 className="text-sm font-semibold">
378
+ {t("catalog.products.compliance.commercial.title", "Commercial terms")}
379
+ </h3>
380
+ <p className="text-xs text-muted-foreground">
381
+ {t(
382
+ "catalog.products.compliance.commercial.description",
383
+ "Order quantity constraints and quote-only selling for B2B.",
384
+ )}
385
+ </p>
386
+ </div>
387
+ <div className="grid gap-4 md:grid-cols-3">
388
+ <div className="space-y-2">
389
+ <Label htmlFor="catalog-product-compliance-min-qty">
390
+ {t("catalog.products.compliance.fields.minOrderQty", "Minimum order quantity")}
391
+ </Label>
392
+ <Input
393
+ id="catalog-product-compliance-min-qty"
394
+ type="number"
395
+ min={1}
396
+ value={values.minOrderQty ?? ""}
397
+ onChange={(event) => setValue("minOrderQty", event.target.value)}
398
+ />
399
+ <FieldError message={errors.minOrderQty} />
400
+ </div>
401
+ <div className="space-y-2">
402
+ <Label htmlFor="catalog-product-compliance-max-qty">
403
+ {t("catalog.products.compliance.fields.maxOrderQty", "Maximum order quantity")}
404
+ </Label>
405
+ <Input
406
+ id="catalog-product-compliance-max-qty"
407
+ type="number"
408
+ min={1}
409
+ value={values.maxOrderQty ?? ""}
410
+ onChange={(event) => setValue("maxOrderQty", event.target.value)}
411
+ />
412
+ <FieldError message={errors.maxOrderQty} />
413
+ </div>
414
+ <div className="space-y-2">
415
+ <Label htmlFor="catalog-product-compliance-qty-increment">
416
+ {t("catalog.products.compliance.fields.orderQtyIncrement", "Quantity increment")}
417
+ </Label>
418
+ <Input
419
+ id="catalog-product-compliance-qty-increment"
420
+ type="number"
421
+ min={1}
422
+ value={values.orderQtyIncrement ?? ""}
423
+ onChange={(event) => setValue("orderQtyIncrement", event.target.value)}
424
+ />
425
+ <FieldError message={errors.orderQtyIncrement} />
426
+ </div>
427
+ </div>
428
+ <label
429
+ className="flex items-center gap-2 text-sm"
430
+ htmlFor="catalog-product-compliance-quote-only"
431
+ >
432
+ <Checkbox
433
+ id="catalog-product-compliance-quote-only"
434
+ checked={values.isQuoteOnly === true}
435
+ onCheckedChange={(checked) => setValue("isQuoteOnly", checked === true)}
436
+ />
437
+ {t("catalog.products.compliance.fields.isQuoteOnly", "Quote only (price on request)")}
438
+ </label>
439
+ </div>
440
+
441
+ <div className="space-y-4">
442
+ <div className="space-y-1">
443
+ <h3 className="text-sm font-semibold">
444
+ {t("catalog.products.compliance.seo.title", "SEO")}
445
+ </h3>
446
+ <p className="text-xs text-muted-foreground">
447
+ {t(
448
+ "catalog.products.compliance.seo.description",
449
+ "Storefront metadata. Title and description are translatable per locale.",
450
+ )}
451
+ </p>
452
+ </div>
453
+ <div className="grid gap-4">
454
+ <div className="space-y-2">
455
+ <Label htmlFor="catalog-product-compliance-seo-title">
456
+ {t("catalog.products.compliance.fields.seoTitle", "SEO title")}
457
+ </Label>
458
+ <Input
459
+ id="catalog-product-compliance-seo-title"
460
+ maxLength={255}
461
+ value={values.seoTitle ?? ""}
462
+ onChange={(event) => setValue("seoTitle", event.target.value)}
463
+ />
464
+ <FieldError message={errors.seoTitle} />
465
+ </div>
466
+ <div className="space-y-2">
467
+ <Label htmlFor="catalog-product-compliance-seo-description">
468
+ {t("catalog.products.compliance.fields.seoDescription", "SEO description")}
469
+ </Label>
470
+ <Textarea
471
+ id="catalog-product-compliance-seo-description"
472
+ rows={3}
473
+ maxLength={1000}
474
+ value={values.seoDescription ?? ""}
475
+ onChange={(event) => setValue("seoDescription", event.target.value)}
476
+ />
477
+ <FieldError message={errors.seoDescription} />
478
+ </div>
479
+ <div className="space-y-2">
480
+ <Label htmlFor="catalog-product-compliance-canonical-url">
481
+ {t("catalog.products.compliance.fields.canonicalUrl", "Canonical URL")}
482
+ </Label>
483
+ <Input
484
+ id="catalog-product-compliance-canonical-url"
485
+ type="url"
486
+ maxLength={500}
487
+ placeholder="https://"
488
+ value={values.canonicalUrl ?? ""}
489
+ onChange={(event) => setValue("canonicalUrl", event.target.value)}
490
+ />
491
+ <FieldError message={errors.canonicalUrl} />
492
+ </div>
493
+ </div>
494
+ </div>
495
+ </div>
496
+ );
497
+ }
@@ -18,6 +18,7 @@ import { MetadataEditor } from './MetadataEditor'
18
18
  import type { PriceKindSummary, TaxRateSummary } from './productForm'
19
19
  import { formatTaxRateLabel } from './productForm'
20
20
  import type { OptionDefinition, VariantFormValues, VariantPriceDraft } from './variantForm'
21
+ import { CATALOG_GTIN_TYPES } from '../../data/types'
21
22
  import { E } from '#generated/entities.ids.generated'
22
23
 
23
24
  type VariantBuilderProps = {
@@ -122,6 +123,48 @@ export function VariantBasicsSection({ values, setValue, errors }: VariantSectio
122
123
  onChange={(event) => setValue('barcode', event.target.value)}
123
124
  placeholder={t('catalog.variants.form.barcodePlaceholder', 'EAN, UPC, etc.')}
124
125
  />
126
+ {errors.barcode ? <p className="text-xs text-destructive">{errors.barcode}</p> : null}
127
+ </div>
128
+ </div>
129
+ <div className="grid gap-4 md:grid-cols-2">
130
+ <div className="space-y-2">
131
+ <Label htmlFor="catalog-variant-gtin-type">
132
+ {t('catalog.variants.form.gtinTypeLabel', 'Identifier type (GTIN)')}
133
+ </Label>
134
+ <Select
135
+ value={values.gtinType ?? 'none'}
136
+ onValueChange={(value) => setValue('gtinType', value === 'none' ? null : value)}
137
+ >
138
+ <SelectTrigger id="catalog-variant-gtin-type">
139
+ <SelectValue />
140
+ </SelectTrigger>
141
+ <SelectContent>
142
+ <SelectItem value="none">{t('catalog.variants.form.gtinTypeNone', 'Untyped')}</SelectItem>
143
+ {CATALOG_GTIN_TYPES.map((type) => (
144
+ <SelectItem key={type} value={type}>
145
+ {t(`catalog.variants.form.gtinTypes.${type}`, type.toUpperCase())}
146
+ </SelectItem>
147
+ ))}
148
+ </SelectContent>
149
+ </Select>
150
+ <p className="text-xs text-muted-foreground">
151
+ {t(
152
+ 'catalog.variants.form.gtinTypeHint',
153
+ 'Typed barcodes are validated and kept unique per organization.',
154
+ )}
155
+ </p>
156
+ {errors.gtinType ? <p className="text-xs text-destructive">{errors.gtinType}</p> : null}
157
+ </div>
158
+ <div className="space-y-2">
159
+ <Label htmlFor="catalog-variant-hs-code">
160
+ {t('catalog.variants.form.hsCodeLabel', 'HS code (customs tariff)')}
161
+ </Label>
162
+ <Input
163
+ id="catalog-variant-hs-code"
164
+ value={values.hsCode}
165
+ onChange={(event) => setValue('hsCode', event.target.value)}
166
+ />
167
+ {errors.hsCode ? <p className="text-xs text-destructive">{errors.hsCode}</p> : null}
125
168
  </div>
126
169
  </div>
127
170
  <div className="grid gap-4 md:grid-cols-2">