'use client'; import { useEffect, useState, useCallback } from 'react'; import { useEnableComments } from '@/hooks/useEnableComments'; interface DoubanComment { id: string; userName: string; userAvatar: string; userUrl: string; rating: number | null; content: string; time: string; votes: number; } interface DoubanCommentsProps { doubanId: number; } // 获取运行时配置的类型 interface RuntimeConfig { EnableComments: boolean; } export default function DoubanComments({ doubanId }: DoubanCommentsProps) { const [comments, setComments] = useState([]); const [loading, setLoading] = useState(false); const [error, setError] = useState(null); const [total, setTotal] = useState(0); const [hasMore, setHasMore] = useState(false); const [hasStartedLoading, setHasStartedLoading] = useState(false); const limit = 20; const enableComments = useEnableComments(); const fetchComments = useCallback(async (startIndex: number) => { try { console.log('正在获取评论,起始位置:', startIndex); setLoading(true); setError(null); const response = await fetch( `/api/douban-comments?id=${doubanId}&start=${startIndex}&limit=${limit}` ); if (!response.ok) { throw new Error('获取评论失败'); } const data = await response.json(); console.log('获取到评论数据:', { newComments: data.comments.length, total: data.total, hasMore: data.hasMore, start: data.start, }); if (startIndex === 0) { setComments(data.comments); } else { setComments((prev) => { console.log('追加评论,之前:', prev.length, '新增:', data.comments.length); return [...prev, ...data.comments]; }); } setTotal(data.total); setHasMore(data.hasMore); console.log('更新后状态 - hasMore:', data.hasMore, 'total:', data.total); } catch (err) { console.error('获取评论失败:', err); setError(err instanceof Error ? err.message : '获取评论失败'); } finally { setLoading(false); } }, [doubanId]); useEffect(() => { // 重置状态当 doubanId 变化时 setHasStartedLoading(false); setComments([]); setLoading(false); setError(null); setTotal(0); setHasMore(false); }, [doubanId]); // 只在 doubanId 变化时重新获取 const startLoading = () => { console.log('开始加载评论'); setHasStartedLoading(true); fetchComments(0); }; const loadMore = () => { console.log('点击加载更多,当前状态:', { loading, hasMore, commentsLength: comments.length, }); if (!loading && hasMore) { // 使用当前已加载的评论数量作为下一页的起始位置 fetchComments(comments.length); } }; // 星级渲染 const renderStars = (rating: number | null) => { if (rating === null) return null; return (
{[1, 2, 3, 4, 5].map((star) => ( ))}
); }; // 如果评论功能被禁用,不显示任何内容 if (!enableComments) { return null; } // 初始状态:显示查看评论按钮 if (!hasStartedLoading) { return (

点击查看豆瓣评论

); } if (loading && comments.length === 0) { return (
加载评论中...
); } if (error && comments.length === 0) { return (

{error}

); } return (
{/* 头部统计 */} {total > 0 && (
{total > comments.length ? `共 ${total} 条短评` : `已加载 ${comments.length} 条短评`}
)} {/* 评论列表 */}
{comments.map((comment) => (
{/* 用户信息 */} {/* 评论内容 */}
{comment.content}
))}
{/* 加载更多按钮 */} {hasMore && (
)} {/* 没有更多了 */} {!hasMore && comments.length > 0 && (
没有更多评论了
)}
); }