import { useEffect, useRef, useState, useCallback } from 'react';
import { Select, Space, Button, message, Spin, Empty } from 'antd';
import { ReloadOutlined, CopyOutlined, VerticalAlignBottomOutlined, SyncOutlined } from '@ant-design/icons';
import axios from 'axios';
import { api } from '@/lib/api';

interface LogViewerProps {
  instanceId: string;
  services: string[];
  initialService?: string;
}

const TAIL_OPTIONS = [
  { label: '100 lines', value: 100 },
  { label: '200 lines', value: 200 },
  { label: '500 lines', value: 500 },
  { label: '1000 lines', value: 1000 },
];

const SINCE_OPTIONS = [
  { label: '1 hour', value: '1h' },
  { label: '6 hours', value: '6h' },
  { label: '24 hours', value: '24h' },
  { label: 'All time', value: '' },
];

const AUTO_REFRESH_INTERVAL = 5000;

export default function LogViewer({ instanceId, services, initialService }: LogViewerProps) {
  const [service, setService] = useState<string | undefined>(initialService);
  const [tail, setTail] = useState(200);
  const [since, setSince] = useState('1h');
  const [logs, setLogs] = useState('');
  const [loading, setLoading] = useState(false);
  const [autoScroll, setAutoScroll] = useState(true);
  const [autoRefresh, setAutoRefresh] = useState(false);
  const logRef = useRef<HTMLPreElement>(null);
  const abortRef = useRef<AbortController | null>(null);
  const loadingRef = useRef(false);

  useEffect(() => {
    if (initialService) setService(initialService);
  }, [initialService]);

  const fetchLogs = useCallback(async () => {
    // Abort any in-flight request
    if (abortRef.current) {
      abortRef.current.abort();
    }
    const controller = new AbortController();
    abortRef.current = controller;

    setLoading(true);
    loadingRef.current = true;
    try {
      const params = new URLSearchParams();
      if (service) params.set('service', service);
      params.set('tail', tail.toString());
      if (since) params.set('since', since);

      const { data } = await api.get(`/instances/${instanceId}/logs?${params}`, {
        signal: controller.signal,
      });
      setLogs(data.data || '');
    } catch (err) {
      // Ignore aborted requests — they're expected during rapid dropdown changes
      if (axios.isCancel(err)) return;
      setLogs('Failed to load logs');
    } finally {
      setLoading(false);
      loadingRef.current = false;
    }
  }, [instanceId, service, tail, since]);

  // Fetch when parameters change
  useEffect(() => {
    fetchLogs();
    // Cleanup: abort on unmount or before next effect run
    return () => {
      if (abortRef.current) {
        abortRef.current.abort();
      }
    };
  }, [fetchLogs]);

  // Auto-refresh interval
  useEffect(() => {
    if (!autoRefresh) return;
    const id = setInterval(() => {
      // Skip if a manual fetch is already in progress
      if (!loadingRef.current) {
        fetchLogs();
      }
    }, AUTO_REFRESH_INTERVAL);
    return () => clearInterval(id);
  }, [autoRefresh, fetchLogs]);

  useEffect(() => {
    if (autoScroll && logRef.current) {
      logRef.current.scrollTop = logRef.current.scrollHeight;
    }
  }, [logs, autoScroll]);

  const handleCopy = async () => {
    try {
      await navigator.clipboard.writeText(logs);
      message.success('Logs copied to clipboard');
    } catch {
      message.error('Failed to copy');
    }
  };

  return (
    <div>
      <Space wrap style={{ marginBottom: 12 }}>
        <Select
          style={{ width: 180 }}
          placeholder="All services"
          allowClear
          value={service}
          onChange={setService}
          options={services.map((s) => ({ label: s, value: s }))}
        />
        <Select
          style={{ width: 120 }}
          value={tail}
          onChange={setTail}
          options={TAIL_OPTIONS}
        />
        <Select
          style={{ width: 120 }}
          value={since}
          onChange={setSince}
          options={SINCE_OPTIONS}
        />
        <Button icon={<ReloadOutlined />} onClick={fetchLogs} loading={loading}>
          Refresh
        </Button>
        <Button icon={<CopyOutlined />} onClick={handleCopy} disabled={!logs}>
          Copy
        </Button>
        <Button
          icon={<VerticalAlignBottomOutlined />}
          type={autoScroll ? 'primary' : 'default'}
          onClick={() => setAutoScroll(!autoScroll)}
        >
          Auto-scroll
        </Button>
        <Button
          icon={<SyncOutlined spin={autoRefresh} />}
          type={autoRefresh ? 'primary' : 'default'}
          onClick={() => setAutoRefresh(!autoRefresh)}
        >
          Auto-refresh
        </Button>
      </Space>

      {loading && !logs ? (
        <div style={{ textAlign: 'center', padding: 40 }}>
          <Spin />
        </div>
      ) : !logs ? (
        <Empty description="No logs available" />
      ) : (
        <pre
          ref={logRef}
          style={{
            background: '#1e1e1e',
            color: '#d4d4d4',
            padding: 16,
            borderRadius: 6,
            fontSize: 12,
            lineHeight: 1.5,
            maxHeight: 600,
            overflow: 'auto',
            fontFamily: "'Fira Code', 'Cascadia Code', 'Consolas', monospace",
            whiteSpace: 'pre-wrap',
            wordBreak: 'break-all',
          }}
        >
          {logs}
        </pre>
      )}
    </div>
  );
}
