import React, { useMemo, useState } from 'react'; import { Button } from '../../components/ui/button'; import { Card, CardContent } from '../../components/ui/card'; import { Input } from '../../components/ui/input'; import { Textarea } from '../../components/ui/textarea'; import { Badge } from '../../components/ui/badge'; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '../../components/ui/select'; import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle } from '../../components/ui/dialog'; import { AlertCircle, Calendar, MessageCircle, Plus, Search, User, X } from 'lucide-react'; import { useCreateThreadMutation, useGetThreadsQuery } from '../../redux/services/forumApi'; import { useToast } from '../../components/toast/useToast'; import DiscussionsView from './DiscussionsView'; const DiscussionsPage: React.FC = () => { const { showToast } = useToast(); const [showNewThreadModal, setShowNewThreadModal] = useState(false); const [searchTerm, setSearchTerm] = useState(''); const [tagsFilter, setTagsFilter] = useState('all'); const [newThreadTitle, setNewThreadTitle] = useState(''); const [newThreadContent, setNewThreadContent] = useState(''); const [tagInput, setTagInput] = useState(''); const [newThreadTags, setNewThreadTags] = useState([]); const [createError, setCreateError] = useState(''); const [selectedThreadId, setSelectedThreadId] = useState(null); const { data: threadsResponse, isLoading: threadsLoading, isFetching: threadsFetching } = useGetThreadsQuery(); const [createThread, { isLoading: isCreatingThread }] = useCreateThreadMutation(); const threads = threadsResponse?.data ?? []; const allTags = useMemo(() => { const set = new Set(); threads.forEach((thread) => { thread.tags.forEach((tag) => set.add(tag)); }); return Array.from(set).sort((a, b) => a.localeCompare(b)); }, [threads]); const filteredThreads = useMemo(() => { return threads.filter((thread) => { const query = searchTerm.trim().toLowerCase(); const matchesSearch = !query || thread.title.toLowerCase().includes(query) || thread.content.toLowerCase().includes(query) || thread.tags.some((tag) => tag.toLowerCase().includes(query)); const matchesTag = tagsFilter === 'all' || thread.tags.includes(tagsFilter); return matchesSearch && matchesTag; }); }, [threads, searchTerm, tagsFilter]); const selectedThread = useMemo( () => threads.find((thread) => thread.id === selectedThreadId) ?? null, [threads, selectedThreadId] ); const getThreadReactionCount = (thread: (typeof threads)[number]) => thread.reactions.reduce((sum, r) => sum + r.count, 0); const formatDate = (date: string) => { const d = new Date(date); return d.toLocaleDateString('en-GB'); }; const resetModal = () => { setNewThreadTitle(''); setNewThreadContent(''); setTagInput(''); setNewThreadTags([]); setCreateError(''); }; const addTag = (rawTag: string) => { const value = rawTag.trim().toLowerCase(); if (!value) return; if (newThreadTags.includes(value)) return; setNewThreadTags((prev) => [...prev, value]); }; const handleTagKeyDown = (e: React.KeyboardEvent) => { if (e.key === 'Enter') { e.preventDefault(); addTag(tagInput); setTagInput(''); } }; const handleCreateThread = async () => { setCreateError(''); if (!newThreadTitle.trim() || !newThreadContent.trim()) { setCreateError('Title and content are required.'); return; } try { const response = await createThread({ title: newThreadTitle.trim(), content: newThreadContent.trim(), tags: newThreadTags, }).unwrap(); showToast('Thread created', response.message || 'Thread created successfully.', 'success'); setShowNewThreadModal(false); resetModal(); } catch (error: any) { const message = error?.data?.message || 'Failed to create thread.'; setCreateError(message); showToast('Create failed', message, 'error'); } }; return (
{selectedThread ? ( setSelectedThreadId(null)} /> ) : ( <>

Discussion Forums

Connect, share, and learn with your cohort members

setSearchTerm(e.target.value)} style={{ paddingLeft: '30px' }} />

Discussions ({filteredThreads.length})

Leadership Development Q4 2024 • 30 members

{(threadsLoading || threadsFetching) && (
Loading threads...
)} {!threadsLoading && filteredThreads.length === 0 && (
No threads found.
)}
{filteredThreads.map((thread) => ( ))}
)} { setShowNewThreadModal(open); if (!open) resetModal(); }} > Start New Discussion Create a new thread for this forum.
{createError && (
{createError}
)}
setNewThreadTitle(e.target.value)} placeholder="What would you like to discuss?" maxLength={150} />