MapStruct 1.5.5与Lombok的区别
下文笔者讲述MapStruct 1.5.5与Lombok的区别,如下所示
MapStruct 1.5.5与Lombok区别说明
| 维度 | MapStruct 1.5.5 | Lombok |
| 核心目标 | 解决不同对象(如 Entity/DTO)的字段映射 | 简化 Java 类编写,消除模板代码(get/set 等) |
| 工作阶段 | 编译期生成映射实现类(如 UserMapperImpl) | 编译期生成类的模板方法(get/set/构造器等) |
| 作用对象 | 映射接口(@Mapper 注解的接口) | 实体类/DTO 等普通 Java 类(@Data/@Getter 等) |
| 核心能力 | 字段映射(名称/类型转换)、集合映射、自定义转换 | 生成 getter/setter、构造器、toString、builder 等 |
| 代码生成逻辑 | 生成类型安全的映射代码(new 对象 + set 字段) | 生成类的基础方法(不创建新对象) |
| 依赖协作 | 可依赖 Lombok 生成的 get/set 完成映射 | 独立工作,也可被 MapStruct 依赖 |
MapStruct 1.5.5与Lombok定位说明
- Lombok:
是“代码简化工具”,核心解决的是“Java 类模板代码冗余”的问题。
如你写一个 `User` 类,不用手动写 `getId()`、`setId()`、`toString()` 这些重复的代码,
加个 `@Data` 注解,Lombok 就会在编译期自动生成这些方法。
它的作用是“简化单个类的编写”,不涉及多个类之间的交互。
例(Lombok 核心用法):
import lombok.Data;
// Lombok 注解:
//编译期生成 get/set/toString/equals/hashCode 等
@Data
public class User {
private Long id;
private String userName;
private Integer age;
// 无需手动写 get/set,Lombok 自动生成
}
- MapStruct 1.5.5:
是“对象映射工具
核心解决的是“不同对象之间字段赋值”的问题。
如
你需要把 `User`(Entity)转成 `UserDTO`(DTO),
不用手动写 `userDTO.setName(user.getUserName())` 这类代码,
定义一个映射接口,
MapStruct 会在编译期生成完整的映射实现类,
自动完成字段赋值(包括名称/类型不一致的转换)。
它的作用是“连接两个不同的类”,
依赖类的 get/set 方法(可由 Lombok 生成)完成映射。
例(MapStruct 核心用法)
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
@Mapper(componentModel = "spring")
public interface UserMapper {
// MapStruct 生成实现类,自动把 user.userName 映射到 userDTO.name
@Mapping(source = "userName", target = "name")
UserDTO userToUserDTO(User user);
}
MapStruct 1.5.5与Lombok代码生成本质
- Lombok:
生成的是"类的内部方法"
如
`User` 类生成 `getUserName()`、`setUserName()`,
这些方法属于 `User` 类本身,
目的是让你能便捷地操作这个类的字段。
编译后你能在 `target/classes` 里
看到 `User.class` 包含这些方法,
但不会生成新的类。
- MapStruct 1.5.5:
生成的是“独立的映射实现类”,
如
定义 `UserMapper` 接口,
MapStruct 会生成 `UserMapperImpl` 类,
这个类里包含完整的映射逻辑:
// MapStruct 自动生成的 UserMapperImpl 核心代码(简化版)
public class UserMapperImpl implements UserMapper {
@Override
public UserDTO userToUserDTO(User user) {
if (user == null) {
return null;
}
UserDTO userDTO = new UserDTO();
userDTO.setName(user.getUserName()); // 对应 @Mapping 的字段映射
userDTO.setId(user.getId());
userDTO.setAge(user.getAge());
return userDTO;
}
}
这个实现类是全新的
目的是完成两个类之间的转换,
而非简化单个类。
MapStruct 1.5.5与Lombok代码依赖关系
二者不是替代关系,而是互补关系:
- MapStruct 本身不关心 get/set 是手动写的还是 Lombok 生成的,
它只需要能调用到这些方法即可;
- 实际开发中,通常先用 Lombok 简化 Entity/DTO 的编写(省去 get/set),
再用 MapStruct 基于这些类完成映射,
二者协同工作效率最高
4. 典型使用场景
- Lombok 适用场景:
- 编写 Entity、DTO、VO 等类时,
消除 get/set/toString 等模板代码;
- 快速生成构造器(@NoArgsConstructor/@AllArgsConstructor)、
建造者模式(@Builder)
- 简化日志声明(@Slf4j)
- MapStruct 1.5.5 适用场景:
- Entity ↔ DTO/VO 的转换
(如 Controller 层接收 DTO 转 Entity 入库,Service 层 Entity 转 VO 返回)
- 字段名称不一致(如 userName → name)、类型不一致(LocalDateTime → String)转换;
- 集合映射(如 list<User> → List<UserDTO>);
- 自定义复杂的映射逻辑(如多源对象映射到一个目标对象)。
二者协同工作完整逻辑
// 1. Lombok 简化 User 类编写(生成 get/set)
@Data
public class User {
private Long id;
private String userName;
private Integer age;
}
// 2. Lombok 简化 UserDTO 类编写
@Data
public class UserDTO {
private Long id;
private String name; // 字段名和 User 不一致
private Integer age;
}
// 3. MapStruct 定义映射规则(依赖 Lombok 生成的 get/set)
@Mapper(componentModel = "spring")
public interface UserMapper {
@Mapping(source = "userName", target = "name")
UserDTO userToUserDTO(User user);
}
// 4. 使用
@Autowired
private UserMapper userMapper;
public void test() {
User user = new User();
user.setId(1L);
user.setUserName("张三");
user.setAge(25);
// MapStruct 调用 Lombok 生成的 get 方法,完成映射
UserDTO dto = userMapper.userToUserDTO(user);
System.out.println(dto.getName()); // 输出:张三
}
总结说明
1. 定位不同:Lombok 是“类内简化工具”,
消除单个类的模板代码;
MapStruct 是“类间映射工具”,
解决不同类的字段转换;
2. 生成内容不同:
Lombok 生成类的基础方法(get/set 等)
MapStruct 生成独立的映射实现类;
3. 关系不同:二者互补而非替代,
实际开发中常协同使用
Lombok 简化类编写,
MapStruct 基于这些类完成映射。
版权声明
本文仅代表作者观点,不代表本站立场。
本文系作者授权发表,未经许可,不得转载。


