'use client' import { AlertTriangle, CheckCircle2, Loader2, Upload } from 'lucide-react' import { useMemo, useState } from 'react' import { toast } from 'sonner' import { createCatalogItem } from '@/actions/catalog-items' import { Badge } from '@/components/ui/badge' import { Button } from '@/components/ui/button' import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogTrigger, } from '@/components/ui/dialog' import { Label } from '@/components/ui/label' import { Textarea } from '@/components/ui/textarea' interface ParsedRow { lineNumber: number raw: string ok: boolean error?: string baseId?: number credits?: number points?: number pointsType?: number } interface BulkImportItemsProps { pageId: number onImported?: () => void } export function BulkImportItems({ pageId, onImported }: BulkImportItemsProps) { const [open, setOpen] = useState(false) const [input, setInput] = useState('') const [importing, setImporting] = useState(false) const parsed = useMemo(() => { const lines = input.split('\n') const out: ParsedRow[] = [] lines.forEach((raw, idx) => { const trimmed = raw.trim() if (!trimmed || trimmed.startsWith('#')) return const parts = trimmed.split(/[,\s;]+/).filter(Boolean) const baseId = parseInt(parts[0], 10) if (Number.isNaN(baseId) || baseId <= 0) { out.push({ lineNumber: idx + 1, raw: trimmed, ok: false, error: 'Invalid base ID' }) return } const credits = parts[1] !== undefined ? parseInt(parts[1], 10) : 0 const points = parts[2] !== undefined ? parseInt(parts[2], 10) : 0 const pointsType = parts[3] !== undefined ? parseInt(parts[3], 10) : 0 if ( (parts[1] !== undefined && Number.isNaN(credits)) || (parts[2] !== undefined && Number.isNaN(points)) ) { out.push({ lineNumber: idx + 1, raw: trimmed, ok: false, error: 'Invalid number' }) return } out.push({ lineNumber: idx + 1, raw: trimmed, ok: true, baseId, credits, points, pointsType, }) }) return out }, [input]) const validCount = parsed.filter((r) => r.ok).length const invalidCount = parsed.length - validCount async function handleImport() { const valid = parsed.filter((r) => r.ok) if (valid.length === 0) { toast.error('No valid rows to import') return } setImporting(true) let success = 0 let failed = 0 for (const row of valid) { try { const res = await createCatalogItem({ pageId, itemIds: String(row.baseId!), catalogName: '', costCredits: row.credits ?? 0, costPoints: row.points ?? 0, pointsType: row.pointsType ?? 0, amount: 1, limitedSells: 0, limitedStack: 0, orderNumber: 1, offerId: -1, songId: 0, haveOffer: '1', clubOnly: '0', extradata: '', }) if (res.ok) success++ else failed++ } catch { failed++ } } setImporting(false) if (success > 0) { toast.success(`Imported ${success} item(s)${failed > 0 ? `, ${failed} failed` : ''}.`) setInput('') setOpen(false) onImported?.() } else { toast.error(`All ${failed} imports failed.`) } } return ( Bulk Import Items