import type { KpiKey } from '../types';
import type { VehicleRecord } from '../types';

export const KPI_CARDS: Array<{ key: KpiKey; title: string; desc: string }> = [
  { key: 'all', title: '所有营运车辆', desc: '未退出运营，且可以用来交付的车辆' },
  { key: 'lease', title: '租赁车辆', desc: '运营状态为「租赁」的车辆，已交付租赁业务项目' },
  { key: 'self', title: '自营车辆', desc: '运营状态为「自营」的车辆，已交付自营业务项目' },
  { key: 'stock', title: '库存车辆', desc: '显示运营状态为「可运营」「待运营」的车辆，这两种状态的车辆均为在库车辆' },
  { key: 'nonOperating', title: '非运营车辆', desc: '公务车、观光车等非运营车辆，不可用于租赁或自营业务使用' },
  { key: 'exit', title: '退出运营车辆', desc: '已退出运营的车辆，不可用于租赁或自营业务使用' },
  { key: 'licenseAbnormal', title: '证照异常车辆', desc: '证照状态为「异常」的车辆，需要将行驶证有效期更新至未过期状态才可进行交车' },
  { key: 'insuranceAbnormal', title: '保险异常车辆', desc: '显示保险状态为「异常」的车辆，交强险或商业险已到期，在完成交强险和商业险采购前无法用于租赁和自营业务' },
];

export const OPERATE_STATUS_OPTIONS = ['租赁', '自营', '可运营', '待运营', '退出运营'];
export const PROJECT_TYPE_OPTIONS = ['租赁', '自营'];
export const VEHICLE_SOURCE_OPTIONS = ['自有', '外租', '挂靠'];
export const INSURANCE_STATUS_OPTIONS = ['正常', '异常'];
export const VEHICLE_STATUS_OPTIONS = [
  '待验车', '未备车', '已备车', '待交车', '已交车', '待还车',
  '销售中', '替换中', '调拨中', '异动中', '三方退租中', '无',
];

export function buildYearOptions(): string[] {
  const year = new Date().getFullYear();
  return Array.from({ length: 13 }, (_, index) => String(year - index));
}

export interface VehicleEditForm {
  parking: string;
  operateStatus: string;
  vehicleStatus: string;
  ownership: string;
  operateCompany: string;
  vehicleSource: string;
  leaseCompany: string;
  year: string;
  purchaseDate: string;
}

export function createVehicleEditForm(record: VehicleRecord): VehicleEditForm {
  return {
    parking: isEmpty(record.parking) ? '' : String(record.parking),
    operateStatus: record.operateStatus || '',
    vehicleStatus: record.vehicleStatus || '',
    ownership: isEmpty(record.ownership) ? '' : String(record.ownership),
    operateCompany: record.operateCompany || '',
    vehicleSource: record.vehicleSource || '',
    leaseCompany: isEmpty(record.leaseCompany) ? '' : String(record.leaseCompany),
    year: isEmpty(record.year) ? '' : String(record.year),
    purchaseDate: isEmpty(record.purchaseDate) ? '' : String(record.purchaseDate),
  };
}

export function applyVehicleEditForm(record: VehicleRecord, form: VehicleEditForm): VehicleRecord {
  return {
    ...record,
    parking: form.parking || '-',
    operateStatus: form.operateStatus,
    vehicleStatus: form.vehicleStatus,
    ownership: form.ownership.trim() || '-',
    operateCompany: form.operateCompany || record.operateCompany,
    vehicleSource: form.vehicleSource || record.vehicleSource,
    leaseCompany: form.leaseCompany.trim() || '-',
    year: form.year || record.year,
    purchaseDate: form.purchaseDate || record.purchaseDate,
  };
}

export const PARKING_REGION_MAP: Record<string, string> = {
  '广州开创大道停车场': '广东省-广州市',
  '开创大道云埔宏仁便民停车场': '广东省-广州市',
  '广州现代停车场': '广东省-广州市',
  '平湖停车场': '浙江省-嘉兴市',
  '嘉兴公司楼下氢能展厅': '浙江省-嘉兴市',
  '汇通检测站停车场': '浙江省-嘉兴市',
  '成都宇通服务站停车场': '四川省-成都市',
  '北京一汽宏特停车场': '北京市-北京市',
};

export const PARKING_OPTIONS = Object.keys(PARKING_REGION_MAP);

export const OPS_STAFF = [
  { name: '张伟', role: '运维专员', regions: ['浙江省-嘉兴市'] },
  { name: '李娜', role: '运维助理', regions: ['广东省-广州市'] },
  { name: '王强', role: '运维主管', regions: ['浙江省-嘉兴市', '广东省-广州市'] },
  { name: '赵敏', role: '运维专员', regions: ['上海市-上海市'] },
];

export function isEmpty(value: unknown): boolean {
  return value === null || value === undefined || value === '' || value === '-';
}

export function displayText(value: unknown, fallback = '—'): string {
  if (isEmpty(value)) return fallback;
  return String(value);
}

/** 详情页空值展示为「无」 */
export function displayUILabel(value: unknown): string {
  return displayText(value, '无');
}

/** 沪牌：车牌以「沪」开头 */
export function isShanghaiPlate(plateNo: string): boolean {
  return String(plateNo || '').trim().startsWith('沪');
}

/** 当前位置列：优先展示 GPS 定位具体地址 */
export function resolveGpsLocationAddress(record: VehicleRecord, fallback = '—'): string {
  if (!isEmpty(record.locationAddress)) {
    return String(record.locationAddress).trim();
  }
  return displayText(record.location, fallback);
}

export function normalizePlate(plate: string): string {
  return plate.replace(/\s+/g, '').toUpperCase();
}

export function parseMultiPlates(text: string): string[] {
  const raw = text.trim();
  if (!raw) return [];
  const lines = raw.split(/\r?\n/).map((l) => l.trim()).filter(Boolean);
  const plates: string[] = [];
  const seen = new Set<string>();
  for (const line of lines) {
    const parts = line.split(/[,，、]/).map((p) => p.trim()).filter(Boolean);
    for (const p of parts) {
      const n = normalizePlate(p);
      if (n && !seen.has(n)) {
        seen.add(n);
        plates.push(n);
      }
    }
  }
  return plates;
}

export const MUNICIPALITIES = ['北京市', '上海市', '天津市', '重庆市'];

export const OPERATE_CITY_SEED = [
  '北京市-北京市', '上海市-上海市', '天津市-天津市', '重庆市-重庆市',
  '广东省-广州市', '广东省-深圳市', '广东省-佛山市', '广东省-韶关市',
  '浙江省-嘉兴市', '浙江省-杭州市', '浙江省-湖州市', '浙江省-金华市', '浙江省-宁波市', '浙江省-绍兴市',
  '江苏省-常州市', '江苏省-南京市', '江苏省-苏州市',
  '四川省-成都市', '四川省-德阳市', '河南省-开封市', '湖北省-武汉市',
  '陕西省-西安市', '新疆维吾尔自治区-乌鲁木齐市',
];

export function formatOperateCity(location: string, fallback = '—'): string {
  if (isEmpty(location)) return fallback;
  const loc = String(location).trim();
  for (const municipality of MUNICIPALITIES) {
    if (loc.startsWith(municipality)) return `${municipality}-${municipality}`;
  }
  const provMatch = loc.match(/^(.*?(?:省|自治区))/);
  if (!provMatch) return loc.includes('市') ? loc : fallback;
  const province = provMatch[1];
  const rest = loc.slice(provMatch[1].length);
  const cityMatch = rest.match(/^(.+?市)/) || rest.match(/^(.+?(?:州|盟|地区))/);
  if (cityMatch) return `${province}-${cityMatch[1]}`;
  return province;
}

export type OperateCitySource = '车机' | 'GPS' | '人工';

export function resolveOperateCitySource(record: VehicleRecord): OperateCitySource | '' {
  if (isEmpty(record.location)) return '';
  if (record.operateCitySource) return record.operateCitySource;
  if (record.telematicsLinked === true) return '车机';
  if (record.telematicsLinked === false && !isEmpty(record.gpsTime)) return 'GPS';
  if (!isEmpty(record.gpsTime)) return 'GPS';
  return '人工';
}

export function operateCitySourceTagClass(source: OperateCitySource): string {
  if (source === '车机') return 'vm-tag vm-tag-teal';
  if (source === 'GPS') return 'vm-tag vm-tag-gps';
  return 'vm-tag vm-tag-manual';
}

export function canEditOperateCity(record: VehicleRecord): boolean {
  return resolveOperateCitySource(record) === '人工';
}

export function parseRegionParts(regionText: string): { province: string; city: string } {
  const text = isEmpty(regionText) ? '' : String(regionText).trim();
  if (!text) return { province: '', city: '' };
  const dash = text.indexOf('-');
  if (dash >= 0) {
    return {
      province: text.slice(0, dash).trim(),
      city: text.slice(dash + 1).trim(),
    };
  }
  if (text.includes('省') || text.includes('自治区') || text.endsWith('市')) {
    return { province: text, city: '' };
  }
  return { province: '', city: text };
}

export function isNonOperating(record: VehicleRecord): boolean {
  return record.vehicleLedgerType === '非运营车辆';
}

export function isOperatingFleet(record: VehicleRecord): boolean {
  if (isNonOperating(record)) return false;
  if (record.operateStatus === '退出运营') return false;
  return true;
}

export function daysUntilExpire(dateStr: string): number | null {
  if (isEmpty(dateStr)) return null;
  const d = new Date(dateStr.slice(0, 10));
  if (Number.isNaN(d.getTime())) return null;
  const today = new Date();
  today.setHours(0, 0, 0, 0);
  d.setHours(0, 0, 0, 0);
  return Math.round((d.getTime() - today.getTime()) / 86400000);
}

export function isLicenseExpired(record: VehicleRecord): boolean {
  const days = daysUntilExpire(record.inspectExpire);
  return days !== null && days < 0;
}

export function matchKpi(record: VehicleRecord, key: KpiKey): boolean {
  const status = record.operateStatus;
  switch (key) {
    case 'all': return isOperatingFleet(record);
    case 'lease': return status === '租赁';
    case 'self': return status === '自营';
    case 'stock': return status === '可运营' || status === '待运营';
    case 'nonOperating': return isNonOperating(record);
    case 'exit': return status === '退出运营';
    case 'licenseAbnormal': return isLicenseExpired(record);
    case 'insuranceAbnormal': return record.insuranceStatus === '异常';
    default: return true;
  }
}

export function countKpi(records: VehicleRecord[], key: KpiKey): number {
  return records.filter((r) => matchKpi(r, key)).length;
}

export function resolveProjectName(record: VehicleRecord): string {
  return resolveProjectDelivery(record).projectName;
}

export interface ProjectDeliveryInfo {
  projectName: string;
  contractNo: string;
  companyName: string;
}

export function isDeliveredToLeaseOrSelfProject(record: VehicleRecord): boolean {
  return record.operateStatus === '租赁' || record.operateStatus === '自营';
}

/** 所属项目：仅展示已交付至租赁/自营项目的三元信息 */
export function resolveProjectDelivery(
  record: VehicleRecord,
  emptyLabel = '—',
): ProjectDeliveryInfo {
  if (!isDeliveredToLeaseOrSelfProject(record)) {
    return {
      projectName: emptyLabel,
      contractNo: emptyLabel,
      companyName: emptyLabel,
    };
  }
  return {
    projectName: displayText(record.projectName, emptyLabel),
    contractNo: displayText(record.contractNo, emptyLabel),
    companyName: displayText(record.customer, emptyLabel),
  };
}

export function resolveThirdPartyLeaseCompany(record: VehicleRecord, emptyLabel = '—'): string {
  if (record.vehicleSource !== '外租') return emptyLabel;
  return displayText(record.leaseCompany, emptyLabel);
}

export function resolveVehicleRegion(record: VehicleRecord, fallback = '未指定区域'): string {
  const region = PARKING_REGION_MAP[record.parking] || formatOperateCity(record.location, '');
  return region || fallback;
}

export function resolveOpsStaffCandidates(record: VehicleRecord): typeof OPS_STAFF {
  const region = resolveVehicleRegion(record, '');
  if (!region) return OPS_STAFF;
  return OPS_STAFF.filter((staff) => (
    staff.regions.some((r) => region.includes(r.split('-')[1]?.replace('市', '') || r))
  ));
}

export function resolveOpsManagers(record: VehicleRecord): string[] {
  if (record.opsManagers?.length) return record.opsManagers;
  return resolveOpsStaffCandidates(record).map((s) => s.name).slice(0, 2);
}

export function formatMileage(mile: string, force = false, emptyFallback = '—'): string {
  if (isEmpty(mile)) return force ? '0 km' : emptyFallback;
  const num = Number(mile);
  if (!Number.isFinite(num)) return String(mile);
  return `${num.toLocaleString('zh-CN', { minimumFractionDigits: 0, maximumFractionDigits: 2 })} km`;
}

export function formatDateYmd(raw: string): string {
  if (isEmpty(raw)) return '';
  return raw.slice(0, 10);
}

export function formatGpsTime(raw: string, emptyLabel = '—'): string {
  if (isEmpty(raw)) return emptyLabel;
  const text = String(raw).trim().replace('T', ' ');
  const match = text.match(/^(\d{4}-\d{2}-\d{2}[ T]\d{2}:\d{2}:\d{2})/);
  if (match) return match[1].replace('T', ' ');
  if (/^\d{4}-\d{2}-\d{2}$/.test(text)) return `${text} 00:00:00`;
  return text.slice(0, 19);
}

/** 交还车里程，无数据时返回空 */
export function formatHandoverMileage(mile: string, emptyLabel = ''): string {
  if (isEmpty(mile)) return emptyLabel;
  const num = Number(mile);
  if (!Number.isFinite(num)) return String(mile);
  return `${num.toLocaleString('zh-CN', { minimumFractionDigits: 0, maximumFractionDigits: 2 })} km`;
}

/** 交还车时间，精确到分钟 */
export function formatHandoverDateTimeMinute(raw: string, emptyLabel = ''): string {
  if (isEmpty(raw)) return emptyLabel;
  const text = String(raw).trim().replace('T', ' ');
  const match = text.match(/^(\d{4}-\d{2}-\d{2})[ T](\d{2}:\d{2})/);
  if (match) return `${match[1]} ${match[2]}`;
  if (/^\d{4}-\d{2}-\d{2}$/.test(text)) return text;
  return text.slice(0, 16);
}

export interface VehicleGpsCoords {
  lat: number;
  lng: number;
}

const LOCATION_COORDS: Record<string, [number, number]> = {
  '广东省广州市': [23.1291, 113.2644],
  '广东省佛山市': [23.0218, 113.1219],
  '广东省': [23.3790, 113.7633],
  '上海市奉贤区': [30.9128, 121.4745],
  '上海市': [31.2304, 121.4737],
  '河南省开封市': [34.7972, 114.3075],
  '江苏省常州市': [31.8122, 119.9692],
  '江苏省苏州市': [31.2989, 120.5853],
  '江苏省南京市': [32.0603, 118.7969],
  '浙江省嘉兴市': [30.7461, 120.7555],
  '浙江省湖州市': [30.8930, 120.0881],
  '浙江省杭州市': [30.2741, 120.1551],
  '浙江省金华市': [29.0784, 119.6476],
  '浙江省宁波市': [29.8683, 121.5440],
  '浙江省绍兴市': [30.0303, 120.5800],
  '浙江省': [29.1411, 120.0985],
  '四川省成都市': [30.5728, 104.0668],
  '四川省德阳市': [31.1270, 104.3980],
  '四川省': [30.6517, 104.0757],
  '北京市大兴区': [39.7269, 116.3414],
  '北京市': [39.9042, 116.4074],
  '湖北省武汉市': [30.5928, 114.3055],
  '陕西省西安市': [34.3416, 108.9398],
  '重庆市大渡口区': [29.4840, 106.4823],
  '新疆维吾尔自治区乌鲁木齐市': [43.8256, 87.6168],
};

function findLocationCoords(location: string): [number, number] | null {
  if (isEmpty(location)) return null;
  const loc = String(location).trim();
  if (LOCATION_COORDS[loc]) return LOCATION_COORDS[loc];
  const sorted = Object.entries(LOCATION_COORDS).sort((a, b) => b[0].length - a[0].length);
  for (const [key, coords] of sorted) {
    if (loc.startsWith(key) || loc.includes(key)) return coords;
  }
  return null;
}

/** 解析车辆 GPS 坐标（样例数据按城市基准点 + 车辆 id 偏移模拟实际定位） */
export function resolveVehicleGpsCoords(record: VehicleRecord): VehicleGpsCoords | null {
  if (typeof record.gpsLat === 'number' && typeof record.gpsLng === 'number') {
    return { lat: record.gpsLat, lng: record.gpsLng };
  }
  const base = findLocationCoords(record.location);
  if (!base) return null;
  const n = parseInt(record.id, 10) || 1;
  return {
    lat: base[0] + ((n % 17) - 8) * 0.006,
    lng: base[1] + ((n % 23) - 11) * 0.006,
  };
}

export function canOpenLocationMap(record: VehicleRecord): boolean {
  if (isEmpty(resolveGpsLocationAddress(record))) return false;
  return resolveVehicleGpsCoords(record) !== null;
}

export function buildMapEmbedUrl(lat: number, lng: number): string {
  const delta = 0.02;
  const bbox = `${lng - delta},${lat - delta},${lng + delta},${lat + delta}`;
  return `https://www.openstreetmap.org/export/embed.html?bbox=${encodeURIComponent(bbox)}&layer=mapnik&marker=${lat}%2C${lng}`;
}
