| // import React, { useState, useEffect } from 'react'; |
| // import { Link } from 'wouter'; |
| // import axios from 'axios'; |
| // import { GoodTwo, Comment } from '@icon-park/react'; |
| // import Header from '../../components/Header'; |
| // import './ForumPage.css'; |
| |
| // const API_BASE = process.env.REACT_APP_API_BASE; |
| |
| // const ForumPage = () => { |
| // const [posts, setPosts] = useState([]); |
| // const [total, setTotal] = useState(0); |
| // const [page, setPage] = useState(1); |
| // const [size, setSize] = useState(10); |
| // const [loading, setLoading] = useState(true); |
| // const [errorMsg, setErrorMsg] = useState(''); |
| |
| // const totalPages = Math.ceil(total / size); |
| |
| // useEffect(() => { |
| // const fetchPosts = async () => { |
| // setLoading(true); |
| // setErrorMsg(''); |
| // try { |
| // const response = await axios.get(`${API_BASE}/echo/forum/posts/getAllPost`, { |
| // params: { page, size } |
| // }); |
| // const postsData = response.data.posts || []; |
| |
| // const userIds = [...new Set(postsData.map(post => post.user_id))]; |
| // const userProfiles = await Promise.all( |
| // userIds.map(async id => { |
| // try { |
| // const res = await axios.get(`${API_BASE}/echo/user/profile`, { |
| // params: { user_id: id } |
| // }); |
| // return { id, profile: res.data }; |
| // } catch { |
| // return { id, profile: { nickname: '未知用户', avatar_url: 'default-avatar.png' } }; |
| // } |
| // }) |
| // ); |
| |
| // const userMap = {}; |
| // userProfiles.forEach(({ id, profile }) => { |
| // userMap[id] = profile; |
| // }); |
| |
| // const postsWithProfiles = postsData.map(post => ({ |
| // ...post, |
| // userProfile: userMap[post.user_id] || { nickname: '未知用户', avatar_url: 'default-avatar.png' } |
| // })); |
| |
| // setPosts(postsWithProfiles); |
| // setTotal(response.data.total || 0); |
| // } catch (error) { |
| // console.error('获取帖子失败:', error); |
| // setErrorMsg('加载失败,请稍后重试'); |
| // } finally { |
| // setLoading(false); |
| // } |
| // }; |
| // fetchPosts(); |
| // }, [page, size]); |
| |
| // const toggleLike = async (postId, liked) => { |
| // try { |
| // if (liked) { |
| // await axios.delete(`${API_BASE}/echo/forum/posts/${postId}/unlike`); |
| // } else { |
| // await axios.post(`${API_BASE}/echo/forum/posts/${postId}/like`); |
| // } |
| |
| // setPosts(prevPosts => |
| // prevPosts.map(post => |
| // post.id === postId |
| // ? { |
| // ...post, |
| // liked: !liked, |
| // likeCount: liked ? post.likeCount - 1 : post.likeCount + 1 |
| // } |
| // : post |
| // ) |
| // ); |
| // } catch (error) { |
| // console.error('点赞操作失败:', error); |
| // } |
| // }; |
| |
| // return ( |
| // <div className="forum-page"> |
| // <Header /> {/* 使用 Header 组件 */} |
| // <div className="forum-content"> |
| // <h2>论坛帖子列表</h2> |
| |
| // {loading ? ( |
| // <p>加载中...</p> |
| // ) : errorMsg ? ( |
| // <p className="error-text">{errorMsg}</p> |
| // ) : posts.length === 0 ? ( |
| // <p>暂无帖子。</p> |
| // ) : ( |
| // <div className="post-list"> |
| // {posts.map(post => ( |
| // <div key={post.id} className="post-card"> |
| // <div className="post-card-top"> |
| // <div className="user-info"> |
| // <img className="avatar" src={post.userProfile.avatar_url} alt="头像" /> |
| // <span className="nickname">{post.userProfile.nickname}</span> |
| // </div> |
| // {post.cover_image_url && ( |
| // <img className="cover-image" src={post.cover_image_url} alt="封面" /> |
| // )} |
| // </div> |
| // <h3>{post.title}</h3> |
| // <p className="post-meta"> |
| // 发布时间:{new Date(post.created_at).toLocaleString()} |
| // </p> |
| // <div className="post-actions"> |
| // <button |
| // className="icon-btn" |
| // onClick={() => toggleLike(post.id, post.liked)} |
| // > |
| // <GoodTwo theme="outline" size="24" fill={post.liked ? '#f00' : '#fff'} /> |
| // <span>{post.likeCount || 0}</span> |
| // </button> |
| // <Link href={`/forum/post/${post.id}`} className="icon-btn"> |
| // <Comment theme="outline" size="24" fill="#fff" /> |
| // <span>{post.commentCount || 0}</span> |
| // </Link> |
| // </div> |
| // <Link href={`/forum/post/${post.id}`} className="btn-secondary">查看详情</Link> |
| // </div> |
| // ))} |
| // </div> |
| // )} |
| |
| // <div className="pagination"> |
| // <button disabled={page === 1} onClick={() => setPage(page - 1)}>上一页</button> |
| // <span>第 {page} 页 / 共 {totalPages} 页</span> |
| // <button disabled={page === totalPages} onClick={() => setPage(page + 1)}>下一页</button> |
| // </div> |
| // </div> |
| // </div> |
| // ); |
| // }; |
| |
| // export default ForumPage; |
| |
| import React, { useState } from 'react'; |
| import Header from '../../../components/Header'; |
| import SearchBar from './components/SearchBar'; |
| import CreatePostButton from './components/CreatePostButton'; |
| import PostList from './components/PostList'; |
| import './ForumPage.css'; |
| |
| const ForumPage = () => { |
| const [searchQuery, setSearchQuery] = useState(''); |
| |
| const handleSearch = (query) => { |
| setSearchQuery(query); |
| }; |
| |
| return ( |
| <div className="forum-page"> |
| <Header /> |
| <div className="toolbar"> |
| <SearchBar onSearch={handleSearch} /> |
| <CreatePostButton /> |
| </div> |
| <PostList search={searchQuery} /> |
| </div> |
| ); |
| }; |
| |
| export default ForumPage; |
| |