# P0-7: IResourceService 需求详细文档 ## 对齐说明 本文档以 `docs/requirements/p0-requirements-set.md` 为准。P0 资源系统包含引用计数和资源组,因为它直接影响 Feature 释放正确性;但 P0 只实现 Addressables 默认后端,其他后端通过插件扩展。 ## 目标 提供异步资源加载、同 key 并发合并、引用计数和资源组释放能力。 ## 接口 ```csharp public interface IResourceService { Task> LoadAsync( string key, CancellationToken cancellationToken) where T : class; IResourceGroup CreateGroup(); } public interface IResourceHandle : IDisposable where T : class { string Key { get; } T Asset { get; } bool IsDisposed { get; } } public interface IResourceGroup : IDisposable { void Add(IResourceHandle handle) where T : class; int Count { get; } } ``` ## 行为规则 - `LoadAsync` 加载失败时抛异常,异常包含 key 和后端类型。 - 同 key 同类型并发加载只触发一次底层加载。 - 每次 `LoadAsync` 返回独立 handle。 - 每个 handle Dispose 时引用计数减一。 - 最后一个 handle Dispose 时释放底层资源。 - `IResourceGroup.Dispose` 释放组内所有 handle。 - 重复 Dispose 不抛异常。 - Group 重复 Add 同一个 handle 时忽略。 - Dispose 后访问 `Asset` 的行为必须固定为返回 null。 ## 默认后端 P0 默认只支持 Addressables。 ```text IResourceService └── AddressablesResourceBackend ``` ## 暂不做 - Resources 后端。 - AssetBundle 后端。 - YooAsset 后端。 - 资源预热。 - 下载进度回调。 - 资源优先级。 - 资源版本管理。 - 编辑器资源扫描和分析工具。 ## 扩展方向 P1/P2 通过后端接口扩展: ```csharp public interface IResourceBackend { Task LoadAsync(string key, CancellationToken cancellationToken) where T : class; void Release(string key, object asset); } ``` ## 验收标准 | # | 标准 | 通过条件 | |---|------|---------| | 1 | 正常加载 | LoadAsync 返回 handle,Asset 可用 | | 2 | 加载失败 | 不存在 key 抛异常并包含 key | | 3 | 引用计数 | 同 key 加载两次,最后一个 handle Dispose 后才释放底层资源 | | 4 | 并发合并 | 同 key 并发 LoadAsync 只触发一次底层加载 | | 5 | Group 释放 | Group Dispose 后组内 handle 全部释放 | | 6 | 重复 Dispose | handle/group 重复 Dispose 不抛异常 | | 7 | Dispose 后 Asset | 返回 null | | 8 | 取消加载 | CancellationToken 取消时抛 `OperationCanceledException` | ## 依赖关系 ```text IResourceService ├── Addressables ├── CancellationToken └── 被 Feature / UIManager / AudioService 依赖 ```