48 lines
1.5 KiB
TypeScript
48 lines
1.5 KiB
TypeScript
import { CartItem, Product, ProductCustomization } from '@/domain/entities';
|
|
import { CustomizationDomainService } from './CustomizationDomainService';
|
|
|
|
/**
|
|
* DOMAIN SERVICE — Cart business rules (pure functions, no storage)
|
|
*/
|
|
export class CartDomainService {
|
|
static calculateSubtotal(items: CartItem[]): number {
|
|
return items.reduce((sum, item) => sum + item.product.price * item.quantity, 0);
|
|
}
|
|
|
|
static calculateItemCount(items: CartItem[]): number {
|
|
return items.reduce((sum, item) => sum + item.quantity, 0);
|
|
}
|
|
|
|
static addItem(
|
|
items: CartItem[],
|
|
product: Product,
|
|
customization: ProductCustomization,
|
|
customizationLabel: string,
|
|
quantity = 1
|
|
): CartItem[] {
|
|
const id = CustomizationDomainService.getCartItemKey(product.id, customization);
|
|
const existing = items.find((item) => item.id === id);
|
|
|
|
if (existing) {
|
|
return items.map((item) =>
|
|
item.id === id ? { ...item, quantity: item.quantity + quantity } : item
|
|
);
|
|
}
|
|
|
|
return [
|
|
...items,
|
|
{ id, product, quantity, customization, customizationLabel },
|
|
];
|
|
}
|
|
|
|
static removeItem(items: CartItem[], id: string): CartItem[] {
|
|
return items.filter((item) => item.id !== id);
|
|
}
|
|
|
|
static updateQuantity(items: CartItem[], id: string, quantity: number): CartItem[] {
|
|
if (quantity <= 0) {
|
|
return CartDomainService.removeItem(items, id);
|
|
}
|
|
return items.map((item) => (item.id === id ? { ...item, quantity } : item));
|
|
}
|
|
} |