// ================================================================
// frontend/src/api/services/inventory.ts
// ================================================================
/**
 * Inventory Service - Complete backend alignment
 *
 * Backend API structure (3-tier architecture):
 * - ATOMIC: ingredients.py, stock_entries.py, transformations.py, temperature_logs.py
 * - OPERATIONS: inventory_operations.py, food_safety_operations.py
 * - ANALYTICS: analytics.py, dashboard.py
 * - COMPLIANCE: food_safety_alerts.py, food_safety_compliance.py
 *
 * Last Updated: 2025-10-05
 * Status: ✅ Complete - Zero drift with backend
 */

import { apiClient } from '../client';
import {
  // Ingredients
  IngredientCreate,
  IngredientUpdate,
  IngredientResponse,
  IngredientFilter,
  BulkIngredientResponse,
  // Stock
  StockCreate,
  StockUpdate,
  StockResponse,
  StockFilter,
  StockMovementCreate,
  StockMovementResponse,
  BulkStockResponse,
  // Operations
  StockConsumptionRequest,
  StockConsumptionResponse,
  // Transformations
  ProductTransformationCreate,
  ProductTransformationResponse,
  // Food Safety
  TemperatureLogCreate,
  TemperatureLogResponse,
  FoodSafetyAlertResponse,
  FoodSafetyComplianceResponse,
  // Classification
  ProductClassificationRequest,
  ProductSuggestionResponse,
  BatchClassificationRequest,
  BatchClassificationResponse,
  BusinessModelAnalysisResponse,
  // Dashboard & Analytics
  InventorySummary,
  InventoryDashboardSummary,
  InventoryAnalytics,
  // Common
  PaginatedResponse,
  DeletionSummary,
} from '../types/inventory';

export class InventoryService {
  private readonly baseUrl = '/tenants';

  // ===================================================================
  // ATOMIC: Ingredients CRUD
  // Backend: services/inventory/app/api/ingredients.py
  // ===================================================================

  async createIngredient(
    tenantId: string,
    ingredientData: IngredientCreate
  ): Promise<IngredientResponse> {
    return apiClient.post<IngredientResponse>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients`,
      ingredientData
    );
  }

  async bulkCreateIngredients(
    tenantId: string,
    ingredients: IngredientCreate[]
  ): Promise<BulkIngredientResponse> {
    return apiClient.post<BulkIngredientResponse>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/bulk`,
      { ingredients }
    );
  }

  async getIngredient(tenantId: string, ingredientId: string): Promise<IngredientResponse> {
    return apiClient.get<IngredientResponse>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/${ingredientId}`
    );
  }

  async getIngredients(
    tenantId: string,
    filter?: IngredientFilter
  ): Promise<IngredientResponse[]> {
    const queryParams = new URLSearchParams();

    if (filter?.category) queryParams.append('category', filter.category);
    if (filter?.stock_status) queryParams.append('stock_status', filter.stock_status);
    if (filter?.requires_refrigeration !== undefined)
      queryParams.append('requires_refrigeration', filter.requires_refrigeration.toString());
    if (filter?.requires_freezing !== undefined)
      queryParams.append('requires_freezing', filter.requires_freezing.toString());
    if (filter?.is_seasonal !== undefined)
      queryParams.append('is_seasonal', filter.is_seasonal.toString());
    if (filter?.supplier_id) queryParams.append('supplier_id', filter.supplier_id);
    if (filter?.expiring_within_days !== undefined)
      queryParams.append('expiring_within_days', filter.expiring_within_days.toString());
    if (filter?.search) queryParams.append('search', filter.search);
    if (filter?.limit !== undefined) queryParams.append('limit', filter.limit.toString());
    if (filter?.offset !== undefined) queryParams.append('offset', filter.offset.toString());
    if (filter?.order_by) queryParams.append('order_by', filter.order_by);
    if (filter?.order_direction) queryParams.append('order_direction', filter.order_direction);

    const url = queryParams.toString()
      ? `${this.baseUrl}/${tenantId}/inventory/ingredients?${queryParams.toString()}`
      : `${this.baseUrl}/${tenantId}/inventory/ingredients`;

    return apiClient.get<IngredientResponse[]>(url);
  }

  async updateIngredient(
    tenantId: string,
    ingredientId: string,
    updateData: IngredientUpdate
  ): Promise<IngredientResponse> {
    return apiClient.put<IngredientResponse>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/${ingredientId}`,
      updateData
    );
  }

  async softDeleteIngredient(tenantId: string, ingredientId: string): Promise<void> {
    return apiClient.delete<void>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/${ingredientId}`
    );
  }

  async hardDeleteIngredient(tenantId: string, ingredientId: string): Promise<DeletionSummary> {
    return apiClient.delete<DeletionSummary>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/${ingredientId}/hard`
    );
  }

  async getIngredientsByCategory(
    tenantId: string
  ): Promise<Record<string, IngredientResponse[]>> {
    return apiClient.get<Record<string, IngredientResponse[]>>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/by-category`
    );
  }

  // ===================================================================
  // ATOMIC: Stock CRUD
  // Backend: services/inventory/app/api/stock_entries.py
  // ===================================================================

  async addStock(tenantId: string, stockData: StockCreate): Promise<StockResponse> {
    return apiClient.post<StockResponse>(
      `${this.baseUrl}/${tenantId}/inventory/stock`,
      stockData
    );
  }

  async bulkAddStock(
    tenantId: string,
    stocks: StockCreate[]
  ): Promise<BulkStockResponse> {
    return apiClient.post<BulkStockResponse>(
      `${this.baseUrl}/${tenantId}/inventory/stock/bulk`,
      { stocks }
    );
  }

  async getStock(tenantId: string, stockId: string): Promise<StockResponse> {
    return apiClient.get<StockResponse>(
      `${this.baseUrl}/${tenantId}/inventory/stock/${stockId}`
    );
  }

  async getStockByIngredient(
    tenantId: string,
    ingredientId: string,
    includeUnavailable: boolean = false
  ): Promise<StockResponse[]> {
    const queryParams = new URLSearchParams();
    queryParams.append('include_unavailable', includeUnavailable.toString());

    return apiClient.get<StockResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/ingredients/${ingredientId}/stock?${queryParams.toString()}`
    );
  }

  async getAllStock(
    tenantId: string,
    filter?: StockFilter
  ): Promise<PaginatedResponse<StockResponse>> {
    const queryParams = new URLSearchParams();

    if (filter?.ingredient_id) queryParams.append('ingredient_id', filter.ingredient_id);
    if (filter?.is_available !== undefined)
      queryParams.append('is_available', filter.is_available.toString());
    if (filter?.is_expired !== undefined)
      queryParams.append('is_expired', filter.is_expired.toString());
    if (filter?.expiring_within_days !== undefined)
      queryParams.append('expiring_within_days', filter.expiring_within_days.toString());
    if (filter?.batch_number) queryParams.append('batch_number', filter.batch_number);
    if (filter?.supplier_id) queryParams.append('supplier_id', filter.supplier_id);
    if (filter?.limit !== undefined) queryParams.append('limit', filter.limit.toString());
    if (filter?.offset !== undefined) queryParams.append('offset', filter.offset.toString());
    if (filter?.order_by) queryParams.append('order_by', filter.order_by);
    if (filter?.order_direction) queryParams.append('order_direction', filter.order_direction);

    const url = queryParams.toString()
      ? `${this.baseUrl}/${tenantId}/inventory/stock?${queryParams.toString()}`
      : `${this.baseUrl}/${tenantId}/inventory/stock`;

    return apiClient.get<PaginatedResponse<StockResponse>>(url);
  }

  async updateStock(
    tenantId: string,
    stockId: string,
    updateData: StockUpdate
  ): Promise<StockResponse> {
    return apiClient.put<StockResponse>(
      `${this.baseUrl}/${tenantId}/inventory/stock/${stockId}`,
      updateData
    );
  }

  async deleteStock(tenantId: string, stockId: string): Promise<{ message: string }> {
    return apiClient.delete<{ message: string }>(
      `${this.baseUrl}/${tenantId}/inventory/stock/${stockId}`
    );
  }

  // ===================================================================
  // ATOMIC: Stock Movements
  // Backend: services/inventory/app/api/stock_entries.py
  // ===================================================================

  async createStockMovement(
    tenantId: string,
    movementData: StockMovementCreate
  ): Promise<StockMovementResponse> {
    return apiClient.post<StockMovementResponse>(
      `${this.baseUrl}/${tenantId}/inventory/stock/movements`,
      movementData
    );
  }

  async getStockMovements(
    tenantId: string,
    ingredientId?: string,
    limit: number = 50,
    offset: number = 0
  ): Promise<StockMovementResponse[]> {
    const queryParams = new URLSearchParams();
    if (ingredientId) queryParams.append('ingredient_id', ingredientId);
    queryParams.append('limit', limit.toString());
    queryParams.append('skip', offset.toString());

    return apiClient.get<StockMovementResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/stock/movements?${queryParams.toString()}`
    );
  }

  // ===================================================================
  // ATOMIC: Transformations
  // Backend: services/inventory/app/api/transformations.py
  // ===================================================================

  async createTransformation(
    tenantId: string,
    transformationData: ProductTransformationCreate
  ): Promise<ProductTransformationResponse> {
    return apiClient.post<ProductTransformationResponse>(
      `${this.baseUrl}/${tenantId}/inventory/transformations`,
      transformationData
    );
  }

  async listTransformations(
    tenantId: string,
    limit: number = 50,
    offset: number = 0
  ): Promise<ProductTransformationResponse[]> {
    const queryParams = new URLSearchParams();
    queryParams.append('limit', limit.toString());
    queryParams.append('skip', offset.toString());

    return apiClient.get<ProductTransformationResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/transformations?${queryParams.toString()}`
    );
  }

  // ===================================================================
  // ATOMIC: Temperature Logs
  // Backend: services/inventory/app/api/temperature_logs.py
  // ===================================================================

  async logTemperature(
    tenantId: string,
    temperatureData: TemperatureLogCreate
  ): Promise<TemperatureLogResponse> {
    return apiClient.post<TemperatureLogResponse>(
      `${this.baseUrl}/${tenantId}/inventory/temperature-logs`,
      temperatureData
    );
  }

  async listTemperatureLogs(
    tenantId: string,
    ingredientId?: string,
    startDate?: string,
    endDate?: string,
    limit: number = 100,
    offset: number = 0
  ): Promise<TemperatureLogResponse[]> {
    const queryParams = new URLSearchParams();
    if (ingredientId) queryParams.append('ingredient_id', ingredientId);
    if (startDate) queryParams.append('start_date', startDate);
    if (endDate) queryParams.append('end_date', endDate);
    queryParams.append('limit', limit.toString());
    queryParams.append('skip', offset.toString());

    return apiClient.get<TemperatureLogResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/temperature-logs?${queryParams.toString()}`
    );
  }

  // ===================================================================
  // OPERATIONS: Stock Management
  // Backend: services/inventory/app/api/inventory_operations.py
  // ===================================================================

  async consumeStock(
    tenantId: string,
    consumptionData: StockConsumptionRequest
  ): Promise<StockConsumptionResponse> {
    const queryParams = new URLSearchParams();
    queryParams.append('ingredient_id', consumptionData.ingredient_id);
    queryParams.append('quantity', consumptionData.quantity.toString());
    if (consumptionData.reference_number)
      queryParams.append('reference_number', consumptionData.reference_number);
    if (consumptionData.notes) queryParams.append('notes', consumptionData.notes);
    if (consumptionData.fifo !== undefined)
      queryParams.append('fifo', consumptionData.fifo.toString());

    return apiClient.post<StockConsumptionResponse>(
      `${this.baseUrl}/${tenantId}/inventory/operations/consume-stock?${queryParams.toString()}`
    );
  }

  async getExpiringStock(
    tenantId: string,
    withinDays: number = 7
  ): Promise<StockResponse[]> {
    const queryParams = new URLSearchParams();
    queryParams.append('days_ahead', withinDays.toString());

    return apiClient.get<StockResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/operations/stock/expiring?${queryParams.toString()}`
    );
  }

  async getExpiredStock(tenantId: string): Promise<StockResponse[]> {
    return apiClient.get<StockResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/operations/stock/expired`
    );
  }

  async getLowStockIngredients(tenantId: string): Promise<IngredientResponse[]> {
    return apiClient.get<IngredientResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/operations/stock/low-stock`
    );
  }

  async getStockSummary(tenantId: string): Promise<InventorySummary> {
    return apiClient.get<InventorySummary>(
      `${this.baseUrl}/${tenantId}/inventory/operations/stock/summary`
    );
  }

  // ===================================================================
  // OPERATIONS: Classification
  // Backend: services/inventory/app/api/inventory_operations.py
  // ===================================================================

  async classifyProduct(
    tenantId: string,
    classificationData: ProductClassificationRequest
  ): Promise<ProductSuggestionResponse> {
    return apiClient.post<ProductSuggestionResponse>(
      `${this.baseUrl}/${tenantId}/inventory/operations/classify`,
      classificationData
    );
  }

  async classifyBatch(
    tenantId: string,
    batchData: BatchClassificationRequest
  ): Promise<BatchClassificationResponse> {
    return apiClient.post<BatchClassificationResponse>(
      `${this.baseUrl}/${tenantId}/inventory/operations/classify-products-batch`,
      batchData
    );
  }

  async analyzeBusinessModel(tenantId: string): Promise<BusinessModelAnalysisResponse> {
    return apiClient.post<BusinessModelAnalysisResponse>(
      `${this.baseUrl}/${tenantId}/inventory/operations/analyze-business-model`
    );
  }

  // ===================================================================
  // OPERATIONS: Batch Inventory Summary (Enterprise Feature)
  // Backend: services/inventory/app/api/inventory_operations.py
  // ===================================================================

  async getBatchInventorySummary(tenantIds: string[]): Promise<Record<string, any>> {
    return apiClient.post<Record<string, any>>(
      '/tenants/batch/inventory-summary',
      {
        tenant_ids: tenantIds,
      }
    );
  }

  // ===================================================================
  // OPERATIONS: Food Safety
  // Backend: services/inventory/app/api/food_safety_operations.py
  // ===================================================================

  async acknowledgeAlert(
    tenantId: string,
    alertId: string,
    notes?: string
  ): Promise<{ message: string }> {
    const queryParams = new URLSearchParams();
    if (notes) queryParams.append('notes', notes);

    return apiClient.post<{ message: string }>(
      `${this.baseUrl}/${tenantId}/inventory/food-safety/alerts/${alertId}/acknowledge?${queryParams.toString()}`
    );
  }

  async resolveAlert(
    tenantId: string,
    alertId: string,
    resolution: string
  ): Promise<{ message: string }> {
    const queryParams = new URLSearchParams();
    queryParams.append('resolution', resolution);

    return apiClient.post<{ message: string }>(
      `${this.baseUrl}/${tenantId}/inventory/food-safety/alerts/${alertId}/resolve?${queryParams.toString()}`
    );
  }

  async getComplianceStatus(tenantId: string): Promise<FoodSafetyComplianceResponse> {
    return apiClient.get<FoodSafetyComplianceResponse>(
      `${this.baseUrl}/${tenantId}/inventory/food-safety/compliance/status`
    );
  }

  // ===================================================================
  // COMPLIANCE: Food Safety Alerts
  // Backend: services/inventory/app/api/food_safety_alerts.py
  // ===================================================================

  async listFoodSafetyAlerts(
    tenantId: string,
    status?: string,
    severity?: string,
    limit: number = 50,
    offset: number = 0
  ): Promise<FoodSafetyAlertResponse[]> {
    const queryParams = new URLSearchParams();
    if (status) queryParams.append('status', status);
    if (severity) queryParams.append('severity', severity);
    queryParams.append('limit', limit.toString());
    queryParams.append('skip', offset.toString());

    return apiClient.get<FoodSafetyAlertResponse[]>(
      `${this.baseUrl}/${tenantId}/inventory/food-safety/alerts?${queryParams.toString()}`
    );
  }

  // ===================================================================
  // ANALYTICS: Dashboard
  // Backend: services/inventory/app/api/dashboard.py
  // ===================================================================

  async getDashboardSummary(tenantId: string): Promise<InventoryDashboardSummary> {
    return apiClient.get<InventoryDashboardSummary>(
      `${this.baseUrl}/${tenantId}/inventory/dashboard/summary`
    );
  }

  async getInventoryAnalytics(
    tenantId: string,
    startDate?: string,
    endDate?: string
  ): Promise<InventoryAnalytics> {
    const queryParams = new URLSearchParams();
    if (startDate) queryParams.append('start_date', startDate);
    if (endDate) queryParams.append('end_date', endDate);

    const url = queryParams.toString()
      ? `${this.baseUrl}/${tenantId}/inventory/analytics?${queryParams.toString()}`
      : `${this.baseUrl}/${tenantId}/inventory/analytics`;

    return apiClient.get<InventoryAnalytics>(url);
  }

  // Legacy method - keeping for backward compatibility during transition
  async getStockAnalytics(
    tenantId: string,
    startDate?: string,
    endDate?: string
  ): Promise<{
    total_ingredients: number;
    total_stock_value: number;
    low_stock_count: number;
    out_of_stock_count: number;
    expiring_soon_count: number;
    stock_turnover_rate: number;
  }> {
    const queryParams = new URLSearchParams();
    if (startDate) queryParams.append('start_date', startDate);
    if (endDate) queryParams.append('end_date', endDate);

    const url = queryParams.toString()
      ? `${this.baseUrl}/${tenantId}/inventory/dashboard/analytics?${queryParams.toString()}`
      : `${this.baseUrl}/${tenantId}/inventory/dashboard/analytics`;

    return apiClient.get(url);
  }
}

export const inventoryService = new InventoryService();
