import { useState, useEffect } from 'react'; import { createClient } from '@supabase/supabase-js'; import { formatCurrency } from '../../lib/event-management'; const supabase = createClient( import.meta.env.PUBLIC_SUPABASE_URL, import.meta.env.PUBLIC_SUPABASE_ANON_KEY ); interface PresaleCode { id: string; code: string; discount_type: 'percentage' | 'fixed'; discount_value: number; max_uses: number; uses_count: number; expires_at: string; is_active: boolean; created_at: string; } interface PresaleTabProps { eventId: string; } export default function PresaleTab({ eventId }: PresaleTabProps) { const [presaleCodes, setPresaleCodes] = useState([]); const [showModal, setShowModal] = useState(false); const [editingCode, setEditingCode] = useState(null); const [formData, setFormData] = useState({ code: '', discount_type: 'percentage' as 'percentage' | 'fixed', discount_value: 10, max_uses: 100, expires_at: '' }); const [loading, setLoading] = useState(true); const [saving, setSaving] = useState(false); useEffect(() => { loadPresaleCodes(); }, [eventId]); const loadPresaleCodes = async () => { setLoading(true); try { const { data, error } = await supabase .from('presale_codes') .select('*') .eq('event_id', eventId) .order('created_at', { ascending: false }); if (error) throw error; setPresaleCodes(data || []); } catch (error) { } finally { setLoading(false); } }; const generateCode = () => { const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'; let result = ''; for (let i = 0; i < 8; i++) { result += chars.charAt(Math.floor(Math.random() * chars.length)); } return result; }; const handleCreateCode = () => { setEditingCode(null); setFormData({ code: generateCode(), discount_type: 'percentage', discount_value: 10, max_uses: 100, expires_at: new Date(Date.now() + 30 * 24 * 60 * 60 * 1000).toISOString().split('T')[0] }); setShowModal(true); }; const handleEditCode = (code: PresaleCode) => { setEditingCode(code); setFormData({ code: code.code, discount_type: code.discount_type, discount_value: code.discount_value, max_uses: code.max_uses, expires_at: code.expires_at.split('T')[0] }); setShowModal(true); }; const handleSaveCode = async () => { setSaving(true); try { const codeData = { ...formData, event_id: eventId, expires_at: new Date(formData.expires_at).toISOString() }; if (editingCode) { const { error } = await supabase .from('presale_codes') .update(codeData) .eq('id', editingCode.id); if (error) throw error; } else { const { error } = await supabase .from('presale_codes') .insert({ ...codeData, is_active: true, uses_count: 0 }); if (error) throw error; } setShowModal(false); loadPresaleCodes(); } catch (error) { } finally { setSaving(false); } }; const handleDeleteCode = async (code: PresaleCode) => { if (confirm(`Are you sure you want to delete the code "${code.code}"?`)) { try { const { error } = await supabase .from('presale_codes') .delete() .eq('id', code.id); if (error) throw error; loadPresaleCodes(); } catch (error) { } } }; const handleToggleCode = async (code: PresaleCode) => { try { const { error } = await supabase .from('presale_codes') .update({ is_active: !code.is_active }) .eq('id', code.id); if (error) throw error; loadPresaleCodes(); } catch (error) { } }; const formatDiscount = (type: string, value: number) => { return type === 'percentage' ? `${value}%` : formatCurrency(value * 100); }; const isExpired = (expiresAt: string) => { return new Date(expiresAt) < new Date(); }; if (loading) { return (
); } return (

Presale Codes

{presaleCodes.length === 0 ? (

No presale codes created yet

) : (
{presaleCodes.map((code) => (
{code.code}
{code.is_active ? 'Active' : 'Inactive'} {isExpired(code.expires_at) && ( Expired )}
{formatDiscount(code.discount_type, code.discount_value)} OFF
Uses
{code.uses_count} / {code.max_uses}
Expires
{new Date(code.expires_at).toLocaleDateString()}
{((code.uses_count / code.max_uses) * 100).toFixed(1)}% used
))}
)} {/* Modal */} {showModal && (

{editingCode ? 'Edit Presale Code' : 'Create Presale Code'}

setFormData(prev => ({ ...prev, code: e.target.value.toUpperCase() }))} className="flex-1 px-4 py-3 bg-white/10 border border-white/20 rounded-l-lg text-white placeholder-white/50 focus:ring-2 focus:ring-blue-500 focus:border-transparent font-mono" placeholder="CODE123" />
setFormData(prev => ({ ...prev, discount_value: parseFloat(e.target.value) || 0 }))} className="w-full px-4 py-3 bg-white/10 border border-white/20 rounded-lg text-white placeholder-white/50 focus:ring-2 focus:ring-blue-500 focus:border-transparent" min="0" step={formData.discount_type === 'percentage' ? "1" : "0.01"} max={formData.discount_type === 'percentage' ? "100" : undefined} />
setFormData(prev => ({ ...prev, max_uses: parseInt(e.target.value) || 0 }))} className="w-full px-4 py-3 bg-white/10 border border-white/20 rounded-lg text-white placeholder-white/50 focus:ring-2 focus:ring-blue-500 focus:border-transparent" min="1" />
setFormData(prev => ({ ...prev, expires_at: e.target.value }))} className="w-full px-4 py-3 bg-white/10 border border-white/20 rounded-lg text-white focus:ring-2 focus:ring-blue-500 focus:border-transparent" />
)}
); }