@open-mercato/core 0.4.7-develop-0a657b411f → 0.4.7-develop-e249d3e7d0

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 (278) hide show
  1. package/dist/generated/entities/carrier_shipment/index.js +37 -0
  2. package/dist/generated/entities/carrier_shipment/index.js.map +7 -0
  3. package/dist/generated/entities/gateway_transaction/index.js +47 -0
  4. package/dist/generated/entities/gateway_transaction/index.js.map +7 -0
  5. package/dist/generated/entities/webhook_processed_event/index.js +17 -0
  6. package/dist/generated/entities/webhook_processed_event/index.js.map +7 -0
  7. package/dist/generated/entities.ids.generated.js +10 -1
  8. package/dist/generated/entities.ids.generated.js.map +2 -2
  9. package/dist/generated/entity-fields-registry.js +6 -0
  10. package/dist/generated/entity-fields-registry.js.map +2 -2
  11. package/dist/modules/data_sync/api/runs/[id]/cancel.js +14 -5
  12. package/dist/modules/data_sync/api/runs/[id]/cancel.js.map +2 -2
  13. package/dist/modules/data_sync/backend/data-sync/page.meta.js +2 -2
  14. package/dist/modules/data_sync/backend/data-sync/page.meta.js.map +1 -1
  15. package/dist/modules/data_sync/backend/data-sync/runs/[id]/page.js +37 -12
  16. package/dist/modules/data_sync/backend/data-sync/runs/[id]/page.js.map +2 -2
  17. package/dist/modules/directory/api/get/tenants/lookup.js +1 -0
  18. package/dist/modules/directory/api/get/tenants/lookup.js.map +2 -2
  19. package/dist/modules/integrations/api/[id]/route.js +38 -11
  20. package/dist/modules/integrations/api/[id]/route.js.map +2 -2
  21. package/dist/modules/integrations/api/logs/route.js +52 -26
  22. package/dist/modules/integrations/api/logs/route.js.map +2 -2
  23. package/dist/modules/integrations/api/route.js +37 -7
  24. package/dist/modules/integrations/api/route.js.map +2 -2
  25. package/dist/modules/integrations/api/umes-read.js +121 -0
  26. package/dist/modules/integrations/api/umes-read.js.map +7 -0
  27. package/dist/modules/integrations/backend/integrations/[id]/page.js +715 -183
  28. package/dist/modules/integrations/backend/integrations/[id]/page.js.map +2 -2
  29. package/dist/modules/integrations/backend/integrations/bundle/[id]/page.js +30 -9
  30. package/dist/modules/integrations/backend/integrations/bundle/[id]/page.js.map +2 -2
  31. package/dist/modules/integrations/backend/integrations/detail-page-widgets.js +46 -0
  32. package/dist/modules/integrations/backend/integrations/detail-page-widgets.js.map +7 -0
  33. package/dist/modules/integrations/backend/integrations/page.js +78 -62
  34. package/dist/modules/integrations/backend/integrations/page.js.map +2 -2
  35. package/dist/modules/integrations/backend/integrations/page.meta.js +2 -2
  36. package/dist/modules/integrations/backend/integrations/page.meta.js.map +1 -1
  37. package/dist/modules/integrations/setup.js +2 -2
  38. package/dist/modules/integrations/setup.js.map +2 -2
  39. package/dist/modules/payment_gateways/acl.js +12 -0
  40. package/dist/modules/payment_gateways/acl.js.map +7 -0
  41. package/dist/modules/payment_gateways/api/cancel/route.js +55 -0
  42. package/dist/modules/payment_gateways/api/cancel/route.js.map +7 -0
  43. package/dist/modules/payment_gateways/api/capture/route.js +55 -0
  44. package/dist/modules/payment_gateways/api/capture/route.js.map +7 -0
  45. package/dist/modules/payment_gateways/api/interceptors.js +24 -0
  46. package/dist/modules/payment_gateways/api/interceptors.js.map +7 -0
  47. package/dist/modules/payment_gateways/api/openapi.js +5 -0
  48. package/dist/modules/payment_gateways/api/openapi.js.map +7 -0
  49. package/dist/modules/payment_gateways/api/refund/route.js +56 -0
  50. package/dist/modules/payment_gateways/api/refund/route.js.map +7 -0
  51. package/dist/modules/payment_gateways/api/sessions/route.js +74 -0
  52. package/dist/modules/payment_gateways/api/sessions/route.js.map +7 -0
  53. package/dist/modules/payment_gateways/api/status/route.js +66 -0
  54. package/dist/modules/payment_gateways/api/status/route.js.map +7 -0
  55. package/dist/modules/payment_gateways/api/transactions/[id]/route.js +118 -0
  56. package/dist/modules/payment_gateways/api/transactions/[id]/route.js.map +7 -0
  57. package/dist/modules/payment_gateways/api/transactions/route.js +113 -0
  58. package/dist/modules/payment_gateways/api/transactions/route.js.map +7 -0
  59. package/dist/modules/payment_gateways/api/webhook/[provider]/route.js +136 -0
  60. package/dist/modules/payment_gateways/api/webhook/[provider]/route.js.map +7 -0
  61. package/dist/modules/payment_gateways/backend/payment-gateways/page.js +496 -0
  62. package/dist/modules/payment_gateways/backend/payment-gateways/page.js.map +7 -0
  63. package/dist/modules/payment_gateways/backend/payment-gateways/page.meta.js +23 -0
  64. package/dist/modules/payment_gateways/backend/payment-gateways/page.meta.js.map +7 -0
  65. package/dist/modules/payment_gateways/data/enrichers.js +5 -0
  66. package/dist/modules/payment_gateways/data/enrichers.js.map +7 -0
  67. package/dist/modules/payment_gateways/data/entities.js +131 -0
  68. package/dist/modules/payment_gateways/data/entities.js.map +7 -0
  69. package/dist/modules/payment_gateways/data/validators.js +57 -0
  70. package/dist/modules/payment_gateways/data/validators.js.map +7 -0
  71. package/dist/modules/payment_gateways/di.js +16 -0
  72. package/dist/modules/payment_gateways/di.js.map +7 -0
  73. package/dist/modules/payment_gateways/events.js +21 -0
  74. package/dist/modules/payment_gateways/events.js.map +7 -0
  75. package/dist/modules/payment_gateways/i18n/en.js +6 -0
  76. package/dist/modules/payment_gateways/i18n/en.js.map +7 -0
  77. package/dist/modules/payment_gateways/i18n/pl.js +6 -0
  78. package/dist/modules/payment_gateways/i18n/pl.js.map +7 -0
  79. package/dist/modules/payment_gateways/index.js +9 -0
  80. package/dist/modules/payment_gateways/index.js.map +7 -0
  81. package/dist/modules/payment_gateways/lib/gateway-service.js +378 -0
  82. package/dist/modules/payment_gateways/lib/gateway-service.js.map +7 -0
  83. package/dist/modules/payment_gateways/lib/queue.js +17 -0
  84. package/dist/modules/payment_gateways/lib/queue.js.map +7 -0
  85. package/dist/modules/payment_gateways/lib/status-machine.js +29 -0
  86. package/dist/modules/payment_gateways/lib/status-machine.js.map +7 -0
  87. package/dist/modules/payment_gateways/lib/webhook-processor.js +88 -0
  88. package/dist/modules/payment_gateways/lib/webhook-processor.js.map +7 -0
  89. package/dist/modules/payment_gateways/lib/webhook-utils.js +42 -0
  90. package/dist/modules/payment_gateways/lib/webhook-utils.js.map +7 -0
  91. package/dist/modules/payment_gateways/migrations/Migration20260305122155.js +19 -0
  92. package/dist/modules/payment_gateways/migrations/Migration20260305122155.js.map +7 -0
  93. package/dist/modules/payment_gateways/setup.js +13 -0
  94. package/dist/modules/payment_gateways/setup.js.map +7 -0
  95. package/dist/modules/payment_gateways/widgets/injection-table.js +7 -0
  96. package/dist/modules/payment_gateways/widgets/injection-table.js.map +7 -0
  97. package/dist/modules/payment_gateways/workers/status-poller.js +44 -0
  98. package/dist/modules/payment_gateways/workers/status-poller.js.map +7 -0
  99. package/dist/modules/payment_gateways/workers/webhook-processor.js +20 -0
  100. package/dist/modules/payment_gateways/workers/webhook-processor.js.map +7 -0
  101. package/dist/modules/sales/data/enrichers.js +72 -0
  102. package/dist/modules/sales/data/enrichers.js.map +7 -0
  103. package/dist/modules/sales/lib/makeSalesLineRoute.js +3 -0
  104. package/dist/modules/sales/lib/makeSalesLineRoute.js.map +2 -2
  105. package/dist/modules/sales/widgets/injection/payment-gateway-config-field/widget.js +29 -0
  106. package/dist/modules/sales/widgets/injection/payment-gateway-config-field/widget.js.map +7 -0
  107. package/dist/modules/sales/widgets/injection/payment-gateway-status-column/widget.js +23 -0
  108. package/dist/modules/sales/widgets/injection/payment-gateway-status-column/widget.js.map +7 -0
  109. package/dist/modules/sales/widgets/injection-table.js +13 -1
  110. package/dist/modules/sales/widgets/injection-table.js.map +2 -2
  111. package/dist/modules/shipping_carriers/acl.js +10 -0
  112. package/dist/modules/shipping_carriers/acl.js.map +7 -0
  113. package/dist/modules/shipping_carriers/api/cancel/route.js +55 -0
  114. package/dist/modules/shipping_carriers/api/cancel/route.js.map +7 -0
  115. package/dist/modules/shipping_carriers/api/interceptors.js +21 -0
  116. package/dist/modules/shipping_carriers/api/interceptors.js.map +7 -0
  117. package/dist/modules/shipping_carriers/api/openapi.js +5 -0
  118. package/dist/modules/shipping_carriers/api/openapi.js.map +7 -0
  119. package/dist/modules/shipping_carriers/api/rates/route.js +55 -0
  120. package/dist/modules/shipping_carriers/api/rates/route.js.map +7 -0
  121. package/dist/modules/shipping_carriers/api/shipments/route.js +61 -0
  122. package/dist/modules/shipping_carriers/api/shipments/route.js.map +7 -0
  123. package/dist/modules/shipping_carriers/api/tracking/route.js +58 -0
  124. package/dist/modules/shipping_carriers/api/tracking/route.js.map +7 -0
  125. package/dist/modules/shipping_carriers/api/webhook/[provider]/route.js +119 -0
  126. package/dist/modules/shipping_carriers/api/webhook/[provider]/route.js.map +7 -0
  127. package/dist/modules/shipping_carriers/data/enrichers.js +82 -0
  128. package/dist/modules/shipping_carriers/data/enrichers.js.map +7 -0
  129. package/dist/modules/shipping_carriers/data/entities.js +80 -0
  130. package/dist/modules/shipping_carriers/data/entities.js.map +7 -0
  131. package/dist/modules/shipping_carriers/data/validators.js +49 -0
  132. package/dist/modules/shipping_carriers/data/validators.js.map +7 -0
  133. package/dist/modules/shipping_carriers/di.js +15 -0
  134. package/dist/modules/shipping_carriers/di.js.map +7 -0
  135. package/dist/modules/shipping_carriers/events.js +19 -0
  136. package/dist/modules/shipping_carriers/events.js.map +7 -0
  137. package/dist/modules/shipping_carriers/i18n/en.js +11 -0
  138. package/dist/modules/shipping_carriers/i18n/en.js.map +7 -0
  139. package/dist/modules/shipping_carriers/i18n/pl.js +11 -0
  140. package/dist/modules/shipping_carriers/i18n/pl.js.map +7 -0
  141. package/dist/modules/shipping_carriers/index.js +9 -0
  142. package/dist/modules/shipping_carriers/index.js.map +7 -0
  143. package/dist/modules/shipping_carriers/lib/adapter-registry.js +29 -0
  144. package/dist/modules/shipping_carriers/lib/adapter-registry.js.map +7 -0
  145. package/dist/modules/shipping_carriers/lib/adapter.js +1 -0
  146. package/dist/modules/shipping_carriers/lib/adapter.js.map +7 -0
  147. package/dist/modules/shipping_carriers/lib/queue.js +17 -0
  148. package/dist/modules/shipping_carriers/lib/queue.js.map +7 -0
  149. package/dist/modules/shipping_carriers/lib/shipping-service.js +155 -0
  150. package/dist/modules/shipping_carriers/lib/shipping-service.js.map +7 -0
  151. package/dist/modules/shipping_carriers/lib/status-sync.js +37 -0
  152. package/dist/modules/shipping_carriers/lib/status-sync.js.map +7 -0
  153. package/dist/modules/shipping_carriers/migrations/Migration20260305170000.js +16 -0
  154. package/dist/modules/shipping_carriers/migrations/Migration20260305170000.js.map +7 -0
  155. package/dist/modules/shipping_carriers/setup.js +13 -0
  156. package/dist/modules/shipping_carriers/setup.js.map +7 -0
  157. package/dist/modules/shipping_carriers/widgets/injection/create-shipment-button/widget.js +25 -0
  158. package/dist/modules/shipping_carriers/widgets/injection/create-shipment-button/widget.js.map +7 -0
  159. package/dist/modules/shipping_carriers/widgets/injection/tracking-column/widget.js +23 -0
  160. package/dist/modules/shipping_carriers/widgets/injection/tracking-column/widget.js.map +7 -0
  161. package/dist/modules/shipping_carriers/widgets/injection/tracking-status-badge/widget.js +40 -0
  162. package/dist/modules/shipping_carriers/widgets/injection/tracking-status-badge/widget.js.map +7 -0
  163. package/dist/modules/shipping_carriers/widgets/injection-table.js +24 -0
  164. package/dist/modules/shipping_carriers/widgets/injection-table.js.map +7 -0
  165. package/dist/modules/shipping_carriers/workers/status-poller.js +21 -0
  166. package/dist/modules/shipping_carriers/workers/status-poller.js.map +7 -0
  167. package/dist/modules/shipping_carriers/workers/webhook-processor.js +54 -0
  168. package/dist/modules/shipping_carriers/workers/webhook-processor.js.map +7 -0
  169. package/dist/modules/translations/api/get/locales.js +1 -0
  170. package/dist/modules/translations/api/get/locales.js.map +2 -2
  171. package/dist/modules/translations/api/put/locales.js +1 -0
  172. package/dist/modules/translations/api/put/locales.js.map +2 -2
  173. package/generated/entities/carrier_shipment/index.ts +17 -0
  174. package/generated/entities/gateway_transaction/index.ts +22 -0
  175. package/generated/entities/webhook_processed_event/index.ts +7 -0
  176. package/generated/entities.ids.generated.ts +10 -1
  177. package/generated/entity-fields-registry.ts +6 -0
  178. package/jest.config.cjs +1 -0
  179. package/package.json +5 -2
  180. package/src/modules/auth/i18n/de.json +1 -0
  181. package/src/modules/auth/i18n/en.json +1 -0
  182. package/src/modules/auth/i18n/es.json +1 -0
  183. package/src/modules/auth/i18n/pl.json +1 -0
  184. package/src/modules/data_sync/api/runs/[id]/cancel.ts +18 -5
  185. package/src/modules/data_sync/backend/data-sync/page.meta.ts +2 -2
  186. package/src/modules/data_sync/backend/data-sync/runs/[id]/page.tsx +50 -12
  187. package/src/modules/directory/api/get/tenants/lookup.ts +1 -0
  188. package/src/modules/integrations/AGENTS.md +31 -0
  189. package/src/modules/integrations/api/[id]/route.ts +38 -11
  190. package/src/modules/integrations/api/logs/route.ts +53 -27
  191. package/src/modules/integrations/api/route.ts +31 -1
  192. package/src/modules/integrations/api/umes-read.ts +177 -0
  193. package/src/modules/integrations/backend/integrations/[id]/page.tsx +902 -202
  194. package/src/modules/integrations/backend/integrations/bundle/[id]/page.tsx +43 -9
  195. package/src/modules/integrations/backend/integrations/detail-page-widgets.ts +74 -0
  196. package/src/modules/integrations/backend/integrations/page.meta.ts +2 -2
  197. package/src/modules/integrations/backend/integrations/page.tsx +65 -54
  198. package/src/modules/integrations/i18n/de.json +15 -0
  199. package/src/modules/integrations/i18n/en.json +15 -0
  200. package/src/modules/integrations/i18n/es.json +15 -0
  201. package/src/modules/integrations/i18n/pl.json +15 -0
  202. package/src/modules/integrations/setup.ts +2 -2
  203. package/src/modules/payment_gateways/acl.ts +8 -0
  204. package/src/modules/payment_gateways/api/cancel/route.ts +56 -0
  205. package/src/modules/payment_gateways/api/capture/route.ts +56 -0
  206. package/src/modules/payment_gateways/api/interceptors.ts +22 -0
  207. package/src/modules/payment_gateways/api/openapi.ts +1 -0
  208. package/src/modules/payment_gateways/api/refund/route.ts +57 -0
  209. package/src/modules/payment_gateways/api/sessions/route.ts +76 -0
  210. package/src/modules/payment_gateways/api/status/route.ts +69 -0
  211. package/src/modules/payment_gateways/api/transactions/[id]/route.ts +123 -0
  212. package/src/modules/payment_gateways/api/transactions/route.ts +120 -0
  213. package/src/modules/payment_gateways/api/webhook/[provider]/route.ts +161 -0
  214. package/src/modules/payment_gateways/backend/payment-gateways/page.meta.ts +19 -0
  215. package/src/modules/payment_gateways/backend/payment-gateways/page.tsx +660 -0
  216. package/src/modules/payment_gateways/data/enrichers.ts +8 -0
  217. package/src/modules/payment_gateways/data/entities.ts +106 -0
  218. package/src/modules/payment_gateways/data/validators.ts +67 -0
  219. package/src/modules/payment_gateways/di.ts +26 -0
  220. package/src/modules/payment_gateways/events.ts +17 -0
  221. package/src/modules/payment_gateways/i18n/de.json +77 -0
  222. package/src/modules/payment_gateways/i18n/en.json +77 -0
  223. package/src/modules/payment_gateways/i18n/en.ts +4 -0
  224. package/src/modules/payment_gateways/i18n/es.json +77 -0
  225. package/src/modules/payment_gateways/i18n/pl.json +77 -0
  226. package/src/modules/payment_gateways/i18n/pl.ts +4 -0
  227. package/src/modules/payment_gateways/index.ts +5 -0
  228. package/src/modules/payment_gateways/lib/gateway-service.ts +486 -0
  229. package/src/modules/payment_gateways/lib/queue.ts +19 -0
  230. package/src/modules/payment_gateways/lib/status-machine.ts +28 -0
  231. package/src/modules/payment_gateways/lib/webhook-processor.ts +133 -0
  232. package/src/modules/payment_gateways/lib/webhook-utils.ts +52 -0
  233. package/src/modules/payment_gateways/migrations/.snapshot-open-mercato.json +373 -0
  234. package/src/modules/payment_gateways/migrations/Migration20260305122155.ts +20 -0
  235. package/src/modules/payment_gateways/setup.ts +11 -0
  236. package/src/modules/payment_gateways/widgets/injection-table.ts +9 -0
  237. package/src/modules/payment_gateways/workers/status-poller.ts +58 -0
  238. package/src/modules/payment_gateways/workers/webhook-processor.ts +30 -0
  239. package/src/modules/sales/data/enrichers.ts +120 -0
  240. package/src/modules/sales/lib/makeSalesLineRoute.ts +3 -0
  241. package/src/modules/sales/widgets/injection/payment-gateway-config-field/widget.ts +28 -0
  242. package/src/modules/sales/widgets/injection/payment-gateway-status-column/widget.ts +22 -0
  243. package/src/modules/sales/widgets/injection-table.ts +12 -0
  244. package/src/modules/shipping_carriers/acl.ts +6 -0
  245. package/src/modules/shipping_carriers/api/cancel/route.ts +53 -0
  246. package/src/modules/shipping_carriers/api/interceptors.ts +19 -0
  247. package/src/modules/shipping_carriers/api/openapi.ts +1 -0
  248. package/src/modules/shipping_carriers/api/rates/route.ts +53 -0
  249. package/src/modules/shipping_carriers/api/shipments/route.ts +59 -0
  250. package/src/modules/shipping_carriers/api/tracking/route.ts +56 -0
  251. package/src/modules/shipping_carriers/api/webhook/[provider]/route.ts +134 -0
  252. package/src/modules/shipping_carriers/data/enrichers.ts +89 -0
  253. package/src/modules/shipping_carriers/data/entities.ts +60 -0
  254. package/src/modules/shipping_carriers/data/validators.ts +48 -0
  255. package/src/modules/shipping_carriers/di.ts +20 -0
  256. package/src/modules/shipping_carriers/events.ts +16 -0
  257. package/src/modules/shipping_carriers/i18n/de.json +7 -0
  258. package/src/modules/shipping_carriers/i18n/en.json +7 -0
  259. package/src/modules/shipping_carriers/i18n/en.ts +7 -0
  260. package/src/modules/shipping_carriers/i18n/es.json +7 -0
  261. package/src/modules/shipping_carriers/i18n/pl.json +7 -0
  262. package/src/modules/shipping_carriers/i18n/pl.ts +7 -0
  263. package/src/modules/shipping_carriers/index.ts +5 -0
  264. package/src/modules/shipping_carriers/lib/adapter-registry.ts +33 -0
  265. package/src/modules/shipping_carriers/lib/adapter.ts +93 -0
  266. package/src/modules/shipping_carriers/lib/queue.ts +19 -0
  267. package/src/modules/shipping_carriers/lib/shipping-service.ts +204 -0
  268. package/src/modules/shipping_carriers/lib/status-sync.ts +38 -0
  269. package/src/modules/shipping_carriers/migrations/Migration20260305170000.ts +14 -0
  270. package/src/modules/shipping_carriers/setup.ts +11 -0
  271. package/src/modules/shipping_carriers/widgets/injection/create-shipment-button/widget.ts +24 -0
  272. package/src/modules/shipping_carriers/widgets/injection/tracking-column/widget.ts +22 -0
  273. package/src/modules/shipping_carriers/widgets/injection/tracking-status-badge/widget.tsx +44 -0
  274. package/src/modules/shipping_carriers/widgets/injection-table.ts +22 -0
  275. package/src/modules/shipping_carriers/workers/status-poller.ts +33 -0
  276. package/src/modules/shipping_carriers/workers/webhook-processor.ts +79 -0
  277. package/src/modules/translations/api/get/locales.ts +1 -0
  278. package/src/modules/translations/api/put/locales.ts +1 -0
@@ -4,7 +4,6 @@ import * as React from "react";
4
4
  import Link from "next/link";
5
5
  import { Page, PageBody } from "@open-mercato/ui/backend/Page";
6
6
  import { Card, CardHeader, CardTitle, CardContent } from "@open-mercato/ui/primitives/card";
7
- import { Badge } from "@open-mercato/ui/primitives/badge";
8
7
  import { Button } from "@open-mercato/ui/primitives/button";
9
8
  import { Switch } from "@open-mercato/ui/primitives/switch";
10
9
  import { Input } from "@open-mercato/ui/primitives/input";
@@ -14,7 +13,7 @@ import { flash } from "@open-mercato/ui/backend/FlashMessages";
14
13
  import { useOrganizationScopeVersion } from "@open-mercato/shared/lib/frontend/useOrganizationScope";
15
14
  import { useT } from "@open-mercato/shared/lib/i18n/context";
16
15
  import { FilterBar } from "@open-mercato/ui/backend/FilterBar";
17
- import { Bell, CreditCard, HardDrive, LayoutGrid, MessageSquare, RefreshCw, Truck, Webhook } from "lucide-react";
16
+ import { Bell, Cog, CreditCard, HardDrive, LayoutGrid, MessageSquare, RefreshCw, Search, Truck, Webhook } from "lucide-react";
18
17
  import {
19
18
  buildIntegrationMarketplaceFilterDefs,
20
19
  getIntegrationMarketplaceCategory,
@@ -31,10 +30,6 @@ const CATEGORY_ICONS = {
31
30
  storage: HardDrive,
32
31
  webhook: Webhook
33
32
  };
34
- function categoryBadgeVariant(category) {
35
- if (!category) return "outline";
36
- return "secondary";
37
- }
38
33
  function IntegrationsMarketplacePage() {
39
34
  const [data, setData] = React.useState(null);
40
35
  const [isLoading, setIsLoading] = React.useState(true);
@@ -110,14 +105,34 @@ function IntegrationsMarketplacePage() {
110
105
  const bundles = (data.bundles ?? []).filter((b) => bundled.has(b.id)).map((b) => ({ ...b, integrations: bundled.get(b.id) ?? [] }));
111
106
  return { bundles, standalone };
112
107
  }, [data, search, selectedCategory]);
108
+ const renderCategoryIcon = React.useCallback((category, className) => {
109
+ if (!category) return null;
110
+ const Icon = CATEGORY_ICONS[category];
111
+ if (!Icon) return null;
112
+ return /* @__PURE__ */ jsx(Icon, { className });
113
+ }, []);
113
114
  if (isLoading) {
114
115
  return /* @__PURE__ */ jsx(Page, { children: /* @__PURE__ */ jsx(PageBody, { children: /* @__PURE__ */ jsx("div", { className: "flex items-center justify-center py-16", children: /* @__PURE__ */ jsx(Spinner, {}) }) }) });
115
116
  }
116
117
  return /* @__PURE__ */ jsx(Page, { children: /* @__PURE__ */ jsx(PageBody, { className: "space-y-6", children: /* @__PURE__ */ jsxs("section", { className: "space-y-6 rounded-lg border bg-background p-6", children: [
117
- /* @__PURE__ */ jsx("header", { className: "flex flex-col gap-4 sm:flex-row sm:items-start sm:justify-between", children: /* @__PURE__ */ jsxs("div", { className: "space-y-1", children: [
118
- /* @__PURE__ */ jsx("h2", { className: "text-lg font-semibold", children: t("integrations.marketplace.title") }),
119
- /* @__PURE__ */ jsx("p", { className: "text-sm text-muted-foreground", children: t("integrations.marketplace.description") })
120
- ] }) }),
118
+ /* @__PURE__ */ jsxs("header", { className: "flex items-center justify-between gap-4", children: [
119
+ /* @__PURE__ */ jsxs("div", { className: "space-y-0.5", children: [
120
+ /* @__PURE__ */ jsx("h2", { className: "text-lg font-semibold", children: t("integrations.marketplace.title") }),
121
+ /* @__PURE__ */ jsx("p", { className: "text-sm text-muted-foreground", children: t("integrations.marketplace.description") })
122
+ ] }),
123
+ /* @__PURE__ */ jsxs("div", { className: "relative w-64 shrink-0 hidden lg:block", children: [
124
+ /* @__PURE__ */ jsx(Search, { className: "absolute left-2.5 top-1/2 -translate-y-1/2 size-4 text-muted-foreground pointer-events-none" }),
125
+ /* @__PURE__ */ jsx(
126
+ Input,
127
+ {
128
+ placeholder: t("integrations.marketplace.search"),
129
+ value: search,
130
+ onChange: (e) => setSearch(e.target.value),
131
+ className: "pl-8"
132
+ }
133
+ )
134
+ ] })
135
+ ] }),
121
136
  /* @__PURE__ */ jsx("div", { className: "lg:hidden", children: /* @__PURE__ */ jsx(
122
137
  FilterBar,
123
138
  {
@@ -131,34 +146,23 @@ function IntegrationsMarketplacePage() {
131
146
  onClear: () => setFilterValues({})
132
147
  }
133
148
  ) }),
134
- /* @__PURE__ */ jsx("div", { className: "hidden lg:flex lg:flex-col gap-4", children: /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-4 sm:flex-row sm:items-center", children: [
135
- /* @__PURE__ */ jsx(
136
- Input,
149
+ /* @__PURE__ */ jsx("div", { className: "hidden lg:flex flex-wrap gap-1.5", children: INTEGRATION_MARKETPLACE_CATEGORIES.map((category) => {
150
+ const Icon = CATEGORY_ICONS[category];
151
+ return /* @__PURE__ */ jsxs(
152
+ Button,
137
153
  {
138
- placeholder: t("integrations.marketplace.search"),
139
- value: search,
140
- onChange: (e) => setSearch(e.target.value),
141
- className: "max-w-sm"
142
- }
143
- ),
144
- /* @__PURE__ */ jsx("div", { className: "flex flex-wrap gap-1.5", children: INTEGRATION_MARKETPLACE_CATEGORIES.map((category) => {
145
- const Icon = CATEGORY_ICONS[category];
146
- return /* @__PURE__ */ jsxs(
147
- Button,
148
- {
149
- type: "button",
150
- variant: selectedCategory === category ? "default" : "outline",
151
- size: "sm",
152
- onClick: () => setFilterValues(normalizeIntegrationMarketplaceFilterValues({ category })),
153
- children: [
154
- Icon ? /* @__PURE__ */ jsx(Icon, { className: "mr-1.5 h-3.5 w-3.5" }) : null,
155
- t(`integrations.marketplace.categories.${category}`)
156
- ]
157
- },
158
- category
159
- );
160
- }) })
161
- ] }) }),
154
+ type: "button",
155
+ variant: selectedCategory === category ? "default" : "outline",
156
+ size: "sm",
157
+ onClick: () => setFilterValues(normalizeIntegrationMarketplaceFilterValues({ category })),
158
+ children: [
159
+ Icon ? /* @__PURE__ */ jsx(Icon, { className: "mr-1.5 h-3.5 w-3.5" }) : null,
160
+ t(`integrations.marketplace.categories.${category}`)
161
+ ]
162
+ },
163
+ category
164
+ );
165
+ }) }),
162
166
  filteredItems.bundles.map((bundle) => /* @__PURE__ */ jsxs(Card, { children: [
163
167
  /* @__PURE__ */ jsx(CardHeader, { children: /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between", children: [
164
168
  /* @__PURE__ */ jsxs("div", { children: [
@@ -166,23 +170,29 @@ function IntegrationsMarketplacePage() {
166
170
  bundle.description && /* @__PURE__ */ jsx("p", { className: "text-muted-foreground text-sm mt-1", children: bundle.description }),
167
171
  /* @__PURE__ */ jsx("p", { className: "text-muted-foreground text-xs mt-1", children: t("integrations.marketplace.integrations", { count: bundle.integrations.length }) })
168
172
  ] }),
169
- /* @__PURE__ */ jsx(Button, { asChild: true, variant: "outline", size: "sm", children: /* @__PURE__ */ jsx(Link, { href: `/backend/integrations/bundle/${encodeURIComponent(bundle.id)}`, children: t("integrations.marketplace.configure") }) })
173
+ /* @__PURE__ */ jsx(Button, { asChild: true, variant: "outline", size: "sm", children: /* @__PURE__ */ jsxs(Link, { href: `/backend/integrations/bundle/${encodeURIComponent(bundle.id)}`, children: [
174
+ /* @__PURE__ */ jsx(Cog, { className: "mr-1.5 h-4 w-4" }),
175
+ t("integrations.marketplace.configure")
176
+ ] }) })
170
177
  ] }) }),
171
178
  /* @__PURE__ */ jsx(CardContent, { children: /* @__PURE__ */ jsx("div", { className: "grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-3", children: bundle.integrations.map((item) => /* @__PURE__ */ jsxs(
172
179
  "div",
173
180
  {
174
181
  className: "flex items-center justify-between rounded-lg border p-3",
175
182
  children: [
176
- /* @__PURE__ */ jsxs("div", { className: "min-w-0", children: [
177
- /* @__PURE__ */ jsx(
178
- Link,
179
- {
180
- href: `/backend/integrations/${encodeURIComponent(item.id)}`,
181
- className: "text-sm font-medium hover:underline",
182
- children: item.title
183
- }
184
- ),
185
- item.category && /* @__PURE__ */ jsx(Badge, { variant: categoryBadgeVariant(item.category), className: "ml-2 text-xs", children: item.category })
183
+ /* @__PURE__ */ jsxs("div", { className: "min-w-0 space-y-1", children: [
184
+ /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-2", children: [
185
+ renderCategoryIcon(item.category, "h-4 w-4 text-muted-foreground"),
186
+ /* @__PURE__ */ jsx(
187
+ Link,
188
+ {
189
+ href: `/backend/integrations/${encodeURIComponent(item.id)}`,
190
+ className: "truncate text-sm font-medium hover:underline",
191
+ children: item.title
192
+ }
193
+ )
194
+ ] }),
195
+ item.company || item.author || item.version ? /* @__PURE__ */ jsx("p", { className: "text-xs text-muted-foreground", children: [item.company || item.author, item.version ? `v${item.version}` : null].filter(Boolean).join(" \xB7 ") }) : null
186
196
  ] }),
187
197
  /* @__PURE__ */ jsx(
188
198
  Switch,
@@ -198,22 +208,28 @@ function IntegrationsMarketplacePage() {
198
208
  )) }) })
199
209
  ] }, bundle.id)),
200
210
  filteredItems.standalone.length > 0 && /* @__PURE__ */ jsx("div", { className: "grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-4", children: filteredItems.standalone.map((item) => /* @__PURE__ */ jsxs(Card, { className: "flex flex-col", children: [
201
- /* @__PURE__ */ jsxs(CardHeader, { children: [
202
- /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between", children: [
203
- /* @__PURE__ */ jsx(CardTitle, { className: "text-base", children: item.title }),
204
- /* @__PURE__ */ jsx(
205
- Switch,
206
- {
207
- checked: item.isEnabled,
208
- disabled: togglingIds.has(item.id),
209
- onCheckedChange: (checked) => void handleToggle(item.id, checked)
210
- }
211
- )
211
+ /* @__PURE__ */ jsx(CardHeader, { children: /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between", children: [
212
+ /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-2", children: [
213
+ renderCategoryIcon(item.category, "h-4 w-4 text-muted-foreground"),
214
+ /* @__PURE__ */ jsx(CardTitle, { className: "text-base", children: item.title })
212
215
  ] }),
213
- item.category && /* @__PURE__ */ jsx(Badge, { variant: categoryBadgeVariant(item.category), className: "w-fit text-xs", children: item.category })
216
+ /* @__PURE__ */ jsx(
217
+ Switch,
218
+ {
219
+ checked: item.isEnabled,
220
+ disabled: togglingIds.has(item.id),
221
+ onCheckedChange: (checked) => void handleToggle(item.id, checked)
222
+ }
223
+ )
224
+ ] }) }),
225
+ /* @__PURE__ */ jsxs(CardContent, { className: "flex-1 space-y-2", children: [
226
+ item.description && /* @__PURE__ */ jsx("p", { className: "text-muted-foreground text-sm", children: item.description }),
227
+ (item.company || item.author || item.version) && /* @__PURE__ */ jsx("p", { className: "text-muted-foreground text-xs", children: [item.company || item.author, item.version ? `v${item.version}` : null].filter(Boolean).join(" \xB7 ") })
214
228
  ] }),
215
- /* @__PURE__ */ jsx(CardContent, { className: "flex-1", children: item.description && /* @__PURE__ */ jsx("p", { className: "text-muted-foreground text-sm", children: item.description }) }),
216
- /* @__PURE__ */ jsx("div", { className: "px-6 pb-4", children: /* @__PURE__ */ jsx(Button, { asChild: true, variant: "outline", size: "sm", className: "w-full", children: /* @__PURE__ */ jsx(Link, { href: `/backend/integrations/${encodeURIComponent(item.id)}`, children: t("integrations.marketplace.configure") }) }) })
229
+ /* @__PURE__ */ jsx("div", { className: "px-6 pb-4", children: /* @__PURE__ */ jsx(Button, { asChild: true, variant: "outline", size: "sm", className: "w-full", children: /* @__PURE__ */ jsxs(Link, { href: `/backend/integrations/${encodeURIComponent(item.id)}`, children: [
230
+ /* @__PURE__ */ jsx(Cog, { className: "mr-1.5 h-4 w-4" }),
231
+ t("integrations.marketplace.configure")
232
+ ] }) }) })
217
233
  ] }, item.id)) }),
218
234
  filteredItems.bundles.length === 0 && filteredItems.standalone.length === 0 && /* @__PURE__ */ jsx("div", { className: "text-center py-12 text-muted-foreground", children: t("integrations.marketplace.noResults") })
219
235
  ] }) }) });
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../../src/modules/integrations/backend/integrations/page.tsx"],
4
- "sourcesContent": ["\"use client\"\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { Card, CardHeader, CardTitle, CardContent } from '@open-mercato/ui/primitives/card'\nimport { Badge } from '@open-mercato/ui/primitives/badge'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { Switch } from '@open-mercato/ui/primitives/switch'\nimport { Input } from '@open-mercato/ui/primitives/input'\nimport { Spinner } from '@open-mercato/ui/primitives/spinner'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useOrganizationScopeVersion } from '@open-mercato/shared/lib/frontend/useOrganizationScope'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\nimport { FilterBar, type FilterValues } from '@open-mercato/ui/backend/FilterBar'\nimport { Bell, CreditCard, HardDrive, LayoutGrid, MessageSquare, RefreshCw, Truck, Webhook } from 'lucide-react'\nimport {\n buildIntegrationMarketplaceFilterDefs,\n getIntegrationMarketplaceCategory,\n INTEGRATION_MARKETPLACE_CATEGORIES,\n normalizeIntegrationMarketplaceFilterValues,\n} from './filters'\n\ntype IntegrationItem = {\n id: string\n title: string\n description?: string\n category?: string\n icon?: string\n bundleId?: string\n isEnabled: boolean\n hasCredentials: boolean\n}\n\ntype BundleItem = {\n id: string\n title: string\n description?: string\n icon?: string\n integrationCount: number\n enabledCount: number\n}\n\ntype ListResponse = {\n items: IntegrationItem[]\n bundles: BundleItem[]\n}\n\nconst CATEGORY_ICONS: Record<string, React.ElementType> = {\n all: LayoutGrid,\n payment: CreditCard,\n shipping: Truck,\n data_sync: RefreshCw,\n communication: MessageSquare,\n notification: Bell,\n storage: HardDrive,\n webhook: Webhook,\n}\n\nfunction categoryBadgeVariant(category: string | undefined): 'default' | 'secondary' | 'outline' {\n if (!category) return 'outline'\n return 'secondary'\n}\n\nexport default function IntegrationsMarketplacePage() {\n const [data, setData] = React.useState<ListResponse | null>(null)\n const [isLoading, setIsLoading] = React.useState(true)\n const [search, setSearch] = React.useState('')\n const [filterValues, setFilterValues] = React.useState<FilterValues>({})\n const [togglingIds, setTogglingIds] = React.useState<Set<string>>(new Set())\n const scopeVersion = useOrganizationScopeVersion()\n const t = useT()\n\n const categoryFilters = React.useMemo(() => buildIntegrationMarketplaceFilterDefs(t), [t])\n const selectedCategory = React.useMemo(() => getIntegrationMarketplaceCategory(filterValues), [filterValues])\n\n const load = React.useCallback(async () => {\n setIsLoading(true)\n const fallback: ListResponse = { items: [], bundles: [] }\n const call = await apiCall<ListResponse>('/api/integrations', undefined, { fallback })\n if (!call.ok) {\n flash(t('integrations.marketplace.loadError'), 'error')\n setIsLoading(false)\n return\n }\n setData(call.result ?? fallback)\n setIsLoading(false)\n }, [t])\n\n React.useEffect(() => { void load() }, [load, scopeVersion])\n\n const handleToggle = React.useCallback(async (integrationId: string, enabled: boolean) => {\n setTogglingIds((prev) => new Set(prev).add(integrationId))\n const call = await apiCall(`/api/integrations/${encodeURIComponent(integrationId)}/state`, {\n method: 'PUT',\n headers: { 'Content-Type': 'application/json' },\n body: JSON.stringify({ isEnabled: enabled }),\n }, { fallback: null })\n\n if (!call.ok) {\n flash(t('integrations.detail.stateError'), 'error')\n } else {\n setData((prev) => {\n if (!prev) return prev\n return {\n ...prev,\n items: prev.items.map((item) =>\n item.id === integrationId ? { ...item, isEnabled: enabled } : item,\n ),\n }\n })\n }\n setTogglingIds((prev) => { const next = new Set(prev); next.delete(integrationId); return next })\n }, [t])\n\n const filteredItems = React.useMemo(() => {\n if (!data) return { bundles: [], standalone: [] }\n\n let items = data.items\n if (search) {\n const q = search.toLowerCase()\n items = items.filter((item) => item.title.toLowerCase().includes(q) || item.description?.toLowerCase().includes(q))\n }\n if (selectedCategory !== 'all') {\n items = items.filter((item) => item.category === selectedCategory)\n }\n\n const bundled = new Map<string, IntegrationItem[]>()\n const standalone: IntegrationItem[] = []\n for (const item of items) {\n if (item.bundleId) {\n const list = bundled.get(item.bundleId) ?? []\n list.push(item)\n bundled.set(item.bundleId, list)\n } else {\n standalone.push(item)\n }\n }\n\n const bundles = (data.bundles ?? [])\n .filter((b) => bundled.has(b.id))\n .map((b) => ({ ...b, integrations: bundled.get(b.id) ?? [] }))\n\n return { bundles, standalone }\n }, [data, search, selectedCategory])\n\n if (isLoading) {\n return (\n <Page>\n <PageBody>\n <div className=\"flex items-center justify-center py-16\">\n <Spinner />\n </div>\n </PageBody>\n </Page>\n )\n }\n\n return (\n <Page>\n <PageBody className=\"space-y-6\">\n <section className=\"space-y-6 rounded-lg border bg-background p-6\">\n <header className=\"flex flex-col gap-4 sm:flex-row sm:items-start sm:justify-between\">\n <div className=\"space-y-1\">\n <h2 className=\"text-lg font-semibold\">{t('integrations.marketplace.title')}</h2>\n <p className=\"text-sm text-muted-foreground\">\n {t('integrations.marketplace.description')}\n </p>\n </div>\n </header>\n\n <div className=\"lg:hidden\">\n <FilterBar\n searchValue={search}\n onSearchChange={setSearch}\n searchPlaceholder={t('integrations.marketplace.search')}\n searchAlign=\"left\"\n filters={categoryFilters}\n values={filterValues}\n onApply={(values) => setFilterValues(normalizeIntegrationMarketplaceFilterValues(values))}\n onClear={() => setFilterValues({})}\n />\n </div>\n\n <div className=\"hidden lg:flex lg:flex-col gap-4\">\n <div className=\"flex flex-col gap-4 sm:flex-row sm:items-center\">\n <Input\n placeholder={t('integrations.marketplace.search')}\n value={search}\n onChange={(e) => setSearch(e.target.value)}\n className=\"max-w-sm\"\n />\n <div className=\"flex flex-wrap gap-1.5\">\n {INTEGRATION_MARKETPLACE_CATEGORIES.map((category) => {\n const Icon = CATEGORY_ICONS[category]\n return (\n <Button\n key={category}\n type=\"button\"\n variant={selectedCategory === category ? 'default' : 'outline'}\n size=\"sm\"\n onClick={() => setFilterValues(normalizeIntegrationMarketplaceFilterValues({ category }))}\n >\n {Icon ? <Icon className=\"mr-1.5 h-3.5 w-3.5\" /> : null}\n {t(`integrations.marketplace.categories.${category}`)}\n </Button>\n )\n })}\n </div>\n </div>\n </div>\n\n {filteredItems.bundles.map((bundle) => (\n <Card key={bundle.id}>\n <CardHeader>\n <div className=\"flex items-center justify-between\">\n <div>\n <CardTitle>{bundle.title}</CardTitle>\n {bundle.description && (\n <p className=\"text-muted-foreground text-sm mt-1\">{bundle.description}</p>\n )}\n <p className=\"text-muted-foreground text-xs mt-1\">\n {t('integrations.marketplace.integrations', { count: bundle.integrations.length })}\n </p>\n </div>\n <Button asChild variant=\"outline\" size=\"sm\">\n <Link href={`/backend/integrations/bundle/${encodeURIComponent(bundle.id)}`}>\n {t('integrations.marketplace.configure')}\n </Link>\n </Button>\n </div>\n </CardHeader>\n <CardContent>\n <div className=\"grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-3\">\n {bundle.integrations.map((item) => (\n <div\n key={item.id}\n className=\"flex items-center justify-between rounded-lg border p-3\"\n >\n <div className=\"min-w-0\">\n <Link\n href={`/backend/integrations/${encodeURIComponent(item.id)}`}\n className=\"text-sm font-medium hover:underline\"\n >\n {item.title}\n </Link>\n {item.category && (\n <Badge variant={categoryBadgeVariant(item.category)} className=\"ml-2 text-xs\">\n {item.category}\n </Badge>\n )}\n </div>\n <Switch\n checked={item.isEnabled}\n disabled={togglingIds.has(item.id)}\n onCheckedChange={(checked) => void handleToggle(item.id, checked)}\n />\n </div>\n ))}\n </div>\n </CardContent>\n </Card>\n ))}\n\n {filteredItems.standalone.length > 0 && (\n <div className=\"grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-4\">\n {filteredItems.standalone.map((item) => (\n <Card key={item.id} className=\"flex flex-col\">\n <CardHeader>\n <div className=\"flex items-center justify-between\">\n <CardTitle className=\"text-base\">{item.title}</CardTitle>\n <Switch\n checked={item.isEnabled}\n disabled={togglingIds.has(item.id)}\n onCheckedChange={(checked) => void handleToggle(item.id, checked)}\n />\n </div>\n {item.category && (\n <Badge variant={categoryBadgeVariant(item.category)} className=\"w-fit text-xs\">\n {item.category}\n </Badge>\n )}\n </CardHeader>\n <CardContent className=\"flex-1\">\n {item.description && (\n <p className=\"text-muted-foreground text-sm\">{item.description}</p>\n )}\n </CardContent>\n <div className=\"px-6 pb-4\">\n <Button asChild variant=\"outline\" size=\"sm\" className=\"w-full\">\n <Link href={`/backend/integrations/${encodeURIComponent(item.id)}`}>\n {t('integrations.marketplace.configure')}\n </Link>\n </Button>\n </div>\n </Card>\n ))}\n </div>\n )}\n\n {filteredItems.bundles.length === 0 && filteredItems.standalone.length === 0 && (\n <div className=\"text-center py-12 text-muted-foreground\">\n {t('integrations.marketplace.noResults')}\n </div>\n )}\n </section>\n </PageBody>\n </Page>\n )\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["\"use client\"\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { Card, CardHeader, CardTitle, CardContent } from '@open-mercato/ui/primitives/card'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { Switch } from '@open-mercato/ui/primitives/switch'\nimport { Input } from '@open-mercato/ui/primitives/input'\nimport { Spinner } from '@open-mercato/ui/primitives/spinner'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useOrganizationScopeVersion } from '@open-mercato/shared/lib/frontend/useOrganizationScope'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\nimport { FilterBar, type FilterValues } from '@open-mercato/ui/backend/FilterBar'\nimport { Bell, Cog, CreditCard, HardDrive, LayoutGrid, MessageSquare, RefreshCw, Search, Truck, Webhook } from 'lucide-react'\nimport {\n buildIntegrationMarketplaceFilterDefs,\n getIntegrationMarketplaceCategory,\n INTEGRATION_MARKETPLACE_CATEGORIES,\n normalizeIntegrationMarketplaceFilterValues,\n} from './filters'\n\ntype IntegrationItem = {\n id: string\n title: string\n description?: string\n category?: string\n icon?: string\n bundleId?: string\n author?: string\n company?: string\n version?: string\n isEnabled: boolean\n hasCredentials: boolean\n}\n\ntype BundleItem = {\n id: string\n title: string\n description?: string\n icon?: string\n integrationCount: number\n enabledCount: number\n}\n\ntype ListResponse = {\n items: IntegrationItem[]\n bundles: BundleItem[]\n}\n\nconst CATEGORY_ICONS: Record<string, React.ElementType> = {\n all: LayoutGrid,\n payment: CreditCard,\n shipping: Truck,\n data_sync: RefreshCw,\n communication: MessageSquare,\n notification: Bell,\n storage: HardDrive,\n webhook: Webhook,\n}\n\nexport default function IntegrationsMarketplacePage() {\n const [data, setData] = React.useState<ListResponse | null>(null)\n const [isLoading, setIsLoading] = React.useState(true)\n const [search, setSearch] = React.useState('')\n const [filterValues, setFilterValues] = React.useState<FilterValues>({})\n const [togglingIds, setTogglingIds] = React.useState<Set<string>>(new Set())\n const scopeVersion = useOrganizationScopeVersion()\n const t = useT()\n\n const categoryFilters = React.useMemo(() => buildIntegrationMarketplaceFilterDefs(t), [t])\n const selectedCategory = React.useMemo(() => getIntegrationMarketplaceCategory(filterValues), [filterValues])\n\n const load = React.useCallback(async () => {\n setIsLoading(true)\n const fallback: ListResponse = { items: [], bundles: [] }\n const call = await apiCall<ListResponse>('/api/integrations', undefined, { fallback })\n if (!call.ok) {\n flash(t('integrations.marketplace.loadError'), 'error')\n setIsLoading(false)\n return\n }\n setData(call.result ?? fallback)\n setIsLoading(false)\n }, [t])\n\n React.useEffect(() => { void load() }, [load, scopeVersion])\n\n const handleToggle = React.useCallback(async (integrationId: string, enabled: boolean) => {\n setTogglingIds((prev) => new Set(prev).add(integrationId))\n const call = await apiCall(`/api/integrations/${encodeURIComponent(integrationId)}/state`, {\n method: 'PUT',\n headers: { 'Content-Type': 'application/json' },\n body: JSON.stringify({ isEnabled: enabled }),\n }, { fallback: null })\n\n if (!call.ok) {\n flash(t('integrations.detail.stateError'), 'error')\n } else {\n setData((prev) => {\n if (!prev) return prev\n return {\n ...prev,\n items: prev.items.map((item) =>\n item.id === integrationId ? { ...item, isEnabled: enabled } : item,\n ),\n }\n })\n }\n setTogglingIds((prev) => { const next = new Set(prev); next.delete(integrationId); return next })\n }, [t])\n\n const filteredItems = React.useMemo(() => {\n if (!data) return { bundles: [], standalone: [] }\n\n let items = data.items\n if (search) {\n const q = search.toLowerCase()\n items = items.filter((item) => item.title.toLowerCase().includes(q) || item.description?.toLowerCase().includes(q))\n }\n if (selectedCategory !== 'all') {\n items = items.filter((item) => item.category === selectedCategory)\n }\n\n const bundled = new Map<string, IntegrationItem[]>()\n const standalone: IntegrationItem[] = []\n for (const item of items) {\n if (item.bundleId) {\n const list = bundled.get(item.bundleId) ?? []\n list.push(item)\n bundled.set(item.bundleId, list)\n } else {\n standalone.push(item)\n }\n }\n\n const bundles = (data.bundles ?? [])\n .filter((b) => bundled.has(b.id))\n .map((b) => ({ ...b, integrations: bundled.get(b.id) ?? [] }))\n\n return { bundles, standalone }\n }, [data, search, selectedCategory])\n\n const renderCategoryIcon = React.useCallback((category: string | undefined, className: string) => {\n if (!category) return null\n const Icon = CATEGORY_ICONS[category]\n if (!Icon) return null\n return <Icon className={className} />\n }, [])\n\n if (isLoading) {\n return (\n <Page>\n <PageBody>\n <div className=\"flex items-center justify-center py-16\">\n <Spinner />\n </div>\n </PageBody>\n </Page>\n )\n }\n\n return (\n <Page>\n <PageBody className=\"space-y-6\">\n <section className=\"space-y-6 rounded-lg border bg-background p-6\">\n <header className=\"flex items-center justify-between gap-4\">\n <div className=\"space-y-0.5\">\n <h2 className=\"text-lg font-semibold\">{t('integrations.marketplace.title')}</h2>\n <p className=\"text-sm text-muted-foreground\">\n {t('integrations.marketplace.description')}\n </p>\n </div>\n <div className=\"relative w-64 shrink-0 hidden lg:block\">\n <Search className=\"absolute left-2.5 top-1/2 -translate-y-1/2 size-4 text-muted-foreground pointer-events-none\" />\n <Input\n placeholder={t('integrations.marketplace.search')}\n value={search}\n onChange={(e) => setSearch(e.target.value)}\n className=\"pl-8\"\n />\n </div>\n </header>\n\n <div className=\"lg:hidden\">\n <FilterBar\n searchValue={search}\n onSearchChange={setSearch}\n searchPlaceholder={t('integrations.marketplace.search')}\n searchAlign=\"left\"\n filters={categoryFilters}\n values={filterValues}\n onApply={(values) => setFilterValues(normalizeIntegrationMarketplaceFilterValues(values))}\n onClear={() => setFilterValues({})}\n />\n </div>\n\n <div className=\"hidden lg:flex flex-wrap gap-1.5\">\n {INTEGRATION_MARKETPLACE_CATEGORIES.map((category) => {\n const Icon = CATEGORY_ICONS[category]\n return (\n <Button\n key={category}\n type=\"button\"\n variant={selectedCategory === category ? 'default' : 'outline'}\n size=\"sm\"\n onClick={() => setFilterValues(normalizeIntegrationMarketplaceFilterValues({ category }))}\n >\n {Icon ? <Icon className=\"mr-1.5 h-3.5 w-3.5\" /> : null}\n {t(`integrations.marketplace.categories.${category}`)}\n </Button>\n )\n })}\n </div>\n\n {filteredItems.bundles.map((bundle) => (\n <Card key={bundle.id}>\n <CardHeader>\n <div className=\"flex items-center justify-between\">\n <div>\n <CardTitle>{bundle.title}</CardTitle>\n {bundle.description && (\n <p className=\"text-muted-foreground text-sm mt-1\">{bundle.description}</p>\n )}\n <p className=\"text-muted-foreground text-xs mt-1\">\n {t('integrations.marketplace.integrations', { count: bundle.integrations.length })}\n </p>\n </div>\n <Button asChild variant=\"outline\" size=\"sm\">\n <Link href={`/backend/integrations/bundle/${encodeURIComponent(bundle.id)}`}>\n <Cog className=\"mr-1.5 h-4 w-4\" />\n {t('integrations.marketplace.configure')}\n </Link>\n </Button>\n </div>\n </CardHeader>\n <CardContent>\n <div className=\"grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-3\">\n {bundle.integrations.map((item) => (\n <div\n key={item.id}\n className=\"flex items-center justify-between rounded-lg border p-3\"\n >\n <div className=\"min-w-0 space-y-1\">\n <div className=\"flex items-center gap-2\">\n {renderCategoryIcon(item.category, 'h-4 w-4 text-muted-foreground')}\n <Link\n href={`/backend/integrations/${encodeURIComponent(item.id)}`}\n className=\"truncate text-sm font-medium hover:underline\"\n >\n {item.title}\n </Link>\n </div>\n {(item.company || item.author || item.version) ? (\n <p className=\"text-xs text-muted-foreground\">\n {[item.company || item.author, item.version ? `v${item.version}` : null].filter(Boolean).join(' \u00B7 ')}\n </p>\n ) : null}\n </div>\n <Switch\n checked={item.isEnabled}\n disabled={togglingIds.has(item.id)}\n onCheckedChange={(checked) => void handleToggle(item.id, checked)}\n />\n </div>\n ))}\n </div>\n </CardContent>\n </Card>\n ))}\n\n {filteredItems.standalone.length > 0 && (\n <div className=\"grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-4\">\n {filteredItems.standalone.map((item) => (\n <Card key={item.id} className=\"flex flex-col\">\n <CardHeader>\n <div className=\"flex items-center justify-between\">\n <div className=\"flex items-center gap-2\">\n {renderCategoryIcon(item.category, 'h-4 w-4 text-muted-foreground')}\n <CardTitle className=\"text-base\">{item.title}</CardTitle>\n </div>\n <Switch\n checked={item.isEnabled}\n disabled={togglingIds.has(item.id)}\n onCheckedChange={(checked) => void handleToggle(item.id, checked)}\n />\n </div>\n </CardHeader>\n <CardContent className=\"flex-1 space-y-2\">\n {item.description && (\n <p className=\"text-muted-foreground text-sm\">{item.description}</p>\n )}\n {(item.company || item.author || item.version) && (\n <p className=\"text-muted-foreground text-xs\">\n {[item.company || item.author, item.version ? `v${item.version}` : null].filter(Boolean).join(' \u00B7 ')}\n </p>\n )}\n </CardContent>\n <div className=\"px-6 pb-4\">\n <Button asChild variant=\"outline\" size=\"sm\" className=\"w-full\">\n <Link href={`/backend/integrations/${encodeURIComponent(item.id)}`}>\n <Cog className=\"mr-1.5 h-4 w-4\" />\n {t('integrations.marketplace.configure')}\n </Link>\n </Button>\n </div>\n </Card>\n ))}\n </div>\n )}\n\n {filteredItems.bundles.length === 0 && filteredItems.standalone.length === 0 && (\n <div className=\"text-center py-12 text-muted-foreground\">\n {t('integrations.marketplace.noResults')}\n </div>\n )}\n </section>\n </PageBody>\n </Page>\n )\n}\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }
@@ -9,8 +9,8 @@ const metadata = {
9
9
  requireFeatures: ["integrations.view"],
10
10
  pageTitle: "Integrations",
11
11
  pageTitleKey: "integrations.nav.title",
12
- pageGroup: "Settings",
13
- pageGroupKey: "settings.sections.general",
12
+ pageGroup: "External systems",
13
+ pageGroupKey: "backend.nav.externalSystems",
14
14
  pageOrder: 50,
15
15
  icon: puzzleIcon,
16
16
  pageContext: "settings",
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../../src/modules/integrations/backend/integrations/page.meta.ts"],
4
- "sourcesContent": ["import React from 'react'\n\nconst puzzleIcon = React.createElement('svg', { width: 16, height: 16, viewBox: '0 0 24 24', fill: 'none', stroke: 'currentColor', strokeWidth: 2 },\n React.createElement('path', { d: 'M19.439 7.85c-.049.322.059.648.289.878l1.568 1.568c.47.47.706 1.087.706 1.704s-.235 1.233-.706 1.704l-1.611 1.611a.98.98 0 0 1-.837.276c-.47-.07-.802-.48-.968-.925a2.501 2.501 0 1 0-3.214 3.214c.446.166.855.497.925.968a.979.979 0 0 1-.276.837l-1.61 1.61a2.404 2.404 0 0 1-1.705.707 2.402 2.402 0 0 1-1.704-.706l-1.568-1.568a1.026 1.026 0 0 0-.877-.29c-.493.074-.84.504-1.02.968a2.5 2.5 0 1 1-3.237-3.237c.464-.18.894-.527.967-1.02a1.026 1.026 0 0 0-.289-.877l-1.568-1.568A2.402 2.402 0 0 1 1.998 12c0-.617.236-1.234.706-1.704L4.23 8.77c.24-.24.581-.353.917-.303.515.077.877.528 1.073 1.01a2.5 2.5 0 1 0 3.259-3.259c-.482-.196-.933-.558-1.01-1.073-.05-.336.062-.676.303-.917l1.525-1.525A2.402 2.402 0 0 1 12 2c.617 0 1.234.236 1.704.706l1.568 1.568c.23.23.556.338.877.29.493-.074.84-.504 1.02-.968a2.5 2.5 0 1 1 3.237 3.237c-.464.18-.894.527-.967 1.02Z' }),\n)\n\nexport const metadata = {\n requireAuth: true,\n requireFeatures: ['integrations.view'],\n pageTitle: 'Integrations',\n pageTitleKey: 'integrations.nav.title',\n pageGroup: 'Settings',\n pageGroupKey: 'settings.sections.general',\n pageOrder: 50,\n icon: puzzleIcon,\n pageContext: 'settings' as const,\n breadcrumb: [{ label: 'Integrations', labelKey: 'integrations.nav.title' }],\n}\n"],
4
+ "sourcesContent": ["import React from 'react'\n\nconst puzzleIcon = React.createElement('svg', { width: 16, height: 16, viewBox: '0 0 24 24', fill: 'none', stroke: 'currentColor', strokeWidth: 2 },\n React.createElement('path', { d: 'M19.439 7.85c-.049.322.059.648.289.878l1.568 1.568c.47.47.706 1.087.706 1.704s-.235 1.233-.706 1.704l-1.611 1.611a.98.98 0 0 1-.837.276c-.47-.07-.802-.48-.968-.925a2.501 2.501 0 1 0-3.214 3.214c.446.166.855.497.925.968a.979.979 0 0 1-.276.837l-1.61 1.61a2.404 2.404 0 0 1-1.705.707 2.402 2.402 0 0 1-1.704-.706l-1.568-1.568a1.026 1.026 0 0 0-.877-.29c-.493.074-.84.504-1.02.968a2.5 2.5 0 1 1-3.237-3.237c.464-.18.894-.527.967-1.02a1.026 1.026 0 0 0-.289-.877l-1.568-1.568A2.402 2.402 0 0 1 1.998 12c0-.617.236-1.234.706-1.704L4.23 8.77c.24-.24.581-.353.917-.303.515.077.877.528 1.073 1.01a2.5 2.5 0 1 0 3.259-3.259c-.482-.196-.933-.558-1.01-1.073-.05-.336.062-.676.303-.917l1.525-1.525A2.402 2.402 0 0 1 12 2c.617 0 1.234.236 1.704.706l1.568 1.568c.23.23.556.338.877.29.493-.074.84-.504 1.02-.968a2.5 2.5 0 1 1 3.237 3.237c-.464.18-.894.527-.967 1.02Z' }),\n)\n\nexport const metadata = {\n requireAuth: true,\n requireFeatures: ['integrations.view'],\n pageTitle: 'Integrations',\n pageTitleKey: 'integrations.nav.title',\n pageGroup: 'External systems',\n pageGroupKey: 'backend.nav.externalSystems',\n pageOrder: 50,\n icon: puzzleIcon,\n pageContext: 'settings' as const,\n breadcrumb: [{ label: 'Integrations', labelKey: 'integrations.nav.title' }],\n}\n"],
5
5
  "mappings": "AAAA,OAAO,WAAW;AAElB,MAAM,aAAa,MAAM;AAAA,EAAc;AAAA,EAAO,EAAE,OAAO,IAAI,QAAQ,IAAI,SAAS,aAAa,MAAM,QAAQ,QAAQ,gBAAgB,aAAa,EAAE;AAAA,EAChJ,MAAM,cAAc,QAAQ,EAAE,GAAG,s1BAAs1B,CAAC;AAC13B;AAEO,MAAM,WAAW;AAAA,EACtB,aAAa;AAAA,EACb,iBAAiB,CAAC,mBAAmB;AAAA,EACrC,WAAW;AAAA,EACX,cAAc;AAAA,EACd,WAAW;AAAA,EACX,cAAc;AAAA,EACd,WAAW;AAAA,EACX,MAAM;AAAA,EACN,aAAa;AAAA,EACb,YAAY,CAAC,EAAE,OAAO,gBAAgB,UAAU,yBAAyB,CAAC;AAC5E;",
6
6
  "names": []
7
7
  }
@@ -1,7 +1,7 @@
1
1
  const setup = {
2
2
  defaultRoleFeatures: {
3
- superadmin: ["integrations.view", "integrations.manage", "integrations.credentials.manage"],
4
- admin: ["integrations.view", "integrations.manage", "integrations.credentials.manage"],
3
+ superadmin: ["integrations.*", "integrations.view", "integrations.manage", "integrations.credentials.manage"],
4
+ admin: ["integrations.*", "integrations.view", "integrations.manage", "integrations.credentials.manage"],
5
5
  employee: ["integrations.view"]
6
6
  }
7
7
  };
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/modules/integrations/setup.ts"],
4
- "sourcesContent": ["import type { ModuleSetupConfig } from '@open-mercato/shared/modules/setup'\n\nexport const setup: ModuleSetupConfig = {\n defaultRoleFeatures: {\n superadmin: ['integrations.view', 'integrations.manage', 'integrations.credentials.manage'],\n admin: ['integrations.view', 'integrations.manage', 'integrations.credentials.manage'],\n employee: ['integrations.view'],\n },\n}\n\nexport default setup\n"],
5
- "mappings": "AAEO,MAAM,QAA2B;AAAA,EACtC,qBAAqB;AAAA,IACnB,YAAY,CAAC,qBAAqB,uBAAuB,iCAAiC;AAAA,IAC1F,OAAO,CAAC,qBAAqB,uBAAuB,iCAAiC;AAAA,IACrF,UAAU,CAAC,mBAAmB;AAAA,EAChC;AACF;AAEA,IAAO,gBAAQ;",
4
+ "sourcesContent": ["import type { ModuleSetupConfig } from '@open-mercato/shared/modules/setup'\n\nexport const setup: ModuleSetupConfig = {\n defaultRoleFeatures: {\n superadmin: ['integrations.*', 'integrations.view', 'integrations.manage', 'integrations.credentials.manage'],\n admin: ['integrations.*', 'integrations.view', 'integrations.manage', 'integrations.credentials.manage'],\n employee: ['integrations.view'],\n },\n}\n\nexport default setup\n"],
5
+ "mappings": "AAEO,MAAM,QAA2B;AAAA,EACtC,qBAAqB;AAAA,IACnB,YAAY,CAAC,kBAAkB,qBAAqB,uBAAuB,iCAAiC;AAAA,IAC5G,OAAO,CAAC,kBAAkB,qBAAqB,uBAAuB,iCAAiC;AAAA,IACvG,UAAU,CAAC,mBAAmB;AAAA,EAChC;AACF;AAEA,IAAO,gBAAQ;",
6
6
  "names": []
7
7
  }
@@ -0,0 +1,12 @@
1
+ const features = [
2
+ { id: "payment_gateways.view", title: "View payment gateway transactions", module: "payment_gateways" },
3
+ { id: "payment_gateways.manage", title: "Create and manage payment sessions", module: "payment_gateways" },
4
+ { id: "payment_gateways.capture", title: "Capture authorized payments", module: "payment_gateways" },
5
+ { id: "payment_gateways.refund", title: "Refund captured payments", module: "payment_gateways" }
6
+ ];
7
+ var acl_default = features;
8
+ export {
9
+ acl_default as default,
10
+ features
11
+ };
12
+ //# sourceMappingURL=acl.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/modules/payment_gateways/acl.ts"],
4
+ "sourcesContent": ["export const features = [\n { id: 'payment_gateways.view', title: 'View payment gateway transactions', module: 'payment_gateways' },\n { id: 'payment_gateways.manage', title: 'Create and manage payment sessions', module: 'payment_gateways' },\n { id: 'payment_gateways.capture', title: 'Capture authorized payments', module: 'payment_gateways' },\n { id: 'payment_gateways.refund', title: 'Refund captured payments', module: 'payment_gateways' },\n]\n\nexport default features\n"],
5
+ "mappings": "AAAO,MAAM,WAAW;AAAA,EACtB,EAAE,IAAI,yBAAyB,OAAO,qCAAqC,QAAQ,mBAAmB;AAAA,EACtG,EAAE,IAAI,2BAA2B,OAAO,sCAAsC,QAAQ,mBAAmB;AAAA,EACzG,EAAE,IAAI,4BAA4B,OAAO,+BAA+B,QAAQ,mBAAmB;AAAA,EACnG,EAAE,IAAI,2BAA2B,OAAO,4BAA4B,QAAQ,mBAAmB;AACjG;AAEA,IAAO,cAAQ;",
6
+ "names": []
7
+ }
@@ -0,0 +1,55 @@
1
+ import { NextResponse } from "next/server";
2
+ import { getAuthFromRequest } from "@open-mercato/shared/lib/auth/server";
3
+ import { createRequestContainer } from "@open-mercato/shared/lib/di/container";
4
+ import { readJsonSafe } from "@open-mercato/shared/lib/http/readJsonSafe";
5
+ import { cancelSchema } from "../../data/validators.js";
6
+ import { paymentGatewaysTag } from "../openapi.js";
7
+ const metadata = {
8
+ path: "/payment_gateways/cancel",
9
+ POST: { requireAuth: true, requireFeatures: ["payment_gateways.manage"] }
10
+ };
11
+ async function POST(req) {
12
+ const auth = await getAuthFromRequest(req);
13
+ if (!auth?.tenantId || !auth.orgId) {
14
+ return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
15
+ }
16
+ const payload = await readJsonSafe(req);
17
+ const parsed = cancelSchema.safeParse(payload);
18
+ if (!parsed.success) {
19
+ return NextResponse.json({ error: "Invalid payload", details: parsed.error.flatten() }, { status: 422 });
20
+ }
21
+ const container = await createRequestContainer();
22
+ const service = container.resolve("paymentGatewayService");
23
+ try {
24
+ const result = await service.cancelPayment(
25
+ parsed.data.transactionId,
26
+ parsed.data.reason,
27
+ { organizationId: auth.orgId, tenantId: auth.tenantId }
28
+ );
29
+ return NextResponse.json(result);
30
+ } catch (err) {
31
+ const message = err instanceof Error ? err.message : "Cancel failed";
32
+ return NextResponse.json({ error: message }, { status: 502 });
33
+ }
34
+ }
35
+ const openApi = {
36
+ tags: [paymentGatewaysTag],
37
+ summary: "Cancel/void an authorized payment",
38
+ methods: {
39
+ POST: {
40
+ summary: "Cancel payment",
41
+ tags: [paymentGatewaysTag],
42
+ responses: [
43
+ { status: 200, description: "Payment cancelled" },
44
+ { status: 422, description: "Invalid payload" },
45
+ { status: 502, description: "Gateway provider error" }
46
+ ]
47
+ }
48
+ }
49
+ };
50
+ export {
51
+ POST,
52
+ metadata,
53
+ openApi
54
+ };
55
+ //# sourceMappingURL=route.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../../src/modules/payment_gateways/api/cancel/route.ts"],
4
+ "sourcesContent": ["import { NextResponse } from 'next/server'\nimport { getAuthFromRequest } from '@open-mercato/shared/lib/auth/server'\nimport { createRequestContainer } from '@open-mercato/shared/lib/di/container'\nimport { readJsonSafe } from '@open-mercato/shared/lib/http/readJsonSafe'\nimport { cancelSchema } from '../../data/validators'\nimport type { PaymentGatewayService } from '../../lib/gateway-service'\nimport { paymentGatewaysTag } from '../openapi'\n\nexport const metadata = {\n path: '/payment_gateways/cancel',\n POST: { requireAuth: true, requireFeatures: ['payment_gateways.manage'] },\n}\n\nexport async function POST(req: Request) {\n const auth = await getAuthFromRequest(req)\n if (!auth?.tenantId || !auth.orgId) {\n return NextResponse.json({ error: 'Unauthorized' }, { status: 401 })\n }\n\n const payload = await readJsonSafe<unknown>(req)\n const parsed = cancelSchema.safeParse(payload)\n if (!parsed.success) {\n return NextResponse.json({ error: 'Invalid payload', details: parsed.error.flatten() }, { status: 422 })\n }\n\n const container = await createRequestContainer()\n const service = container.resolve('paymentGatewayService') as PaymentGatewayService\n\n try {\n const result = await service.cancelPayment(\n parsed.data.transactionId,\n parsed.data.reason,\n { organizationId: auth.orgId as string, tenantId: auth.tenantId },\n )\n return NextResponse.json(result)\n } catch (err: unknown) {\n const message = err instanceof Error ? err.message : 'Cancel failed'\n return NextResponse.json({ error: message }, { status: 502 })\n }\n}\n\nexport const openApi = {\n tags: [paymentGatewaysTag],\n summary: 'Cancel/void an authorized payment',\n methods: {\n POST: {\n summary: 'Cancel payment',\n tags: [paymentGatewaysTag],\n responses: [\n { status: 200, description: 'Payment cancelled' },\n { status: 422, description: 'Invalid payload' },\n { status: 502, description: 'Gateway provider error' },\n ],\n },\n },\n}\n"],
5
+ "mappings": "AAAA,SAAS,oBAAoB;AAC7B,SAAS,0BAA0B;AACnC,SAAS,8BAA8B;AACvC,SAAS,oBAAoB;AAC7B,SAAS,oBAAoB;AAE7B,SAAS,0BAA0B;AAE5B,MAAM,WAAW;AAAA,EACtB,MAAM;AAAA,EACN,MAAM,EAAE,aAAa,MAAM,iBAAiB,CAAC,yBAAyB,EAAE;AAC1E;AAEA,eAAsB,KAAK,KAAc;AACvC,QAAM,OAAO,MAAM,mBAAmB,GAAG;AACzC,MAAI,CAAC,MAAM,YAAY,CAAC,KAAK,OAAO;AAClC,WAAO,aAAa,KAAK,EAAE,OAAO,eAAe,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrE;AAEA,QAAM,UAAU,MAAM,aAAsB,GAAG;AAC/C,QAAM,SAAS,aAAa,UAAU,OAAO;AAC7C,MAAI,CAAC,OAAO,SAAS;AACnB,WAAO,aAAa,KAAK,EAAE,OAAO,mBAAmB,SAAS,OAAO,MAAM,QAAQ,EAAE,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACzG;AAEA,QAAM,YAAY,MAAM,uBAAuB;AAC/C,QAAM,UAAU,UAAU,QAAQ,uBAAuB;AAEzD,MAAI;AACF,UAAM,SAAS,MAAM,QAAQ;AAAA,MAC3B,OAAO,KAAK;AAAA,MACZ,OAAO,KAAK;AAAA,MACZ,EAAE,gBAAgB,KAAK,OAAiB,UAAU,KAAK,SAAS;AAAA,IAClE;AACA,WAAO,aAAa,KAAK,MAAM;AAAA,EACjC,SAAS,KAAc;AACrB,UAAM,UAAU,eAAe,QAAQ,IAAI,UAAU;AACrD,WAAO,aAAa,KAAK,EAAE,OAAO,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAC9D;AACF;AAEO,MAAM,UAAU;AAAA,EACrB,MAAM,CAAC,kBAAkB;AAAA,EACzB,SAAS;AAAA,EACT,SAAS;AAAA,IACP,MAAM;AAAA,MACJ,SAAS;AAAA,MACT,MAAM,CAAC,kBAAkB;AAAA,MACzB,WAAW;AAAA,QACT,EAAE,QAAQ,KAAK,aAAa,oBAAoB;AAAA,QAChD,EAAE,QAAQ,KAAK,aAAa,kBAAkB;AAAA,QAC9C,EAAE,QAAQ,KAAK,aAAa,yBAAyB;AAAA,MACvD;AAAA,IACF;AAAA,EACF;AACF;",
6
+ "names": []
7
+ }
@@ -0,0 +1,55 @@
1
+ import { NextResponse } from "next/server";
2
+ import { getAuthFromRequest } from "@open-mercato/shared/lib/auth/server";
3
+ import { createRequestContainer } from "@open-mercato/shared/lib/di/container";
4
+ import { readJsonSafe } from "@open-mercato/shared/lib/http/readJsonSafe";
5
+ import { captureSchema } from "../../data/validators.js";
6
+ import { paymentGatewaysTag } from "../openapi.js";
7
+ const metadata = {
8
+ path: "/payment_gateways/capture",
9
+ POST: { requireAuth: true, requireFeatures: ["payment_gateways.capture"] }
10
+ };
11
+ async function POST(req) {
12
+ const auth = await getAuthFromRequest(req);
13
+ if (!auth?.tenantId || !auth.orgId) {
14
+ return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
15
+ }
16
+ const payload = await readJsonSafe(req);
17
+ const parsed = captureSchema.safeParse(payload);
18
+ if (!parsed.success) {
19
+ return NextResponse.json({ error: "Invalid payload", details: parsed.error.flatten() }, { status: 422 });
20
+ }
21
+ const container = await createRequestContainer();
22
+ const service = container.resolve("paymentGatewayService");
23
+ try {
24
+ const result = await service.capturePayment(
25
+ parsed.data.transactionId,
26
+ parsed.data.amount,
27
+ { organizationId: auth.orgId, tenantId: auth.tenantId }
28
+ );
29
+ return NextResponse.json(result);
30
+ } catch (err) {
31
+ const message = err instanceof Error ? err.message : "Capture failed";
32
+ return NextResponse.json({ error: message }, { status: 502 });
33
+ }
34
+ }
35
+ const openApi = {
36
+ tags: [paymentGatewaysTag],
37
+ summary: "Capture an authorized payment",
38
+ methods: {
39
+ POST: {
40
+ summary: "Capture payment",
41
+ tags: [paymentGatewaysTag],
42
+ responses: [
43
+ { status: 200, description: "Payment captured" },
44
+ { status: 422, description: "Invalid payload" },
45
+ { status: 502, description: "Gateway provider error" }
46
+ ]
47
+ }
48
+ }
49
+ };
50
+ export {
51
+ POST,
52
+ metadata,
53
+ openApi
54
+ };
55
+ //# sourceMappingURL=route.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../../src/modules/payment_gateways/api/capture/route.ts"],
4
+ "sourcesContent": ["import { NextResponse } from 'next/server'\nimport { getAuthFromRequest } from '@open-mercato/shared/lib/auth/server'\nimport { createRequestContainer } from '@open-mercato/shared/lib/di/container'\nimport { readJsonSafe } from '@open-mercato/shared/lib/http/readJsonSafe'\nimport { captureSchema } from '../../data/validators'\nimport type { PaymentGatewayService } from '../../lib/gateway-service'\nimport { paymentGatewaysTag } from '../openapi'\n\nexport const metadata = {\n path: '/payment_gateways/capture',\n POST: { requireAuth: true, requireFeatures: ['payment_gateways.capture'] },\n}\n\nexport async function POST(req: Request) {\n const auth = await getAuthFromRequest(req)\n if (!auth?.tenantId || !auth.orgId) {\n return NextResponse.json({ error: 'Unauthorized' }, { status: 401 })\n }\n\n const payload = await readJsonSafe<unknown>(req)\n const parsed = captureSchema.safeParse(payload)\n if (!parsed.success) {\n return NextResponse.json({ error: 'Invalid payload', details: parsed.error.flatten() }, { status: 422 })\n }\n\n const container = await createRequestContainer()\n const service = container.resolve('paymentGatewayService') as PaymentGatewayService\n\n try {\n const result = await service.capturePayment(\n parsed.data.transactionId,\n parsed.data.amount,\n { organizationId: auth.orgId as string, tenantId: auth.tenantId },\n )\n return NextResponse.json(result)\n } catch (err: unknown) {\n const message = err instanceof Error ? err.message : 'Capture failed'\n return NextResponse.json({ error: message }, { status: 502 })\n }\n}\n\nexport const openApi = {\n tags: [paymentGatewaysTag],\n summary: 'Capture an authorized payment',\n methods: {\n POST: {\n summary: 'Capture payment',\n tags: [paymentGatewaysTag],\n responses: [\n { status: 200, description: 'Payment captured' },\n { status: 422, description: 'Invalid payload' },\n { status: 502, description: 'Gateway provider error' },\n ],\n },\n },\n}\n"],
5
+ "mappings": "AAAA,SAAS,oBAAoB;AAC7B,SAAS,0BAA0B;AACnC,SAAS,8BAA8B;AACvC,SAAS,oBAAoB;AAC7B,SAAS,qBAAqB;AAE9B,SAAS,0BAA0B;AAE5B,MAAM,WAAW;AAAA,EACtB,MAAM;AAAA,EACN,MAAM,EAAE,aAAa,MAAM,iBAAiB,CAAC,0BAA0B,EAAE;AAC3E;AAEA,eAAsB,KAAK,KAAc;AACvC,QAAM,OAAO,MAAM,mBAAmB,GAAG;AACzC,MAAI,CAAC,MAAM,YAAY,CAAC,KAAK,OAAO;AAClC,WAAO,aAAa,KAAK,EAAE,OAAO,eAAe,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACrE;AAEA,QAAM,UAAU,MAAM,aAAsB,GAAG;AAC/C,QAAM,SAAS,cAAc,UAAU,OAAO;AAC9C,MAAI,CAAC,OAAO,SAAS;AACnB,WAAO,aAAa,KAAK,EAAE,OAAO,mBAAmB,SAAS,OAAO,MAAM,QAAQ,EAAE,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EACzG;AAEA,QAAM,YAAY,MAAM,uBAAuB;AAC/C,QAAM,UAAU,UAAU,QAAQ,uBAAuB;AAEzD,MAAI;AACF,UAAM,SAAS,MAAM,QAAQ;AAAA,MAC3B,OAAO,KAAK;AAAA,MACZ,OAAO,KAAK;AAAA,MACZ,EAAE,gBAAgB,KAAK,OAAiB,UAAU,KAAK,SAAS;AAAA,IAClE;AACA,WAAO,aAAa,KAAK,MAAM;AAAA,EACjC,SAAS,KAAc;AACrB,UAAM,UAAU,eAAe,QAAQ,IAAI,UAAU;AACrD,WAAO,aAAa,KAAK,EAAE,OAAO,QAAQ,GAAG,EAAE,QAAQ,IAAI,CAAC;AAAA,EAC9D;AACF;AAEO,MAAM,UAAU;AAAA,EACrB,MAAM,CAAC,kBAAkB;AAAA,EACzB,SAAS;AAAA,EACT,SAAS;AAAA,IACP,MAAM;AAAA,MACJ,SAAS;AAAA,MACT,MAAM,CAAC,kBAAkB;AAAA,MACzB,WAAW;AAAA,QACT,EAAE,QAAQ,KAAK,aAAa,mBAAmB;AAAA,QAC/C,EAAE,QAAQ,KAAK,aAAa,kBAAkB;AAAA,QAC9C,EAAE,QAAQ,KAAK,aAAa,yBAAyB;AAAA,MACvD;AAAA,IACF;AAAA,EACF;AACF;",
6
+ "names": []
7
+ }
@@ -0,0 +1,24 @@
1
+ import { getGatewayAdapter } from "@open-mercato/shared/modules/payment_gateways/types";
2
+ const interceptors = [
3
+ {
4
+ id: "payment_gateways.validate-provider",
5
+ targetRoute: "sessions",
6
+ methods: ["POST"],
7
+ priority: 100,
8
+ async before(request) {
9
+ const providerKey = request.body?.providerKey;
10
+ if (typeof providerKey !== "string" || providerKey.trim().length === 0) {
11
+ return { ok: false, statusCode: 422, message: "providerKey is required" };
12
+ }
13
+ const adapter = getGatewayAdapter(providerKey.trim());
14
+ if (!adapter) {
15
+ return { ok: false, statusCode: 422, message: `Unknown payment provider: ${providerKey}` };
16
+ }
17
+ return { ok: true };
18
+ }
19
+ }
20
+ ];
21
+ export {
22
+ interceptors
23
+ };
24
+ //# sourceMappingURL=interceptors.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../src/modules/payment_gateways/api/interceptors.ts"],
4
+ "sourcesContent": ["import type { ApiInterceptor } from '@open-mercato/shared/lib/crud/api-interceptor'\nimport { getGatewayAdapter } from '@open-mercato/shared/modules/payment_gateways/types'\n\nexport const interceptors: ApiInterceptor[] = [\n {\n id: 'payment_gateways.validate-provider',\n targetRoute: 'sessions',\n methods: ['POST'],\n priority: 100,\n async before(request) {\n const providerKey = request.body?.providerKey\n if (typeof providerKey !== 'string' || providerKey.trim().length === 0) {\n return { ok: false, statusCode: 422, message: 'providerKey is required' }\n }\n const adapter = getGatewayAdapter(providerKey.trim())\n if (!adapter) {\n return { ok: false, statusCode: 422, message: `Unknown payment provider: ${providerKey}` }\n }\n return { ok: true }\n },\n },\n]\n"],
5
+ "mappings": "AACA,SAAS,yBAAyB;AAE3B,MAAM,eAAiC;AAAA,EAC5C;AAAA,IACE,IAAI;AAAA,IACJ,aAAa;AAAA,IACb,SAAS,CAAC,MAAM;AAAA,IAChB,UAAU;AAAA,IACV,MAAM,OAAO,SAAS;AACpB,YAAM,cAAc,QAAQ,MAAM;AAClC,UAAI,OAAO,gBAAgB,YAAY,YAAY,KAAK,EAAE,WAAW,GAAG;AACtE,eAAO,EAAE,IAAI,OAAO,YAAY,KAAK,SAAS,0BAA0B;AAAA,MAC1E;AACA,YAAM,UAAU,kBAAkB,YAAY,KAAK,CAAC;AACpD,UAAI,CAAC,SAAS;AACZ,eAAO,EAAE,IAAI,OAAO,YAAY,KAAK,SAAS,6BAA6B,WAAW,GAAG;AAAA,MAC3F;AACA,aAAO,EAAE,IAAI,KAAK;AAAA,IACpB;AAAA,EACF;AACF;",
6
+ "names": []
7
+ }
@@ -0,0 +1,5 @@
1
+ const paymentGatewaysTag = "PaymentGateways";
2
+ export {
3
+ paymentGatewaysTag
4
+ };
5
+ //# sourceMappingURL=openapi.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../src/modules/payment_gateways/api/openapi.ts"],
4
+ "sourcesContent": ["export const paymentGatewaysTag = 'PaymentGateways'\n"],
5
+ "mappings": "AAAO,MAAM,qBAAqB;",
6
+ "names": []
7
+ }