fix-postlist
Change-Id: I2b3679ab45b516686f2f204b7a6de89cd1473a48
diff --git a/src/pages/Forum/posts-main/components/PostList.jsx b/src/pages/Forum/posts-main/components/PostList.jsx
index 676ec45..3eba6f8 100644
--- a/src/pages/Forum/posts-main/components/PostList.jsx
+++ b/src/pages/Forum/posts-main/components/PostList.jsx
@@ -1,8 +1,175 @@
+// import React, { useEffect, useState } from 'react';
+// import axios from 'axios';
+// import { Link } from 'wouter';
+// import { GoodTwo, Comment, Star } from '@icon-park/react';
+// import { likePost, unlikePost, collectPost } from '../../posts-detail/api';
+// import './PostList.css';
+
+// const API_BASE = process.env.REACT_APP_API_BASE;
+
+// const PostList = ({ search }) => {
+// const [posts, setPosts] = useState([]);
+// const [page, setPage] = useState(1);
+// const [total, setTotal] = useState(0);
+// const [loading, setLoading] = useState(true);
+// const [errorMsg, setErrorMsg] = useState('');
+
+// const size = 10; // 每页条数
+// const totalPages = Math.ceil(total / size);
+
+// useEffect(() => {
+// const fetchPosts = async () => {
+// setLoading(true);
+// setErrorMsg('');
+// try {
+// const res = await axios.get(`${API_BASE}/echo/forum/posts`, {
+// params: {
+// page: page,
+// pageSize: size,
+// sortBy: 'createdAt', // 按时间排序
+// order: 'desc' // 按降序排序
+// }
+// });
+
+// const postsData = res.data.posts || [];
+// const userIds = [...new Set(postsData.map(p => p.user_id))];
+
+// // 获取用户信息
+// const profiles = await Promise.all(userIds.map(async id => {
+// try {
+// const r = await axios.get(`${API_BASE}/echo/user/profile`, {
+// params: { user_id: id }
+// });
+// return { id, profile: r.data };
+// } catch {
+// return { id, profile: { nickname: '未知用户', avatar_url: 'default-avatar.png' } };
+// }
+// }));
+
+// const userMap = {};
+// profiles.forEach(({ id, profile }) => { userMap[id] = profile; });
+
+// // 更新帖子数据
+// const postsWithProfiles = postsData
+// .filter(post => post.title.includes(search))
+// .map(post => ({
+// ...post,
+// userProfile: userMap[post.user_id] || {}
+// }));
+
+// setPosts(postsWithProfiles);
+// setTotal(res.data.total || 0);
+// } catch (err) {
+// console.error('加载失败:', err);
+// setErrorMsg('加载失败,请稍后重试');
+// } finally {
+// setLoading(false);
+// }
+// };
+
+// fetchPosts();
+// }, [page, search]);
+
+// // 点赞/取消点赞操作
+// const toggleLike = async (postId, liked, userId) => {
+// try {
+// if (liked) {
+// await unlikePost(postId); // 取消点赞
+// } else {
+// await likePost(postId, userId); // 点赞
+// }
+
+// setPosts(posts =>
+// posts.map(post =>
+// post.id === postId
+// ? { ...post, liked: !liked, likeCount: liked ? post.likeCount - 1 : post.likeCount + 1 }
+// : post
+// )
+// );
+// } catch (err) {
+// console.error('点赞失败:', err);
+// }
+// };
+
+// // 收藏/取消收藏操作
+// const toggleCollect = async (postId, collected, userId) => {
+// try {
+// const action = collected ? 'cancel' : 'collect';
+// await collectPost(postId, userId, action);
+
+// setPosts(posts =>
+// posts.map(post =>
+// post.id === postId
+// ? { ...post, collected: !collected, collectCount: collected ? post.collectCount - 1 : post.collectCount + 1 }
+// : post
+// )
+// );
+// } catch (err) {
+// console.error('收藏失败:', err);
+// }
+// };
+
+// return (
+// <div className="post-list">
+// {loading ? <p>加载中...</p> :
+// errorMsg ? <p className="error-text">{errorMsg}</p> :
+// posts.length === 0 ? <p>暂无帖子。</p> :
+// posts.map(post => (
+// <Link
+// key={post.id}
+// href={`/forum/post/${post.id}`}
+// className="post-card"
+// style={{ backgroundColor: '#e9ded2' }}
+// >
+// <div className="user-info">
+// <img className="avatar" src={post.userProfile.avatar_url} alt="头像" />
+// <span className="nickname" style={{ color: '#755e50' }}>{post.userProfile.nickname}</span>
+// </div>
+// {post.cover_image_url && (
+// <img className="cover-image" src={post.cover_image_url} alt="封面" />
+// )}
+// <h3 style={{ color: '#000000' }}>{post.title}</h3>
+// <div className="post-meta">
+// <span>发布时间:{new Date(post.createdAt).toLocaleString()}</span>
+// <div className="post-actions">
+// {/* 点赞按钮 */}
+// <button className="icon-btn" onClick={(e) => { e.stopPropagation(); toggleLike(post.id, post.liked, post.user_id); }}>
+// <GoodTwo theme="outline" size="24" fill={post.liked ? '#f00' : '#fff'} />
+// <span>{post.likeCount}</span>
+// </button>
+
+// {/* 收藏按钮 */}
+// <button className="icon-btn" onClick={(e) => { e.stopPropagation(); toggleCollect(post.id, post.collected, post.user_id); }}>
+// <Star theme="outline" size="24" fill={post.collected ? '#ffd700' : '#fff'} />
+// <span>{post.collectCount}</span>
+// </button>
+
+// <Link href={`/forum/post/${post.id}`} className="icon-btn" onClick={(e) => e.stopPropagation()}>
+// <Comment theme="outline" size="24" fill="#fff" />
+// <span>{post.commentCount}</span>
+// </Link>
+// </div>
+// </div>
+// </Link>
+// ))
+// }
+
+// <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>
+// );
+// };
+
+// export default PostList;
+
import React, { useEffect, useState } from 'react';
import axios from 'axios';
import { Link } from 'wouter';
import { GoodTwo, Comment, Star } from '@icon-park/react';
-import { likePost, unlikePost, collectPost } from '../../posts-detail/api';
+import { likePost, unlikePost, collectPost } from '../../posts-detail/api';
import './PostList.css';
const API_BASE = process.env.REACT_APP_API_BASE;
@@ -14,7 +181,7 @@
const [loading, setLoading] = useState(true);
const [errorMsg, setErrorMsg] = useState('');
- const size = 10; // 每页条数
+ const size = 10;
const totalPages = Math.ceil(total / size);
useEffect(() => {
@@ -22,39 +189,47 @@
setLoading(true);
setErrorMsg('');
try {
- const res = await axios.get(`${API_BASE}/echo/forum/posts`, {
- params: {
- page: page,
+ const res = await axios.get(`${API_BASE}/echo/forum/posts/getAllPosts`, {
+ params: {
+ page,
pageSize: size,
- sortBy: 'createdAt', // 按时间排序
- order: 'desc' // 按降序排序
+ sortBy: 'createdAt',
+ order: 'desc'
}
});
const postsData = res.data.posts || [];
- const userIds = [...new Set(postsData.map(p => p.user_id))];
- // 获取用户信息
+ // 收集所有 user_id
+ const userIds = [...new Set(postsData.map(post => post.user_id))];
+
+ // 批量请求用户资料
const profiles = await Promise.all(userIds.map(async id => {
try {
const r = await axios.get(`${API_BASE}/echo/user/profile`, {
params: { user_id: id }
});
return { id, profile: r.data };
- } catch {
+ } catch (e) {
return { id, profile: { nickname: '未知用户', avatar_url: 'default-avatar.png' } };
}
}));
+ // 创建 user_id -> profile 映射
const userMap = {};
- profiles.forEach(({ id, profile }) => { userMap[id] = profile; });
+ profiles.forEach(({ id, profile }) => {
+ userMap[id] = profile;
+ });
- // 更新帖子数据
+ // 过滤并补充 profile
const postsWithProfiles = postsData
- .filter(post => post.title.includes(search))
+ .filter(post => post.title.toLowerCase().includes(search.toLowerCase()))
.map(post => ({
...post,
- userProfile: userMap[post.user_id] || {}
+ userProfile: userMap[post.user_id] || { nickname: '未知用户', avatar_url: 'default-avatar.png' },
+ liked: false,
+ collected: false,
+ commentCount: 0
}));
setPosts(postsWithProfiles);
@@ -70,18 +245,17 @@
fetchPosts();
}, [page, search]);
- // 点赞/取消点赞操作
const toggleLike = async (postId, liked, userId) => {
try {
if (liked) {
- await unlikePost(postId); // 取消点赞
+ await unlikePost(postId);
} else {
- await likePost(postId, userId); // 点赞
+ await likePost(postId, userId);
}
setPosts(posts =>
posts.map(post =>
- post.id === postId
+ post.postNo === postId
? { ...post, liked: !liked, likeCount: liked ? post.likeCount - 1 : post.likeCount + 1 }
: post
)
@@ -91,7 +265,6 @@
}
};
- // 收藏/取消收藏操作
const toggleCollect = async (postId, collected, userId) => {
try {
const action = collected ? 'cancel' : 'collect';
@@ -99,7 +272,7 @@
setPosts(posts =>
posts.map(post =>
- post.id === postId
+ post.postNo === postId
? { ...post, collected: !collected, collectCount: collected ? post.collectCount - 1 : post.collectCount + 1 }
: post
)
@@ -116,8 +289,8 @@
posts.length === 0 ? <p>暂无帖子。</p> :
posts.map(post => (
<Link
- key={post.id}
- href={`/forum/post/${post.id}`}
+ key={post.postNo}
+ href={`/forum/post/${post.postNo}`}
className="post-card"
style={{ backgroundColor: '#e9ded2' }}
>
@@ -125,26 +298,24 @@
<img className="avatar" src={post.userProfile.avatar_url} alt="头像" />
<span className="nickname" style={{ color: '#755e50' }}>{post.userProfile.nickname}</span>
</div>
- {post.cover_image_url && (
- <img className="cover-image" src={post.cover_image_url} alt="封面" />
+ {post.imgUrl && (
+ <img className="cover-image" src={post.imgUrl} alt="封面" />
)}
<h3 style={{ color: '#000000' }}>{post.title}</h3>
<div className="post-meta">
<span>发布时间:{new Date(post.createdAt).toLocaleString()}</span>
<div className="post-actions">
- {/* 点赞按钮 */}
- <button className="icon-btn" onClick={(e) => { e.stopPropagation(); toggleLike(post.id, post.liked, post.user_id); }}>
+ <button className="icon-btn" onClick={(e) => { e.stopPropagation(); toggleLike(post.postNo, post.liked, post.user_id); }}>
<GoodTwo theme="outline" size="24" fill={post.liked ? '#f00' : '#fff'} />
<span>{post.likeCount}</span>
</button>
-
- {/* 收藏按钮 */}
- <button className="icon-btn" onClick={(e) => { e.stopPropagation(); toggleCollect(post.id, post.collected, post.user_id); }}>
+
+ <button className="icon-btn" onClick={(e) => { e.stopPropagation(); toggleCollect(post.postNo, post.collected, post.user_id); }}>
<Star theme="outline" size="24" fill={post.collected ? '#ffd700' : '#fff'} />
<span>{post.collectCount}</span>
</button>
-
- <Link href={`/forum/post/${post.id}`} className="icon-btn" onClick={(e) => e.stopPropagation()}>
+
+ <Link href={`/forum/post/${post.postNo}`} className="icon-btn" onClick={(e) => e.stopPropagation()}>
<Comment theme="outline" size="24" fill="#fff" />
<span>{post.commentCount}</span>
</Link>
@@ -153,7 +324,7 @@
</Link>
))
}
-
+
<div className="pagination">
<button disabled={page === 1} onClick={() => setPage(page - 1)}>上一页</button>
<span>第 {page} 页 / 共 {totalPages} 页</span>
@@ -163,4 +334,4 @@
);
};
-export default PostList;
\ No newline at end of file
+export default PostList;
diff --git a/src/pages/MyDynamics/MyDynamics.jsx b/src/pages/MyDynamics/MyDynamics.jsx
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/src/pages/MyDynamics/MyDynamics.jsx