import { apiClient, ApiResponse } from './client'; // Enums export enum PurchaseOrderStatus { DRAFT = 'draft', PENDING = 'pending', APPROVED = 'approved', SENT = 'sent', PARTIALLY_RECEIVED = 'partially_received', RECEIVED = 'received', CANCELLED = 'cancelled', } export enum DeliveryStatus { SCHEDULED = 'scheduled', IN_TRANSIT = 'in_transit', DELIVERED = 'delivered', FAILED = 'failed', RETURNED = 'returned', } // Request/Response Types export interface PurchaseOrderItem { ingredient_id: string; ingredient_name: string; quantity: number; unit_price: number; total_price: number; notes?: string; } export interface PurchaseOrderCreate { supplier_id: string; items: PurchaseOrderItem[]; delivery_date?: string; notes?: string; priority?: 'low' | 'normal' | 'high' | 'urgent'; } export interface PurchaseOrderUpdate { supplier_id?: string; delivery_date?: string; notes?: string; priority?: 'low' | 'normal' | 'high' | 'urgent'; status?: PurchaseOrderStatus; } export interface PurchaseOrderResponse { id: string; tenant_id: string; order_number: string; supplier_id: string; supplier_name: string; status: PurchaseOrderStatus; items: PurchaseOrderItem[]; subtotal: number; tax_amount: number; total_amount: number; delivery_date?: string; expected_delivery_date?: string; actual_delivery_date?: string; notes?: string; priority: 'low' | 'normal' | 'high' | 'urgent'; created_at: string; updated_at: string; created_by: string; approved_by?: string; approved_at?: string; } export interface Supplier { id: string; tenant_id: string; name: string; contact_name?: string; email?: string; phone?: string; address: string; tax_id?: string; payment_terms?: string; delivery_terms?: string; rating?: number; is_active: boolean; performance_metrics: { on_time_delivery_rate: number; quality_score: number; total_orders: number; average_delivery_time: number; }; created_at: string; updated_at: string; } export interface DeliveryResponse { id: string; tenant_id: string; purchase_order_id: string; delivery_number: string; supplier_id: string; status: DeliveryStatus; scheduled_date: string; actual_delivery_date?: string; delivery_items: Array<{ ingredient_id: string; ingredient_name: string; ordered_quantity: number; delivered_quantity: number; unit_price: number; batch_number?: string; expiration_date?: string; quality_notes?: string; }>; total_items: number; delivery_notes?: string; quality_check_notes?: string; received_by?: string; created_at: string; updated_at: string; } class ProcurementService { private readonly baseUrl = '/procurement'; // Purchase Order management async getPurchaseOrders(params?: { page?: number; size?: number; status?: PurchaseOrderStatus; supplier_id?: string; start_date?: string; end_date?: string; }): Promise> { const queryParams = new URLSearchParams(); if (params) { Object.entries(params).forEach(([key, value]) => { if (value !== undefined) { queryParams.append(key, value.toString()); } }); } const url = queryParams.toString() ? `${this.baseUrl}/purchase-orders?${queryParams.toString()}` : `${this.baseUrl}/purchase-orders`; return apiClient.get(url); } async getPurchaseOrder(orderId: string): Promise> { return apiClient.get(`${this.baseUrl}/purchase-orders/${orderId}`); } async createPurchaseOrder(orderData: PurchaseOrderCreate): Promise> { return apiClient.post(`${this.baseUrl}/purchase-orders`, orderData); } async updatePurchaseOrder(orderId: string, orderData: PurchaseOrderUpdate): Promise> { return apiClient.put(`${this.baseUrl}/purchase-orders/${orderId}`, orderData); } async approvePurchaseOrder(orderId: string): Promise> { return apiClient.post(`${this.baseUrl}/purchase-orders/${orderId}/approve`); } async sendPurchaseOrder(orderId: string, sendEmail: boolean = true): Promise> { return apiClient.post(`${this.baseUrl}/purchase-orders/${orderId}/send`, { send_email: sendEmail }); } async cancelPurchaseOrder(orderId: string, reason?: string): Promise> { return apiClient.post(`${this.baseUrl}/purchase-orders/${orderId}/cancel`, { reason }); } // Supplier management async getSuppliers(params?: { page?: number; size?: number; is_active?: boolean; search?: string; }): Promise> { const queryParams = new URLSearchParams(); if (params) { Object.entries(params).forEach(([key, value]) => { if (value !== undefined) { queryParams.append(key, value.toString()); } }); } const url = queryParams.toString() ? `${this.baseUrl}/suppliers?${queryParams.toString()}` : `${this.baseUrl}/suppliers`; return apiClient.get(url); } async getSupplier(supplierId: string): Promise> { return apiClient.get(`${this.baseUrl}/suppliers/${supplierId}`); } async createSupplier(supplierData: Omit): Promise> { return apiClient.post(`${this.baseUrl}/suppliers`, supplierData); } async updateSupplier(supplierId: string, supplierData: Partial): Promise> { return apiClient.put(`${this.baseUrl}/suppliers/${supplierId}`, supplierData); } async deleteSupplier(supplierId: string): Promise> { return apiClient.delete(`${this.baseUrl}/suppliers/${supplierId}`); } async getSupplierPerformance(supplierId: string): Promise; recent_deliveries: DeliveryResponse[]; }>> { return apiClient.get(`${this.baseUrl}/suppliers/${supplierId}/performance`); } // Delivery management async getDeliveries(params?: { page?: number; size?: number; status?: DeliveryStatus; supplier_id?: string; purchase_order_id?: string; start_date?: string; end_date?: string; }): Promise> { const queryParams = new URLSearchParams(); if (params) { Object.entries(params).forEach(([key, value]) => { if (value !== undefined) { queryParams.append(key, value.toString()); } }); } const url = queryParams.toString() ? `${this.baseUrl}/deliveries?${queryParams.toString()}` : `${this.baseUrl}/deliveries`; return apiClient.get(url); } async getDelivery(deliveryId: string): Promise> { return apiClient.get(`${this.baseUrl}/deliveries/${deliveryId}`); } async receiveDelivery(deliveryId: string, deliveryData: { delivered_items: Array<{ ingredient_id: string; delivered_quantity: number; batch_number?: string; expiration_date?: string; quality_notes?: string; }>; delivery_notes?: string; quality_check_notes?: string; }): Promise> { return apiClient.post(`${this.baseUrl}/deliveries/${deliveryId}/receive`, deliveryData); } async reportDeliveryIssue(deliveryId: string, issue: { issue_type: 'late_delivery' | 'quality_issue' | 'quantity_mismatch' | 'damaged_goods' | 'other'; description: string; affected_items?: string[]; severity: 'low' | 'medium' | 'high'; }): Promise> { return apiClient.post(`${this.baseUrl}/deliveries/${deliveryId}/report-issue`, issue); } // Analytics and reporting async getProcurementAnalytics(params?: { start_date?: string; end_date?: string; supplier_id?: string; }): Promise; spending_trends: Array<{ month: string; total_spending: number; order_count: number; }>; }>> { const queryParams = new URLSearchParams(); if (params) { Object.entries(params).forEach(([key, value]) => { if (value !== undefined) { queryParams.append(key, value.toString()); } }); } const url = queryParams.toString() ? `${this.baseUrl}/analytics?${queryParams.toString()}` : `${this.baseUrl}/analytics`; return apiClient.get(url); } async getSpendingByCategory(params?: { start_date?: string; end_date?: string; }): Promise>> { const queryParams = new URLSearchParams(); if (params) { Object.entries(params).forEach(([key, value]) => { if (value !== undefined) { queryParams.append(key, value.toString()); } }); } const url = queryParams.toString() ? `${this.baseUrl}/spending/by-category?${queryParams.toString()}` : `${this.baseUrl}/spending/by-category`; return apiClient.get(url); } // Automated procurement async getReorderSuggestions(): Promise>> { return apiClient.get(`${this.baseUrl}/reorder-suggestions`); } async createReorderFromSuggestions(suggestions: Array<{ ingredient_id: string; supplier_id: string; quantity: number; }>): Promise> { return apiClient.post(`${this.baseUrl}/auto-reorder`, { suggestions }); } // Utility methods getPurchaseOrderStatusOptions(): { value: PurchaseOrderStatus; label: string; color: string }[] { return [ { value: PurchaseOrderStatus.DRAFT, label: 'Draft', color: 'gray' }, { value: PurchaseOrderStatus.PENDING, label: 'Pending', color: 'yellow' }, { value: PurchaseOrderStatus.APPROVED, label: 'Approved', color: 'blue' }, { value: PurchaseOrderStatus.SENT, label: 'Sent', color: 'purple' }, { value: PurchaseOrderStatus.PARTIALLY_RECEIVED, label: 'Partially Received', color: 'orange' }, { value: PurchaseOrderStatus.RECEIVED, label: 'Received', color: 'green' }, { value: PurchaseOrderStatus.CANCELLED, label: 'Cancelled', color: 'red' }, ]; } getDeliveryStatusOptions(): { value: DeliveryStatus; label: string; color: string }[] { return [ { value: DeliveryStatus.SCHEDULED, label: 'Scheduled', color: 'blue' }, { value: DeliveryStatus.IN_TRANSIT, label: 'In Transit', color: 'yellow' }, { value: DeliveryStatus.DELIVERED, label: 'Delivered', color: 'green' }, { value: DeliveryStatus.FAILED, label: 'Failed', color: 'red' }, { value: DeliveryStatus.RETURNED, label: 'Returned', color: 'orange' }, ]; } getPriorityOptions(): { value: string; label: string; color: string }[] { return [ { value: 'low', label: 'Low', color: 'gray' }, { value: 'normal', label: 'Normal', color: 'blue' }, { value: 'high', label: 'High', color: 'orange' }, { value: 'urgent', label: 'Urgent', color: 'red' }, ]; } } export const procurementService = new ProcurementService();