fix(usercenter): 刷新 /user/ 不再先闪登录页(引导期一律加载态)

根因:静态导出 SSR 首屏读不到 localStorage(hasRefresh 服务端恒 false),旧守卫
!ready&&hasRefresh() 在此时为 false → 首屏渲染成登录页 → 刷新 /user/ 浏览器先显示
登录页 HTML,再水合+续期跳回面板(闪现);且 render 期调 hasRefresh 造成 SSR/客户端
不一致加剧闪现。

修:引导未完成(!ready)一律显示加载态(不读 localStorage、不渲染登录页),SSR 与
客户端首屏一致;引导完再定:已登录→面板、未登录/失败→登录页。刷新不再闪登录页。

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
wangjia
2026-07-08 14:28:17 +08:00
parent 09b1944376
commit e3e1d43d5d
+7 -5
View File
@@ -124,17 +124,19 @@ export default function UserCenter() {
setView('overview');
}
// 已登录(本地有 refresh token)但会话续期未完成:显示加载态而非登录页,
// 避免"先闪登录页再跳面板"(从官网带登录态进来时的 bug)。续期成功→面板、失败→登录页。
if (!ready && hasRefresh()) {
// 引导(会话续期)未完成前一律显示加载态,不渲染登录页。关键:静态导出下 SSR 首屏
// 读不到 localStorage(hasRefresh 服务端恒 false),若此时渲染登录页 → 刷新 /user/ 会
// "先闪登录页再水合跳回面板"。且在 render 期调 hasRefresh() 会造成 SSR/客户端不一致。
// 故引导期(!ready)只显示加载态(不读 localStorage),引导完再定:已登录→面板、
// 未登录/续期失败→登录页。
if (!ready) {
return (
<div style={{ minHeight: '70vh', display: 'flex', alignItems: 'center', justifyContent: 'center', color: 'var(--fg3)', fontSize: 14 }}>
{t('loading')}
</div>
);
}
// 无 refresh token(未登录)或续期失败:渲染登录页。
if (!ready || !authed) {
if (!authed) {
return <Login onDone={onLoginDone} />;
}