【问题标题】:ModelMapper handling java 8 Optional<MyObjectDto> fields to Optional<MyObject>ModelMapper 处理 java 8 Optional<MyObjectDto> 字段到 Optional<MyObject>
【发布时间】:2015-02-19 10:23:00
【问题描述】:

我一直在应用程序中使用 modelmapper 和 java 8 Optionals,它们工作正常,因为它们是原始类型;直到我将模型对象的一个​​字段更改为可选类型。然后所有的地狱都崩溃了。事实证明,许多库不能很好地处理泛型。

这是结构

public class MyObjectDto
{
   private Optional<MySubObjectDto> mySubObject;
}

public MyObject
{
   privae Optional<MySubjObject> mySubObject;
}

当我尝试将MyObjectDto 映射到MyObject 时,modelmapper 调用

public void setMySubObject(Optional<MySubObject> mySubObject){
   this.mySubObject = mySubObject;
}

Optional&lt;MySubObjectDto&gt;,我不明白这怎么可能(它们之间没有继承)。当然,崩溃很快。现在我已经将我的设置器更改为接受 Dto 类型只是为了生存下来,但这从长远来看是行不通的。有没有更好的方法来解决这个问题,还是我应该制造一个问题?

【问题讨论】:

  • 我认为正在发生的事情是 ModelMapper 不关注 Optional 的通用部分,而只是在两个类中匹配 mySubObject
  • 这也是我的假设。我想知道是否有任何方法可以配置它。例如,在休眠验证中,可以为此类问题注册ValueUnwrappers。

标签: java java-8 optional modelmapper


【解决方案1】:

所以我深入研究了模型映射器代码,并通过查看一些通用实现来完成这项工作:

modelMapper.createTypeMap(Optional.class, Optional.class).setConverter(new OptionalConverter());

public class OptionalConverter implements ConditionalConverter<Optional, Optional> {

  public MatchResult match(Class<?> sourceType, Class<?> destinationType) {
    if (Optional.class.isAssignableFrom(destinationType)) {
      return MatchResult.FULL;
    } else {
      return MatchResult.NONE;
    }
  }

  private Class<?> getElementType(MappingContext<Optional, Optional> context) {
    Mapping mapping = context.getMapping();
    if (mapping instanceof PropertyMapping) {
      PropertyInfo destInfo = ((PropertyMapping) mapping).getLastDestinationProperty();
      Class<?> elementType = TypeResolver.resolveArgument(destInfo.getGenericType(),
                                                          destInfo.getInitialType());
      return elementType == TypeResolver.Unknown.class ? Object.class : elementType;
    } else if (context.getGenericDestinationType() instanceof ParameterizedType) {
      return Types.rawTypeFor(((ParameterizedType) context.getGenericDestinationType()).getActualTypeArguments()[0]);
    }

    return Object.class;
  }

  public Optional<?> convert(MappingContext<Optional, Optional> context) {
    Class<?> optionalType = getElementType(context);
    Optional source = context.getSource();
    Object dest = null;
    if (source != null && source.isPresent()) {
      MappingContext<?, ?> optionalContext = context.create(source.get(), optionalType);
      dest = context.getMappingEngine().map(optionalContext);
    }

    return Optional.ofNullable(dest);
  }

}

【讨论】:

    猜你喜欢
    • 2016-08-19
    • 1970-01-01
    • 2020-07-14
    • 1970-01-01
    • 1970-01-01
    • 2019-07-20
    • 2023-03-31
    • 1970-01-01
    • 2019-06-11
    相关资源
    最近更新 更多