对外API设计应隐藏内部核心实体,通过DTO或命令/查询对象定义清晰契约,禁止Order、User等实体跨层泄漏,所有转换集中于防腐层,用模块化包结构和静态检查强化边界。

在对外 API 设计中隐藏内部核心实体,关键不是“不让别人看到类”,而是切断外部对核心实体的直接依赖——让调用方只能通过你定义的契约交互,无法触碰、构造、修改甚至感知到领域模型的存在。
用接口抽象业务意图,而非暴露实体
对外 API 的入参和返回值,必须是语义清晰、职责单一的 DTO 或命令/查询对象,而不是 Order、User 这类核心聚合根或实体类。例如:
- 提供
OrderService.submit(PlaceOrderCommand),而不是submit(Order order) - 返回
OrderConfirmation(含订单号、时间、状态),而非整个Order实体 - 所有字段命名使用本上下文语言(如
shippingStatus),不照搬数据库字段名或第三方系统字段(如logistics_code)
禁止核心实体跨层泄漏
一旦发现以下情况,说明封装已失效:
- Controller 层方法签名中出现
public ResponseEntity<User> getUser(...) - DTO 类里嵌套了
private final com.xxx.domain.User user; - JSON 序列化时直接返回
@RequestBody User,且未做脱敏或裁剪
修复方式:所有出入口都走专用 DTO,用 MapStruct 或手动 copy 构建,确保核心实体生命周期严格限定在领域层内。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
立即学习“Java免费学习笔记(深入)”;
用模块系统或包结构强化边界
借助 Java 9+ 模块系统或约定式包结构,物理隔离核心实体:
- 将核心实体放在
com.example.order.domain包下,且不导出该包(module-info.java中只exports com.example.order.api;) - 若未用 JPMS,至少按包命名规范约束:
domain(仅限内部)、api(对外契约)、infrastructure(技术实现)分层明确 - 配合 IDE 或静态检查工具(如 ArchUnit),禁止
api包下的类 importdomain包中的实体
把转换逻辑收束到防腐层或适配器
内外模型转换不能散落在 Controller 或 Service 中,而应集中到 ACL(防腐层)或专门的 Adapter:
- Controller 只接收
PlaceOrderRequest,调用orderApplicationService.place(...) - Application Service 内部通过
orderMapper.toDomain(request)转为Order,处理完再转回OrderConfirmation - Mapper 类不暴露核心实体构造细节,也不允许外部 new 它;其构造逻辑(如 ID 生成、状态初始化)全部封装在 domain 层

















