import { AlertCircle } from 'lucide-react';

import { cn } from '@/lib/utils';

type ErrorSource = 'validation' | 'server' | 'network' | 'unknown';

interface ErrorMessageProps {
  /** The raw error string or object. Pass null/undefined to render nothing. */
  error?: string | null;
  /** Override the automatically-detected source. */
  source?: ErrorSource;
  className?: string;
  /** Render inline (no icon, compact) vs block (icon, padded card). Default: 'block' */
  variant?: 'inline' | 'block';
}

/** Maps technical/HTTP errors to friendly user-facing messages. */
function friendlyMessage(raw: string): string {
  const lower = raw.toLowerCase();
  if (lower.includes('network') || lower.includes('fetch') || lower.includes('failed to fetch')) {
    return 'Check your internet connection and try again.';
  }
  if (lower.includes('timeout') || lower.includes('timed out')) {
    return 'The request took too long. Try again.';
  }
  if (lower.includes('unauthorized') || lower.includes('unauthenticated') || lower.includes('401')) {
    return 'You are not authorized to perform this action.';
  }
  if (lower.includes('forbidden') || lower.includes('403')) {
    return 'You do not have permission to do that.';
  }
  if (lower.includes('not found') || lower.includes('404')) {
    return 'That item could not be found. It may have been deleted.';
  }
  if (lower.includes('too many') || lower.includes('rate limit') || lower.includes('429')) {
    return 'Too many requests. You can retry after a short wait. In the meantime, review your existing recommendations.';
  }
  if (lower.match(/5\d{2}/) || lower.includes('server error') || lower.includes('internal')) {
    return 'Something went wrong on our end. Try again.';
  }
  if (lower.includes('validation_failed') || lower.includes('unprocessable')) {
    return 'Check your entries and try again.';
  }
  if (lower.includes('validation') || lower.includes('invalid')) {
    return 'Check your input and try again.';
  }
  if (lower.includes('quota_exceeded') || lower.includes('over_quota')) {
    return 'Your account has reached its limit. Upgrade your plan or wait for the next billing cycle.';
  }
  if (lower.includes('service_unavailable') || lower.includes('503')) {
    return 'This service is temporarily unavailable. Try again in a few minutes.';
  }
  if (lower.includes('conflict') || lower.includes('409')) {
    return 'This action conflicts with another change. Refresh and try again.';
  }
  if (
    lower.includes('file_too_large') ||
    lower.includes('413') ||
    lower.includes('content_too_large')
  ) {
    return 'The file is too large. Choose a smaller file.';
  }
  if (lower.includes('invalid_format') || lower.includes('unsupported_media')) {
    return 'The format is incorrect. Check the accepted formats.';
  }
  if (lower.includes('ai_key_invalid') || lower.includes('invalid_api_key')) {
    return 'Your AI API key appears to be invalid. Check your key in Settings → AI.';
  }
  if (lower.includes('ai_quota_exceeded') || lower.includes('insufficient_quota')) {
    return 'Your AI API quota has been exhausted. Check your OpenAI account usage.';
  }
  if (lower.includes('wp_connection_failed') || lower.includes('wp_unreachable')) {
    return "Couldn't connect to your WordPress site. Check that the plugin is installed and your site is reachable.";
  }
  if (lower.includes('serp_key_invalid') || lower.includes('dataforseo')) {
    return 'Your DataForSEO key is invalid. Verify it in Settings → SERP Key.';
  }
  // Return as-is if it's already a plain user-facing sentence
  return raw;
}

/**
 * Displays a user-friendly, consistently-styled error message.
 *
 * - `variant="block"` — icon + padded area, used for page-level/section errors
 * - `variant="inline"` — compact, used beneath form fields or inline with content
 *
 * Pass `error={null}` to render nothing (safe to always render).
 */
export function ErrorMessage({ error, source: _source, className, variant = 'block' }: ErrorMessageProps) {
  if (!error) return null;

  const message = friendlyMessage(error);

  if (variant === 'inline') {
    return (
      <p
        role="alert"
        className={cn('flex items-center gap-1.5 text-sm text-destructive', className)}
      >
        <AlertCircle className="h-3.5 w-3.5 shrink-0" aria-hidden="true" />
        {message}
      </p>
    );
  }

  return (
    <div
      role="alert"
      className={cn(
        'flex items-start gap-3 rounded-md border border-destructive/30 bg-destructive/5 px-4 py-3 text-sm text-destructive',
        className,
      )}
    >
      <AlertCircle className="mt-0.5 h-4 w-4 shrink-0" aria-hidden="true" />
      <span>{message}</span>
    </div>
  );
}
