@endora-commerce/mod-carts 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.
- package/LICENSE +21 -0
- package/README.md +62 -0
- package/dist/admin/components/CartApprovalPolicyPanel.d.ts +51 -0
- package/dist/admin/components/CartApprovalPolicyPanel.d.ts.map +1 -0
- package/dist/admin/components/CartApprovalPolicyPanel.js +59 -0
- package/dist/admin/components/CartApprovalPolicyPanel.js.map +1 -0
- package/dist/admin/index.d.ts +38 -0
- package/dist/admin/index.d.ts.map +1 -0
- package/dist/admin/index.js +73 -0
- package/dist/admin/index.js.map +1 -0
- package/dist/admin/pages/CartDetail.d.ts +3 -0
- package/dist/admin/pages/CartDetail.d.ts.map +1 -0
- package/dist/admin/pages/CartDetail.js +74 -0
- package/dist/admin/pages/CartDetail.js.map +1 -0
- package/dist/admin/pages/CartsList.d.ts +3 -0
- package/dist/admin/pages/CartsList.d.ts.map +1 -0
- package/dist/admin/pages/CartsList.js +90 -0
- package/dist/admin/pages/CartsList.js.map +1 -0
- package/dist/admin/zones/CartApprovalPolicy.d.ts +29 -0
- package/dist/admin/zones/CartApprovalPolicy.d.ts.map +1 -0
- package/dist/admin/zones/CartApprovalPolicy.js +11 -0
- package/dist/admin/zones/CartApprovalPolicy.js.map +1 -0
- package/dist/backend/cli/abandonment-sweep.d.ts +64 -0
- package/dist/backend/cli/abandonment-sweep.d.ts.map +1 -0
- package/dist/backend/cli/abandonment-sweep.js +17 -0
- package/dist/backend/cli/abandonment-sweep.js.map +1 -0
- package/dist/backend/entities/cart-audit-entry.entity.d.ts +29 -0
- package/dist/backend/entities/cart-audit-entry.entity.d.ts.map +1 -0
- package/dist/backend/entities/cart-audit-entry.entity.js +109 -0
- package/dist/backend/entities/cart-audit-entry.entity.js.map +1 -0
- package/dist/backend/entities/cart-item.entity.d.ts +42 -0
- package/dist/backend/entities/cart-item.entity.d.ts.map +1 -0
- package/dist/backend/entities/cart-item.entity.js +119 -0
- package/dist/backend/entities/cart-item.entity.js.map +1 -0
- package/dist/backend/entities/cart.entity.d.ts +96 -0
- package/dist/backend/entities/cart.entity.d.ts.map +1 -0
- package/dist/backend/entities/cart.entity.js +207 -0
- package/dist/backend/entities/cart.entity.js.map +1 -0
- package/dist/backend/index.d.ts +122 -0
- package/dist/backend/index.d.ts.map +1 -0
- package/dist/backend/index.js +184 -0
- package/dist/backend/index.js.map +1 -0
- package/dist/backend/routes.admin.d.ts +31 -0
- package/dist/backend/routes.admin.d.ts.map +1 -0
- package/dist/backend/routes.admin.js +95 -0
- package/dist/backend/routes.admin.js.map +1 -0
- package/dist/backend/routes.d.ts +101 -0
- package/dist/backend/routes.d.ts.map +1 -0
- package/dist/backend/routes.js +620 -0
- package/dist/backend/routes.js.map +1 -0
- package/dist/backend/routes.organization.d.ts +29 -0
- package/dist/backend/routes.organization.d.ts.map +1 -0
- package/dist/backend/routes.organization.js +150 -0
- package/dist/backend/routes.organization.js.map +1 -0
- package/dist/backend/services/cart-abandonment-settings.d.ts +34 -0
- package/dist/backend/services/cart-abandonment-settings.d.ts.map +1 -0
- package/dist/backend/services/cart-abandonment-settings.js +55 -0
- package/dist/backend/services/cart-abandonment-settings.js.map +1 -0
- package/dist/backend/services/cart-abandonment-worker.d.ts +110 -0
- package/dist/backend/services/cart-abandonment-worker.d.ts.map +1 -0
- package/dist/backend/services/cart-abandonment-worker.js +185 -0
- package/dist/backend/services/cart-abandonment-worker.js.map +1 -0
- package/dist/backend/services/cart-admin-service.d.ts +58 -0
- package/dist/backend/services/cart-admin-service.d.ts.map +1 -0
- package/dist/backend/services/cart-admin-service.js +397 -0
- package/dist/backend/services/cart-admin-service.js.map +1 -0
- package/dist/backend/services/cart-approval-service.d.ts +147 -0
- package/dist/backend/services/cart-approval-service.d.ts.map +1 -0
- package/dist/backend/services/cart-approval-service.js +242 -0
- package/dist/backend/services/cart-approval-service.js.map +1 -0
- package/dist/backend/services/cart-audit-service.d.ts +75 -0
- package/dist/backend/services/cart-audit-service.d.ts.map +1 -0
- package/dist/backend/services/cart-audit-service.js +70 -0
- package/dist/backend/services/cart-audit-service.js.map +1 -0
- package/dist/backend/services/cart-conversion-service.d.ts +104 -0
- package/dist/backend/services/cart-conversion-service.d.ts.map +1 -0
- package/dist/backend/services/cart-conversion-service.js +175 -0
- package/dist/backend/services/cart-conversion-service.js.map +1 -0
- package/dist/backend/services/cart-coupon-service.d.ts +129 -0
- package/dist/backend/services/cart-coupon-service.d.ts.map +1 -0
- package/dist/backend/services/cart-coupon-service.js +244 -0
- package/dist/backend/services/cart-coupon-service.js.map +1 -0
- package/dist/backend/services/cart-organization-visibility-service.d.ts +43 -0
- package/dist/backend/services/cart-organization-visibility-service.d.ts.map +1 -0
- package/dist/backend/services/cart-organization-visibility-service.js +98 -0
- package/dist/backend/services/cart-organization-visibility-service.js.map +1 -0
- package/dist/backend/services/cart-placement-apply-port.d.ts +38 -0
- package/dist/backend/services/cart-placement-apply-port.d.ts.map +1 -0
- package/dist/backend/services/cart-placement-apply-port.js +71 -0
- package/dist/backend/services/cart-placement-apply-port.js.map +1 -0
- package/dist/backend/services/cart-pricing-recompute.d.ts +62 -0
- package/dist/backend/services/cart-pricing-recompute.d.ts.map +1 -0
- package/dist/backend/services/cart-pricing-recompute.js +131 -0
- package/dist/backend/services/cart-pricing-recompute.js.map +1 -0
- package/dist/backend/services/cart-query-service.d.ts +29 -0
- package/dist/backend/services/cart-query-service.d.ts.map +1 -0
- package/dist/backend/services/cart-query-service.js +40 -0
- package/dist/backend/services/cart-query-service.js.map +1 -0
- package/dist/backend/services/cart-read-port.d.ts +40 -0
- package/dist/backend/services/cart-read-port.d.ts.map +1 -0
- package/dist/backend/services/cart-read-port.js +144 -0
- package/dist/backend/services/cart-read-port.js.map +1 -0
- package/dist/backend/services/cart-recompute-cache.d.ts +49 -0
- package/dist/backend/services/cart-recompute-cache.d.ts.map +1 -0
- package/dist/backend/services/cart-recompute-cache.js +56 -0
- package/dist/backend/services/cart-recompute-cache.js.map +1 -0
- package/dist/backend/services/cart-service.d.ts +165 -0
- package/dist/backend/services/cart-service.d.ts.map +1 -0
- package/dist/backend/services/cart-service.js +556 -0
- package/dist/backend/services/cart-service.js.map +1 -0
- package/dist/backend/services/cart-state-machine.d.ts +51 -0
- package/dist/backend/services/cart-state-machine.d.ts.map +1 -0
- package/dist/backend/services/cart-state-machine.js +74 -0
- package/dist/backend/services/cart-state-machine.js.map +1 -0
- package/dist/backend/services/cart-upsell-service.d.ts +57 -0
- package/dist/backend/services/cart-upsell-service.d.ts.map +1 -0
- package/dist/backend/services/cart-upsell-service.js +100 -0
- package/dist/backend/services/cart-upsell-service.js.map +1 -0
- package/dist/backend/services/customer-group-resolver.d.ts +27 -0
- package/dist/backend/services/customer-group-resolver.d.ts.map +1 -0
- package/dist/backend/services/customer-group-resolver.js +32 -0
- package/dist/backend/services/customer-group-resolver.js.map +1 -0
- package/dist/manifest.d.ts +221 -0
- package/dist/manifest.d.ts.map +1 -0
- package/dist/manifest.js +224 -0
- package/dist/manifest.js.map +1 -0
- package/dist/migrations/20260611T140352_carts_consolidation.d.ts +43 -0
- package/dist/migrations/20260611T140352_carts_consolidation.d.ts.map +1 -0
- package/dist/migrations/20260611T140352_carts_consolidation.js +237 -0
- package/dist/migrations/20260611T140352_carts_consolidation.js.map +1 -0
- package/dist/migrations/20260611T140413_carts_cart_item_packaging.d.ts +12 -0
- package/dist/migrations/20260611T140413_carts_cart_item_packaging.d.ts.map +1 -0
- package/dist/migrations/20260611T140413_carts_cart_item_packaging.js +20 -0
- package/dist/migrations/20260611T140413_carts_cart_item_packaging.js.map +1 -0
- package/dist/migrations/20260818T081253_carts_cart_completed_order_fk.d.ts +50 -0
- package/dist/migrations/20260818T081253_carts_cart_completed_order_fk.d.ts.map +1 -0
- package/dist/migrations/20260818T081253_carts_cart_completed_order_fk.js +62 -0
- package/dist/migrations/20260818T081253_carts_cart_completed_order_fk.js.map +1 -0
- package/dist/migrations/20260830T112911_carts_organization_attribution_check.d.ts +67 -0
- package/dist/migrations/20260830T112911_carts_organization_attribution_check.d.ts.map +1 -0
- package/dist/migrations/20260830T112911_carts_organization_attribution_check.js +121 -0
- package/dist/migrations/20260830T112911_carts_organization_attribution_check.js.map +1 -0
- package/dist/migrations/index.d.ts +30 -0
- package/dist/migrations/index.d.ts.map +1 -0
- package/dist/migrations/index.js +35 -0
- package/dist/migrations/index.js.map +1 -0
- package/dist/ports/index.d.ts +106 -0
- package/dist/ports/index.d.ts.map +1 -0
- package/dist/ports/index.js +2 -0
- package/dist/ports/index.js.map +1 -0
- package/docs/carts.md +232 -0
- package/i18n/en.json +96 -0
- package/i18n/pl.json +96 -0
- package/package.json +107 -0
- package/tailwind.css +14 -0
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
2
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
3
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
4
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
5
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
6
|
+
};
|
|
7
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
8
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
9
|
+
};
|
|
10
|
+
import { Entity, Index, OptionalProps, PrimaryKey, Property, Unique } from '@mikro-orm/core';
|
|
11
|
+
import { CustomerScoped } from '@endora-commerce/platform/tenancy';
|
|
12
|
+
import { randomUUID } from 'crypto';
|
|
13
|
+
/**
|
|
14
|
+
* Cart — a buyer's in-progress basket. Owned by a Customer (authenticated)
|
|
15
|
+
* or an anonymous session (cookie-token addressable). Scoped to a Sales
|
|
16
|
+
* Channel (feature 027) so the spec's "one active cart per
|
|
17
|
+
* (Customer, Sales Channel)" rule holds.
|
|
18
|
+
*
|
|
19
|
+
* Status lifecycle (feature 027):
|
|
20
|
+
* active → abandoned (sweep: last_activity_at past threshold)
|
|
21
|
+
* abandoned → active (owner activity)
|
|
22
|
+
* active → completed (checkout success OR cart→QR conversion)
|
|
23
|
+
* active → rejected (org-admin reject OR platform-admin reject)
|
|
24
|
+
*
|
|
25
|
+
* Legacy `converted` was migrated to `completed` by migration 050. Mass
|
|
26
|
+
* code in the repo that previously wrote `'converted'` now writes
|
|
27
|
+
* `'completed'` (CartService.clearForCustomer).
|
|
28
|
+
*
|
|
29
|
+
* `approval_status` is the orthogonal sub-state that gates checkout when
|
|
30
|
+
* the Organization's `requires_cart_approval` policy is `true`. Self-
|
|
31
|
+
* approval exemption: a cart created by an Org Admin is born with
|
|
32
|
+
* `approval_status='not_required'` regardless of the policy. Post-approval
|
|
33
|
+
* mutation re-arms `approved → pending` (see CartApprovalService).
|
|
34
|
+
*
|
|
35
|
+
* `version` is the optimistic-lock token used by the approval / mutation
|
|
36
|
+
* race (buyer-vs-Org-Admin) — aligned with the convention shared by
|
|
37
|
+
* features 003 / 026.
|
|
38
|
+
*/
|
|
39
|
+
let Cart = class Cart {
|
|
40
|
+
[OptionalProps];
|
|
41
|
+
id = randomUUID();
|
|
42
|
+
customerAccountId;
|
|
43
|
+
organizationId;
|
|
44
|
+
anonymousCartToken;
|
|
45
|
+
/**
|
|
46
|
+
* Sales channel the cart is scoped to. Backfilled to the system-default
|
|
47
|
+
* channel by migration 050; NULL is read as "system default" until the
|
|
48
|
+
* next consolidation tightens it (see research.md §R3).
|
|
49
|
+
*/
|
|
50
|
+
salesChannelId;
|
|
51
|
+
status = 'active';
|
|
52
|
+
approvalStatus = 'not_required';
|
|
53
|
+
submittedForApprovalAt;
|
|
54
|
+
approvedAt;
|
|
55
|
+
approvedByCustomerAccountId;
|
|
56
|
+
rejectedAt;
|
|
57
|
+
/** Free-form `customer:<uuid>` / `admin:<uuid>` / `org_admin:<uuid>`. */
|
|
58
|
+
rejectedByActor;
|
|
59
|
+
rejectedReason;
|
|
60
|
+
/**
|
|
61
|
+
* The Promotion.code the buyer most recently applied to this cart. The
|
|
62
|
+
* resolver in PromotionService.applyToCart consumes this on every read.
|
|
63
|
+
* Persisted even on terminal carts for audit / analytics.
|
|
64
|
+
*/
|
|
65
|
+
appliedPromotionCode;
|
|
66
|
+
/**
|
|
67
|
+
* The order this cart produced, set by `placeOrder` beside
|
|
68
|
+
* `status = 'completed'` and inside the placement transaction (D-94.1).
|
|
69
|
+
*
|
|
70
|
+
* The twin of {@link convertedToQuoteRequestId}: the two terminal artefacts
|
|
71
|
+
* a cart can leave behind, and until D-94 only one of them was recorded —
|
|
72
|
+
* asked which order emptied a completed cart, the platform answered by
|
|
73
|
+
* correlating timestamps. `carts_completed_order_fk` holds it
|
|
74
|
+
* (`on delete set null`), for the reason the QR pointer's migration wrote
|
|
75
|
+
* down for its own: deleting the order does not invalidate the fact that
|
|
76
|
+
* the cart was once completed.
|
|
77
|
+
*
|
|
78
|
+
* Nullable, and it stays nullable. It cannot be backfilled — no surviving
|
|
79
|
+
* record says which order emptied which historical cart — and
|
|
80
|
+
* `status = 'completed'` does not imply it: `CartService.clearForCustomer`,
|
|
81
|
+
* the anonymous-merge source and the quote-request conversion all reach
|
|
82
|
+
* `completed` without an order.
|
|
83
|
+
*/
|
|
84
|
+
completedOrderId;
|
|
85
|
+
/** Set on Cart → Quote Request conversion (feature 027 US3). */
|
|
86
|
+
convertedToQuoteRequestId;
|
|
87
|
+
/**
|
|
88
|
+
* Idempotency stamp for the abandonment-sweep notification. Cleared on
|
|
89
|
+
* reactivation so the next abandonment cycle can notify again.
|
|
90
|
+
*/
|
|
91
|
+
abandonmentNotifiedAt;
|
|
92
|
+
/**
|
|
93
|
+
* Bumped by every buyer-driven add / remove / qty / coupon / explicit
|
|
94
|
+
* page-open. Drives the abandonment sweep. NOT bumped by mini-cart
|
|
95
|
+
* hovers or non-owner inspections (Org-Admin / platform-admin reads).
|
|
96
|
+
*/
|
|
97
|
+
lastActivityAt = new Date();
|
|
98
|
+
/** Optimistic-lock token (auto-incremented by MikroORM on every update). */
|
|
99
|
+
version;
|
|
100
|
+
createdAt = new Date();
|
|
101
|
+
updatedAt = new Date();
|
|
102
|
+
};
|
|
103
|
+
__decorate([
|
|
104
|
+
PrimaryKey({ type: 'uuid' }),
|
|
105
|
+
__metadata("design:type", String)
|
|
106
|
+
], Cart.prototype, "id", void 0);
|
|
107
|
+
__decorate([
|
|
108
|
+
Property({ type: 'uuid', nullable: true }),
|
|
109
|
+
Index(),
|
|
110
|
+
__metadata("design:type", Object)
|
|
111
|
+
], Cart.prototype, "customerAccountId", void 0);
|
|
112
|
+
__decorate([
|
|
113
|
+
Property({ type: 'uuid', nullable: true }),
|
|
114
|
+
Index(),
|
|
115
|
+
__metadata("design:type", Object)
|
|
116
|
+
], Cart.prototype, "organizationId", void 0);
|
|
117
|
+
__decorate([
|
|
118
|
+
Property({ type: 'string', length: 64, nullable: true }),
|
|
119
|
+
Unique(),
|
|
120
|
+
__metadata("design:type", Object)
|
|
121
|
+
], Cart.prototype, "anonymousCartToken", void 0);
|
|
122
|
+
__decorate([
|
|
123
|
+
Property({ type: 'uuid', nullable: true }),
|
|
124
|
+
__metadata("design:type", Object)
|
|
125
|
+
], Cart.prototype, "salesChannelId", void 0);
|
|
126
|
+
__decorate([
|
|
127
|
+
Property({ type: 'string', length: 16 }),
|
|
128
|
+
__metadata("design:type", String)
|
|
129
|
+
], Cart.prototype, "status", void 0);
|
|
130
|
+
__decorate([
|
|
131
|
+
Property({ type: 'string', length: 32 }),
|
|
132
|
+
__metadata("design:type", String)
|
|
133
|
+
], Cart.prototype, "approvalStatus", void 0);
|
|
134
|
+
__decorate([
|
|
135
|
+
Property({ type: 'datetime', nullable: true }),
|
|
136
|
+
__metadata("design:type", Object)
|
|
137
|
+
], Cart.prototype, "submittedForApprovalAt", void 0);
|
|
138
|
+
__decorate([
|
|
139
|
+
Property({ type: 'datetime', nullable: true }),
|
|
140
|
+
__metadata("design:type", Object)
|
|
141
|
+
], Cart.prototype, "approvedAt", void 0);
|
|
142
|
+
__decorate([
|
|
143
|
+
Property({ type: 'uuid', nullable: true }),
|
|
144
|
+
__metadata("design:type", Object)
|
|
145
|
+
], Cart.prototype, "approvedByCustomerAccountId", void 0);
|
|
146
|
+
__decorate([
|
|
147
|
+
Property({ type: 'datetime', nullable: true }),
|
|
148
|
+
__metadata("design:type", Object)
|
|
149
|
+
], Cart.prototype, "rejectedAt", void 0);
|
|
150
|
+
__decorate([
|
|
151
|
+
Property({ type: 'string', length: 48, nullable: true }),
|
|
152
|
+
__metadata("design:type", Object)
|
|
153
|
+
], Cart.prototype, "rejectedByActor", void 0);
|
|
154
|
+
__decorate([
|
|
155
|
+
Property({ type: 'text', nullable: true }),
|
|
156
|
+
__metadata("design:type", Object)
|
|
157
|
+
], Cart.prototype, "rejectedReason", void 0);
|
|
158
|
+
__decorate([
|
|
159
|
+
Property({ type: 'string', length: 64, nullable: true }),
|
|
160
|
+
__metadata("design:type", Object)
|
|
161
|
+
], Cart.prototype, "appliedPromotionCode", void 0);
|
|
162
|
+
__decorate([
|
|
163
|
+
Property({ type: 'uuid', nullable: true }),
|
|
164
|
+
__metadata("design:type", Object)
|
|
165
|
+
], Cart.prototype, "completedOrderId", void 0);
|
|
166
|
+
__decorate([
|
|
167
|
+
Property({ type: 'uuid', nullable: true }),
|
|
168
|
+
__metadata("design:type", Object)
|
|
169
|
+
], Cart.prototype, "convertedToQuoteRequestId", void 0);
|
|
170
|
+
__decorate([
|
|
171
|
+
Property({ type: 'datetime', nullable: true }),
|
|
172
|
+
__metadata("design:type", Object)
|
|
173
|
+
], Cart.prototype, "abandonmentNotifiedAt", void 0);
|
|
174
|
+
__decorate([
|
|
175
|
+
Property({ type: 'datetime' }),
|
|
176
|
+
__metadata("design:type", Date)
|
|
177
|
+
], Cart.prototype, "lastActivityAt", void 0);
|
|
178
|
+
__decorate([
|
|
179
|
+
Property({ type: 'integer', version: true }),
|
|
180
|
+
__metadata("design:type", Number)
|
|
181
|
+
], Cart.prototype, "version", void 0);
|
|
182
|
+
__decorate([
|
|
183
|
+
Property({ type: 'datetime', onCreate: () => new Date() }),
|
|
184
|
+
__metadata("design:type", Date)
|
|
185
|
+
], Cart.prototype, "createdAt", void 0);
|
|
186
|
+
__decorate([
|
|
187
|
+
Property({ type: 'datetime', onUpdate: () => new Date() }),
|
|
188
|
+
__metadata("design:type", Date)
|
|
189
|
+
], Cart.prototype, "updatedAt", void 0);
|
|
190
|
+
Cart = __decorate([
|
|
191
|
+
CustomerScoped(),
|
|
192
|
+
Entity({ tableName: 'carts' })
|
|
193
|
+
], Cart);
|
|
194
|
+
export { Cart };
|
|
195
|
+
export const CART_STATUSES = [
|
|
196
|
+
'active',
|
|
197
|
+
'abandoned',
|
|
198
|
+
'completed',
|
|
199
|
+
'rejected',
|
|
200
|
+
];
|
|
201
|
+
export const CART_APPROVAL_STATUSES = [
|
|
202
|
+
'not_required',
|
|
203
|
+
'pending',
|
|
204
|
+
'approved',
|
|
205
|
+
'rejected_by_org_admin',
|
|
206
|
+
];
|
|
207
|
+
//# sourceMappingURL=cart.entity.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cart.entity.js","sourceRoot":"","sources":["../../../src/backend/entities/cart.entity.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
import type { EntityManager } from '@mikro-orm/postgresql';
|
|
2
|
+
import type { Redis } from 'ioredis';
|
|
3
|
+
import type { AuditPort } from '@endora-commerce/platform/kernel';
|
|
4
|
+
import type { CatalogProductReadPort, CustomerAccountReadPort, LinePricePort, OrganizationDetailsPort, PromotionApplyPort, PromotionCodePort, QuoteRequestReadPort, RfqCustomerPort } from '@endora-commerce/contracts';
|
|
5
|
+
import type { ModuleContext } from '@endora-commerce/platform/kernel';
|
|
6
|
+
import type { OrganizationReadPort } from '@endora-commerce/platform/kernel';
|
|
7
|
+
import type { RequireAdminFactory } from '@endora-commerce/platform/kernel';
|
|
8
|
+
import type { SettingsReadPort } from '@endora-commerce/platform/kernel';
|
|
9
|
+
import { CartService } from './services/cart-service.js';
|
|
10
|
+
import { CartAuditService } from './services/cart-audit-service.js';
|
|
11
|
+
import { CartApprovalService } from './services/cart-approval-service.js';
|
|
12
|
+
import { CartRecomputeCache } from './services/cart-recompute-cache.js';
|
|
13
|
+
import { CartAbandonmentWorker } from './services/cart-abandonment-worker.js';
|
|
14
|
+
import { type CartsDeps } from './routes.js';
|
|
15
|
+
import { CartAuditEntry } from './entities/cart-audit-entry.entity.js';
|
|
16
|
+
import { CartItem } from './entities/cart-item.entity.js';
|
|
17
|
+
import { Cart } from './entities/cart.entity.js';
|
|
18
|
+
/**
|
|
19
|
+
* `carts` — the module that owned 4593 lines and registered none of them
|
|
20
|
+
* (feature 072, wave 3, T136).
|
|
21
|
+
*
|
|
22
|
+
* Every service here was constructed inside `orders/plugin.ts`, and most of them
|
|
23
|
+
* **conditionally**: `options.auditLogService ? new CartAuditService(…) :
|
|
24
|
+
* undefined`, and so on down a chain where each `undefined` disabled the next
|
|
25
|
+
* thing. That made feature availability a function of which arguments a
|
|
26
|
+
* composition root happened to pass, which is the defect T141's task text names
|
|
27
|
+
* for `orders` and which `languages` produced in wave 1 as a live bug.
|
|
28
|
+
*
|
|
29
|
+
* The stake was not theoretical. Without `CartRecomputeCache` there is no
|
|
30
|
+
* `CartPricingRecompute`, so every full-cart read returns the snapshotted
|
|
31
|
+
* `unit_price` instead of a re-resolved engine price. Without `CartAuditService`
|
|
32
|
+
* there is no `CartApprovalService`, so the organization approval routes never
|
|
33
|
+
* registered at all — the route *surface* was a function of arguments, the same
|
|
34
|
+
* finding `shopping_lists` produced in T133.
|
|
35
|
+
*
|
|
36
|
+
* All thirteen registrations are unconditional now. `auditLogService` and
|
|
37
|
+
* `redis` are kernel-owned names, so there is nothing left to branch on.
|
|
38
|
+
*
|
|
39
|
+
* **`cartService` is a port, and the outward edge is a different one.** Four
|
|
40
|
+
* modules read the cart service — `orders`, `shopping_lists`, `quick_order` and
|
|
41
|
+
* this module's own routes — and all four sit downstream in the manifest graph,
|
|
42
|
+
* so it is an ordinary `providePort`. What points *outward* is
|
|
43
|
+
* `pushLineToShoppingList` / `appendShoppingListToCart`: `carts` reaching into
|
|
44
|
+
* `shopping_lists`, which cannot be a port because `shopping_lists → orders →
|
|
45
|
+
* carts` would close a cycle. That is {@link CartsCradle.cartShoppingListBridge}
|
|
46
|
+
* — a contribution point **this module owns**, defaulted to a refusal naming the
|
|
47
|
+
* absent module, which is the direction `shipmentEmailSender` uses and the
|
|
48
|
+
* mirror image of the `shoppingListServiceSink` this conversion retires.
|
|
49
|
+
*
|
|
50
|
+
* The `RfqService` `Proxy` that lived in `orders/plugin.ts` is gone with it:
|
|
51
|
+
* it existed only to late-bind a service that `quote_requests` has provided as
|
|
52
|
+
* a real port since T132.
|
|
53
|
+
*
|
|
54
|
+
* The two abandonment settings are read here, through the settings port, rather
|
|
55
|
+
* than resolved by each root. They are `carts.abandonment.*` — this module's own
|
|
56
|
+
* knobs — and the identical try/catch-to-default stood in both compositions.
|
|
57
|
+
*/
|
|
58
|
+
/**
|
|
59
|
+
* How this composition reaches `shopping_lists`, which `carts` may not import.
|
|
60
|
+
*
|
|
61
|
+
* Both shapes are taken from the route module's own option types rather than
|
|
62
|
+
* restated, so a change there is a type error here instead of a drift.
|
|
63
|
+
*/
|
|
64
|
+
export interface CartShoppingListBridge {
|
|
65
|
+
readonly pushLineToShoppingList: NonNullable<CartsDeps['pushLineToShoppingList']>;
|
|
66
|
+
readonly appendShoppingListToCart: NonNullable<CartsDeps['appendShoppingListToCart']>;
|
|
67
|
+
}
|
|
68
|
+
/** What `carts` resolves from the container, and the names it owns. */
|
|
69
|
+
export interface CartsCradle {
|
|
70
|
+
readonly emFactory: () => EntityManager;
|
|
71
|
+
readonly auditLogService: AuditPort;
|
|
72
|
+
readonly redis: Redis;
|
|
73
|
+
readonly requireAdmin: RequireAdminFactory;
|
|
74
|
+
readonly settingsReadPort: SettingsReadPort;
|
|
75
|
+
/**
|
|
76
|
+
* Feature 075, Phase C — the six ports every service here used to reach by
|
|
77
|
+
* importing another module's class or entity. Each is a contract type from
|
|
78
|
+
* `@endora-commerce/contracts`, never the provider's class, and each is resolved lazily
|
|
79
|
+
* by a string literal so a switched-off owner answers at the call.
|
|
80
|
+
*/
|
|
81
|
+
readonly pricingService: LinePricePort;
|
|
82
|
+
readonly promotionService: PromotionApplyPort;
|
|
83
|
+
readonly promotionCodePort: PromotionCodePort;
|
|
84
|
+
readonly rfqService: RfqCustomerPort;
|
|
85
|
+
readonly quoteRequestReadPort: QuoteRequestReadPort;
|
|
86
|
+
readonly catalogProductReadPort: CatalogProductReadPort;
|
|
87
|
+
readonly customerAccountReadPort: CustomerAccountReadPort;
|
|
88
|
+
readonly organizationDetailsPort: OrganizationDetailsPort;
|
|
89
|
+
/** Root-shaped: production reads `request.actor`, the harness `request.testActor`. */
|
|
90
|
+
readonly cartActorResolver: CartsDeps['resolveCartActor'];
|
|
91
|
+
/**
|
|
92
|
+
* The tenancy read port (T138). Was `organizationTransactGuard`, a closure
|
|
93
|
+
* each root wrote over `OrganizationContextService` — and which the harness
|
|
94
|
+
* registered as `async () => undefined`, so feature 026's rule that an
|
|
95
|
+
* unapproved Organization may not transact was enforced in production and by
|
|
96
|
+
* no test at all.
|
|
97
|
+
*/
|
|
98
|
+
readonly organizationReadPort: OrganizationReadPort;
|
|
99
|
+
/** Contribution point: absent means save-to-list and list-to-cart refuse. */
|
|
100
|
+
readonly cartShoppingListBridge: CartShoppingListBridge;
|
|
101
|
+
/** Contribution point: absent means the sweep flips status and sends nothing. */
|
|
102
|
+
readonly cartAbandonmentNotifier: ConstructorParameters<typeof CartAbandonmentWorker>[0]['dispatchNotification'] | undefined;
|
|
103
|
+
readonly cartService: CartService;
|
|
104
|
+
readonly cartAuditService: CartAuditService;
|
|
105
|
+
readonly cartApprovalService: CartApprovalService;
|
|
106
|
+
readonly cartRecomputeCache: CartRecomputeCache;
|
|
107
|
+
readonly cartAbandonmentWorker: CartAbandonmentWorker;
|
|
108
|
+
}
|
|
109
|
+
export declare function registerModule(ctx: ModuleContext): void;
|
|
110
|
+
/**
|
|
111
|
+
* The module's persisted entity classes, on the `./backend` subpath, as one
|
|
112
|
+
* array and **no named class export** (D-168).
|
|
113
|
+
*
|
|
114
|
+
* This is the shape the platform reads when the package is *installed*: the
|
|
115
|
+
* boot-time loader (`src/packages/package-runtime.ts`, `exported['entities']`)
|
|
116
|
+
* and the static declaration reader (`scripts/lib/package-declarations.ts`),
|
|
117
|
+
* which is the third source of `check:module-boundary`'s `table→owner` map and
|
|
118
|
+
* the package pass of `check-entity-tenant-classification`. A missing array is
|
|
119
|
+
* answered with `[]` — zero entities registered, no error anywhere.
|
|
120
|
+
*/
|
|
121
|
+
export declare const entities: (typeof Cart | typeof CartItem | typeof CartAuditEntry)[];
|
|
122
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/backend/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
import { ERROR_CODES } from '@endora-commerce/contracts';
|
|
2
|
+
import { HttpError } from '@endora-commerce/platform/http';
|
|
3
|
+
import { lazyPort } from '@endora-commerce/platform/kernel';
|
|
4
|
+
import { abandonmentSettingsReaders } from './services/cart-abandonment-settings.js';
|
|
5
|
+
import { CartQueryService } from './services/cart-query-service.js';
|
|
6
|
+
import { CartPlacementApplyService } from './services/cart-placement-apply-port.js';
|
|
7
|
+
import { CartReadService, createCartWritePort } from './services/cart-read-port.js';
|
|
8
|
+
import { CartService } from './services/cart-service.js';
|
|
9
|
+
import { CartUpsellService } from './services/cart-upsell-service.js';
|
|
10
|
+
import { CartCouponService } from './services/cart-coupon-service.js';
|
|
11
|
+
import { CartConversionService } from './services/cart-conversion-service.js';
|
|
12
|
+
import { CartAdminService } from './services/cart-admin-service.js';
|
|
13
|
+
import { CartAuditService } from './services/cart-audit-service.js';
|
|
14
|
+
import { CartApprovalService } from './services/cart-approval-service.js';
|
|
15
|
+
import { CartOrganizationVisibilityService } from './services/cart-organization-visibility-service.js';
|
|
16
|
+
import { CartRecomputeCache } from './services/cart-recompute-cache.js';
|
|
17
|
+
import { CartPricingRecompute } from './services/cart-pricing-recompute.js';
|
|
18
|
+
import { CartAbandonmentWorker } from './services/cart-abandonment-worker.js';
|
|
19
|
+
import { registerCartRoutes } from './routes.js';
|
|
20
|
+
import { registerCartsAdminRoutes } from './routes.admin.js';
|
|
21
|
+
import { registerCartsOrganizationRoutes } from './routes.organization.js';
|
|
22
|
+
import { CartAuditEntry } from './entities/cart-audit-entry.entity.js';
|
|
23
|
+
import { CartItem } from './entities/cart-item.entity.js';
|
|
24
|
+
import { Cart } from './entities/cart.entity.js';
|
|
25
|
+
/** Refuses in the shape Constitution XVII item 3 requires: an explicit 503. */
|
|
26
|
+
function refuseShoppingList() {
|
|
27
|
+
const refuse = async () => {
|
|
28
|
+
throw new HttpError(503, ERROR_CODES.MODULE_DISABLED, 'Shopping lists are not available in this deployment.', { module: 'shopping_lists' });
|
|
29
|
+
};
|
|
30
|
+
return { pushLineToShoppingList: refuse, appendShoppingListToCart: refuse };
|
|
31
|
+
}
|
|
32
|
+
export function registerModule(ctx) {
|
|
33
|
+
ctx.di.register({
|
|
34
|
+
// Contribution point, defaulted to a refusal that names the absent module
|
|
35
|
+
// rather than a 404 that does not.
|
|
36
|
+
cartShoppingListBridge: ctx
|
|
37
|
+
.asFunction(() => refuseShoppingList())
|
|
38
|
+
.singleton(),
|
|
39
|
+
// Contribution point: a deployment with no outbound mail flips the cart's
|
|
40
|
+
// status and sends nothing, which is a coherent state.
|
|
41
|
+
cartAbandonmentNotifier: ctx
|
|
42
|
+
.asFunction(() => undefined)
|
|
43
|
+
.singleton(),
|
|
44
|
+
cartRecomputeCache: ctx
|
|
45
|
+
.asFunction(({ redis }) => new CartRecomputeCache(redis))
|
|
46
|
+
.singleton(),
|
|
47
|
+
cartAuditService: ctx
|
|
48
|
+
.asFunction(({ emFactory, auditLogService }) => new CartAuditService(emFactory, auditLogService))
|
|
49
|
+
.singleton(),
|
|
50
|
+
cartApprovalService: ctx
|
|
51
|
+
.asFunction(({ emFactory, cartAuditService }) => new CartApprovalService(emFactory, cartAuditService, lazyPort(ctx, 'organizationDetailsPort'), lazyPort(ctx, 'organizationCartApprovalWritePort'), lazyPort(ctx, 'customerAccountReadPort')))
|
|
52
|
+
.singleton(),
|
|
53
|
+
cartAbandonmentWorker: ctx
|
|
54
|
+
.asFunction(({ emFactory, cartAuditService }) => new CartAbandonmentWorker({
|
|
55
|
+
emFactory,
|
|
56
|
+
cartAuditService,
|
|
57
|
+
/**
|
|
58
|
+
* This module's own settings, read through the port it holds — the
|
|
59
|
+
* identical try/catch-to-default stood in both roots before T136,
|
|
60
|
+
* and in the ops CLI until issue #54. It lives in one file now
|
|
61
|
+
* (`services/cart-abandonment-settings.ts`), which also carries the
|
|
62
|
+
* D-41/D-43 history of what these two reads used to get wrong.
|
|
63
|
+
*
|
|
64
|
+
* The thunk is what keeps the port read lazy: a gate captured into
|
|
65
|
+
* this singleton would keep answering after `settings` is switched
|
|
66
|
+
* off.
|
|
67
|
+
*/
|
|
68
|
+
...abandonmentSettingsReaders(() => ctx.cradle().settingsReadPort),
|
|
69
|
+
dispatchNotification: async (input) => {
|
|
70
|
+
await ctx.cradle().cartAbandonmentNotifier?.(input);
|
|
71
|
+
},
|
|
72
|
+
}))
|
|
73
|
+
.singleton(),
|
|
74
|
+
});
|
|
75
|
+
ctx.di.providePort('cartService', ctx
|
|
76
|
+
.asFunction(({ emFactory, cartApprovalService, cartAuditService, cartRecomputeCache }) => new CartService(emFactory, lazyPort(ctx, 'pricingService'), lazyPort(ctx, 'catalogProductReadPort'), lazyPort(ctx, 'organizationDetailsPort'), lazyPort(ctx, 'salesChannelMembershipPort'), cartApprovalService, cartAuditService, cartRecomputeCache))
|
|
77
|
+
.singleton());
|
|
78
|
+
// ---------------------------------------------------------------------------
|
|
79
|
+
// Feature 075, Phase P — the published surface.
|
|
80
|
+
//
|
|
81
|
+
// `cartService` above hands out the class, and five modules type themselves
|
|
82
|
+
// against it. These three are what they rewire to: none carries a `Cart` or
|
|
83
|
+
// a `CartItem` across the boundary, and `cartWritePort` adds the one
|
|
84
|
+
// operation two of them were writing by hand — clear the customer's active
|
|
85
|
+
// cart and seed it with these lines, which `orders`' reorder and
|
|
86
|
+
// `quote_requests`' quote conversion each spelled out with `em.create(Cart,
|
|
87
|
+
// …)` against this module's tables.
|
|
88
|
+
// ---------------------------------------------------------------------------
|
|
89
|
+
ctx.di.providePort('cartReadPort', ctx.asFunction(({ emFactory }) => new CartReadService(emFactory)).singleton());
|
|
90
|
+
ctx.di.providePort('cartWritePort', ctx
|
|
91
|
+
.asFunction(({ emFactory }) => createCartWritePort(emFactory, () => ctx.cradle().cartService))
|
|
92
|
+
.singleton());
|
|
93
|
+
/**
|
|
94
|
+
* The basket half of order placement, on the **caller's** `EntityManager`
|
|
95
|
+
* (feature 080, T048; D-169).
|
|
96
|
+
*
|
|
97
|
+
* `orders` imported this module's `Cart` and `CartItem` classes for it until
|
|
98
|
+
* T048 — a co-transactional seam D-78 point 2 ruled permanent and D-94.1
|
|
99
|
+
* settled with `carts_completed_order_fk`. The constraint and the transaction
|
|
100
|
+
* are unchanged; what moved is the four statements, to the module that owns
|
|
101
|
+
* the two tables. `CartPlacementApplyPort` is declared in this module's
|
|
102
|
+
* `ports/` directory rather than in `@endora-commerce/contracts`, because its
|
|
103
|
+
* methods take a MikroORM `EntityManager` and FR-034 keeps that package free
|
|
104
|
+
* of them.
|
|
105
|
+
*
|
|
106
|
+
* It sits beside `cartReadPort` rather than replacing it: that port is the
|
|
107
|
+
* standalone read, on this module's own `EntityManager`, and `orders`' total
|
|
108
|
+
* preview is its consumer. The doc block on `CartReadPort` predicted both
|
|
109
|
+
* halves of this arrangement and asked whoever settled the escalation to
|
|
110
|
+
* write the real consumer down; T048 is that settlement.
|
|
111
|
+
*/
|
|
112
|
+
ctx.di.providePort('cartPlacementApplyPort', ctx.asFunction(() => new CartPlacementApplyService()).singleton());
|
|
113
|
+
ctx.di.providePort('cartQueryPort', ctx.asFunction(({ emFactory }) => new CartQueryService(emFactory)).singleton());
|
|
114
|
+
ctx.routes(async (app) => {
|
|
115
|
+
const cradle = ctx.cradle();
|
|
116
|
+
const emFactory = cradle.emFactory;
|
|
117
|
+
const resolveCartActor = (req) => ctx.cradle().cartActorResolver(req);
|
|
118
|
+
// Lazily, even though the module owns this port: route *registration* runs
|
|
119
|
+
// inside `buildServer` whatever the module's effective state is, so reading
|
|
120
|
+
// the gate here — through the cradle alias above, which is how it stayed
|
|
121
|
+
// invisible to `check-port-dependencies` — would stop the next start
|
|
122
|
+
// instead of stopping the routes (D-40).
|
|
123
|
+
const cartService = lazyPort(ctx, 'cartService');
|
|
124
|
+
await registerCartRoutes(app, {
|
|
125
|
+
emFactory,
|
|
126
|
+
resolveCartActor,
|
|
127
|
+
cartService,
|
|
128
|
+
catalogProducts: lazyPort(ctx, 'catalogProductReadPort'),
|
|
129
|
+
cartUpsellService: new CartUpsellService(emFactory, lazyPort(ctx, 'catalogProductReadPort')),
|
|
130
|
+
cartCouponService: new CartCouponService(emFactory, lazyPort(ctx, 'promotionService'), lazyPort(ctx, 'promotionCodePort'), lazyPort(ctx, 'customerAccountReadPort'), lazyPort(ctx, 'organizationDetailsPort'), cradle.cartApprovalService),
|
|
131
|
+
cartConversionService: new CartConversionService(emFactory, cartService, lazyPort(ctx, 'rfqService'), lazyPort(ctx, 'quoteRequestReadPort'), lazyPort(ctx, 'catalogProductReadPort'), lazyPort(ctx, 'salesChannelMembershipPort')),
|
|
132
|
+
cartPricingRecompute: new CartPricingRecompute(emFactory, lazyPort(ctx, 'pricingService'), cradle.cartRecomputeCache, lazyPort(ctx, 'catalogProductReadPort'), lazyPort(ctx, 'organizationDetailsPort')),
|
|
133
|
+
assertOrganizationCanTransact: async (organizationId) => {
|
|
134
|
+
await ctx.cradle().organizationReadPort.assertCanTransact(organizationId);
|
|
135
|
+
},
|
|
136
|
+
pushLineToShoppingList: (input) => ctx.cradle().cartShoppingListBridge.pushLineToShoppingList(input),
|
|
137
|
+
appendShoppingListToCart: (input) => ctx.cradle().cartShoppingListBridge.appendShoppingListToCart(input),
|
|
138
|
+
});
|
|
139
|
+
// Registered unconditionally. Before T136 these two mounted only when the
|
|
140
|
+
// chain of optional arguments happened to reach them, so an approval or
|
|
141
|
+
// admin surface could be absent with nothing saying so; the module's own
|
|
142
|
+
// activation control is the intentional gate now.
|
|
143
|
+
await registerCartsOrganizationRoutes(app, {
|
|
144
|
+
emFactory,
|
|
145
|
+
resolveCartActor,
|
|
146
|
+
cartService,
|
|
147
|
+
cartApprovalService: cradle.cartApprovalService,
|
|
148
|
+
customerAccounts: lazyPort(ctx, 'customerAccountReadPort'),
|
|
149
|
+
visibilityService: new CartOrganizationVisibilityService(emFactory, lazyPort(ctx, 'customerAccountReadPort')),
|
|
150
|
+
});
|
|
151
|
+
await registerCartsAdminRoutes(app, {
|
|
152
|
+
requireAdmin: cradle.requireAdmin,
|
|
153
|
+
cartAdminService: new CartAdminService(emFactory, cradle.cartAuditService, lazyPort(ctx, 'customerAccountReadPort'), lazyPort(ctx, 'organizationDetailsPort'), lazyPort(ctx, 'catalogProductReadPort'), lazyPort(ctx, 'promotionService')),
|
|
154
|
+
cartApprovalService: cradle.cartApprovalService,
|
|
155
|
+
resolveAdminUserId: (req) => {
|
|
156
|
+
const prodActor = req.actor;
|
|
157
|
+
if (prodActor?.kind === 'admin' && prodActor.adminUserId)
|
|
158
|
+
return prodActor.adminUserId;
|
|
159
|
+
const testActor = req
|
|
160
|
+
.testActor;
|
|
161
|
+
if (testActor?.kind === 'admin' && testActor.adminUserId)
|
|
162
|
+
return testActor.adminUserId;
|
|
163
|
+
return null;
|
|
164
|
+
},
|
|
165
|
+
});
|
|
166
|
+
});
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* The module's persisted entity classes, on the `./backend` subpath, as one
|
|
170
|
+
* array and **no named class export** (D-168).
|
|
171
|
+
*
|
|
172
|
+
* This is the shape the platform reads when the package is *installed*: the
|
|
173
|
+
* boot-time loader (`src/packages/package-runtime.ts`, `exported['entities']`)
|
|
174
|
+
* and the static declaration reader (`scripts/lib/package-declarations.ts`),
|
|
175
|
+
* which is the third source of `check:module-boundary`'s `table→owner` map and
|
|
176
|
+
* the package pass of `check-entity-tenant-classification`. A missing array is
|
|
177
|
+
* answered with `[]` — zero entities registered, no error anywhere.
|
|
178
|
+
*/
|
|
179
|
+
export const entities = [
|
|
180
|
+
CartAuditEntry,
|
|
181
|
+
CartItem,
|
|
182
|
+
Cart,
|
|
183
|
+
];
|
|
184
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/backend/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import type { FastifyInstance, FastifyRequest } from 'fastify';
|
|
2
|
+
import type { CartAdminService } from './services/cart-admin-service.js';
|
|
3
|
+
import type { CartApprovalService } from './services/cart-approval-service.js';
|
|
4
|
+
import type { RequireAdminFactory } from '@endora-commerce/platform/kernel';
|
|
5
|
+
/**
|
|
6
|
+
* Admin Carts routes (feature 027 US6).
|
|
7
|
+
*
|
|
8
|
+
* - GET /api/v1/admin/carts carts:read
|
|
9
|
+
* - GET /api/v1/admin/carts/:id carts:read
|
|
10
|
+
* - GET /api/v1/admin/carts/:id/audit carts:read
|
|
11
|
+
* - POST /api/v1/admin/carts/:id/reject carts:reject
|
|
12
|
+
* - GET /api/v1/admin/organizations/:id/cart-approval-policy customers:manage
|
|
13
|
+
* - PATCH /api/v1/admin/organizations/:id/cart-approval-policy customers:manage
|
|
14
|
+
*/
|
|
15
|
+
export interface CartsAdminRoutesDeps {
|
|
16
|
+
cartAdminService: CartAdminService;
|
|
17
|
+
/**
|
|
18
|
+
* Feature 027 US4 — platform-admin proxy for the per-Organization
|
|
19
|
+
* `requires_cart_approval` policy. Optional so legacy compositions
|
|
20
|
+
* still build; production wires it.
|
|
21
|
+
*/
|
|
22
|
+
cartApprovalService?: CartApprovalService;
|
|
23
|
+
requireAdmin: RequireAdminFactory;
|
|
24
|
+
/**
|
|
25
|
+
* Resolves the admin user id from the authenticated session. Used as
|
|
26
|
+
* the `actor` on the audit-log row for the reject action.
|
|
27
|
+
*/
|
|
28
|
+
resolveAdminUserId: (req: FastifyRequest) => string | null;
|
|
29
|
+
}
|
|
30
|
+
export declare function registerCartsAdminRoutes(app: FastifyInstance, deps: CartsAdminRoutesDeps): Promise<void>;
|
|
31
|
+
//# sourceMappingURL=routes.admin.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"routes.admin.d.ts","sourceRoot":"","sources":["../../src/backend/routes.admin.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,SAAS,CAAC;AAO/D,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,kCAAkC,CAAC;AACzE,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,qCAAqC,CAAC;AAE/E,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,kCAAkC,CAAC;AAE5E;;;;;;;;;GASG;AAEH,MAAM,WAAW,oBAAoB;IACnC,gBAAgB,EAAE,gBAAgB,CAAC;IACnC;;;;OAIG;IACH,mBAAmB,CAAC,EAAE,mBAAmB,CAAC;IAC1C,YAAY,EAAE,mBAAmB,CAAC;IAClC;;;OAGG;IACH,kBAAkB,EAAE,CAAC,GAAG,EAAE,cAAc,KAAK,MAAM,GAAG,IAAI,CAAC;CAC5D;AAED,wBAAsB,wBAAwB,CAC5C,GAAG,EAAE,eAAe,EACpB,IAAI,EAAE,oBAAoB,GACzB,OAAO,CAAC,IAAI,CAAC,CA6Hf"}
|