482796fc52
The loading screen now owns every wait: starter questions, today's starlanguage and the rectification entry summary are fetched in a prepare phase before reveal (4s budget, static fallbacks), the rectification chunk is warmed, recent sessions are prefetched, and no component spinner remains after the page appears. BUG-479. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_0193vBv6w5MV2cifdTUu9H5P
4.6 KiB
4.6 KiB
PROGRESS · 首页加载统一:一次等待、一次揭幕(2026-09-02)
分支:codex/unified-loading-20260902
基线:origin/staging @ 02f06255,并先行合入 codex/streaming-ux-20260901 @ c846c44a(任务书前置条件;合并无冲突,merge commit 25e3094f)。本轮改动写在合并后的代码形态上。
执行方:Claude(用户 2026-09-02 明示"直接开始执行")。
结论
登录后只有一次揭幕。加载屏两阶段(载入账户 → 准备对话),阶段二并行取推荐问题、今日星语、校正入口摘要并预热校正分包;全部就绪或 4 秒到期才揭幕;揭幕后首页无任何组件级 spinner / busy / "正在…"文案(流式生成中除外)。
与任务书的差异
- 当前会话消息:合入的流式分支已把
fetchSessionDetail前移到setHydrated之前(page.tsx启动 effect),本轮不再重复做,只把它计入"阶段二"的语义说明。 - 阶段二实现方式:没有把三个请求搬进启动 effect 的
Promise.allSettled,而是把三个既有 effect 的门槛从hydrated改为bootstrapPhase("account" → "prepare"),再用一个揭幕 effect 汇总就绪状态。理由:三个 effect 各自带重试/身份守卫/缓存逻辑(推荐问题的onboardingRequestIdentity、今日星语的当日缓存与一次重试),原样复用不会产生重复请求,也不必复制这些逻辑。合同测试锁bootstrapPhase === "account" || !accountId门槛恰为 3 处。 - 今日星语的 pending 文案:任务书写"非个性化文案";实际采用与 unavailable 相同的静态句「今天的星语还没写出来。」,到达后静默替换。原「正在写下今天的星语。」删除。
改动清单
| 文件 | 内容 |
|---|---|
src/lib/home-bootstrap.ts(新) |
BootstrapPhase、BOOTSTRAP_PREPARE_TIMEOUT_MS = 4000、SESSION_PREFETCH_COUNT = 5、bootstrapPrepareSettled、bootstrapRevealDelayMs、bootstrapLoadingCopy、sessionIdsToPrefetch |
src/app/page.tsx |
bootstrapPhase / rectificationEntrySummarySettled state、prepareStartedAt ref;finally 里成功路径改 setBootstrapPhase("prepare")(失败仍 setHydrated(true));三个 effect 门槛与依赖改为 bootstrapPhase;入口摘要 effect 加 finally 置 settled;新增揭幕 effect(就绪或超时)、分包预热 effect、揭幕后预取 effect;加载屏文案按阶段;删 starter-loading 分支、dailyStarlanguageBusy、InlineSpinner import 与会话切换 spinner |
src/components/starter-home.tsx |
删 dailyStarlanguageBusy prop 与 aria-busy |
src/app/globals.css |
删两处 .starter-loading 定义(已无使用) |
DESIGN.md §9 |
整页阻塞行改为"两阶段载入";补首页揭幕规则段 |
tests/home-bootstrap-reveal.test.ts(新) |
7 条:纯函数 + 源码合同 |
tests/daily-starlanguage.test.ts |
例外条款:effect 切片标记改为新门槛与新依赖(原值 !hydrated ... / [..., hydrated, ...]);aria-busy={dailyStarlanguageBusy} 正断言改为不存在(原值见注释) |
tests/starter-questions.test.ts |
例外条款:守卫切片终点由 "(onboardingPending ?" 改为 "<StarterHome"(原值见注释) |
docs/BUG_HISTORY.md |
BUG-479 |
onboardingPending 变量保留(滚动 effect 与 productEntrypointsDisabled 仍用),只是不再驱动渲染分支。
验证(本机,无 Docker)
./node_modules/.bin/tsc --noEmit:exit 0。npm run lint:0 error(72 warning,全部既有;本轮改动文件无新增 warning)。npm test:2493 条,pass 2459 / fail 24 / skipped 10;24 条失败清单与551d6317基线逐字相同(数据库/部署类既有环境缺口),无新增。- Python quick-gate 前端契约四文件:24 passed。
next build(默认 Turbopack):exit 0,┌ ○ /Static。- 首屏 JS gzip-9(预渲染
index.html引用的/_next/static/**.js去重后求和):合并点25e3094f基线 513,570 B → 本轮 513,889 B,+319 B / +0.06%(±2% 内)。
未做 / 待用户
- 无登录态:登录后单次揭幕、Slow 3G 下 4 秒兜底揭幕、切换会话零 spinner 均未在浏览器实测,由合同测试覆盖。建议照
docs/testing/staging-manual-walkthrough-20260901.md加一条:DevTools 节流 Slow 3G 刷新首页,加载屏应出现"正在准备对话"文案,最多约 4 秒后一次进入完整界面,进入后无任何转圈。 - 本分支包含
codex/streaming-ux-20260901的合并;合入 staging 时会一并带入该分支(其独立验收见该轮记录)。