import React, { useMemo } from 'react';

const HARD_SPAM = [
  'free', 'winner', 'winners', 'you won', 'prize', 'prizes', 'claim', 'guaranteed',
  'act now', 'click here', 'urgent', 'limited time', 'no obligation', 'risk-free',
  'risk free', 'no cost', 'earn money', 'make money', 'cash', 'billion', 'million dollars',
  'congratulations', 'selected', 'you have been selected', 'buy now',
];

const PROMO_WORDS = [
  'sale', 'offer', 'deal', 'deals', 'discount', 'discounts', 'save', 'savings',
  'exclusive', 'shop', 'order', 'buy', 'purchase', 'promo', 'promotion', 'coupon',
  'marketing', 'advertisement', 'sponsored', 'newsletter',
];

const GOOD_OPENERS = [
  'invitation', 'invite', 'update', 'recap', 'reminder', 'quick', 'following up',
  'meeting', 'event', 'welcome', 'thank', 'thank you', 'introducing', 'resource',
  'question', 'idea', 'thought', 'connecting',
];

interface Flag {
  label: string;
  type: 'danger' | 'warn' | 'good';
}

function countEmojis(str: string): number {
  const emojiRx = /\p{Emoji_Presentation}|\p{Extended_Pictographic}/gu;
  return (str.match(emojiRx) || []).length;
}

function hasAllCapsWord(str: string): boolean {
  return str.split(/\s+/).some(w => w.length >= 3 && w === w.toUpperCase() && /[A-Z]/.test(w));
}

function percentSignCount(str: string): number {
  return (str.match(/%/g) || []).length;
}

function excessivePunctuation(str: string): boolean {
  return /[!]{2,}|[?]{2,}/.test(str);
}

export function scoreSubject(subject: string): {
  score: number;
  grade: string;
  gradeColor: string;
  flags: Flag[];
  tips: string[];
} {
  const flags: Flag[] = [];
  const tips: string[] = [];
  let score = 100;

  if (!subject || subject.trim().length === 0) {
    return { score: 0, grade: '—', gradeColor: 'text-slate-400', flags: [], tips: ['Enter a subject line to see your score.'] };
  }

  const lower = subject.toLowerCase();

  const hardHits = HARD_SPAM.filter(w => lower.includes(w));
  hardHits.forEach(w => {
    score -= 15;
    flags.push({ label: `Spam trigger: "${w}"`, type: 'danger' });
  });

  const promoHits = PROMO_WORDS.filter(w => lower.includes(w) && !hardHits.includes(w));
  promoHits.forEach(w => {
    score -= 8;
    flags.push({ label: `Promotional word: "${w}"`, type: 'warn' });
  });

  if (hasAllCapsWord(subject)) {
    score -= 12;
    flags.push({ label: 'ALL CAPS word detected', type: 'danger' });
    tips.push('Avoid ALL CAPS — it reads as shouting and triggers filters.');
  }

  if (excessivePunctuation(subject)) {
    score -= 10;
    flags.push({ label: 'Excessive punctuation (!! or ??)', type: 'danger' });
    tips.push('Replace !! or ?? with a single ! or ? at most.');
  }

  const emojiCount = countEmojis(subject);
  if (emojiCount === 1) {
    score -= 3;
    flags.push({ label: '1 emoji — use sparingly', type: 'warn' });
  } else if (emojiCount > 1) {
    score -= 8;
    flags.push({ label: `${emojiCount} emojis — too many`, type: 'danger' });
    tips.push('Limit emojis to 0–1. Multiple emojis are a strong Promotions signal.');
  }

  if (/\$/.test(subject)) {
    score -= 8;
    flags.push({ label: 'Dollar sign ($) in subject', type: 'warn' });
  }

  if (percentSignCount(subject) > 0) {
    score -= 8;
    flags.push({ label: 'Percent sign (%) in subject', type: 'warn' });
  }

  if (/\b(re:|fwd?:)(\s|$)/i.test(subject)) {
    score -= 20;
    flags.push({ label: 'Fake Re:/Fwd: — spam filter trigger', type: 'danger' });
    tips.push('Re: or Fwd: anywhere in the subject is a known spam tactic — filters catch it regardless of position.');
  }

  const len = subject.length;
  if (len > 65) {
    score -= 10;
    flags.push({ label: `Too long (${len} chars — Gmail truncates at ~60)`, type: 'warn' });
    tips.push('Keep subjects under 60 characters for full display on mobile and desktop.');
  } else if (len < 10) {
    score -= 8;
    flags.push({ label: 'Very short — may look like spam', type: 'warn' });
  } else if (len >= 30 && len <= 55) {
    score += 5;
    flags.push({ label: `Good length (${len} chars)`, type: 'good' });
  }

  if (/\?$/.test(subject.trim())) {
    score += 5;
    flags.push({ label: 'Question format — conversational', type: 'good' });
  }

  if (/\{\{.+?\}\}/.test(subject)) {
    score += 5;
    flags.push({ label: 'Personalization token detected', type: 'good' });
    tips.push('Personalized subjects (e.g. {{first_name}}) improve open rates significantly.');
  }

  const goodHit = GOOD_OPENERS.find(w => lower.includes(w));
  if (goodHit) {
    score += 5;
    flags.push({ label: `Inbox-friendly word: "${goodHit}"`, type: 'good' });
  }

  if (flags.length === 0 || flags.every(f => f.type === 'good')) {
    tips.push('Looks clean. Consider A/B testing a personalized version with {{first_name}}.');
  }

  if (hardHits.length === 0 && promoHits.length === 0 && !hasAllCapsWord(subject)) {
    tips.push('No major filters triggered. Keep the email body light on images to reinforce inbox placement.');
  }

  score = Math.max(0, Math.min(100, score));

  let grade = 'F';
  let gradeColor = 'text-red-600';
  if (score >= 90) { grade = 'A'; gradeColor = 'text-emerald-600'; }
  else if (score >= 75) { grade = 'B'; gradeColor = 'text-green-600'; }
  else if (score >= 60) { grade = 'C'; gradeColor = 'text-yellow-600'; }
  else if (score >= 45) { grade = 'D'; gradeColor = 'text-orange-600'; }

  return { score, grade, gradeColor, flags, tips };
}

interface Props {
  subject: string;
}

export default function SubjectScorer({ subject }: Props) {
  const { score, grade, gradeColor, flags, tips } = useMemo(() => scoreSubject(subject), [subject]);

  if (!subject || subject.trim().length === 0) return null;

  const barColor =
    score >= 90 ? 'bg-emerald-500' :
    score >= 75 ? 'bg-green-500' :
    score >= 60 ? 'bg-yellow-400' :
    score >= 45 ? 'bg-orange-400' : 'bg-red-500';

  const dangers = flags.filter(f => f.type === 'danger');
  const warns   = flags.filter(f => f.type === 'warn');
  const goods   = flags.filter(f => f.type === 'good');

  return (
    <div className="mt-2 bg-slate-50 border border-slate-100 rounded-xl p-4 space-y-3 text-xs">
      {/* Score bar */}
      <div className="flex items-center gap-3">
        <span className={`text-3xl font-black ${gradeColor} w-8 text-center`}>{grade}</span>
        <div className="flex-1 space-y-1">
          <div className="flex justify-between text-[10px] font-bold text-slate-400 uppercase tracking-wider">
            <span>Inbox Score</span>
            <span>{score}/100</span>
          </div>
          <div className="h-2 bg-slate-200 rounded-full overflow-hidden">
            <div className={`h-full rounded-full transition-all duration-300 ${barColor}`} style={{ width: `${score}%` }} />
          </div>
        </div>
      </div>

      {/* Flags */}
      {(dangers.length > 0 || warns.length > 0 || goods.length > 0) && (
        <div className="space-y-1">
          {dangers.map((f, i) => (
            <div key={i} className="flex items-center gap-2 text-red-700">
              <span className="w-1.5 h-1.5 rounded-full bg-red-500 flex-shrink-0" />
              {f.label}
            </div>
          ))}
          {warns.map((f, i) => (
            <div key={i} className="flex items-center gap-2 text-amber-700">
              <span className="w-1.5 h-1.5 rounded-full bg-amber-400 flex-shrink-0" />
              {f.label}
            </div>
          ))}
          {goods.map((f, i) => (
            <div key={i} className="flex items-center gap-2 text-emerald-700">
              <span className="w-1.5 h-1.5 rounded-full bg-emerald-500 flex-shrink-0" />
              {f.label}
            </div>
          ))}
        </div>
      )}

      {/* Tips */}
      {tips.length > 0 && (
        <div className="border-t border-slate-200 pt-2 space-y-1 text-slate-500 italic">
          {tips.map((t, i) => <p key={i}>{t}</p>)}
        </div>
      )}
    </div>
  );
}
