import React, { Component, ErrorInfo, ReactNode } from 'react';
import { AlertTriangle, Home, RefreshCw } from 'lucide-react';
import { Button } from '@/components/ui/button';
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card';
import { handleError } from '@/lib/errorHandler';

interface RouteErrorBoundaryProps {
  children: ReactNode;
}

interface RouteErrorBoundaryState {
  hasError: boolean;
  error: Error | null;
}

type ErrorWithId = Error & { errorId: string };

export class RouteErrorBoundary extends Component<RouteErrorBoundaryProps, RouteErrorBoundaryState> {
  constructor(props: RouteErrorBoundaryProps) {
    super(props);
    this.state = {
      hasError: false,
      error: null,
    };
  }

  static getDerivedStateFromError(error: Error): Partial<RouteErrorBoundaryState> {
    return {
      hasError: true,
      error,
    };
  }

  componentDidCatch(error: Error, errorInfo: ErrorInfo) {
    // Detect chunk load failures (deployment cache issue)
    const isChunkLoadError = 
      error.message.includes('Failed to fetch dynamically imported module') ||
      error.message.includes('Loading chunk') ||
      error.message.includes('ChunkLoadError');

    if (isChunkLoadError) {
      // Check if we've already tried reloading
      const hasReloaded = sessionStorage.getItem('chunk-load-reload');
      
      if (!hasReloaded) {
        // Mark as reloaded and reload once
        sessionStorage.setItem('chunk-load-reload', 'true');
        window.location.reload();
        return; // Don't log error yet
      } else {
        // Second failure - clear flag and show error
        sessionStorage.removeItem('chunk-load-reload');
      }
    }

    // Log to database and get error ID for user reference
    const errorId = handleError(error, {
      action: 'Route-level component crash',
      metadata: {
        componentStack: errorInfo.componentStack,
        url: window.location.href,
        severity: isChunkLoadError ? 'medium' : 'critical',
        isChunkLoadError,
      },
    });

    this.setState({ error: { ...error, errorId } as ErrorWithId });
  }

  handleReload = () => {
    window.location.reload();
  };

  handleClearCacheAndReload = async () => {
    try {
      // Clear all caches
      if ('caches' in window) {
        const cacheNames = await caches.keys();
        await Promise.all(cacheNames.map(name => caches.delete(name)));
      }

      // Unregister service workers
      if ('serviceWorker' in navigator) {
        const registrations = await navigator.serviceWorker.getRegistrations();
        await Promise.all(registrations.map(reg => reg.unregister()));
      }

      // Clear session storage chunk reload flag
      sessionStorage.removeItem('chunk-load-reload');

      // Force reload bypassing cache
      window.location.reload();
    } catch (error) {
      // Fallback to regular reload if cache clearing fails
      console.error('Failed to clear cache:', error);
      window.location.reload();
    }
  };

  handleGoHome = () => {
    window.location.href = '/';
  };

  render() {
    if (this.state.hasError) {
      const isChunkError = 
        this.state.error?.message.includes('Failed to fetch dynamically imported module') ||
        this.state.error?.message.includes('Loading chunk') ||
        this.state.error?.message.includes('ChunkLoadError');

      return (
        <div className="min-h-screen flex items-center justify-center p-4 bg-background">
          <Card className="max-w-lg w-full shadow-lg">
            <CardHeader className="text-center pb-4">
              <div className="mx-auto w-16 h-16 bg-destructive/10 rounded-full flex items-center justify-center mb-4">
                <AlertTriangle className="w-8 h-8 text-destructive" />
              </div>
              <CardTitle className="text-2xl">
                {isChunkError ? 'App Update Required' : 'Something Went Wrong'}
              </CardTitle>
              <CardDescription className="mt-2 space-y-2">
                {isChunkError ? (
                  <>
                    <p>The app has been updated with new features and improvements.</p>
                    <p className="text-sm font-medium">
                      To continue, please clear your browser cache and reload:
                    </p>
                    <ul className="text-sm list-disc list-inside space-y-1 ml-2">
                      <li>Click "Clear Cache & Reload" below, or</li>
                      <li>Press <kbd className="px-1.5 py-0.5 text-xs font-semibold bg-muted rounded">Ctrl+Shift+R</kbd> (Windows/Linux) or <kbd className="px-1.5 py-0.5 text-xs font-semibold bg-muted rounded">⌘+Shift+R</kbd> (Mac)</li>
                    </ul>
                  </>
                ) : (
                  "We encountered an unexpected error. This has been logged and we'll look into it."
                )}
              </CardDescription>
            </CardHeader>
            <CardContent className="space-y-4">
              {this.state.error && (
                <div className="p-3 bg-muted rounded-lg space-y-2">
                  {import.meta.env.DEV && (
                    <p className="text-xs font-mono text-muted-foreground">
                      {this.state.error.message}
                    </p>
                  )}
                  {(this.state.error as ErrorWithId)?.errorId && (
                    <p className="text-xs font-mono bg-destructive/10 px-2 py-1 rounded">
                      Reference ID: {(this.state.error as ErrorWithId).errorId.slice(0, 8)}
                    </p>
                  )}
                </div>
              )}

              <div className="flex flex-col gap-2">
                {isChunkError && (
                  <Button
                    variant="default"
                    onClick={this.handleClearCacheAndReload}
                    className="w-full gap-2"
                  >
                    <RefreshCw className="w-4 h-4" />
                    Clear Cache & Reload
                  </Button>
                )}
                <div className="flex flex-col sm:flex-row gap-2">
                  <Button
                    variant={isChunkError ? "outline" : "default"}
                    onClick={this.handleReload}
                    className="flex-1 gap-2"
                  >
                    <RefreshCw className="w-4 h-4" />
                    Reload Page
                  </Button>
                  <Button
                    variant="outline"
                    onClick={this.handleGoHome}
                    className="flex-1 gap-2"
                  >
                    <Home className="w-4 h-4" />
                    Go Home
                  </Button>
                </div>
              </div>

              <p className="text-xs text-center text-muted-foreground">
                If this problem persists, please contact support
              </p>
            </CardContent>
          </Card>
        </div>
      );
    }

    return this.props.children;
  }
}
