mirror of
https://github.com/Yuyi-Oak/BlueArchiveToolkit.git
synced 2026-07-22 01:15:14 +08:00
feat: implement production cas v1
This commit is contained in:
@@ -10,6 +10,7 @@ BlueArchive Toolkit 采用 **Monorepo + 多语言混合** 架构,旨在构建
|
||||
|
||||
- `adr/0001-engine-and-application-boundaries.md`:Rust 引擎与 Go 应用层边界。
|
||||
- `adr/0002-cas-v1-design-boundary.md`:CAS V1 设计边界。
|
||||
- `adr/0003-cas-core-interface-and-error-boundary.md`:CAS 核心接口与错误边界冻结。
|
||||
|
||||
---
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# ADR 0002: CAS V1 设计边界
|
||||
|
||||
**状态**:已接受
|
||||
**状态**:已实现
|
||||
**日期**:2026-06-28
|
||||
**关联缺口**:`../../reports/CURRENT_GAPS.md`
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
|
||||
## 背景
|
||||
|
||||
当前代码中存在两处 CAS 相关实现:
|
||||
历史代码中存在两处 CAS 相关实现:
|
||||
|
||||
1. `crates/bat-cas-engine/src/storage.rs`
|
||||
2. `infrastructure/src/cas/filesystem.rs`
|
||||
@@ -71,6 +71,6 @@ CAS V1 不以“能通过简单 put/get 测试”为完成标准。必须满足
|
||||
|
||||
## 后续迁移要求
|
||||
|
||||
1. 将 `infrastructure/src/cas/filesystem.rs` 中的直接文件写入逻辑迁移为调用 `bat-cas-engine`。
|
||||
2. 移除固定返回值的引用计数和 GC 占位逻辑。
|
||||
3. 在 `docs/reports/CURRENT_GAPS.md` 中逐项关闭 G-002、G-003、G-004。
|
||||
1. `infrastructure/src/cas/filesystem.rs` 已迁移为调用 `bat-cas-engine`。
|
||||
2. 固定返回值的引用计数和 GC 占位逻辑已移除。
|
||||
3. `docs/reports/CURRENT_GAPS.md` 中的 G-002、G-003、G-004 已关闭。
|
||||
|
||||
@@ -0,0 +1,50 @@
|
||||
# ADR 0003: CAS 核心接口与错误边界冻结
|
||||
|
||||
**状态**:已接受
|
||||
**日期**:2026-06-28
|
||||
**关联实现**:`../../../core/src/repositories/cas_repository.rs`、`../../../crates/bat-cas-engine/src/repository.rs`、`../../../infrastructure/src/cas/filesystem.rs`
|
||||
|
||||
---
|
||||
|
||||
## 背景
|
||||
|
||||
CAS 是资源同步、资源版本共享、AssetBundle 缓存、Patch 回滚和本地对象存储的基础能力。当前阶段需要冻结 CAS V1 对外接口,避免后续 Manifest、Resource Repository 和 CLI 开发时继续改动底层边界。
|
||||
|
||||
---
|
||||
|
||||
## 决策
|
||||
|
||||
CAS V1 对外领域接口继续使用 `bat_core::repositories::cas_repository::CasRepository`,并冻结以下语义:
|
||||
|
||||
1. `store(data)` 存储对象并增加引用计数。
|
||||
2. `get(id)` 读取对象并校验 Hash。
|
||||
3. `exists(id)` 只表达对象文件存在性,不增加引用。
|
||||
4. `add_reference(id)` 增加已存在对象引用。
|
||||
5. `remove_reference(id)` 减少引用计数,引用计数不得低于 0。
|
||||
6. `get_reference_count(id)` 返回持久化引用计数。
|
||||
7. `gc()` 删除引用计数为 0 的对象及其元数据。
|
||||
8. `store_from_file()` 和 `export_to_file()` 保留为领域接口默认便捷方法。
|
||||
|
||||
---
|
||||
|
||||
## 错误映射
|
||||
|
||||
`bat-cas-engine::CasError` 在 infrastructure 适配层映射为 `bat_core::Error`:
|
||||
|
||||
1. `Io` -> `Error::Io`
|
||||
2. `ObjectNotFound` -> `Error::NotFound`
|
||||
3. `HashMismatch` -> `Error::InvalidArgument`
|
||||
4. `InvalidHash` -> `Error::InvalidArgument`
|
||||
5. `ReferenceUnderflow` -> `Error::InvalidArgument`
|
||||
6. `Database` -> `Error::Other`
|
||||
7. `Other` -> `Error::Other`
|
||||
|
||||
该映射保证应用层可以只依赖 `bat-core` 的错误边界,不直接泄漏 CAS 引擎内部错误类型。
|
||||
|
||||
---
|
||||
|
||||
## 后果
|
||||
|
||||
1. 后续 Go CLI/API 只能通过领域仓储接口或稳定 FFI 调用 CAS,不直接依赖对象目录结构。
|
||||
2. CAS V1 后续可以替换元数据后端,但不能改变领域接口语义。
|
||||
3. 如果以后需要 dry-run GC、批量引用更新或流式存储,应作为新接口扩展,不破坏当前 trait。
|
||||
@@ -84,10 +84,11 @@ git check-ignore -v Cargo.lock CLAUDE.md
|
||||
|
||||
## 5. 下一阶段入口
|
||||
|
||||
基线建立后,下一阶段只推进两件事:
|
||||
CAS V1 完成后,下一阶段优先推进:
|
||||
|
||||
1. 冻结核心接口。
|
||||
2. 完成 CAS V1。
|
||||
1. Manifest 真实解析。
|
||||
2. Go CLI 的 `doctor` 和基础命令框架。
|
||||
3. Resource Repository 持久化 schema。
|
||||
|
||||
优先阅读:
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
限制:
|
||||
|
||||
- 原项目历史未恢复。
|
||||
- 需要创建首次基线提交。
|
||||
- 后续历史从当前基线提交开始。
|
||||
|
||||
验收:
|
||||
|
||||
@@ -36,28 +36,30 @@
|
||||
|
||||
### G-002:CAS 有两套实现边界
|
||||
|
||||
现象:
|
||||
状态:**已关闭**
|
||||
|
||||
原现象:
|
||||
|
||||
- `crates/bat-cas-engine/src/storage.rs` 有文件系统存储。
|
||||
- `infrastructure/src/cas/filesystem.rs` 也实现了文件系统 CAS repository。
|
||||
|
||||
影响:
|
||||
处理结果:
|
||||
|
||||
- 后续引用计数、GC、元数据会重复实现。
|
||||
- FFI/Go/领域仓储边界容易混乱。
|
||||
- `crates/bat-cas-engine` 新增 `repository` 组合层,成为 CAS 核心实现。
|
||||
- `infrastructure/src/cas/filesystem.rs` 已改为 `bat-core::CasRepository` 适配层。
|
||||
- infrastructure 不再直接写对象文件,不再维护自己的引用计数逻辑。
|
||||
|
||||
建议:
|
||||
验收证据:
|
||||
|
||||
- `bat-cas-engine` 负责核心 CAS 引擎。
|
||||
- `infrastructure` 只负责把核心引擎适配到 `bat-core::repositories::CasRepository`。
|
||||
|
||||
验收:
|
||||
|
||||
- 文件写入、读取、引用计数、GC 只在一个核心实现中维护。
|
||||
- `bat-cas-engine::repository::FileSystemCasRepository`
|
||||
- `bat_infrastructure::FileSystemCasRepository`
|
||||
- `cargo test --workspace`
|
||||
|
||||
### G-003:CAS 引用计数和 GC 未实现
|
||||
|
||||
现象:
|
||||
状态:**已关闭**
|
||||
|
||||
原现象:
|
||||
|
||||
- `FileSystemCasRepository::add_reference` 返回固定 `1`。
|
||||
- `remove_reference` 返回固定 `0`。
|
||||
@@ -65,19 +67,15 @@
|
||||
- `gc` 返回固定 `0`。
|
||||
- `crates/bat-cas-engine/src/refcount.rs` 是占位。
|
||||
|
||||
影响:
|
||||
处理结果:
|
||||
|
||||
- 无法安全删除对象。
|
||||
- 无法支持多版本共享和垃圾回收。
|
||||
- 不符合项目最终目标。
|
||||
- `crates/bat-cas-engine/src/refcount.rs` 使用 SQLite 保存对象元数据和引用计数。
|
||||
- `store()` 会存储对象并增加引用计数。
|
||||
- `add_reference()`、`remove_reference()`、`get_reference_count()` 已持久化。
|
||||
- `gc()` 删除引用计数为 0 的对象和元数据。
|
||||
- `gc_candidates()` 提供 dry-run 能力。
|
||||
|
||||
建议:
|
||||
|
||||
- 设计 `ObjectMetadata`、`ReferenceRecord`、`GcPolicy`。
|
||||
- 使用事务化元数据后端。
|
||||
- GC 必须包含安全窗口和 dry-run。
|
||||
|
||||
验收:
|
||||
验收证据:
|
||||
|
||||
- 引用计数增减有持久化测试。
|
||||
- GC 不删除仍被引用对象。
|
||||
@@ -89,17 +87,21 @@
|
||||
|
||||
### G-004:CAS 写入不是生产级原子流程
|
||||
|
||||
现象:
|
||||
状态:**已关闭**
|
||||
|
||||
原现象:
|
||||
|
||||
- 当前写入直接写目标路径。
|
||||
- 缺少临时文件、fsync、原子 rename、并发冲突处理。
|
||||
|
||||
影响:
|
||||
处理结果:
|
||||
|
||||
- 写入中断可能留下损坏对象。
|
||||
- 多进程/多任务并发写入存在竞态。
|
||||
- `FileSystemStorage::put()` 使用临时文件写入、文件 sync、原子 rename、目录 sync。
|
||||
- 读取对象时强制 Hash 校验。
|
||||
- 并发写入相同内容只保留一个对象,引用计数按调用次数递增。
|
||||
- 损坏对象读取返回 `HashMismatch`。
|
||||
|
||||
验收:
|
||||
验收证据:
|
||||
|
||||
- 写入失败不会留下可见半成品对象。
|
||||
- 并发写入相同内容只产生一个对象。
|
||||
@@ -297,14 +299,11 @@
|
||||
|
||||
## 6. 当前关闭顺序建议
|
||||
|
||||
1. G-002
|
||||
2. G-003
|
||||
3. G-004
|
||||
4. G-007
|
||||
5. G-008
|
||||
6. G-005
|
||||
7. G-011
|
||||
8. G-012
|
||||
9. G-006
|
||||
1. G-007
|
||||
2. G-008
|
||||
3. G-005
|
||||
4. G-011
|
||||
5. G-012
|
||||
6. G-006
|
||||
|
||||
这个顺序优先建立可信工作区和基础存储,再推进资源同步、解析、翻译和补丁。
|
||||
|
||||
Reference in New Issue
Block a user