import { ExternalLink, Link2, RefreshCcw, Save, Trash2 } from 'lucide-react'
import { startTransition, useCallback, useEffect, useMemo, useState } from 'react'
import { toast } from 'sonner'

import { FormField } from '@/components/form-field'
import { MediaUrlControls } from '@/components/media-url-controls'
import { Badge } from '@/components/ui/badge'
import { Button } from '@/components/ui/button'
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card'
import { Input } from '@/components/ui/input'
import { Select } from '@/components/ui/select'
import { Skeleton } from '@/components/ui/skeleton'
import { Textarea } from '@/components/ui/textarea'
import { adminApi, ApiError } from '@/lib/api'
import { emptyToNull, formatDateTime, formatFriendLinkStatus } from '@/lib/admin-format'
import type { FriendLinkPayload, FriendLinkRecord } from '@/lib/types'

type FriendLinkFormState = {
  siteName: string
  siteUrl: string
  avatarUrl: string
  description: string
  category: string
  status: string
}

const defaultFriendLinkForm: FriendLinkFormState = {
  siteName: '',
  siteUrl: '',
  avatarUrl: '',
  description: '',
  category: '',
  status: 'pending',
}

function toFormState(link: FriendLinkRecord): FriendLinkFormState {
  return {
    siteName: link.site_name ?? '',
    siteUrl: link.site_url,
    avatarUrl: link.avatar_url ?? '',
    description: link.description ?? '',
    category: link.category ?? '',
    status: link.status ?? 'pending',
  }
}

function toPayload(form: FriendLinkFormState): FriendLinkPayload {
  return {
    siteName: emptyToNull(form.siteName),
    siteUrl: form.siteUrl.trim(),
    avatarUrl: emptyToNull(form.avatarUrl),
    description: emptyToNull(form.description),
    category: emptyToNull(form.category),
    status: emptyToNull(form.status) ?? 'pending',
  }
}

function statusBadgeVariant(status: string | null) {
  switch (status) {
    case 'approved':
      return 'success' as const
    case 'rejected':
      return 'danger' as const
    default:
      return 'warning' as const
  }
}

export function FriendLinksPage() {
  const [links, setLinks] = useState<FriendLinkRecord[]>([])
  const [selectedId, setSelectedId] = useState<number | null>(null)
  const [form, setForm] = useState<FriendLinkFormState>(defaultFriendLinkForm)
  const [loading, setLoading] = useState(true)
  const [refreshing, setRefreshing] = useState(false)
  const [saving, setSaving] = useState(false)
  const [deleting, setDeleting] = useState(false)
  const [searchTerm, setSearchTerm] = useState('')
  const [statusFilter, setStatusFilter] = useState('all')

  const loadLinks = useCallback(async (showToast = false) => {
    try {
      if (showToast) {
        setRefreshing(true)
      }

      const next = await adminApi.listFriendLinks()
      startTransition(() => {
        setLinks(next)
      })

      if (showToast) {
        toast.success('友链列表已刷新。')
      }
    } catch (error) {
      if (error instanceof ApiError && error.status === 401) {
        return
      }
      toast.error(error instanceof ApiError ? error.message : '无法加载友链列表。')
    } finally {
      setLoading(false)
      setRefreshing(false)
    }
  }, [])

  useEffect(() => {
    void loadLinks(false)
  }, [loadLinks])

  const filteredLinks = useMemo(() => {
    return links.filter((link) => {
      const matchesSearch =
        !searchTerm ||
        [
          link.site_name ?? '',
          link.site_url,
          link.category ?? '',
          link.description ?? '',
          link.status ?? '',
        ]
          .join('\n')
          .toLowerCase()
          .includes(searchTerm.toLowerCase())

      const matchesStatus = statusFilter === 'all' || (link.status ?? 'pending') === statusFilter

      return matchesSearch && matchesStatus
    })
  }, [links, searchTerm, statusFilter])

  const selectedLink = useMemo(
    () => links.find((link) => link.id === selectedId) ?? null,
    [links, selectedId],
  )

  return (
    <div className="space-y-6">
      <div className="flex flex-col gap-4 xl:flex-row xl:items-end xl:justify-between">
        <div className="space-y-3">
          <Badge variant="secondary">友链</Badge>
          <div>
            <h2 className="text-3xl font-semibold tracking-tight">友链申请队列</h2>
            <p className="mt-2 max-w-3xl text-sm leading-7 text-muted-foreground">
              审核前台提交的友链申请，维护站点信息，并在待审核、已通过、已拒绝之间完成流转。
            </p>
          </div>
        </div>

        <div className="flex flex-wrap items-center gap-3">
          <Button
            variant="outline"
            onClick={() => {
              setSelectedId(null)
              setForm(defaultFriendLinkForm)
            }}
          >
            新建友链
          </Button>
          <Button variant="secondary" onClick={() => void loadLinks(true)} disabled={refreshing}>
            <RefreshCcw className="h-4 w-4" />
            {refreshing ? '刷新中...' : '刷新'}
          </Button>
        </div>
      </div>

      <div className="grid gap-6 xl:grid-cols-[0.92fr_1.08fr]">
        <Card>
          <CardHeader>
            <CardTitle>友链列表</CardTitle>
            <CardDescription>
              选择一条友链进行编辑，或者直接在右侧创建新记录。
            </CardDescription>
          </CardHeader>
          <CardContent className="space-y-4">
            <div className="grid gap-3 lg:grid-cols-[1.2fr_0.6fr]">
              <Input
                placeholder="按站点名、URL、分类或备注搜索"
                value={searchTerm}
                onChange={(event) => setSearchTerm(event.target.value)}
              />
              <Select
                value={statusFilter}
                onChange={(event) => setStatusFilter(event.target.value)}
              >
                <option value="all">全部状态</option>
                <option value="pending">待审核</option>
                <option value="approved">已通过</option>
                <option value="rejected">已拒绝</option>
              </Select>
            </div>

            {loading ? (
              <Skeleton className="h-[620px] rounded-3xl" />
            ) : (
              <div className="space-y-3">
                {filteredLinks.map((link) => (
                  <button
                    key={link.id}
                    type="button"
                    onClick={() => {
                      setSelectedId(link.id)
                      setForm(toFormState(link))
                    }}
                    className={`w-full rounded-3xl border px-4 py-4 text-left transition ${
                      selectedId === link.id
                        ? 'border-primary/30 bg-primary/10 shadow-[0_12px_30px_rgba(37,99,235,0.12)]'
                        : 'border-border/70 bg-background/60 hover:border-border'
                    }`}
                  >
                    <div className="flex items-start justify-between gap-3">
                      <div className="min-w-0 space-y-1">
                        <div className="flex flex-wrap items-center gap-2">
                          <span className="font-medium">{link.site_name ?? '未命名站点'}</span>
                          <Badge variant={statusBadgeVariant(link.status)}>
                            {formatFriendLinkStatus(link.status)}
                          </Badge>
                        </div>
                        <p className="truncate text-sm text-muted-foreground">{link.site_url}</p>
                        <p className="line-clamp-2 text-sm text-muted-foreground">
                          {link.description ?? '暂无简介。'}
                        </p>
                      </div>
                      <div className="text-right text-xs text-muted-foreground">
                        <p>{link.category ?? '未分类'}</p>
                        <p className="mt-1">{formatDateTime(link.created_at)}</p>
                      </div>
                    </div>
                  </button>
                ))}

                {!filteredLinks.length ? (
                  <div className="flex flex-col items-center gap-3 rounded-3xl border border-dashed border-border/70 px-6 py-14 text-center text-muted-foreground">
                    <Link2 className="h-8 w-8" />
                    <p>当前筛选条件下没有匹配的友链。</p>
                  </div>
                ) : null}
              </div>
            )}
          </CardContent>
        </Card>

        <Card>
          <CardHeader className="flex flex-col gap-4 xl:flex-row xl:items-start xl:justify-between">
            <div>
              <CardTitle>{selectedLink ? '编辑友链' : '新建友链'}</CardTitle>
              <CardDescription>
                维护前台友链页依赖的互链地址、分类和审核状态。
              </CardDescription>
            </div>
            <div className="flex flex-wrap items-center gap-3">
              {selectedLink ? (
                <Button variant="outline" asChild>
                  <a href={selectedLink.site_url} target="_blank" rel="noreferrer">
                    <ExternalLink className="h-4 w-4" />
                    访问站点
                  </a>
                </Button>
              ) : null}
              {selectedLink ? (
                <>
                  <Button
                    variant={form.status === 'approved' ? 'default' : 'outline'}
                    onClick={() => setForm((current) => ({ ...current, status: 'approved' }))}
                  >
                    通过
                  </Button>
                  <Button
                    variant={form.status === 'pending' ? 'secondary' : 'outline'}
                    onClick={() => setForm((current) => ({ ...current, status: 'pending' }))}
                  >
                    待审核
                  </Button>
                  <Button
                    variant={form.status === 'rejected' ? 'danger' : 'outline'}
                    onClick={() => setForm((current) => ({ ...current, status: 'rejected' }))}
                  >
                    拒绝
                  </Button>
                </>
              ) : null}
              <Button
                onClick={async () => {
                  if (!form.siteUrl.trim()) {
                    toast.error('站点 URL 不能为空。')
                    return
                  }

                  try {
                    setSaving(true)
                    const payload = toPayload(form)
                    if (selectedLink) {
                      const updated = await adminApi.updateFriendLink(selectedLink.id, payload)
                      startTransition(() => {
                        setSelectedId(updated.id)
                        setForm(toFormState(updated))
                      })
                      toast.success('友链已更新。')
                    } else {
                      const created = await adminApi.createFriendLink(payload)
                      startTransition(() => {
                        setSelectedId(created.id)
                        setForm(toFormState(created))
                      })
                      toast.success('友链已创建。')
                    }
                    await loadLinks(false)
                  } catch (error) {
                    toast.error(error instanceof ApiError ? error.message : '无法保存友链。')
                  } finally {
                    setSaving(false)
                  }
                }}
                disabled={saving}
              >
                <Save className="h-4 w-4" />
                {saving ? '保存中...' : selectedLink ? '保存修改' : '创建友链'}
              </Button>
              {selectedLink ? (
                <Button
                  variant="danger"
                  disabled={deleting}
                  onClick={async () => {
                    if (!window.confirm('确定删除这条友链吗？')) {
                      return
                    }

                    try {
                      setDeleting(true)
                      await adminApi.deleteFriendLink(selectedLink.id)
                      toast.success('友链已删除。')
                      setSelectedId(null)
                      setForm(defaultFriendLinkForm)
                      await loadLinks(false)
                    } catch (error) {
                      toast.error(error instanceof ApiError ? error.message : '无法删除友链。')
                    } finally {
                      setDeleting(false)
                    }
                  }}
                >
                  <Trash2 className="h-4 w-4" />
                  {deleting ? '删除中...' : '删除'}
                </Button>
              ) : null}
            </div>
          </CardHeader>
          <CardContent className="space-y-5">
            {selectedLink ? (
              <div className="rounded-3xl border border-border/70 bg-background/60 p-5">
                <div className="flex items-center justify-between gap-3">
                  <div>
                    <p className="text-xs uppercase tracking-[0.18em] text-muted-foreground">
                      当前记录
                    </p>
                    <p className="mt-2 text-sm text-muted-foreground">
                      创建于 {formatDateTime(selectedLink.created_at)}
                    </p>
                  </div>
                  <Badge variant={statusBadgeVariant(selectedLink.status)}>
                    {formatFriendLinkStatus(selectedLink.status)}
                  </Badge>
                </div>
              </div>
            ) : null}

            <div className="grid gap-5 lg:grid-cols-2">
              <FormField label="站点名称">
                <Input
                  value={form.siteName}
                  onChange={(event) =>
                    setForm((current) => ({ ...current, siteName: event.target.value }))
                  }
                />
              </FormField>
              <FormField label="站点 URL">
                <Input
                  value={form.siteUrl}
                  onChange={(event) =>
                    setForm((current) => ({ ...current, siteUrl: event.target.value }))
                  }
                />
              </FormField>
              <FormField label="头像 URL" hint="可直接填写外链，也可以上传 / 抓取 / 从媒体库选择后自动回填。">
                <div className="space-y-3">
                  <Input
                    value={form.avatarUrl}
                    onChange={(event) =>
                      setForm((current) => ({ ...current, avatarUrl: event.target.value }))
                    }
                  />
                  <MediaUrlControls
                    value={form.avatarUrl}
                    onChange={(avatarUrl) =>
                      setForm((current) => ({ ...current, avatarUrl }))
                    }
                    prefix="friend-link-avatars/"
                    contextLabel="友链头像上传"
                    remoteTitle={form.siteName || form.siteUrl || '友链头像'}
                    dataTestIdPrefix="friend-link-avatar"
                  />
                </div>
              </FormField>
              <FormField label="分类">
                <Input
                  value={form.category}
                  onChange={(event) =>
                    setForm((current) => ({ ...current, category: event.target.value }))
                  }
                />
              </FormField>
              <div className="lg:col-span-2">
                <FormField label="状态">
                  <div className="grid gap-3 sm:grid-cols-3">
                    <button
                      type="button"
                      onClick={() => setForm((current) => ({ ...current, status: 'pending' }))}
                      className={`rounded-2xl border px-4 py-3 text-left transition ${
                        form.status === 'pending'
                          ? 'border-amber-500/40 bg-amber-500/10 text-amber-700'
                          : 'border-border/70 bg-background/60 hover:border-border'
                      }`}
                    >
                      <div className="font-medium">待审核</div>
                      <p className="mt-1 text-xs text-muted-foreground">保留在队列里继续观察。</p>
                    </button>
                    <button
                      type="button"
                      onClick={() => setForm((current) => ({ ...current, status: 'approved' }))}
                      className={`rounded-2xl border px-4 py-3 text-left transition ${
                        form.status === 'approved'
                          ? 'border-emerald-500/40 bg-emerald-500/10 text-emerald-700'
                          : 'border-border/70 bg-background/60 hover:border-border'
                      }`}
                    >
                      <div className="font-medium">通过</div>
                      <p className="mt-1 text-xs text-muted-foreground">前台会按已通过友链展示。</p>
                    </button>
                    <button
                      type="button"
                      onClick={() => setForm((current) => ({ ...current, status: 'rejected' }))}
                      className={`rounded-2xl border px-4 py-3 text-left transition ${
                        form.status === 'rejected'
                          ? 'border-rose-500/40 bg-rose-500/10 text-rose-700'
                          : 'border-border/70 bg-background/60 hover:border-border'
                      }`}
                    >
                      <div className="font-medium">拒绝</div>
                      <p className="mt-1 text-xs text-muted-foreground">保留记录，但不在前台展示。</p>
                    </button>
                  </div>
                </FormField>
              </div>
              <div className="lg:col-span-2">
                <FormField label="简介">
                  <Textarea
                    value={form.description}
                    onChange={(event) =>
                      setForm((current) => ({ ...current, description: event.target.value }))
                    }
                  />
                </FormField>
              </div>
            </div>
          </CardContent>
        </Card>
      </div>
    </div>
  )
}
