# 档案API **本文引用的文件** - [routes.go](file://internal/handler/routes.go) - [profile_handler.go](file://internal/handler/profile_handler.go) - [profile_service.go](file://internal/service/profile_service.go) - [profile_repository.go](file://internal/repository/profile_repository.go) - [common.go](file://internal/types/common.go) - [response.go](file://internal/model/response.go) - [profile.go](file://internal/model/profile.go) - [texture.go](file://internal/model/texture.go) - [texture_service.go](file://internal/service/texture_service.go) - [texture_repository.go](file://internal/repository/texture_repository.go) - [postgres.go](file://pkg/database/postgres.go) ## 目录 1. [简介](#简介) 2. [项目结构](#项目结构) 3. [核心组件](#核心组件) 4. [架构总览](#架构总览) 5. [详细组件分析](#详细组件分析) 6. [依赖分析](#依赖分析) 7. [性能考虑](#性能考虑) 8. [故障排查指南](#故障排查指南) 9. [结论](#结论) 10. [附录](#附录) ## 简介 本文件面向开发者与集成方,系统化梳理“档案API”的设计与使用方法,覆盖以下能力: - 档案的创建、查询、更新、删除与“活跃档案”设置 - 公开获取档案详情与需要认证的档案管理端点 - 档案与Minecraft用户UUID的关系、活跃档案的概念 - 档案列表的获取方式 - 完整的API使用示例,包括创建档案的请求体结构与获取档案详情的响应格式 - 档案与材质之间的关系 ## 项目结构 档案API位于路由组 `/api/v1/profile` 下,采用“公开路由 + 认证路由”的分层设计: - 公开路由:通过档案UUID获取档案详情 - 认证路由:需要携带JWT令牌,支持创建、查询列表、更新、删除、设置活跃档案 ```mermaid graph TB subgraph "路由组 /api/v1/profile" A["GET /:uuid
公开:获取档案详情"] subgraph "认证组" B["POST /
创建档案"] C["GET /
获取我的档案列表"] D["PUT /:uuid
更新档案"] E["DELETE /:uuid
删除档案"] F["POST /:uuid/activate
设置活跃档案"] end end ``` 图表来源 - [routes.go](file://internal/handler/routes.go#L63-L79) 章节来源 - [routes.go](file://internal/handler/routes.go#L63-L79) ## 核心组件 - 路由注册:集中于路由文件,定义公开与认证端点 - 处理器:profile_handler 负责鉴权、参数解析、调用服务层并返回统一响应 - 服务层:profile_service 实现业务规则(如创建档案时生成UUID与RSA私钥、设置活跃状态、权限校验等) - 仓储层:profile_repository 封装数据库操作(增删改查、统计、事务) - 类型与模型:types 中定义请求/响应结构;model 中定义档案与材质模型及响应结构 - 数据库:通过GORM连接PostgreSQL,统一日志与连接池配置 章节来源 - [routes.go](file://internal/handler/routes.go#L63-L79) - [profile_handler.go](file://internal/handler/profile_handler.go#L1-L399) - [profile_service.go](file://internal/service/profile_service.go#L1-L253) - [profile_repository.go](file://internal/repository/profile_repository.go#L1-L200) - [common.go](file://internal/types/common.go#L81-L207) - [response.go](file://internal/model/response.go#L1-L86) - [profile.go](file://internal/model/profile.go#L1-L64) - [texture.go](file://internal/model/texture.go#L1-L77) - [postgres.go](file://pkg/database/postgres.go#L1-L74) ## 架构总览 档案API遵循经典的三层架构:HTTP路由 -> 处理器 -> 服务 -> 仓储 -> 数据库。认证中间件确保仅持有有效令牌的用户可访问受保护端点。 ```mermaid graph TB Client["客户端"] --> R["Gin 路由
/api/v1/profile"] R --> M["认证中间件"] M --> H["处理器
profile_handler"] H --> S["服务层
profile_service"] S --> Repo["仓储层
profile_repository"] Repo --> DB["数据库
PostgreSQL(GORM)"] ``` 图表来源 - [routes.go](file://internal/handler/routes.go#L63-L79) - [profile_handler.go](file://internal/handler/profile_handler.go#L1-L399) - [profile_service.go](file://internal/service/profile_service.go#L1-L253) - [profile_repository.go](file://internal/repository/profile_repository.go#L1-L200) - [postgres.go](file://pkg/database/postgres.go#L1-L74) ## 详细组件分析 ### 路由与端点 - 公开端点 - GET /api/v1/profile/:uuid:根据UUID获取档案详情 - 认证端点 - POST /api/v1/profile:创建档案 - GET /api/v1/profile:获取当前用户的所有档案列表 - PUT /api/v1/profile/:uuid:更新档案(可更新角色名、皮肤ID、披风ID) - DELETE /api/v1/profile/:uuid:删除档案 - POST /api/v1/profile/:uuid/activate:设置活跃档案(同时将该用户其他档案设为非活跃) 章节来源 - [routes.go](file://internal/handler/routes.go#L63-L79) ### 处理器与鉴权 - 认证中间件:所有认证端点均使用认证中间件,从上下文提取user_id - 参数绑定:使用Gin的ShouldBindJSON进行请求体校验 - 统一响应:使用统一响应结构,错误码与消息标准化 章节来源 - [profile_handler.go](file://internal/handler/profile_handler.go#L1-L399) - [response.go](file://internal/model/response.go#L1-L86) ### 服务层业务规则 - 创建档案 - 校验用户存在且状态正常 - 校验角色名唯一 - 生成UUID与RSA私钥(PEM格式) - 默认设置为活跃档案,并将该用户其他档案设为非活跃 - 更新档案 - 校验档案归属(仅档案所属用户可更新) - 校验新角色名唯一 - 支持更新角色名、皮肤ID、披风ID - 删除档案 - 校验档案归属 - 设置活跃档案 - 校验档案归属 - 使用事务将该用户其他档案设为非活跃,再将目标档案设为活跃 - 同步更新最后使用时间 - 档案数量限制 - 通过服务层检查当前用户档案数量是否超过上限 章节来源 - [profile_service.go](file://internal/service/profile_service.go#L1-L253) ### 仓储层与数据库 - 查询 - FindProfileByUUID:按UUID查询并预加载皮肤与披风 - FindProfilesByUserID:按用户ID查询并预加载皮肤与披风,按创建时间倒序 - FindProfileByName:按角色名查询 - 更新 - UpdateProfile、UpdateProfileFields - 删除 - DeleteProfile(按UUID删除) - 统计 - CountProfilesByUserID - 活跃状态 - SetActiveProfile:事务内将该用户其他档案设为非活跃,再将目标档案设为活跃 - 最后使用时间 - UpdateProfileLastUsedAt 章节来源 - [profile_repository.go](file://internal/repository/profile_repository.go#L1-L200) ### 模型与类型 - 档案模型 - 字段:UUID、用户ID、角色名、皮肤ID、披风ID、活跃状态、最后使用时间、创建/更新时间 - 关联:User、Skin(Texture)、Cape(Texture) - 档案响应结构 - ProfileResponse:包含UUID、角色名、textures(皮肤/披风)、活跃状态、最后使用时间、创建时间 - ProfileTexturesData:包含SKIN与CAPE两个可选字段 - ProfileTexture:包含URL与可选metadata(如模型类型) - 请求/响应类型 - CreateProfileRequest:name(必填,1-16字符) - UpdateProfileRequest:name(可选)、skin_id(可选)、cape_id(可选) - ProfileInfo:用于列表与详情的统一返回字段 章节来源 - [profile.go](file://internal/model/profile.go#L1-L64) - [common.go](file://internal/types/common.go#L81-L207) ### 档案与材质的关系 - 档案可关联两种材质:皮肤(SkinID)与披风(CapeID) - 材质模型包含类型(SKIN/CAPE)、URL、哈希、大小、公开状态等 - 服务层与仓储层均支持对材质的创建、查询、更新、删除、收藏等操作,但这些属于独立的材质API范畴 章节来源 - [profile.go](file://internal/model/profile.go#L1-L64) - [texture.go](file://internal/model/texture.go#L1-L77) - [texture_service.go](file://internal/service/texture_service.go#L1-L252) - [texture_repository.go](file://internal/repository/texture_repository.go#L1-L232) ### API使用示例 - 创建档案 - 方法与路径:POST /api/v1/profile - 认证:需要JWT - 请求体结构(CreateProfileRequest) - name:字符串,必填,长度1-16 - 成功响应:返回ProfileInfo(包含UUID、用户ID、角色名、皮肤ID、披风ID、活跃状态、最后使用时间、创建/更新时间) - 常见错误:400(参数错误/达到档案数量上限)、401(未授权)、500(服务器错误) - 获取我的档案列表 - 方法与路径:GET /api/v1/profile - 认证:需要JWT - 成功响应:数组,元素为ProfileInfo - 获取档案详情 - 方法与路径:GET /api/v1/profile/{uuid} - 认证:公开端点,无需JWT - 成功响应:ProfileInfo - 更新档案 - 方法与路径:PUT /api/v1/profile/{uuid} - 认证:需要JWT - 请求体结构(UpdateProfileRequest) - name:字符串,可选,长度1-16 - skin_id:整数,可选 - cape_id:整数,可选 - 成功响应:ProfileInfo - 删除档案 - 方法与路径:DELETE /api/v1/profile/{uuid} - 认证:需要JWT - 成功响应:{"message":"删除成功"} - 设置活跃档案 - 方法与路径:POST /api/v1/profile/{uuid}/activate - 认证:需要JWT - 成功响应:{"message":"设置成功"} 章节来源 - [profile_handler.go](file://internal/handler/profile_handler.go#L1-L399) - [common.go](file://internal/types/common.go#L81-L207) - [response.go](file://internal/model/response.go#L1-L86) ### 活跃档案概念 - 每个用户在同一时刻只能有一个“活跃档案” - 当创建新档案或切换活跃档案时,系统会将该用户其他档案设为非活跃 - 设置活跃档案会同步更新最后使用时间 章节来源 - [profile_service.go](file://internal/service/profile_service.go#L1-L253) - [profile_repository.go](file://internal/repository/profile_repository.go#L89-L117) ### 档案列表获取方式 - 通过认证端点 GET /api/v1/profile 获取当前用户的所有档案 - 返回顺序按创建时间倒序 章节来源 - [profile_handler.go](file://internal/handler/profile_handler.go#L95-L151) - [profile_service.go](file://internal/service/profile_service.go#L83-L90) - [profile_repository.go](file://internal/repository/profile_repository.go#L44-L57) ### 档案与Minecraft用户UUID的关系 - 档案模型包含UUID字段,用于标识Minecraft角色 - 档案与用户通过user_id关联 - 公开端点通过UUID获取档案详情,不涉及用户身份 章节来源 - [profile.go](file://internal/model/profile.go#L1-L64) - [routes.go](file://internal/handler/routes.go#L63-L79) ## 依赖分析 - 路由到处理器:路由文件注册各端点,处理器负责鉴权与参数解析 - 处理器到服务:处理器调用服务层实现业务逻辑 - 服务到仓储:服务层封装业务规则并委托仓储层执行数据库操作 - 仓储到数据库:仓储层通过GORM访问PostgreSQL ```mermaid graph LR Routes["routes.go"] --> Handler["profile_handler.go"] Handler --> Service["profile_service.go"] Service --> Repo["profile_repository.go"] Repo --> DB["postgres.go"] ``` 图表来源 - [routes.go](file://internal/handler/routes.go#L63-L79) - [profile_handler.go](file://internal/handler/profile_handler.go#L1-L399) - [profile_service.go](file://internal/service/profile_service.go#L1-L253) - [profile_repository.go](file://internal/repository/profile_repository.go#L1-L200) - [postgres.go](file://pkg/database/postgres.go#L1-L74) ## 性能考虑 - 预加载策略:查询档案时预加载皮肤与披风,减少N+1查询风险 - 分页与排序:列表查询按创建时间倒序,避免全量扫描 - 事务一致性:设置活跃档案使用事务,保证原子性 - 连接池:数据库连接池配置合理,建议结合实际负载调整 章节来源 - [profile_repository.go](file://internal/repository/profile_repository.go#L19-L57) - [profile_service.go](file://internal/service/profile_service.go#L161-L188) - [postgres.go](file://pkg/database/postgres.go#L1-L74) ## 故障排查指南 - 未授权 - 现象:返回401 - 排查:确认JWT是否正确传递与有效 - 参数错误 - 现象:返回400 - 排查:检查请求体字段是否符合长度与类型要求 - 无权操作 - 现象:返回403 - 排查:确认操作的档案是否属于当前用户 - 资源不存在 - 现象:返回404 - 排查:确认UUID是否正确、档案是否被删除 - 达到上限 - 现象:返回400 - 排查:检查当前用户档案数量与系统限制 章节来源 - [profile_handler.go](file://internal/handler/profile_handler.go#L1-L399) - [response.go](file://internal/model/response.go#L1-L86) ## 结论 档案API以清晰的公开/认证分层设计,结合严格的鉴权与参数校验,提供了完整的Minecraft角色档案生命周期管理能力。通过服务层的业务规则与仓储层的事务保障,系统在一致性与扩展性方面具备良好基础。建议在生产环境中配合限流、缓存与监控进一步优化性能与稳定性。 ## 附录 ### API端点一览 - 公开 - GET /api/v1/profile/:uuid - 认证 - POST /api/v1/profile - GET /api/v1/profile - PUT /api/v1/profile/:uuid - DELETE /api/v1/profile/:uuid - POST /api/v1/profile/:uuid/activate 章节来源 - [routes.go](file://internal/handler/routes.go#L63-L79)