'use client'; import { useState, useEffect } from 'react'; import Link from 'next/link'; import { HeartIcon, RepeatIcon, MessageIcon, FlagIcon, TrashIcon } from '@/components/Icons'; import { Post } from '@/lib/types'; import { useAuth } from '@/lib/contexts/AuthContext'; interface PostCardProps { post: Post; onLike?: (id: string, currentLiked: boolean) => void; onRepost?: (id: string, currentReposted: boolean) => void; onComment?: (post: Post) => void; onDelete?: (id: string) => void; isDetail?: boolean; } export function PostCard({ post, onLike, onRepost, onComment, onDelete, isDetail }: PostCardProps) { const { user: currentUser } = useAuth(); const [liked, setLiked] = useState(post.isLiked || false); const [reposted, setReposted] = useState(post.isReposted || false); const [reporting, setReporting] = useState(false); const [deleting, setDeleting] = useState(false); // Sync state if post changes (e.g. after a re-render from parent) useEffect(() => { setLiked(post.isLiked || false); setReposted(post.isReposted || false); }, [post.isLiked, post.isReposted, post.id]); const formatTime = (dateStr: string) => { const date = new Date(dateStr); const now = new Date(); const diff = now.getTime() - date.getTime(); const minutes = Math.floor(diff / 60000); const hours = Math.floor(minutes / 60); const days = Math.floor(hours / 24); if (minutes < 1) return 'now'; if (minutes < 60) return `${minutes}m`; if (hours < 24) return `${hours}h`; if (days < 7) return `${days}d`; return date.toLocaleDateString(); }; const handleLike = (e: React.MouseEvent) => { e.preventDefault(); e.stopPropagation(); const currentLiked = liked; setLiked(!currentLiked); onLike?.(post.id, currentLiked); // Pass current state before toggle }; const handleRepost = (e: React.MouseEvent) => { e.preventDefault(); e.stopPropagation(); const currentReposted = reposted; setReposted(!currentReposted); onRepost?.(post.id, currentReposted); // Pass current state before toggle }; const handleComment = (e: React.MouseEvent) => { e.preventDefault(); e.stopPropagation(); onComment?.(post); }; const handleReport = async (e: React.MouseEvent) => { e.preventDefault(); e.stopPropagation(); if (reporting) return; const reason = window.prompt('Why are you reporting this post?'); if (!reason) return; setReporting(true); try { const res = await fetch('/api/reports', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ targetType: 'post', targetId: post.id, reason }), }); if (!res.ok) { if (res.status === 401) { alert('Please log in to report.'); } else { alert('Report failed. Please try again.'); } } else { alert('Report submitted. Thank you.'); } } catch { alert('Report failed. Please try again.'); } finally { setReporting(false); } }; const handleDelete = async (e: React.MouseEvent) => { e.preventDefault(); e.stopPropagation(); if (deleting) return; if (!window.confirm('Are you sure you want to delete this post? This action cannot be undone.')) return; setDeleting(true); try { const res = await fetch(`/api/posts/${post.id}`, { method: 'DELETE', }); if (res.ok) { onDelete?.(post.id); } else { const data = await res.json(); alert(data.error || 'Failed to delete post'); } } catch { alert('Failed to delete post'); } finally { setDeleting(false); } }; const postUrl = `/${post.author.handle}/posts/${post.id}`; return (
e.stopPropagation()}>
{post.author.avatarUrl ? ( {post.author.displayName} ) : ( post.author.displayName?.charAt(0).toUpperCase() || post.author.handle.charAt(0).toUpperCase() )}
e.stopPropagation()}> {post.author.displayName || post.author.handle} @{post.author.handle} ยท {formatTime(post.createdAt)}
{post.replyTo && (
Replied to e.stopPropagation()}>@{post.replyTo.author.handle}
)}
{post.content}
{post.media && post.media.length > 0 && (
{post.media.map((item) => (
{item.altText
))}
)} {post.linkPreviewUrl && ( e.stopPropagation()} > {post.linkPreviewImage && (
{post.linkPreviewTitle
)}
{post.linkPreviewTitle}
{post.linkPreviewDescription && (
{post.linkPreviewDescription}
)}
{new URL(post.linkPreviewUrl.startsWith('http') ? post.linkPreviewUrl : `https://${post.linkPreviewUrl}`).hostname}
)}
{currentUser?.id === post.author.id && ( )}
); }