1136 lines
32 KiB
Markdown
1136 lines
32 KiB
Markdown
# i18n 国际化集成计划
|
||
|
||
## TL;DR
|
||
|
||
> **Quick Summary**: 为 Electron + React 应用添加完整的国际化支持,使用 react-i18next + @lobehub/i18n-cli,支持中日英三语切换,包含渲染进程和主进程的全面国际化。
|
||
>
|
||
> **Deliverables**:
|
||
>
|
||
> - 完整的 i18n 配置和语言文件结构
|
||
> - 渲染进程所有组件的国际化
|
||
> - 主进程 IPC 错误消息国际化
|
||
> - 独立的设置页面(语言切换)
|
||
> - 用户语言偏好持久化
|
||
> - Ant Design locale 同步切换
|
||
>
|
||
> **Estimated Effort**: Medium
|
||
> **Parallel Execution**: YES - 5 waves
|
||
> **Critical Path**: Wave 1 → Wave 2 → Wave 3 → Wave 4 → Final Verification
|
||
|
||
---
|
||
|
||
## Context
|
||
|
||
### Original Request
|
||
|
||
用户需要添加 i18n 对所有内容进行国际化,支持中日英三语,需要在设置里面加上切换组件。
|
||
|
||
### Interview Summary
|
||
|
||
**Key Discussions**:
|
||
|
||
- **翻译文件管理**: 静态导入(简单可靠,无需 IPC 文件访问)
|
||
- **自动化翻译**: 需要 @lobehub/i18n-cli(AI 自动生成翻译)
|
||
- **语言切换位置**: 创建独立设置页面
|
||
- **支持语言**: 中文(zh-CN)、日文(ja-JP)、英文(en-US)
|
||
- **主进程国际化**: 需要(IPC 错误消息、日志等)
|
||
- **用户偏好持久化**: 需要持久化保存用户语言选择
|
||
- **测试策略**: Agent QA
|
||
|
||
**Research Findings**:
|
||
|
||
- react-i18next 是成熟稳定的基础方案,社区庞大
|
||
- LobeChat 方案本质上是 react-i18next + @lobehub/i18n-cli 自动化工具
|
||
- 项目目前完全没有 i18n 实现,存在大量硬编码中文文本
|
||
- 已有 Ant Design 国际化配置(固定为 zh-CN),需改为动态切换
|
||
- 已有 Zustand stores 架构,可新增 localeStore
|
||
|
||
### Self-Review Gaps
|
||
|
||
**Identified Gaps** (addressed):
|
||
|
||
- **命名空间划分**: 采用功能模块划分(common, domain, settings, errors)
|
||
- **语言检测策略**: 使用 i18next-browser-languagedetector + 持久化存储
|
||
- **主进程同步机制**: 通过 IPC 通道同步语言状态
|
||
- **AI 翻译质量**: 首次 AI 翻译后需要人工校验关键术语
|
||
|
||
---
|
||
|
||
## Work Objectives
|
||
|
||
### Core Objective
|
||
|
||
为 Kintone Customize Manager 添加完整的国际化支持,实现中日英三语切换,覆盖渲染进程 UI 和主进程错误消息。
|
||
|
||
### Concrete Deliverables
|
||
|
||
- `src/renderer/src/locales/` - 语言文件目录(中日英三语)
|
||
- `src/renderer/src/stores/localeStore.ts` - 语言状态管理
|
||
- `src/renderer/src/components/Settings/` - 设置页面组件
|
||
- `src/renderer/src/i18n.ts` - i18n 配置文件
|
||
- `src/shared/types/locale.ts` - 语言类型定义
|
||
- 修改所有现有组件的硬编码文本为 `t()` 调用
|
||
- 修改主进程 IPC 错误消息为国际化文本
|
||
|
||
### Definition of Done
|
||
|
||
- [x] 用户可以在设置页面切换语言
|
||
- [x] 切换后所有 UI 文本立即更新
|
||
- [x] Ant Design 组件语言同步切换
|
||
- [x] 主进程 IPC 错误消息正确显示当前语言
|
||
- [x] 用户语言选择持久化保存
|
||
- [x] 重启应用后语言设置保持
|
||
|
||
### Must Have
|
||
|
||
- react-i18next + i18next 核心库
|
||
- @lobehub/i18n-cli 自动化翻译
|
||
- 中日英三语完整翻译
|
||
- 语言切换 UI 组件
|
||
- 用户偏好持久化
|
||
|
||
### Must NOT Have (Guardrails)
|
||
|
||
- 不使用 i18next-electron-fs-backend(静态导入足够)
|
||
- 不支持 RTL 语言(中日英都是 LTR)
|
||
- 不引入远程翻译文件加载
|
||
- 不在 MVP 阶段过度抽象翻译 key 结构
|
||
|
||
---
|
||
|
||
## Verification Strategy (MANDATORY)
|
||
|
||
### Test Decision
|
||
|
||
- **Infrastructure exists**: NO
|
||
- **Automated tests**: None
|
||
- **Framework**: N/A
|
||
- **Primary Verification**: Agent-Executed QA Scenarios
|
||
|
||
### QA Policy
|
||
|
||
Every task MUST include agent-executed QA scenarios.
|
||
Evidence saved to `.sisyphus/evidence/task-{N}-{scenario-slug}.{ext}`.
|
||
|
||
- **Frontend/UI**: Use Playwright — Navigate, interact, assert DOM, screenshot
|
||
- **Language Switch**: Verify UI text changes, Ant Design locale updates
|
||
- **Persistence**: Verify language preference saved and restored
|
||
|
||
---
|
||
|
||
## Execution Strategy
|
||
|
||
### Parallel Execution Waves
|
||
|
||
```
|
||
Wave 1 (Foundation - 6 tasks, MAX PARALLEL):
|
||
├── Task 1: 安装依赖 [quick]
|
||
├── Task 2: 创建类型定义 [quick]
|
||
├── Task 3: 创建语言文件目录结构 [quick]
|
||
├── Task 4: 创建 localeStore [quick]
|
||
├── Task 5: 配置 i18n 实例 [quick]
|
||
└── Task 6: 配置 @lobehub/i18n-cli [quick]
|
||
|
||
Wave 2 (Core Integration - 4 tasks, depends on Wave 1):
|
||
├── Task 7: 渲染进程 i18n Provider 集成 [quick]
|
||
├── Task 8: Ant Design locale 同步 [quick]
|
||
├── Task 9: 主进程 IPC 语言同步 [unspecified-high]
|
||
└── Task 10: Preload 暴露语言 API [quick]
|
||
|
||
Wave 3 (Component Migration - depends on Wave 2):
|
||
├── Task 11: App.tsx 国际化 [quick]
|
||
├── Task 12: DomainManager 国际化 [quick]
|
||
├── Task 13: 其他组件国际化 [unspecified-high]
|
||
└── Task 14: 主进程错误消息国际化 [unspecified-high]
|
||
|
||
Wave 4 (Settings & Polish - depends on Wave 3):
|
||
├── Task 15: 创建设置页面组件 [visual-engineering]
|
||
├── Task 16: 语言切换 UI 实现 [visual-engineering]
|
||
└── Task 17: 用户偏好持久化 [quick]
|
||
|
||
Wave FINAL (Verification - 4 parallel tasks):
|
||
├── Task F1: Plan compliance audit (oracle)
|
||
├── Task F2: Code quality review (unspecified-high)
|
||
├── Task F3: Real manual QA (unspecified-high)
|
||
└── Task F4: Scope fidelity check (deep)
|
||
|
||
Critical Path: Wave 1 → Wave 2 → Wave 3 → Wave 4 → Final
|
||
Parallel Speedup: ~60% faster than sequential
|
||
Max Concurrent: 6 (Wave 1)
|
||
```
|
||
|
||
### Dependency Matrix
|
||
|
||
| Task | Depends On | Blocks |
|
||
| ----- | ---------- | ------ |
|
||
| 1-6 | - | 7-10 |
|
||
| 7-10 | 1-6 | 11-14 |
|
||
| 11-14 | 7-10 | 15-17 |
|
||
| 15-17 | 11-14 | F1-F4 |
|
||
| F1-F4 | All | - |
|
||
|
||
### Agent Dispatch Summary
|
||
|
||
- **Wave 1**: 6 tasks → all `quick`
|
||
- **Wave 2**: 4 tasks → 3 `quick` + 1 `unspecified-high`
|
||
- **Wave 3**: 4 tasks → 2 `quick` + 2 `unspecified-high`
|
||
- **Wave 4**: 3 tasks → 2 `visual-engineering` + 1 `quick`
|
||
- **FINAL**: 4 tasks → oracle, unspecified-high, unspecified-high, deep
|
||
|
||
---
|
||
|
||
## TODOs
|
||
|
||
> Implementation + Test = ONE Task. Never separate.
|
||
> EVERY task MUST have: Recommended Agent Profile + Parallelization info + QA Scenarios.
|
||
|
||
- [x] 1. 安装 i18n 相关依赖
|
||
|
||
**What to do**:
|
||
- 安装 `i18next` 和 `react-i18next`
|
||
- 安装 `i18next-browser-languagedetector`
|
||
- 安装 `@lobehub/i18n-cli`
|
||
- 验证安装成功
|
||
|
||
**Must NOT do**:
|
||
- 不要安装 `i18next-electron-fs-backend`(不需要)
|
||
- 不要安装 `i18next-http-backend`(静态导入)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 简单的 npm install 命令
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 1 (with Tasks 2-6)
|
||
- **Blocks**: Tasks 7-10
|
||
- **Blocked By**: None
|
||
|
||
**References**:
|
||
- `package.json` - 添加依赖到项目
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] `package.json` 包含 i18next, react-i18next, i18next-browser-languagedetector, @lobehub/i18n-cli
|
||
- [x] `npm ls i18next` 显示已安装
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证依赖安装成功
|
||
Tool: Bash
|
||
Preconditions: package.json 已更新
|
||
Steps:
|
||
1. npm ls i18next react-i18next i18next-browser-languagedetector @lobehub/i18n-cli
|
||
2. 检查所有依赖都显示版本号
|
||
Expected Result: 所有 4 个依赖都显示已安装版本
|
||
Failure Indicators: 任何依赖显示 "missing" 或 "UNMET"
|
||
Evidence: .sisyphus/evidence/task-01-deps-installed.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 2. 创建语言类型定义
|
||
|
||
**What to do**:
|
||
- 创建 `src/shared/types/locale.ts`
|
||
- 定义 `LocaleCode` 类型('zh-CN' | 'ja-JP' | 'en-US')
|
||
- 定义 `LocaleConfig` 接口
|
||
- 导出类型供其他模块使用
|
||
|
||
**Must NOT do**:
|
||
- 不要添加其他语言代码(只支持中日英)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 简单的类型定义文件
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 1 (with Tasks 1, 3-6)
|
||
- **Blocks**: Tasks 4, 7-10
|
||
- **Blocked By**: None
|
||
|
||
**References**:
|
||
- `src/shared/types/` - 参考现有类型定义风格
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 文件 `src/shared/types/locale.ts` 存在
|
||
- [x] 导出 `LocaleCode` 和 `LocaleConfig` 类型
|
||
- [x] TypeScript 编译通过
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证类型定义正确
|
||
Tool: Bash
|
||
Preconditions: 文件已创建
|
||
Steps:
|
||
1. npx tsc --noEmit
|
||
2. 检查无类型错误
|
||
Expected Result: 编译成功,无错误
|
||
Failure Indicators: TypeScript 报类型错误
|
||
Evidence: .sisyphus/evidence/task-02-types-compiled.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 3. 创建语言文件目录结构
|
||
|
||
**What to do**:
|
||
- 创建 `src/renderer/src/locales/` 目录
|
||
- 创建 `default/` 子目录存放源语言文件(中文)
|
||
- 创建 `zh-CN/`, `ja-JP/`, `en-US/` 三个语言目录
|
||
- 创建命名空间文件:`common.json`, `domain.json`, `settings.json`, `errors.json`
|
||
- 为每个命名空间添加初始翻译内容
|
||
|
||
**Must NOT do**:
|
||
- 不要创建空的 JSON 文件(要有初始内容)
|
||
- 不要使用嵌套对象结构(使用扁平 key)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 创建目录和文件结构
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 1 (with Tasks 1-2, 4-6)
|
||
- **Blocks**: Tasks 5, 7
|
||
- **Blocked By**: None
|
||
|
||
**References**:
|
||
- LobeHub i18n 文档: https://lobehub.com/docs/development/internationalization/internationalization-implementation
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 目录结构符合 LobeChat 规范
|
||
- [x] 每个语言目录包含 4 个命名空间 JSON 文件
|
||
- [x] 每个文件包含至少 5 个翻译 key
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证目录结构完整
|
||
Tool: Bash
|
||
Preconditions: 目录已创建
|
||
Steps:
|
||
1. ls -R src/renderer/src/locales/
|
||
2. 检查所有目录和文件存在
|
||
Expected Result: 显示完整目录树,包含 default/, zh-CN/, ja-JP/, en-US/ 和 4 个 JSON 文件
|
||
Failure Indicators: 任何目录或文件缺失
|
||
Evidence: .sisyphus/evidence/task-03-locale-structure.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 4. 创建 localeStore
|
||
|
||
**What to do**:
|
||
- 创建 `src/renderer/src/stores/localeStore.ts`
|
||
- 定义语言状态:`locale: LocaleCode`
|
||
- 定义切换语言方法:`setLocale(locale: LocaleCode)`
|
||
- 集成 persist middleware 持久化语言偏好
|
||
- 导出 `useLocaleStore` hook
|
||
|
||
**Must NOT do**:
|
||
- 不要在 store 中存储翻译内容(由 i18next 管理)
|
||
- 不要忘记 persist 配置
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 简单的 Zustand store
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 1 (with Tasks 1-3, 5-6)
|
||
- **Blocks**: Tasks 7, 15-17
|
||
- **Blocked By**: Task 2(类型定义)
|
||
|
||
**References**:
|
||
- `src/renderer/src/stores/domainStore.ts` - 参考 store 结构
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 文件 `src/renderer/src/stores/localeStore.ts` 存在
|
||
- [x] 导出 `useLocaleStore` hook
|
||
- [x] 包含 persist 配置
|
||
- [x] TypeScript 编译通过
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 store 功能正确
|
||
Tool: Bash
|
||
Preconditions: store 已创建
|
||
Steps:
|
||
1. npx tsc --noEmit
|
||
2. 检查无类型错误
|
||
Expected Result: 编译成功
|
||
Failure Indicators: TypeScript 报错
|
||
Evidence: .sisyphus/evidence/task-04-store-compiled.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 5. 配置 i18n 实例
|
||
|
||
**What to do**:
|
||
- 创建 `src/renderer/src/i18n.ts`
|
||
- 配置 i18next 初始化
|
||
- 配置静态资源导入(从 locales 目录)
|
||
- 配置语言检测器(localStorage + navigator)
|
||
- 配置默认语言和回退语言
|
||
- 配置命名空间
|
||
|
||
**Must NOT do**:
|
||
- 不要使用 HTTP backend(静态导入)
|
||
- 不要忘记设置 `escapeValue: false`(React 已处理)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 标准的 i18next 配置
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 1 (with Tasks 1-4, 6)
|
||
- **Blocks**: Tasks 7, 8
|
||
- **Blocked By**: Task 3(语言文件)
|
||
|
||
**References**:
|
||
- react-i18next 文档: https://react.i18next.com
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 文件 `src/renderer/src/i18n.ts` 存在
|
||
- [x] i18n 实例正确初始化
|
||
- [x] TypeScript 编译通过
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 i18n 配置正确
|
||
Tool: Bash
|
||
Preconditions: i18n.ts 已创建
|
||
Steps:
|
||
1. npx tsc --noEmit
|
||
2. 检查无类型错误
|
||
Expected Result: 编译成功
|
||
Failure Indicators: TypeScript 报错
|
||
Evidence: .sisyphus/evidence/task-05-i18n-config.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 6. 配置 @lobehub/i18n-cli
|
||
|
||
**What to do**:
|
||
- 创建 `.i18nrc.js` 配置文件
|
||
- 配置源语言目录(default/)
|
||
- 配置输出语言目录(zh-CN/, ja-JP/, en-US/)
|
||
- 配置 AI 翻译服务
|
||
- 添加 npm script `i18n` 用于生成翻译
|
||
|
||
**Must NOT do**:
|
||
- 不要提交 API key 到 git
|
||
- 不要在 CI 中运行 AI 翻译(成本考虑)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 配置文件创建
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 1 (with Tasks 1-5)
|
||
- **Blocks**: None(可选工具)
|
||
- **Blocked By**: Task 1(依赖安装)
|
||
|
||
**References**:
|
||
- @lobehub/i18n-cli 文档: https://www.npmjs.com/package/@lobehub/i18n-cli
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 文件 `.i18nrc.js` 存在
|
||
- [x] package.json 包含 `i18n` script
|
||
- [x] 配置文件格式正确
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 i18n-cli 配置正确
|
||
Tool: Bash
|
||
Preconditions: 配置文件已创建
|
||
Steps:
|
||
1. npm run i18n -- --help
|
||
2. 检查命令可用
|
||
Expected Result: 显示 i18n-cli 帮助信息
|
||
Failure Indicators: 命令不存在或报错
|
||
Evidence: .sisyphus/evidence/task-06-i18n-cli.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 7. 渲染进程 i18n Provider 集成
|
||
|
||
**What to do**:
|
||
- 在 `main.tsx` 中导入 i18n 实例
|
||
- 使用 `I18nextProvider` 包裹 App
|
||
- 或使用 `initReactI18next` 自动绑定
|
||
- 验证 i18n 在 React 组件中可用
|
||
|
||
**Must NOT do**:
|
||
- 不要重复初始化 i18n
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 标准 React 集成
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 2 (with Tasks 8-10)
|
||
- **Blocks**: Tasks 11-14
|
||
- **Blocked By**: Wave 1
|
||
|
||
**References**:
|
||
- `src/renderer/src/main.tsx` - React 入口文件
|
||
- `src/renderer/src/i18n.ts` - i18n 配置
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] `useTranslation` hook 可用
|
||
- [x] 应用启动无错误
|
||
- [x] `t()` 函数返回正确翻译
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 i18n Provider 集成成功
|
||
Tool: Playwright
|
||
Preconditions: 应用已启动
|
||
Steps:
|
||
1. 启动应用 npm run dev
|
||
2. 打开浏览器访问应用
|
||
3. 检查页面正常渲染
|
||
Expected Result: 应用正常启动,无控制台错误
|
||
Failure Indicators: 控制台有 i18n 相关错误
|
||
Evidence: .sisyphus/evidence/task-07-provider-integrated.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 8. Ant Design locale 同步
|
||
|
||
**What to do**:
|
||
- 创建 locale 映射函数,将 i18next locale 转换为 Ant Design locale
|
||
- 在 App.tsx 中使用 `ConfigProvider` 的 locale 属性
|
||
- 监听 i18n 语言变化,同步更新 Ant Design locale
|
||
- 导入 Ant Design 的 zhCN, jaJP, enUS locale
|
||
|
||
**Must NOT do**:
|
||
- 不要硬编码 locale(动态获取)
|
||
- 不要忘记处理语言变化事件
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: Ant Design 配置更新
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 2 (with Tasks 7, 9-10)
|
||
- **Blocks**: Task 16
|
||
- **Blocked By**: Wave 1, Task 4
|
||
|
||
**References**:
|
||
- `src/renderer/src/App.tsx` - 已有 ConfigProvider
|
||
- Ant Design 国际化文档: https://ant.design/docs/react/i18n
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] Ant Design 组件语言跟随 i18n 变化
|
||
- [x] DatePicker, Pagination 等组件显示正确语言
|
||
- [x] 切换语言后 Ant Design locale 立即更新
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 Ant Design locale 同步
|
||
Tool: Playwright
|
||
Preconditions: 应用已启动,i18n 已配置
|
||
Steps:
|
||
1. 打开设置页面
|
||
2. 切换语言到 English
|
||
3. 检查 Ant Design 组件(如 DatePicker)显示英文
|
||
4. 切换语言到日本語
|
||
5. 检查组件显示日文
|
||
Expected Result: Ant Design 组件语言随切换变化
|
||
Failure Indicators: 组件仍显示中文
|
||
Evidence: .sisyphus/evidence/task-08-antd-locale.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 9. 主进程 IPC 语言同步
|
||
|
||
**What to do**:
|
||
- 在主进程创建 IPC 处理器 `get-locale` 和 `set-locale`
|
||
- 存储当前语言设置(可与渲染进程 localStorage 同步)
|
||
- 主进程加载对应的错误消息翻译
|
||
- IPC 错误响应使用当前语言
|
||
|
||
**Must NOT do**:
|
||
- 不要在主进程使用 i18next(用简单的消息映射)
|
||
- 不要忘记同步主进程和渲染进程的语言状态
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `unspecified-high`
|
||
- Reason: 涉及 IPC 通信和主进程逻辑
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 2 (with Tasks 7-8, 10)
|
||
- **Blocks**: Task 14
|
||
- **Blocked By**: Wave 1
|
||
|
||
**References**:
|
||
- `src/main/ipc-handlers.ts` - IPC 处理器
|
||
- `src/main/storage.ts` - 存储逻辑
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] IPC 通道 `get-locale` 返回当前语言
|
||
- [x] IPC 通道 `set-locale` 更新语言设置
|
||
- [x] 主进程错误消息根据语言显示
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证主进程语言同步
|
||
Tool: Bash
|
||
Preconditions: IPC 已实现
|
||
Steps:
|
||
1. 启动应用
|
||
2. 触发一个 IPC 错误(如无效 domain)
|
||
3. 检查错误消息语言
|
||
4. 切换语言
|
||
5. 再次触发错误
|
||
6. 检查错误消息语言变化
|
||
Expected Result: 错误消息语言跟随设置变化
|
||
Failure Indicators: 错误消息始终是同一语言
|
||
Evidence: .sisyphus/evidence/task-09-ipc-locale.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 10. Preload 暴露语言 API
|
||
|
||
**What to do**:
|
||
- 在 `preload/index.ts` 中暴露 `getLocale` 和 `setLocale` API
|
||
- 添加类型声明到 `preload/index.d.ts`
|
||
- 确保类型安全
|
||
|
||
**Must NOT do**:
|
||
- 不要暴露不必要的 IPC 通道
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 简单的 preload 扩展
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 2 (with Tasks 7-9)
|
||
- **Blocks**: Task 14
|
||
- **Blocked By**: Task 9
|
||
|
||
**References**:
|
||
- `src/preload/index.ts` - 现有 preload API
|
||
- `src/preload/index.d.ts` - 类型声明
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] `window.api.getLocale()` 可用
|
||
- [x] `window.api.setLocale(locale)` 可用
|
||
- [x] TypeScript 类型正确
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 preload API 可用
|
||
Tool: Playwright
|
||
Preconditions: preload 已更新
|
||
Steps:
|
||
1. 打开开发者工具
|
||
2. 执行 window.api.getLocale()
|
||
3. 检查返回当前语言
|
||
Expected Result: 返回 'zh-CN' 或其他语言代码
|
||
Failure Indicators: API 不存在或报错
|
||
Evidence: .sisyphus/evidence/task-10-preload-api.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 11. App.tsx 国际化
|
||
|
||
**What to do**:
|
||
- 提取所有硬编码中文文本到翻译文件
|
||
- 使用 `useTranslation` hook 获取 `t` 函数
|
||
- 替换硬编码文本为 `t('key')` 调用
|
||
- 更新 `default/common.ts` 添加翻译 key
|
||
|
||
**Must NOT do**:
|
||
- 不要遗漏任何硬编码文本
|
||
- 不要使用不存在的 key
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 文本替换工作
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 3 (with Tasks 12-14)
|
||
- **Blocks**: Task 15
|
||
- **Blocked By**: Wave 2
|
||
|
||
**References**:
|
||
- `src/renderer/src/App.tsx` - 当前组件
|
||
- `src/renderer/src/locales/default/common.ts` - 翻译文件
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] App.tsx 无硬编码中文文本
|
||
- [x] 所有文本通过 `t()` 获取
|
||
- [x] 语言切换后文本更新
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 App.tsx 国际化
|
||
Tool: Playwright
|
||
Preconditions: 组件已国际化
|
||
Steps:
|
||
1. 启动应用
|
||
2. 检查顶部导航文本
|
||
3. 切换语言到 English
|
||
4. 检查文本变为英文
|
||
5. 切换语言到日本語
|
||
6. 检查文本变为日文
|
||
Expected Result: 所有文本随语言切换变化
|
||
Failure Indicators: 部分文本仍是中文
|
||
Evidence: .sisyphus/evidence/task-11-app-i18n.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 12. DomainManager 国际化
|
||
|
||
**What to do**:
|
||
- 提取 DomainManager 组件所有硬编码文本
|
||
- 添加 `domain` 命名空间翻译 key
|
||
- 使用 `useTranslation('domain')` 获取专用翻译
|
||
- 替换所有硬编码文本
|
||
|
||
**Must NOT do**:
|
||
- 不要混用命名空间(domain 相关用 domain 命名空间)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: 文本替换工作
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 3 (with Tasks 11, 13-14)
|
||
- **Blocks**: Task 15
|
||
- **Blocked By**: Wave 2
|
||
|
||
**References**:
|
||
- `src/renderer/src/components/DomainManager/DomainManager.tsx`
|
||
- `src/renderer/src/locales/default/domain.ts`
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] DomainManager 无硬编码文本
|
||
- [x] 所有文本通过 `t()` 获取
|
||
- [x] 错误消息也已国际化
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证 DomainManager 国际化
|
||
Tool: Playwright
|
||
Preconditions: 组件已国际化
|
||
Steps:
|
||
1. 打开 Domain 管理页面
|
||
2. 检查所有按钮和标签文本
|
||
3. 切换语言
|
||
4. 检查文本变化
|
||
5. 触发错误(如添加无效 domain)
|
||
6. 检查错误消息语言
|
||
Expected Result: 所有文本和错误消息随语言变化
|
||
Failure Indicators: 部分文本仍是硬编码
|
||
Evidence: .sisyphus/evidence/task-12-domain-i18n.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 13. 其他组件国际化
|
||
|
||
**What to do**:
|
||
- 扫描 `src/renderer/src/components/` 所有组件
|
||
- 提取所有硬编码文本到对应命名空间
|
||
- 批量替换为 `t()` 调用
|
||
- 确保无遗漏
|
||
|
||
**Must NOT do**:
|
||
- 不要遗漏任何组件
|
||
- 不要重复定义相同的 key
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `unspecified-high`
|
||
- Reason: 涉及多个组件,需要仔细检查
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 3 (with Tasks 11-12, 14)
|
||
- **Blocks**: Task 15
|
||
- **Blocked By**: Wave 2
|
||
|
||
**References**:
|
||
- `src/renderer/src/components/` - 所有组件
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 所有组件无硬编码文本
|
||
- [x] TypeScript 编译通过
|
||
- [x] 语言切换功能正常
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证所有组件国际化
|
||
Tool: Playwright
|
||
Preconditions: 所有组件已国际化
|
||
Steps:
|
||
1. 遍历应用所有页面
|
||
2. 检查每个页面的文本
|
||
3. 切换语言
|
||
4. 检查所有页面文本变化
|
||
Expected Result: 所有页面文本随语言变化
|
||
Failure Indicators: 发现硬编码文本
|
||
Evidence: .sisyphus/evidence/task-13-all-components.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 14. 主进程错误消息国际化
|
||
|
||
**What to do**:
|
||
- 创建主进程错误消息映射表
|
||
- 在 `ipc-handlers.ts` 中使用映射表
|
||
- 在 `kintone-api.ts` 中使用映射表
|
||
- 确保错误消息根据语言返回
|
||
|
||
**Must NOT do**:
|
||
- 不要在主进程使用 react-i18next
|
||
- 不要硬编码错误消息
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `unspecified-high`
|
||
- Reason: 涉及主进程逻辑修改
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 3 (with Tasks 11-13)
|
||
- **Blocks**: Final Verification
|
||
- **Blocked By**: Task 9, 10
|
||
|
||
**References**:
|
||
- `src/main/ipc-handlers.ts`
|
||
- `src/main/kintone-api.ts`
|
||
- `src/main/storage.ts`
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 主进程错误消息根据语言返回
|
||
- [x] IPC 错误响应使用正确语言
|
||
- [x] 无硬编码错误消息
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证主进程错误消息国际化
|
||
Tool: Bash + Playwright
|
||
Preconditions: 主进程已国际化
|
||
Steps:
|
||
1. 启动应用
|
||
2. 设置语言为 English
|
||
3. 触发错误(如无效 API token)
|
||
4. 检查错误消息为英文
|
||
5. 设置语言为日本語
|
||
6. 再次触发错误
|
||
7. 检查错误消息为日文
|
||
Expected Result: 错误消息语言正确
|
||
Failure Indicators: 错误消息语言不正确
|
||
Evidence: .sisyphus/evidence/task-14-main-errors.txt
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 15. 创建设置页面组件
|
||
|
||
**What to do**:
|
||
- 创建 `src/renderer/src/components/Settings/` 目录
|
||
- 创建 `Settings.tsx` 主组件
|
||
- 使用 Ant Design 组件构建 UI
|
||
- 包含语言切换区域
|
||
- 添加到应用路由或状态管理
|
||
|
||
**Must NOT do**:
|
||
- 不要过度设计(MVP 阶段)
|
||
- 不要包含不必要的设置项
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `visual-engineering`
|
||
- Reason: UI 组件开发
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 4 (with Tasks 16-17)
|
||
- **Blocks**: Final Verification
|
||
- **Blocked By**: Wave 3
|
||
|
||
**References**:
|
||
- `src/renderer/src/components/DomainManager/` - 参考组件结构
|
||
- Ant Design 组件库
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 设置页面可通过菜单访问
|
||
- [x] UI 布局清晰美观
|
||
- [x] 响应式设计
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证设置页面可访问
|
||
Tool: Playwright
|
||
Preconditions: 设置页面已创建
|
||
Steps:
|
||
1. 启动应用
|
||
2. 点击设置菜单
|
||
3. 检查设置页面显示
|
||
4. 截图
|
||
Expected Result: 设置页面正常显示
|
||
Failure Indicators: 页面空白或报错
|
||
Evidence: .sisyphus/evidence/task-15-settings-page.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 16. 语言切换 UI 实现
|
||
|
||
**What to do**:
|
||
- 在设置页面添加语言切换组件
|
||
- 使用 Radio 或 Select 组件
|
||
- 显示三个选项:中文、日本語、English
|
||
- 切换后立即更新 UI
|
||
- 同步更新 i18n 和 localeStore
|
||
|
||
**Must NOT do**:
|
||
- 不要忘记同步 Ant Design locale
|
||
- 不要忘记持久化用户选择
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `visual-engineering`
|
||
- Reason: UI 交互组件
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 4 (with Tasks 15, 17)
|
||
- **Blocks**: Final Verification
|
||
- **Blocked By**: Task 15
|
||
|
||
**References**:
|
||
- `src/renderer/src/stores/localeStore.ts`
|
||
- `src/renderer/src/i18n.ts`
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 语言切换 UI 显示正确
|
||
- [x] 切换后 UI 立即更新
|
||
- [x] Ant Design 组件语言同步
|
||
- [x] 选择已持久化
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证语言切换功能
|
||
Tool: Playwright
|
||
Preconditions: 语言切换 UI 已实现
|
||
Steps:
|
||
1. 打开设置页面
|
||
2. 当前语言是中文
|
||
3. 点击 English 选项
|
||
4. 检查所有 UI 文本变为英文
|
||
5. 检查 Ant Design 组件(如日期选择器)变为英文
|
||
6. 刷新页面
|
||
7. 检查语言仍为英文
|
||
Expected Result: 语言切换立即生效,刷新后保持
|
||
Failure Indicators: 切换后部分文本未更新,或刷新后重置
|
||
Evidence: .sisyphus/evidence/task-16-lang-switch.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
- [x] 17. 用户偏好持久化
|
||
|
||
**What to do**:
|
||
- 确保 localeStore 使用 persist middleware
|
||
- 验证 localStorage 正确存储语言偏好
|
||
- 应用启动时恢复用户语言选择
|
||
- 主进程也读取持久化的语言设置
|
||
|
||
**Must NOT do**:
|
||
- 不要忘记处理首次启动(无持久化数据)
|
||
|
||
**Recommended Agent Profile**:
|
||
- **Category**: `quick`
|
||
- Reason: Zustand persist 配置
|
||
- **Skills**: []
|
||
|
||
**Parallelization**:
|
||
- **Can Run In Parallel**: YES
|
||
- **Parallel Group**: Wave 4 (with Tasks 15-16)
|
||
- **Blocks**: Final Verification
|
||
- **Blocked By**: Task 4
|
||
|
||
**References**:
|
||
- `src/renderer/src/stores/localeStore.ts`
|
||
|
||
**Acceptance Criteria**:
|
||
- [x] 语言选择保存到 localStorage
|
||
- [x] 重启应用后语言设置保持
|
||
- [x] 首次启动使用系统语言
|
||
|
||
**QA Scenarios**:
|
||
|
||
```
|
||
Scenario: 验证语言偏好持久化
|
||
Tool: Playwright
|
||
Preconditions: 持久化已实现
|
||
Steps:
|
||
1. 打开应用
|
||
2. 切换语言到日本語
|
||
3. 关闭应用
|
||
4. 重新打开应用
|
||
5. 检查语言仍为日本語
|
||
6. 检查 localStorage 中有语言设置
|
||
Expected Result: 重启后语言设置保持
|
||
Failure Indicators: 重启后语言重置为默认
|
||
Evidence: .sisyphus/evidence/task-17-persistence.png
|
||
```
|
||
|
||
**Commit**: NO
|
||
|
||
---
|
||
|
||
## Final Verification Wave (MANDATORY)
|
||
|
||
- [x] F1. **Plan Compliance Audit** — `oracle`
|
||
Read the plan end-to-end. For each "Must Have": verify implementation exists. For each "Must NOT Have": search codebase for forbidden patterns. Check evidence files exist.
|
||
Output: `Must Have [N/N] | Must NOT Have [N/N] | Tasks [N/N] | VERDICT: APPROVE/REJECT`
|
||
|
||
- [x] F2. **Code Quality Review** — `unspecified-high`
|
||
Run `npx tsc --noEmit` + linter. Review all changed files for: `as any`/`@ts-ignore`, empty catches, unused imports. Check AI slop patterns.
|
||
Output: `Build [PASS/FAIL] | Lint [PASS/FAIL] | Files [N clean/N issues] | VERDICT`
|
||
|
||
- [x] F3. **Real Manual QA** — `unspecified-high` (+ `playwright` skill)
|
||
Start from clean state. Execute EVERY QA scenario from EVERY task. Test language switching across all pages. Test persistence. Save evidence.
|
||
Output: `Scenarios [N/N pass] | VERDICT`
|
||
|
||
- [x] F4. **Scope Fidelity Check** — `deep`
|
||
Verify 1:1 — everything in spec was built, nothing beyond spec was built. Check "Must NOT do" compliance.
|
||
Output: `Tasks [N/N compliant] | VERDICT`
|
||
|
||
---
|
||
|
||
## Commit Strategy
|
||
|
||
- **Commit 1**: `feat(i18n): add i18n infrastructure and dependencies`
|
||
- Files: package.json, src/shared/types/locale.ts, src/renderer/src/locales/, src/renderer/src/stores/localeStore.ts, src/renderer/src/i18n.ts, .i18nrc.js
|
||
- Pre-commit: `npx tsc --noEmit`
|
||
|
||
- **Commit 2**: `feat(i18n): integrate i18n into renderer and main process`
|
||
- Files: src/renderer/src/main.tsx, src/renderer/src/App.tsx, src/preload/index.ts, src/preload/index.d.ts, src/main/ipc-handlers.ts, src/main/kintone-api.ts
|
||
- Pre-commit: `npx tsc --noEmit`
|
||
|
||
- **Commit 3**: `feat(i18n): internationalize all components`
|
||
- Files: src/renderer/src/components/**/\*.tsx, src/renderer/src/locales/**/\*.ts
|
||
- Pre-commit: `npx tsc --noEmit`
|
||
|
||
- **Commit 4**: `feat(i18n): add settings page with language switcher`
|
||
- Files: src/renderer/src/components/Settings/
|
||
- Pre-commit: `npx tsc --noEmit`
|
||
|
||
---
|
||
|
||
## Success Criteria
|
||
|
||
### Verification Commands
|
||
|
||
```bash
|
||
# 检查依赖安装
|
||
npm ls i18next react-i18next i18next-browser-languagedetector @lobehub/i18n-cli
|
||
|
||
# 类型检查
|
||
npx tsc --noEmit
|
||
|
||
# 运行应用
|
||
npm run dev
|
||
|
||
# 生成翻译(可选)
|
||
npm run i18n
|
||
```
|
||
|
||
### Final Checklist
|
||
|
||
- [x] All "Must Have" present
|
||
- [x] All "Must NOT Have" absent
|
||
- [x] All TypeScript compiles without errors
|
||
- [x] Language switcher works correctly
|
||
- [x] All UI text updates on language change
|
||
- [x] Ant Design components use correct locale
|
||
- [x] Main process errors show correct language
|
||
- [x] User preference persists across restarts
|
||
- [x] @lobehub/i18n-cli configured and usable
|