'use client'; import clsx from 'clsx'; import type { UserTicket, Payment } from '@/lib/api'; // One logical status per meaning, mapped to a single pale colour everywhere. // confirmed -> pale green // awaiting -> pale amber (user said they paid, admin checking) // unpaid -> pale red // attended -> pale blue (replaces the raw "checked_in" value) // cancelled -> pale gray // onHold -> pale slate (spot released after the payment deadline passed) export type DashStatus = | 'confirmed' | 'awaiting' | 'unpaid' | 'attended' | 'cancelled' | 'onHold'; /** * Collapse a ticket status + payment status into a single user-facing status. * Never surface raw values like "checked_in" or "pending_approval". */ export function deriveTicketStatus( ticketStatus?: string, paymentStatus?: string ): DashStatus { if (ticketStatus === 'checked_in') return 'attended'; if (ticketStatus === 'cancelled') return 'cancelled'; if (ticketStatus === 'on_hold' || paymentStatus === 'on_hold') return 'onHold'; if (paymentStatus === 'paid' || ticketStatus === 'confirmed') return 'confirmed'; if (paymentStatus === 'pending_approval') return 'awaiting'; return 'unpaid'; } /** Status for a standalone payment record (Payments tab). */ export function derivePaymentStatus(paymentStatus?: string): DashStatus { if (paymentStatus === 'paid') return 'confirmed'; if (paymentStatus === 'pending_approval') return 'awaiting'; if (paymentStatus === 'on_hold') return 'onHold'; if (paymentStatus === 'refunded') return 'cancelled'; return 'unpaid'; } export function statusLabel(status: DashStatus, locale: string): string { const labels: Record = { confirmed: { en: 'Confirmed', es: 'Confirmado' }, awaiting: { en: 'Awaiting approval', es: 'Esperando aprobación' }, unpaid: { en: 'Unpaid', es: 'No pagado' }, attended: { en: 'Attended', es: 'Asistió' }, cancelled: { en: 'Cancelled', es: 'Cancelado' }, onHold: { en: 'On Hold', es: 'En Espera' }, }; return locale === 'es' ? labels[status].es : labels[status].en; } const PILL_STYLES: Record = { confirmed: 'bg-green-100 text-green-800', awaiting: 'bg-amber-100 text-amber-800', unpaid: 'bg-red-100 text-red-700', attended: 'bg-blue-100 text-blue-800', cancelled: 'bg-gray-100 text-gray-600', onHold: 'bg-slate-100 text-slate-600', }; export function StatusPill({ status, locale, className, }: { status: DashStatus; locale: string; className?: string; }) { return ( {statusLabel(status, locale)} ); } /** Convenience: derive + render a pill straight from a ticket. */ export function TicketStatusPill({ ticket, locale, className, }: { ticket: Pick & { payment?: Pick | null }; locale: string; className?: string; }) { const status = deriveTicketStatus(ticket.status, ticket.payment?.status); return ; }