'use client'

import { useState, useCallback } from 'react'
import type { FlowNode, IntegrationConfig } from '@/lib/types'
import { SUPPORTED_CHAINS, getBalances, detectSafeChains } from '@/lib/api/safe-client'
import type { SafeBalance, DetectedChain } from '@/lib/api/safe-client'
import { safeBalancesToFunnels } from '@/lib/integrations'

interface IntegrationPanelProps {
  isOpen: boolean
  onClose: () => void
  onImportNodes: (nodes: FlowNode[]) => void
  integrations?: IntegrationConfig
  onIntegrationsChange: (config: IntegrationConfig) => void
}

export default function IntegrationPanel({
  isOpen,
  onClose,
  onImportNodes,
  integrations,
  onIntegrationsChange,
}: IntegrationPanelProps) {
  // Safe wallet state
  const [safeAddress, setSafeAddress] = useState(integrations?.safe?.address || '')
  const [selectedChains, setSelectedChains] = useState<number[]>(
    integrations?.safe?.chainIds || [100, 10]
  )
  const [detectedChains, setDetectedChains] = useState<DetectedChain[]>([])
  const [balances, setBalances] = useState<Map<number, SafeBalance[]>>(new Map())
  const [safeFetching, setSafeFetching] = useState(false)
  const [safeError, setSafeError] = useState('')

  // rVote state
  const [rvoteSlug, setRvoteSlug] = useState(integrations?.rvote?.spaceSlug || '')
  const [rvoteFetching, setRvoteFetching] = useState(false)
  const [rvoteError, setRvoteError] = useState('')
  const [rvoteSpace, setRvoteSpace] = useState<{ name: string; memberCount: number } | null>(null)
  const [rvoteProposals, setRvoteProposals] = useState<Array<{ id: string; title: string; score: number }>>([])

  const handleFetchSafe = useCallback(async () => {
    if (!safeAddress.match(/^0x[a-fA-F0-9]{40}$/)) {
      setSafeError('Invalid Ethereum address')
      return
    }

    setSafeFetching(true)
    setSafeError('')
    setBalances(new Map())

    try {
      const detected = await detectSafeChains(safeAddress, selectedChains)
      setDetectedChains(detected)

      if (detected.length === 0) {
        setSafeError('No Safe found on selected chains')
        setSafeFetching(false)
        return
      }

      const balanceMap = new Map<number, SafeBalance[]>()
      for (const { chainId } of detected) {
        const chainBalances = await getBalances(safeAddress, chainId)
        balanceMap.set(chainId, chainBalances)
      }
      setBalances(balanceMap)

      onIntegrationsChange({
        ...integrations,
        safe: {
          address: safeAddress,
          chainIds: detected.map((d) => d.chainId),
          lastSyncedAt: Date.now(),
        },
      })
    } catch (e) {
      setSafeError(e instanceof Error ? e.message : 'Failed to fetch')
    } finally {
      setSafeFetching(false)
    }
  }, [safeAddress, selectedChains, integrations, onIntegrationsChange])

  const handleImportSafe = useCallback(() => {
    const allNodes: FlowNode[] = []
    let xOffset = 0

    balances.forEach((chainBalances, chainId) => {
      const nodes = safeBalancesToFunnels(chainBalances, safeAddress, chainId, {
        x: xOffset,
        y: 100,
      })
      allNodes.push(...nodes)
      xOffset += nodes.length * 280
    })

    if (allNodes.length > 0) {
      onImportNodes(allNodes)
      onClose()
    }
  }, [balances, safeAddress, onImportNodes, onClose])

  const handleFetchRvote = useCallback(async () => {
    if (!rvoteSlug.trim()) {
      setRvoteError('Enter a space slug')
      return
    }

    setRvoteFetching(true)
    setRvoteError('')

    try {
      // Fetch via proxy to avoid CORS
      const spaceRes = await fetch(`/api/proxy/rvote?endpoint=space&slug=${encodeURIComponent(rvoteSlug)}`)
      if (!spaceRes.ok) {
        setRvoteError(spaceRes.status === 404 ? 'Space not found' : 'Failed to fetch space')
        setRvoteFetching(false)
        return
      }
      const space = await spaceRes.json()
      setRvoteSpace({ name: space.name, memberCount: space._count?.members || 0 })

      const proposalsRes = await fetch(
        `/api/proxy/rvote?endpoint=proposals&slug=${encodeURIComponent(rvoteSlug)}&status=PASSED`
      )
      if (proposalsRes.ok) {
        const data = await proposalsRes.json()
        const proposals = data.proposals || data.results || data || []
        setRvoteProposals(
          Array.isArray(proposals)
            ? proposals.map((p: { id: string; title: string; score: number }) => ({
                id: p.id,
                title: p.title,
                score: p.score,
              }))
            : []
        )
      }

      onIntegrationsChange({
        ...integrations,
        rvote: {
          spaceSlug: rvoteSlug,
          spaceName: space.name,
          lastSyncedAt: Date.now(),
        },
      })
    } catch (e) {
      setRvoteError(e instanceof Error ? e.message : 'Failed to fetch')
    } finally {
      setRvoteFetching(false)
    }
  }, [rvoteSlug, integrations, onIntegrationsChange])

  const handleImportRvote = useCallback(async () => {
    if (rvoteProposals.length === 0) return

    // Re-fetch full proposal data for import
    try {
      const res = await fetch(
        `/api/proxy/rvote?endpoint=proposals&slug=${encodeURIComponent(rvoteSlug)}&status=PASSED`
      )
      if (!res.ok) return
      const data = await res.json()
      const proposals = data.proposals || data.results || data || []
      if (!Array.isArray(proposals)) return

      const { proposalsToOutcomes } = await import('@/lib/integrations')
      const nodes = proposalsToOutcomes(proposals, rvoteSlug)
      if (nodes.length > 0) {
        onImportNodes(nodes)
        onClose()
      }
    } catch {
      setRvoteError('Failed to import proposals')
    }
  }, [rvoteProposals, rvoteSlug, onImportNodes, onClose])

  const toggleChain = (chainId: number) => {
    setSelectedChains((prev) =>
      prev.includes(chainId) ? prev.filter((c) => c !== chainId) : [...prev, chainId]
    )
  }

  if (!isOpen) return null

  const totalBalances = Array.from(balances.values()).flat().filter((b) => parseFloat(b.fiatBalance) > 1)

  return (
    <div className="fixed inset-0 z-50 flex items-center justify-center bg-black/30 backdrop-blur-sm">
      <div className="bg-white rounded-xl shadow-2xl border border-slate-200 w-full max-w-lg max-h-[85vh] overflow-y-auto m-4">
        <div className="sticky top-0 bg-white border-b border-slate-200 px-6 py-4 flex items-center justify-between rounded-t-xl">
          <h2 className="text-lg font-bold text-slate-800">Link External Data</h2>
          <button onClick={onClose} className="text-slate-400 hover:text-slate-600 text-xl font-bold">
            &times;
          </button>
        </div>

        <div className="p-6 space-y-6">
          {/* ─── Safe Wallet Section ─── */}
          <div>
            <h3 className="text-sm font-semibold text-slate-700 uppercase tracking-wide mb-3 flex items-center gap-2">
              <span className="w-2 h-2 rounded-full bg-emerald-500" />
              Safe Wallet → Funnels
            </h3>

            <div className="space-y-3">
              <input
                type="text"
                value={safeAddress}
                onChange={(e) => setSafeAddress(e.target.value)}
                placeholder="0x... Safe address"
                className="w-full px-3 py-2 rounded-lg border border-slate-300 text-sm font-mono focus:outline-none focus:border-blue-400 focus:ring-1 focus:ring-blue-400"
              />

              <div className="flex gap-2">
                {Object.entries(SUPPORTED_CHAINS).map(([id, chain]) => (
                  <button
                    key={id}
                    onClick={() => toggleChain(Number(id))}
                    className={`px-3 py-1.5 rounded-md text-xs font-medium border transition-all ${
                      selectedChains.includes(Number(id))
                        ? 'border-current text-white'
                        : 'border-slate-200 text-slate-400'
                    }`}
                    style={
                      selectedChains.includes(Number(id))
                        ? { backgroundColor: chain.color, borderColor: chain.color }
                        : undefined
                    }
                  >
                    {chain.name}
                  </button>
                ))}
              </div>

              <button
                onClick={handleFetchSafe}
                disabled={safeFetching || !safeAddress || selectedChains.length === 0}
                className="w-full px-4 py-2 rounded-lg text-sm font-medium bg-emerald-500 text-white hover:bg-emerald-600 disabled:bg-slate-200 disabled:text-slate-400 transition-all"
              >
                {safeFetching ? 'Fetching...' : 'Fetch Balances'}
              </button>

              {safeError && <p className="text-xs text-red-500">{safeError}</p>}

              {detectedChains.length > 0 && (
                <div className="bg-slate-50 rounded-lg p-3 space-y-2">
                  <p className="text-xs text-slate-500">
                    Safe found on{' '}
                    {detectedChains.map((d) => d.chain.name).join(', ')}
                    {' '}({detectedChains[0]?.safeInfo.owners.length} owners, {detectedChains[0]?.safeInfo.threshold} threshold)
                  </p>

                  {totalBalances.length > 0 && (
                    <>
                      <div className="space-y-1">
                        {totalBalances.slice(0, 8).map((b, i) => (
                          <div key={i} className="flex items-center justify-between text-xs">
                            <span className="font-medium text-slate-700">{b.symbol}</span>
                            <span className="text-slate-500">
                              {b.balanceFormatted} (${parseFloat(b.fiatBalance).toLocaleString(undefined, { maximumFractionDigits: 0 })})
                            </span>
                          </div>
                        ))}
                        {totalBalances.length > 8 && (
                          <p className="text-[10px] text-slate-400">
                            +{totalBalances.length - 8} more tokens
                          </p>
                        )}
                      </div>

                      <button
                        onClick={handleImportSafe}
                        className="w-full px-3 py-2 rounded-lg text-sm font-medium bg-blue-500 text-white hover:bg-blue-600 transition-all"
                      >
                        Import {totalBalances.length} Funnel{totalBalances.length !== 1 ? 's' : ''}
                      </button>
                    </>
                  )}
                </div>
              )}
            </div>
          </div>

          <div className="border-t border-slate-200" />

          {/* ─── rVote Section ─── */}
          <div>
            <h3 className="text-sm font-semibold text-slate-700 uppercase tracking-wide mb-3 flex items-center gap-2">
              <span className="w-2 h-2 rounded-full bg-violet-500" />
              rVote Space → Outcomes
            </h3>

            <div className="space-y-3">
              <div className="flex gap-2">
                <input
                  type="text"
                  value={rvoteSlug}
                  onChange={(e) => setRvoteSlug(e.target.value)}
                  placeholder="Space slug (e.g., crypto)"
                  className="flex-1 px-3 py-2 rounded-lg border border-slate-300 text-sm focus:outline-none focus:border-violet-400 focus:ring-1 focus:ring-violet-400"
                />
                <span className="flex items-center text-xs text-slate-400">.rvote.online</span>
              </div>

              <button
                onClick={handleFetchRvote}
                disabled={rvoteFetching || !rvoteSlug.trim()}
                className="w-full px-4 py-2 rounded-lg text-sm font-medium bg-violet-500 text-white hover:bg-violet-600 disabled:bg-slate-200 disabled:text-slate-400 transition-all"
              >
                {rvoteFetching ? 'Fetching...' : 'Fetch Proposals'}
              </button>

              {rvoteError && <p className="text-xs text-red-500">{rvoteError}</p>}

              {rvoteSpace && (
                <div className="bg-slate-50 rounded-lg p-3 space-y-2">
                  <p className="text-xs text-slate-500">
                    <span className="font-medium text-slate-700">{rvoteSpace.name}</span>
                    {' '}&bull; {rvoteSpace.memberCount} members
                    {' '}&bull; {rvoteProposals.length} passed proposal{rvoteProposals.length !== 1 ? 's' : ''}
                  </p>

                  {rvoteProposals.length > 0 ? (
                    <>
                      <div className="space-y-1">
                        {rvoteProposals.slice(0, 6).map((p) => (
                          <div key={p.id} className="flex items-center justify-between text-xs">
                            <span className="text-slate-700 truncate mr-2">{p.title}</span>
                            <span className="text-violet-500 font-medium shrink-0">+{p.score}</span>
                          </div>
                        ))}
                        {rvoteProposals.length > 6 && (
                          <p className="text-[10px] text-slate-400">
                            +{rvoteProposals.length - 6} more
                          </p>
                        )}
                      </div>

                      <button
                        onClick={handleImportRvote}
                        className="w-full px-3 py-2 rounded-lg text-sm font-medium bg-blue-500 text-white hover:bg-blue-600 transition-all"
                      >
                        Import {rvoteProposals.length} Outcome{rvoteProposals.length !== 1 ? 's' : ''}
                      </button>
                    </>
                  ) : (
                    <p className="text-xs text-slate-400">No passed proposals found in this space</p>
                  )}
                </div>
              )}
            </div>
          </div>
        </div>
      </div>
    </div>
  )
}
