diff --git a/client/harmony/entry/src/main/ets/pages/MainPage.ets b/client/harmony/entry/src/main/ets/pages/MainPage.ets index 47b3039..3f65128 100644 --- a/client/harmony/entry/src/main/ets/pages/MainPage.ets +++ b/client/harmony/entry/src/main/ets/pages/MainPage.ets @@ -18,7 +18,7 @@ import { MailApi, InboxResponse } from '../api/MailApi'; import { AccountManager, AccountInfo } from '../api/AccountManager'; import { SseService, SseEvent } from '../api/SseService'; import { AppearanceStore } from '../common/AppearanceStore'; -import { MailStore, MailSnapshot, INBOX_PAGE_SIZE } from '../common/MailStore'; +import { MailStore, MailSnapshot, AccountError, INBOX_PAGE_SIZE } from '../common/MailStore'; import { AppearanceApi } from '../api/AppearanceApi'; import { performLogout } from '../api/Logout'; import { ComposeIntent } from '../common/ComposeIntent'; @@ -502,6 +502,26 @@ struct InboxTab { } /** 把 store 快照接进本组件的 `@State`(触发 ArkUI 刷新)。 */ + /** + * 聚合模式下**单个账号**取失败的原因(`MailStore` 已在收集,此前没人读)。 + * + * ★★ 2026-09-21 补(逐页对齐 WebUI 时发现的安全网断线): + * 数据一直在 `MailSnapshot.accountErrors` 里、两处 load 都写, + * 但**界面从来没有读过它** ⇒ 某个账号拉不到邮件时列表**静默少一整份**, + * 而界面看起来完全正常 —— 用户会得出错误结论("没人给我发信")。 + */ + @State accountErrors: AccountError[] = []; + + /** 把聚合失败拼成 WebUI 那句文案:「a(原因);b(原因)」 */ + private accountErrorText(): string { + const parts: string[] = []; + for (let i = 0; i < this.accountErrors.length; i++) { + const e: AccountError = this.accountErrors[i]; + parts.push(e.reason.length > 0 ? e.account + '(' + e.reason + ')' : e.account); + } + return parts.join(';'); + } + private applyStoreSnapshot(snap: MailSnapshot): void { /* * `MailLike[]` → `MailSummary[]`:store 持有的是接口类型(它不该依赖具体实现类), @@ -516,6 +536,8 @@ struct InboxTab { this.notice = snap.notice; this.loading = snap.loading; this.error = snap.error; + /* 聚合失败原因(见 `accountErrors` 的注释:数据一直有,界面前面没接) */ + this.accountErrors = snap.accountErrors; } /** 展开状态放在数组里(ArkTS 的 @State 对 Map/Set 的变更不总是能观察到) */ @@ -613,6 +635,31 @@ struct InboxTab { .padding({ left: 10, right: 10 }) .margin({ top: 10 }) + /* + * 聚合失败横幅(对齐 WebUI `MailList.tsx:85-96` 的 `account-errors`)。 + * + * 文案/形状照 WebUI: + * 「有 {n} 个账号没取到:{账号}({原因});…」 + * 琥珀底 + 琥珀边 + 11 号字(`bg-amber-50 border-amber-200 text-amber-800`)。 + * + * ★★ 为什么值得单独占一块地方(WebUI 原注释): + * 「聚合时**某个账号取不到**必须说出来:静默丢掉它,列表会少一整份邮件, + * 而界面看起来完全正常 —— 这正是"聚合"最容易骗人的失败方式」 + * + * 本仓的情况更糟一点:`MailStore` **一直在收集**这些失败 + * (`snap.accountErrors`,两处 load 都写),但**界面从来没有读过它** ⇒ + * 这个安全网当前是断的。是逐页对齐时比对出来的,不是猜的。 + */ + if (this.accountErrors.length > 0) { + Text('有 ' + this.accountErrors.length + ' 个账号没取到:' + this.accountErrorText()) + .fontSize(11).fontColor(Theme.warnFgDark) + .width('100%') + .padding({ left: 8, right: 8, top: 6, bottom: 6 }) + .backgroundColor(Theme.warnBg) + .borderRadius(6) + .margin({ top: 6 }) + } + // 账号选择器下拉 if (this.showAccountPicker && this.accountList.length > 1) { Column() {