mapstruct应用

一、maven依赖

<dependency>
	<groupId>org.mapstruct</groupId>
	<artifactId>mapstruct</artifactId>
	<version>1.6.0</version>
</dependency>
<dependency>
	<groupId>org.mapstruct</groupId>
	<artifactId>mapstruct-processor</artifactId>
	<version>1.6.0</version>
</dependency>

二、创建对象

@Data
public class UserDto {

    private Long id;
    private String username;
    private String address;
    private String comment;
    private Date birthday;
    private Integer gender;

    private Date createTime;
    private Date updateTime;
    private String createUser;
    private String updateUser;
    private Integer yn;
    private AddressInfo addressInfo;

}

@Getter
@Setter
public class User {

    private String name;
    private Integer gender;
    private Integer age;
    private AddressInfo addressInfo;
    private Map<String, String> extents;
    private Integer isDefault;
    private String birthday;

}

@Data
public class AddressInfo implements Serializable {
    private static final long serialVersionUID = 1398783661313031605L;
    private String provinceNo;
    private String provinceName;
    private String cityNo;
    private String cityName;
    private String countyNo;
    private String countyName;
    private String townNo;
    private String townName;
    private String detailAddress;
	
    /**
     * 地址全路径
     */
    private String fullAddress;
    private AgreementInfo agreementInfo;

}

@Setter
@Getter
public class AgreementInfo implements Serializable {

    private static final long serialVersionUID = -5707331500296054799L;
	
    private String agreementType;
    
}

三、创建转换对象接口

/**
 * 使用spring依赖注入
 *
 * @date 2024/9/13 17:46
 */

@Mapper(componentModel = "spring")
public interface CommonConvertMapper {

    /**
     * 可以通过此实例调用方法,此实例为一个静态常量,调用单例模式
     */
    CommonConvertMapper INSTANCE = Mappers.getMapper(CommonConvertMapper.class);

    /**
     * 用户对象转换
     *
     * @param userDto 入参
     * @return 返回值
     */
    @Mappings({
            // 同级别不同字段名称转换
            @Mapping(source = "username", target = "name"),
            // 将字段映射到成员对象的某个字段上
            @Mapping(source = "address", target = "addressInfo.fullAddress"),
            // 目标字段使用表达式获取源对象的多个属性拼接进行赋值
            @Mapping(target = "addressInfo.provinceName", expression = "java(userDto.getUsername() + '&' + userDto.getAddress())"),
            // 时间格式转换
            @Mapping(source = "birthday", target = "birthday", dateFormat = "yyyy-MM-dd HH:mm:ss"),
            // 目标字段设置常量
            @Mapping(constant = "3", target = "isDefault"),
    })
    User convertUserDtoToUser(UserDto userDto);

    /**
     * 用户对象转换
     *
     * @param map 入参
     * @return 返回值
     */
    @Mappings({
            // 目标字段使用表达式赋值
            @Mapping(target = "createUser", expression = "java(java.util.UUID.randomUUID().toString())"),
            // 时间格式转换
            @Mapping(source = "birthday", target = "birthday", dateFormat = "yyyy-MM-dd HH:mm:ss"),
            // 从MAP中获取多个字段的值拼接并赋值到目标字段上
            @Mapping(target = "comment", expression = "java(map.get(\"username\") + '&' + map.get(\"address\"))"),
            // 从MAP中获取多个字段的值拼接并赋值到目标字段上
            @Mapping(target = "addressInfo", expression = "java(com.alibaba.fastjson.JSON.parseObject(map.get(\"addressInfo\"), com.summer.toolkit.dto.AddressInfo.class))"),
    })
    UserDto convertMapToUserDto(Map<String, String> map);

    /**
     * 用户对象转换,深拷贝地址信息对象
     *
     * @param userDto 入参
     * @return 返回值
     */
    @Mappings({
            // 同级别不同字段名称转换
            @Mapping(source = "username", target = "name"),
            // 将字段映射到成员对象的某个字段上
            @Mapping(target = "addressInfo", expression = "java(convertAddressInfo(userDto.getAddressInfo()))"),
            // 时间格式转换
            @Mapping(source = "birthday", target = "birthday", dateFormat = "yyyy-MM-dd HH:mm:ss"),
            // 目标字段设置常量
            @Mapping(constant = "3", target = "isDefault"),
    })
    User convertUserDtoToUserDeep(UserDto userDto);

    /**
     * 将 AddressInfo 对象转换为指定格式的地址信息。
     *
     * @param addressInfo 待转换的地址信息对象。
     * @return 转换后的地址信息。
     */
    @Mappings({
            @Mapping(target = "agreementInfo", expression = "java(convertAgreementInfo(addressInfo.getAgreementInfo()))"),
    })
    AddressInfo convertAddressInfo(AddressInfo addressInfo);

    /**
     * 将AgreementInfo对象转换为指定格式。
     *
     * @param agreementInfo 需要转换的AgreementInfo对象。
     * @return 转换后的AgreementInfo对象。
     */
    @Mappings({})
    AgreementInfo convertAgreementInfo(AgreementInfo agreementInfo);

}

四、测试方法

@Slf4j
@ExtendWith(MockitoExtension.class)
@EnabledIfEnvironmentVariable(named = "DEBUG", matches = "true")
public class CommonConvertMapperTest {

    /**
     * 结果如下:
     * {"addressInfo":{"detailAddress":"小明&北京市大兴区亦庄经济开发区","fullAddress":"北京市大兴区亦庄经济开发区"},"birthday":"2024-09-13 21:05:43","gender":1,"isDefault":3,"name":"小明"}
     */
    @Test
    public void testConvertUserDtoToUser() {
        UserDto userDto = new UserDto();
        userDto.setUsername("小明");
        userDto.setGender(1);
        userDto.setAddress("北京市大兴区亦庄经济开发区");
        userDto.setBirthday(new Date());
        User user = CommonConvertMapper.INSTANCE.convertUserDtoToUser(userDto);
        log.info("结果:{}", JSON.toJSONString(user));
    }

    /**
     * 结果如下:
     * {"address":"北京市大兴区亦庄经济开发区","birthday":1726232766000,"comment":"小明&北京市大兴区亦庄经济开发区","createUser":"ba2907a8-6ed2-4936-a9e9-2b41cf0a58c0","id":10,"username":"小明"}
     */
    @Test
    public void testConvertMapToUserDto() {
        Map<String, String> map = new HashMap<>(16);
        map.put("id", "10");
        map.put("username", "小明");
        map.put("address", "北京市大兴区亦庄经济开发区");
        map.put("createUser", "小明");
        map.put("birthday", DateUtils.format(new Date()));
        UserDto userDto = CommonConvertMapper.INSTANCE.convertMapToUserDto(map);
        log.info("结果:{}", JSON.toJSONString(userDto));
    }

	@Test
    @DisplayName("对象转换")
    @EnabledOnOs(OS.WINDOWS)
    public void testConvertUserDtoToUserDeep() {
        UserDto userDto = new UserDto();
        userDto.setUsername("小明");
        userDto.setGender(1);
        userDto.setAddress("北京市大兴区亦庄经济开发区");
        userDto.setBirthday(new Date());
        userDto.setId(1L);

        AddressInfo addressInfo = new AddressInfo();
        addressInfo.setDetailAddress("北京市大兴区亦庄经济开发区");
        userDto.setAddressInfo(addressInfo);

        AgreementInfo agreementInfo = new AgreementInfo();
        agreementInfo.setAgreementId("123");
        addressInfo.setAgreementInfo(agreementInfo);

        User user = CommonConvertMapper.INSTANCE.convertUserDtoToUserDeep(userDto);
        user.getAddressInfo().setDetailAddress("河北省");
        log.info("结果:{}", JSON.toJSONString(user));
        log.debug("结果:{}", JSON.toJSONString(user));
    }

}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值