@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,26 @@
1
+ import type { RuleEvaluation } from './application-rule-evaluator.js';
2
+ /**
3
+ * Pure priority chain resolver (feature 011 / FR-026, FR-027).
4
+ *
5
+ * Picks one matching list per the deterministic order:
6
+ * 1. List whose rule explicitly names the customer's Organization
7
+ * 2. else explicit Customer Group
8
+ * 3. else explicit Category
9
+ * 4. else explicit Sales Channel
10
+ * 5. else any other matching list
11
+ *
12
+ * Tie-break at every step: most recent `modifiedAt` first, then
13
+ * lexicographically smallest `name`. Tie-break is total — the same input
14
+ * yields the same picked list every run.
15
+ */
16
+ export interface PriceListCandidate<TList = unknown> {
17
+ list: TList;
18
+ evaluation: RuleEvaluation;
19
+ modifiedAt: Date;
20
+ name: string;
21
+ /** Marker for the seeded `Default` row — the resolver's terminal fallback. */
22
+ isSystem: boolean;
23
+ }
24
+ export declare function pickPriorityChain<TList>(candidates: readonly PriceListCandidate<TList>[]): PriceListCandidate<TList> | null;
25
+ export declare function tieBreak<TList>(candidates: readonly PriceListCandidate<TList>[]): PriceListCandidate<TList>;
26
+ //# sourceMappingURL=price-list-resolver.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"price-list-resolver.d.ts","sourceRoot":"","sources":["../../../src/backend/services/price-list-resolver.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAEtE;;;;;;;;;;;;;GAaG;AACH,MAAM,WAAW,kBAAkB,CAAC,KAAK,GAAG,OAAO;IACjD,IAAI,EAAE,KAAK,CAAC;IACZ,UAAU,EAAE,cAAc,CAAC;IAC3B,UAAU,EAAE,IAAI,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,8EAA8E;IAC9E,QAAQ,EAAE,OAAO,CAAC;CACnB;AASD,wBAAgB,iBAAiB,CAAC,KAAK,EACrC,UAAU,EAAE,SAAS,kBAAkB,CAAC,KAAK,CAAC,EAAE,GAC/C,kBAAkB,CAAC,KAAK,CAAC,GAAG,IAAI,CAqBlC;AAED,wBAAgB,QAAQ,CAAC,KAAK,EAC5B,UAAU,EAAE,SAAS,kBAAkB,CAAC,KAAK,CAAC,EAAE,GAC/C,kBAAkB,CAAC,KAAK,CAAC,CAQ3B"}
@@ -0,0 +1,37 @@
1
+ const PRIORITY_ORDER = [
2
+ 'organization',
3
+ 'customerGroup',
4
+ 'category',
5
+ 'salesChannel',
6
+ ];
7
+ export function pickPriorityChain(candidates) {
8
+ if (candidates.length === 0)
9
+ return null;
10
+ for (const level of PRIORITY_ORDER) {
11
+ const atLevel = candidates.filter((c) => c.evaluation.explicitOn.has(level));
12
+ if (atLevel.length === 0)
13
+ continue;
14
+ if (level === 'organization') {
15
+ // Feature 056 — within the organization level, a list naming a NEARER org
16
+ // (smaller nearness rank) outranks one naming a farther ancestor (R5). A
17
+ // flat direct-org match is rank 0, so flat behavior is unchanged.
18
+ const nearest = Math.min(...atLevel.map((c) => c.evaluation.organizationRank ?? Number.POSITIVE_INFINITY));
19
+ const nearestOnly = atLevel.filter((c) => (c.evaluation.organizationRank ?? Number.POSITIVE_INFINITY) === nearest);
20
+ return tieBreak(nearestOnly);
21
+ }
22
+ return tieBreak(atLevel);
23
+ }
24
+ // Step 5 — any other matching list. Default lives here.
25
+ return tieBreak(candidates);
26
+ }
27
+ export function tieBreak(candidates) {
28
+ // Most recent modifiedAt first, then lexicographic name.
29
+ const sorted = [...candidates].sort((a, b) => {
30
+ const dt = b.modifiedAt.getTime() - a.modifiedAt.getTime();
31
+ if (dt !== 0)
32
+ return dt;
33
+ return a.name.localeCompare(b.name);
34
+ });
35
+ return sorted[0];
36
+ }
37
+ //# sourceMappingURL=price-list-resolver.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"price-list-resolver.js","sourceRoot":"","sources":["../../../src/backend/services/price-list-resolver.ts"],"names":[],"mappings":"AA0BA,MAAM,cAAc,GAAiC;IACnD,cAAc;IACd,eAAe;IACf,UAAU;IACV,cAAc;CACf,CAAC;AAEF,MAAM,UAAU,iBAAiB,CAC/B,UAAgD;IAEhD,IAAI,UAAU,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IACzC,KAAK,MAAM,KAAK,IAAI,cAAc,EAAE,CAAC;QACnC,MAAM,OAAO,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,UAAU,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC;QAC7E,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC;YAAE,SAAS;QACnC,IAAI,KAAK,KAAK,cAAc,EAAE,CAAC;YAC7B,0EAA0E;YAC1E,yEAAyE;YACzE,kEAAkE;YAClE,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,CACtB,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,gBAAgB,IAAI,MAAM,CAAC,iBAAiB,CAAC,CACjF,CAAC;YACF,MAAM,WAAW,GAAG,OAAO,CAAC,MAAM,CAChC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,gBAAgB,IAAI,MAAM,CAAC,iBAAiB,CAAC,KAAK,OAAO,CAC/E,CAAC;YACF,OAAO,QAAQ,CAAC,WAAW,CAAC,CAAC;QAC/B,CAAC;QACD,OAAO,QAAQ,CAAC,OAAO,CAAC,CAAC;IAC3B,CAAC;IACD,wDAAwD;IACxD,OAAO,QAAQ,CAAC,UAAU,CAAC,CAAC;AAC9B,CAAC;AAED,MAAM,UAAU,QAAQ,CACtB,UAAgD;IAEhD,yDAAyD;IACzD,MAAM,MAAM,GAAG,CAAC,GAAG,UAAU,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;QAC3C,MAAM,EAAE,GAAG,CAAC,CAAC,UAAU,CAAC,OAAO,EAAE,GAAG,CAAC,CAAC,UAAU,CAAC,OAAO,EAAE,CAAC;QAC3D,IAAI,EAAE,KAAK,CAAC;YAAE,OAAO,EAAE,CAAC;QACxB,OAAO,CAAC,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC;IACtC,CAAC,CAAC,CAAC;IACH,OAAO,MAAM,CAAC,CAAC,CAAE,CAAC;AACpB,CAAC"}
@@ -0,0 +1,431 @@
1
+ import type { EntityManager } from '@mikro-orm/postgresql';
2
+ import { type ApplicationRule } from '@endora-commerce/contracts';
3
+ import type { CatalogCategoryReadPort, CatalogProductReadPort, CustomerGroupReadPort, OrganizationDetailsPort } from '@endora-commerce/contracts';
4
+ import { PriceList } from '../entities/price-list.entity.js';
5
+ import { PriceDisplayModeOverride } from '../entities/price-display-mode-override.entity.js';
6
+ import type { AuditPort } from '@endora-commerce/platform/kernel';
7
+ import type { CommandBus } from '@endora-commerce/platform/commands';
8
+ import type { PriceListsAuditContext } from '../plugin.js';
9
+ export type DisplayMode = 'gross_only' | 'net_only' | 'both' | 'none';
10
+ export type DisplayModeOverrideScope = 'organization' | 'category' | 'product';
11
+ export type PriceListStatus = 'draft' | 'active' | 'scheduled' | 'expired';
12
+ export type PriceListType = 'base' | 'sale';
13
+ export interface CreatePriceListInput {
14
+ name: string;
15
+ type: PriceListType;
16
+ startsAt?: Date | null;
17
+ endsAt?: Date | null;
18
+ applicationRule?: ApplicationRule;
19
+ }
20
+ export interface PatchPriceListInput {
21
+ name?: string;
22
+ type?: PriceListType;
23
+ startsAt?: Date | null;
24
+ endsAt?: Date | null;
25
+ applicationRule?: ApplicationRule;
26
+ }
27
+ export interface BracketInput {
28
+ minQuantity: number;
29
+ maxQuantity: number | null;
30
+ /** Decimal amount as string (the storage shape on `price_list_price_brackets`). */
31
+ amount: string;
32
+ }
33
+ export interface ReplaceProductsResult {
34
+ added: number;
35
+ removed: number;
36
+ unchanged: number;
37
+ }
38
+ export interface CopyCurrencyResult {
39
+ added: number;
40
+ }
41
+ /**
42
+ * The neighbours this service has to **ask** rather than query (feature 075
43
+ * Phase C).
44
+ *
45
+ * A price-list rule and a display-mode override both point at rows two other
46
+ * modules own — an organisation, a category, a product — and this service used
47
+ * to validate them with `em.count(Organization, …)` and friends, which is
48
+ * another module's table on this module's connection. It answers rows whatever
49
+ * state that module is in, so an operator with `catalog` switched off could
50
+ * still pin a price list to a category the platform will not serve.
51
+ *
52
+ * Grouped into one object because it is one decision: a composition either
53
+ * knows how to reach its neighbours or it does not, and there is no coherent
54
+ * state where it can resolve categories but not organisations.
55
+ */
56
+ export interface PriceListTargetReads {
57
+ organizationDetails: OrganizationDetailsPort;
58
+ catalogCategoryRead: CatalogCategoryReadPort;
59
+ catalogProductRead: CatalogProductReadPort;
60
+ /**
61
+ * Feature 076 (D-79) — customer groups moved to `customer_accounts`, so the
62
+ * rule-target validation reads them the same way it already read
63
+ * organisations and categories.
64
+ */
65
+ customerGroupRead: CustomerGroupReadPort;
66
+ }
67
+ /**
68
+ * PriceListService — admin CRUD over PriceList + the two child collections
69
+ * (items + assignments). Keeping all three operations on the same service
70
+ * keeps the "edit a price list and its rules" admin flow on one transaction
71
+ * boundary when we need it later.
72
+ */
73
+ export declare class PriceListService {
74
+ #private;
75
+ private readonly emFactory;
76
+ /**
77
+ * Optional pricing cache. Every write path on this service calls
78
+ * `invalidateAll()` so the next read repopulates from the DB.
79
+ * Coarse but correct — fan-out makes per-tuple invalidation
80
+ * unprofitable until profiling shows otherwise.
81
+ */
82
+ private readonly pricingCache?;
83
+ /** Feature 024 — optional audit log writer. When omitted, no audit
84
+ * rows are emitted (tests that don't care about audit pass nothing). */
85
+ private readonly auditLog?;
86
+ /**
87
+ * Feature 054 — when injected, `patch` runs through the Command Bus so the
88
+ * update is audited co-transactionally (Principle XIII). Optional: bus-less
89
+ * construction keeps the legacy audit path, byte-identical.
90
+ */
91
+ private readonly commandBus?;
92
+ /**
93
+ * Feature 075 Phase C — the ports behind every rule-target and
94
+ * override-target existence check. Optional in the signature because a
95
+ * price list with no organisation, category or product target never reaches
96
+ * them; **never optional in effect**, because the paths that need them
97
+ * refuse rather than skip when they are absent (see {@link targets}).
98
+ */
99
+ private readonly targetReads?;
100
+ constructor(emFactory: () => EntityManager,
101
+ /**
102
+ * Optional pricing cache. Every write path on this service calls
103
+ * `invalidateAll()` so the next read repopulates from the DB.
104
+ * Coarse but correct — fan-out makes per-tuple invalidation
105
+ * unprofitable until profiling shows otherwise.
106
+ */
107
+ pricingCache?: {
108
+ invalidateAll: () => void;
109
+ } | undefined,
110
+ /** Feature 024 — optional audit log writer. When omitted, no audit
111
+ * rows are emitted (tests that don't care about audit pass nothing). */
112
+ auditLog?: AuditPort | undefined,
113
+ /**
114
+ * Feature 054 — when injected, `patch` runs through the Command Bus so the
115
+ * update is audited co-transactionally (Principle XIII). Optional: bus-less
116
+ * construction keeps the legacy audit path, byte-identical.
117
+ */
118
+ commandBus?: CommandBus | undefined,
119
+ /**
120
+ * Feature 075 Phase C — the ports behind every rule-target and
121
+ * override-target existence check. Optional in the signature because a
122
+ * price list with no organisation, category or product target never reaches
123
+ * them; **never optional in effect**, because the paths that need them
124
+ * refuse rather than skip when they are absent (see {@link targets}).
125
+ */
126
+ targetReads?: PriceListTargetReads | undefined);
127
+ /**
128
+ * The neighbour ports, or a refusal. Skipping the validation when nothing was
129
+ * wired would turn "this composition cannot reach `catalog`" into "every
130
+ * category id is valid", which is the fail-open shape feature 075 exists to
131
+ * remove.
132
+ */
133
+ private targets;
134
+ private invalidatePricingCache;
135
+ private audit;
136
+ listEngine(filter?: {
137
+ status?: PriceListStatus[];
138
+ type?: PriceListType[];
139
+ search?: string;
140
+ }): Promise<PriceList[]>;
141
+ getById(id: string, em?: EntityManager): Promise<PriceList>;
142
+ remove(id: string): Promise<void>;
143
+ /**
144
+ * Default-list rule-attachment guard (FR-006). Rejects any attempt to attach
145
+ * a non-empty Application Rule to the seeded `Default` row.
146
+ */
147
+ assertCanSetApplicationRule(id: string, rule: {
148
+ kind: string;
149
+ }): Promise<void>;
150
+ /**
151
+ * Default-list status-change guard (FR-005 / FR-006 / spec.md §State Machines).
152
+ * The system Default row stays `active` for the platform's lifetime. The
153
+ * service rejects any attempt to move it to `draft`, `scheduled`, or `expired`.
154
+ */
155
+ assertCanTransitionStatus(id: string, nextStatus: 'draft' | 'active' | 'scheduled' | 'expired'): Promise<void>;
156
+ /**
157
+ * Create a new price list. Status defaults to `draft`. Default-list
158
+ * protections are out of scope here — system rows are seeded by migration
159
+ * 031, never created via this method.
160
+ */
161
+ create(input: CreatePriceListInput, auditCtx?: PriceListsAuditContext): Promise<PriceList>;
162
+ /**
163
+ * Partial update. Bumps `modifiedAt` on every material change.
164
+ * Refuses non-empty rule attachment on the seeded `Default` row (FR-006).
165
+ */
166
+ patch(id: string, input: PatchPriceListInput, auditCtx?: PriceListsAuditContext): Promise<PriceList>;
167
+ /**
168
+ * Manual transition: draft → active (or scheduled / expired if dates
169
+ * dictate). FR-009 row 1.
170
+ */
171
+ activate(id: string, auditCtx?: PriceListsAuditContext): Promise<PriceList>;
172
+ /**
173
+ * Manual transition: any state → draft. Freezes the list immediately.
174
+ */
175
+ draftify(id: string, auditCtx?: PriceListsAuditContext): Promise<PriceList>;
176
+ /**
177
+ * Duplicate a price list. Copies the rule, the assigned products, and
178
+ * every bracket row. Resets status to `draft`, clears dates, and derives
179
+ * a unique name (suffix ` (copy)`, ` (copy 2)`, …) — FR-013.
180
+ */
181
+ duplicate(id: string, auditCtx?: PriceListsAuditContext): Promise<PriceList>;
182
+ /**
183
+ * Normalise + validate an Application Rule (US4 / FR-020..FR-024).
184
+ *
185
+ * Steps in order:
186
+ * 1. Recursively walk the AST.
187
+ * 2. For criteria: dedupe values, uppercase currency codes, validate
188
+ * target IDs against their respective tables. Empty `values` arrays
189
+ * collapse to `{ kind: 'all' }`.
190
+ * 3. For groups: recursively normalise each child, then drop children
191
+ * that collapsed to `{ kind: 'all' }`. If the group becomes empty
192
+ * it collapses to `{ kind: 'all' }` as well; if it's left with a
193
+ * single child, that child takes its place.
194
+ * 4. Reject malformed currencies, depth > 5, and unknown target IDs
195
+ * with `400 VALIDATION_FAILED`.
196
+ *
197
+ * Returns the normalised rule. Does NOT enforce FR-023 (non-Default
198
+ * rules must be non-empty); that gate fires at activation time.
199
+ */
200
+ normaliseAndValidateRule(rule: ApplicationRule): Promise<ApplicationRule>;
201
+ private normaliseRuleNode;
202
+ /**
203
+ * Validate that every value in an ID-based criterion is a real row in the
204
+ * appropriate table. Throws `400 VALIDATION_FAILED` for any unknown ID.
205
+ */
206
+ private assertTargetsExist;
207
+ /**
208
+ * Date sanity per FR-010: `endsAt` must be greater than `startsAt`; at
209
+ * creation time `endsAt` must be in the future.
210
+ */
211
+ private assertDateSanity;
212
+ /**
213
+ * For a given product, return every price list the product is assigned
214
+ * to with a per-currency bracket summary and a deep-link path. Powers
215
+ * the admin Catalog product editor's Pricing tab (FR-044/045/046).
216
+ */
217
+ summarizeBracketsForProduct(productId: string): Promise<Array<{
218
+ list: {
219
+ id: string;
220
+ name: string;
221
+ type: 'base' | 'sale';
222
+ status: 'draft' | 'active' | 'scheduled' | 'expired';
223
+ modifiedAt: Date;
224
+ };
225
+ summary: Array<{
226
+ currencyCode: string;
227
+ summary: string;
228
+ }>;
229
+ deepLinkPath: string;
230
+ }>>;
231
+ /**
232
+ * Build a human-readable summary string for one currency's bracket
233
+ * series, e.g.:
234
+ * - "80,0000 across 1 bracket"
235
+ * - "80,0000 – 100,0000 across 3 brackets"
236
+ * The numeric formatting deliberately keeps the storage scale (4
237
+ * fractional digits); the admin UI may re-format per locale.
238
+ */
239
+ private summariseBrackets;
240
+ private formatAmount;
241
+ /**
242
+ * Upsert a per-Org / per-Category / per-Product display-mode override
243
+ * (FR-038). The mode value `'inherit'` deletes the override row.
244
+ * Validates the target ID against the appropriate table — orphans are
245
+ * refused with 400 (the polymorphic FK is enforced here, not at the DB
246
+ * level, since the target table varies — see data-model.md §1.4).
247
+ */
248
+ upsertDisplayModeOverride(scope: DisplayModeOverrideScope, targetId: string, mode: DisplayMode | 'inherit'): Promise<PriceDisplayModeOverride | null>;
249
+ listDisplayModeOverrides(scope?: DisplayModeOverrideScope): Promise<PriceDisplayModeOverride[]>;
250
+ getDisplayModeOverride(scope: DisplayModeOverrideScope, targetId: string): Promise<PriceDisplayModeOverride | null>;
251
+ /**
252
+ * Update a `pricing.*` settings-group display-mode key. Settings are
253
+ * per-sales-channel under the foundation settings module — when no
254
+ * channel is supplied, this method writes the value across every
255
+ * sales channel (treating it as a tenant-wide override). For
256
+ * channel-specific overrides, callers may pass a single channel.
257
+ *
258
+ * `key` is the bare suffix (e.g. `default_display_mode` or
259
+ * `unauthenticated_display_mode`) — the full code is derived as
260
+ * `pricing.<key>`.
261
+ */
262
+ setSettingsDisplayMode(key: 'default_display_mode' | 'unauthenticated_display_mode', mode: DisplayMode, salesChannelId?: string): Promise<void>;
263
+ /**
264
+ * Read the value of a `pricing.*` display-mode setting for a sales
265
+ * channel. Resolves along the settings tier chain
266
+ * per-channel override → global value → manifest `defaultValue`
267
+ * (mirroring `SettingsService.get`). The global tier lives on
268
+ * `settings.global_value` and is what the admin "All channels" editor
269
+ * writes; without it a globally-set mode (e.g. `both`) was ignored and
270
+ * the resolver silently fell back to the manifest default `gross_only`.
271
+ */
272
+ readSettingsDisplayMode(key: 'default_display_mode' | 'unauthenticated_display_mode', salesChannelId: string): Promise<DisplayMode>;
273
+ /**
274
+ * Resolve the effective display mode for a (product, organization?,
275
+ * salesChannel) tuple along the FR-039 chain
276
+ * Product → Category → Organization → Settings.
277
+ *
278
+ * Walks the product's category memberships to find the most specific
279
+ * category override (deepest in the tree, with `(sort_order ASC, id ASC)`
280
+ * as the deterministic tie-break). Reads override rows from
281
+ * `price_display_mode_overrides`; falls back to the per-channel
282
+ * settings value (`default_display_mode` for signed-in customers,
283
+ * `unauthenticated_display_mode` for guests).
284
+ */
285
+ resolveDisplayMode(input: {
286
+ productId: string;
287
+ organizationId: string | null;
288
+ salesChannelId: string;
289
+ customerKind: 'guest' | 'signed_in';
290
+ }): Promise<DisplayMode>;
291
+ /**
292
+ * The chain's answer with **no product in hand** — feature 086 / FR-016.
293
+ *
294
+ * A price ordering and a price range are refused where the page may not show
295
+ * prices at all, and `pricing.unauthenticated_display_mode = none` is the
296
+ * supported "hide prices until login" configuration. Deciding that needs the
297
+ * mode a *page* resolves to, which is the Organization → Settings tail of the
298
+ * FR-039 chain with the product and category steps deliberately absent.
299
+ *
300
+ * **The absence is the ruling, not a shortcut** (spec 086, clarification 2).
301
+ * A single product overridden to `none` keeps its position in a price
302
+ * ordering: a per-product override reads as "ask us for a quote" rather than
303
+ * "this price is secret", and withdrawing the whole control because one
304
+ * product opts out would make the sort appear and disappear as a buyer walks
305
+ * the catalogue. Moving those products to the tail instead is a change to
306
+ * this method's two omitted steps and to nothing else.
307
+ *
308
+ * The decision itself still goes through `decideDisplayMode`, so a page and a
309
+ * card cannot rank the organisation tier differently.
310
+ */
311
+ resolvePageDisplayMode(input: {
312
+ organizationId: string | null;
313
+ salesChannelId: string;
314
+ customerKind: 'guest' | 'signed_in';
315
+ }): Promise<DisplayMode>;
316
+ /**
317
+ * The same chain for a **set** of products (issue #132 follow-up).
318
+ *
319
+ * A catalogue listing asked this question once per product, which cost four
320
+ * to six queries per card on the page's hottest read. Every step is a set
321
+ * lookup — the product-scope overrides, the category memberships, the
322
+ * category-scope overrides, the one organization row and the one settings
323
+ * pair — so the whole page costs what a single product used to.
324
+ *
325
+ * The *decision* is not duplicated: both this method and `resolveDisplayMode`
326
+ * hand their four inputs to `decideDisplayMode`, so a batched page cannot
327
+ * rank an override differently from a product page. Only the loading differs.
328
+ *
329
+ * `categoryIdsByProduct` is an optional prefetch for a caller that has
330
+ * already read the memberships — `PricingService.resolveListingPrices` needs
331
+ * them for the application rules and would otherwise read the same table
332
+ * twice per page.
333
+ */
334
+ resolveDisplayModes(input: {
335
+ productIds: readonly string[];
336
+ organizationId: string | null;
337
+ salesChannelId: string;
338
+ customerKind: 'guest' | 'signed_in';
339
+ categoryIdsByProduct?: ReadonlyMap<string, ReadonlySet<string>>;
340
+ }): Promise<Map<string, DisplayMode>>;
341
+ /**
342
+ * `(product, category)` memberships for a set of products, read through
343
+ * `catalog`'s port (feature 075 / D-87).
344
+ *
345
+ * One call for the whole set, not one per product: the port takes the array
346
+ * for exactly this reason, and a page turning into a round trip per card is
347
+ * the regression this shape exists to prevent.
348
+ *
349
+ * **Structural, deliberately** — no `activeOnly`. The single-product path
350
+ * ranks the same memberships, and `evaluateApplicationRule`'s `category`
351
+ * criterion tests the raw membership, so narrowing to live categories here
352
+ * would make the display-mode chain and the rule that prices the product
353
+ * disagree about which categories a product is in.
354
+ *
355
+ * Every product asked about gets an entry, so an uncategorised product is an
356
+ * empty set rather than a missing key.
357
+ */
358
+ private loadCategoryMemberships;
359
+ /**
360
+ * Turn category-scope override rows into the chain's ranking inputs.
361
+ *
362
+ * `ancestorsOf` answers the category **and** its ancestors, nearest-first, so
363
+ * one port call replaces the `findOne` plus the parent-pointer loop that
364
+ * walked `catalog`'s table a level at a time. Depth is the chain length minus
365
+ * the category itself; an unknown id answers an empty chain and is dropped,
366
+ * which is what the old `continue` did.
367
+ */
368
+ private rankCategoryOverrides;
369
+ /**
370
+ * Validate that a polymorphic override target exists in the appropriate
371
+ * table. Throws 400 VALIDATION_FAILED on orphan target IDs (FR-038).
372
+ */
373
+ private assertOverrideTargetExists;
374
+ /**
375
+ * List the assigned products for a price list, with their per-currency
376
+ * brackets in `minQuantity` ascending order. Powers the admin Products
377
+ * tab and the linked-price-lists panel from US8.
378
+ */
379
+ listProducts(priceListId: string): Promise<Array<{
380
+ productId: string;
381
+ bracketsByCurrency: Record<string, BracketInput[]>;
382
+ }>>;
383
+ /**
384
+ * Idempotent append: assigns a single product to a price list. No-op when
385
+ * the assignment already exists. The list's `modifiedAt` is bumped only
386
+ * when the assignment is actually new.
387
+ */
388
+ addProduct(priceListId: string, productId: string): Promise<void>;
389
+ /**
390
+ * Removes a product's assignment + its bracket rows (cascade via FK).
391
+ * No-op when the assignment does not exist.
392
+ */
393
+ removeProduct(priceListId: string, productId: string): Promise<void>;
394
+ /**
395
+ * Bulk delta replacement of the product roster. Adds new pairs, removes
396
+ * pairs absent from the request. Returns the {added, removed, unchanged}
397
+ * counts. Cascade deletes brackets for removed pairs.
398
+ */
399
+ replaceProducts(priceListId: string, productIds: readonly string[], auditCtx?: PriceListsAuditContext): Promise<ReplaceProductsResult>;
400
+ /**
401
+ * Bulk replacement of bracket rows for one (list, product) pair across
402
+ * every currency in the request. Currencies absent from the input are
403
+ * cleared. Brackets are validated for:
404
+ * - assignment existence (404 when product is not in the list);
405
+ * - per-row sanity: minQuantity ≥ 1, maxQuantity ≥ minQuantity (when
406
+ * present), amount ≥ 0;
407
+ * - per-currency overlap freedom (FR-015).
408
+ *
409
+ * The whole save runs in one EM flush so a partial save is impossible.
410
+ */
411
+ replaceBrackets(priceListId: string, productId: string, bracketsByCurrency: Record<string, readonly BracketInput[]>, auditCtx?: PriceListsAuditContext): Promise<Record<string, BracketInput[]>>;
412
+ /**
413
+ * Convenience: copy one currency's brackets into other currencies for the
414
+ * same (list, product) pair. The target currencies' existing brackets (if
415
+ * any) are NOT cleared — this method appends. Conflicts on
416
+ * `(currency, minQuantity)` are refused via the PK constraint (caller
417
+ * should normally use this on currencies with no brackets yet, e.g. via
418
+ * the admin "Copy currency" affordance).
419
+ */
420
+ copyCurrencyBrackets(priceListId: string, productId: string, fromCurrency: string, toCurrencies: readonly string[]): Promise<CopyCurrencyResult>;
421
+ /**
422
+ * Per-row bracket sanity (FR-014, FR-015).
423
+ */
424
+ private assertBracketSanity;
425
+ /**
426
+ * Overlap-freedom within a currency series (FR-015). Assumes the input is
427
+ * sorted ascending by `minQuantity`.
428
+ */
429
+ private assertNoOverlap;
430
+ }
431
+ //# sourceMappingURL=price-list-service.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"price-list-service.d.ts","sourceRoot":"","sources":["../../../src/backend/services/price-list-service.ts"],"names":[],"mappings":"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"}