import type { KeywordCombination, SearchFieldType, SearchPipelineConfig } from "../core/types.ts";

type MerchantIdentity = {
  merchant_url?: unknown;
  contact_page_url?: unknown;
  merchant_name?: unknown;
  offer_url?: unknown;
  title?: unknown;
};

type BaseNormalizedProduct = {
  index: number;
  title: string;
  offer_url: string;
  image_url: string;
  merchant_name: string;
  merchant_url: string;
  wangwang_url: string;
  offer_screenshot_path: string;
  contact_page_url: string;
  detected_contacts: unknown[];
  has_phone_contact?: boolean;
  qualification_status?: string;
  contact_collection_reason?: string;
};

export type StageResultProduct = BaseNormalizedProduct & {
  source: string;
  main_keyword: string;
  stage_label: string;
  stage_order: number;
  stage_kind: SearchExecutionStage["kind"];
  stage_main_keyword: string;
  stage_keyword_hit_rate: number | null;
  stage_rank: number;
  is_placeholder: boolean;
  placeholder_reason: string;
};

export type SearchExecutionStage =
  | {
    kind: "keyword";
    label: string;
    stageOrder: number;
    pipelineConfig: SearchPipelineConfig;
    mode: "configured" | "default" | "fixed_runtime";
    fields: SearchFieldType[];
    requiresBrandHitGuard: boolean;
  }
  | {
    kind: "image";
    label: string;
    stageOrder: number;
  };

export type StageMergeResult = {
  merged: StageResultProduct[];
  inserted: StageResultProduct[];
  insertedCount: number;
  duplicateCount: number;
};

function normalizeText(value: unknown) {
  return String(value ?? "").replace(/\s+/g, " ").trim();
}

function isPlaceholderContactValue(value: unknown) {
  return /^(?:暂无|无|空|--|-|保密|未填写|未公开|暂无信息|暂未填写|n\/?a|none|null)$/i.test(normalizeText(value));
}

function stripChinaCountryCode(digitsOnly: string) {
  if (digitsOnly.startsWith("0086") && digitsOnly.length > 4) {
    return digitsOnly.slice(4);
  }

  if (digitsOnly.startsWith("86") && digitsOnly.length > 2) {
    return digitsOnly.slice(2);
  }

  return digitsOnly;
}

function hasCompleteMobileNumber(value: unknown) {
  const digitsOnly = normalizeText(value).replace(/[^\d]/g, "");
  const withoutCountryCode = stripChinaCountryCode(digitsOnly);
  return /^1[3-9]\d{9}$/.test(withoutCountryCode);
}

function hasCompleteLandlineNumber(value: unknown) {
  const digitsOnly = normalizeText(value).replace(/[^\d]/g, "");
  const withoutCountryCode = stripChinaCountryCode(digitsOnly);

  if (!/^0\d{9,11}$/.test(withoutCountryCode)) {
    return false;
  }

  const areaCodeLength = /^(010|020|021|022|023|024|025|027|028|029)/.test(withoutCountryCode) ? 3 : 4;
  const subscriberNumber = withoutCountryCode.slice(areaCodeLength);
  return subscriberNumber.length >= 7;
}

export function isCompletePhoneContactValue(type: unknown, value: unknown) {
  const normalizedType = normalizeText(type).toLowerCase();
  const normalizedValue = normalizeText(value);

  if (!normalizedValue || isPlaceholderContactValue(normalizedValue)) {
    return false;
  }

  if (normalizedType === "mobile") {
    return hasCompleteMobileNumber(normalizedValue);
  }

  if (normalizedType === "phone") {
    return hasCompleteMobileNumber(normalizedValue) || hasCompleteLandlineNumber(normalizedValue);
  }

  return false;
}

export function hasDetectedPhoneContact(contacts: unknown) {
  return (Array.isArray(contacts) ? contacts : []).some((contact) => {
    if (!contact || typeof contact !== "object") {
      return false;
    }

    const record = contact as Record<string, unknown>;
    const type = normalizeText(record.type).toLowerCase();
    const value = normalizeText(record.value);
    return isCompletePhoneContactValue(type, value);
  });
}

export function filterProductsWithDetectedPhoneContacts<T extends BaseNormalizedProduct>(products: T[]) {
  const filtered: T[] = [];
  let droppedCount = 0;

  for (const product of products) {
    if (hasDetectedPhoneContact(product.detected_contacts)) {
      filtered.push(product);
    } else {
      droppedCount += 1;
    }
  }

  return { filtered, droppedCount };
}

function buildKeywordStageConfig(
  baseConfig: SearchPipelineConfig,
  keywordCombinations: KeywordCombination[],
  includeAiKeyword: boolean,
): SearchPipelineConfig {
  return {
    keywordSearchEnabled: true,
    imageSearchEnabled: false,
    keywordCombinations,
    includeAiKeyword,
  };
}

export function buildKeywordArtifactPipelineConfig(pipelineConfig: SearchPipelineConfig): SearchPipelineConfig {
  return buildKeywordStageConfig(
    pipelineConfig,
    [],
    false,
  );
}

export function buildSearchExecutionStages(pipelineConfig: SearchPipelineConfig): SearchExecutionStage[] {
  const stages: SearchExecutionStage[] = [];
  let stageOrder = 1;

  if (pipelineConfig.keywordSearchEnabled) {
    stages.push({
      kind: "keyword",
      label: "关键词搜索（AI 自动多轮）",
      stageOrder,
      pipelineConfig: buildKeywordArtifactPipelineConfig(pipelineConfig),
      mode: "fixed_runtime",
      fields: [],
      requiresBrandHitGuard: false,
    });
    stageOrder += 1;
  }

  return stages;
}

export function annotateStageProducts(
  products: BaseNormalizedProduct[],
  meta: {
    source: string;
    mainKeyword: string;
    stageLabel: string;
    stageOrder: number;
    stageKind: SearchExecutionStage["kind"];
    stageKeywordHitRate: number | null;
  },
): StageResultProduct[] {
  return products.map((product, index) => ({
    ...product,
    source: meta.source,
    main_keyword: meta.mainKeyword,
    stage_label: meta.stageLabel,
    stage_order: meta.stageOrder,
    stage_kind: meta.stageKind,
    stage_main_keyword: meta.mainKeyword,
    stage_keyword_hit_rate: meta.stageKeywordHitRate,
    stage_rank: index + 1,
    is_placeholder: false,
    placeholder_reason: "",
  }));
}

function placeholderTitle(reason: string) {
  if (reason === "brand_zero_hit_stop") {
    return "品牌命中率为 0%，已停止后续搜索";
  }

  return "当前阶段未产出可展示商家";
}

export function buildPlaceholderStageProduct(meta: {
  source: string;
  mainKeyword: string;
  stageLabel: string;
  stageOrder: number;
  stageKind: SearchExecutionStage["kind"];
  stageKeywordHitRate: number | null;
  placeholderReason: string;
}): StageResultProduct {
  return {
    index: 1,
    title: placeholderTitle(meta.placeholderReason),
    offer_url: "",
    image_url: "",
    merchant_name: "",
    merchant_url: "",
    wangwang_url: "",
    offer_screenshot_path: "",
    contact_page_url: "",
    detected_contacts: [],
    has_phone_contact: false,
    qualification_status: "placeholder",
    contact_collection_reason: "",
    source: meta.source,
    main_keyword: meta.mainKeyword,
    stage_label: meta.stageLabel,
    stage_order: meta.stageOrder,
    stage_kind: meta.stageKind,
    stage_main_keyword: meta.mainKeyword,
    stage_keyword_hit_rate: meta.stageKeywordHitRate,
    stage_rank: 1,
    is_placeholder: true,
    placeholder_reason: meta.placeholderReason,
  };
}

export function buildMerchantKey(product: MerchantIdentity) {
  return normalizeText(product.merchant_url)
    || normalizeText(product.contact_page_url)
    || normalizeText(product.merchant_name)
    || normalizeText(product.offer_url)
    || normalizeText(product.title);
}

export function mergeStageProducts(
  accumulatedProducts: StageResultProduct[],
  stageProducts: StageResultProduct[],
): StageMergeResult {
  const seenKeys = new Set(
    accumulatedProducts
      .map((product) => buildMerchantKey(product))
      .filter(Boolean),
  );

  const merged = [...accumulatedProducts];
  const inserted: StageResultProduct[] = [];
  let duplicateCount = 0;

  for (const product of stageProducts) {
    const merchantKey = buildMerchantKey(product);
    if (merchantKey && seenKeys.has(merchantKey)) {
      duplicateCount += 1;
      continue;
    }

    if (merchantKey) {
      seenKeys.add(merchantKey);
    }

    merged.push(product);
    inserted.push(product);
  }

  return {
    merged,
    inserted,
    insertedCount: inserted.length,
    duplicateCount,
  };
}
