/**
 * Market Data WebSocket 연결 상태만 확인하는 훅
 * - 대시보드 상단 등에서 연결 상태 표시용
 * - 실제 차트 데이터는 useMarketDataWebSocket 사용
 */
import { useState, useEffect, useRef, useCallback } from 'react';

export type ConnectionStatus = 'disconnected' | 'connecting' | 'connected' | 'error';

const httpToWs = (url: string): string => {
  return url.replace(/^http:\/\//i, 'ws://').replace(/^https:\/\//i, 'wss://');
};

// Market Data URL: 런타임 환경에 따라 동적 결정
const getMarketDataUrl = (): string => {
  const envUrl = process.env.REACT_APP_MARKET_DATA_URL;
  if (envUrl) return envUrl.replace(/\/$/, '');
  
  // 런타임 환경 감지
  if (typeof window === 'undefined') {
    return '/market-data'; // SSR fallback
  }
  
  const isLocalhost = window.location.hostname === 'localhost' || 
    window.location.hostname === '127.0.0.1' ||
    window.location.hostname === '';
  
  if (isLocalhost) {
    // 로컬 개발 시 localhost 서버로 직접 연결
    return 'http://localhost:8086';
  }
  
  // 서버 환경: 현재 origin 사용 (nginx가 프록시)
  return `${window.location.origin}/market-data`;
};

const getMarketDataWsUrl = (): string => httpToWs(getMarketDataUrl());

interface UseWebSocketConnectionStatusOptions {
  enabled?: boolean;
  /** 구독용 마켓 (연결 유지를 위해 subscribe 필요) */
  market?: string;
  timeframe?: string;
}

export const useWebSocketConnectionStatus = ({
  enabled = true,
  market = 'KRW-BTC',
  timeframe = '1m',
}: UseWebSocketConnectionStatusOptions = {}) => {
  const [status, setStatus] = useState<ConnectionStatus>('disconnected');
  const wsRef = useRef<WebSocket | null>(null);
  const reconnectTimeoutRef = useRef<NodeJS.Timeout | null>(null);
  const reconnectAttemptsRef = useRef(0);

  const connect = useCallback(() => {
    if (!enabled) return;
    if (wsRef.current) {
      const state = wsRef.current.readyState;
      if (state === WebSocket.CONNECTING || state === WebSocket.OPEN) return;
    }

    setStatus('connecting');
    const wsUrl = `${getMarketDataWsUrl()}/ws/chart`;
    const ws = new WebSocket(wsUrl);

    ws.onopen = () => {
      setStatus('connected');
      reconnectAttemptsRef.current = 0;
      ws.send(JSON.stringify({ type: 'subscribe', market, timeframe }));
    };

    ws.onmessage = () => {
      // 메시지 수신 = 연결 유지됨 (ping/pong, snapshot 등 무시)
    };

    ws.onerror = () => {
      setStatus('error');
    };

    ws.onclose = () => {
      if (wsRef.current === ws) wsRef.current = null;
      setStatus('disconnected');

      const MAX_RETRIES = 3;
      if (enabled && !reconnectTimeoutRef.current && reconnectAttemptsRef.current < MAX_RETRIES) {
        const delay = Math.min(1000 * Math.pow(2, reconnectAttemptsRef.current), 10000);
        reconnectAttemptsRef.current += 1;
        reconnectTimeoutRef.current = setTimeout(() => {
          reconnectTimeoutRef.current = null;
          connect();
        }, delay);
      }
    };

    wsRef.current = ws;
  }, [enabled, market, timeframe]);

  const disconnect = useCallback(() => {
    if (reconnectTimeoutRef.current) {
      clearTimeout(reconnectTimeoutRef.current);
      reconnectTimeoutRef.current = null;
    }
    if (wsRef.current) {
      const ws = wsRef.current;
      wsRef.current = null;
      try {
        if (ws.readyState === WebSocket.OPEN) {
          ws.send(JSON.stringify({ type: 'unsubscribe' }));
        }
        ws.onopen = null;
        ws.onmessage = null;
        ws.onerror = null;
        ws.onclose = null;
        if (ws.readyState !== WebSocket.CLOSED) ws.close();
      } catch {
        // ignore
      }
    }
    setStatus('disconnected');
  }, []);

  useEffect(() => {
    if (enabled) connect();
    else disconnect();
    return () => disconnect();
  }, [enabled, market, timeframe, connect, disconnect]);

  return { status };
};
