import React, { useState } from 'react'; import { useTranslation } from 'react-i18next'; import { Link } from 'react-router-dom'; import { Ticket, TicketComment, TicketStatus, TicketPriority, TicketCategory } from '../types'; import { useTickets, useTicketComments, useCreateTicketComment } from '../hooks/useTickets'; import { MessageSquare, Plus, Clock, CheckCircle, AlertCircle, HelpCircle, ChevronRight, Send, User as UserIcon, BookOpen, Code, LifeBuoy } from 'lucide-react'; import TicketModal from '../components/TicketModal'; import { useSandbox } from '../contexts/SandboxContext'; // Status badge component const StatusBadge: React.FC<{ status: TicketStatus }> = ({ status }) => { const { t } = useTranslation(); const statusConfig: Record = { OPEN: { color: 'bg-blue-100 text-blue-800 dark:bg-blue-900/30 dark:text-blue-300', icon: }, IN_PROGRESS: { color: 'bg-yellow-100 text-yellow-800 dark:bg-yellow-900/30 dark:text-yellow-300', icon: }, AWAITING_RESPONSE: { color: 'bg-purple-100 text-purple-800 dark:bg-purple-900/30 dark:text-purple-300', icon: }, RESOLVED: { color: 'bg-green-100 text-green-800 dark:bg-green-900/30 dark:text-green-300', icon: }, CLOSED: { color: 'bg-gray-100 text-gray-800 dark:bg-gray-700 dark:text-gray-300', icon: }, }; const config = statusConfig[status]; return ( {config.icon} {t(`tickets.status.${status.toLowerCase()}`)} ); }; // Priority badge component const PriorityBadge: React.FC<{ priority: TicketPriority }> = ({ priority }) => { const { t } = useTranslation(); const priorityConfig: Record = { LOW: 'bg-gray-100 text-gray-600 dark:bg-gray-700 dark:text-gray-400', MEDIUM: 'bg-blue-100 text-blue-600 dark:bg-blue-900/30 dark:text-blue-400', HIGH: 'bg-orange-100 text-orange-600 dark:bg-orange-900/30 dark:text-orange-400', URGENT: 'bg-red-100 text-red-600 dark:bg-red-900/30 dark:text-red-400', }; return ( {t(`tickets.priorities.${priority.toLowerCase()}`)} ); }; // Ticket detail view (read-only for business users viewing platform tickets) const TicketDetail: React.FC<{ ticket: Ticket; onBack: () => void }> = ({ ticket, onBack }) => { const { t } = useTranslation(); const [replyText, setReplyText] = useState(''); // Fetch comments for this ticket const { data: comments = [], isLoading: isLoadingComments } = useTicketComments(ticket.id); const createCommentMutation = useCreateTicketComment(); // Filter out internal comments (business users shouldn't see platform's internal notes) const visibleComments = comments.filter((comment: TicketComment) => !comment.isInternal); const handleSubmitReply = async (e: React.FormEvent) => { e.preventDefault(); if (!replyText.trim()) return; await createCommentMutation.mutateAsync({ ticketId: ticket.id, commentData: { commentText: replyText.trim(), isInternal: false, // Business replies are never internal }, }); setReplyText(''); }; const isTicketClosed = ticket.status === 'CLOSED'; return (
{/* Header */}

{ticket.subject}

{t('tickets.ticketNumber', 'Ticket #{{number}}', { number: ticket.ticketNumber })} {' • '} {t('tickets.createdAt', 'Created {{date}}', { date: new Date(ticket.createdAt).toLocaleDateString() })}

{/* Description */}

{t('tickets.description')}

{ticket.description}

{/* Status message */}
{ticket.status === 'OPEN' && (

{t('platformSupport.statusOpen', 'Your request has been received. Our support team will review it shortly.')}

)} {ticket.status === 'IN_PROGRESS' && (

{t('platformSupport.statusInProgress', 'Our support team is currently working on your request.')}

)} {ticket.status === 'AWAITING_RESPONSE' && (

{t('platformSupport.statusAwaitingResponse', 'We need additional information from you. Please reply below.')}

)} {ticket.status === 'RESOLVED' && (

{t('platformSupport.statusResolved', 'Your request has been resolved. Thank you for contacting SmoothSchedule support!')}

)} {ticket.status === 'CLOSED' && (

{t('platformSupport.statusClosed', 'This ticket has been closed.')}

)}
{/* Comments / Conversation */}

{t('platformSupport.conversation', 'Conversation')}

{isLoadingComments ? (
{t('common.loading')}
) : visibleComments.length === 0 ? (

{t('platformSupport.noRepliesYet', 'No replies yet. Our support team will respond soon.')}

) : (
{visibleComments.map((comment: TicketComment) => (
{comment.authorFullName || comment.authorEmail}
{new Date(comment.createdAt).toLocaleString()}

{comment.commentText}

))}
)}
{/* Reply Form */} {!isTicketClosed ? (