找回密码
立即注册
搜索
热搜: Java Python Linux Go
发回帖 发新帖

373

积分

0

好友

49

主题
发表于 2025-11-28 00:05:55 | 查看: 24| 回复: 0

Spring Boot项目中,常见一种危险的写法:Controller直接接收Entity对象,返回的也是Entity。前端修改一个字段,Entity就得跟着改;数据库调整一列,所有接口都可能报错。

这种写法看似快捷,实则将后续维护成本拉满。一旦实体对象与数据库、接口强绑定,业务稍复杂,系统就会陷入"牵一发而动全身"的困境。

本文通过直观方式阐述Entity、DTO、VO在企业项目中的角色与边界,并提供一套可落地的模型结构,帮助项目保持干净、稳定与可维护。

图片

1 为什么不能让Entity到处乱用?

许多Spring Boot初学者会这样编写代码:

@PostMapping("/saveUser")
public User save(@RequestBody User user) {
    return userService.save(user);
}

表面看似合理,实则问题重重:

1. Entity映射数据库结构,变动影响全局

数据库字段变更 → Entity随之改变 → 所有接口、序列化、校验逻辑都需调整

业务逻辑被数据库架构直接制约。

2. Entity常包含敏感字段

例如password、status、createTime等字段,直接返回前端存在安全隐患。

3. Entity非接口模型或业务对象

它仅是"数据库行的映射"。接口有特定需求,业务有独立表达,与Entity无必然关联。

Entity不应承担DTO、VO、BO的职责。

图片

2 DTO专用于请求接收,非万能容器

DTO(Data Transfer Object)作为接口层数据模型,仅负责:

  • 接收前端传入数据
  • 字段精确对应接口需求
  • 通过校验注解确保输入合法性

DTO特征:

  1. 字段精简、目标明确
  2. 不包含数据库无关信息
  3. 不参与业务逻辑处理
  4. 校验注解应加在DTO而非Entity上

示例:

@Data
public class UserCreateDTO {
    @NotBlank
    private String username;
    @NotBlank
    private String password;
    @Size(max = 50)
    private String nickname;
}

DTO核心目标:确保接口入参准确、简洁、可控。

图片

3 VO用于数据返回,非数据库字段复制

VO(View Object)是"接口返回前端的展示模型"。

它不关注数据库结构,只考虑前端展示需求

例如用户详情页,前端可能需要:

  • id
  • nickname
  • avatar
  • age
  • 脱敏后的location

对应VO设计:

@Data
public class UserDetailVO {
    private Long id;
    private String nickname;
    private String avatar;
    private Integer age;
    private String location;
}

注意要点:

  1. 返回字段按业务展示需求组织
  2. 支持字段组合、格式化、脱敏处理
  3. 独立于数据库结构,可随前端需求灵活调整

VO是独立的展示层模型,非Entity复制品。

图片

4 Entity专注数据库表结构映射

Entity是数据库结构在代码中的直接映射,不承担业务或接口职责。

特征如下:

  • 字段与数据库列严格对应
  • 不直接暴露给前端
  • 不用于接收请求参数
  • 逻辑上代表"单条数据记录"
  • 常用注解:@TableName、@TableId、@TableField

示例:

@Data
@TableName("user")
public class UserEntity {
    @TableId
    private Long id;
    private String username;
    private String password;
    private String nickname;
    private Integer age;
    private String address;
    private String phone;
}

Entity不应处理DTO/VO的任务。

图片

5 企业级对象流转模型

标准请求链路如下:

图片

流程解析:

1. 输入仅通过DTO

防止数据库字段暴露,确保校验逻辑统一

2. 业务围绕Entity展开

Service层使用Entity作为核心业务数据模型

3. 输出仅通过VO

返回数据结构与数据库解耦

彻底避免一比一映射导致的混乱。

图片

6 企业项目为何必须分层使用DTO/Entity/VO?

1. 提升可维护性

前端字段变更只需调整DTO或VO,不影响数据库结构

2. 增强可扩展性

同一Entity可对应多个DTO和VO,适应不同场景

3. 加强安全性

敏感字段不会随Entity原样返回

4. 优化代码整洁度

Controller专注请求处理、Service专注业务逻辑、Entity专注数据映射

职责清晰,阅读成本显著降低。

图片

7 实际项目常见错误写法

❌ 错误1:DTO、VO、Entity混用

导致字段归属模糊,职责混乱

❌ 错误2:VO与Entity完全一致

丧失返回模型的独立价值

❌ 错误3:新业务直接扩展Entity字段

最终Entity成为无法维护的"万能类"

❌ 错误4:DTO未经校验直接透传

使Controller层漏洞百出

这些问题正是Service层逐渐混乱的根源。

图片

总结

Spring Boot对象模型并非越简越好,关键在于保持边界清晰、职责独立

  • DTO → 接口输入
  • VO → 接口输出
  • Entity → 数据库映射

三者各司其职,系统结构自然清晰,可维护性大幅提升。

遵循这套对象治理规则,即使项目规模扩大,代码仍能保持稳定与清晰。




上一篇:摄像头钓鱼攻击实战:CamPhish与ngrok工具使用指南
下一篇:Linux分区表原理与实战:MBR/GPT深度解析与性能优化
您需要登录后才可以回帖 登录 | 立即注册

手机版|小黑屋|网站地图|云栈社区(YunPan.Plus) ( 苏ICP备2022046150号-2 )

GMT+8, 2025-12-7 03:44 , Processed in 0.074285 second(s), 39 queries , Gzip On.

Powered by Discuz! X3.5

© 2025-2025 CloudStack.

快速回复 返回顶部 返回列表