feat(patch):统一清单驱动汉化发布
bat-rust / Build and test Rust (push) Canceled after 0s
bat-rust / Build and test Go API (push) Canceled after 0s

This commit is contained in:
2026-09-12 01:35:29 +08:00
parent 69b6e36bf0
commit 8a77502272
26 changed files with 2250 additions and 158 deletions
+8 -8
View File
@@ -1,6 +1,6 @@
# AssetBundle 与资源解析路线图
- **更新时间**2026-09-04
- **更新时间**2026-09-12
- **适用范围**:Rust 解析引擎、官方同步后的解析缓存、CAS/ResourceRepository 接入、后续文本提取和 Patch 发布。
- **权威关联**`PROJECT_PLAN.md` Milestone 3/4/5/8`docs/reports/CURRENT_GAPS.md` G-005/G-007/G-011/G-011D。
- **开发状态**:解析扩展当前按路线图和真实回归继续推进。
@@ -32,7 +32,7 @@
| UnityFS container | `.bundle`、zip 内 bundle | header、block、directory、解压文件、基础摘要 | 已支持基础解包、LZ4/LZMA、alignment、大小/计数/路径/边界校验;受支持 patch 可保留容器形态重建 |
| Serialized file | UnityFS directory 文件 | header、type table、TypeTree node、object table、TextAsset bytes | 已支持基础表结构和 TextAsset bytes |
| Unity 对象字段 | TextAsset、MonoBehaviour、ScriptableObject | 可翻译文本单元、上下文、资源定位 | TypeTree 基础字段读取、`SerializedReference` / prefixed managed-reference metadata alias、payload 提取和字符串提取已落地,真实结构覆盖继续扩大 |
| Patch 发布 | 已翻译 TextUnit、中间格式、原版资源 | 可验证 localized patch manifest、汉化 release 目录、current/state | 已支持 TextAsset、TypeTree string field、managed-reference string field 的 UnityFS parse→modify→rebuild→reparse;可验证 ZIP 内 bundle 时会重写外层 ZIP;通用 manifest 发布仍未完成 |
| Patch 发布 | 已翻译 TextUnit、中间格式、原版资源 | 可验证 localized patch manifest、汉化 release 目录、current/state | generic manifest 已驱动 Binary/JSON/Text 与当前支持的 UnityFS 操作;可验证 ZIP 内 bundle 时会在外层重写后重新读取、重解析并校验定位字段/替换值 |
---
@@ -171,9 +171,9 @@ catalog 仍按“明确不支持”处理,不把低保真路径伪装成完整
交付:
1. 已定义 `localized-patch-manifest.json`:目标官方版本、localized release、输出文件、hash、size、byte delta、TextUnit/provider/review trace 和回滚信息。
1. 已定义并接入 generic `PatchManifest`:目标官方版本、localized release、输出文件、hash、size、按序 operation、算法载荷、UnityFS 定位、TextUnit/provider/review trace 和回滚信息。
2. 已支持 UnityFS TextAsset、TypeTree string field 和 managed-reference string field 的 localized patch 操作;普通 ZIP 条目在 `archive_entry` 可验证、内层可重解析时会解包、重建并重写外层 ZIP,路径穿越、symlink、混合直接/ZIP patch 和无效内层 bundle 明确失败。
3. MonoBehaviour/ScriptableObject 字段替换必须依赖 P2 字段级解析结果。
3. MonoBehaviour/ScriptableObject 字段替换必须依赖 P2 字段级解析结果generic manifest 不把 UnityFS 定位信息扁平化
4. Patch 产物写入配置化汉化发布根下的 `.staging/<id>`,校验通过后发布到 `versions/<id>` 并切换 `current`rollback 按 manifest 恢复上一 release。
5. 成功后发布状态从 `not_localized` 切到 `localized``localized.status` 要求 state、current symlink 和 patch manifest 同时匹配当前官方 releaseZIP 外层文件和内层 UnityFS 也必须通过发布后重解析校验。
@@ -181,7 +181,7 @@ catalog 仍按“明确不支持”处理,不把低保真路径伪装成完整
1. Patch 失败不影响 `bat-resources/current`
2. 汉化 release 保留官方相对目录结构。
3. `localized` 状态能证明原版和汉化两套资源都已发布,且 patch manifest 可验证。
3. `localized` 状态能证明原版和汉化两套资源都已发布,且 generic/localized patch manifest 可验证。
---
@@ -210,7 +210,7 @@ catalog 仍按“明确不支持”处理,不把低保真路径伪装成完整
1. 继续补充 Addressables Windows/Android 真实 catalog 样本和独立二进制格式诊断。
2. 继续补充 TypeTree 字段 reader、MonoBehaviour/ScriptableObject 遍历和真实版本差异。
3. 基于 `translation.worker.run` 扩展 TM/Glossary 和通用 manifest Patch 构建
3. 基于 `translation.worker.run` 继续扩展 TM/Glossary provenance 和真实资源发布样本
4. 扩展翻译任务结果在 CAS/ResourceRepository 查询面的索引。
5.通用 Binary/JSON/Text Patch 基础上继续扩展复杂 AssetBundle 重打包和通用
Patch 发布流程统一,保留当前受支持 localized patch 发布/rollback 链路
5. generic Binary/JSON/Text Patch 基础上继续扩展复杂 AssetBundle 重打包,但只在
新结构有真实 fixture 和完整重建验证时接入;不扩大当前 UnityFS V1 的宣称范围
@@ -244,7 +244,7 @@ trusted 和 release/TextUnit/provider/run provenance`translation.tasks` 优
13. 发布完成后先对比上一完整 release 和当前 release 的 `official-download-manifest.json`,写出 `official-resource-changes.json``crowdin-translation-handoff.json`。同一 destination 只有 size 或 BLAKE3 变化才算 modified;新增+变更资源进入解析/翻译 handoff,删除资源只进入差异记录。当前只预留 Crowdin 本地 handoff,不发外部 API 请求。
14. 随后刷新 active release 下的 `official-parse-cache.json``official-textunit-index.json`,并从 Added/Modified 资源、parse cache 与 TextUnit 明细索引派生 `official-textunit-tasks.json``crowdin-textunit-queue.json` 和版本化的 `translation-tasks.sqlite`up-to-date 轮询在已有有效解析缓存、TextUnit 明细索引和 TextUnit 队列时只读取摘要,不重复解析,重新同步队列时保留已有 worker 状态。
15. 若启用 `--import-repository`,已校验 release 会被导入 CAS + `ResourceRepository`,并可经 `resource.index` 查询。历史 release 候选失效时,已有 CAS 对象会先经过完整性和元数据校验,再增加 release 引用并原子物化;当前 release 在 `official-cas-reuse-references.json` 中记录引用,staging/release 清理时递减,失败则回退网络并保留诊断。
16. 官方同步报告默认给出 `localized_release_status=not_localized`,表示原版资源已发布、汉化资源未发布;支持的 UnityFS TextAsset、TypeTree string field 和 managed-reference string field patch 发布成功并通过 `localized-patch-manifest.json`、current symlink、release ID 及 ZIP 内层重解析校验后,`localized.status` 才返回 `localized`,表示原版和汉化两套资源都已发布。`translation.proofread` 只会把 workflow 标记成 `manual_proofreading` / `translation.manual_proofreading`,不会回退已发布汉化 release 的发布状态。
16. 官方同步报告默认给出 `localized_release_status=not_localized`,表示原版资源已发布、汉化资源未发布;generic manifest 驱动的 Binary/JSON/Text 以及当前支持的 UnityFS TextAsset、TypeTree string field 和 managed-reference string field patch 发布成功并通过 `localized-patch-manifest.json`、current symlink、release ID 及 ZIP 内层最终重解析校验后,`localized.status` 才返回 `localized`,表示原版和汉化两套资源都已发布。`translation.proofread` 只会把 workflow 标记成 `manual_proofreading` / `translation.manual_proofreading`,不会回退已发布汉化 release 的发布状态。
维护期特殊分支:如果官方 launcher/server-info 已经指向新资源根,但 client-patch seed marker 或必需 seed catalog 仍返回 403/404 等未开放状态,`bat` 返回 `waiting_for_official_resources`,保留现有 `current`,不创建失败 staging;若本轮启用 `--auto-discover`,会在 `<output>/official-launcher-bootstrap.pending.json` 写入待处理 launcher bootstrap 证据,供后续排障和自研客户端开发使用。
+4 -2
View File
@@ -1,6 +1,6 @@
# 官方资源 Release 布局与资源侧契约
- **更新时间**2026-09-04
- **更新时间**2026-09-12
- **用途**:冻结日服官方资源在本地发布根上的布局、URL 映射、seed 规则、`bat`/`bat-api` 关系,以及 `bat-api` 分发 path 的 1:1 对应关系。
- **范围**:资源发现 / 清单 / 落盘 / 只读分发(**不是**完整游戏业务 API)。
- **权威代码**
@@ -75,7 +75,9 @@
<localized-output>/ # 汉化产物发布根(--localized-output / BAT_LOCALIZED_OUTPUT
current -> versions/<id> # 已汉化后才切换;未汉化状态不发布
versions/<id>/ # 与官方相对路径一致的汉化资源
localized-version-state.json # 预留:后续 Patch 发布阶段维护,官方同步阶段不写入
localized-patch-manifest.json # localized wrapper + generic PatchManifest 审计输入/结果
.staging/<id>/ # generic/translation patch 未发布写侧
localized-version-state.json # localized current、官方 source release 和 workflow 状态
```
官方资源发布和汉化发布是两个独立状态:
+2 -2
View File
@@ -89,8 +89,8 @@ git check-ignore -v Cargo.lock CLAUDE.md AGENTS.md CONTRIBUTING.md
当前开发优先推进:
1. 继续 AssetBundle 复杂对象解析、真实 fixture 和发布级重打包。
2. 基于 `translation.worker.run` 继续扩展 TM/Glossary,并推进通用 manifest Patch 构建
3. 扩展 ResourceRepository 查询面:更丰富的 TextUnit/TM 查询和通用 Patch 发布所需资源视图。
2. 基于 `translation.worker.run` 继续扩展 TM/Glossary,并补充复杂 AssetBundle 的真实 fixture 与发布验证
3. 扩展 ResourceRepository 查询面:更丰富的 TextUnit/TM 查询和 generic manifest 发布所需资源视图。
4.`docs/guides/official-full-pull-smoke.md` 在隔离目录执行真实官方网络全量下载 smoke,并保留运行报告。
5. 在资源和翻译契约稳定后推进完整 Web 协作后台和完整游戏业务 API。
+18 -2
View File
@@ -336,7 +336,8 @@ source text、destination 和 archive entry 后再落库。blocking Glossary QA
## localized patch 发布与回滚
`i18n publish` 会在独立的 `.staging/<localized-release-id>` 中复制当前官方
release,校验工作台与当前 TextUnit 索引的 source/location 一致后,写入已有支持
release,校验工作台或 generic patch manifest 与当前官方 release 的 source identity
一致后,按确定的 operation sequence 写入 Binary、JSON、UTF-8 Text,以及已有支持
范围内的 TextAsset、TypeTree string field 和 managed-reference string field
patch。校验通过后才原子切换 `localized/current`,并在 release manifest 中记录
源/目标 BLAKE3、字节数、patch kind、TextUnit、provider、review、发布时重新计算的
@@ -359,6 +360,21 @@ bat i18n publish \
--localized-release-id release-worker-1
```
已有 generic manifest 时直接发布:
```bash
bat i18n publish \
--patch-manifest /tmp/bat-patch-manifest.json \
--localized-release-id localized-v1
```
manifest 必须声明当前官方 `source_version` 和目标 localized `target_version`
文件 hash/size、操作顺序和算法载荷;直接文件支持 Binary/JSON/TextUnityFS 操作
必须保留 serialized file、path ID、field path 或 TextAsset 定位,ZIP 内 UnityFS
还必须保留 `archive_entry`。Rust 会在 staging 中逐操作验证 source precondition、
最终 hash/size,并在 ZIP 外层重写后重新读取条目、重解析 UnityFS 和校验实际替换值。
其他未支持的 UnityFS 结构仍明确拒绝。
发布失败会清理 staging,不切换 `current`。当前 release 的 rollback 目标由
manifest 记录,执行后删除本次版本目录并恢复上一版本;没有上一版本时移除
`current`
@@ -370,7 +386,7 @@ bat i18n rollback --localized-release-id release-worker-1
Rust RPC 方法为 `localized.publish``localized.rollback`bat-api 对应为
`POST /admin/control/localized-publish``POST /admin/control/localized-rollback`
以及鉴权的 `GET /admin/translation/status`。发布请求必须且只能包含
`translation_file``from_worker=true`rollback 可省略 release ID 以操作当前
`translation_file``from_worker=true``patch_manifest`rollback 可省略 release ID 以操作当前
release。Go 只做鉴权、参数校验和转发,状态与产物仍由 Rust 持有。
## 边界
+10 -2
View File
@@ -337,7 +337,7 @@ Glossary 只把 `approved` term 发送为 provider constraints。worker 会在 t
| 方法 | 状态 | params | data |
|---|---|---|---|
| `localized.status` | 已实现 | `null` | 汉化发布状态、当前官方 release 匹配关系和汉化输出目录。 |
| `localized.publish` | 已实现 | `{ "translation_file": "...", "localized_release_id": "...", "force": false }``{ "from_worker": true, "localized_release_id": "...", "force": false }` | 已校验并发布的汉化 release、manifest 和完整性报告。 |
| `localized.publish` | 已实现 | `{ "translation_file": "...", "localized_release_id": "...", "force": false }``{ "from_worker": true, "localized_release_id": "...", "force": false }``{ "patch_manifest": "...", "localized_release_id": "...", "force": false }`;三者只能选一个 | 已校验并发布的汉化 release、generic/localized manifest 和完整性报告。 |
| `localized.rollback` | 已实现 | `{ "localized_release_id": "..." }`,可省略 | 删除当前 release、恢复 manifest 记录的上一 release 和新状态。 |
`localized.status` 严格按 daemon / `config.toml` 或环境变量中的 `BAT_LOCALIZED_OUTPUT`
@@ -353,12 +353,20 @@ Glossary 只把 `approved` term 发送为 provider constraints。worker 会在 t
`current` symlink 指向汉化发布根下对应的 `versions/<id>`,并且该版本目录中的
`localized-patch-manifest.json` 存在且 release ID 匹配。响应会返回
`patch_manifest_path``patch_manifest_available`
`patch_manifest_matches_release``patch_file_count`
`patch_manifest_matches_release``patch_manifest_integrity_status`
`patch_manifest_source_version``patch_manifest_target_version`
`patch_file_count``patch_operation_count``patch_kind_counts`
`patch_text_asset_operation_count``rollback_previous_current_target`
每个 localized patch operation 的 manifest metadata 记录发布时重新计算的
`glossary_qa`(包括 `qa_identity`)及对应 `glossary_override`,不会复用 workbench
中已经过期的 QA 快照。
`localized.publish` 也可直接接收由 Rust `bat-patch` 构建的 generic manifest。
Rust 会把其 source version 绑定当前官方 release,在独立 staging 中按 manifest
顺序执行 Binary、JSON、UTF-8 Text 和当前支持的 UnityFS TextAsset/TypeTree 字段
操作,并保留实际操作载荷、hash/size、定位信息和 TextUnit/TM/Glossary/review
provenance。Go 只做鉴权、typed 参数校验和 RPC 转发。
### catalog
| 方法 | 状态 | params | data |
+14 -13
View File
@@ -1,6 +1,6 @@
# 当前实现缺口清单
- **更新时间**2026-09-10
- **更新时间**2026-09-12
- **文档角色**:只记录尚未完成、仍需验证或仍需设计的工作,不重复维护完整实现状态。
- **当前事实**:以源码、测试、稳定契约和 `CURRENT_STATUS.md` 为准。
- **Go 进度**`GO_STATUS.md`
@@ -32,21 +32,22 @@ directory 形态和未修改对象/字段,并明确拒绝未知压缩或无法
回归和 `bat-infrastructure` 的解析缓存、ZIP 内 bundle 发布测试。新增格式覆盖必须
同时补真实 fixture、回归测试和文档。
### G-006:通用 Patch 发布仍未完成
### G-006:通用 Patch 的复杂格式和运维视图仍未完成
状态:**基础完成,发布流程部分完成**
状态:**V1 已完成(当前支持类型),复杂格式和运维扩展继续推进**
`bat-patch` 已提供 Binary/JSON/Text Patch、manifest、BLAKE3/size 校验和
rollback 元数据;文件级 `patch.apply` 与受支持的 UnityFS TextAsset、TypeTree
string field、managed-reference string field 写入及 localized publish/rollback
已可用。
`bat-patch` 已提供 Binary/JSON/Text Patch、manifest builder、BLAKE3/size 校验和
rollback 元数据;`LocalizedPatchService` 已使用同一有序 generic manifest 驱动
Binary/JSON/Text 与当前支持的 UnityFS TextAsset、TypeTree string/semantic field
写入及 localized publish/rollback。发布会在独立 staging 中校验 source/target identity、
逐操作 precondition、ZIP 内层重解析和实际字段替换,并保留 TextUnit/TM/Glossary/review
provenance`localized.publish``i18n publish` 和 bat-api typed forwarding 均已接入。
仍需完成:
- 通用 manifest 驱动的跨类型 patch build/apply/publish/rollback。
- 任意复杂 AssetBundle 重打包和完整翻译文件集合构建;当前 localized publish 已支持
可验证 ZIP 内 bundle 的外层 ZIP 重写,但不扩大 UnityFS 结构支持范围。
- 原版 release 与 localized release 双发布后的查询、分发和清理策略。
- 原版 release 与 localized release 双发布后的更丰富查询、分发和清理策略。
所有发布产物必须先进入独立 staging,通过完整性校验后再原子发布;失败不得改变
已发布的 `bat-resources/current``bat-localized/current`
@@ -105,14 +106,14 @@ format 等资源级过滤,`parse.text_units` / `parse.errors` 和翻译任务
- 从同一 manifest fingerprint 追溯资源、解析缓存、翻译任务和发布产物。
- 更多 schema 迁移、权限、并发和损坏恢复场景验证。
### G-011D:双 release 的完整查询与发布策略仍未完成
### G-011D:双 release 的完整查询与运维策略仍未完成
状态:**受支持范围完成,通用范围部分完成**
状态:**发布闭环完成,查询/清理扩展继续推进**
官方原版和 localized release 已分离,受支持 patch 可独立 staging、校验、发布和
rollback`localized.status` 能校验当前官方 release 与 patch manifest 的一致性。
仍需完成通用 patch 发布、复杂重打包、双 release 查询/分发视图和清理策略。
仍需完成复杂重打包、双 release 查询/分发视图和清理策略。
### G-012Translation Memory V1 已实现,扩展能力仍缺失
@@ -147,7 +148,7 @@ Rust `bat` 已提供独立项目级 `glossary.sqlite`term/alias/recommended/a
## 3. 后续推进顺序
1. 继续 G-005:更多真实 AssetBundle 样本、复杂字段解析、版本差异和任意结构重打包。
2. 继续 G-006/G-011D通用 manifest Patch 和双 release 查询/清理策略。
2. 继续 G-006/G-011D复杂 AssetBundle 兼容和双 release 查询/清理策略。
3. 继续 G-011/G-012/G-013/G-014:资源查询、TM/Glossary 扩展和 Provider
扩展体系。
4. 在隔离环境执行 `make official-smoke`,补充真实网络长期运行报告。
+2 -2
View File
@@ -1,6 +1,6 @@
# Go 侧进度与边界(权威)
- **更新时间**2026-09-04
- **更新时间**2026-09-12
- **用途**:统一 Go module `bat-api` 的产品边界、既有约定和组件进度;其他文档与此冲突时以本文为准。
- **关联缺口**G-009(资源 bootstrap/分发);相关契约见 `docs/architecture/official-resource-backend.md` §7 和 `docs/guides/bat-api-local-live-smoke.md`
@@ -95,7 +95,7 @@
| 组件 | 路径 | 状态 | 说明 |
|---|---|---|---|
| Module | `go.mod``bat-api` | 已用 | 服务层模块名 |
| RPC client | `internal/backendrpc` | **完成** | Unix socket JSON-RPC transport + typed helpertyped helper 覆盖 daemon 已实现控制/查询、`resource.state/sync/verify/repair/manifest/list``catalog.*``parse.*``localized.status/publish/rollback``task.*``translation.tasks``translation.handoff``translation.task.update``translation.worker.run``translation.proofread``translation.memory.summary/query/confirm``translation.glossary.summary/query/diagnose/add/update/approve/deprecate/delete` 和文件级 UnityFS patch 调用;`resource.index``patch.apply` 仍通过通用 `Call` 走同一 contractfake transport 单测和 `internal/api/testdata/contract/` mirror test 固化 Rust 输出字段 |
| RPC client | `internal/backendrpc` | **完成** | Unix socket JSON-RPC transport + typed helpertyped helper 覆盖 daemon 已实现控制/查询、`resource.state/sync/verify/repair/manifest/list``catalog.*``parse.*``localized.status/publish/rollback``task.*``translation.tasks``translation.handoff``translation.task.update``translation.worker.run``translation.proofread``translation.memory.summary/query/confirm``translation.glossary.summary/query/diagnose/add/update/approve/deprecate/delete` 和文件级 UnityFS patch 调用;`localized.publish` 的 typed params 支持 `translation_file``from_worker``patch_manifest` 三选一;`resource.index``patch.apply` 仍通过通用 `Call` 走同一 contractfake transport 单测和 `internal/api/testdata/contract/` mirror test 固化 Rust 输出字段 |
| 资源 bootstrap/分发 | `cmd/bat-api` + `internal/api` | **MVP+生产控制面** | RPC 发现 + 周期刷新/诊断 + `/v1/bootstrap` + `/v1/launcher/bootstrap` + launcher 资源 metadata 兼容 + `/readyz` + CDN Range/缓存头 + 鉴权/限流/访问日志/反代适配 + OpenAPI + 管理控制白名单 + translation/TM/Glossary admin forwarding + 内嵌 dashboard + `.env` |
| 试验 CLI | `cmd/bat` | **试验** | doctor 固定 okmanifest/sync 走 FFI |
| FFI | `internal/ffi` | **可选** | 需 `build-ffi` |