fix(user): 优化用户页面余额积分等数据加载体验

- useRequest 改为 stale-while-revalidate 机制,缓存命中时立即展示数据并后台刷新
- 增加本地存储持久化,冷启动时先展示存储数据,避免骨架屏
- user 页面使用 mutate 结合本地缓存即时更新界面
- 网络请求失败时保留缓存数据,仅清除 loading 状态
- 优化加载逻辑,保障 30 秒缓存内数据可快速响应且自动刷新
This commit is contained in:
2026-07-04 15:34:46 +08:00
parent df5886a62d
commit b07a3525db
3 changed files with 65 additions and 9 deletions

View File

@@ -217,16 +217,21 @@ export function useRequest<T = any, P extends any[] = any[]>(
abortControllerRef.current?.abort()
abortControllerRef.current = new SimpleAbortController()
// 检查缓存
// 检查缓存 - stale-while-revalidate: 立即展示缓存数据,同时后台刷新
let servedFromCache = false
if (cacheKey) {
const cached = getCache<T>(cacheKey)
if (cached !== null) {
setState({ data: cached, loading: false, error: null, initialized: true })
return cached
servedFromCache = true
// 不 return继续发网络请求静默刷新
}
}
setState(prev => ({ ...prev, loading: true, error: null }))
// 无缓存时才显示 loading skeleton
if (!servedFromCache) {
setState(prev => ({ ...prev, loading: true, error: null }))
}
try {
let result!: T
@@ -268,7 +273,12 @@ export function useRequest<T = any, P extends any[] = any[]>(
} catch (err: unknown) {
if (!isMountedRef.current) return
const error = err instanceof Error ? err : new Error(String(err))
setState({ data: null, loading: false, error, initialized: true })
// 有缓存时网络失败不清除数据,仅清除 loading 状态
if (!servedFromCache) {
setState({ data: null, loading: false, error, initialized: true })
} else {
setState(prev => ({ ...prev, loading: false }))
}
onErrorRef.current?.(error, p)
return undefined
}