ModelMapper转换器完全指南:自定义对象映射的终极教程

张开发
2026/4/18 9:38:39 15 分钟阅读

分享文章

ModelMapper转换器完全指南:自定义对象映射的终极教程
ModelMapper转换器完全指南自定义对象映射的终极教程【免费下载链接】modelmapperIntelligent object mapping项目地址: https://gitcode.com/gh_mirrors/mo/modelmapperModelMapper是一款强大的智能对象映射工具它能够帮助开发者轻松实现不同对象之间的属性转换与映射。本文将为您提供一份全面的ModelMapper转换器使用指南从基础概念到高级技巧助您掌握自定义对象映射的精髓。一、ModelMapper转换器基础1.1 什么是转换器在ModelMapper中转换器Converter是实现对象间属性转换的核心组件。它允许您定义自定义的转换逻辑处理那些无法通过默认映射规则完成的属性转换。1.2 转换器的基本结构一个典型的ModelMapper转换器实现如下public class CollectionToArrayNodeConverter implements ConditionalConverterCollectionObject, ArrayNode { Override public MatchResult match(Class? sourceType, Class? destinationType) { return Collection.class.isAssignableFrom(sourceType) ArrayNode.class.isAssignableFrom(destinationType) ? MatchResult.FULL : MatchResult.NONE; } Override public ArrayNode convert(MappingContextCollectionObject, ArrayNode context) { // 转换逻辑实现 } }这个转换器实现了ConditionalConverter接口包含两个主要方法match()判断该转换器是否适用于给定的源类型和目标类型convert()执行实际的转换逻辑二、创建自定义转换器2.1 实现Converter接口创建自定义转换器最直接的方式是实现Converter接口modelMapper.addConverter(new ConverterCar, AnotherCar() { Override public AnotherCar convert(MappingContextCar, AnotherCar context) { Car source context.getSource(); AnotherCar destination context.getDestination(); // 自定义转换逻辑 destination.setMake(source.getManufacturer()); destination.setYear(source.getProductionYear()); return destination; } });2.2 使用AbstractConverter抽象类对于简单的转换您可以使用AbstractConverter抽象类它提供了更简洁的实现方式modelMapper.addConverter(new AbstractConverterInteger, ComplexObject() { Override protected ComplexObject convert(Integer source) { ComplexObject result new ComplexObject(); result.setValue(source); result.setProcessed(true); return result; } });三、注册和使用转换器3.1 全局注册转换器通过配置将转换器注册为全局转换器使其对所有映射生效modelMapper.getConfiguration().getConverters().add(0, new PrimitiveJsonNodeConverter()); modelMapper.getConfiguration().getConverters().add(0, new ArrayNodeToCollectionConverter());3.2 类型映射专用转换器为特定的类型映射注册转换器modelMapper.createTypeMap(Source.class, Dest.class).setConverter(new ConverterSource, Dest() { Override public Dest convert(MappingContextSource, Dest context) { // 类型特定的转换逻辑 } });3.3 命名类型映射的转换器为命名的类型映射注册转换器modelMapper.createTypeMap(Source.class, Dest.class, converted).setConverter( new ConverterSource, Dest() { Override public Dest convert(MappingContextSource, Dest context) { // 命名类型映射的转换逻辑 } } );四、高级转换器技巧4.1 条件转换器创建只在特定条件下才应用的转换器public class PrimitiveJsonNodeConverter implements ConditionalConverterJsonNode, Object { Override public MatchResult match(Class? sourceType, Class? destinationType) { return (JsonNode.class.isAssignableFrom(sourceType) !ContainerNode.class.isAssignableFrom(sourceType)) ? MatchResult.FULL : MatchResult.NONE; } Override public Object convert(MappingContextJsonNode, Object context) { // 转换逻辑 } }4.2 日期转换器示例创建一个将字符串转换为日期的转换器final ConverterString, Date dateConverter new ConverterString, Date() { Override public Date convert(MappingContextString, Date context) { try { return new SimpleDateFormat(yyyy-MM-dd).parse(context.getSource()); } catch (ParseException e) { return null; } } }; // 使用转换器 modelMapper.createTypeMap(Source.class, Dest.class).addMapping( source(dateString), destination(date), dateConverter );4.3 集合转换器处理集合类型的转换public class ArrayNodeToCollectionConverter implements ConditionalConverterArrayNode, CollectionObject { Override public MatchResult match(Class? sourceType, Class? destinationType) { return Collection.class.isAssignableFrom(destinationType) sourceType.isAssignableFrom(ArrayNode.class) ? MatchResult.FULL : MatchResult.NONE; } Override public CollectionObject convert(MappingContextArrayNode, CollectionObject context) { ArrayNode source context.getSource(); CollectionObject destination context.getDestination(); for (JsonNode node : source) { destination.add(context.getMappingEngine().map(node, Object.class)); } return destination; } }五、实战案例复杂对象转换5.1 支付信息转换器static class PaymentInfoConverter implements ConverterListPaymentInfo, ListObject { private boolean billing; PaymentInfoConverter(boolean billing) { this.billing billing; } Override public ListObject convert(MappingContextListPaymentInfo, ListObject context) { ListPaymentInfo source context.getSource(); ListObject result new ArrayList(); for (PaymentInfo info : source) { if (billing info.isBilling()) { result.add(convertToBillingDTO(info)); } else if (!billing !info.isBilling()) { result.add(convertToShippingDTO(info)); } } return result; } // 辅助转换方法 private Object convertToBillingDTO(PaymentInfo info) { // 转换逻辑 } private Object convertToShippingDTO(PaymentInfo info) { // 转换逻辑 } } // 使用方式 modelMapper.createTypeMap(Order.class, OrderDTO.class) .addMapping(source - source.getPaymentInfos(), destination - destination.setBillingInfos(null), new PaymentInfoConverter(true)) .addMapping(source - source.getPaymentInfos(), destination - destination.setShippingInfos(null), new PaymentInfoConverter(false));六、常见问题与解决方案6.1 转换器优先级当多个转换器都可以应用于某个类型转换时可以通过添加顺序控制优先级// 数字越小优先级越高 modelMapper.getConfiguration().getConverters().add(0, highPriorityConverter); modelMapper.getConfiguration().getConverters().add(1, lowPriorityConverter);6.2 处理空值在转换器中显式处理空值情况Override public Object convert(MappingContextJsonNode, Object context) { JsonNode source context.getSource(); if (source null || source.isNull()) { return null; } // 正常转换逻辑 }6.3 调试转换器使用ModelMapper的错误处理机制调试转换器modelMapper.getConfiguration().setValidationMode(ValidationMode.STRICT); try { // 执行映射 } catch (ValidationException e) { // 处理验证错误 System.out.println(Mapping errors: e.getMessage()); }七、总结ModelMapper转换器为对象映射提供了强大的灵活性和可扩展性。通过本文介绍的方法您可以创建各种类型的转换器处理简单到复杂的对象转换需求。无论是全局转换器还是特定类型映射的转换器都能帮助您轻松实现自定义的对象映射逻辑。掌握ModelMapper转换器的使用将极大提高您的开发效率让对象映射不再成为项目开发的瓶颈。开始尝试创建您的第一个自定义转换器体验智能对象映射的强大功能吧要开始使用ModelMapper您可以克隆仓库git clone https://gitcode.com/gh_mirrors/mo/modelmapper然后根据项目文档进行配置和使用。【免费下载链接】modelmapperIntelligent object mapping项目地址: https://gitcode.com/gh_mirrors/mo/modelmapper创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

更多文章