Отображение абстрактного класса с помощью ModelMapper - PullRequest
1 голос
/ 11 июля 2019

У меня такая простая структура классов, в которой есть абстрактные классы и подклассы.Я хочу, чтобы они были сопоставлены со структурой класса назначения с помощью ModelMapper .

Я проверил, и ни одно из решений других вопросов, связанных с отображением абстрактных классов, не решает мою проблему. Этот комментарий и этот комментарий как-то ближе всего к тому, чего я хочу достичь, но в приведенном ниже сценарии все равно не получается.

Сообщение проверки, полученное от ModelMapperэто:

org.modelmapper.MappingException: ModelMapper mapping errors:

1) Failed to instantiate instance of destination 
com.mls.services.MapperTest$DestParent. Ensure that 
com.mls.services.MapperTest$DestParent has a non-private no-argument 
constructor.
...

Что для меня ясно, поскольку класс DestParent является абстрактным и не может быть создан.

Есть ли способ заставить это работать?

Воттестовый исходный код как тестовый пример JUnit.Утверждение внизу терпит неудачу, или проверка вызывает исключение, если я пытаюсь исправить это:

public class MapperTest {

  abstract static class SourceParent {}

  static class SourceSubA extends SourceParent {}

  static class SourceSubB extends SourceParent {}

  abstract static class DestParent {}

  static class DestSubA extends DestParent {}

  static class DestSubB extends DestParent {}

  static class Source {
    SourceParent item;

    public SourceParent getItem() {return item;}
    public void setItem(SourceParent item) {this.item = item;}
  }

  static class Dest {
    DestParent item;

    public DestParent getItem() {return item;}
    public void setItem(DestParent item) {this.item = item;}
  }

  @Test
  public void test() {
    ModelMapper modelMapper = new ModelMapper();

    TypeMap<Source, Dest> typeMap = modelMapper.createTypeMap(Source.class, Dest.class);

    // modelMapper.getConfiguration().setMatchingStrategy(MatchingStrategies.LOOSE);

    modelMapper
        .createTypeMap(SourceSubA.class, DestParent.class)
        .setConverter(
            mappingContext -> modelMapper.map(mappingContext.getSource(), DestSubA.class));

    modelMapper
        .createTypeMap(SourceSubB.class, DestParent.class)
        .setConverter(
            mappingContext -> modelMapper.map(mappingContext.getSource(), DestSubB.class));

    typeMap.addMapping(Source::getItem, Dest::setItem);

    TypeMap<SourceParent, DestParent> itemTypeMap =
        modelMapper.createTypeMap(SourceParent.class, DestParent.class);
    itemTypeMap.include(SourceSubA.class, DestSubA.class);
    itemTypeMap.include(SourceSubB.class, DestSubB.class);

    Source source = new Source();
    source.item = new SourceSubB();
    Dest dest = modelMapper.map(source, Dest.class);
    modelMapper.validate();

    Assert.assertTrue(dest.item instanceof DestSubB);
  }
}
...