import { startTransition, useDeferredValue, useEffect, useState } from 'react'
import { z } from 'zod'
import { useForm, useWatch } from 'react-hook-form'
import { zodResolver } from '@hookform/resolvers/zod'
import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query'
import { toast } from 'sonner'
import {
  ArrowLeft,
  ChevronLeft,
  ChevronRight,
  FilterX,
  Loader2,
  PencilLine,
  Plus,
  RefreshCw,
  Search,
  Trash2,
} from 'lucide-react'
import { apiOrigin } from '@/lib/api/client'
import { TableImagePreview } from '@/components/table-image-preview'
import {
  createStory,
  deleteStory,
  fetchStories,
  updateStory,
} from '@/lib/api/stories'
import { uploadImage } from '@/lib/api/upload'
import type { AdminStoryRecord } from '@/lib/api/types'
import { handleServerError } from '@/lib/handle-server-error'
import { getPageNumbers } from '@/lib/utils'
import { Badge } from '@/components/ui/badge'
import { Button } from '@/components/ui/button'
import {
  Card,
  CardContent,
  CardDescription,
  CardHeader,
  CardTitle,
} from '@/components/ui/card'
import {
  Form,
  FormControl,
  FormField,
  FormItem,
  FormLabel,
  FormMessage,
} from '@/components/ui/form'
import { Input } from '@/components/ui/input'
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from '@/components/ui/select'
import { Switch } from '@/components/ui/switch'
import {
  Table,
  TableBody,
  TableCell,
  TableHead,
  TableHeader,
  TableRow,
} from '@/components/ui/table'
import { Textarea } from '@/components/ui/textarea'
import { ImageUploadField } from '@/components/image-upload-field'
import { ConfirmDialog } from '@/components/confirm-dialog'
import { Main } from '@/components/layout/main'
import { StoriesHeader } from './components/stories-header'

const perPage = 15

const storyFormSchema = z.object({
  title: z.string().min(1, 'Başlık zorunludur'),
  badge: z.string().optional().default(''),
  content: z.string().min(1, 'İçerik zorunludur'),
  image: z.string().optional().default(''),
  ctaText: z.string().optional().default(''),
  ctaUrl: z.string().optional().default(''),
  orderIndex: z.coerce.number().default(0),
  isActive: z.boolean().default(true),
})

type StoryFormValues = z.output<typeof storyFormSchema>

function StoryEditorPage({ story, isPending, onCancel, onSubmit }: { story: AdminStoryRecord | null; isPending: boolean; onCancel: () => void; onSubmit: (values: StoryFormValues) => Promise<void> }) {
  const form = useForm<StoryFormValues>({ resolver: zodResolver(storyFormSchema), defaultValues: { title: story?.title ?? '', badge: story?.badge ?? '', content: story?.content ?? '', image: story?.image ?? '', ctaText: story?.ctaText ?? '', ctaUrl: story?.ctaUrl ?? '', orderIndex: story?.orderIndex ?? 0, isActive: story?.isActive ?? true } })

  useEffect(() => { form.reset({ title: story?.title ?? '', badge: story?.badge ?? '', content: story?.content ?? '', image: story?.image ?? '', ctaText: story?.ctaText ?? '', ctaUrl: story?.ctaUrl ?? '', orderIndex: story?.orderIndex ?? 0, isActive: story?.isActive ?? true }); startTransition(() => setSelectedImage({ file: null, previewUrl: null })) }, [story, form])

  const [selectedImage, setSelectedImage] = useState<{ file: File | null; previewUrl: string | null }>({ file: null, previewUrl: null })
  const imageValue = useWatch({ control: form.control, name: 'image' })
  const imageUploadMutation = useMutation({ mutationFn: uploadImage, onError: handleServerError })

  useEffect(() => { return () => { if (selectedImage.previewUrl) URL.revokeObjectURL(selectedImage.previewUrl) } }, [selectedImage.previewUrl])

  const previewUrl = selectedImage.previewUrl ? selectedImage.previewUrl : imageValue ? imageValue.startsWith('http') ? imageValue : `${apiOrigin}/${imageValue.replace(/^\/+/, '')}` : null

  return (
    <Card className='border-border/70 shadow-sm'>
      <CardHeader className='border-b border-border/70 bg-muted/20 px-5 py-4'>
        <div className='flex flex-col gap-3 sm:flex-row sm:items-start sm:justify-between'>
          <div className='space-y-1'><CardTitle>{story ? 'Hikayeyi düzenle' : 'Yeni hikaye oluştur'}</CardTitle><CardDescription>Anasayfa hikaye/tanıtım kartları</CardDescription></div>
          <Button type='button' variant='ghost' size='sm' className='h-8 rounded-lg px-2 text-muted-foreground sm:shrink-0' onClick={onCancel}><ArrowLeft />Listeye dön</Button>
        </div>
      </CardHeader>
      <CardContent className='p-4 md:p-5'>
        <Form {...form}>
          <form onSubmit={form.handleSubmit(async (values) => { let nextImage = values.image ?? ''; if (selectedImage.file) { const result = await imageUploadMutation.mutateAsync(selectedImage.file); nextImage = result.path; form.setValue('image', nextImage) } await onSubmit({ ...values, image: nextImage }); if (selectedImage.file) { toast.success('Görsel ve hikaye kaydedildi.'); setSelectedImage({ file: null, previewUrl: null }) } })} className='space-y-4'>
            <div className='grid gap-4 xl:grid-cols-[300px_minmax(0,1fr)]'>
              <FormField control={form.control} name='image' render={({ field }) => (<FormItem><FormControl><ImageUploadField value={field.value ?? ''} onChange={field.onChange} previewUrl={previewUrl} pendingFileName={selectedImage.file?.name ?? null} isSaving={isPending || imageUploadMutation.isPending} onFileSelect={(file) => { setSelectedImage((cur) => { if (cur.previewUrl) URL.revokeObjectURL(cur.previewUrl); return { file, previewUrl: URL.createObjectURL(file) } }) }} onClearSelection={() => { if (selectedImage.previewUrl) URL.revokeObjectURL(selectedImage.previewUrl); setSelectedImage({ file: null, previewUrl: null }) }} label='Hikaye görseli' /></FormControl></FormItem>)} />
              <div className='space-y-4'>
                <div className='rounded-3xl border border-border/70 bg-card p-4 shadow-sm'>
                  <div className='mb-3 border-b border-border/70 pb-3'><p className='text-sm font-semibold'>Temel bilgiler</p></div>
                  <div className='space-y-3'>
                    <div className='grid gap-3 md:grid-cols-2'>
                      <FormField control={form.control} name='title' render={({ field }) => (<FormItem><FormLabel>Başlık</FormLabel><FormControl><Input {...field} placeholder='Hikaye başlığı' /></FormControl><FormMessage /></FormItem>)} />
                      <FormField control={form.control} name='badge' render={({ field }) => (<FormItem><FormLabel>Etiket (opsiyonel)</FormLabel><FormControl><Input {...field} placeholder='Tanıtım, Yeni Dönem...' /></FormControl></FormItem>)} />
                    </div>
                    <FormField control={form.control} name='content' render={({ field }) => (<FormItem><FormLabel>İçerik</FormLabel><FormControl><Textarea {...field} rows={4} placeholder='Hikaye metni...' /></FormControl><FormMessage /></FormItem>)} />
                  </div>
                </div>
                <div className='rounded-3xl border border-border/70 bg-card p-4 shadow-sm'>
                  <div className='mb-3 border-b border-border/70 pb-3'><p className='text-sm font-semibold'>Buton & Sıralama</p></div>
                  <div className='space-y-3'>
                    <div className='grid gap-3 md:grid-cols-2'>
                      <FormField control={form.control} name='ctaText' render={({ field }) => (<FormItem><FormLabel>Buton metni</FormLabel><FormControl><Input {...field} placeholder='Detaylı Bilgi' /></FormControl></FormItem>)} />
                      <FormField control={form.control} name='ctaUrl' render={({ field }) => (<FormItem><FormLabel>Buton linki</FormLabel><FormControl><Input {...field} placeholder='/kurumsal/hakkimizda' /></FormControl></FormItem>)} />
                    </div>
                    <div className='grid gap-3 md:grid-cols-2'>
                      <FormField control={form.control} name='orderIndex' render={({ field }) => (<FormItem><FormLabel>Sıralama</FormLabel><FormControl><Input {...field} type='number' min={0} /></FormControl></FormItem>)} />
                      <FormField control={form.control} name='isActive' render={({ field }) => (<FormItem className='flex items-center justify-between rounded-2xl border border-border/70 px-4 py-2.5'><div><FormLabel>Aktif</FormLabel><p className='text-xs text-muted-foreground'>Sitede görünsün</p></div><FormControl><Switch checked={field.value} onCheckedChange={field.onChange} /></FormControl></FormItem>)} />
                    </div>
                  </div>
                </div>
              </div>
            </div>
            <div className='flex flex-wrap justify-end gap-3 border-t border-border/70 pt-4'>
              <Button type='button' variant='outline' onClick={onCancel}>Vazgeç</Button>
              <Button type='submit' className='rounded-xl' disabled={isPending}>{isPending && <Loader2 className='animate-spin' />}{story ? 'Kaydet' : 'Oluştur'}</Button>
            </div>
          </form>
        </Form>
      </CardContent>
    </Card>
  )
}

export function StoriesPage() {
  const queryClient = useQueryClient()
  const [page, setPage] = useState(1)
  const [search, setSearch] = useState('')
  const deferredSearch = useDeferredValue(search)
  const [statusFilter, setStatusFilter] = useState('all')
  const [editorOpen, setEditorOpen] = useState(false)
  const [activeStory, setActiveStory] = useState<AdminStoryRecord | null>(null)
  const [storyToDelete, setStoryToDelete] = useState<AdminStoryRecord | null>(null)

  const hasActiveFilters = search !== '' || statusFilter !== 'all'

  const storiesQuery = useQuery({ queryKey: ['stories', page, deferredSearch, statusFilter], queryFn: () => fetchStories({ page, perPage, search: deferredSearch || undefined, is_active: statusFilter === 'all' ? undefined : statusFilter === 'active' }) })

  const upsertMutation = useMutation({
    mutationFn: async (values: StoryFormValues) => {
      const payload = { title: values.title, badge: values.badge || null, content: values.content, image: values.image || null, cta_text: values.ctaText || null, cta_url: values.ctaUrl || null, order_index: values.orderIndex, is_active: values.isActive }
      if (activeStory) return updateStory(activeStory.id, payload)
      return createStory(payload)
    },
    onSuccess: async () => { toast.success(activeStory ? 'Hikaye güncellendi' : 'Hikaye oluşturuldu'); await queryClient.invalidateQueries({ queryKey: ['stories'] }); setEditorOpen(false); setActiveStory(null) },
    onError: handleServerError,
  })

  const deleteMutation = useMutation({
    mutationFn: async (id: number | string) => deleteStory(id),
    onSuccess: async () => { toast.success('Hikaye silindi'); await queryClient.invalidateQueries({ queryKey: ['stories'] }); setStoryToDelete(null) },
    onError: handleServerError,
  })

  const pageNumbers = getPageNumbers(page, storiesQuery.data?.meta.lastPage ?? 1)

  return (
    <>
      <StoriesHeader />
      <Main className='space-y-6'>
        {editorOpen ? (
          <StoryEditorPage story={activeStory} isPending={upsertMutation.isPending} onCancel={() => { setEditorOpen(false); setActiveStory(null) }} onSubmit={async (values) => { await upsertMutation.mutateAsync(values) }} />
        ) : (
          <Card>
            <CardHeader className='gap-4'>
              <div className='flex flex-col gap-4 xl:flex-row xl:items-start xl:justify-between'>
                <div><CardTitle>Hikayeler</CardTitle><CardDescription>Anasayfa hikaye/tanıtım kartları</CardDescription></div>
                <div className='flex flex-wrap gap-2'>
                  <Button variant='outline' className='rounded-xl' onClick={() => storiesQuery.refetch()}><RefreshCw className={storiesQuery.isFetching ? 'animate-spin' : ''} />Yenile</Button>
                  <Button className='rounded-xl' onClick={() => { setActiveStory(null); setEditorOpen(true) }}><Plus />Ekle</Button>
                </div>
              </div>
              <div className='rounded-2xl border border-dashed border-border/70 bg-muted/20 p-4 space-y-3'>
                <div className='relative'><Search className='pointer-events-none absolute top-1/2 left-3 size-4 -translate-y-1/2 text-muted-foreground' /><Input placeholder='Hikaye ara...' className='pl-9' value={search} onChange={(e) => { setSearch(e.target.value); setPage(1) }} /></div>
                <div className='grid gap-3 grid-cols-[1fr_auto]'>
                  <Select value={statusFilter} onValueChange={(v) => startTransition(() => { setStatusFilter(v); setPage(1) })}><SelectTrigger><SelectValue placeholder='Durum' /></SelectTrigger><SelectContent><SelectItem value='all'>Tümü</SelectItem><SelectItem value='active'>Aktif</SelectItem><SelectItem value='inactive'>Pasif</SelectItem></SelectContent></Select>
                  {hasActiveFilters && (<Button variant='outline' className='rounded-xl' onClick={() => { setSearch(''); setStatusFilter('all'); setPage(1) }}><FilterX />Temizle</Button>)}
                </div>
              </div>
            </CardHeader>
            <CardContent className='space-y-4'>
              <div className='rounded-2xl border border-border/70'>
                <Table>
                  <TableHeader><TableRow><TableHead className='w-16 px-4'>Görsel</TableHead><TableHead>Başlık</TableHead><TableHead>Etiket</TableHead><TableHead>Buton</TableHead><TableHead className='w-16'>Sıra</TableHead><TableHead className='w-16'>Durum</TableHead><TableHead className='w-40 text-right'>İşlemler</TableHead></TableRow></TableHeader>
                  <TableBody>
                    {storiesQuery.isLoading ? (
                      <TableRow><TableCell colSpan={7} className='h-28 text-center text-muted-foreground'><Loader2 className='mx-auto mb-2 size-5 animate-spin' />Yükleniyor...</TableCell></TableRow>
                    ) : storiesQuery.data?.items.length ? (
                      storiesQuery.data.items.map((story) => (
                        <TableRow key={story.id}>
                          <TableCell className='px-4'>
                            <TableImagePreview src={story.image} alt={story.title} />
                          </TableCell>
                          <TableCell className='py-3 font-medium'>{story.title}</TableCell>
                          <TableCell>{story.badge ? (<Badge variant='outline' className='rounded-full'>{story.badge}</Badge>) : '\u2014'}</TableCell>
                          <TableCell className='text-sm text-muted-foreground'>{story.ctaText || '\u2014'}</TableCell>
                          <TableCell className='text-center text-sm tabular-nums'>{story.orderIndex}</TableCell>
                          <TableCell><Badge variant={story.isActive ? 'default' : 'secondary'} className='rounded-full'>{story.isActive ? 'Aktif' : 'Pasif'}</Badge></TableCell>
                          <TableCell>
                            <div className='flex justify-end gap-2'>
                              <Button variant='outline' size='sm' className='rounded-xl' onClick={() => { setActiveStory(story); setEditorOpen(true) }}><PencilLine />Düzenle</Button>
                              <Button variant='destructive' size='sm' className='rounded-xl' onClick={() => setStoryToDelete(story)}><Trash2 /></Button>
                            </div>
                          </TableCell>
                        </TableRow>
                      ))
                    ) : (
                      <TableRow><TableCell colSpan={7} className='h-28 text-center text-muted-foreground'>Hikaye bulunamadı.</TableCell></TableRow>
                    )}
                  </TableBody>
                </Table>
              </div>
              <div className='flex flex-col gap-4 sm:flex-row sm:items-center sm:justify-between'>
                <p className='text-sm text-muted-foreground'>Toplam {storiesQuery.data?.meta.total ?? 0} kayıt. Sayfa {page} / {storiesQuery.data?.meta.lastPage ?? 1}</p>
                <div className='flex flex-wrap items-center gap-2'>
                  <Button variant='outline' size='sm' onClick={() => startTransition(() => setPage((c) => Math.max(1, c - 1)))} disabled={page === 1}><ChevronLeft /></Button>
                  {pageNumbers.map((item, index) => item === '...' ? (<span key={`${item}-${index}`} className='px-2 text-sm text-muted-foreground'>...</span>) : (<Button key={item} size='sm' variant={item === page ? 'default' : 'outline'} onClick={() => startTransition(() => setPage(Number(item)))}>{item}</Button>))}
                  <Button variant='outline' size='sm' onClick={() => startTransition(() => setPage((c) => Math.min(storiesQuery.data?.meta.lastPage ?? 1, c + 1)))} disabled={page === (storiesQuery.data?.meta.lastPage ?? 1)}><ChevronRight /></Button>
                </div>
              </div>
            </CardContent>
          </Card>
        )}
      </Main>
      <ConfirmDialog open={!!storyToDelete} onOpenChange={(open) => { if (!open) setStoryToDelete(null) }} title='Hikayeyi silmek istediğinize emin misiniz?' desc={`"${storyToDelete?.title ?? ''}" kalıcı olarak silinecek.`} confirmText='Evet, sil' cancelBtnText='İptal' destructive isLoading={deleteMutation.isPending} handleConfirm={() => { if (storyToDelete) deleteMutation.mutate(storyToDelete.id) }} />
    </>
  )
}
