import { useState, useEffect, useCallback } from 'react'
import { adminApi, type SurveyResponseDetail, type SurveyResponseListResponse } from '@/api/admin'
import { PageHeader } from '@/components/admin'
import {
  ChevronDown,
  Download,
  User,
  Link2,
  Loader2,
  Eye,
  EyeOff,
  Archive,
  ArchiveRestore,
  Trash2,
  CheckSquare,
  Square,
  MoreHorizontal,
  Circle,
} from 'lucide-react'
import { cn } from '@/lib/utils'
import { toast } from '@/lib/toast'

const QUESTIONS: { id: string; num: string; text: string; type: 'mc' | 'mc-multi' | 'range' | 'text' | 'rank' }[] = [
  { id: 'prereqs', num: '1', text: 'Before you start troubleshooting, what info do you need?', type: 'mc-multi' },
  { id: 'verify_fix', num: '2', text: 'After you apply a fix, how do you verify it actually worked?', type: 'mc' },
  { id: 'steps_at_a_time', num: '3', text: 'How many steps do you prefer to see at once?', type: 'range' },
  { id: 'first_step', num: '4', text: 'A vague ticket comes in: "Internet is down." What\'s your FIRST move?', type: 'mc' },
  { id: 'junior_mistake', num: '5', text: 'Most common mistake you see junior engineers make?', type: 'mc' },
  { id: 'pivot', num: '6', text: 'How do you decide when to stop pursuing one theory and pivot?', type: 'mc' },
  { id: 'scenario_approach', num: '7', text: 'Walk through your first 3 diagnostic steps for this ticket.', type: 'text' },
  { id: 'scenario_deeper', num: '8', text: 'Server pings fine, you can RDP in. What do you check next?', type: 'text' },
  { id: 'doc_pct', num: '9', text: 'What percentage of troubleshooting steps do you actually document?', type: 'range' },
  { id: 'go_to_commands', num: '10', text: 'Top 3 go-to PowerShell commands or one-liners?', type: 'text' },
  { id: 'secret_weapon', num: '11', text: 'Secret weapon command/tool/technique?', type: 'text' },
  { id: 'gotcha', num: '12', text: 'Issue where the obvious diagnosis was WRONG?', type: 'text' },
  { id: 'hard_rules', num: '13', text: 'Which "rules" do you follow?', type: 'mc-multi' },
  { id: 'prioritization', num: '14', text: 'Rank factors by diagnostic priority influence.', type: 'rank' },
  { id: 'detail_level', num: '15', text: 'How specific should AI diagnostic suggestions be?', type: 'mc' },
  { id: 'ai_personality', num: '16', text: 'What makes an AI feel like a useful colleague?', type: 'mc' },
]

function AnswerDisplay({ value, type }: { value: string | string[] | undefined; type: string }) {
  if (!value || (Array.isArray(value) && value.length === 0)) {
    return <p className="text-sm italic text-muted-foreground/60">No answer</p>
  }

  if (type === 'mc-multi' && Array.isArray(value)) {
    return (
      <div className="flex flex-wrap gap-1.5">
        {value.map((v, i) => (
          <span
            key={i}
            className="inline-block rounded-full bg-accent-dim px-2.5 py-0.5 font-sans text-xs text-[0.625rem] uppercase tracking-wider text-primary"
          >
            {v}
          </span>
        ))}
      </div>
    )
  }

  if (type === 'rank' && Array.isArray(value)) {
    return (
      <ol className="space-y-1">
        {value.map((v, i) => (
          <li key={i} className="flex items-start gap-2 text-sm text-foreground/90">
            <span className="font-sans text-xs text-xs font-bold text-primary">{i + 1}.</span>
            {v}
          </li>
        ))}
      </ol>
    )
  }

  if (type === 'text') {
    return (
      <div className="border-l-2 border-primary/30 pl-3">
        <p className="text-sm text-foreground/90 whitespace-pre-wrap">{String(value)}</p>
      </div>
    )
  }

  return <p className="text-sm text-foreground/90">{String(value)}</p>
}

function ExpandedDetail({ response }: { response: SurveyResponseDetail }) {
  return (
    <tr>
      <td colSpan={8} className="p-0">
        <div
          className="px-6 py-5"
          style={{
            background: 'rgba(0, 0, 0, 0.15)',
            borderTop: '1px solid rgba(96, 165, 250, 0.1)',
          }}
        >
          <div className="grid grid-cols-1 gap-3 md:grid-cols-2">
            {QUESTIONS.map((q) => (
              <div
                key={q.id}
                className="rounded-lg p-4"
                style={{
                  background: 'var(--color-bg-card)',
                  border: '1px solid var(--color-border-default)',
                }}
              >
                <p className="font-sans text-xs text-[0.625rem] uppercase tracking-widest text-primary mb-1">
                  Q{q.num}
                </p>
                <p className="text-xs text-muted-foreground mb-2">{q.text}</p>
                <AnswerDisplay value={response.responses[q.id]} type={q.type} />
              </div>
            ))}
          </div>
        </div>
      </td>
    </tr>
  )
}

function ResponseRow({
  response,
  index,
  isExpanded,
  isSelected,
  onToggle,
  onSelect,
  onMarkRead,
  onArchive,
  onDelete,
}: {
  response: SurveyResponseDetail
  index: number
  isExpanded: boolean
  isSelected: boolean
  onToggle: () => void
  onSelect: () => void
  onMarkRead: () => void
  onArchive: () => void
  onDelete: () => void
}) {
  const answeredCount = QUESTIONS.filter((q) => {
    const val = response.responses[q.id]
    return val !== undefined && val !== null && val !== '' && !(Array.isArray(val) && val.length === 0)
  }).length

  const [showMenu, setShowMenu] = useState(false)

  return (
    <>
      <tr
        className={cn(
          'border-b border-border/50 transition-colors cursor-pointer',
          !response.is_read && 'bg-primary/3',
          'hover:bg-card'
        )}
      >
        {/* Checkbox */}
        <td className="px-2 py-3 w-8" onClick={e => { e.stopPropagation(); onSelect() }}>
          {isSelected ? (
            <CheckSquare className="h-4 w-4 text-primary cursor-pointer" />
          ) : (
            <Square className="h-4 w-4 text-muted-foreground/40 cursor-pointer hover:text-muted-foreground" />
          )}
        </td>

        {/* Unread dot */}
        <td className="px-1 py-3 w-6" onClick={onToggle}>
          {!response.is_read && (
            <Circle className="h-2.5 w-2.5 fill-primary text-primary" />
          )}
        </td>

        {/* Expand chevron */}
        <td className="px-2 py-3 w-8" onClick={onToggle}>
          <ChevronDown
            className={cn(
              'h-4 w-4 text-muted-foreground transition-transform',
              isExpanded && 'rotate-180'
            )}
          />
        </td>
        <td className="px-4 py-3 font-sans text-xs text-xs text-muted-foreground" onClick={onToggle}>{index + 1}</td>
        <td className={cn('px-4 py-3 text-sm', !response.is_read ? 'text-foreground font-medium' : 'text-foreground')} onClick={onToggle}>
          {response.respondent_name || <span className="text-muted-foreground italic">Anonymous</span>}
        </td>
        <td className="px-4 py-3" onClick={onToggle}>
          {response.source === 'invite' ? (
            <span className="inline-flex items-center gap-1.5 rounded-full px-2 py-0.5 font-sans text-xs text-[0.625rem] uppercase tracking-wider bg-accent-dim text-primary">
              <User className="h-3 w-3" />
              Invite
              {response.invite_name && (
                <span className="text-primary/70">({response.invite_name})</span>
              )}
            </span>
          ) : (
            <span className="inline-flex items-center gap-1.5 rounded-full px-2 py-0.5 font-sans text-xs text-[0.625rem] uppercase tracking-wider bg-brand-border text-muted-foreground">
              <Link2 className="h-3 w-3" />
              Direct
            </span>
          )}
        </td>
        <td className="px-4 py-3 font-sans text-xs text-xs text-muted-foreground" onClick={onToggle}>
          {new Date(response.created_at).toLocaleDateString('en-US', {
            month: 'short',
            day: 'numeric',
            year: 'numeric',
          })}
        </td>
        <td className="px-4 py-3 text-sm text-muted-foreground" onClick={onToggle}>
          {answeredCount} / {QUESTIONS.length}
        </td>
        {/* Actions */}
        <td className="px-3 py-3 w-10 relative">
          <button
            onClick={e => { e.stopPropagation(); setShowMenu(!showMenu) }}
            className="p-1.5 rounded-lg hover:bg-border text-muted-foreground hover:text-foreground transition-colors"
          >
            <MoreHorizontal className="h-4 w-4" />
          </button>
          {showMenu && (
            <>
              <div className="fixed inset-0 z-40" onClick={() => setShowMenu(false)} />
              <div
                className="absolute right-3 top-full z-50 mt-1 w-44 rounded-xl py-1 shadow-xl"
                style={{ background: 'var(--color-bg-card)', border: '1px solid var(--color-border-default)', }}
              >
                <button
                  onClick={() => { onMarkRead(); setShowMenu(false) }}
                  className="flex w-full items-center gap-2.5 px-3 py-2 text-xs text-muted-foreground hover:text-foreground hover:bg-input transition-colors"
                >
                  {response.is_read ? <EyeOff className="h-3.5 w-3.5" /> : <Eye className="h-3.5 w-3.5" />}
                  {response.is_read ? 'Mark Unread' : 'Mark Read'}
                </button>
                <button
                  onClick={() => { onArchive(); setShowMenu(false) }}
                  className="flex w-full items-center gap-2.5 px-3 py-2 text-xs text-muted-foreground hover:text-foreground hover:bg-input transition-colors"
                >
                  {response.archived_at ? <ArchiveRestore className="h-3.5 w-3.5" /> : <Archive className="h-3.5 w-3.5" />}
                  {response.archived_at ? 'Unarchive' : 'Archive'}
                </button>
                <div className="my-1 border-t" style={{ borderColor: 'var(--color-border-default)' }} />
                <button
                  onClick={() => { onDelete(); setShowMenu(false) }}
                  className="flex w-full items-center gap-2.5 px-3 py-2 text-xs text-rose-400 hover:bg-rose-500/10 transition-colors"
                >
                  <Trash2 className="h-3.5 w-3.5" />
                  Delete
                </button>
              </div>
            </>
          )}
        </td>
      </tr>
      {isExpanded && <ExpandedDetail response={response} />}
    </>
  )
}

export default function SurveyResponsesPage() {
  const [data, setData] = useState<SurveyResponseListResponse | null>(null)
  const [loading, setLoading] = useState(true)
  const [error, setError] = useState<string | null>(null)
  const [expandedId, setExpandedId] = useState<string | null>(null)
  const [exporting, setExporting] = useState(false)
  const [selectedIds, setSelectedIds] = useState<Set<string>>(new Set())
  const [showArchived, setShowArchived] = useState(false)

  const fetchData = useCallback(async () => {
    try {
      const result = await adminApi.listSurveyResponses(showArchived)
      setData(result)
    } catch {
      setError('Failed to load survey responses')
    } finally {
      setLoading(false)
    }
  }, [showArchived])

  useEffect(() => {
    setLoading(true)
    fetchData()
  }, [fetchData])

  const handleExport = async () => {
    setExporting(true)
    try {
      const blob = await adminApi.exportSurveyResponsesCsv()
      const url = URL.createObjectURL(blob)
      const a = document.createElement('a')
      a.href = url
      a.download = 'survey-responses.csv'
      a.click()
      URL.revokeObjectURL(url)
    } catch {
      setError('Export failed')
    } finally {
      setExporting(false)
    }
  }

  const handleMarkRead = async (id: string, currentlyRead: boolean) => {
    try {
      if (currentlyRead) {
        await adminApi.markResponseUnread(id)
      } else {
        await adminApi.markResponseRead(id)
      }
      setData(prev => prev ? {
        ...prev,
        unread: prev.unread + (currentlyRead ? 1 : -1),
        responses: prev.responses.map(r => r.id === id ? { ...r, is_read: !currentlyRead } : r),
      } : prev)
    } catch {
      toast.error('Failed to update read status')
    }
  }

  const handleArchive = async (id: string, currentlyArchived: boolean) => {
    try {
      if (currentlyArchived) {
        await adminApi.unarchiveResponse(id)
        setData(prev => prev ? {
          ...prev,
          responses: prev.responses.map(r => r.id === id ? { ...r, archived_at: null } : r),
        } : prev)
      } else {
        await adminApi.archiveResponse(id)
        if (!showArchived) {
          setData(prev => prev ? {
            ...prev,
            total: prev.total - 1,
            responses: prev.responses.filter(r => r.id !== id),
          } : prev)
        } else {
          setData(prev => prev ? {
            ...prev,
            responses: prev.responses.map(r => r.id === id ? { ...r, archived_at: new Date().toISOString() } : r),
          } : prev)
        }
      }
      toast.success(currentlyArchived ? 'Response unarchived' : 'Response archived')
    } catch {
      toast.error('Failed to update archive status')
    }
  }

  const handleDelete = async (id: string) => {
    if (!confirm('Permanently delete this response? This cannot be undone.')) return
    try {
      await adminApi.deleteResponse(id)
      setData(prev => prev ? {
        ...prev,
        total: prev.total - 1,
        responses: prev.responses.filter(r => r.id !== id),
      } : prev)
      setSelectedIds(prev => { const next = new Set(prev); next.delete(id); return next })
      toast.success('Response deleted')
    } catch {
      toast.error('Failed to delete response')
    }
  }

  const handleBulkAction = async (action: string) => {
    if (selectedIds.size === 0) return
    if (action === 'delete' && !confirm(`Permanently delete ${selectedIds.size} response(s)?`)) return

    try {
      await adminApi.bulkActionResponses(action, Array.from(selectedIds))
      setSelectedIds(new Set())
      fetchData()
      toast.success(`${action.replace('_', ' ')} applied to ${selectedIds.size} response(s)`)
    } catch {
      toast.error('Bulk action failed')
    }
  }

  const toggleSelect = (id: string) => {
    setSelectedIds(prev => {
      const next = new Set(prev)
      if (next.has(id)) next.delete(id)
      else next.add(id)
      return next
    })
  }

  const toggleSelectAll = () => {
    const responses = data?.responses ?? []
    if (selectedIds.size === responses.length) {
      setSelectedIds(new Set())
    } else {
      setSelectedIds(new Set(responses.map(r => r.id)))
    }
  }

  // Auto-mark as read when expanding
  const handleExpand = (id: string) => {
    const newId = expandedId === id ? null : id
    setExpandedId(newId)
    if (newId) {
      const resp = data?.responses.find(r => r.id === newId)
      if (resp && !resp.is_read) {
        handleMarkRead(newId, false)
      }
    }
  }

  if (loading) {
    return (
      <div className="flex items-center justify-center py-20">
        <Loader2 className="h-6 w-6 animate-spin text-primary" />
      </div>
    )
  }

  if (error && !data) {
    return (
      <div className="px-6 py-8">
        <div className="card-flat p-6 text-center text-rose-400">{error}</div>
      </div>
    )
  }

  const responses = data?.responses ?? []

  return (
    <div className="space-y-6 px-6 py-8">
      <PageHeader
        title="Survey Responses"
        description={`${data?.total ?? 0} total responses collected`}
        action={
          <div className="flex items-center gap-2">
            {/* Archive toggle */}
            <button
              onClick={() => setShowArchived(!showArchived)}
              className={cn(
                'inline-flex items-center gap-2 rounded-lg px-3 py-2 text-xs font-medium transition-colors border',
                showArchived
                  ? 'bg-accent-dim text-primary border-primary/20'
                  : 'bg-input text-muted-foreground border-border hover:border-border-hover'
              )}
            >
              <Archive className="h-3.5 w-3.5" />
              {showArchived ? 'Showing Archived' : 'Show Archived'}
            </button>
            <button
              onClick={handleExport}
              disabled={exporting || responses.length === 0}
              className="inline-flex items-center gap-2 rounded-lg bg-input border border-border px-4 py-2 text-sm font-medium text-foreground transition-colors hover:border-border-hover disabled:opacity-50"
            >
              {exporting ? (
                <Loader2 className="h-4 w-4 animate-spin" />
              ) : (
                <Download className="h-4 w-4" />
              )}
              Export CSV
            </button>
          </div>
        }
      />

      {error && (
        <div className="rounded-lg border border-rose-500/20 bg-rose-500/10 px-4 py-2 text-sm text-rose-400">
          {error}
        </div>
      )}

      {/* Stat cards */}
      <div className="flex gap-4">
        <div className="card-flat px-5 py-4 flex-1">
          <p className="font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground mb-1">
            Total Responses
          </p>
          <p className="text-2xl font-heading font-bold text-accent-text">
            {data?.total ?? 0}
          </p>
        </div>
        <div className="card-flat px-5 py-4 flex-1">
          <p className="font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground mb-1">
            This Week
          </p>
          <p className="text-2xl font-heading font-bold text-foreground">
            {data?.this_week ?? 0}
          </p>
        </div>
        <div className="card-flat px-5 py-4 flex-1">
          <p className="font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground mb-1">
            Unread
          </p>
          <p className={cn(
            'text-2xl font-heading font-bold',
            (data?.unread ?? 0) > 0 ? 'text-primary' : 'text-foreground'
          )}>
            {data?.unread ?? 0}
          </p>
        </div>
      </div>

      {/* Bulk actions bar */}
      {selectedIds.size > 0 && (
        <div
          className="flex items-center gap-3 rounded-xl px-4 py-2.5"
          style={{ background: 'rgba(96, 165, 250, 0.08)', border: '1px solid rgba(96, 165, 250, 0.15)' }}
        >
          <span className="text-sm text-primary font-medium">
            {selectedIds.size} selected
          </span>
          <div className="flex-1" />
          <button
            onClick={() => handleBulkAction('mark_read')}
            className="inline-flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium text-muted-foreground hover:text-foreground hover:bg-border transition-colors"
          >
            <Eye className="h-3.5 w-3.5" />
            Mark Read
          </button>
          <button
            onClick={() => handleBulkAction('mark_unread')}
            className="inline-flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium text-muted-foreground hover:text-foreground hover:bg-border transition-colors"
          >
            <EyeOff className="h-3.5 w-3.5" />
            Mark Unread
          </button>
          <button
            onClick={() => handleBulkAction('archive')}
            className="inline-flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium text-muted-foreground hover:text-foreground hover:bg-border transition-colors"
          >
            <Archive className="h-3.5 w-3.5" />
            Archive
          </button>
          <button
            onClick={() => handleBulkAction('delete')}
            className="inline-flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium text-rose-400 hover:bg-rose-500/10 transition-colors"
          >
            <Trash2 className="h-3.5 w-3.5" />
            Delete
          </button>
          <button
            onClick={() => setSelectedIds(new Set())}
            className="px-3 py-1.5 rounded-lg text-xs font-medium text-muted-foreground hover:text-foreground hover:bg-border transition-colors"
          >
            Clear
          </button>
        </div>
      )}

      {/* Table */}
      <div className="card-flat overflow-hidden">
        <table className="w-full">
          <thead>
            <tr className="border-b border-border/50">
              <th className="px-2 py-3 w-8">
                <button onClick={toggleSelectAll} className="text-muted-foreground/40 hover:text-muted-foreground">
                  {selectedIds.size > 0 && selectedIds.size === responses.length ? (
                    <CheckSquare className="h-4 w-4 text-primary" />
                  ) : (
                    <Square className="h-4 w-4" />
                  )}
                </button>
              </th>
              <th className="px-1 py-3 w-6" />
              <th className="px-2 py-3 w-8" />
              <th className="px-4 py-3 text-left font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground">
                #
              </th>
              <th className="px-4 py-3 text-left font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground">
                Respondent
              </th>
              <th className="px-4 py-3 text-left font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground">
                Source
              </th>
              <th className="px-4 py-3 text-left font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground">
                Date
              </th>
              <th className="px-4 py-3 text-left font-sans text-xs text-[0.625rem] uppercase tracking-widest text-muted-foreground">
                Answered
              </th>
              <th className="px-3 py-3 w-10" />
            </tr>
          </thead>
          <tbody>
            {responses.length === 0 ? (
              <tr>
                <td colSpan={9} className="px-4 py-12 text-center text-sm text-muted-foreground">
                  {showArchived ? 'No archived responses.' : 'No survey responses yet.'}
                </td>
              </tr>
            ) : (
              responses.map((response, index) => (
                <ResponseRow
                  key={response.id}
                  response={response}
                  index={index}
                  isExpanded={expandedId === response.id}
                  isSelected={selectedIds.has(response.id)}
                  onToggle={() => handleExpand(response.id)}
                  onSelect={() => toggleSelect(response.id)}
                  onMarkRead={() => handleMarkRead(response.id, response.is_read)}
                  onArchive={() => handleArchive(response.id, !!response.archived_at)}
                  onDelete={() => handleDelete(response.id)}
                />
              ))
            )}
          </tbody>
        </table>
      </div>
    </div>
  )
}
