fix: 修复 Socket 新事件通知后不刷新列表的问题
问题描述: - 用户在第1页时收到新事件 Socket 通知 - 系统调用 handlePageChange(1) 想要刷新列表 - 但列表未刷新,新事件不显示 - 控制台日志显示"⚠️ 重复点击当前页: 1" 根本原因: - usePagination 的 handlePageChange 函数有"重复点击"检查 - 当 newPage === currentPage 时直接 return(第 169-174 行) - Socket 新事件触发刷新时,当前在第1页,调用 handlePageChange(1) - 函数误认为是"用户重复点击分页按钮",阻止了刷新 设计冲突: - 原始设计:防止用户重复点击分页按钮,避免不必要的 API 请求 ✅ - 副作用:阻止了 Socket 新事件触发的强制刷新逻辑 ❌ 修复方案(添加 force 参数): 1. 修改 handlePageChange 函数签名:(newPage, force = false) - force = true: 强制刷新(绕过"重复点击"检查) - force = false: 正常翻页(保留原有检查) 2. 修改边界检查逻辑(第 173-184 行): - 只有在非强制模式下才检查重复点击 - 强制模式下,即使页码相同也继续执行 - 添加日志:🔄 [翻页] 强制刷新当前页 3. 修改 Socket 新事件刷新调用(DynamicNewsCard.js:231): - 修改前:handlePageChange(1) - 修改后:handlePageChange(1, true) // force = true 修改文件: - src/views/Community/components/DynamicNewsCard/hooks/usePagination.js - 第 161 行:修改函数签名(添加 force 参数) - 第 173-184 行:修改边界检查逻辑(添加 force 判断) - src/views/Community/components/DynamicNewsCard.js - 第 230-231 行:修改 handlePageChange 调用(传递 force: true) 修复效果: - ✅ 收到新事件后,第1页强制刷新并显示新事件 - ✅ 保留原有的"重复点击"优化(普通翻页) - ✅ 不影响其他页面的用户体验(第2页及以上不打断) - ✅ 清晰的日志区分: - 🔄 [翻页] 强制刷新当前页: 1(强制刷新) - ⚠️ [翻页] 重复点击当前页: 2(阻止重复点击) 🤖 Generated with Claude Code
This commit is contained in:
@@ -227,8 +227,8 @@ const [currentMode, setCurrentMode] = useState('vertical');
|
|||||||
// ========== 纵向模式 ==========
|
// ========== 纵向模式 ==========
|
||||||
// 只在第1页时刷新,避免打断用户浏览其他页
|
// 只在第1页时刷新,避免打断用户浏览其他页
|
||||||
if (state.currentPage === 1) {
|
if (state.currentPage === 1) {
|
||||||
console.log('[DynamicNewsCard] 纵向模式 + 第1页 → 刷新列表');
|
console.log('[DynamicNewsCard] 纵向模式 + 第1页 → 强制刷新列表');
|
||||||
handlePageChange(1); // 清空缓存并刷新第1页
|
handlePageChange(1, true); // ⚡ 传递 force = true,强制刷新第1页
|
||||||
toast({
|
toast({
|
||||||
title: '检测到新事件',
|
title: '检测到新事件',
|
||||||
status: 'info',
|
status: 'info',
|
||||||
|
|||||||
@@ -158,7 +158,11 @@ export const usePagination = ({
|
|||||||
}, [dispatch, pageSize, toast, mode]); // 移除 filters 依赖,使用 filtersRef 读取最新值
|
}, [dispatch, pageSize, toast, mode]); // 移除 filters 依赖,使用 filtersRef 读取最新值
|
||||||
|
|
||||||
// 翻页处理(第1页强制刷新 + 其他页缓存)
|
// 翻页处理(第1页强制刷新 + 其他页缓存)
|
||||||
const handlePageChange = useCallback(async (newPage) => {
|
const handlePageChange = useCallback(async (newPage, force = false) => {
|
||||||
|
// force 参数:是否强制刷新(绕过"重复点击"检查)
|
||||||
|
// - true: 强制刷新(Socket 新事件触发)
|
||||||
|
// - false: 正常翻页(用户点击分页按钮)
|
||||||
|
|
||||||
// 边界检查 1: 检查页码范围
|
// 边界检查 1: 检查页码范围
|
||||||
if (newPage < 1 || newPage > totalPages) {
|
if (newPage < 1 || newPage > totalPages) {
|
||||||
console.log(`%c⚠️ [翻页] 页码超出范围: ${newPage}`, 'color: #DC2626; font-weight: bold;');
|
console.log(`%c⚠️ [翻页] 页码超出范围: ${newPage}`, 'color: #DC2626; font-weight: bold;');
|
||||||
@@ -166,13 +170,19 @@ export const usePagination = ({
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 边界检查 2: 检查是否重复点击
|
// 边界检查 2: 检查是否重复点击(强制刷新时绕过此检查)
|
||||||
if (newPage === currentPage) {
|
if (!force && newPage === currentPage) {
|
||||||
console.log(`%c⚠️ [翻页] 重复点击当前页: ${newPage}`, 'color: #EAB308; font-weight: bold;');
|
console.log(`%c⚠️ [翻页] 重复点击当前页: ${newPage}`, 'color: #EAB308; font-weight: bold;');
|
||||||
logger.debug('usePagination', '页码未改变', { newPage });
|
logger.debug('usePagination', '页码未改变', { newPage });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ⚡ 如果是强制刷新(force = true),即使页码相同也继续执行
|
||||||
|
if (force && newPage === currentPage) {
|
||||||
|
console.log(`%c🔄 [翻页] 强制刷新当前页: ${newPage}`, 'color: #10B981; font-weight: bold;');
|
||||||
|
logger.info('usePagination', '强制刷新当前页', { newPage });
|
||||||
|
}
|
||||||
|
|
||||||
// 边界检查 3: 防止竞态条件 - 只拦截相同页面的重复请求
|
// 边界检查 3: 防止竞态条件 - 只拦截相同页面的重复请求
|
||||||
if (loadingPage === newPage) {
|
if (loadingPage === newPage) {
|
||||||
console.log(`%c⚠️ [翻页] 第${newPage}页正在加载中,忽略重复请求`, 'color: #EAB308; font-weight: bold;');
|
console.log(`%c⚠️ [翻页] 第${newPage}页正在加载中,忽略重复请求`, 'color: #EAB308; font-weight: bold;');
|
||||||
|
|||||||
Reference in New Issue
Block a user