@endora-commerce/mod-price-lists 0.100.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (171) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +59 -0
  3. package/dist/admin/components/ApplicationRuleBuilder.d.ts +24 -0
  4. package/dist/admin/components/ApplicationRuleBuilder.d.ts.map +1 -0
  5. package/dist/admin/components/ApplicationRuleBuilder.js +249 -0
  6. package/dist/admin/components/ApplicationRuleBuilder.js.map +1 -0
  7. package/dist/admin/components/BracketGrid.d.ts +29 -0
  8. package/dist/admin/components/BracketGrid.d.ts.map +1 -0
  9. package/dist/admin/components/BracketGrid.js +252 -0
  10. package/dist/admin/components/BracketGrid.js.map +1 -0
  11. package/dist/admin/components/DisplayModeOverrideRow.d.ts +46 -0
  12. package/dist/admin/components/DisplayModeOverrideRow.d.ts.map +1 -0
  13. package/dist/admin/components/DisplayModeOverrideRow.js +109 -0
  14. package/dist/admin/components/DisplayModeOverrideRow.js.map +1 -0
  15. package/dist/admin/components/LinkedPriceListsPanel.d.ts +55 -0
  16. package/dist/admin/components/LinkedPriceListsPanel.d.ts.map +1 -0
  17. package/dist/admin/components/LinkedPriceListsPanel.js +131 -0
  18. package/dist/admin/components/LinkedPriceListsPanel.js.map +1 -0
  19. package/dist/admin/index.d.ts +34 -0
  20. package/dist/admin/index.d.ts.map +1 -0
  21. package/dist/admin/index.js +119 -0
  22. package/dist/admin/index.js.map +1 -0
  23. package/dist/admin/pages/DisplayModeOverridesPage.d.ts +25 -0
  24. package/dist/admin/pages/DisplayModeOverridesPage.d.ts.map +1 -0
  25. package/dist/admin/pages/DisplayModeOverridesPage.js +266 -0
  26. package/dist/admin/pages/DisplayModeOverridesPage.js.map +1 -0
  27. package/dist/admin/pages/PriceListDetailPage.d.ts +23 -0
  28. package/dist/admin/pages/PriceListDetailPage.d.ts.map +1 -0
  29. package/dist/admin/pages/PriceListDetailPage.js +421 -0
  30. package/dist/admin/pages/PriceListDetailPage.js.map +1 -0
  31. package/dist/admin/pages/PriceListsPage.d.ts +17 -0
  32. package/dist/admin/pages/PriceListsPage.d.ts.map +1 -0
  33. package/dist/admin/pages/PriceListsPage.js +198 -0
  34. package/dist/admin/pages/PriceListsPage.js.map +1 -0
  35. package/dist/admin/zones/CategoryDisplayMode.d.ts +27 -0
  36. package/dist/admin/zones/CategoryDisplayMode.d.ts.map +1 -0
  37. package/dist/admin/zones/CategoryDisplayMode.js +11 -0
  38. package/dist/admin/zones/CategoryDisplayMode.js.map +1 -0
  39. package/dist/admin/zones/OrganizationDisplayMode.d.ts +36 -0
  40. package/dist/admin/zones/OrganizationDisplayMode.d.ts.map +1 -0
  41. package/dist/admin/zones/OrganizationDisplayMode.js +12 -0
  42. package/dist/admin/zones/OrganizationDisplayMode.js.map +1 -0
  43. package/dist/admin/zones/ProductLinkedPriceLists.d.ts +16 -0
  44. package/dist/admin/zones/ProductLinkedPriceLists.d.ts.map +1 -0
  45. package/dist/admin/zones/ProductLinkedPriceLists.js +7 -0
  46. package/dist/admin/zones/ProductLinkedPriceLists.js.map +1 -0
  47. package/dist/backend/entities/price-display-mode-override.entity.d.ts +23 -0
  48. package/dist/backend/entities/price-display-mode-override.entity.d.ts.map +1 -0
  49. package/dist/backend/entities/price-display-mode-override.entity.js +58 -0
  50. package/dist/backend/entities/price-display-mode-override.entity.js.map +1 -0
  51. package/dist/backend/entities/price-list-price-bracket.entity.d.ts +26 -0
  52. package/dist/backend/entities/price-list-price-bracket.entity.d.ts.map +1 -0
  53. package/dist/backend/entities/price-list-price-bracket.entity.js +73 -0
  54. package/dist/backend/entities/price-list-price-bracket.entity.js.map +1 -0
  55. package/dist/backend/entities/price-list-product.entity.d.ts +15 -0
  56. package/dist/backend/entities/price-list-product.entity.d.ts.map +1 -0
  57. package/dist/backend/entities/price-list-product.entity.js +43 -0
  58. package/dist/backend/entities/price-list-product.entity.js.map +1 -0
  59. package/dist/backend/entities/price-list.entity.d.ts +34 -0
  60. package/dist/backend/entities/price-list.entity.d.ts.map +1 -0
  61. package/dist/backend/entities/price-list.entity.js +115 -0
  62. package/dist/backend/entities/price-list.entity.js.map +1 -0
  63. package/dist/backend/index.d.ts +125 -0
  64. package/dist/backend/index.d.ts.map +1 -0
  65. package/dist/backend/index.js +179 -0
  66. package/dist/backend/index.js.map +1 -0
  67. package/dist/backend/plugin.d.ts +68 -0
  68. package/dist/backend/plugin.d.ts.map +1 -0
  69. package/dist/backend/plugin.js +88 -0
  70. package/dist/backend/plugin.js.map +1 -0
  71. package/dist/backend/routes.d.ts +40 -0
  72. package/dist/backend/routes.d.ts.map +1 -0
  73. package/dist/backend/routes.js +447 -0
  74. package/dist/backend/routes.js.map +1 -0
  75. package/dist/backend/routes.storefront.d.ts +47 -0
  76. package/dist/backend/routes.storefront.d.ts.map +1 -0
  77. package/dist/backend/routes.storefront.js +131 -0
  78. package/dist/backend/routes.storefront.js.map +1 -0
  79. package/dist/backend/services/application-rule-evaluator.d.ts +25 -0
  80. package/dist/backend/services/application-rule-evaluator.d.ts.map +1 -0
  81. package/dist/backend/services/application-rule-evaluator.js +2 -0
  82. package/dist/backend/services/application-rule-evaluator.js.map +1 -0
  83. package/dist/backend/services/audit-references.d.ts +11 -0
  84. package/dist/backend/services/audit-references.d.ts.map +1 -0
  85. package/dist/backend/services/audit-references.js +23 -0
  86. package/dist/backend/services/audit-references.js.map +1 -0
  87. package/dist/backend/services/default-price-list-migration.d.ts +70 -0
  88. package/dist/backend/services/default-price-list-migration.d.ts.map +1 -0
  89. package/dist/backend/services/default-price-list-migration.js +177 -0
  90. package/dist/backend/services/default-price-list-migration.js.map +1 -0
  91. package/dist/backend/services/display-mode-resolver.d.ts +78 -0
  92. package/dist/backend/services/display-mode-resolver.d.ts.map +1 -0
  93. package/dist/backend/services/display-mode-resolver.js +71 -0
  94. package/dist/backend/services/display-mode-resolver.js.map +1 -0
  95. package/dist/backend/services/listing-price-chain.d.ts +26 -0
  96. package/dist/backend/services/listing-price-chain.d.ts.map +1 -0
  97. package/dist/backend/services/listing-price-chain.js +55 -0
  98. package/dist/backend/services/listing-price-chain.js.map +1 -0
  99. package/dist/backend/services/price-bracket-resolver.d.ts +24 -0
  100. package/dist/backend/services/price-bracket-resolver.d.ts.map +1 -0
  101. package/dist/backend/services/price-bracket-resolver.js +16 -0
  102. package/dist/backend/services/price-bracket-resolver.js.map +1 -0
  103. package/dist/backend/services/price-list-candidate-vector.d.ts +116 -0
  104. package/dist/backend/services/price-list-candidate-vector.d.ts.map +1 -0
  105. package/dist/backend/services/price-list-candidate-vector.js +133 -0
  106. package/dist/backend/services/price-list-candidate-vector.js.map +1 -0
  107. package/dist/backend/services/price-list-currency-reference.d.ts +12 -0
  108. package/dist/backend/services/price-list-currency-reference.d.ts.map +1 -0
  109. package/dist/backend/services/price-list-currency-reference.js +24 -0
  110. package/dist/backend/services/price-list-currency-reference.js.map +1 -0
  111. package/dist/backend/services/price-list-read-port.d.ts +29 -0
  112. package/dist/backend/services/price-list-read-port.d.ts.map +1 -0
  113. package/dist/backend/services/price-list-read-port.js +64 -0
  114. package/dist/backend/services/price-list-read-port.js.map +1 -0
  115. package/dist/backend/services/price-list-resolver.d.ts +26 -0
  116. package/dist/backend/services/price-list-resolver.d.ts.map +1 -0
  117. package/dist/backend/services/price-list-resolver.js +37 -0
  118. package/dist/backend/services/price-list-resolver.js.map +1 -0
  119. package/dist/backend/services/price-list-service.d.ts +431 -0
  120. package/dist/backend/services/price-list-service.d.ts.map +1 -0
  121. package/dist/backend/services/price-list-service.js +1238 -0
  122. package/dist/backend/services/price-list-service.js.map +1 -0
  123. package/dist/backend/services/price-list-status-worker.d.ts +28 -0
  124. package/dist/backend/services/price-list-status-worker.d.ts.map +1 -0
  125. package/dist/backend/services/price-list-status-worker.js +38 -0
  126. package/dist/backend/services/price-list-status-worker.js.map +1 -0
  127. package/dist/backend/services/pricing-cache.d.ts +53 -0
  128. package/dist/backend/services/pricing-cache.d.ts.map +1 -0
  129. package/dist/backend/services/pricing-cache.js +88 -0
  130. package/dist/backend/services/pricing-cache.js.map +1 -0
  131. package/dist/backend/services/pricing-service.d.ts +304 -0
  132. package/dist/backend/services/pricing-service.d.ts.map +1 -0
  133. package/dist/backend/services/pricing-service.interface.d.ts +151 -0
  134. package/dist/backend/services/pricing-service.interface.d.ts.map +1 -0
  135. package/dist/backend/services/pricing-service.interface.js +10 -0
  136. package/dist/backend/services/pricing-service.interface.js.map +1 -0
  137. package/dist/backend/services/pricing-service.js +803 -0
  138. package/dist/backend/services/pricing-service.js.map +1 -0
  139. package/dist/backend/services/unit-price-ordering.d.ts +121 -0
  140. package/dist/backend/services/unit-price-ordering.d.ts.map +1 -0
  141. package/dist/backend/services/unit-price-ordering.js +164 -0
  142. package/dist/backend/services/unit-price-ordering.js.map +1 -0
  143. package/dist/manifest.d.ts +218 -0
  144. package/dist/manifest.d.ts.map +1 -0
  145. package/dist/manifest.js +228 -0
  146. package/dist/manifest.js.map +1 -0
  147. package/dist/migrations/20260426T075235_price_lists_pricing_init.d.ts +24 -0
  148. package/dist/migrations/20260426T075235_price_lists_pricing_init.d.ts.map +1 -0
  149. package/dist/migrations/20260426T075235_price_lists_pricing_init.js +89 -0
  150. package/dist/migrations/20260426T075235_price_lists_pricing_init.js.map +1 -0
  151. package/dist/migrations/20260504T125655_price_lists_engine.d.ts +6 -0
  152. package/dist/migrations/20260504T125655_price_lists_engine.d.ts.map +1 -0
  153. package/dist/migrations/20260504T125655_price_lists_engine.js +319 -0
  154. package/dist/migrations/20260504T125655_price_lists_engine.js.map +1 -0
  155. package/dist/migrations/20260817T055457_price_lists_single_system_price_list.d.ts +15 -0
  156. package/dist/migrations/20260817T055457_price_lists_single_system_price_list.d.ts.map +1 -0
  157. package/dist/migrations/20260817T055457_price_lists_single_system_price_list.js +58 -0
  158. package/dist/migrations/20260817T055457_price_lists_single_system_price_list.js.map +1 -0
  159. package/dist/migrations/20260821T135907_price_lists_unit_price_amount_index.d.ts +40 -0
  160. package/dist/migrations/20260821T135907_price_lists_unit_price_amount_index.d.ts.map +1 -0
  161. package/dist/migrations/20260821T135907_price_lists_unit_price_amount_index.js +46 -0
  162. package/dist/migrations/20260821T135907_price_lists_unit_price_amount_index.js.map +1 -0
  163. package/dist/migrations/index.d.ts +30 -0
  164. package/dist/migrations/index.d.ts.map +1 -0
  165. package/dist/migrations/index.js +35 -0
  166. package/dist/migrations/index.js.map +1 -0
  167. package/docs/price_lists.md +278 -0
  168. package/i18n/en.json +14 -0
  169. package/i18n/pl.json +14 -0
  170. package/package.json +99 -0
  171. package/tailwind.css +14 -0
@@ -0,0 +1,88 @@
1
+ import { PriceListService } from './services/price-list-service.js';
2
+ import { PricingService } from './services/pricing-service.js';
3
+ import { PriceListStatusWorker } from './services/price-list-status-worker.js';
4
+ import { PricingCache } from './services/pricing-cache.js';
5
+ import { registerPricingRoutes } from './routes.js';
6
+ import { registerStorefrontPricingRoutes } from './routes.storefront.js';
7
+ import { effectiveState } from '@endora-commerce/platform/kernel';
8
+ import { enterSystemScope } from '@endora-commerce/platform/kernel';
9
+ const STATUS_SWEEP_INTERVAL_MS = 5 * 60 * 1000;
10
+ export function priceListsModule(options) {
11
+ const pricingCache = new PricingCache(options.pricingCacheTtlMs !== undefined ? { ttlMs: options.pricingCacheTtlMs } : {});
12
+ const priceListService = new PriceListService(options.emFactory, pricingCache, options.auditLogService, options.commandBus, options.targetReads);
13
+ // This module builds the engine; a deployment that overrides it wraps the
14
+ // `pricingService` **registration** from an overlay module's
15
+ // `ctx.di.decorate` (D-103), so nothing about the override reaches this
16
+ // factory. It used to: `decoratePricingService` was a contribution point a
17
+ // composition root filled from a file under `apps/<deployment>/decorations/`,
18
+ // and that seam is retired — one mechanism, and it is the one that needs no
19
+ // edit here when a second deployment overrides a second service.
20
+ //
21
+ // Consumers read `handle.pricingService` as the *contract* rather than as the
22
+ // class, and that still matters: what the container hands out is a wrapper
23
+ // whenever a deployment decorates the registration.
24
+ const pricingService = new PricingService(options.emFactory, pricingCache, options.resolveOrgChain, options.targetReads);
25
+ const statusWorker = new PriceListStatusWorker(options.emFactory);
26
+ return {
27
+ handle: { priceListService, pricingService, statusWorker },
28
+ plugin: async (app) => {
29
+ await registerPricingRoutes(app, {
30
+ priceListService,
31
+ pricingService,
32
+ emFactory: options.emFactory,
33
+ requireAdmin: options.requireAdmin,
34
+ catalogProductRead: options.targetReads.catalogProductRead,
35
+ catalogCategoryRead: options.targetReads.catalogCategoryRead,
36
+ organizationDetails: options.targetReads.organizationDetails,
37
+ customerGroupRead: options.targetReads.customerGroupRead,
38
+ customerAccountRead: options.customerAccountRead,
39
+ ...(options.resolveAdminAuditContext
40
+ ? { resolveAdminAuditContext: options.resolveAdminAuditContext }
41
+ : {}),
42
+ });
43
+ await registerStorefrontPricingRoutes(app, {
44
+ priceListService,
45
+ pricingService,
46
+ emFactory: options.emFactory,
47
+ catalogProductRead: options.targetReads.catalogProductRead,
48
+ organizationDetails: options.targetReads.organizationDetails,
49
+ });
50
+ if (options.enableStatusSweeper !== false) {
51
+ const handle = setInterval(() => {
52
+ // Presence is asked first, and outside the promise chain's `catch`
53
+ // (issue #126). The route seam gates *requests*; this body is not one,
54
+ // so it runs at boot whatever the effective state, and a timer
55
+ // callback has nowhere to throw to — `ModuleDisabledError` cannot
56
+ // propagate from here and must be *decided*, not caught. Asking it
57
+ // below, inside the `catch`, would make a switched-off module and a
58
+ // genuinely failed sweep the same silent no-op — and a sweep that runs
59
+ // while price lists are off changes what customers are charged.
60
+ if (!effectiveState.isPresent('price_lists'))
61
+ return;
62
+ // Feature 072 (T034) — the timer is the entry point, so the scope
63
+ // opens here and not inside `sweep()`: the same method is reachable
64
+ // from an admin route (`routes.ts`), where it already runs inside the
65
+ // request's scope and must not open a second one.
66
+ enterSystemScope('price_lists: status sweep', () => statusWorker.sweep(), {
67
+ entryPoint: 'interval',
68
+ })
69
+ .then((result) => {
70
+ if (result.scheduledToActive > 0 || result.activeToExpired > 0) {
71
+ app.log.info({ result }, 'price-list status sweep flipped lifecycle rows');
72
+ }
73
+ })
74
+ .catch((err) => {
75
+ app.log.error({ err }, 'price-list status sweep failed');
76
+ });
77
+ }, STATUS_SWEEP_INTERVAL_MS);
78
+ // Don't keep the Node process alive purely for the sweeper.
79
+ if (typeof handle.unref === 'function')
80
+ handle.unref();
81
+ app.addHook('onClose', async () => {
82
+ clearInterval(handle);
83
+ });
84
+ }
85
+ },
86
+ };
87
+ }
88
+ //# sourceMappingURL=plugin.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"plugin.js","sourceRoot":"","sources":["../../src/backend/plugin.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,40 @@
1
+ import type { FastifyInstance, FastifyRequest } from 'fastify';
2
+ import type { PriceListService } from './services/price-list-service.js';
3
+ import type { PricingServiceContract } from './services/pricing-service.interface.js';
4
+ import type { EntityManager } from '@mikro-orm/postgresql';
5
+ import type { CatalogCategoryReadPort, CatalogProductReadPort, CustomerAccountReadPort, CustomerGroupReadPort, OrganizationDetailsPort } from '@endora-commerce/contracts';
6
+ import type { RequireAdminFactory } from '@endora-commerce/platform/kernel';
7
+ export interface PricingRoutesDeps {
8
+ priceListService: PriceListService;
9
+ pricingService: PricingServiceContract;
10
+ emFactory: () => EntityManager;
11
+ requireAdmin: RequireAdminFactory;
12
+ /**
13
+ * Feature 075 Phase C — the neighbour reads these admin screens make. The
14
+ * rule-target pickers list organisations and categories; the product pricing
15
+ * panel and the resolved-price probe resolve a product. All three used to be
16
+ * `em.find` against tables this module does not own; each fails closed at the
17
+ * seam now, which is the right answer for an admin screen that would
18
+ * otherwise offer targets the platform cannot serve.
19
+ */
20
+ catalogProductRead: CatalogProductReadPort;
21
+ catalogCategoryRead: CatalogCategoryReadPort;
22
+ organizationDetails: OrganizationDetailsPort;
23
+ /**
24
+ * Feature 076 (D-79) — the last two neighbour reads this module made by
25
+ * importing another module's entity, both of them into `customer_accounts`.
26
+ * The rule-target picker lists customer groups; the admin resolved-price
27
+ * probe reads the customer behind the price it is asked to explain. Both fail
28
+ * closed at the seam, which is the right answer for a probe that would
29
+ * otherwise price for a customer the platform will not identify.
30
+ */
31
+ customerGroupRead: CustomerGroupReadPort;
32
+ customerAccountRead: CustomerAccountReadPort;
33
+ /** Feature 024 — resolves admin actor identity for audit entries. */
34
+ resolveAdminAuditContext?: (req: FastifyRequest) => {
35
+ actorAdminUserId: string;
36
+ impersonatedCustomerAccountId?: string | null;
37
+ };
38
+ }
39
+ export declare function registerPricingRoutes(app: FastifyInstance, deps: PricingRoutesDeps): Promise<void>;
40
+ //# sourceMappingURL=routes.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"routes.d.ts","sourceRoot":"","sources":["../../src/backend/routes.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,SAAS,CAAC;AAY/D,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,kCAAkC,CAAC;AACzE,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,yCAAyC,CAAC;AAEtF,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAE3D,OAAO,KAAK,EACV,uBAAuB,EACvB,sBAAsB,EACtB,uBAAuB,EACvB,qBAAqB,EACrB,uBAAuB,EACxB,MAAM,4BAA4B,CAAC;AACpC,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,kCAAkC,CAAC;AAG5E,MAAM,WAAW,iBAAiB;IAChC,gBAAgB,EAAE,gBAAgB,CAAC;IACnC,cAAc,EAAE,sBAAsB,CAAC;IACvC,SAAS,EAAE,MAAM,aAAa,CAAC;IAC/B,YAAY,EAAE,mBAAmB,CAAC;IAClC;;;;;;;OAOG;IACH,kBAAkB,EAAE,sBAAsB,CAAC;IAC3C,mBAAmB,EAAE,uBAAuB,CAAC;IAC7C,mBAAmB,EAAE,uBAAuB,CAAC;IAC7C;;;;;;;OAOG;IACH,iBAAiB,EAAE,qBAAqB,CAAC;IACzC,mBAAmB,EAAE,uBAAuB,CAAC;IAC7C,qEAAqE;IACrE,wBAAwB,CAAC,EAAE,CAAC,GAAG,EAAE,cAAc,KAAK;QAClD,gBAAgB,EAAE,MAAM,CAAC;QACzB,6BAA6B,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;KAC/C,CAAC;CACH;AAuCD,wBAAsB,qBAAqB,CACzC,GAAG,EAAE,eAAe,EACpB,IAAI,EAAE,iBAAiB,GACtB,OAAO,CAAC,IAAI,CAAC,CAklBf"}
@@ -0,0 +1,447 @@
1
+ import { createPriceListEngineRequestSchema, patchPriceListEngineRequestSchema, replaceBracketsRequestSchema, replaceProductsRequestSchema, ERROR_CODES, } from '@endora-commerce/contracts';
2
+ import { z } from 'zod';
3
+ import { HttpError } from '@endora-commerce/platform/http';
4
+ import { ruleVisibleForScope } from '@endora-commerce/platform/tenancy';
5
+ import { SalesChannel } from '@endora-commerce/platform/kernel';
6
+ import { PRICE_LIST_PERMISSIONS } from '../manifest.js';
7
+ function buildAuditCtx(request, resolver) {
8
+ const base = resolver?.(request);
9
+ if (!base)
10
+ return undefined;
11
+ return {
12
+ actorAdminUserId: base.actorAdminUserId,
13
+ impersonatedCustomerAccountId: base.impersonatedCustomerAccountId ?? null,
14
+ ipAddress: request.ip ?? null,
15
+ userAgent: typeof request.headers['user-agent'] === 'string'
16
+ ? request.headers['user-agent']
17
+ : null,
18
+ requestId: request.id,
19
+ };
20
+ }
21
+ /**
22
+ * Feature 050 — price_lists is rule-scoped: its org targeting lives in the
23
+ * applicationRule AST, not a column. Collect the org ids a rule targets so a
24
+ * scoped admin only sees lists targeting one of their orgs (or global lists).
25
+ */
26
+ function extractRuleOrgTargets(rule) {
27
+ if (!rule)
28
+ return [];
29
+ switch (rule.kind) {
30
+ case 'all':
31
+ return [];
32
+ case 'criterion':
33
+ return rule.type === 'organization' ? [...rule.values] : [];
34
+ case 'group':
35
+ return rule.children.flatMap(extractRuleOrgTargets);
36
+ }
37
+ }
38
+ export async function registerPricingRoutes(app, deps) {
39
+ const { priceListService, pricingService, emFactory, requireAdmin, catalogProductRead, catalogCategoryRead, organizationDetails, customerGroupRead, customerAccountRead, } = deps;
40
+ /**
41
+ * Issue #219 — this module's own gates. Every route below used to name
42
+ * `catalog:write`, which bought the ability to change what customers pay with
43
+ * a permission granted for content work. The split is by what the route does:
44
+ * a listing or a picker is `price_lists:read`, anything that persists is
45
+ * `price_lists:write`.
46
+ *
47
+ * No compatibility shim: `catalog:write` is refused here now, so a role that
48
+ * needs pricing is granted a pricing code deliberately. See the first-
49
+ * deployment checklist item D3.
50
+ */
51
+ const readGate = requireAdmin(PRICE_LIST_PERMISSIONS.READ);
52
+ const writeGate = requireAdmin(PRICE_LIST_PERMISSIONS.WRITE);
53
+ // ---- Engine routes (feature 011) -----------------------------------
54
+ app.get('/api/v1/admin/price-lists-engine', { preHandler: readGate }, async (request) => {
55
+ const status = toArray(request.query.status).filter((s) => s === 'draft' || s === 'active' || s === 'scheduled' || s === 'expired');
56
+ const type = toArray(request.query.type).filter((t) => t === 'base' || t === 'sale');
57
+ const filter = {};
58
+ if (status.length > 0)
59
+ filter.status = status;
60
+ if (type.length > 0)
61
+ filter.type = type;
62
+ if (typeof request.query.search === 'string' && request.query.search.trim().length > 0) {
63
+ filter.search = request.query.search.trim();
64
+ }
65
+ const rows = await priceListService.listEngine(filter);
66
+ // Feature 050 — hide price lists that target only orgs outside the scope.
67
+ const scoped = rows.filter((r) => ruleVisibleForScope(extractRuleOrgTargets(r.applicationRule)));
68
+ return { data: { items: scoped.map(serializePriceListEngine) } };
69
+ });
70
+ app.post('/api/v1/admin/price-lists-engine', {
71
+ preHandler: writeGate,
72
+ schema: { body: createPriceListEngineRequestSchema },
73
+ }, async (request, reply) => {
74
+ const body = createPriceListEngineRequestSchema.parse(request.body);
75
+ const row = await priceListService.create({
76
+ name: body.name,
77
+ type: body.type,
78
+ startsAt: body.startsAt ? new Date(body.startsAt) : null,
79
+ endsAt: body.endsAt ? new Date(body.endsAt) : null,
80
+ ...(body.applicationRule !== undefined ? { applicationRule: body.applicationRule } : {}),
81
+ }, buildAuditCtx(request, deps.resolveAdminAuditContext));
82
+ reply.status(201);
83
+ return { data: serializePriceListEngine(row) };
84
+ });
85
+ app.patch('/api/v1/admin/price-lists-engine/:id', {
86
+ preHandler: writeGate,
87
+ schema: { body: patchPriceListEngineRequestSchema },
88
+ }, async (request) => {
89
+ const body = patchPriceListEngineRequestSchema.parse(request.body);
90
+ const patch = {};
91
+ if (body.name !== undefined)
92
+ patch.name = body.name;
93
+ if (body.type !== undefined)
94
+ patch.type = body.type;
95
+ if (body.startsAt !== undefined)
96
+ patch.startsAt = body.startsAt ? new Date(body.startsAt) : null;
97
+ if (body.endsAt !== undefined)
98
+ patch.endsAt = body.endsAt ? new Date(body.endsAt) : null;
99
+ if (body.applicationRule !== undefined)
100
+ patch.applicationRule = body.applicationRule;
101
+ const row = await priceListService.patch(request.params.id, patch, buildAuditCtx(request, deps.resolveAdminAuditContext));
102
+ return { data: serializePriceListEngine(row) };
103
+ });
104
+ app.get('/api/v1/admin/price-lists-engine/:id', { preHandler: readGate }, async (request) => {
105
+ const row = await priceListService.getById(request.params.id);
106
+ if (!ruleVisibleForScope(extractRuleOrgTargets(row.applicationRule))) {
107
+ throw new HttpError(404, ERROR_CODES.NOT_FOUND, `Price list ${request.params.id} not found.`);
108
+ }
109
+ return { data: serializePriceListEngine(row) };
110
+ });
111
+ app.post('/api/v1/admin/price-lists-engine/:id/activate', { preHandler: writeGate }, async (request) => {
112
+ const row = await priceListService.activate(request.params.id, buildAuditCtx(request, deps.resolveAdminAuditContext));
113
+ return { data: serializePriceListEngine(row) };
114
+ });
115
+ app.post('/api/v1/admin/price-lists-engine/:id/draftify', { preHandler: writeGate }, async (request) => {
116
+ const row = await priceListService.draftify(request.params.id, buildAuditCtx(request, deps.resolveAdminAuditContext));
117
+ return { data: serializePriceListEngine(row) };
118
+ });
119
+ app.post('/api/v1/admin/price-lists-engine/:id/duplicate', { preHandler: writeGate }, async (request, reply) => {
120
+ const dup = await priceListService.duplicate(request.params.id, buildAuditCtx(request, deps.resolveAdminAuditContext));
121
+ reply.status(201);
122
+ return { data: serializePriceListEngine(dup) };
123
+ });
124
+ app.delete('/api/v1/admin/price-lists-engine/:id', { preHandler: writeGate }, async (request, reply) => {
125
+ await priceListService.remove(request.params.id);
126
+ return reply.status(204).send();
127
+ });
128
+ // ---- Engine: product roster + bracket pricing (US3) ----------------
129
+ app.get('/api/v1/admin/price-lists-engine/:id/products', { preHandler: readGate }, async (request) => {
130
+ const items = await priceListService.listProducts(request.params.id);
131
+ return { data: { items } };
132
+ });
133
+ app.put('/api/v1/admin/price-lists-engine/:id/products', {
134
+ preHandler: writeGate,
135
+ schema: { body: replaceProductsRequestSchema },
136
+ }, async (request) => {
137
+ const body = replaceProductsRequestSchema.parse(request.body);
138
+ const result = await priceListService.replaceProducts(request.params.id, body.productIds, buildAuditCtx(request, deps.resolveAdminAuditContext));
139
+ return { data: result };
140
+ });
141
+ app.post('/api/v1/admin/price-lists-engine/:id/products', {
142
+ preHandler: writeGate,
143
+ schema: { body: z.object({ productId: z.string().uuid() }) },
144
+ }, async (request, reply) => {
145
+ const body = z.object({ productId: z.string().uuid() }).parse(request.body);
146
+ await priceListService.addProduct(request.params.id, body.productId);
147
+ reply.status(201);
148
+ return { data: { priceListId: request.params.id, productId: body.productId } };
149
+ });
150
+ app.delete('/api/v1/admin/price-lists-engine/:id/products/:productId', { preHandler: writeGate }, async (request, reply) => {
151
+ await priceListService.removeProduct(request.params.id, request.params.productId);
152
+ return reply.status(204).send();
153
+ });
154
+ app.get('/api/v1/admin/price-lists-engine/:id/products/:productId/brackets', { preHandler: readGate }, async (request) => {
155
+ const list = await priceListService.listProducts(request.params.id);
156
+ const entry = list.find((e) => e.productId === request.params.productId);
157
+ if (!entry) {
158
+ return { data: { bracketsByCurrency: {} } };
159
+ }
160
+ return { data: { bracketsByCurrency: entry.bracketsByCurrency } };
161
+ });
162
+ app.put('/api/v1/admin/price-lists-engine/:id/products/:productId/brackets', {
163
+ preHandler: writeGate,
164
+ schema: { body: replaceBracketsRequestSchema },
165
+ }, async (request) => {
166
+ const body = replaceBracketsRequestSchema.parse(request.body);
167
+ const out = await priceListService.replaceBrackets(request.params.id, request.params.productId, body.bracketsByCurrency, buildAuditCtx(request, deps.resolveAdminAuditContext));
168
+ return { data: { bracketsByCurrency: out } };
169
+ });
170
+ app.post('/api/v1/admin/price-lists-engine/:id/products/:productId/brackets/copy', {
171
+ preHandler: writeGate,
172
+ schema: {
173
+ body: z.object({
174
+ fromCurrency: z.string().regex(/^[A-Z]{3}$/),
175
+ toCurrencies: z.array(z.string().regex(/^[A-Z]{3}$/)).min(1),
176
+ }),
177
+ },
178
+ }, async (request) => {
179
+ const body = z
180
+ .object({
181
+ fromCurrency: z.string().regex(/^[A-Z]{3}$/),
182
+ toCurrencies: z.array(z.string().regex(/^[A-Z]{3}$/)).min(1),
183
+ })
184
+ .parse(request.body);
185
+ const result = await priceListService.copyCurrencyBrackets(request.params.id, request.params.productId, body.fromCurrency, body.toCurrencies);
186
+ return { data: result };
187
+ });
188
+ // ---- Rule-builder pickers (US4) -----------------------------------
189
+ app.get('/api/v1/admin/pricing/rule-targets/sales-channels', { preHandler: readGate }, async () => {
190
+ const em = emFactory();
191
+ const rows = await em.find(SalesChannel, {}, { orderBy: { code: 'asc' } });
192
+ return {
193
+ data: {
194
+ items: rows.map((r) => ({
195
+ id: r.id,
196
+ code: r.code,
197
+ name: r.name,
198
+ })),
199
+ },
200
+ };
201
+ });
202
+ /**
203
+ * Issue #180 removed `catalog:write` from the canonical customer-group
204
+ * endpoints and missed this copy — a pricing rule-target picker, not a
205
+ * catalogue surface. The `promotions` and `pwa` twins have always answered
206
+ * behind their own module's read code; so does this one now.
207
+ */
208
+ app.get('/api/v1/admin/pricing/rule-targets/customer-groups', { preHandler: readGate }, async () => {
209
+ // Already ordered by code on the owner's side.
210
+ const rows = await customerGroupRead.listAll();
211
+ return {
212
+ data: {
213
+ items: rows.map((r) => ({ id: r.id, code: r.code, name: r.name })),
214
+ },
215
+ };
216
+ });
217
+ app.get('/api/v1/admin/pricing/rule-targets/organizations', { preHandler: readGate }, async (request) => {
218
+ const limit = Math.min(200, Math.max(1, Number(request.query.limit ?? '50')));
219
+ const search = (request.query.search ?? '').trim();
220
+ // `searchByName` matches the diacritic-folded `nameSearch` column, where
221
+ // this picker used to `$ilike` on `name` — so a search for "lodz" now
222
+ // finds "Łódź" here as it already did on the order list.
223
+ const rows = await organizationDetails.searchByName(search, limit);
224
+ return {
225
+ data: {
226
+ items: rows.map((r) => ({ id: r.id, name: r.name, taxId: r.taxId })),
227
+ nextCursor: null,
228
+ },
229
+ };
230
+ });
231
+ app.get('/api/v1/admin/pricing/rule-targets/categories', { preHandler: readGate }, async () => {
232
+ // The port's `listAll` is already ordered by sort order then slug.
233
+ const rows = await catalogCategoryRead.listAll();
234
+ return {
235
+ data: {
236
+ items: rows.map((r) => ({
237
+ id: r.id,
238
+ slug: r.slug,
239
+ name: r.name,
240
+ parentCategoryId: r.parentCategoryId ?? null,
241
+ sortOrder: r.sortOrder,
242
+ })),
243
+ },
244
+ };
245
+ });
246
+ app.get('/api/v1/admin/pricing/rule-targets/currencies', { preHandler: readGate }, async () => {
247
+ const em = emFactory();
248
+ const channels = await em.find(SalesChannel, {});
249
+ const exposed = new Map();
250
+ for (const ch of channels) {
251
+ for (const cur of ch.currencies ?? []) {
252
+ if (typeof cur !== 'string' || cur.length !== 3)
253
+ continue;
254
+ const key = cur.toUpperCase();
255
+ const list = exposed.get(key) ?? [];
256
+ list.push(ch.code);
257
+ exposed.set(key, list);
258
+ }
259
+ }
260
+ const items = [...exposed.entries()]
261
+ .map(([code, exposedByChannels]) => ({ code, exposedByChannels }))
262
+ .sort((a, b) => a.code.localeCompare(b.code));
263
+ return { data: { items } };
264
+ });
265
+ // ---- Linked price-lists panel for the product editor (US8) -------
266
+ app.get('/api/v1/admin/products/:productId/price-lists', { preHandler: readGate }, async (request, reply) => {
267
+ const product = await catalogProductRead.findById(request.params.productId);
268
+ if (!product) {
269
+ reply.status(404);
270
+ return { error: { code: 'NOT_FOUND', message: 'Product not found.' } };
271
+ }
272
+ const items = await priceListService.summarizeBracketsForProduct(request.params.productId);
273
+ return {
274
+ data: {
275
+ items: items.map((it) => ({
276
+ list: {
277
+ id: it.list.id,
278
+ name: it.list.name,
279
+ type: it.list.type,
280
+ status: it.list.status,
281
+ modifiedAt: it.list.modifiedAt.toISOString(),
282
+ },
283
+ summary: it.summary,
284
+ deepLinkPath: it.deepLinkPath,
285
+ })),
286
+ },
287
+ };
288
+ });
289
+ // ---- Display-mode overrides (US7) ----------------------------------
290
+ app.get('/api/v1/admin/pricing/display-mode-overrides', { preHandler: readGate }, async (request) => {
291
+ const items = await priceListService.listDisplayModeOverrides(request.query.scope);
292
+ return {
293
+ data: {
294
+ items: items.map((o) => ({
295
+ scope: o.scope,
296
+ targetId: o.targetId,
297
+ mode: o.mode,
298
+ updatedAt: o.updatedAt.toISOString(),
299
+ })),
300
+ },
301
+ };
302
+ });
303
+ app.get('/api/v1/admin/pricing/display-mode-overrides/:scope/:targetId', { preHandler: readGate }, async (request, reply) => {
304
+ const row = await priceListService.getDisplayModeOverride(request.params.scope, request.params.targetId);
305
+ if (!row) {
306
+ reply.status(404);
307
+ return { error: { code: 'NOT_FOUND', message: 'Override not found.' } };
308
+ }
309
+ return {
310
+ data: {
311
+ scope: row.scope,
312
+ targetId: row.targetId,
313
+ mode: row.mode,
314
+ updatedAt: row.updatedAt.toISOString(),
315
+ },
316
+ };
317
+ });
318
+ app.put('/api/v1/admin/pricing/display-mode-overrides/:scope/:targetId', {
319
+ preHandler: writeGate,
320
+ schema: {
321
+ body: z.object({
322
+ mode: z.enum(['gross_only', 'net_only', 'both', 'none', 'inherit']),
323
+ }),
324
+ },
325
+ }, async (request, reply) => {
326
+ const body = z
327
+ .object({ mode: z.enum(['gross_only', 'net_only', 'both', 'none', 'inherit']) })
328
+ .parse(request.body);
329
+ const row = await priceListService.upsertDisplayModeOverride(request.params.scope, request.params.targetId, body.mode);
330
+ if (!row) {
331
+ return reply.status(204).send();
332
+ }
333
+ return {
334
+ data: {
335
+ scope: row.scope,
336
+ targetId: row.targetId,
337
+ mode: row.mode,
338
+ updatedAt: row.updatedAt.toISOString(),
339
+ },
340
+ };
341
+ });
342
+ // Storefront-public routes live in `routes.storefront.ts` and are mounted
343
+ // separately from `plugin.ts` so the admin and storefront surfaces stay
344
+ // independently auditable. See T025/T026.
345
+ // Test-only sweeper hook — the production code path runs the worker on the
346
+ // BullMQ queue every 5 min. This endpoint lets integration tests advance
347
+ // the state machine without waiting for the queue tick.
348
+ app.post('/api/v1/admin/price-lists-engine/internal/sweep', { preHandler: writeGate }, async () => {
349
+ // The worker reads/writes through the same EM as the rest of the
350
+ // module; constructed here so the route doesn't pin the worker to
351
+ // the module-level construction.
352
+ const { PriceListStatusWorker } = await import('./services/price-list-status-worker.js');
353
+ const worker = new PriceListStatusWorker(emFactory);
354
+ const result = await worker.sweep();
355
+ return { data: result };
356
+ });
357
+ // ---- Admin price resolution for a specific customer -----------------
358
+ // Resolves the effective unit price for a (product, customer/organization)
359
+ // pair so admin-side flows (notably "create quote request on behalf of a
360
+ // customer") can pre-fill the agreed unit price from the customer's price
361
+ // lists instead of leaving the field blank. Mirrors the storefront resolver
362
+ // but threads the customer's organization + group context.
363
+ //
364
+ // D-173 — it is gated on this module's own read code, not on `rfqs:handle`.
365
+ // The caller is the RFQ create screen, but what the endpoint serves is a
366
+ // price-list resolution, and `price_lists` declares itself
367
+ // `nonDeactivatable` while `quote_requests` is switchable: `rfqs:handle`
368
+ // leaves `/admin-roles` the moment an operator switches quote requests off,
369
+ // and this route, which cannot be switched off with it, went on enforcing a
370
+ // code nobody could be granted. That is the consequence D-166 wrote down for
371
+ // the sales-rep endpoints and did not generalise.
372
+ //
373
+ // The label test decides which repair applies: *"Handle quote requests"* is
374
+ // not a sentence about a price-resolution endpoint, so the code does not
375
+ // become shared — the consumer gates on a code it owns. Issue #219 already
376
+ // ruled that a pricing read sits behind `price_lists:read`; a role that
377
+ // handles RFQs and prefills agreed prices holds both, which is why
378
+ // `sales_representative` gains the read code in the dev seed.
379
+ app.get('/api/v1/admin/products/:id/resolved-price', { preHandler: readGate }, async (request, reply) => {
380
+ const em = emFactory();
381
+ const product = await catalogProductRead.findById(request.params.id);
382
+ if (!product) {
383
+ return reply
384
+ .status(404)
385
+ .send({ error: { code: 'NOT_FOUND', message: 'Product not found.' } });
386
+ }
387
+ const customer = request.query.customerAccountId
388
+ ? await customerAccountRead.findById(request.query.customerAccountId)
389
+ : null;
390
+ const organizationId = request.query.organizationId ?? customer?.organizationId ?? null;
391
+ const organization = organizationId
392
+ ? await organizationDetails.findById(organizationId)
393
+ : null;
394
+ const salesChannel = await em.findOne(SalesChannel, { systemDefault: true });
395
+ if (!salesChannel) {
396
+ return reply
397
+ .status(400)
398
+ .send({ error: { code: 'VALIDATION_FAILED', message: 'No default sales channel.' } });
399
+ }
400
+ const quantity = Math.max(1, Number(request.query.quantity ?? '1') || 1);
401
+ const currency = request.query.currency?.toUpperCase() ?? salesChannel.defaultCurrency;
402
+ const customerGroupId = customer?.customerGroupId ?? organization?.customerGroupId ?? null;
403
+ const resolved = await pricingService.resolveLinePrice({
404
+ product,
405
+ variantId: request.query.variantId ?? null,
406
+ context: {
407
+ quantity,
408
+ organization: organization ?? null,
409
+ customerGroupId,
410
+ salesChannel,
411
+ currencyCode: currency,
412
+ },
413
+ });
414
+ return {
415
+ data: {
416
+ resolvedPrice: resolved
417
+ ? {
418
+ amount: resolved.amount,
419
+ currency: resolved.currency,
420
+ isSale: resolved.isSale,
421
+ priceListId: resolved.priceListId,
422
+ }
423
+ : null,
424
+ },
425
+ };
426
+ });
427
+ }
428
+ function toArray(v) {
429
+ if (v === undefined)
430
+ return [];
431
+ return Array.isArray(v) ? v : [v];
432
+ }
433
+ function serializePriceListEngine(row) {
434
+ return {
435
+ id: row.id,
436
+ name: row.name,
437
+ type: row.type,
438
+ status: row.status,
439
+ startsAt: row.startsAt ? row.startsAt.toISOString() : null,
440
+ endsAt: row.endsAt ? row.endsAt.toISOString() : null,
441
+ applicationRule: row.applicationRule,
442
+ isSystem: row.isSystem,
443
+ modifiedAt: row.modifiedAt.toISOString(),
444
+ createdAt: row.createdAt.toISOString(),
445
+ };
446
+ }
447
+ //# sourceMappingURL=routes.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"routes.js","sourceRoot":"","sources":["../../src/backend/routes.ts"],"names":[],"mappings":"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"}