'use client'; import { useState } from 'react'; import { Button } from '@/components/ui/button'; import { Dialog, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle, } from '@/components/ui/dialog'; import { Input } from '@/components/ui/input'; import { Label } from '@/components/ui/label'; import { Alert, AlertDescription } from '@/components/ui/alert'; import { Upload, FileText, Download, AlertCircle } from 'lucide-react'; interface ImportCSVModalProps { isOpen: boolean; onClose: () => void; onImport: (data: any[]) => void; type: 'propositions' | 'participants'; campaignTitle?: string; } export default function ImportCSVModal({ isOpen, onClose, onImport, type, campaignTitle }: ImportCSVModalProps) { const [file, setFile] = useState(null); const [loading, setLoading] = useState(false); const [error, setError] = useState(''); const [preview, setPreview] = useState([]); const handleFileChange = (e: React.ChangeEvent) => { const selectedFile = e.target.files?.[0]; if (selectedFile) { if (selectedFile.type !== 'text/csv' && !selectedFile.name.endsWith('.csv')) { setError('Veuillez sélectionner un fichier CSV valide.'); return; } setFile(selectedFile); setError(''); parseCSV(selectedFile); } }; const parseCSV = (file: File) => { const reader = new FileReader(); reader.onload = (e) => { const text = e.target?.result as string; const lines = text.split('\n').filter(line => line.trim()); if (lines.length < 2) { setError('Le fichier CSV doit contenir au moins un en-tête et une ligne de données.'); return; } const headers = lines[0].split(',').map(h => h.trim().replace(/"/g, '')); const data = lines.slice(1).map(line => { const values = line.split(',').map(v => v.trim().replace(/"/g, '')); const row: any = {}; headers.forEach((header, index) => { row[header] = values[index] || ''; }); return row; }); setPreview(data.slice(0, 5)); // Afficher les 5 premières lignes }; reader.readAsText(file); }; const handleImport = async () => { if (!file) return; setLoading(true); try { const reader = new FileReader(); reader.onload = (e) => { const text = e.target?.result as string; const lines = text.split('\n').filter(line => line.trim()); const headers = lines[0].split(',').map(h => h.trim().replace(/"/g, '')); const data = lines.slice(1).map(line => { const values = line.split(',').map(v => v.trim().replace(/"/g, '')); const row: any = {}; headers.forEach((header, index) => { row[header] = values[index] || ''; }); return row; }); onImport(data); onClose(); setFile(null); setPreview([]); }; reader.readAsText(file); } catch (error) { setError('Erreur lors de l\'import du fichier.'); } finally { setLoading(false); } }; const getExpectedColumns = () => { if (type === 'propositions') { return ['title', 'description', 'author_first_name', 'author_last_name', 'author_email']; } else { return ['first_name', 'last_name', 'email']; } }; const downloadTemplate = () => { const columns = getExpectedColumns(); const csvContent = columns.join(',') + '\n'; const blob = new Blob([csvContent], { type: 'text/csv' }); const url = window.URL.createObjectURL(blob); const a = document.createElement('a'); a.href = url; a.download = `template_${type}.csv`; a.click(); window.URL.revokeObjectURL(url); }; return ( Importer des {type === 'propositions' ? 'propositions' : 'participants'} depuis CSV Importez en masse des {type === 'propositions' ? 'propositions' : 'participants'} depuis un fichier CSV. {campaignTitle && ( Campagne : {campaignTitle} )}
{/* Template download */}
Téléchargez le modèle CSV
{/* Expected columns */}

Colonnes attendues :

{getExpectedColumns().join(', ')}
{/* File upload */}
{/* Error message */} {error && ( {error} )} {/* Preview */} {preview.length > 0 && (
{Object.keys(preview[0] || {}).map((header) => ( ))} {preview.map((row, index) => ( {Object.values(row).map((value, cellIndex) => ( ))} ))}
{header}
{String(value)}
)}
); }