在JAVA项目开发过程中,时常会涉及到对象间属性值拷贝,这种场景有多个框架或者技术可以实现,比如Spring和Apache给我们提供了BeatUtils工具,其实现机制是通过反射机制。
这里我们介绍另一个框架MapStruct来实现。
代码demo
- pom 引入
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<mapstruct.version>1.3.1.Final</mapstruct.version>
</properties>
<dependencies>
<dependency>
<groupId>org.mapstruct</groupId>
<artifactId>mapstruct</artifactId>
<version>${mapstruct.version}</version>
</dependency>
<dependency>
<groupId>org.mapstruct</groupId>
<artifactId>mapstruct-jdk8</artifactId>
<version>${mapstruct.version}</version>
</dependency>
<dependency>
<groupId>org.mapstruct</groupId>
<artifactId>mapstruct-processor</artifactId>
<version>${mapstruct.version}</version>
</dependency>
</dependencies>
- 新建两个pojo
package com.xx.mapstruct;
import lombok.Data;
@Data
public class Src {
private String name;
}
package com.xx.mapstruct;
import lombok.Data;
@Data
public class Target {
private String name;
}
- 新建一个转换接口 DemoMap,里面代码大致如下:
package com.xx.mapstruct;
import org.mapstruct.Mapper;
import org.mapstruct.factory.Mappers;
@Mapper
public interface DemoMap {
// @A
DemoMap CAR_MAP = Mappers.getMapper(DemoMap.class);
// @B
Target tar(Src src);
}
@A: 通过Mappers来创建一个DemoMap的实例A,该实例主要用处在于供外部代码提供属性复制的功能;
@B:我们看接口里定义了一个tar方法,我们根据自己的需求定义入参和出参数,外部代码获得实例A后可以调用该方法进行对象间属性复制
- 测试类
package com.xx;
import com.xx.mapstruct.DemoMap;
import com.xx.mapstruct.Src;
import com.xx.mapstruct.Target;
import org.junit.Test;
public class MapStructTest {
@Test
public void test01() {
Src src = new Src();
src.setName("ppp");
Target tar = DemoMap.CAR_MAP.tar(src);
System.out.println(tar.getName());
}
}
- 测试结果
指定源属性与目标属性
上面只是一个简单的属性复制demo,默认在两个属性名称一样的两个属性间复制;如果两个对象间的属性名称不一致,则需要手动指定;
- 新建一个pojo
package com.xx.mapstruct;
import lombok.Data;
@Data
public class Target2 {
private String name2;
}
- 新增转换方法,这里主要用 @Mapping 注解进行属性映射定义
package com.xx.mapstruct;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
import org.mapstruct.factory.Mappers;
@Mapper
public interface DemoMap {
DemoMap CAR_MAP = Mappers.getMapper(DemoMap.class);
Target tar(Src src);
// @A
@Mapping(source = "name", target = "name2")
Target2 tar2(Src src);
}
@A:指定属性转换关系
- 测试类
@Test
public void test02() {
Src src = new Src();
src.setName("ppp02");
Target2 tar = DemoMap.CAR_MAP.tar2(src);
System.out.println(tar.getName2());
}
- 测试结果
实现原理
其主要原理是 JAVA AbstractProcessor javac代码编译期处理,自动生成方法对于的代码;JAVA AbstractProcessor自定义开发可以参考我的:JAVA AbstractProcessor javac代码编译期SPI接口
代码上传到 【gitee】 可下载查看
over~