You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

389 lines
20 KiB

1 month ago
# 领域模型
<cite>
**本文引用的文件**
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [ResultCodeEnum.java](file://crm-base/src/main/java/com/crm/base/domain/result/ResultCodeEnum.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [PageConverter.java](file://crm-base/src/main/java/com/crm/base/utils/PageConverter.java)
- [AssertUtils.java](file://crm-base/src/main/java/com/crm/base/utils/AssertUtils.java)
- [BaseEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/BaseEntity.java)
- [OwnedEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/OwnedEntity.java)
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [BusinessErrorException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/BusinessErrorException.java)
- [MissingParameterException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/MissingParameterException.java)
- [PermissionErrorException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/PermissionErrorException.java)
- [ResourceNotExistException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/ResourceNotExistException.java)
- [LoginParam.java](file://crm-auth/src/main/java/com/crm/auth/domain/param/LoginParam.java)
- [UserInfoDTO.java](file://crm-auth/src/main/java/com/crm/auth/domain/dto/UserInfoDTO.java)
</cite>
## 目录
1. [简介](#简介)
2. [项目结构](#项目结构)
3. [核心组件](#核心组件)
4. [架构总览](#架构总览)
5. [详细组件分析](#详细组件分析)
6. [依赖关系分析](#依赖关系分析)
7. [性能考虑](#性能考虑)
8. [故障排查指南](#故障排查指南)
9. [结论](#结论)
10. [附录](#附录)
## 简介
本文件面向领域模型与数据契约,系统性说明 BaseDTO、BaseParam 的基类设计与继承关系,统一响应 Result 与分页结果 PageResult 的结构与用法,阐述 DTO 与 Param 的设计原则、字段验证规则与转换策略,并给出领域模型的扩展指导与自定义数据对象的创建规范。目标是帮助开发者在 CRM 后端项目中以一致、可维护的方式定义数据传输对象、参数对象以及统一的接口响应格式。
## 项目结构
本项目采用多模块组织,领域模型相关的基础类型集中在 crm-base 模块中,业务模块(如 crm-auth)通过引入基础模块复用这些通用能力。关键位置如下:
- 基础 DTO 与 Param:crm-base/domain/{dto,param}
- 统一响应封装:crm-base/domain/result
- 工具与转换器:crm-base/utils
- 异常与全局处理:crm-base/advice 与 crm-base/domain/exception
- 实体基类:crm-base/domain/entity
```mermaid
graph TB
subgraph "基础模块 crm-base"
A["domain/dto/BaseDTO"]
B["domain/param/BaseParam"]
C["domain/result/Result"]
D["domain/result/PageResult"]
E["utils/BeanCopyUtils"]
F["utils/PageConverter"]
G["advice/GlobalExceptionHandlerAdvice"]
H["domain/entity/BaseEntity"]
I["domain/entity/OwnedEntity"]
end
subgraph "业务模块 crm-auth"
J["domain/param/LoginParam"]
K["domain/dto/UserInfoDTO"]
end
A --> C
B --> C
D --> C
E --> A
E --> B
F --> D
G --> C
H --> I
J --> B
K --> A
```
图表来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [PageConverter.java](file://crm-base/src/main/java/com/crm/base/utils/PageConverter.java)
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [BaseEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/BaseEntity.java)
- [OwnedEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/OwnedEntity.java)
- [LoginParam.java](file://crm-auth/src/main/java/com/crm/auth/domain/param/LoginParam.java)
- [UserInfoDTO.java](file://crm-auth/src/main/java/com/crm/auth/domain/dto/UserInfoDTO.java)
章节来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [PageConverter.java](file://crm-base/src/main/java/com/crm/base/utils/PageConverter.java)
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [BaseEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/BaseEntity.java)
- [OwnedEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/OwnedEntity.java)
- [LoginParam.java](file://crm-auth/src/main/java/com/crm/auth/domain/param/LoginParam.java)
- [UserInfoDTO.java](file://crm-auth/src/main/java/com/crm/auth/domain/dto/UserInfoDTO.java)
## 核心组件
- BaseDTO:所有数据传输对象的基类,提供统一的序列化、审计或扩展字段约定,便于跨层传递数据。
- BaseParam:所有请求参数的基类,集中承载校验注解、分页与排序等通用能力,简化 Controller 入参定义。
- Result:统一响应封装,包含状态码、消息与数据体,确保前后端交互一致性。
- PageResult:分页结果封装,聚合页码、总数、列表数据等分页元信息。
- BeanCopyUtils:对象拷贝工具,用于 DTO/Param/Entity 之间的属性映射与转换。
- PageConverter:分页转换工具,将框架分页对象转换为 PageResult。
- AssertUtils:断言工具,用于快速进行参数合法性校验。
- GlobalExceptionHandlerAdvice:全局异常处理器,将业务异常转换为统一 Result。
章节来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [PageConverter.java](file://crm-base/src/main/java/com/crm/base/utils/PageConverter.java)
- [AssertUtils.java](file://crm-base/src/main/java/com/crm/base/utils/AssertUtils.java)
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
## 架构总览
下图展示了领域模型在请求链路中的角色与交互:Controller 接收 BaseParam 派生参数,经服务层处理返回 Result 或 PageResult;DTO 作为跨层数据载体,通过 BeanCopyUtils 与 Entity 相互转换。
```mermaid
sequenceDiagram
participant Client as "客户端"
participant Controller as "控制器"
participant Service as "服务层"
participant Utils as "工具类"
participant Response as "统一响应"
Client->>Controller : "HTTP 请求(BaseParam)"
Controller->>Controller : "参数校验(注解/断言)"
Controller->>Service : "调用业务方法"
Service->>Utils : "对象转换(BeanCopyUtils)"
Service-->>Controller : "业务结果(DTO/Entity)"
Controller->>Response : "封装为Result/PageResult"
Response-->>Client : "JSON 响应"
```
图表来源
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
## 详细组件分析
### BaseDTO 与 BaseParam 基类设计
- BaseDTO
- 职责:作为数据传输对象的基类,统一序列化行为与扩展点,避免在各 DTO 中重复定义公共字段。
- 设计要点:仅暴露必要字段,保持不可变或最小可变性;避免携带持久化细节。
- BaseParam
- 职责:作为请求参数的基类,集中声明校验注解、分页与排序等通用能力。
- 设计要点:与 Controller 入参解耦,便于单元测试与 Mock;支持可选字段与默认值。
```mermaid
classDiagram
class BaseDTO {
+ "公共字段与行为"
}
class BaseParam {
+ "公共字段与行为"
}
class UserInfoDTO
class LoginParam
UserInfoDTO --|> BaseDTO : "继承"
LoginParam --|> BaseParam : "继承"
```
图表来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [UserInfoDTO.java](file://crm-auth/src/main/java/com/crm/auth/domain/dto/UserInfoDTO.java)
- [LoginParam.java](file://crm-auth/src/main/java/com/crm/auth/domain/param/LoginParam.java)
章节来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [UserInfoDTO.java](file://crm-auth/src/main/java/com/crm/auth/domain/dto/UserInfoDTO.java)
- [LoginParam.java](file://crm-auth/src/main/java/com/crm/auth/domain/param/LoginParam.java)
### Result 与 PageResult 统一响应封装
- Result
- 结构:包含状态码、消息、数据体三部分,保证接口返回结构一致。
- 使用:成功路径返回 data,失败路径设置错误码与消息,由全局异常处理器统一转换。
- PageResult
- 结构:包含当前页、每页大小、总记录数、总页数、数据列表等分页元信息。
- 使用:服务层返回分页数据后,通过 PageConverter 转换为 PageResult。
```mermaid
classDiagram
class Result {
+ "状态码"
+ "消息"
+ "数据体"
}
class PageResult {
+ "当前页"
+ "每页大小"
+ "总记录数"
+ "总页数"
+ "数据列表"
}
class ResultCodeEnum {
+ "枚举定义"
}
PageResult --> Result : "引用"
Result --> ResultCodeEnum : "使用"
```
图表来源
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [ResultCodeEnum.java](file://crm-base/src/main/java/com/crm/base/domain/result/ResultCodeEnum.java)
章节来源
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [ResultCodeEnum.java](file://crm-base/src/main/java/com/crm/base/domain/result/ResultCodeEnum.java)
### DTO/Param 设计原则与字段验证规则
- 设计原则
- 单一职责:DTO 仅承载传输所需字段,Param 仅承载入参与校验。
- 最小暴露:对外只暴露必要字段,避免泄露内部实现细节。
- 可组合:通过继承 BaseDTO/BaseParam 复用公共能力。
- 字段验证规则
- 优先使用注解式校验(如非空、长度、格式),结合 AssertUtils 进行业务级断言。
- 对复杂校验逻辑在服务层集中处理,保持 Controller 简洁。
- 转换策略
- 使用 BeanCopyUtils 完成 DTO/Param/Entity 之间的属性映射。
- 对于复杂映射场景,可在服务层编写专用转换器,避免在 DTO/Param 中耦合业务逻辑。
```mermaid
flowchart TD
Start(["开始"]) --> Validate["参数校验(注解/断言)"]
Validate --> Valid{"校验通过?"}
Valid --> |否| ReturnError["返回错误Result"]
Valid --> |是| Convert["对象转换(BeanCopyUtils)"]
Convert --> Business["执行业务逻辑"]
Business --> BuildResult["构建Result/PageResult"]
BuildResult --> End(["结束"])
ReturnError --> End
```
图表来源
- [AssertUtils.java](file://crm-base/src/main/java/com/crm/base/utils/AssertUtils.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
章节来源
- [AssertUtils.java](file://crm-base/src/main/java/com/crm/base/utils/AssertUtils.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
### 领域模型扩展指导与自定义数据对象规范
- 扩展 BaseDTO/BaseParam
- 新增 DTO:继承 BaseDTO,仅添加必要字段,保持不可变性。
- 新增 Param:继承 BaseParam,集中声明校验注解,必要时提供默认值。
- 自定义数据对象
- 命名规范:以业务语义命名,避免技术实现词汇。
- 字段类型:优先使用标准类型与枚举,减少歧义。
- 序列化:如需控制 JSON 输出,仅在 DTO 上标注,不在 Param 上标注。
- 与实体的关系
- BaseEntity/OwenedEntity 作为持久化基类,DTO/Param 不应直接继承实体基类。
- 通过 BeanCopyUtils 进行单向或双向转换,保持边界清晰。
```mermaid
classDiagram
class BaseEntity {
+ "公共持久化字段"
}
class OwnedEntity {
+ "数据归属字段"
}
class CustomDTO
class CustomParam
OwnedEntity --|> BaseEntity : "继承"
CustomDTO --|> BaseDTO : "继承"
CustomParam --|> BaseParam : "继承"
```
图表来源
- [BaseEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/BaseEntity.java)
- [OwnedEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/OwnedEntity.java)
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
章节来源
- [BaseEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/BaseEntity.java)
- [OwnedEntity.java](file://crm-base/src/main/java/com/crm/base/domain/entity/OwnedEntity.java)
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
## 依赖关系分析
- 组件内聚与耦合
- BaseDTO/BaseParam 低耦合,仅依赖基础类型与工具类。
- Result/PageResult 被各层广泛引用,需保持稳定。
- BeanCopyUtils/PageConverter 为横切工具,降低转换复杂度。
- 外部依赖
- 全局异常处理器与 Result 配合,确保错误路径一致。
- 业务模块通过继承 BaseDTO/BaseParam 复用能力。
```mermaid
graph LR
BaseDTO --> BeanCopyUtils
BaseParam --> BeanCopyUtils
PageResult --> PageConverter
GlobalExceptionHandlerAdvice --> Result
Result --> ResultCodeEnum
```
图表来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [PageConverter.java](file://crm-base/src/main/java/com/crm/base/utils/PageConverter.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [ResultCodeEnum.java](file://crm-base/src/main/java/com/crm/base/domain/result/ResultCodeEnum.java)
章节来源
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [BeanCopyUtils.java](file://crm-base/src/main/java/com/crm/base/utils/BeanCopyUtils.java)
- [PageConverter.java](file://crm-base/src/main/java/com/crm/base/utils/PageConverter.java)
- [PageResult.java](file://crm-base/src/main/java/com/crm/base/domain/result/PageResult.java)
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [ResultCodeEnum.java](file://crm-base/src/main/java/com/crm/base/domain/result/ResultCodeEnum.java)
## 性能考虑
- 对象转换
- 使用 BeanCopyUtils 批量转换,避免逐字段赋值带来的样板代码与潜在性能损耗。
- 对高频转换场景,可缓存映射配置以减少反射开销。
- 分页查询
- 通过 PageConverter 将数据库分页结果转换为 PageResult,避免全量加载。
- 合理设置每页大小,避免过大导致内存压力。
- 响应封装
- Result/PageResult 尽量轻量,避免在响应中包含冗余字段。
- 对大对象返回时,考虑按需字段选择与延迟加载。
[本节为通用性能建议,不直接分析具体文件]
## 故障排查指南
- 常见异常
- 业务异常:BusinessErrorException,表示业务规则不满足。
- 参数缺失:MissingParameterException,表示必填参数未传入。
- 权限异常:PermissionErrorException,表示权限不足。
- 资源不存在:ResourceNotExistException,表示目标资源不存在。
- 全局处理
- GlobalExceptionHandlerAdvice 捕获上述异常并转换为统一 Result,确保前端一致体验。
- 调试建议
- 在 Controller 层打印入参与关键中间结果。
- 使用 AssertUtils 快速定位参数问题。
- 检查 ResultCodeEnum 的状态码是否与前端约定一致。
章节来源
- [GlobalExceptionHandlerAdvice.java](file://crm-base/src/main/java/com/crm/base/advice/GlobalExceptionHandlerAdvice.java)
- [BusinessErrorException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/BusinessErrorException.java)
- [MissingParameterException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/MissingParameterException.java)
- [PermissionErrorException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/PermissionErrorException.java)
- [ResourceNotExistException.java](file://crm-base/src/main/java/com/crm/base/domain/exception/ResourceNotExistException.java)
- [Result.java](file://crm-base/src/main/java/com/crm/base/domain/result/Result.java)
- [ResultCodeEnum.java](file://crm-base/src/main/java/com/crm/base/domain/result/ResultCodeEnum.java)
## 结论
通过 BaseDTO/BaseParam 的基类抽象、Result/PageResult 的统一封装,以及 BeanCopyUtils/PageConverter 的工具支撑,项目在领域模型层面实现了高内聚、低耦合与一致的交互契约。遵循本文的设计原则与扩展规范,可有效提升代码可维护性与团队协作效率。
[本节为总结性内容,不直接分析具体文件]
## 附录
- 最佳实践清单
- DTO/Param 严格分离,避免混用。
- 校验优先注解,复杂逻辑下沉至服务层。
- 转换统一使用工具类,禁止手写样板代码。
- 异常统一抛出并由全局处理器收敛。
- 参考示例
- 登录参数:LoginParam 继承 BaseParam,集中声明校验注解。
- 用户信息:UserInfoDTO 继承 BaseDTO,仅暴露必要字段。
章节来源
- [LoginParam.java](file://crm-auth/src/main/java/com/crm/auth/domain/param/LoginParam.java)
- [UserInfoDTO.java](file://crm-auth/src/main/java/com/crm/auth/domain/dto/UserInfoDTO.java)
- [BaseParam.java](file://crm-base/src/main/java/com/crm/base/domain/param/BaseParam.java)
- [BaseDTO.java](file://crm-base/src/main/java/com/crm/base/domain/dto/BaseDTO.java)