docs+fix(home): amend resumable hint to point at history (brief amendment)

- D2 resumable hint becomes「上次那次校正还没完成,可以在历史对话里接着做。」
  so it does not imply the homepage pill resumes (it always creates).
- The click-time non-self error in useRectificationSurface is the same
  user-visible sentence as the homepage hint; add the full stop.
- Source, test, VOICE, DESIGN, CHANGELOG, BUG-1041, testing list and
  PROGRESS (amendment by Claude) updated.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017eEAG8HD3mm8gsKXgk8uU8
This commit is contained in:
Jesse_Chen
2026-09-26 08:50:18 +08:00
co-authored by Claude Opus 5.5
parent b5a02ca861
commit f04da1038b
9 changed files with 16 additions and 12 deletions
+1 -1
View File
@@ -3,7 +3,7 @@
## 2026-09-26 — 首页开场小字拆开,今日星语和点数换图标(待验收)
- 今日趋势(今日星语卡片那一句,每天生成)挪到问候语下面单独一行,浅色、最多两行;还没生成时写「今天的星语还没写出来。」,没有出生分钟时不显示。
- 入口按钮下面平时不再有字,只在需要动手时出一句:有没做完的校正写「上次那次校正还没完成,可以接着做。」;当前人物不是本人写「生时校正暂时只支持本人。」。删掉「不确定出生时间时…」「上次已经校正完…」两句。
- 入口按钮下面平时不再有字,只在需要动手时出一句:有没做完的校正写「上次那次校正还没完成,可以在历史对话里接着做。」;当前人物不是本人写「生时校正暂时只支持本人。」。删掉「不确定出生时间时…」「上次已经校正完…」两句。
- 修好已校正过的账户仍被当成第一次的问题(BUG-1041):首页读校正状态时一直读错字段名,所以从没出现过「再次校正」和未完成提示。
- 今日星语入口图标换成带星的月亮,右上角点数换成硬币,两处不再是同一个图标;读屏名称不变。
- Skill 版本不 bump。不改接口、今日星语生成逻辑和数据库;登录态真机与部署待验收。
+1 -1
View File
@@ -13938,7 +13938,7 @@
- 触发条件:任何有未完成或已完成校正 Case 的账户打开首页。
- 根因:`GET /api/rectification/cases/entry-summary` 返回 `getRectificationEntrySummary` 投影后的 **camelCase** 对象(`hasResumableCase` / `hasTerminalCaseWithTime` / `latestTerminal.caseId`…),只有底下的 RPC 行是 snake_case;而浏览器端 `entrySummaryFromResponse` 只读 snake_case 键(`has_resumable_case` 等),所以每一个真实响应都被解析成「什么都没有」。`resolveRectificationEntryAction` 恒为 `start`,`rectificationCardAction === "restart"` 与 `hasResumableCase` 分支从未命中。自 2026-08-11 `ca748466`(BUG-163 入口改造)起存在。测试没拦住:`rectification-v9-entry-routing.test.ts`、`home-warm-return-lifecycle.test.tsx`、`new-chat-from-people-lifecycle.test.tsx` 的 entry-summary mock 都是手写的 snake_case,不是路由真实输出;`rectification-v9-case-service.test.ts` 只测到服务端投影为止,两段之间没有往返合同。
- 修复:`entrySummaryFromResponse` 以路由真实的 camelCase 形状为准,同时仍读 snake_case(RPC 形状不会再静默塌成空)。首页小字按 TASK-starter-home-polish-20260926 D2 改为只读 summary 的 `hasResumableCase` 与当前人物,不再依赖派生的 `restart`。
- 验证:`frontend/tests/starter-home-polish-20260926.test.tsx`「BUG-1041: the homepage parser reads what the entry-summary route actually returns」:用 `getRectificationEntrySummary`(假 RPC)产出、`JSON` 往返后交给 `entrySummaryFromResponse`,断言 `hasTerminalCaseWithTime`、`latestTerminal`、`restart` 与未完成提示;修复前该条失败(解析结果全 false)。本地 `next start` + Chrome 151,`/api/*` 以 camelCase 形状回放:已校正账户可访问名「再次校正」、无小字;未完成账户显示「上次那次校正还没完成,可以接着做。」。全量 3960 条 / 61 失败,失败名单与基线逐条一致。
- 验证:`frontend/tests/starter-home-polish-20260926.test.tsx`「BUG-1041: the homepage parser reads what the entry-summary route actually returns」:用 `getRectificationEntrySummary`(假 RPC)产出、`JSON` 往返后交给 `entrySummaryFromResponse`,断言 `hasTerminalCaseWithTime`、`latestTerminal`、`restart` 与未完成提示;修复前该条失败(解析结果全 false)。本地 `next start` + Chrome 151,`/api/*` 以 camelCase 形状回放:已校正账户可访问名「再次校正」、无小字;未完成账户显示「上次那次校正还没完成,可以在历史对话里接着做。」。全量 3960 条 / 61 失败,失败名单与基线逐条一致。
- 防复发:往返合同测试锁住「路由输出 → 首页解析」一段;新的首页测试 fixture 用路由真实的 camelCase 形状。旧的 snake_case mock 仍能被解析,未改动。
- 相关记录:BUG-163(入口摘要由服务端 Case 驱动)、BUG-1040(暖快照缓存的正是解析后的 summary,快照结构不变)。
- 复发自:无。
@@ -14,7 +14,7 @@
| 任务 | 文件 | 内容 |
| --- | --- | --- |
| T1 / D1 | `components/starter-home.tsx`、`app/(app)/page.tsx`、`globals.css` | `StarterGreeting` 加可选 `dailyTrend` / `dailyTrendSettled`,渲染 `.starter-greeting-sub`(`--color-ink-secondary`、`--type-body-sm`、两行截断)。`page.tsx` 传 `natalMinuteAvailable ? dailyStarlanguageTrend : null`,读的就是 BUG-1040 暖快照初始化的同一个 `dailyStarlanguage` state;未就绪沿用静态句「今天的星语还没写出来。」+ `role="status"`,无 `aria-busy`、无新等待态。 |
| T2 / D2 | `components/starter-home.tsx` | 新增纯函数 `rectificationEntryHint(forSelf, summary)`:非本人 →「生时校正暂时只支持本人。」;`summary.hasResumableCase` →「上次那次校正还没完成,可以接着做。」;其余 `null`,不渲染 `<p>`。删「不确定出生时间时…」「上次已经校正完…」「未完成的那次可以从左侧继续」「看看今天的整体节奏」四句与「·」拼接。`StarterEntries` 去掉不再用的 `dailyStarlanguage` / `dailyStarlanguageTrend` / `rectificationCardAction` 三个 prop。 |
| T2 / D2 | `components/starter-home.tsx` | 新增纯函数 `rectificationEntryHint(forSelf, summary)`:非本人 →「生时校正暂时只支持本人。」;`summary.hasResumableCase` →「上次那次校正还没完成,可以在历史对话里接着做。」(任务书修订后文案,见下);其余 `null`,不渲染 `<p>`。删「不确定出生时间时…」「上次已经校正完…」「未完成的那次可以从左侧继续」「看看今天的整体节奏」四句与「·」拼接。`StarterEntries` 去掉不再用的 `dailyStarlanguage` / `dailyStarlanguageTrend` / `rectificationCardAction` 三个 prop。 |
| T2 / 分支误判 | `lib/rectification-entry.ts` | **真 bug(BUG-1041)**:`/api/rectification/cases/entry-summary` 返回 camelCase(`getRectificationEntrySummary` 的投影),`entrySummaryFromResponse` 只读 snake_case,每个真实响应都解析成全 false。改为优先读 camelCase、仍兼容 snake_case。结果:已校正账户可访问名变回「再次校正」,未完成提示能出现。 |
| T2 / D4 | — | 边界句「出生时间不足以支持的判断我会说明,不会补造具体分钟。」原位保留。 |
| T3 / D3 | `components/starter-home.tsx`、`app/(app)/page.tsx` | 今日星语入口 `Sparkles` → `MoonStar`;右上角点数 `Sparkles` → `Coins`(`className="credit-icon"`、`aria-hidden`、按钮 `aria-label` 不变)。已确认 lucide-react 1.24.0 同时导出 `MoonStar`、`Coins`。 |
@@ -49,7 +49,7 @@
| 场景 | 副行 | 入口下方 | 其他 |
| --- | --- | --- | --- |
| 375 / 1280 × 明 / 暗,已校正账户 | 趋势句两行,明 `rgb(95,95,89)` / 暗 `rgb(179,175,164)`,14px | 无 | 生时校正可访问名「再次校正」;图标 moon-star / coins;无横向溢出 |
| 375 明,未完成校正 | 趋势句 | 「上次那次校正还没完成,可以接着做。」 | 可访问名「开始新的生时校正」 |
| 375 明,未完成校正 | 趋势句 | 「上次那次校正还没完成,可以接着做。」(截图为修订前文案) | 可访问名「开始新的生时校正」 |
| 375 明,首次 | 趋势句 | 无 | — |
| 1280 明,今日星语 unavailable | 「今天的星语还没写出来。」`role="status"` | 无 | — |
| 375 明,无出生分钟 | 不渲染 | 仅边界句 | 入口「查看今日运势」 |
@@ -65,5 +65,9 @@
## 观察(未处理,留给产品 / Claude 定夺)
- 首页「生时校正」按钮走 `intent=homepage`,服务端总是**新建** Case;未完成的那次要从侧栏继续。产品指定的新文案「上次那次校正还没完成,可以接着做。」没有说「从左侧」,用户可能以为点按钮就会接着做。按任务书原文实现,未改。
- `useRectificationSurface.rectificationLimitedToSelf` 点击时的错误文案仍是无句号的「生时校正暂时只支持本人」(非本人时按钮已禁用,正常点不到),不在本单范围。
- ~~首页「生时校正」按钮走 `intent=homepage`,服务端总是新建 Case;未完成的那次要从侧栏继续,原文案「上次那次校正还没完成,可以接着做。」可能让用户以为点按钮就会接着做。~~ 已处理,见「任务书修订」。
## 任务书修订(Claude,2026-09-26)
- 任务书作者(Claude)采纳上面的观察,修订 D2 未完成提示为「上次那次校正还没完成,可以在历史对话里接着做。」:「历史对话」对桌面侧栏和手机抽屉都成立,不说「左侧」。源码、`starter-home-polish-20260926.test.tsx`、VOICE、DESIGN、CHANGELOG、BUG-1041、真机清单同步改。仓库内截图 `starter-375-light-resumable.png` 仍是修订前文案,未重拍。
- 同一修订:`useRectificationSurface.rectificationLimitedToSelf` 点击时的错误文案与首页非本人提示是同一句用户可见文案(经 `rectificationErrorMessage` 显示在入口下方的 `form-error`),补句号为「生时校正暂时只支持本人。」。无测试断言该字符串。
+1 -1
View File
@@ -3,7 +3,7 @@
本轮在本地 `next start` + 无头 Chrome 里用虚构接口数据截过图(`starter-home-polish-20260926/`),没有登录态真机。下面留给真人,用自己的账户在 staging 上照做:
1. 打开首页:问候语下面一行浅色小字是今天的趋势句,最多两行;入口按钮(今日星语、生时校正)下面没有字。
2. 如果你有一次没做完的生时校正:入口按钮下面只有一句「上次那次校正还没完成,可以接着做。」。
2. 如果你有一次没做完的生时校正:入口按钮下面只有一句「上次那次校正还没完成,可以在历史对话里接着做。」。
3. 如果你已经校正完、没有没做完的:按钮下面没有字;用读屏(VoiceOver)读生时校正按钮,应读「再次校正」。
4. 在星盘档案里切到另一个人再回首页:按钮下面只有「生时校正暂时只支持本人。」,生时校正按钮是灰的。
5. 今日星语按钮是带星的月亮图标,右上角点数是硬币图标,两处不一样。
+1 -1
View File
@@ -602,7 +602,7 @@ page. Three parts now, in reading order:
visible branches and reads the entry summary itself, never the session list
and never the derived start/restart label: a non-self current person →
「生时校正暂时只支持本人。」; otherwise `hasResumableCase` →
「上次那次校正还没完成,可以接着做。」. First runs and finished cases show no
「上次那次校正还没完成,可以在历史对话里接着做。」. First runs and finished cases show no
hint. The old first-run and "redo" sentences are gone. (The summary parser had
been reading the wrong key casing since 2026-08-11, so every account looked
like a first run — BUG-1041.)
+1 -1
View File
@@ -18,7 +18,7 @@ Jyotisha 的可见文案是产品的一部分。正确性红线(真实性、
首页开场语只有一行,不带追问句,不用星星、月亮、陪伴一类比喻。
首页开场语下面可以有一行今日趋势(今日星语卡片的 trend,每日生成);还没生成时写「今天的星语还没写出来。」,没有出生分钟时不写。入口按钮下面平时不写字,只在用户需要动手时写一句:有没做完的校正写「上次那次校正还没完成,可以接着做。」;当前人物不是本人写「生时校正暂时只支持本人。」。不再写「不确定出生时间时,用记得住的经历一步步缩小范围」「上次已经校正完,可以拿最新资料再来一次」,也不要用「·」把两句不相干的提示拼成一行。
首页开场语下面可以有一行今日趋势(今日星语卡片的 trend,每日生成);还没生成时写「今天的星语还没写出来。」,没有出生分钟时不写。入口按钮下面平时不写字,只在用户需要动手时写一句:有没做完的校正写「上次那次校正还没完成,可以在历史对话里接着做。」;当前人物不是本人写「生时校正暂时只支持本人。」。不再写「不确定出生时间时,用记得住的经历一步步缩小范围」「上次已经校正完,可以拿最新资料再来一次」,也不要用「·」把两句不相干的提示拼成一行。
## 星盘空状态、0 年大运、星历切日期
+1 -1
View File
@@ -54,7 +54,7 @@ export function rectificationEntryHint(
summary: RectificationEntrySummary | null,
): string | null {
if (!rectificationForSelf) return "生时校正暂时只支持本人。";
if (summary?.hasResumableCase) return "上次那次校正还没完成,可以接着做。";
if (summary?.hasResumableCase) return "上次那次校正还没完成,可以在历史对话里接着做。";
return null;
}
@@ -345,7 +345,7 @@ export function useRectificationSurface(params: RectificationSurfaceParams) {
function rectificationLimitedToSelf(): boolean {
if (readCurrentSubjectId() === "self") return false;
setRectificationError("生时校正暂时只支持本人");
setRectificationError("生时校正暂时只支持本人。");
return true;
}
@@ -22,7 +22,7 @@ import { createClientLifecycleHarness } from "./react-client-lifecycle-test-supp
Object.assign(globalThis, { React });
const CASE_ID = "00000000-0000-4000-8000-000000000041";
const RESUMABLE_HINT = "上次那次校正还没完成,可以接着做。";
const RESUMABLE_HINT = "上次那次校正还没完成,可以在历史对话里接着做。";
const NON_SELF_HINT = "生时校正暂时只支持本人。";
const REMOVED_HINTS = /不确定出生时间时|上次已经校正完|未完成的那次可以从左侧继续|看看今天的整体节奏| · /;