/// Local Data Source: Invoices
///
/// Provides mock invoice data for development and testing.
library;

import 'dart:convert';

import 'package:flutter/foundation.dart';
import 'package:worker/features/orders/data/models/invoice_model.dart';

/// Invoices Local Data Source
///
/// Manages local mock invoice data.
class InvoicesLocalDataSource {
  /// Get all mock invoices
  Future<List<InvoiceModel>> getAllInvoices() async {
    try {
      debugPrint('[InvoicesLocalDataSource] Loading mock invoices...');

      // Parse mock JSON data
      final decoded = jsonDecode(_mockInvoicesJson);
      if (decoded is! List) {
        throw Exception('Invalid JSON format: expected List');
      }

      final invoices = decoded
          .map((json) => InvoiceModel.fromJson(json as Map<String, dynamic>))
          .toList();

      debugPrint(
        '[InvoicesLocalDataSource] Loaded ${invoices.length} invoices',
      );
      return invoices;
    } catch (e, stackTrace) {
      debugPrint('[InvoicesLocalDataSource] Error loading invoices: $e');
      debugPrint('Stack trace: $stackTrace');
      rethrow;
    }
  }

  /// Get invoices by status
  Future<List<InvoiceModel>> getInvoicesByStatus(String status) async {
    try {
      final allInvoices = await getAllInvoices();
      final filtered = allInvoices
          .where((invoice) => invoice.status.name == status)
          .toList();

      debugPrint(
        '[InvoicesLocalDataSource] Filtered ${filtered.length} invoices with status: $status',
      );
      return filtered;
    } catch (e) {
      debugPrint('[InvoicesLocalDataSource] Error filtering invoices: $e');
      rethrow;
    }
  }

  /// Search invoices by invoice number or order ID
  Future<List<InvoiceModel>> searchInvoices(String query) async {
    try {
      if (query.isEmpty) {
        return getAllInvoices();
      }

      final allInvoices = await getAllInvoices();
      final filtered = allInvoices
          .where(
            (invoice) =>
                invoice.invoiceNumber.toLowerCase().contains(
                  query.toLowerCase(),
                ) ||
                (invoice.orderId?.toLowerCase().contains(query.toLowerCase()) ??
                    false),
          )
          .toList();

      debugPrint(
        '[InvoicesLocalDataSource] Found ${filtered.length} invoices matching "$query"',
      );
      return filtered;
    } catch (e) {
      debugPrint('[InvoicesLocalDataSource] Error searching invoices: $e');
      rethrow;
    }
  }

  /// Get invoice by ID
  Future<InvoiceModel?> getInvoiceById(String invoiceId) async {
    try {
      final allInvoices = await getAllInvoices();
      final invoice = allInvoices.firstWhere(
        (invoice) => invoice.invoiceId == invoiceId,
        orElse: () => throw Exception('Invoice not found: $invoiceId'),
      );

      debugPrint(
        '[InvoicesLocalDataSource] Found invoice: ${invoice.invoiceNumber}',
      );
      return invoice;
    } catch (e) {
      debugPrint('[InvoicesLocalDataSource] Error getting invoice: $e');
      return null;
    }
  }

  /// Get overdue invoices
  Future<List<InvoiceModel>> getOverdueInvoices() async {
    try {
      final allInvoices = await getAllInvoices();
      final overdue = allInvoices
          .where((invoice) => invoice.isOverdue)
          .toList();

      debugPrint(
        '[InvoicesLocalDataSource] Found ${overdue.length} overdue invoices',
      );
      return overdue;
    } catch (e) {
      debugPrint(
        '[InvoicesLocalDataSource] Error getting overdue invoices: $e',
      );
      rethrow;
    }
  }

  /// Get unpaid invoices (issued but not paid)
  Future<List<InvoiceModel>> getUnpaidInvoices() async {
    try {
      final allInvoices = await getAllInvoices();
      final unpaid = allInvoices
          .where(
            (invoice) => invoice.status.name == 'issued' && !invoice.isPaid,
          )
          .toList();

      debugPrint(
        '[InvoicesLocalDataSource] Found ${unpaid.length} unpaid invoices',
      );
      return unpaid;
    } catch (e) {
      debugPrint('[InvoicesLocalDataSource] Error getting unpaid invoices: $e');
      rethrow;
    }
  }

  /// Mock invoices JSON data
  /// Matches the HTML design with 5 sample invoices
  static const String _mockInvoicesJson = '''
  [
    {
      "invoice_id": "inv_001",
      "invoice_number": "INV001",
      "user_id": "user_001",
      "order_id": "ord_001",
      "invoice_type": "sales",
      "issue_date": "2025-08-03T00:00:00.000Z",
      "due_date": "2025-08-13T00:00:00.000Z",
      "currency": "VND",
      "subtotal_amount": 85000000,
      "tax_amount": 0,
      "discount_amount": 0,
      "shipping_amount": 0,
      "total_amount": 85000000,
      "amount_paid": 25000000,
      "amount_remaining": 60000000,
      "status": "overdue",
      "payment_terms": "Thanh toán trong 10 ngày",
      "notes": "Hóa đơn cho đơn hàng DH001234",
      "created_at": "2025-08-03T00:00:00.000Z",
      "updated_at": "2025-08-03T00:00:00.000Z"
    },
    {
      "invoice_id": "inv_002",
      "invoice_number": "INV002",
      "user_id": "user_001",
      "order_id": "ord_002",
      "invoice_type": "sales",
      "issue_date": "2025-07-15T00:00:00.000Z",
      "due_date": "2025-08-15T00:00:00.000Z",
      "currency": "VND",
      "subtotal_amount": 42500000,
      "tax_amount": 0,
      "discount_amount": 0,
      "shipping_amount": 0,
      "total_amount": 42500000,
      "amount_paid": 0,
      "amount_remaining": 42500000,
      "status": "issued",
      "payment_terms": "Thanh toán trong 30 ngày",
      "notes": "Hóa đơn cho đơn hàng DH001233",
      "created_at": "2025-07-15T00:00:00.000Z",
      "updated_at": "2025-07-15T00:00:00.000Z"
    },
    {
      "invoice_id": "inv_003",
      "invoice_number": "INV003",
      "user_id": "user_001",
      "order_id": "ord_003",
      "invoice_type": "sales",
      "issue_date": "2025-06-01T00:00:00.000Z",
      "due_date": "2025-07-01T00:00:00.000Z",
      "currency": "VND",
      "subtotal_amount": 150000000,
      "tax_amount": 0,
      "discount_amount": 0,
      "shipping_amount": 0,
      "total_amount": 150000000,
      "amount_paid": 75000000,
      "amount_remaining": 75000000,
      "status": "partiallyPaid",
      "payment_terms": "Thanh toán theo tiến độ",
      "notes": "Hóa đơn cho đơn hàng DH001232 - Đã thanh toán 50%",
      "created_at": "2025-06-01T00:00:00.000Z",
      "updated_at": "2025-06-15T00:00:00.000Z"
    },
    {
      "invoice_id": "inv_004",
      "invoice_number": "INV004",
      "user_id": "user_001",
      "order_id": "ord_004",
      "invoice_type": "sales",
      "issue_date": "2025-05-10T00:00:00.000Z",
      "due_date": "2025-06-10T00:00:00.000Z",
      "currency": "VND",
      "subtotal_amount": 32800000,
      "tax_amount": 0,
      "discount_amount": 0,
      "shipping_amount": 0,
      "total_amount": 32800000,
      "amount_paid": 32800000,
      "amount_remaining": 0,
      "status": "paid",
      "payment_terms": "Thanh toán ngay",
      "notes": "Hóa đơn cho đơn hàng DH001231 - Đã thanh toán đầy đủ",
      "created_at": "2025-05-10T00:00:00.000Z",
      "updated_at": "2025-05-12T00:00:00.000Z"
    },
    {
      "invoice_id": "inv_005",
      "invoice_number": "INV005",
      "user_id": "user_001",
      "order_id": "ord_005",
      "invoice_type": "sales",
      "issue_date": "2025-04-20T00:00:00.000Z",
      "due_date": "2025-05-20T00:00:00.000Z",
      "currency": "VND",
      "subtotal_amount": 95300000,
      "tax_amount": 0,
      "discount_amount": 0,
      "shipping_amount": 0,
      "total_amount": 95300000,
      "amount_paid": 0,
      "amount_remaining": 95300000,
      "status": "overdue",
      "payment_terms": "Thanh toán trong 30 ngày",
      "notes": "Hóa đơn cho đơn hàng DH001230 - Đã quá hạn",
      "created_at": "2025-04-20T00:00:00.000Z",
      "updated_at": "2025-04-20T00:00:00.000Z"
    }
  ]
  ''';
}
