import React, { createContext, useContext, useState, useEffect } from 'react'; import { useToast } from '@/components/ui/use-toast'; import { Cell, Post, Comment } from '@/types'; import { mockCells, mockPosts, mockComments } from '@/data/mockData'; import { useAuth } from './AuthContext'; interface ForumContextType { cells: Cell[]; posts: Post[]; comments: Comment[]; loading: boolean; error: string | null; getCellById: (id: string) => Cell | undefined; getPostsByCell: (cellId: string) => Post[]; getCommentsByPost: (postId: string) => Comment[]; createPost: (cellId: string, content: string) => Promise; createComment: (postId: string, content: string) => Promise; votePost: (postId: string, isUpvote: boolean) => Promise; voteComment: (commentId: string, isUpvote: boolean) => Promise; createCell: (title: string, description: string, icon: string) => Promise; } const ForumContext = createContext(undefined); export function ForumProvider({ children }: { children: React.ReactNode }) { const [cells, setCells] = useState([]); const [posts, setPosts] = useState([]); const [comments, setComments] = useState([]); const [loading, setLoading] = useState(true); const [error, setError] = useState(null); const { currentUser, isAuthenticated } = useAuth(); const { toast } = useToast(); useEffect(() => { const loadData = async () => { try { await new Promise(resolve => setTimeout(resolve, 1000)); setCells(mockCells); setPosts(mockPosts); setComments(mockComments); } catch (err) { console.error("Error loading forum data:", err); setError("Failed to load forum data. Please try again later."); } finally { setLoading(false); } }; loadData(); }, []); const getCellById = (id: string): Cell | undefined => { return cells.find(cell => cell.id === id); }; const getPostsByCell = (cellId: string): Post[] => { return posts.filter(post => post.cellId === cellId) .sort((a, b) => b.timestamp - a.timestamp); }; const getCommentsByPost = (postId: string): Comment[] => { return comments.filter(comment => comment.postId === postId) .sort((a, b) => a.timestamp - b.timestamp); }; const createPost = async (cellId: string, content: string): Promise => { if (!isAuthenticated || !currentUser) { toast({ title: "Authentication Required", description: "You need to verify Ordinal ownership to post.", variant: "destructive", }); return null; } try { const newPost: Post = { id: `post-${Date.now()}`, cellId, authorAddress: currentUser.address, content, timestamp: Date.now(), upvotes: [], downvotes: [], }; setPosts(prev => [newPost, ...prev]); toast({ title: "Post Created", description: "Your post has been published successfully.", }); return newPost; } catch (error) { console.error("Error creating post:", error); toast({ title: "Post Failed", description: "Failed to create post. Please try again.", variant: "destructive", }); return null; } }; const createComment = async (postId: string, content: string): Promise => { if (!isAuthenticated || !currentUser) { toast({ title: "Authentication Required", description: "You need to verify Ordinal ownership to comment.", variant: "destructive", }); return null; } try { const newComment: Comment = { id: `comment-${Date.now()}`, postId, authorAddress: currentUser.address, content, timestamp: Date.now(), upvotes: [], downvotes: [], }; setComments(prev => [...prev, newComment]); toast({ title: "Comment Added", description: "Your comment has been published.", }); return newComment; } catch (error) { console.error("Error creating comment:", error); toast({ title: "Comment Failed", description: "Failed to add comment. Please try again.", variant: "destructive", }); return null; } }; const votePost = async (postId: string, isUpvote: boolean): Promise => { if (!isAuthenticated || !currentUser) { toast({ title: "Authentication Required", description: "You need to verify Ordinal ownership to vote.", variant: "destructive", }); return false; } try { setPosts(prev => prev.map(post => { if (post.id === postId) { const userAddress = currentUser.address; const filteredUpvotes = post.upvotes.filter(addr => addr !== userAddress); const filteredDownvotes = post.downvotes.filter(addr => addr !== userAddress); if (isUpvote) { return { ...post, upvotes: [...filteredUpvotes, userAddress], downvotes: filteredDownvotes, }; } else { return { ...post, upvotes: filteredUpvotes, downvotes: [...filteredDownvotes, userAddress], }; } } return post; })); return true; } catch (error) { console.error("Error voting on post:", error); toast({ title: "Vote Failed", description: "Failed to register your vote. Please try again.", variant: "destructive", }); return false; } }; const voteComment = async (commentId: string, isUpvote: boolean): Promise => { if (!isAuthenticated || !currentUser) { toast({ title: "Authentication Required", description: "You need to verify Ordinal ownership to vote.", variant: "destructive", }); return false; } try { setComments(prev => prev.map(comment => { if (comment.id === commentId) { const userAddress = currentUser.address; const filteredUpvotes = comment.upvotes.filter(addr => addr !== userAddress); const filteredDownvotes = comment.downvotes.filter(addr => addr !== userAddress); if (isUpvote) { return { ...comment, upvotes: [...filteredUpvotes, userAddress], downvotes: filteredDownvotes, }; } else { return { ...comment, upvotes: filteredUpvotes, downvotes: [...filteredDownvotes, userAddress], }; } } return comment; })); return true; } catch (error) { console.error("Error voting on comment:", error); toast({ title: "Vote Failed", description: "Failed to register your vote. Please try again.", variant: "destructive", }); return false; } }; const createCell = async (title: string, description: string, icon: string): Promise => { if (!isAuthenticated || !currentUser) { toast({ title: "Authentication Required", description: "You need to verify Ordinal ownership to create a cell.", variant: "destructive", }); return null; } try { const newCell: Cell = { id: `cell-${Date.now()}`, name: title, description, icon, }; setCells(prev => [...prev, newCell]); toast({ title: "Cell Created", description: "Your cell has been created successfully.", }); return newCell; } catch (error) { console.error("Error creating cell:", error); toast({ title: "Creation Failed", description: "Failed to create cell. Please try again.", variant: "destructive", }); return null; } }; return ( {children} ); } export const useForum = () => { const context = useContext(ForumContext); if (context === undefined) { throw new Error("useForum must be used within a ForumProvider"); } return context; };