/**
 * Group WhatsApp talkback: only auto-reply when the channel/bot is @mentioned,
 * the message looks like a direct support question, or the inbound is a follow-up
 * to the channel’s last question (no @tag required).
 */
export function shouldReplyInWhatsAppGroup(opts: {
  text: string;
  channelPhone: string;
  channelName?: string | null;
  mentionedPhones?: string[];
  /** Channel account phone + LID digits from the WA worker (sock.user). */
  channelMentionIds?: string[];
  /**
   * Most recent outbound on the ticket (before this inbound).
   * When it asks something, later untagged inbounds count as answers until the
   * channel sends a non-question outbound (or the inbound is pure chatter).
   */
  priorOutbound?: { content: string } | null;
}): boolean {
  const text = (opts.text ?? '').trim();
  if (!text) return false;

  const channelDigits = (opts.channelPhone ?? '').replace(/\D/g, '');
  const mentionedDigits = (opts.mentionedPhones ?? []).map(p => p.replace(/\D/g, '')).filter(Boolean);
  const identityIds = [
    ...new Set(
      [channelDigits, ...(opts.channelMentionIds ?? []).map(p => p.replace(/\D/g, ''))].filter(Boolean),
    ),
  ];

  // structured mentionedJid list vs channel phone / LID
  if (mentionedDigits.some(m => identityIds.some(id => idsMatch(m, id)))) {
    return true;
  }

  // Inline @phone or @LID in the message body (clients that don't fill mentionedJid)
  if (identityIds.some(id => textMentionsId(text, id))) {
    return true;
  }

  const lower = text.toLowerCase();
  if (/\b@?\s*silicon\s*support\b/i.test(text)) return true;
  if (/\b@support\b/i.test(text)) return true;

  const channelName = opts.channelName?.trim().toLowerCase();
  if (channelName && channelName.length >= 3 && lower.includes(`@${channelName}`)) {
    return true;
  }

  // Direct question to the group (no need to @mention)
  if (looksLikeSupportQuestion(text)) return true;

  // Follow-up: last channel outbound asked something → inbound may omit @tag
  if (
    opts.priorOutbound &&
    channelAskedQuestion(opts.priorOutbound.content) &&
    !isCasualChatter(text)
  ) {
    return true;
  }

  return false;
}

/** Outbound from AI/staff that is prompting the customer for information. */
export function channelAskedQuestion(content: string): boolean {
  const text = (content ?? '').trim();
  if (!text) return false;
  if (/\?/.test(text)) return true;
  return /^(could you|can you|please\b|tell me|let me know|confirm\b|which\b|what\b|when\b|where\b|how\b|do you|are you|would you|describe|provide|choose|pick|select)\b/i.test(
    text,
  );
}

/** Social noise that should not continue an AI thread even after a channel question. */
export function isCasualChatter(text: string): boolean {
  const t = text.trim().toLowerCase();
  if (!t) return true;
  if (/^(lol+|haha+|hehe+|lmao+|ok+|okay|k+|cool|nice|thanks|thx|ty|cheers|bye|gg|👋|😂|🤣|👍|🙏)+[!~.]*$/i.test(t)) {
    return true;
  }
  if (/^(see you|catch you|on (my )?way|be right back|brb)\b/i.test(t)) return true;
  return false;
}

function idsMatch(a: string, b: string): boolean {
  if (!a || !b) return false;
  if (a === b) return true;
  // Phone numbers: allow trailing-digit overlap; LIDs are compared exactly above
  const short = Math.min(a.length, b.length, 10);
  if (short < 8) return false;
  // Avoid false LID↔phone matches when lengths differ a lot (LID vs E.164)
  if (Math.abs(a.length - b.length) > 4) return false;
  return a.slice(-short) === b.slice(-short);
}

function textMentionsId(text: string, idDigits: string): boolean {
  if (!idDigits) return false;
  const compact = text.replace(/[^\d@]/g, '');
  if (compact.includes(`@${idDigits}`)) return true;
  if (idDigits.length >= 9 && compact.includes(`@${idDigits.slice(-9)}`)) return true;
  if (idDigits.length >= 10 && compact.includes(`@${idDigits.slice(-10)}`)) return true;
  return false;
}

function looksLikeSupportQuestion(text: string): boolean {
  if (/\?\s*$/.test(text.trim())) return true;
  return /^(can you|could you|would you|please\b|help\b|how (do|can|to)|what (is|are|should)|where (is|can)|when (can|will|is)|why (is|does|can)|is there|do you|are you able|need help|assist)\b/i.test(
    text.trim(),
  );
}
