import { useState } from 'react'
import {
  useIvWatchlist, useIvSnapshot, useIvHistory, useWatchlistTickers, useAddWatchlistTicker, useRemoveWatchlistTicker,
  useSaxoIvWatchlist, useSaxoIvSnapshot, useSaxoIvHistory, useInstrumentsWatchlist,
} from '../hooks/useApi'
import { Activity, TrendingUp, TrendingDown, Minus, RefreshCw, ChevronDown, ChevronUp, Database, Plus, Trash2, List, Link2 } from 'lucide-react'
import { api } from '../hooks/useApi'
import { useQueryClient } from '@tanstack/react-query'
import clsx from 'clsx'

// ── Helpers ───────────────────────────────────────────────────────────────────

function ivRankColor(rank: number | null | undefined): string {
  if (rank == null) return 'text-slate-500'
  if (rank >= 80) return 'text-red-400'
  if (rank >= 50) return 'text-amber-400'
  if (rank >= 20) return 'text-emerald-400'
  return 'text-blue-400'
}

function ivRankBg(rank: number | null | undefined): string {
  if (rank == null) return 'bg-dark-700/30 border-slate-700/30'
  if (rank >= 80) return 'bg-red-900/20 border-red-700/30'
  if (rank >= 50) return 'bg-amber-900/10 border-amber-700/20'
  if (rank >= 20) return 'bg-emerald-900/10 border-emerald-700/20'
  return 'bg-blue-900/20 border-blue-700/30'
}

function ivSignalLabel(rank: number | null | undefined) {
  if (rank == null) return null
  if (rank >= 80) return { text: 'Sell vol', icon: <TrendingDown className="w-3 h-3" />, cls: 'text-red-400' }
  if (rank < 20)  return { text: 'Buy vol', icon: <TrendingUp className="w-3 h-3" />, cls: 'text-blue-400' }
  return { text: 'Neutral', icon: <Minus className="w-3 h-3" />, cls: 'text-slate-500' }
}

function StructureBadge({ structure }: { structure: string | null | undefined }) {
  if (!structure) return null
  const map: Record<string, { label: string; cls: string }> = {
    contango:      { label: 'Contango ↗', cls: 'text-emerald-400 bg-emerald-900/20 border-emerald-700/30' },
    backwardation: { label: 'Backwardation ↘', cls: 'text-red-400 bg-red-900/20 border-red-700/30' },
    flat:          { label: 'Flat →', cls: 'text-slate-400 bg-slate-800 border-slate-700/30' },
  }
  const s = map[structure] || { label: structure, cls: 'text-slate-400 bg-slate-800 border-slate-700' }
  return <span className={clsx('text-[9px] font-semibold px-1.5 py-0.5 rounded border', s.cls)}>{s.label}</span>
}

function IvBar({ rank }: { rank: number | null | undefined }) {
  if (rank == null) return <div className="h-1.5 w-full bg-slate-800 rounded-full" />
  const color = rank >= 80 ? 'bg-red-500' : rank >= 50 ? 'bg-amber-500' : rank >= 20 ? 'bg-emerald-500' : 'bg-blue-500'
  return (
    <div className="h-1.5 w-full bg-slate-800 rounded-full overflow-hidden">
      <div className={clsx('h-full rounded-full', color)} style={{ width: `${Math.min(rank, 100)}%` }} />
    </div>
  )
}

function IvSparkline({ history }: { history: { recorded_date: string; iv_current: number }[] }) {
  if (!history || history.length < 3) return null
  const vals = [...history].reverse().map(h => h.iv_current * 100)
  const max = Math.max(...vals)
  const min = Math.min(...vals)
  const range = max - min || 1
  const W = 100, H = 28
  const points = vals.map((v, i) => {
    const x = (i / (vals.length - 1)) * W
    const y = H - ((v - min) / range) * (H - 2) - 1
    return `${x.toFixed(1)},${y.toFixed(1)}`
  }).join(' ')
  return (
    <svg width={W} height={H} className="opacity-70">
      <polyline points={points} fill="none" stroke="#60a5fa" strokeWidth="1.5" strokeLinejoin="round" />
      <circle
        cx={W} cy={H - ((vals[vals.length - 1] - min) / range) * (H - 2) - 1}
        r="2" fill="#60a5fa" />
    </svg>
  )
}

// ── Expanded detail panel for one ticker ─────────────────────────────────────
function TickerDetail({ ticker }: { ticker: string }) {
  const { data: snap, isLoading } = useIvSnapshot(ticker)
  const { data: histData } = useIvHistory(ticker, 90)

  if (isLoading) return <div className="h-20 mt-3 animate-pulse bg-dark-700 rounded" />
  if (!snap) return null

  const ts   = (snap.term_structure  || {}) as any
  const skew = (snap.skew            || {}) as any
  const flow = (snap.options_flow    || {}) as any
  const history: any[] = histData?.history || []

  return (
    <div className="mt-3 border-t border-slate-700/30 pt-3 grid grid-cols-3 gap-4">

      {/* Term Structure */}
      <div>
        <div className="text-[9px] text-slate-500 uppercase tracking-wide font-semibold mb-2">Term Structure</div>
        <div className="space-y-1.5">
          {([['30d', ts.iv_30d], ['60d', ts.iv_60d], ['90d', ts.iv_90d], ['180d', ts.iv_180d]] as [string, number | undefined][]).map(([label, iv]) =>
            iv ? (
              <div key={label} className="flex items-center gap-2">
                <span className="text-[9px] text-slate-600 w-7 shrink-0">{label}</span>
                <div className="flex-1 h-1 bg-slate-800 rounded-full overflow-hidden">
                  <div className="h-full bg-blue-500/50 rounded-full" style={{ width: `${Math.min(iv * 300, 100)}%` }} />
                </div>
                <span className="text-[9px] text-slate-300 font-mono w-9 text-right">{(iv * 100).toFixed(1)}%</span>
              </div>
            ) : null
          )}
          {ts.structure && <div className="mt-1"><StructureBadge structure={ts.structure} /></div>}
        </div>
      </div>

      {/* Skew */}
      <div>
        <div className="text-[9px] text-slate-500 uppercase tracking-wide font-semibold mb-2">Skew Put/Call</div>
        {skew.put_skew != null ? (
          <div className="space-y-1">
            <div className="flex justify-between text-[9px]">
              <span className="text-slate-600">Put 25Δ</span>
              <span className="text-slate-300 font-mono">{skew.iv_put_25d}%</span>
            </div>
            <div className="flex justify-between text-[9px]">
              <span className="text-slate-600">Call 25Δ</span>
              <span className="text-slate-300 font-mono">{skew.iv_call_25d}%</span>
            </div>
            <div className={clsx('text-[10px] font-bold mt-1',
              skew.skew_pct > 3 ? 'text-red-400' : skew.skew_pct < -2 ? 'text-blue-400' : 'text-slate-400')}>
              {skew.skew_pct > 0 ? '+' : ''}{skew.skew_pct} pts
            </div>
            {skew.interpretation && (
              <div className="text-[9px] text-slate-600 italic leading-tight">{skew.interpretation}</div>
            )}
          </div>
        ) : (
          <div className="text-[9px] text-slate-700 italic">Insufficient data</div>
        )}
      </div>

      {/* Options Flow */}
      <div>
        <div className="text-[9px] text-slate-500 uppercase tracking-wide font-semibold mb-2">Options Flow</div>
        {flow.pc_oi_ratio != null ? (
          <div className="space-y-1">
            <div className="flex justify-between text-[9px]">
              <span className="text-slate-600">P/C OI ratio</span>
              <span className={clsx('font-mono font-bold',
                flow.pc_oi_ratio > 1.3 ? 'text-red-400' : flow.pc_oi_ratio < 0.7 ? 'text-blue-400' : 'text-slate-300')}>
                {flow.pc_oi_ratio}
              </span>
            </div>
            {flow.flow_bias && <div className="text-[9px] text-slate-500">{flow.flow_bias}</div>}
            {flow.gamma_bias && <div className="text-[9px] text-amber-500/70">{flow.gamma_bias}</div>}
            {flow.unusual_strikes?.length > 0 && (
              <div className="mt-1 pt-1 border-t border-slate-700/30">
                <div className="text-[8px] text-slate-600 mb-0.5">Unusual strikes</div>
                {flow.unusual_strikes.slice(0, 2).map((s: any) => (
                  <div key={s.strike} className="text-[8px] font-mono text-slate-500">
                    {s.strike} {s.type.toUpperCase()} OI={s.total_oi.toLocaleString()}
                    <span className="text-slate-700"> ({s.pct_otm > 0 ? '+' : ''}{s.pct_otm}%)</span>
                  </div>
                ))}
              </div>
            )}
          </div>
        ) : (
          <div className="text-[9px] text-slate-700 italic">No OI available</div>
        )}
      </div>

      {/* History sparkline */}
      {history.length > 4 && (
        <div className="col-span-3 flex items-center gap-3 pt-1 border-t border-slate-700/20">
          <span className="text-[9px] text-slate-600 shrink-0">IV 90d</span>
          <IvSparkline history={history} />
          <div className="text-[9px] text-slate-600">
            min <span className="text-slate-400">{snap.iv_min_52w_pct}%</span>
            {' · '}max <span className="text-slate-400">{snap.iv_max_52w_pct}%</span>
            {' · '}{snap.history_days}d of history
            {snap.iv_change_1d_pct != null && (
              <>
                {' · '}vs prior day{' '}
                <span className={snap.iv_change_1d_pct > 0 ? 'text-orange-400' : snap.iv_change_1d_pct < 0 ? 'text-blue-400' : 'text-slate-400'}>
                  {snap.iv_change_1d_pct >= 0 ? '+' : ''}{snap.iv_change_1d_pct}pt
                </span>
              </>
            )}
          </div>
        </div>
      )}
    </div>
  )
}

// ── Watchlist Row ─────────────────────────────────────────────────────────────
function WatchlistRow({ item }: { item: any }) {
  const [expanded, setExpanded] = useState(false)
  const signal = ivSignalLabel(item.iv_rank)

  return (
    <div className={clsx('rounded-lg border transition-all', ivRankBg(item.iv_rank))}>
      <div
        className="flex items-center gap-3 px-3 py-2.5 cursor-pointer"
        onClick={() => setExpanded(!expanded)}
      >
        <div className="w-14 shrink-0">
          <div className="text-sm font-bold text-slate-200">{item.ticker}</div>
          {item.proxy && item.proxy !== item.ticker && (
            <div className="text-[8px] text-slate-700">↳ {item.proxy}</div>
          )}
        </div>

        <div className="w-16 shrink-0">
          <span className={clsx('text-sm font-bold font-mono', ivRankColor(item.iv_rank))}>
            {item.iv_current_pct != null ? `${item.iv_source === 'history' ? '~' : ''}${item.iv_current_pct}%` : '—'}
          </span>
          {item.iv_change_1d_pct != null && Math.abs(item.iv_change_1d_pct) >= 0.1 && (
            <span className={clsx('ml-1 text-[9px] font-mono', item.iv_change_1d_pct > 0 ? 'text-orange-400' : 'text-blue-400')}>
              {item.iv_change_1d_pct >= 0 ? '+' : ''}{item.iv_change_1d_pct.toFixed(1)}
            </span>
          )}
          <div className="text-[8px] text-slate-600">{item.iv_source === 'history' ? 'Estimated IV' : 'Current IV'}</div>
        </div>

        <div className="flex-1 min-w-0 space-y-1">
          <div className="flex items-center justify-between">
            <span className="text-[9px] text-slate-600">IV Rank</span>
            <span className={clsx('text-[10px] font-bold font-mono', ivRankColor(item.iv_rank))}>
              {item.iv_rank != null ? `${item.iv_rank}%` : 'N/A'}
            </span>
          </div>
          <IvBar rank={item.iv_rank} />
        </div>

        <div className="w-16 text-right shrink-0">
          <div className="text-[8px] text-slate-600">Pctile</div>
          <div className={clsx('text-[10px] font-mono font-bold', ivRankColor(item.iv_rank))}>
            {item.iv_percentile != null ? `${item.iv_percentile}%` : '—'}
          </div>
        </div>

        <div className="w-32 text-right shrink-0">
          {signal && (
            <div className={clsx('flex items-center justify-end gap-1 text-[10px] font-semibold', signal.cls)}>
              {signal.icon} {signal.text}
            </div>
          )}
          {item.history_days > 0 && (
            <div className="text-[8px] text-slate-500">{item.history_days}d history</div>
          )}
        </div>

        <div className="text-slate-700">
          {expanded ? <ChevronUp className="w-3.5 h-3.5" /> : <ChevronDown className="w-3.5 h-3.5" />}
        </div>
      </div>

      {expanded && (
        <div className="px-3 pb-3">
          <TickerDetail ticker={item.proxy || item.ticker} />
        </div>
      )}
    </div>
  )
}

// ── Saxo-only expanded detail — separate from TickerDetail above by design: this reads
// exclusively from /api/saxo/iv-*, computed from our own accumulated saxo_option_snapshots,
// never blended with the yfinance-based IV watchlist. No Options Flow section — Saxo
// snapshots carry no open interest/volume, so there's nothing honest to show there. ──
function SaxoTickerDetail({ ticker }: { ticker: string }) {
  const { data: snap, isLoading } = useSaxoIvSnapshot(ticker)
  const { data: histData } = useSaxoIvHistory(ticker, 90)

  if (isLoading) return <div className="h-20 mt-3 animate-pulse bg-dark-700 rounded" />
  if (!snap) return null

  const ts   = (snap.term_structure || {}) as any
  const skew = (snap.skew           || {}) as any
  const history: any[] = histData?.history || []

  return (
    <div className="mt-3 border-t border-slate-700/30 pt-3 grid grid-cols-2 gap-4">
      {/* Term Structure */}
      <div>
        <div className="text-[9px] text-slate-500 uppercase tracking-wide font-semibold mb-2">Term Structure (Saxo)</div>
        <div className="space-y-1.5">
          {([['30d', ts.iv_30d], ['60d', ts.iv_60d], ['90d', ts.iv_90d], ['180d', ts.iv_180d]] as [string, number | undefined][]).map(([label, iv]) =>
            iv ? (
              <div key={label} className="flex items-center gap-2">
                <span className="text-[9px] text-slate-500 w-7 shrink-0">{label}</span>
                <div className="flex-1 h-1 bg-slate-800 rounded-full overflow-hidden">
                  <div className="h-full bg-blue-500/50 rounded-full" style={{ width: `${Math.min(iv * 300, 100)}%` }} />
                </div>
                <span className="text-[9px] text-slate-300 font-mono w-9 text-right">{(iv * 100).toFixed(1)}%</span>
              </div>
            ) : null
          )}
          {ts.structure && <div className="mt-1"><StructureBadge structure={ts.structure} /></div>}
          {!ts.iv_30d && !ts.iv_60d && !ts.iv_90d && !ts.iv_180d && (
            <div className="text-[9px] text-slate-500 italic">Not enough expiries captured yet</div>
          )}
        </div>
      </div>

      {/* Skew */}
      <div>
        <div className="text-[9px] text-slate-500 uppercase tracking-wide font-semibold mb-2">Skew Put/Call (Saxo)</div>
        {skew.put_skew != null ? (
          <div className="space-y-1">
            <div className="flex justify-between text-[9px]">
              <span className="text-slate-500">Put 25Δ</span>
              <span className="text-slate-300 font-mono">{skew.iv_put_25d}%</span>
            </div>
            <div className="flex justify-between text-[9px]">
              <span className="text-slate-500">Call 25Δ</span>
              <span className="text-slate-300 font-mono">{skew.iv_call_25d}%</span>
            </div>
            <div className={clsx('text-[10px] font-bold mt-1',
              skew.skew_pct > 3 ? 'text-red-400' : skew.skew_pct < -2 ? 'text-blue-400' : 'text-slate-400')}>
              {skew.skew_pct > 0 ? '+' : ''}{skew.skew_pct} pts
            </div>
            {skew.interpretation && (
              <div className="text-[9px] text-slate-500 italic leading-tight">{skew.interpretation}</div>
            )}
          </div>
        ) : (
          <div className="text-[9px] text-slate-500 italic">Insufficient data</div>
        )}
      </div>

      {/* History sparkline */}
      {history.length > 4 && (
        <div className="col-span-2 flex items-center gap-3 pt-1 border-t border-slate-700/20">
          <span className="text-[9px] text-slate-500 shrink-0">IV 90d</span>
          <IvSparkline history={history} />
          <div className="text-[9px] text-slate-500">
            min <span className="text-slate-400">{snap.iv_min_52w_pct}%</span>
            {' · '}max <span className="text-slate-400">{snap.iv_max_52w_pct}%</span>
            {' · '}{snap.history_days}d of Saxo history
            {snap.iv_change_1d_pct != null && (
              <>
                {' · '}vs prior day{' '}
                <span className={snap.iv_change_1d_pct > 0 ? 'text-orange-400' : snap.iv_change_1d_pct < 0 ? 'text-blue-400' : 'text-slate-400'}>
                  {snap.iv_change_1d_pct >= 0 ? '+' : ''}{snap.iv_change_1d_pct}pt
                </span>
              </>
            )}
          </div>
        </div>
      )}
      {history.length <= 4 && (
        <div className="col-span-2 text-[9px] text-slate-500 italic pt-1 border-t border-slate-700/20">
          Not enough accumulated days yet for a Rank/Percentile — keep the Saxo watchlist snapshotting and it fills in on its own.
        </div>
      )}
    </div>
  )
}

// ── Saxo Watchlist Row — same layout as WatchlistRow, fed by /api/saxo/iv-* only ──
function SaxoWatchlistRow({ item }: { item: any }) {
  const [expanded, setExpanded] = useState(false)
  const signal = ivSignalLabel(item.iv_rank)

  return (
    <div className={clsx('rounded-lg border transition-all', ivRankBg(item.iv_rank))}>
      <div
        className="flex items-center gap-3 px-3 py-2.5 cursor-pointer"
        onClick={() => setExpanded(!expanded)}
      >
        <div className="w-20 shrink-0">
          <div className="text-sm font-bold text-slate-200 truncate" title={item.ticker}>{item.displayName ?? item.ticker}</div>
          <div className="text-[8px] text-slate-500 flex items-center gap-0.5"><Link2 className="w-2 h-2" /> Saxo</div>
        </div>

        <div className="w-16 shrink-0">
          <span className={clsx('text-sm font-bold font-mono', ivRankColor(item.iv_rank))}>
            {item.iv_current_pct != null ? `${item.iv_current_pct}%` : '—'}
          </span>
          {item.iv_change_1d_pct != null && Math.abs(item.iv_change_1d_pct) >= 0.1 && (
            <span className={clsx('ml-1 text-[9px] font-mono', item.iv_change_1d_pct > 0 ? 'text-orange-400' : 'text-blue-400')}>
              {item.iv_change_1d_pct >= 0 ? '+' : ''}{item.iv_change_1d_pct.toFixed(1)}
            </span>
          )}
          <div className="text-[8px] text-slate-500">Current IV</div>
        </div>

        <div className="flex-1 min-w-0 space-y-1">
          <div className="flex items-center justify-between">
            <span className="text-[9px] text-slate-500">IV Rank</span>
            <span className={clsx('text-[10px] font-bold font-mono', ivRankColor(item.iv_rank))}>
              {item.iv_rank != null ? `${item.iv_rank}%` : 'N/A'}
            </span>
          </div>
          <IvBar rank={item.iv_rank} />
        </div>

        <div className="w-16 text-right shrink-0">
          <div className="text-[8px] text-slate-500">Pctile</div>
          <div className={clsx('text-[10px] font-mono font-bold', ivRankColor(item.iv_rank))}>
            {item.iv_percentile != null ? `${item.iv_percentile}%` : '—'}
          </div>
        </div>

        <div className="w-32 text-right shrink-0">
          {signal && (
            <div className={clsx('flex items-center justify-end gap-1 text-[10px] font-semibold', signal.cls)}>
              {signal.icon} {signal.text}
            </div>
          )}
          {item.history_days > 0 && (
            <div className="text-[8px] text-slate-500">{item.history_days}d Saxo history</div>
          )}
        </div>

        <div className="text-slate-500">
          {expanded ? <ChevronUp className="w-3.5 h-3.5" /> : <ChevronDown className="w-3.5 h-3.5" />}
        </div>
      </div>

      {expanded && (
        <div className="px-3 pb-3">
          <SaxoTickerDetail ticker={item.ticker} />
        </div>
      )}
    </div>
  )
}

// ── Watchlist Manager ─────────────────────────────────────────────────────────
function WatchlistManager() {
  const qc = useQueryClient()
  const { data } = useWatchlistTickers()
  const { mutate: addTicker, isPending: adding } = useAddWatchlistTicker()
  const { mutate: removeTicker } = useRemoveWatchlistTicker()
  const [input, setInput] = useState('')
  const [showInactive, setShowInactive] = useState(false)

  const entries: any[] = data?.tickers ?? []
  const active = entries.filter(e => e.is_active)
  const inactive = entries.filter(e => !e.is_active)

  const handleAdd = () => {
    const t = input.trim().toUpperCase()
    if (!t) return
    addTicker(t, {
      onSuccess: () => {
        setInput('')
        qc.invalidateQueries({ queryKey: ['watchlist-tickers'] })
        qc.invalidateQueries({ queryKey: ['iv-watchlist'] })
      }
    })
  }

  const handleRemove = (ticker: string) => {
    removeTicker(ticker, {
      onSuccess: () => {
        qc.invalidateQueries({ queryKey: ['watchlist-tickers'] })
        qc.invalidateQueries({ queryKey: ['iv-watchlist'] })
      }
    })
  }

  return (
    <div className="card space-y-3">
      <div className="flex items-center gap-2">
        <List className="w-4 h-4 text-slate-400" />
        <span className="text-sm font-semibold text-slate-300">IV Watchlist Manager</span>
        <span className="ml-auto text-xs text-slate-600">{active.length} active tickers</span>
      </div>

      {/* Add ticker */}
      <div className="flex gap-2">
        <input
          className="flex-1 bg-slate-800 border border-slate-700 rounded px-3 py-1.5 text-xs text-slate-300 placeholder:text-slate-600"
          placeholder="Add ticker (e.g. AAPL, FXI, EEM…)"
          value={input}
          onChange={e => setInput(e.target.value.toUpperCase())}
          onKeyDown={e => e.key === 'Enter' && handleAdd()}
        />
        <button
          onClick={handleAdd}
          disabled={adding || !input.trim()}
          className="flex items-center gap-1.5 px-3 py-1.5 text-xs bg-blue-600/20 hover:bg-blue-600/30 border border-blue-600/40 text-blue-400 rounded disabled:opacity-40 transition-all"
        >
          <Plus className="w-3.5 h-3.5" />
          {adding ? 'Adding...' : 'Add'}
        </button>
      </div>
      <p className="text-[10px] text-slate-600">The system automatically bootstraps 1 year of IV history for each new ticker added.</p>

      {/* Active tickers */}
      <div className="flex flex-wrap gap-1.5">
        {active.map(e => (
          <span key={e.ticker} className={clsx(
            'inline-flex items-center gap-1 px-2 py-0.5 rounded text-[10px] font-mono',
            e.added_by === 'builtin' ? 'bg-slate-800 text-slate-400 border border-slate-700/50' :
            e.added_by === 'cycle'   ? 'bg-blue-900/30 text-blue-300 border border-blue-700/30' :
                                       'bg-emerald-900/20 text-emerald-300 border border-emerald-700/30'
          )}>
            {e.ticker}
            {e.added_by !== 'builtin' && (
              <button onClick={() => handleRemove(e.ticker)} className="opacity-50 hover:opacity-100 ml-0.5">
                <Trash2 className="w-2.5 h-2.5" />
              </button>
            )}
          </span>
        ))}
      </div>
      <div className="text-[9px] text-slate-700 flex gap-3">
        <span className="text-slate-800 border-b border-slate-700">■</span> Builtins &nbsp;
        <span className="text-blue-700 border-b border-blue-700">■</span> Auto (cycle) &nbsp;
        <span className="text-emerald-700 border-b border-emerald-700">■</span> Manual
      </div>

      {inactive.length > 0 && (
        <button onClick={() => setShowInactive(!showInactive)} className="text-[10px] text-slate-600 hover:text-slate-400">
          {showInactive ? 'Hide' : `Show ${inactive.length} disabled ticker(s)`}
        </button>
      )}
      {showInactive && inactive.map(e => (
        <span key={e.ticker} className="inline-flex items-center gap-1 px-2 py-0.5 rounded text-[10px] font-mono bg-slate-900 text-slate-700 line-through mr-1">
          {e.ticker}
        </span>
      ))}
    </div>
  )
}

// ── Main page ─────────────────────────────────────────────────────────────────
export default function OptionsLab() {
  // yfinance-based IV watchlist — disabled per user request (2026-07-21): Options Lab
  // should only show Saxo broker data now, linked from Config -> Instruments Watchlist.
  // Kept commented out rather than deleted in case yfinance coverage is wanted again
  // later (e.g. for symbols with no Saxo link).
  //
  // const { data, isLoading, refetch, isFetching } = useIvWatchlist()
  // const [bootstrapping, setBootstrapping] = useState(false)
  // const [bootstrapMsg, setBootstrapMsg] = useState<string | null>(null)
  // const items: any[] = data?.items || []
  //
  // const sellVol = items.filter(i => (i.iv_rank ?? 50) >= 80)
  // const buyVol  = items.filter(i => i.iv_rank != null && i.iv_rank < 20)
  // const neutral = items.filter(i => i.iv_rank != null && i.iv_rank >= 20 && i.iv_rank < 80)
  // const noData  = items.filter(i => i.iv_rank == null)
  //
  // const handleBootstrap = async () => {
  //   setBootstrapping(true)
  //   setBootstrapMsg(null)
  //   try {
  //     await api.post('/options-vol/bootstrap-history')
  //     setBootstrapMsg('Bootstrap started (~60s) — refresh in 1 minute to see updated IV Ranks.')
  //     setTimeout(() => refetch(), 70_000)
  //   } catch {
  //     setBootstrapMsg('Error during bootstrap.')
  //   } finally {
  //     setBootstrapping(false)
  //   }
  // }
  //
  // // Show bootstrap banner if most items have no meaningful IV Rank (stuck at 50 or null)
  // const needsBootstrap = items.length > 0 && items.filter(i => i.iv_rank == null || i.iv_rank === 50).length > items.length * 0.6

  const { data: saxoData, isLoading: saxoLoading, refetch: refetchSaxo, isFetching: saxoFetching } = useSaxoIvWatchlist()
  const { data: watchlistInstruments } = useInstrumentsWatchlist()
  // Cross-reference the Saxo IV watchlist (keyed by Saxo option symbol, e.g. "MCLU6")
  // against the tracked instruments (keyed by our own ticker, e.g. "CL=F") to show the
  // friendly/renamed name instead of the raw Saxo symbol.
  const nameBySaxoOptionSymbol: Record<string, string> = {}
  for (const w of ((watchlistInstruments as any[]) ?? [])) {
    if (w.saxo_option_symbol) nameBySaxoOptionSymbol[w.saxo_option_symbol] = w.name || w.ticker
  }
  const saxoItems: any[] = (saxoData?.items || []).map((item: any) => ({
    ...item,
    displayName: nameBySaxoOptionSymbol[item.ticker] || item.ticker,
  }))

  return (
    <div className="p-6 space-y-5">
      {/* yfinance bootstrap banner — disabled along with the yfinance section below.
      {needsBootstrap && !bootstrapMsg && (
        <div className="flex items-center justify-between gap-3 px-4 py-3 rounded border border-amber-700/40 bg-amber-900/10 text-xs text-amber-300">
          <span>⚠️ Insufficient IV history — IV Rank stuck at 50%. Bootstrap 1 year of realized data to calibrate the Rank.</span>
          <button
            onClick={handleBootstrap}
            disabled={bootstrapping}
            className="flex items-center gap-1.5 text-xs bg-amber-700/30 hover:bg-amber-700/50 border border-amber-600/50 text-amber-200 px-3 py-1.5 rounded transition-all whitespace-nowrap disabled:opacity-50"
          >
            <Database className={clsx('w-3.5 h-3.5', bootstrapping && 'animate-pulse')} />
            {bootstrapping ? 'Loading...' : 'Initialize history'}
          </button>
        </div>
      )}
      {bootstrapMsg && (
        <div className="px-4 py-3 rounded border border-blue-700/40 bg-blue-900/10 text-xs text-blue-300">
          ℹ️ {bootstrapMsg}
        </div>
      )}
      */}

      <div className="flex items-center justify-between">
        <div>
          <h1 className="text-xl font-bold text-white flex items-center gap-2">
            <Activity className="w-5 h-5 text-blue-400" /> Options Lab
          </h1>
          <p className="text-xs text-slate-500 mt-0.5">
            Saxo broker data · IV Rank · Term Structure · Skew
          </p>
        </div>
      </div>

      {/* Légende */}
      <div className="grid grid-cols-2 gap-3">
        <div className="card bg-red-900/10 border-red-700/20 text-xs">
          <div className="flex items-center gap-2 mb-1">
            <TrendingDown className="w-3.5 h-3.5 text-red-400" />
            <span className="font-semibold text-red-400">IV Rank &gt; 80% — Sell vol</span>
          </div>
          <div className="text-slate-500 leading-snug">Credit spreads, iron condors, covered calls. Premium is high → seller has the edge.</div>
        </div>
        <div className="card bg-blue-900/10 border-blue-700/20 text-xs">
          <div className="flex items-center gap-2 mb-1">
            <TrendingUp className="w-3.5 h-3.5 text-blue-400" />
            <span className="font-semibold text-blue-400">IV Rank &lt; 20% — Buy convexity</span>
          </div>
          <div className="text-slate-500 leading-snug">Long calls, long puts, straddles, strangles. Premium is cheap → good time to buy gamma.</div>
        </div>
      </div>
      <div className="text-[10px] text-slate-600 -mt-2 px-1">
        <strong className="text-slate-500">Contango</strong> = short IV &lt; long IV (calm market, good for selling short term) ·
        <strong className="text-slate-500"> Backwardation</strong> = short IV &gt; long IV (stress, good for buying short protection) ·
        <strong className="text-slate-500"> Skew +</strong> = puts more expensive than calls (institutional bearish bias)
      </div>

      {/* yfinance IV watchlist rows — disabled along with the hooks/state above.
      {isLoading ? (
        <div className="space-y-2">
          {[...Array(6)].map((_, i) => <div key={i} className="h-12 animate-pulse bg-dark-700 rounded-lg" />)}
        </div>
      ) : items.length === 0 ? (
        <div className="card text-center py-12 text-slate-600">
          <Activity className="w-8 h-8 mx-auto mb-3 opacity-30" />
          <div className="font-semibold mb-1 text-slate-500">No IV data available</div>
          <div className="text-xs text-slate-600">
            US ETFs are required (SPY, QQQ, GLD...).
            <br />IV Rank requires history — data accumulates with each refresh.
          </div>
          <button onClick={() => refetch()} disabled={isFetching}
            className="mt-4 text-xs bg-blue-600 hover:bg-blue-500 text-white px-4 py-1.5 rounded disabled:opacity-50">
            Start collection
          </button>
        </div>
      ) : (
        <div className="space-y-5">
          {sellVol.length > 0 && (
            <div>
              <div className="text-xs font-semibold text-red-400 uppercase tracking-wide mb-2 flex items-center gap-1.5">
                <TrendingDown className="w-3.5 h-3.5" /> Sell vol — IVR &gt; 80% ({sellVol.length})
              </div>
              <div className="space-y-1.5">{sellVol.map(item => <WatchlistRow key={item.ticker} item={item} />)}</div>
            </div>
          )}
          {buyVol.length > 0 && (
            <div>
              <div className="text-xs font-semibold text-blue-400 uppercase tracking-wide mb-2 flex items-center gap-1.5">
                <TrendingUp className="w-3.5 h-3.5" /> Buy vol — IVR &lt; 20% ({buyVol.length})
              </div>
              <div className="space-y-1.5">{buyVol.map(item => <WatchlistRow key={item.ticker} item={item} />)}</div>
            </div>
          )}
          {neutral.length > 0 && (
            <div>
              <div className="text-xs font-semibold text-slate-500 uppercase tracking-wide mb-2 flex items-center gap-1.5">
                <Minus className="w-3.5 h-3.5" /> Neutral zone — IVR 20–80% ({neutral.length})
              </div>
              <div className="space-y-1.5">{neutral.map(item => <WatchlistRow key={item.ticker} item={item} />)}</div>
            </div>
          )}
          {noData.length > 0 && (
            <div>
              <div className="text-xs text-slate-500 uppercase tracking-wide mb-2">No history ({noData.length})</div>
              <div className="space-y-1.5">{noData.map(item => <WatchlistRow key={item.ticker} item={item} />)}</div>
            </div>
          )}
        </div>
      )}
      */}

      {/* ── Saxo section — the only IV data source now. Symbols come from the Saxo
          watchlist (Config → Saxo), auto-populated by linking a tracked instrument to a
          Saxo symbol (Config → Instruments Watchlist). Computed purely from our own
          accumulated saxo_option_snapshots, never blended with yfinance IV. ── */}
      <div>
        <div className="flex items-center justify-between mb-3">
          <div>
            <div className="text-sm font-bold text-white flex items-center gap-2">
              <Link2 className="w-4 h-4 text-emerald-400" /> Saxo Broker Data
            </div>
            <p className="text-[10px] text-slate-500 mt-0.5">
              IV Rank · Term Structure · Skew, computed only from your Saxo watchlist's accumulated option snapshots — manage the symbol list in Config → Saxo.
            </p>
          </div>
          <button
            onClick={() => refetchSaxo()}
            disabled={saxoFetching}
            className="flex items-center gap-1.5 text-xs border border-slate-600 text-slate-400 hover:text-slate-200 hover:border-slate-500 px-3 py-1.5 rounded transition-all disabled:opacity-50"
          >
            <RefreshCw className={clsx('w-3.5 h-3.5', saxoFetching && 'animate-spin')} />
            {saxoFetching ? 'Loading...' : 'Refresh'}
          </button>
        </div>

        {saxoLoading ? (
          <div className="space-y-2">
            {[...Array(2)].map((_, i) => <div key={i} className="h-12 animate-pulse bg-dark-700 rounded-lg" />)}
          </div>
        ) : saxoItems.length === 0 ? (
          <div className="card text-center py-8 text-slate-500 text-xs">
            No Saxo IV data yet — add symbols to the Saxo watchlist (Config → Saxo) and let a few snapshot cycles accumulate.
          </div>
        ) : (
          <div className="space-y-1.5">
            {saxoItems.map(item => <SaxoWatchlistRow key={item.ticker} item={item} />)}
          </div>
        )}
      </div>

      {/* yfinance IV Watchlist Manager — disabled along with the section above.
      <WatchlistManager />
      */}
    </div>
  )
}
