// utils/parseFullAddress.js
// 完整的独立地址解析函数（支持返回完整格式：含代码、经纬度、POI等）

// ===================== 基础配置 - 可根据实际需求扩展 =====================
// 1. 省市区名称+代码映射表（简化版，如需完整数据可从areaData导入）
const AREA_CODE_MAP = {
  // 省份映射（名称 -> { code, 下属城市 }）
  province: {
    "北京市": { code: "110000", cities: ["北京市"] },
    "天津市": { code: "120000", cities: ["天津市"] },
    "河北省": { code: "130000", cities: ["石家庄市", "唐山市", "秦皇岛市"] },
    "山西省": { code: "140000", cities: ["太原市", "大同市"] },
    "内蒙古自治区": { code: "150000", cities: ["呼和浩特市", "包头市"] },
    "辽宁省": { code: "210000", cities: ["沈阳市", "大连市"] },
    "吉林省": { code: "220000", cities: ["长春市", "吉林市"] },
    "黑龙江省": { code: "230000", cities: ["哈尔滨市", "齐齐哈尔市"] },
    "上海市": { code: "310000", cities: ["上海市"] },
    "江苏省": { code: "320000", cities: ["南京市", "无锡市", "苏州市"] },
    "浙江省": { code: "330000", cities: ["杭州市", "宁波市", "温州市"] },
    "安徽省": { code: "340000", cities: ["合肥市", "芜湖市"] },
    "福建省": { code: "350000", cities: ["福州市", "厦门市"] },
    "江西省": { code: "360000", cities: ["南昌市", "九江市"] },
    "山东省": { code: "370000", cities: ["济南市", "青岛市"] },
    "河南省": { code: "410000", cities: ["郑州市", "洛阳市"] },
    "湖北省": { code: "420000", cities: ["武汉市", "宜昌市"] },
    "湖南省": { code: "430000", cities: ["长沙市", "株洲市"] },
    "广东省": { code: "440000", cities: ["广州市", "深圳市", "佛山市"] },
    "广西壮族自治区": { code: "450000", cities: ["南宁市", "柳州市"] },
    "海南省": { code: "460000", cities: ["海口市", "三亚市"] },
    "重庆市": { code: "500000", cities: ["重庆市"] },
    "四川省": { code: "510000", cities: ["成都市", "绵阳市"] },
    "贵州省": { code: "520000", cities: ["贵阳市", "遵义市"] },
    "云南省": { code: "530000", cities: ["昆明市", "大理市"] },
    "西藏自治区": { code: "540000", cities: ["拉萨市"] },
    "陕西省": { code: "610000", cities: ["西安市", "宝鸡市"] },
    "甘肃省": { code: "620000", cities: ["兰州市", "天水市"] },
    "青海省": { code: "630000", cities: ["西宁市"] },
    "宁夏回族自治区": { code: "640000", cities: ["银川市"] },
    "新疆维吾尔自治区": { code: "650000", cities: ["乌鲁木齐市"] },
    "台湾省": { code: "710000", cities: ["台北市", "高雄市"] },
    "香港特别行政区": { code: "810000", cities: ["香港特别行政区"] },
    "澳门特别行政区": { code: "820000", cities: ["澳门特别行政区"] }
  },
  // 城市映射（名称 -> { code, 下属区县 }）
  city: {
    "北京市": { code: "110100", districts: ["东城区", "西城区", "朝阳区", "海淀区", "顺义区"] },
    "天津市": { code: "120100", districts: ["和平区", "河东区", "西青区", "北辰区"] },
    "深圳市": { code: "440300", districts: ["罗湖区", "福田区", "南山区", "宝安区", "龙岗区"] },
    "广州市": { code: "440100", districts: ["越秀区", "海珠区", "天河区"] },
    "上海市": { code: "310100", districts: ["黄浦区", "徐汇区", "长宁区"] },
    "杭州市": { code: "330100", districts: ["上城区", "拱墅区", "西湖区"] }
  },
  // 区县映射（名称 -> { code, 经纬度 }）
  district: {
    "东城区": { code: "110101", lat: 39.938874, lng: 116.407413 },
    "西城区": { code: "110102", lat: 39.914745, lng: 116.366761 },
    "朝阳区": { code: "110105", lat: 39.948859, lng: 116.487501 },
    "海淀区": { code: "110108", lat: 39.992947, lng: 116.316486 },
    "顺义区": { code: "110113", lat: 40.111562, lng: 116.658249 }, // 修正你示例中的错误代码（120101是天津和平区）
    "南山区": { code: "440305", lat: 22.542895, lng: 113.941649 },
    "福田区": { code: "440304", lat: 22.543096, lng: 114.057865 },
    "罗湖区": { code: "440303", lat: 22.552726, lng: 114.104663 }
  }
};

// 2. 标准省市区名称集合（从映射表中提取，用于匹配）
const PROVINCES = Object.keys(AREA_CODE_MAP.province);
const CITIES = Object.keys(AREA_CODE_MAP.city);
const DISTRICTS = Object.keys(AREA_CODE_MAP.district);

// 3. POI关键词（用于提取建筑物名称）
const POI_KEYWORDS = ["大厦", "小区", "花园", "公寓", "写字楼", "酒店", "广场", "中心", "别墅", "商铺"];

// ===================== 工具函数 =====================
/**
 * 提取手机号（纯函数）
 * @param {string} text - 输入文本
 * @returns {string} 提取的手机号
 */
function extractPhone(text) {
  if (!text) return '';
  const phoneReg = /1[3-9]\d{9}|1[3-9]\d{2}[- ]?\d{4}[- ]?\d{4}/g;
  const match = text.match(phoneReg);
  return match ? match[0].replace(/\D/g, '') : '';
}

/**
 * 提取姓名（纯函数）
 * @param {string} text - 输入文本
 * @returns {string} 提取的姓名
 */
function extractName(text) {
  if (!text) return '';
  const nameReg = /[\u4e00-\u9fa5]{2,4}/;
  const match = text.match(nameReg);
  return match ? match[0] : '';
}

/**
 * 提取POI名称（从详细地址中提取建筑物名称）
 * @param {string} detail - 详细地址
 * @returns {string} POI名称
 */
function extractPOIName(detail) {
  if (!detail) return '';
  // 匹配包含POI关键词的连续字符（2-10字）
  const poiReg = new RegExp(`[\\u4e00-\\u9fa5a-zA-Z0-9]{2,10}(${POI_KEYWORDS.join('|')})`, 'g');
  const matches = detail.match(poiReg);
  return matches && matches.length > 0 ? matches[0] : '';
}

/**
 * 获取行政区划代码
 * @param {string} province - 省份名称
 * @param {string} city - 城市名称
 * @param {string} district - 区县名称
 * @returns {object} { provinceCode, cityCode, districtCode }
 */
function getAreaCodes(province, city, district) {
  return {
    provinceCode: AREA_CODE_MAP.province[province]?.code || '',
    cityCode: AREA_CODE_MAP.city[city]?.code || '',
    districtCode: AREA_CODE_MAP.district[district]?.code || ''
  };
}

/**
 * 获取经纬度（优先区县，无则城市，无则省份）
 * @param {string} province - 省份名称
 * @param {string} city - 城市名称
 * @param {string} district - 区县名称
 * @returns {object} { latitude, longitude }
 */
function getLatLng(province, city, district) {
  // 区县经纬度
  if (district && AREA_CODE_MAP.district[district]) {
    return {
      latitude: AREA_CODE_MAP.district[district].lat,
      longitude: AREA_CODE_MAP.district[district].lng
    };
  }
  // 城市默认经纬度（可扩展城市经纬度映射）
  const cityLatLngMap = {
    "北京市": { lat: 39.9042, lng: 116.4074 },
    "上海市": { lat: 31.2304, lng: 121.4737 },
    "深圳市": { lat: 22.5431, lng: 114.0579 },
    "广州市": { lat: 23.1289, lng: 113.2655 }
  };
  if (city && cityLatLngMap[city]) {
    return {
      latitude: cityLatLngMap[city].lat,
      longitude: cityLatLngMap[city].lng
    };
  }
  // 省份默认经纬度
  const provinceLatLngMap = {
    "广东省": { lat: 23.1289, lng: 113.2655 },
    "江苏省": { lat: 32.0473, lng: 118.7624 },
    "浙江省": { lat: 30.2795, lng: 120.1576 }
  };
  if (province && provinceLatLngMap[province]) {
    return {
      latitude: provinceLatLngMap[province].lat,
      longitude: provinceLatLngMap[province].lng
    };
  }
  // 默认经纬度（北京）
  return { latitude: 39.9042, longitude: 116.4074 };
}

/**
 * 识别省市区（纯函数，基于映射表优化匹配准确性）
 * @param {string} text - 输入文本
 * @returns {object} { province, city, district, remainingText }
 */
function recognizeArea(text) {
  if (!text) return { province: '', city: '', district: '', remainingText: '' };

  let province = '';
  let city = '';
  let district = '';
  let remainingText = text.trim();

  // 1. 匹配省份（优先长名称，避免短名称误匹配）
  const sortedProvinces = [...PROVINCES].sort((a, b) => b.length - a.length);
  for (const p of sortedProvinces) {
    if (remainingText.includes(p)) {
      province = p;
      remainingText = remainingText.replace(p, '').trim();
      break;
    }
  }

  // 2. 匹配城市（基于已选省份过滤，提升准确性）
  let candidateCities = [...CITIES].sort((a, b) => b.length - a.length);
  if (province && AREA_CODE_MAP.province[province].cities) {
    candidateCities = candidateCities.filter(c => AREA_CODE_MAP.province[province].cities.includes(c));
  }
  for (const c of candidateCities) {
    if (remainingText.includes(c)) {
      city = c;
      remainingText = remainingText.replace(c, '').trim();
      break;
    }
  }

  // 3. 匹配区县（基于已选城市过滤）
  let candidateDistricts = [...DISTRICTS].sort((a, b) => b.length - a.length);
  if (city && AREA_CODE_MAP.city[city].districts) {
    candidateDistricts = candidateDistricts.filter(d => AREA_CODE_MAP.city[city].districts.includes(d));
  }
  for (const d of candidateDistricts) {
    if (remainingText.includes(d)) {
      district = d;
      remainingText = remainingText.replace(d, '').trim();
      break;
    }
  }

  return { province, city, district, remainingText };
}

/**
 * 完整地址解析（返回完整格式：含代码、经纬度、POI等）
 * @param {string} text - 输入文本
 * @param {object} [options] - 可选配置
 * @param {boolean} [options.isDefault=false] - 是否默认地址
 * @returns {object} 完整解析结果
 */
const parseFullAddress = (text, options = {}) => {
  const { isDefault = false } = options;
  if (!text) return {
    receiver: '',
    phone: '',
    province: '',
    provinceCode: '',
    city: '',
    cityCode: '',
    district: '',
    districtCode: '',
    detail: '',
    poiName: '',
    latitude: 0,
    longitude: 0,
    isDefault
  };

  let remainingText = text.trim();

  // 1. 提取手机号
  const phone = extractPhone(remainingText);
  if (phone) {
    const phoneReg = new RegExp(
      phone.replace(/(\d)/g, '\\d') + '|' + 
      phone.replace(/(\d{3})(\d{4})(\d{4})/, '$1[- ]?$2[- ]?$3'), 
      'g'
    );
    remainingText = remainingText.replace(phoneReg, '').replace(/\s+/g, ' ').trim();
  }

  // 2. 识别省市区
  const { province, city, district, remainingText: textAfterArea } = recognizeArea(remainingText);
  remainingText = textAfterArea;

  // 3. 提取姓名
  let receiver = extractName(remainingText);
  if (receiver) {
    remainingText = remainingText.replace(receiver, '').trim();
  } else {
    const reverseText = remainingText.split('').reverse().join('');
    const reverseName = extractName(reverseText);
    if (reverseName) {
      receiver = reverseName.split('').reverse().join('');
      remainingText = remainingText.replace(new RegExp(receiver + '$'), '').trim();
    }
  }

  // 4. 处理详细地址（过滤重复省市区）
  let detail = remainingText;
  const areaPrefix = [
    `${province}${city}${district}`,
    `${province}${city}`,
    `${city}${district}`
  ];
  for (const prefix of areaPrefix) {
    if (detail.includes(prefix)) {
      detail = detail.replace(prefix, '').trim();
      break;
    }
  }

  // 5. 补充扩展字段
  const { provinceCode, cityCode, districtCode } = getAreaCodes(province, city, district);
  const { latitude, longitude } = getLatLng(province, city, district);
  const poiName = extractPOIName(detail);

  return {
    receiver,          // 收件人姓名
    phone,             // 手机号
    province,          // 省份名称
    provinceCode,      // 省份代码（如：440000）
    city,              // 城市名称
    cityCode,          // 城市代码（如：440300）
    district,          // 区县名称
    districtCode,      // 区县代码（如：440305）
    detail,            // 详细地址
    poiName,           // POI名称（建筑物/小区名称）
    latitude,          // 纬度
    longitude,         // 经度
    isDefault          // 是否默认地址（默认false）
  };
};

// 导出函数
module.exports = { parseFullAddress };


