@marianmeres/ecsuite 1.0.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 (49) hide show
  1. package/AGENTS.md +218 -0
  2. package/API.md +865 -0
  3. package/LICENSE +21 -0
  4. package/README.md +149 -0
  5. package/dist/adapters/mock/cart.d.ts +20 -0
  6. package/dist/adapters/mock/cart.js +86 -0
  7. package/dist/adapters/mock/customer.d.ts +20 -0
  8. package/dist/adapters/mock/customer.js +58 -0
  9. package/dist/adapters/mock/mod.d.ts +9 -0
  10. package/dist/adapters/mock/mod.js +9 -0
  11. package/dist/adapters/mock/order.d.ts +20 -0
  12. package/dist/adapters/mock/order.js +66 -0
  13. package/dist/adapters/mock/payment.d.ts +20 -0
  14. package/dist/adapters/mock/payment.js +55 -0
  15. package/dist/adapters/mock/product.d.ts +25 -0
  16. package/dist/adapters/mock/product.js +60 -0
  17. package/dist/adapters/mock/wishlist.d.ts +20 -0
  18. package/dist/adapters/mock/wishlist.js +70 -0
  19. package/dist/adapters/mod.d.ts +6 -0
  20. package/dist/adapters/mod.js +6 -0
  21. package/dist/domains/base.d.ts +83 -0
  22. package/dist/domains/base.js +187 -0
  23. package/dist/domains/cart.d.ts +96 -0
  24. package/dist/domains/cart.js +287 -0
  25. package/dist/domains/customer.d.ts +74 -0
  26. package/dist/domains/customer.js +183 -0
  27. package/dist/domains/mod.d.ts +13 -0
  28. package/dist/domains/mod.js +13 -0
  29. package/dist/domains/order.d.ts +83 -0
  30. package/dist/domains/order.js +233 -0
  31. package/dist/domains/payment.d.ts +83 -0
  32. package/dist/domains/payment.js +175 -0
  33. package/dist/domains/product.d.ts +130 -0
  34. package/dist/domains/product.js +241 -0
  35. package/dist/domains/wishlist.d.ts +101 -0
  36. package/dist/domains/wishlist.js +256 -0
  37. package/dist/mod.d.ts +28 -0
  38. package/dist/mod.js +32 -0
  39. package/dist/suite.d.ts +115 -0
  40. package/dist/suite.js +168 -0
  41. package/dist/types/adapter.d.ts +77 -0
  42. package/dist/types/adapter.js +7 -0
  43. package/dist/types/events.d.ts +111 -0
  44. package/dist/types/events.js +7 -0
  45. package/dist/types/mod.d.ts +9 -0
  46. package/dist/types/mod.js +9 -0
  47. package/dist/types/state.d.ts +61 -0
  48. package/dist/types/state.js +7 -0
  49. package/package.json +28 -0
package/API.md ADDED
@@ -0,0 +1,865 @@
1
+ # @marianmeres/ecsuite API Reference
2
+
3
+ Complete API documentation for the e-commerce frontend UI helper library.
4
+
5
+ ## Table of Contents
6
+
7
+ - [ECSuite](#ecsuite)
8
+ - [Domain Managers](#domain-managers)
9
+ - [CartManager](#cartmanager)
10
+ - [WishlistManager](#wishlistmanager)
11
+ - [OrderManager](#ordermanager)
12
+ - [CustomerManager](#customermanager)
13
+ - [PaymentManager](#paymentmanager)
14
+ - [ProductManager](#productmanager)
15
+ - [Adapter Interfaces](#adapter-interfaces)
16
+ - [Types](#types)
17
+ - [Events](#events)
18
+ - [Mock Adapters](#mock-adapters)
19
+
20
+ ---
21
+
22
+ ## ECSuite
23
+
24
+ Main orchestrator class that coordinates all domain managers.
25
+
26
+ ### createECSuite(config?)
27
+
28
+ Factory function to create an ECSuite instance.
29
+
30
+ ```typescript
31
+ function createECSuite(config?: ECSuiteConfig): ECSuite
32
+ ```
33
+
34
+ ### ECSuiteConfig
35
+
36
+ ```typescript
37
+ interface ECSuiteConfig {
38
+ /** Initial context (customerId, sessionId) */
39
+ context?: DomainContext;
40
+ /** Adapters for server communication */
41
+ adapters?: {
42
+ cart?: CartAdapter;
43
+ wishlist?: WishlistAdapter;
44
+ order?: OrderAdapter;
45
+ customer?: CustomerAdapter;
46
+ payment?: PaymentAdapter;
47
+ product?: ProductAdapter;
48
+ };
49
+ /** Storage configuration */
50
+ storage?: {
51
+ /** Cart storage key (default: "ecsuite:cart") */
52
+ cartKey?: string;
53
+ /** Wishlist storage key (default: "ecsuite:wishlist") */
54
+ wishlistKey?: string;
55
+ /** Storage type for persisted domains (default: "local") */
56
+ type?: StorageType;
57
+ };
58
+ /** Product cache TTL in milliseconds (default: 5 minutes) */
59
+ productCacheTtl?: number;
60
+ /** Auto-initialize on creation (default: true) */
61
+ autoInitialize?: boolean;
62
+ }
63
+ ```
64
+
65
+ ### ECSuite Class
66
+
67
+ #### Properties
68
+
69
+ | Property | Type | Description |
70
+ |----------|------|-------------|
71
+ | `cart` | `CartManager` | Cart domain manager |
72
+ | `wishlist` | `WishlistManager` | Wishlist domain manager |
73
+ | `order` | `OrderManager` | Order domain manager |
74
+ | `customer` | `CustomerManager` | Customer domain manager |
75
+ | `payment` | `PaymentManager` | Payment domain manager |
76
+ | `product` | `ProductManager` | Product domain manager |
77
+
78
+ #### Methods
79
+
80
+ ##### initialize()
81
+
82
+ Initialize all domains. Called automatically if `autoInitialize` is true.
83
+
84
+ ```typescript
85
+ async initialize(): Promise<void>
86
+ ```
87
+
88
+ ##### setContext(context)
89
+
90
+ Update context across all domains.
91
+
92
+ ```typescript
93
+ setContext(context: DomainContext): void
94
+ ```
95
+
96
+ ##### getContext()
97
+
98
+ Get the current context.
99
+
100
+ ```typescript
101
+ getContext(): DomainContext
102
+ ```
103
+
104
+ ##### on(eventType, callback)
105
+
106
+ Subscribe to a specific event type.
107
+
108
+ ```typescript
109
+ on(eventType: ECSuiteEventType, callback: Subscriber): Unsubscriber
110
+ ```
111
+
112
+ ##### onAny(callback)
113
+
114
+ Subscribe to all events.
115
+
116
+ ```typescript
117
+ onAny(callback: (envelope: { event: string; data: ECSuiteEvent }) => void): Unsubscriber
118
+ ```
119
+
120
+ ##### once(eventType, callback)
121
+
122
+ Subscribe once to an event.
123
+
124
+ ```typescript
125
+ once(eventType: ECSuiteEventType, callback: Subscriber): Unsubscriber
126
+ ```
127
+
128
+ ##### reset()
129
+
130
+ Reset all domains to initial state.
131
+
132
+ ```typescript
133
+ reset(): void
134
+ ```
135
+
136
+ ---
137
+
138
+ ## Domain Managers
139
+
140
+ All domain managers share a common interface:
141
+
142
+ - `subscribe(callback)` - Svelte-compatible store subscription
143
+ - `get()` - Get current state synchronously
144
+ - `setAdapter(adapter)` - Set the adapter
145
+ - `getAdapter()` - Get the adapter (may be null)
146
+ - `setContext(context)` - Update context
147
+ - `getContext()` - Get current context
148
+ - `initialize()` - Initialize the domain
149
+ - `reset()` - Reset to initial state
150
+
151
+ ### State Wrapper
152
+
153
+ All domains wrap their data in `DomainStateWrapper<T>`:
154
+
155
+ ```typescript
156
+ interface DomainStateWrapper<T> {
157
+ state: DomainState; // "initializing" | "ready" | "syncing" | "error"
158
+ data: T | null; // Domain data
159
+ error: DomainError | null; // Error info when state is "error"
160
+ lastSyncedAt: number | null; // Timestamp of last sync
161
+ }
162
+ ```
163
+
164
+ ---
165
+
166
+ ### CartManager
167
+
168
+ Manages shopping cart with localStorage persistence and optimistic updates.
169
+
170
+ #### Constructor Options
171
+
172
+ ```typescript
173
+ interface CartManagerOptions {
174
+ adapter?: CartAdapter;
175
+ storageKey?: string; // default: "ecsuite:cart"
176
+ storageType?: StorageType; // default: "local"
177
+ context?: DomainContext;
178
+ pubsub?: PubSub;
179
+ }
180
+ ```
181
+
182
+ #### Methods
183
+
184
+ ##### addItem(item)
185
+
186
+ Add item to cart. Increments quantity if product already exists.
187
+
188
+ ```typescript
189
+ async addItem(item: CartItem): Promise<void>
190
+ ```
191
+
192
+ **Emits:** `cart:item:added`
193
+
194
+ ##### updateItemQuantity(productId, quantity)
195
+
196
+ Update item quantity. Removes item if quantity <= 0.
197
+
198
+ ```typescript
199
+ async updateItemQuantity(productId: UUID, quantity: number): Promise<void>
200
+ ```
201
+
202
+ **Emits:** `cart:item:updated`
203
+
204
+ ##### removeItem(productId)
205
+
206
+ Remove item from cart.
207
+
208
+ ```typescript
209
+ async removeItem(productId: UUID): Promise<void>
210
+ ```
211
+
212
+ **Emits:** `cart:item:removed`
213
+
214
+ ##### clear()
215
+
216
+ Clear all items from cart.
217
+
218
+ ```typescript
219
+ async clear(): Promise<void>
220
+ ```
221
+
222
+ **Emits:** `cart:cleared`
223
+
224
+ ##### getItemCount()
225
+
226
+ Get total item count (sum of all quantities).
227
+
228
+ ```typescript
229
+ getItemCount(): number
230
+ ```
231
+
232
+ ##### hasProduct(productId)
233
+
234
+ Check if product is in cart.
235
+
236
+ ```typescript
237
+ hasProduct(productId: UUID): boolean
238
+ ```
239
+
240
+ ##### getItem(productId)
241
+
242
+ Get cart item by product ID.
243
+
244
+ ```typescript
245
+ getItem(productId: UUID): CartItem | undefined
246
+ ```
247
+
248
+ ##### getEnrichedItems(productManager)
249
+
250
+ Get cart items with product data and line totals.
251
+
252
+ ```typescript
253
+ async getEnrichedItems(productManager: ProductManager): Promise<EnrichedCartItem[]>
254
+ ```
255
+
256
+ ---
257
+
258
+ ### WishlistManager
259
+
260
+ Manages wishlist with localStorage persistence and optimistic updates.
261
+
262
+ #### Constructor Options
263
+
264
+ ```typescript
265
+ interface WishlistManagerOptions {
266
+ adapter?: WishlistAdapter;
267
+ storageKey?: string; // default: "ecsuite:wishlist"
268
+ storageType?: StorageType; // default: "local"
269
+ context?: DomainContext;
270
+ pubsub?: PubSub;
271
+ }
272
+ ```
273
+
274
+ #### Methods
275
+
276
+ ##### addItem(productId)
277
+
278
+ Add product to wishlist. No-op if already present.
279
+
280
+ ```typescript
281
+ async addItem(productId: UUID): Promise<void>
282
+ ```
283
+
284
+ **Emits:** `wishlist:item:added`
285
+
286
+ ##### removeItem(productId)
287
+
288
+ Remove product from wishlist.
289
+
290
+ ```typescript
291
+ async removeItem(productId: UUID): Promise<void>
292
+ ```
293
+
294
+ **Emits:** `wishlist:item:removed`
295
+
296
+ ##### toggleItem(productId)
297
+
298
+ Toggle product in wishlist. Returns true if added, false if removed.
299
+
300
+ ```typescript
301
+ async toggleItem(productId: UUID): Promise<boolean>
302
+ ```
303
+
304
+ ##### clear()
305
+
306
+ Clear all items from wishlist.
307
+
308
+ ```typescript
309
+ async clear(): Promise<void>
310
+ ```
311
+
312
+ **Emits:** `wishlist:cleared`
313
+
314
+ ##### getItemCount()
315
+
316
+ Get number of items in wishlist.
317
+
318
+ ```typescript
319
+ getItemCount(): number
320
+ ```
321
+
322
+ ##### hasProduct(productId)
323
+
324
+ Check if product is in wishlist.
325
+
326
+ ```typescript
327
+ hasProduct(productId: UUID): boolean
328
+ ```
329
+
330
+ ##### getItem(productId)
331
+
332
+ Get wishlist item by product ID.
333
+
334
+ ```typescript
335
+ getItem(productId: UUID): WishlistItem | undefined
336
+ ```
337
+
338
+ ##### getProductIds()
339
+
340
+ Get all product IDs in wishlist.
341
+
342
+ ```typescript
343
+ getProductIds(): UUID[]
344
+ ```
345
+
346
+ ##### getEnrichedItems(productManager)
347
+
348
+ Get wishlist items with product data.
349
+
350
+ ```typescript
351
+ async getEnrichedItems(productManager: ProductManager): Promise<EnrichedWishlistItem[]>
352
+ ```
353
+
354
+ ---
355
+
356
+ ### OrderManager
357
+
358
+ Manages orders with server-side data source (no local persistence).
359
+
360
+ #### Constructor Options
361
+
362
+ ```typescript
363
+ interface OrderManagerOptions {
364
+ adapter?: OrderAdapter;
365
+ context?: DomainContext;
366
+ pubsub?: PubSub;
367
+ }
368
+ ```
369
+
370
+ #### Methods
371
+
372
+ ##### fetchAll()
373
+
374
+ Fetch all orders from server.
375
+
376
+ ```typescript
377
+ async fetchAll(): Promise<void>
378
+ ```
379
+
380
+ **Emits:** `order:fetched`
381
+
382
+ ##### fetchOne(orderId)
383
+
384
+ Fetch single order by ID.
385
+
386
+ ```typescript
387
+ async fetchOne(orderId: UUID): Promise<OrderData | null>
388
+ ```
389
+
390
+ ##### create(orderData)
391
+
392
+ Create a new order.
393
+
394
+ ```typescript
395
+ async create(orderData: OrderCreatePayload): Promise<OrderData | null>
396
+ ```
397
+
398
+ **Emits:** `order:created`
399
+
400
+ ##### getOrderCount()
401
+
402
+ Get total number of orders.
403
+
404
+ ```typescript
405
+ getOrderCount(): number
406
+ ```
407
+
408
+ ##### getOrders()
409
+
410
+ Get all orders.
411
+
412
+ ```typescript
413
+ getOrders(): OrderData[]
414
+ ```
415
+
416
+ ##### getOrderByIndex(index)
417
+
418
+ Get order by index.
419
+
420
+ ```typescript
421
+ getOrderByIndex(index: number): OrderData | undefined
422
+ ```
423
+
424
+ ---
425
+
426
+ ### CustomerManager
427
+
428
+ Manages customer profile with server-side data source.
429
+
430
+ #### Constructor Options
431
+
432
+ ```typescript
433
+ interface CustomerManagerOptions {
434
+ adapter?: CustomerAdapter;
435
+ context?: DomainContext;
436
+ pubsub?: PubSub;
437
+ }
438
+ ```
439
+
440
+ #### Methods
441
+
442
+ ##### refresh()
443
+
444
+ Refresh customer data from server.
445
+
446
+ ```typescript
447
+ async refresh(): Promise<void>
448
+ ```
449
+
450
+ **Emits:** `customer:fetched`
451
+
452
+ ##### update(data)
453
+
454
+ Update customer data with optimistic update.
455
+
456
+ ```typescript
457
+ async update(data: Partial<CustomerData>): Promise<void>
458
+ ```
459
+
460
+ **Emits:** `customer:updated`
461
+
462
+ ##### getEmail()
463
+
464
+ Get customer email.
465
+
466
+ ```typescript
467
+ getEmail(): string | null
468
+ ```
469
+
470
+ ##### getName()
471
+
472
+ Get customer name.
473
+
474
+ ```typescript
475
+ getName(): string | null
476
+ ```
477
+
478
+ ##### isGuest()
479
+
480
+ Check if customer is a guest.
481
+
482
+ ```typescript
483
+ isGuest(): boolean
484
+ ```
485
+
486
+ ##### hasData()
487
+
488
+ Check if customer data is loaded.
489
+
490
+ ```typescript
491
+ hasData(): boolean
492
+ ```
493
+
494
+ ---
495
+
496
+ ### PaymentManager
497
+
498
+ Manages payment data with server-side source (read-only).
499
+
500
+ #### Constructor Options
501
+
502
+ ```typescript
503
+ interface PaymentManagerOptions {
504
+ adapter?: PaymentAdapter;
505
+ context?: DomainContext;
506
+ pubsub?: PubSub;
507
+ }
508
+ ```
509
+
510
+ #### Methods
511
+
512
+ ##### fetchForOrder(orderId)
513
+
514
+ Fetch payments for a specific order.
515
+
516
+ ```typescript
517
+ async fetchForOrder(orderId: UUID): Promise<PaymentData[]>
518
+ ```
519
+
520
+ **Emits:** `payment:fetched`
521
+
522
+ ##### fetchOne(paymentId)
523
+
524
+ Fetch single payment by ID.
525
+
526
+ ```typescript
527
+ async fetchOne(paymentId: UUID): Promise<PaymentData | null>
528
+ ```
529
+
530
+ ##### getPaymentCount()
531
+
532
+ Get number of fetched payments.
533
+
534
+ ```typescript
535
+ getPaymentCount(): number
536
+ ```
537
+
538
+ ##### getPayments()
539
+
540
+ Get all fetched payments.
541
+
542
+ ```typescript
543
+ getPayments(): PaymentData[]
544
+ ```
545
+
546
+ ##### getPaymentByRef(providerReference)
547
+
548
+ Get payment by provider reference.
549
+
550
+ ```typescript
551
+ getPaymentByRef(providerReference: string): PaymentData | undefined
552
+ ```
553
+
554
+ ##### clearCache()
555
+
556
+ Clear local payment cache.
557
+
558
+ ```typescript
559
+ clearCache(): void
560
+ ```
561
+
562
+ ---
563
+
564
+ ### ProductManager
565
+
566
+ Manages product data with in-memory caching. Unlike other managers, uses a simple cache layer instead of state machine.
567
+
568
+ #### Constructor Options
569
+
570
+ ```typescript
571
+ interface ProductManagerOptions {
572
+ adapter?: ProductAdapter;
573
+ context?: DomainContext;
574
+ pubsub?: PubSub;
575
+ cacheTtl?: number; // default: 5 minutes
576
+ }
577
+ ```
578
+
579
+ #### Methods
580
+
581
+ ##### getById(productId)
582
+
583
+ Get single product by ID. Returns from cache if valid.
584
+
585
+ ```typescript
586
+ async getById(productId: UUID): Promise<ProductData | null>
587
+ ```
588
+
589
+ **Emits:** `product:fetched` (on server fetch)
590
+
591
+ ##### getByIds(productIds)
592
+
593
+ Get multiple products by IDs. Uses batch fetch for missing items.
594
+
595
+ ```typescript
596
+ async getByIds(productIds: UUID[]): Promise<Map<UUID, ProductData>>
597
+ ```
598
+
599
+ **Emits:** `product:fetched` (for each server fetch)
600
+
601
+ ##### prefetch(productIds)
602
+
603
+ Prefetch products into cache.
604
+
605
+ ```typescript
606
+ async prefetch(productIds: UUID[]): Promise<void>
607
+ ```
608
+
609
+ ##### isCached(productId)
610
+
611
+ Check if product is in cache and not expired.
612
+
613
+ ```typescript
614
+ isCached(productId: UUID): boolean
615
+ ```
616
+
617
+ ##### getCacheSize()
618
+
619
+ Get number of cached products.
620
+
621
+ ```typescript
622
+ getCacheSize(): number
623
+ ```
624
+
625
+ ##### clearCache(productId?)
626
+
627
+ Clear cache entirely or for specific product.
628
+
629
+ ```typescript
630
+ clearCache(productId?: UUID): void
631
+ ```
632
+
633
+ ---
634
+
635
+ ## Adapter Interfaces
636
+
637
+ ### AdapterResult<T>
638
+
639
+ All adapter methods return this result type:
640
+
641
+ ```typescript
642
+ interface AdapterResult<T> {
643
+ success: boolean;
644
+ data?: T;
645
+ error?: {
646
+ code: string;
647
+ message: string;
648
+ };
649
+ }
650
+ ```
651
+
652
+ ### CartAdapter
653
+
654
+ ```typescript
655
+ interface CartAdapter {
656
+ fetch(ctx: DomainContext): Promise<AdapterResult<CartData>>;
657
+ addItem(item: CartItem, ctx: DomainContext): Promise<AdapterResult<CartData>>;
658
+ updateItem(productId: UUID, quantity: number, ctx: DomainContext): Promise<AdapterResult<CartData>>;
659
+ removeItem(productId: UUID, ctx: DomainContext): Promise<AdapterResult<CartData>>;
660
+ clear(ctx: DomainContext): Promise<AdapterResult<CartData>>;
661
+ sync(cart: CartData, ctx: DomainContext): Promise<AdapterResult<CartData>>;
662
+ }
663
+ ```
664
+
665
+ ### WishlistAdapter
666
+
667
+ ```typescript
668
+ interface WishlistAdapter {
669
+ fetch(ctx: DomainContext): Promise<AdapterResult<WishlistData>>;
670
+ addItem(productId: UUID, ctx: DomainContext): Promise<AdapterResult<WishlistData>>;
671
+ removeItem(productId: UUID, ctx: DomainContext): Promise<AdapterResult<WishlistData>>;
672
+ clear(ctx: DomainContext): Promise<AdapterResult<WishlistData>>;
673
+ sync(wishlist: WishlistData, ctx: DomainContext): Promise<AdapterResult<WishlistData>>;
674
+ }
675
+ ```
676
+
677
+ ### OrderAdapter
678
+
679
+ ```typescript
680
+ interface OrderAdapter {
681
+ fetchAll(ctx: DomainContext): Promise<AdapterResult<OrderData[]>>;
682
+ fetchOne(orderId: UUID, ctx: DomainContext): Promise<AdapterResult<OrderData>>;
683
+ create(order: OrderCreatePayload, ctx: DomainContext): Promise<AdapterResult<OrderData>>;
684
+ }
685
+ ```
686
+
687
+ ### CustomerAdapter
688
+
689
+ ```typescript
690
+ interface CustomerAdapter {
691
+ fetch(ctx: DomainContext): Promise<AdapterResult<CustomerData>>;
692
+ update(data: Partial<CustomerData>, ctx: DomainContext): Promise<AdapterResult<CustomerData>>;
693
+ }
694
+ ```
695
+
696
+ ### PaymentAdapter
697
+
698
+ ```typescript
699
+ interface PaymentAdapter {
700
+ fetchForOrder(orderId: UUID, ctx: DomainContext): Promise<AdapterResult<PaymentData[]>>;
701
+ fetchOne(paymentId: UUID, ctx: DomainContext): Promise<AdapterResult<PaymentData>>;
702
+ }
703
+ ```
704
+
705
+ ### ProductAdapter
706
+
707
+ ```typescript
708
+ interface ProductAdapter {
709
+ fetchOne(productId: UUID, ctx: DomainContext): Promise<AdapterResult<ProductData>>;
710
+ fetchMany(productIds: UUID[], ctx: DomainContext): Promise<AdapterResult<ProductData[]>>;
711
+ }
712
+ ```
713
+
714
+ ---
715
+
716
+ ## Types
717
+
718
+ ### DomainState
719
+
720
+ ```typescript
721
+ type DomainState = "initializing" | "ready" | "syncing" | "error";
722
+ ```
723
+
724
+ ### DomainContext
725
+
726
+ ```typescript
727
+ interface DomainContext {
728
+ customerId?: UUID;
729
+ sessionId?: UUID;
730
+ }
731
+ ```
732
+
733
+ ### DomainError
734
+
735
+ ```typescript
736
+ interface DomainError {
737
+ code: string;
738
+ message: string;
739
+ operation: string;
740
+ originalError?: unknown;
741
+ }
742
+ ```
743
+
744
+ ### StorageType
745
+
746
+ ```typescript
747
+ type StorageType = "local" | "session" | "memory" | null;
748
+ ```
749
+
750
+ ### WishlistItem
751
+
752
+ ```typescript
753
+ interface WishlistItem {
754
+ product_id: UUID;
755
+ added_at?: number;
756
+ }
757
+ ```
758
+
759
+ ### WishlistData
760
+
761
+ ```typescript
762
+ interface WishlistData {
763
+ items: WishlistItem[];
764
+ }
765
+ ```
766
+
767
+ ### EnrichedCartItem
768
+
769
+ ```typescript
770
+ interface EnrichedCartItem extends CartItem {
771
+ product: ProductData | null;
772
+ lineTotal: number;
773
+ }
774
+ ```
775
+
776
+ ### EnrichedWishlistItem
777
+
778
+ ```typescript
779
+ interface EnrichedWishlistItem extends WishlistItem {
780
+ product: ProductData | null;
781
+ }
782
+ ```
783
+
784
+ ---
785
+
786
+ ## Events
787
+
788
+ ### Event Types
789
+
790
+ | Event | Description |
791
+ |-------|-------------|
792
+ | `domain:state:changed` | Domain state transitioned |
793
+ | `domain:error` | Domain operation failed |
794
+ | `domain:synced` | Domain successfully synced |
795
+ | `cart:item:added` | Cart item added |
796
+ | `cart:item:updated` | Cart item quantity updated |
797
+ | `cart:item:removed` | Cart item removed |
798
+ | `cart:cleared` | Cart cleared |
799
+ | `wishlist:item:added` | Wishlist item added |
800
+ | `wishlist:item:removed` | Wishlist item removed |
801
+ | `wishlist:cleared` | Wishlist cleared |
802
+ | `order:created` | Order created |
803
+ | `order:fetched` | Orders fetched |
804
+ | `customer:updated` | Customer updated |
805
+ | `customer:fetched` | Customer fetched |
806
+ | `payment:fetched` | Payments fetched |
807
+ | `product:fetched` | Product fetched |
808
+
809
+ ### Event Interfaces
810
+
811
+ All events extend `ECSuiteEventBase`:
812
+
813
+ ```typescript
814
+ interface ECSuiteEventBase {
815
+ timestamp: number;
816
+ domain: DomainName;
817
+ }
818
+ ```
819
+
820
+ ---
821
+
822
+ ## Mock Adapters
823
+
824
+ Mock adapters are provided for testing:
825
+
826
+ ```typescript
827
+ import {
828
+ createMockCartAdapter,
829
+ createMockWishlistAdapter,
830
+ createMockOrderAdapter,
831
+ createMockCustomerAdapter,
832
+ createMockPaymentAdapter,
833
+ createMockProductAdapter,
834
+ } from "@marianmeres/ecsuite";
835
+ ```
836
+
837
+ ### Mock Adapter Options
838
+
839
+ All mock adapters support:
840
+
841
+ ```typescript
842
+ interface MockAdapterOptions {
843
+ initialData?: T; // Initial data
844
+ delay?: number; // Network delay in ms (default: 50)
845
+ forceError?: { // Force errors for testing
846
+ operation?: string;
847
+ code?: string;
848
+ message?: string;
849
+ };
850
+ }
851
+ ```
852
+
853
+ ### Example
854
+
855
+ ```typescript
856
+ const suite = createECSuite({
857
+ adapters: {
858
+ cart: createMockCartAdapter({
859
+ initialData: { items: [{ product_id: "p1", quantity: 2 }] },
860
+ delay: 100,
861
+ }),
862
+ },
863
+ storage: { type: "memory" },
864
+ });
865
+ ```