import type {
  LeaseBusinessDetailRow,
  LeaseDetailFilters,
  LeaseDetailKpiSummary,
} from '../types';
import { EMPTY_LEASE_DETAIL_KPI } from '../types';
import { resolveDetailPaymentStatus } from './payment-status';

export function detailRowYearMonth(row: LeaseBusinessDetailRow): string {
  return `${row.year}-${String(row.month).padStart(2, '0')}`;
}

export function formatMoney(value: number): string {
  return value.toLocaleString('zh-CN', { minimumFractionDigits: 2, maximumFractionDigits: 2 });
}

export function displayText(value: unknown): string {
  if (value === null || value === undefined || value === '' || value === '/') return '';
  return String(value);
}

export function displayMoney(value: number, treatZeroAsEmpty = true): string {
  if (treatZeroAsEmpty && value === 0) return '';
  return formatMoney(value);
}

export function displayDeposit(value: number | string): string {
  if (value === '/' || value === '' || value === null || value === undefined) return '';
  if (typeof value === 'number') return displayMoney(value);
  return String(value);
}

export function displayOutstanding(value: number): { text: string; warn: boolean } {
  if (value === 0) return { text: '0.00', warn: false };
  return { text: formatMoney(value), warn: value > 0 };
}

export function applyDetailFilters(
  rows: LeaseBusinessDetailRow[],
  filters: LeaseDetailFilters,
): LeaseBusinessDetailRow[] {
  const customerQ = filters.customerName.trim().toLowerCase();
  return rows.filter((row) => {
    if (filters.statMonth && detailRowYearMonth(row) !== filters.statMonth) return false;
    if (filters.businessDept && row.businessDept !== filters.businessDept) return false;
    if (filters.salesperson && row.salesperson !== filters.salesperson) return false;
    if (customerQ && !row.customerName.toLowerCase().includes(customerQ)) return false;
    if (filters.paymentStatus) {
      const status = resolveDetailPaymentStatus(row.receivableTotal, row.receivedAmount);
      if (status !== filters.paymentStatus) return false;
    }
    if (filters.plateNos.length > 0 && !filters.plateNos.includes(row.plateNo)) return false;
    return true;
  });
}

export function sumDetailKpi(rows: LeaseBusinessDetailRow[]): LeaseDetailKpiSummary {
  if (rows.length === 0) return { ...EMPTY_LEASE_DETAIL_KPI };

  return rows.reduce(
    (acc, row) => ({
      deposit: acc.deposit + (typeof row.deposit === 'number' ? row.deposit : 0),
      contractRent: acc.contractRent + row.contractRent,
      receivableTotal: acc.receivableTotal + row.receivableTotal,
      receivableRent: acc.receivableRent + row.receivableRent,
      monthlyIncome: acc.monthlyIncome + row.monthlyIncome,
      monthlyRent: acc.monthlyRent + row.monthlyRent,
      maintenanceIncome: acc.maintenanceIncome + row.maintenanceIncome,
      insuranceSurcharge: acc.insuranceSurcharge + row.insuranceSurcharge,
      opsFeeIncome: acc.opsFeeIncome + row.opsFeeIncome,
      otherIncome: acc.otherIncome + row.otherIncome,
      mileageDeduction: acc.mileageDeduction + row.mileageDeduction,
      otherDeduction: acc.otherDeduction + row.otherDeduction,
      receivedAmount: acc.receivedAmount + row.receivedAmount,
      outstanding: acc.outstanding + row.outstanding,
      vehicleStandardCost: acc.vehicleStandardCost + row.vehicleStandardCost,
      vehicleActualCost: acc.vehicleActualCost + row.vehicleActualCost,
      insuranceFee: acc.insuranceFee + row.insuranceFee,
      hydrogenFee: acc.hydrogenFee + row.hydrogenFee,
      opsFeeCost: acc.opsFeeCost + row.opsFeeCost,
      brokerageFee: acc.brokerageFee + row.brokerageFee,
      otherCost: acc.otherCost + row.otherCost,
      totalCost: acc.totalCost + row.totalCost,
      profitLoss: acc.profitLoss + row.profitLoss,
    }),
    { ...EMPTY_LEASE_DETAIL_KPI },
  );
}

export function buildDetailOptions(
  rows: LeaseBusinessDetailRow[],
  key: 'businessDept' | 'salesperson',
): string[] {
  const set = new Set<string>();
  rows.forEach((row) => {
    const value = row[key];
    if (value.trim()) set.add(value);
  });
  return Array.from(set).sort((a, b) => a.localeCompare(b, 'zh-CN'));
}

export function buildDetailMonthOptions(rows: LeaseBusinessDetailRow[]): string[] {
  const set = new Set<string>();
  rows.forEach((row) => set.add(detailRowYearMonth(row)));
  return Array.from(set).sort((a, b) => b.localeCompare(a));
}
