import { useState } from 'react'
import { AdminTable, type Column } from '../../components/admin/AdminTable'
import { PokemonFormModal } from '../../components/admin/PokemonFormModal'
import { BulkImportModal } from '../../components/admin/BulkImportModal'
import {
  usePokemonList,
  useCreatePokemon,
  useUpdatePokemon,
  useDeletePokemon,
  useBulkImportPokemon,
} from '../../hooks/useAdmin'
import { exportPokemon } from '../../api/admin'
import { downloadJson } from '../../utils/download'
import type { Pokemon, CreatePokemonInput, UpdatePokemonInput } from '../../types'

const PAGE_SIZE = 50

const POKEMON_TYPES = [
  'bug', 'dark', 'dragon', 'electric', 'fairy', 'fighting', 'fire', 'flying',
  'ghost', 'grass', 'ground', 'ice', 'normal', 'poison', 'psychic', 'rock',
  'steel', 'water',
]

export function AdminPokemon() {
  const [search, setSearch] = useState('')
  const [typeFilter, setTypeFilter] = useState('')
  const [page, setPage] = useState(0)
  const offset = page * PAGE_SIZE
  const { data, isLoading } = usePokemonList(search || undefined, PAGE_SIZE, offset, typeFilter || undefined)
  const pokemon = data?.items ?? []
  const total = data?.total ?? 0
  const totalPages = Math.ceil(total / PAGE_SIZE)
  const createPokemon = useCreatePokemon()
  const updatePokemon = useUpdatePokemon()
  const deletePokemon = useDeletePokemon()
  const bulkImport = useBulkImportPokemon()

  const [showCreate, setShowCreate] = useState(false)
  const [showBulkImport, setShowBulkImport] = useState(false)
  const [editing, setEditing] = useState<Pokemon | null>(null)

  const columns: Column<Pokemon>[] = [
    { header: 'Dex #', accessor: (p) => p.nationalDex, className: 'w-16' },
    {
      header: 'Sprite',
      className: 'w-16',
      accessor: (p) =>
        p.spriteUrl ? (
          <img src={p.spriteUrl} alt={p.name} className="w-8 h-8" />
        ) : (
          <div className="w-8 h-8 bg-gray-200 dark:bg-gray-700 rounded" />
        ),
    },
    { header: 'Name', accessor: (p) => p.name },
    { header: 'Types', accessor: (p) => p.types.join(', ') },
  ]

  return (
    <div>
      <div className="flex justify-between items-center mb-4">
        <h2 className="text-xl font-semibold">Pokemon</h2>
        <div className="flex gap-2">
          <button
            onClick={async () => {
              const data = await exportPokemon()
              downloadJson(data, 'pokemon.json')
            }}
            className="px-4 py-2 text-sm font-medium rounded-md border border-gray-300 dark:border-gray-600 text-gray-700 dark:text-gray-300 hover:bg-gray-50 dark:hover:bg-gray-800"
          >
            Export
          </button>
          <button
            onClick={() => setShowBulkImport(true)}
            className="px-4 py-2 text-sm font-medium rounded-md border border-gray-300 dark:border-gray-600 hover:bg-gray-50 dark:hover:bg-gray-700"
          >
            Bulk Import
          </button>
          <button
            onClick={() => setShowCreate(true)}
            className="px-4 py-2 text-sm font-medium rounded-md bg-blue-600 text-white hover:bg-blue-700"
          >
            Add Pokemon
          </button>
        </div>
      </div>

      <div className="mb-4 flex items-center gap-4">
        <input
          type="text"
          value={search}
          onChange={(e) => {
            setSearch(e.target.value)
            setPage(0)
          }}
          placeholder="Search by name..."
          className="w-full max-w-sm px-3 py-2 border rounded-md dark:bg-gray-700 dark:border-gray-600"
        />
        <select
          value={typeFilter}
          onChange={(e) => {
            setTypeFilter(e.target.value)
            setPage(0)
          }}
          className="px-3 py-2 border rounded-md dark:bg-gray-700 dark:border-gray-600"
        >
          <option value="">All types</option>
          {POKEMON_TYPES.map((t) => (
            <option key={t} value={t}>{t.charAt(0).toUpperCase() + t.slice(1)}</option>
          ))}
        </select>
        {(search || typeFilter) && (
          <button
            onClick={() => { setSearch(''); setTypeFilter(''); setPage(0) }}
            className="text-sm text-gray-500 hover:text-gray-700 dark:text-gray-400 dark:hover:text-gray-200"
          >
            Clear filters
          </button>
        )}
        <span className="text-sm text-gray-500 dark:text-gray-400 whitespace-nowrap">
          {total} pokemon
        </span>
      </div>

      <AdminTable
        columns={columns}
        data={pokemon}
        isLoading={isLoading}
        emptyMessage="No pokemon found."
        keyFn={(p) => p.id}
        onRowClick={(p) => setEditing(p)}
      />

      {/* Pagination */}
      {totalPages > 1 && (
        <div className="mt-4 flex items-center justify-between">
          <div className="text-sm text-gray-500 dark:text-gray-400">
            Showing {offset + 1}-{Math.min(offset + PAGE_SIZE, total)} of {total}
          </div>
          <div className="flex items-center gap-2">
            <button
              onClick={() => setPage(0)}
              disabled={page === 0}
              className="px-3 py-1 text-sm rounded border border-gray-300 dark:border-gray-600 disabled:opacity-50 disabled:cursor-not-allowed hover:bg-gray-50 dark:hover:bg-gray-700"
            >
              First
            </button>
            <button
              onClick={() => setPage((p) => Math.max(0, p - 1))}
              disabled={page === 0}
              className="px-3 py-1 text-sm rounded border border-gray-300 dark:border-gray-600 disabled:opacity-50 disabled:cursor-not-allowed hover:bg-gray-50 dark:hover:bg-gray-700"
            >
              Prev
            </button>
            <span className="text-sm text-gray-600 dark:text-gray-300 px-2">
              Page {page + 1} of {totalPages}
            </span>
            <button
              onClick={() => setPage((p) => Math.min(totalPages - 1, p + 1))}
              disabled={page >= totalPages - 1}
              className="px-3 py-1 text-sm rounded border border-gray-300 dark:border-gray-600 disabled:opacity-50 disabled:cursor-not-allowed hover:bg-gray-50 dark:hover:bg-gray-700"
            >
              Next
            </button>
            <button
              onClick={() => setPage(totalPages - 1)}
              disabled={page >= totalPages - 1}
              className="px-3 py-1 text-sm rounded border border-gray-300 dark:border-gray-600 disabled:opacity-50 disabled:cursor-not-allowed hover:bg-gray-50 dark:hover:bg-gray-700"
            >
              Last
            </button>
          </div>
        </div>
      )}

      {showCreate && (
        <PokemonFormModal
          onSubmit={(data) =>
            createPokemon.mutate(data as CreatePokemonInput, {
              onSuccess: () => setShowCreate(false),
            })
          }
          onClose={() => setShowCreate(false)}
          isSubmitting={createPokemon.isPending}
        />
      )}

      {showBulkImport && (
        <BulkImportModal
          title="Bulk Import Pokemon"
          example={`[\n  { "pokeapi_id": 1, "national_dex": 1, "name": "Bulbasaur", "types": ["Grass", "Poison"] }\n]`}
          onSubmit={(items) => bulkImport.mutateAsync(items as Parameters<typeof bulkImport.mutateAsync>[0])}
          onClose={() => setShowBulkImport(false)}
        />
      )}

      {editing && (
        <PokemonFormModal
          pokemon={editing}
          onSubmit={(data) =>
            updatePokemon.mutate(
              { id: editing.id, data: data as UpdatePokemonInput },
              { onSuccess: () => setEditing(null) },
            )
          }
          onClose={() => setEditing(null)}
          isSubmitting={updatePokemon.isPending}
          onDelete={() =>
            deletePokemon.mutate(editing.id, {
              onSuccess: () => setEditing(null),
            })
          }
          isDeleting={deletePokemon.isPending}
        />
      )}
    </div>
  )
}
